You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
399 lines
11 KiB
C++
399 lines
11 KiB
C++
/*=========================================================================
|
|
|
|
Program: Visualization Toolkit
|
|
|
|
Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
|
|
All rights reserved.
|
|
See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
|
|
|
|
This software is distributed WITHOUT ANY WARRANTY; without even
|
|
the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
|
|
PURPOSE. See the above copyright notice for more information.
|
|
|
|
=========================================================================*/
|
|
/**
|
|
* @class vtkOpenGLFluidMapper
|
|
* @brief Render fluid from position data (and color, if available)
|
|
*
|
|
* An OpenGL mapper that display fluid volume using a screen space
|
|
* fluid rendering technique. Thanks to Nghia Truong for the algorihtm
|
|
* and initial implementation.
|
|
*/
|
|
|
|
#ifndef vtkOpenGLFluidMapper_h
|
|
#define vtkOpenGLFluidMapper_h
|
|
|
|
#include "vtkAbstractVolumeMapper.h"
|
|
|
|
#include "vtkOpenGLHelper.h" // used for ivars
|
|
#include "vtkRenderingOpenGL2Module.h" // For export macro
|
|
#include "vtkShader.h" // for methods
|
|
#include "vtkSmartPointer.h" // for ivars
|
|
|
|
#include <map> //for methods
|
|
|
|
class vtkMatrix3x3;
|
|
class vtkMatrix4x4;
|
|
class vtkOpenGLFramebufferObject;
|
|
class vtkOpenGLRenderWindow;
|
|
class vtkOpenGLState;
|
|
class vtkOpenGLQuadHelper;
|
|
class vtkOpenGLVertexBufferObjectGroup;
|
|
class vtkPolyData;
|
|
class vtkTextureObject;
|
|
|
|
class VTKRENDERINGOPENGL2_EXPORT vtkOpenGLFluidMapper : public vtkAbstractVolumeMapper
|
|
{
|
|
public:
|
|
static vtkOpenGLFluidMapper* New();
|
|
vtkTypeMacro(vtkOpenGLFluidMapper, vtkAbstractVolumeMapper);
|
|
void PrintSelf(ostream& os, vtkIndent indent) override;
|
|
|
|
//@{
|
|
/**
|
|
* Specify the input data to map.
|
|
*/
|
|
void SetInputData(vtkPolyData* in);
|
|
vtkPolyData* GetInput();
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Turn on/off flag to control whether scalar data is used to color objects.
|
|
*/
|
|
vtkSetMacro(ScalarVisibility, bool);
|
|
vtkGetMacro(ScalarVisibility, bool);
|
|
vtkBooleanMacro(ScalarVisibility, bool);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Set/Get the particle radius, must be explicitly set by user
|
|
* To fuse the gaps between particles and obtain a smooth surface,
|
|
* this parameter need to be slightly larger than the actual particle radius,
|
|
* (particle radius is the half distance between two consecutive particles in
|
|
* regular pattern sampling)
|
|
*/
|
|
vtkSetMacro(ParticleRadius, float);
|
|
vtkGetMacro(ParticleRadius, float);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the number of filter iterations to filter the depth surface
|
|
* This is an optional parameter, default value is 3
|
|
* Usually set this to around 3-5
|
|
* Too many filter iterations will over-smooth the surface
|
|
*/
|
|
vtkSetMacro(SurfaceFilterIterations, uint32_t);
|
|
vtkGetMacro(SurfaceFilterIterations, uint32_t);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the number of filter iterations to filter the volume thickness
|
|
* and particle color This is an optional parameter, default value is 3
|
|
*/
|
|
vtkSetMacro(ThicknessAndVolumeColorFilterIterations, uint32_t);
|
|
vtkGetMacro(ThicknessAndVolumeColorFilterIterations, uint32_t);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the filter radius for smoothing the depth surface
|
|
* This is an optional parameter, default value is 5
|
|
* This is not exactly the radius in pixels,
|
|
* instead it is just a parameter used for computing the actual filter
|
|
* radius in the screen space filtering
|
|
*/
|
|
vtkSetMacro(SurfaceFilterRadius, uint32_t);
|
|
vtkGetMacro(SurfaceFilterRadius, uint32_t);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the filter radius to filter the volume thickness and particle
|
|
* color This is an optional parameter, default value is 10 (pixels)
|
|
*/
|
|
vtkSetMacro(ThicknessAndVolumeColorFilterRadius, float);
|
|
vtkGetMacro(ThicknessAndVolumeColorFilterRadius, float);
|
|
//@}
|
|
|
|
/**
|
|
* Filter method to filter the depth buffer
|
|
*/
|
|
enum FluidSurfaceFilterMethod
|
|
{
|
|
BilateralGaussian = 0,
|
|
NarrowRange,
|
|
// New filter method can be added here,
|
|
NumFilterMethods
|
|
};
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the filter method for filtering fluid surface
|
|
*/
|
|
vtkSetMacro(SurfaceFilterMethod, vtkOpenGLFluidMapper::FluidSurfaceFilterMethod);
|
|
vtkGetMacro(SurfaceFilterMethod, vtkOpenGLFluidMapper::FluidSurfaceFilterMethod);
|
|
//@}
|
|
|
|
/**
|
|
* Optional parameters, exclusively for narrow range filter
|
|
* The first parameter is to control smoothing between surface depth values
|
|
* The second parameter is to control curvature of the surface edges
|
|
*/
|
|
void SetNarrowRangeFilterParameters(float lambda, float mu)
|
|
{
|
|
this->NRFilterLambda = lambda;
|
|
this->NRFilterMu = mu;
|
|
}
|
|
|
|
/**
|
|
* Optional parameters, exclusively for bilateral gaussian filter
|
|
* The parameter is for controlling smoothing between surface depth values
|
|
*/
|
|
void SetBilateralGaussianFilterParameter(float sigmaDepth)
|
|
{
|
|
this->BiGaussFilterSigmaDepth = sigmaDepth;
|
|
}
|
|
|
|
/**
|
|
* Display mode for the fluid, default value is TransparentFluidVolume
|
|
*/
|
|
enum FluidDisplayMode
|
|
{
|
|
UnfilteredOpaqueSurface = 0,
|
|
FilteredOpaqueSurface,
|
|
UnfilteredSurfaceNormal,
|
|
FilteredSurfaceNormal,
|
|
TransparentFluidVolume,
|
|
NumDisplayModes
|
|
};
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the display mode
|
|
*/
|
|
vtkSetMacro(DisplayMode, vtkOpenGLFluidMapper::FluidDisplayMode);
|
|
vtkGetMacro(DisplayMode, vtkOpenGLFluidMapper::FluidDisplayMode);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the fluid attenuation color
|
|
* (color that will be absorpted exponentially when going through the fluid
|
|
* volume)
|
|
*/
|
|
vtkSetVector3Macro(AttenuationColor, float);
|
|
vtkGetVector3Macro(AttenuationColor, float);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the fluid surface color if rendered in opaque surface mode
|
|
* without particle color
|
|
*/
|
|
vtkSetVector3Macro(OpaqueColor, float);
|
|
vtkGetVector3Macro(OpaqueColor, float);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the power value for particle color if input data has particle
|
|
* color Default value is 0.1, and can be set to any non-negative number The
|
|
* particle color is then recomputed as newColor = pow(oldColor, power) *
|
|
* scale
|
|
*/
|
|
vtkSetMacro(ParticleColorPower, float);
|
|
vtkGetMacro(ParticleColorPower, float);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the scale value for particle color if input data has particle
|
|
* color Default value is 1.0, and can be set to any non-negative number The
|
|
* particle color is then recomputed as newColor = pow(oldColor, power) *
|
|
* scale
|
|
*/
|
|
vtkSetMacro(ParticleColorScale, float);
|
|
vtkGetMacro(ParticleColorScale, float);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the fluid volume attenuation scale, which will be multiplied
|
|
* with attennuation color Default value is 1.0, and can be set to any
|
|
* non-negative number The larger attennuation scale, the darker fluid
|
|
* color
|
|
*/
|
|
vtkSetMacro(AttenuationScale, float);
|
|
vtkGetMacro(AttenuationScale, float);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the fluid surface additional reflection scale This value is in
|
|
* [0, 1], which 0 means using the reflection color computed from fresnel
|
|
* equation, and 1 means using reflection color as [1, 1, 1] Default value
|
|
* is 0
|
|
*/
|
|
vtkSetMacro(AdditionalReflection, float);
|
|
vtkGetMacro(AdditionalReflection, float);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the scale value for refraction This is needed for tweak
|
|
* refraction of volumes with different size scales For example, fluid
|
|
* volume having diameter of 100.0 will refract light much more than
|
|
* volume with diameter 1.0 This value is in [0, 1], default value is 1.0
|
|
*/
|
|
vtkSetMacro(RefractionScale, float);
|
|
vtkGetMacro(RefractionScale, float);
|
|
//@}
|
|
|
|
//@{
|
|
/**
|
|
* Get/Set the fluid refraction index. The default value is 1.33 (water)
|
|
*/
|
|
vtkSetMacro(RefractiveIndex, float);
|
|
vtkGetMacro(RefractiveIndex, float);
|
|
//@}
|
|
|
|
/**
|
|
* This calls RenderPiece
|
|
*/
|
|
void Render(vtkRenderer* ren, vtkVolume* vol) override;
|
|
|
|
/**
|
|
* Release graphics resources and ask components to release their own
|
|
* resources.
|
|
* \pre w_exists: w!=0
|
|
*/
|
|
void ReleaseGraphicsResources(vtkWindow* w) override;
|
|
|
|
protected:
|
|
vtkOpenGLFluidMapper();
|
|
~vtkOpenGLFluidMapper() override;
|
|
|
|
/**
|
|
* Perform string replacements on the shader templates
|
|
*/
|
|
void UpdateDepthThicknessColorShaders(
|
|
vtkOpenGLHelper& glHelper, vtkRenderer* renderer, vtkVolume* vol);
|
|
|
|
/**
|
|
* Set the shader parameters related to the actor/mapper/camera
|
|
*/
|
|
void SetDepthThicknessColorShaderParameters(
|
|
vtkOpenGLHelper& glHelper, vtkRenderer* renderer, vtkVolume* vol);
|
|
|
|
/**
|
|
* Setup the texture buffers
|
|
*/
|
|
void SetupBuffers(vtkOpenGLRenderWindow* const renderWindow);
|
|
|
|
/**
|
|
* Render the fluid particles
|
|
*/
|
|
void RenderParticles(vtkRenderer* renderer, vtkVolume* vol);
|
|
|
|
// Public parameters, their usage are stated at their Get/Set functions
|
|
// ======>>>>>
|
|
float ParticleRadius = 1.0f;
|
|
|
|
FluidSurfaceFilterMethod SurfaceFilterMethod = FluidSurfaceFilterMethod::NarrowRange;
|
|
uint32_t SurfaceFilterIterations = 3u;
|
|
uint32_t SurfaceFilterRadius = 5u;
|
|
float NRFilterLambda = 10.0f;
|
|
float NRFilterMu = 1.0f;
|
|
float BiGaussFilterSigmaDepth = 10.0f;
|
|
|
|
uint32_t ThicknessAndVolumeColorFilterIterations = 3u;
|
|
uint32_t ThicknessAndVolumeColorFilterRadius = 10u;
|
|
|
|
FluidDisplayMode DisplayMode = FluidDisplayMode::TransparentFluidVolume;
|
|
|
|
float OpaqueColor[3]{ 0.0f, 0.0f, 0.95f };
|
|
float AttenuationColor[3]{ 0.5f, 0.2f, 0.05f };
|
|
float ParticleColorPower = 0.1f;
|
|
float ParticleColorScale = 1.0f;
|
|
float AttenuationScale = 1.0f;
|
|
float AdditionalReflection = 0.0f;
|
|
float RefractionScale = 1.0f;
|
|
float RefractiveIndex = 1.33f;
|
|
|
|
bool ScalarVisibility = false;
|
|
bool InDepthPass = true;
|
|
|
|
// Private parameters ======>>>>>
|
|
|
|
// Indicate that the input data has a color buffer
|
|
bool HasVertexColor = false;
|
|
|
|
// Cache viewport dimensions
|
|
int ViewportX;
|
|
int ViewportY;
|
|
int ViewportWidth;
|
|
int ViewportHeight;
|
|
|
|
// Cache camera parameters
|
|
vtkMatrix4x4* CamWCVC;
|
|
vtkMatrix3x3* CamInvertedNorms;
|
|
vtkMatrix4x4* CamVCDC;
|
|
vtkMatrix4x4* CamWCDC;
|
|
vtkMatrix4x4* CamDCVC;
|
|
vtkTypeBool CamParallelProjection;
|
|
|
|
// Frame buffers
|
|
vtkSmartPointer<vtkOpenGLFramebufferObject> FBFluidEyeZ;
|
|
vtkSmartPointer<vtkOpenGLFramebufferObject> FBThickness;
|
|
vtkSmartPointer<vtkOpenGLFramebufferObject> FBFilterThickness;
|
|
vtkSmartPointer<vtkOpenGLFramebufferObject> FBCompNormal;
|
|
vtkSmartPointer<vtkOpenGLFramebufferObject> FBFilterDepth;
|
|
|
|
// Screen quad render
|
|
vtkOpenGLQuadHelper* QuadFluidDepthFilter[NumFilterMethods]{ nullptr, nullptr };
|
|
vtkOpenGLQuadHelper* QuadThicknessFilter = nullptr;
|
|
vtkOpenGLQuadHelper* QuadFluidNormal = nullptr;
|
|
vtkOpenGLQuadHelper* QuadFinalBlend = nullptr;
|
|
|
|
// The VBO and its layout for rendering particles
|
|
vtkSmartPointer<vtkOpenGLVertexBufferObjectGroup> VBOs;
|
|
vtkTimeStamp VBOBuildTime; // When was the OpenGL VBO updated?
|
|
vtkOpenGLHelper GLHelperDepthThickness;
|
|
|
|
// Texture buffers
|
|
enum TextureBuffers
|
|
{
|
|
OpaqueZ = 0,
|
|
OpaqueRGBA,
|
|
FluidZ,
|
|
FluidEyeZ,
|
|
SmoothedFluidEyeZ,
|
|
FluidThickness,
|
|
SmoothedFluidThickness,
|
|
FluidNormal,
|
|
NumTexBuffers
|
|
};
|
|
|
|
// These are optional texture buffers
|
|
enum OptionalTextureBuffers
|
|
{
|
|
Color = 0,
|
|
SmoothedColor,
|
|
NumOptionalTexBuffers
|
|
};
|
|
|
|
vtkTextureObject* TexBuffer[NumTexBuffers];
|
|
vtkTextureObject* OptionalTexBuffer[NumOptionalTexBuffers];
|
|
vtkMatrix4x4* TempMatrix4;
|
|
|
|
private:
|
|
vtkOpenGLFluidMapper(const vtkOpenGLFluidMapper&) = delete;
|
|
void operator=(const vtkOpenGLFluidMapper&) = delete;
|
|
};
|
|
|
|
#endif
|