diff --git a/include/osgVolume/MultipassTechnique b/include/osgVolume/MultipassTechnique index 8c0ee367e..5fa14441b 100644 --- a/include/osgVolume/MultipassTechnique +++ b/include/osgVolume/MultipassTechnique @@ -73,7 +73,8 @@ class OSGVOLUME_EXPORT MultipassTechnique : public VolumeTechnique osg::ref_ptr backFaceDepthTexture; osg::ref_ptr backFaceRttCamera; - osg::ref_ptr texgenUniform; + osg::ref_ptr eyeToTileUniform; + osg::ref_ptr tileToImageUniform; }; /** Called from VolumeScene to create the TileData container when a multi-pass technique is being used. diff --git a/src/osgVolume/MultipassTechnique.cpp b/src/osgVolume/MultipassTechnique.cpp index db0d92556..392ebc640 100644 --- a/src/osgVolume/MultipassTechnique.cpp +++ b/src/osgVolume/MultipassTechnique.cpp @@ -199,6 +199,12 @@ MultipassTechnique::MultipassTileData::MultipassTileData(osgUtil::CullVisitor* c stateset = new osg::StateSet; + eyeToTileUniform = new osg::Uniform("eyeToTile",osg::Matrixf()); + stateset->addUniform(eyeToTileUniform.get()); + + tileToImageUniform = new osg::Uniform("tileToImage",osg::Matrixf()); + stateset->addUniform(tileToImageUniform.get()); + switch(currentRenderingMode) { case(MultipassTechnique::CUBE): @@ -206,8 +212,6 @@ MultipassTechnique::MultipassTileData::MultipassTileData(osgUtil::CullVisitor* c // no need to set up RTT Cameras; OSG_NOTICE<<"Setting up MultipassTileData for CUBE rendering"<addUniform(texgenUniform.get()); break; } case(MultipassTechnique::HULL): @@ -218,10 +222,7 @@ MultipassTechnique::MultipassTileData::MultipassTileData(osgUtil::CullVisitor* c frontFaceRttCamera->setCullCallback(new RTTCameraCullCallback(this, mpt)); frontFaceRttCamera->getOrCreateStateSet()->setAttributeAndModes(new osg::CullFace(osg::CullFace::BACK), osg::StateAttribute::ON|osg::StateAttribute::OVERRIDE); - texgenUniform = new osg::Uniform("texgen",osg::Matrixf()); - stateset->setTextureAttribute(2, frontFaceDepthTexture.get(), osg::StateAttribute::ON|osg::StateAttribute::OVERRIDE); - stateset->addUniform(texgenUniform.get()); break; } case(MultipassTechnique::CUBE_AND_HULL): @@ -237,11 +238,8 @@ MultipassTechnique::MultipassTileData::MultipassTileData(osgUtil::CullVisitor* c backFaceRttCamera->setCullCallback(new RTTCameraCullCallback(this, mpt)); backFaceRttCamera->getOrCreateStateSet()->setAttributeAndModes(new osg::CullFace(osg::CullFace::FRONT), osg::StateAttribute::ON|osg::StateAttribute::OVERRIDE); - texgenUniform = new osg::Uniform("texgen",osg::Matrixf()); - stateset->setTextureAttribute(2, frontFaceDepthTexture.get(), osg::StateAttribute::ON|osg::StateAttribute::OVERRIDE); stateset->setTextureAttribute(3, backFaceDepthTexture.get(), osg::StateAttribute::ON|osg::StateAttribute::OVERRIDE); - stateset->addUniform(texgenUniform.get()); break; } } @@ -1056,13 +1054,27 @@ void MultipassTechnique::cull(osgUtil::CullVisitor* cv) if (vs) { MultipassTileData* tileData = dynamic_cast(vs->getTileData(cv, getVolumeTile())); - if (tileData && tileData->texgenUniform.valid()) + if (tileData) { + Locator* tileLocator = _volumeTile->getLocator(); + osg::Matrixd tileToEye = tileLocator->getTransform() * (*(cv->getModelViewMatrix())); + osg::Matrixd eyeToTile; + eyeToTile.invert(tileToEye); + + tileData->eyeToTileUniform->set(osg::Matrixf(eyeToTile)); + Locator* layerLocator = _volumeTile->getLayer()->getLocator(); - osg::Matrix imv = layerLocator->getTransform() * (*(cv->getModelViewMatrix())); - osg::Matrix inverse_imv; - inverse_imv.invert(imv); - tileData->texgenUniform->set(osg::Matrixf(inverse_imv)); + if (tileLocator==layerLocator) + { + tileData->tileToImageUniform->set(osg::Matrixf::identity()); + } + else + { + osg::Matrixd tileToImage(tileLocator->getTransform() * osg::Matrixd::inverse(layerLocator->getTransform())); + tileData->tileToImageUniform->set(osg::Matrixf(tileToImage)); + } + + // OSG_NOTICE<<"Updating texgen"<setValue(sampleRatio); } if (_updateSampleDensity && cpv._sampleRatioWhenMovingProperty.valid()) { - float sampleRatio = v2*4; + float sampleRatio = (1.0-v2)*20.0; OSG_NOTICE<<"Setting sample ratio to "<setValue(sampleRatio); } diff --git a/src/osgVolume/Shaders/volume_accumulateSamples_iso_tf_frag.cpp b/src/osgVolume/Shaders/volume_accumulateSamples_iso_tf_frag.cpp index 3c9c86a9f..2323bb947 100644 --- a/src/osgVolume/Shaders/volume_accumulateSamples_iso_tf_frag.cpp +++ b/src/osgVolume/Shaders/volume_accumulateSamples_iso_tf_frag.cpp @@ -5,7 +5,7 @@ char volume_accumulateSamples_iso_tf_frag[] = "#version 110\n" "uniform sampler1D tfTexture;\n" "uniform float tfScale;\n" "uniform float tfOffset;\n" - "\n" + "uniform float TransparencyValue;\n" "uniform float IsoSurfaceValue;\n" "\n" "varying vec3 lightDirection;\n" @@ -53,6 +53,7 @@ char volume_accumulateSamples_iso_tf_frag[] = "#version 110\n" " color.g *= lightScale;\n" " color.b *= lightScale;\n" " }\n" + " fragColor.a = clamp(fragColor.a*Transparency, 0.0, 1.0);\n" " return color;\n" " }\n" "\n" diff --git a/src/osgVolume/Shaders/volume_accumulateSamples_lit_tf_frag.cpp b/src/osgVolume/Shaders/volume_accumulateSamples_lit_tf_frag.cpp index 928c790bc..ef8e93529 100644 --- a/src/osgVolume/Shaders/volume_accumulateSamples_lit_tf_frag.cpp +++ b/src/osgVolume/Shaders/volume_accumulateSamples_lit_tf_frag.cpp @@ -5,6 +5,7 @@ char volume_accumulateSamples_lit_tf_frag[] = "#version 110\n" "uniform sampler1D tfTexture;\n" "uniform float tfScale;\n" "uniform float tfOffset;\n" + "uniform float TransparencyValue;\n" "\n" "uniform float AlphaFuncValue;\n" "\n" @@ -12,12 +13,22 @@ char volume_accumulateSamples_lit_tf_frag[] = "#version 110\n" "\n" "vec4 accumulateSamples(vec4 fragColor, vec3 ts, vec3 te, vec3 dt, float scale, float cutoff, int num_iterations)\n" "{\n" - " vec3 texcoord = te.xyz;\n" "\n" " float normalSampleDistance = length(dt);\n" " vec3 deltaX = vec3(normalSampleDistance, 0.0, 0.0);\n" " vec3 deltaY = vec3(0.0, normalSampleDistance, 0.0);\n" " vec3 deltaZ = vec3(0.0, 0.0, normalSampleDistance);\n" + " vec3 texcoord = te.xyz;\n" + "\n" + " // scale = mix(scale, 1.0, 1.0);\n" + " //scale = mix(scale, 1.0, 0.75);\n" + "\n" + " // scale = 4.0;\n" + " if (scale>=1.0)\n" + " {\n" + " return vec4(1.0,1.0,1.0,1.0);\n" + " scale = 1.0;\n" + " }\n" "\n" " while(num_iterations>0 && fragColor.a0) fragColor.a = 1.0;\n" + " if (fragColor.wmax_a)\n" " {\n" " float v = a * tfScale + tfOffset;\n" - " fragColor = texture1D( tfTexture, v);\n" - " max_a = a;\n" + " vec4 color = texture1D( tfTexture, v);\n" + " if (color.a>AlphaFuncValue)\n" + " {\n" + " fragColor = color;\n" + " max_a = a;\n" + " }\n" " }\n" "\n" " texcoord += dt;\n" @@ -27,6 +33,8 @@ char volume_accumulateSamples_mip_tf_frag[] = "#version 110\n" " --num_iterations;\n" " }\n" "\n" + " fragColor.a *= TransparencyValue;\n" + "\n" " return fragColor;\n" "}\n" "\n"; diff --git a/src/osgVolume/Shaders/volume_accumulateSamples_standard_tf_frag.cpp b/src/osgVolume/Shaders/volume_accumulateSamples_standard_tf_frag.cpp index b5a56fae9..7ad477434 100644 --- a/src/osgVolume/Shaders/volume_accumulateSamples_standard_tf_frag.cpp +++ b/src/osgVolume/Shaders/volume_accumulateSamples_standard_tf_frag.cpp @@ -1,28 +1,32 @@ char volume_accumulateSamples_standard_tf_frag[] = "#version 110\n" "\n" "uniform sampler3D volumeTexture;\n" - "\n" "uniform sampler1D tfTexture;\n" + "\n" "uniform float tfScale;\n" "uniform float tfOffset;\n" - "\n" + "uniform float TransparencyValue;\n" "uniform float AlphaFuncValue;\n" "\n" "vec4 accumulateSamples(vec4 fragColor, vec3 ts, vec3 te, vec3 dt, float scale, float cutoff, int num_iterations)\n" "{\n" " vec3 texcoord = te.xyz;\n" "\n" - " while(num_iterations>0 && fragColor.a0 && transmittance>=t_cutoff)\n" " {\n" " float a = texture3D( volumeTexture, texcoord).a;\n" " float v = a * tfScale + tfOffset;\n" " vec4 color = texture1D( tfTexture, v);\n" "\n" - " if (a>AlphaFuncValue)\n" + " if (a>=AlphaFuncValue)\n" " {\n" - " float r = color.a * ((1.0-fragColor.a)*scale);\n" + " float ca = clamp(color.a*TransparencyValue, 0.0, 1.0);\n" + " float new_transmitance = transmittance*pow(1.0-ca, scale);\n" + " float r = transmittance-new_transmitance;\n" " fragColor.rgb += color.rgb*r;\n" - " fragColor.a += r;\n" + " transmittance = new_transmitance;\n" " }\n" "\n" " texcoord += dt;\n" @@ -30,8 +34,8 @@ char volume_accumulateSamples_standard_tf_frag[] = "#version 110\n" " --num_iterations;\n" " }\n" "\n" + " fragColor.a = clamp(1.0-transmittance, 0.0, 1.0);\n" " if (num_iterations>0) fragColor.a = 1.0;\n" - " if (fragColor.a>1.0) fragColor.a = 1.0;\n" "\n" " return fragColor;\n" "}\n" diff --git a/src/osgVolume/Shaders/volume_compute_ray_color_frag.cpp b/src/osgVolume/Shaders/volume_compute_ray_color_frag.cpp index b463e8b3f..40b12b860 100644 --- a/src/osgVolume/Shaders/volume_compute_ray_color_frag.cpp +++ b/src/osgVolume/Shaders/volume_compute_ray_color_frag.cpp @@ -3,10 +3,10 @@ char volume_compute_ray_color_frag[] = "#version 110\n" "uniform vec4 viewportDimensions;\n" "uniform sampler3D volumeTexture;\n" "uniform vec3 volumeCellSize;\n" - "\n" + "uniform mat4 tileToImage;\n" "uniform float SampleRatioValue;\n" - "uniform float TransparencyValue;\n" - "varying mat4 texgen_withProjectionMatrixInverse;\n" + "\n" + "varying mat4 texgen_eyeToTile;\n" "\n" "// forward declare, probided by volume_accumulateSamples*.frag shaders\n" "vec4 accumulateSamples(vec4 fragColor, vec3 ts, vec3 te, vec3 dt, float scale, float cutoff, int num_iterations);\n" @@ -30,7 +30,6 @@ char volume_compute_ray_color_frag[] = "#version 110\n" " if (num_iterations>max_iterations)\n" " {\n" " num_iterations = max_iterations;\n" - " baseColor.r = 0.0;\n" " }\n" "\n" " // traverse from front to back\n" @@ -38,11 +37,9 @@ char volume_compute_ray_color_frag[] = "#version 110\n" " float stepLength = length(deltaTexCoord);\n" "\n" " //float scale = 0.5/sampleRatio;\n" - " float scale = stepLength/length(volumeCellSize);\n" + " float scale = 1.73*stepLength/length(volumeCellSize);\n" " if (scale>1.0) scale = 1.0;\n" "\n" - " scale *= TransparencyValue;\n" - "\n" " float cutoff = 1.0-1.0/256.0;\n" "\n" " fragColor = accumulateSamples(fragColor, ts, te, deltaTexCoord, scale, cutoff, num_iterations);\n" @@ -115,8 +112,22 @@ char volume_compute_ray_color_frag[] = "#version 110\n" " vec4 start_clip = vec4((px/viewportWidth)*2.0-1.0, (py/viewportHeight)*2.0-1.0, (depth_start)*2.0-1.0, 1.0);\n" " vec4 end_clip = vec4((px/viewportWidth)*2.0-1.0, (py/viewportHeight)*2.0-1.0, (depth_end)*2.0-1.0, 1.0);\n" "\n" - " vec4 start_texcoord = texgen_withProjectionMatrixInverse * start_clip;\n" - " vec4 end_texcoord = texgen_withProjectionMatrixInverse * end_clip;\n" + " // compute the coords in tile coordinates\n" + " vec4 start_tile = texgen_eyeToTile * start_clip;\n" + " vec4 end_tile = texgen_eyeToTile * end_clip;\n" + "\n" + " start_tile.xyz = start_tile.xyz / start_tile.w;\n" + " start_tile.w = 1.0;\n" + "\n" + " end_tile.xyz = end_tile.xyz / end_tile.w;\n" + " end_tile.w = 1.0;\n" + "\n" + " vec4 clamped_start_tile = vec4(clampToUnitCube(end_tile.xyz, start_tile.xyz), 1.0);\n" + " vec4 clamped_end_tile = vec4(clampToUnitCube(start_tile.xyz, end_tile.xyz), 1.0);\n" + "\n" + " // compute texcoords in image/texture coords\n" + " vec4 start_texcoord = tileToImage * clamped_start_tile;\n" + " vec4 end_texcoord = tileToImage * clamped_end_tile;\n" "\n" " start_texcoord.xyz = start_texcoord.xyz / start_texcoord.w;\n" " start_texcoord.w = 1.0;\n" diff --git a/src/osgVolume/VolumeScene.cpp b/src/osgVolume/VolumeScene.cpp index 3fc66adc5..78a43748b 100644 --- a/src/osgVolume/VolumeScene.cpp +++ b/src/osgVolume/VolumeScene.cpp @@ -405,7 +405,7 @@ void VolumeScene::traverse(osg::NodeVisitor& nv) TileData* tileData = itr->second.get(); if (!tileData || !(tileData->active)) { - OSG_NOTICE<<"Skipping TileData that is inactive : "<