Commit 49c9152b authored by Sebastian Eichelbaum's avatar Sebastian Eichelbaum
Browse files

[CHANGE] - improved tube rendering.

parent b8351def
......@@ -69,7 +69,7 @@ wge_LightIntensityParameter wge_DefaultLightIntensity = wge_LightIntensityParame
*/
wge_LightIntensityParameter wge_DefaultLightIntensityLessDiffuse = wge_LightIntensityParameter(
0.2, // material ambient
0.3, // material diffuse
0.35, // material diffuse
1.0, // material specular
100.0, // material shininess
1.0, // light diffuse
......
......@@ -104,6 +104,7 @@ void WMFiberDisplaySimple::properties()
m_tubeGroup = m_properties->addPropertyGroup( "Tube Rendering", "If true, advanced fake-tube rendering is used." );
m_tubeEnable = m_tubeGroup->addProperty( "Enable Tubes", "If set, fake-tube rendering is used.", false, m_propCondition );
m_tubeRibbon = m_tubeGroup->addProperty( "Ribbon mode", "If set, the tubes look like flat ribbons.", false );
m_tubeZoomable = m_tubeGroup->addProperty( "Zoomable", "If set, fake-tube get thicker when zoomed in. If not set, they always keep the same "
"size in screen-space. This emulates standard OpenGL lines.", true );
m_tubeSize = m_tubeGroup->addProperty( "Width", "The size of the tubes.", 2.0 );
......@@ -164,6 +165,9 @@ void WMFiberDisplaySimple::moduleMain()
m_shader->addPreprocessor( WGEShaderPreprocessor::SPtr(
new WGEShaderPropertyDefineOptions< WPropBool >( m_tubeZoomable, "ZOOMABLE_DISABLED", "ZOOMABLE_ENABLED" ) )
);
m_shader->addPreprocessor( WGEShaderPreprocessor::SPtr(
new WGEShaderPropertyDefineOptions< WPropBool >( m_tubeRibbon, "RIBBON_DISABLED", "RIBBON_ENABLED" ) )
);
osg::ref_ptr< WGEPropertyUniform< WPropDouble > > tubeSizeUniform = new WGEPropertyUniform< WPropDouble >( "u_tubeSize", m_tubeSize );
// get notified about data changes
......
......@@ -163,6 +163,11 @@ private:
*/
WPropBool m_tubeZoomable;
/**
* Creates a ribbon-like appearance.
*/
WPropBool m_tubeRibbon;
/**
* The size. The meaning somehow relates to tubeZoomable. If a tube is zoomable, the size is the smallest size in pixels on screen of totally
* zoomed out.
......
......@@ -28,21 +28,7 @@
#include "WGETextureTools.glsl"
#include "WGEPostprocessing.glsl"
/////////////////////////////////////////////////////////////////////////////
// Varyings
/////////////////////////////////////////////////////////////////////////////
#ifdef CLIPPLANE_ENABLED
/**
* The distance to the plane
*/
varying float dist;
#endif
/**
* The surface normal. Needed for nice lighting.
*/
varying vec3 v_normal;
#include "WMFiberDisplaySimple-varyings.glsl"
/////////////////////////////////////////////////////////////////////////////
// Uniforms
......@@ -78,14 +64,55 @@ void main()
}
#endif
// the depth of the fragment. For lines and flattubes this is the fragments z value. Tubes need to recalculate this
float depth = gl_FragCoord.z;
// this allows modification of surface brightness corresponding to current surface parameter
float colorScaler = 1.0;
// the normal acutally used for lighting
vec3 normal = normalize( v_normal );
// We need to differentiate several cases here: Lines, FlatTubes and Tubes
#ifdef TUBE_ENABLED
#ifdef RIBBON_ENABLED
// colorScaler = 1.0; // surface parameter should have no influence
// normal = v_normal // apply lighting equally on the surface
// depth = gl_FragCoord.z; // as it is a flat ribbon
#else
#ifndef ILLUMINATION_ENABLED
// For tubes, we need to create some "tube-effect" with the surface parameter if lighting is disabled.
// If light is enabled, the corrected normal ensures proper tube-effect.
colorScaler = 1.0 - abs( v_surfaceParam );
#endif
// The normal needs to be adopted too. Use the surface parameter to interpolate along the ortogonal tangent direction using the biNormal.
normal = normalize( mix( normal, normalize( v_biNormal ), abs( v_surfaceParam ) ) );
// Correct fragment depth
// We use the known world-space diameter and move the vertex along the corrected normal using the surface parameter
vec3 v = v_vertex.xyz + normal * v_diameter * ( 1.0 - abs( v_surfaceParam ) );
// apply standard projection:
vec4 vProj = gl_ProjectionMatrix * vec4( v.xyz, 1.0 );
depth = ( 0.5 * vProj.z / vProj.w ) + 0.5;
#endif // RIBBON_ENABLED
#else // !TUBE_ENABLED
// colorScaler = 1.0; // surface parameter should have no influence as lines are 1px thick
// normal = v_normal; // for lines, the normal does not need to be modified
// depth = gl_FragCoord.z; // the vertex is at the correct depth -> fragment too.
#endif // TUBE_ENABLED
// Calculate light finally
#ifdef ILLUMINATION_ENABLED
float light = blinnPhongIlluminationIntensity( wge_DefaultLightIntensityLessDiffuse, normalize( v_normal ) );
float light = blinnPhongIlluminationIntensity( wge_DefaultLightIntensityLessDiffuse, normal );
#else
float light = 1.0;
#endif
wge_FragColor = vec4( vec3( gl_Color.xyz * light ), gl_Color.a );
wge_FragNormal = textureNormalize( v_normal );
gl_FragDepth = gl_FragCoord.z;
// finally set the color and depth
wge_FragColor = vec4( vec3( gl_Color.xyz * light * colorScaler ), gl_Color.a );
wge_FragNormal = textureNormalize( normal );
gl_FragDepth = depth;
}
//---------------------------------------------------------------------------
//
// Project: OpenWalnut ( http://www.openwalnut.org )
//
// Copyright 2009 OpenWalnut Community, BSV@Uni-Leipzig and CNCF@MPI-CBS
// For more information see http://www.openwalnut.org/copying
//
// This file is part of OpenWalnut.
//
// OpenWalnut is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// OpenWalnut is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with OpenWalnut. If not, see <http://www.gnu.org/licenses/>.
//
//---------------------------------------------------------------------------
/////////////////////////////////////////////////////////////////////////////
// Varyings
/////////////////////////////////////////////////////////////////////////////
#ifdef CLIPPLANE_ENABLED
/**
* The distance to the plane
*/
varying float dist;
#endif
/**
* The surface normal. Needed for nice lighting.
*/
varying vec3 v_normal;
/**
* The normal parameterizing the surface in orthogonal tangent direction.
*/
varying vec3 v_biNormal;
/**
* The actual, corrected vertex.
*/
varying vec4 v_vertex;
/**
* The diameter of the tube in world-space.
*/
varying float v_diameter;
/**
* This is the interpolated surface parameter describing the surface orthogonal to the tangent. 0 is the center of the strip and -1 and 1 the
* borders.
*/
varying float v_surfaceParam;
......@@ -24,21 +24,7 @@
#version 120
/////////////////////////////////////////////////////////////////////////////
// Varyings
/////////////////////////////////////////////////////////////////////////////
#ifdef CLIPPLANE_ENABLED
/**
* The distance to the plane
*/
varying float dist;
#endif
/**
* The surface normal. Needed for nice lighting.
*/
varying vec3 v_normal;
#include "WMFiberDisplaySimple-varyings.glsl"
/////////////////////////////////////////////////////////////////////////////
// Uniforms
......@@ -84,7 +70,7 @@ void main()
#endif // CLIPPLANE_ENABLED
// The same accounds for the vertex. Transfer it to world-space.
vec4 vertex = gl_ModelViewMatrix * gl_Vertex;
v_vertex = gl_ModelViewMatrix * gl_Vertex;
#if ( defined ILLUMINATION_ENABLED || defined TUBE_ENABLED )
// Grab the tangent. We have uploaded it normalized in gl_Normal per vertex
......@@ -96,14 +82,15 @@ void main()
// Each vertex on the quad which are on the same position have a texture coordinate to differentiate them. But only if the tube mode is
// active.
float upDownIndicator = gl_MultiTexCoord0.s;
v_surfaceParam = gl_MultiTexCoord0.s;
#ifndef TUBE_ENABLED
upDownIndicator = 1.0;
v_surfaceParam = 1.0;
#endif // !TUBE_ENABLED
// To enforce that each quad's normal points towards the user, we move the two vertex (which are at the same point currently) according to
// the direction stored in gl_MultiTexCoord0
vec3 offset = normalize( upDownIndicator * cross( view, tangent ) );
vec3 offset = normalize( v_surfaceParam * cross( view, tangent ) );
v_biNormal = offset;
#ifdef TUBE_ENABLED
#ifdef ZOOMABLE_ENABLED
......@@ -112,7 +99,7 @@ void main()
float worldScale = length( ( gl_ModelViewMatrix * vec4( 1.0, 1.0, 1.0, 0.0 ) ).xyz );
// worldScale now contains the scaling which is done by ModelView transformation (including the camera).
// With this, we can ensure that our offset (calculated later), which is of unit-length, is scaled acccording to the camera zoom. The
// With this, we can ensure that our offset, which is of unit-length, is scaled acccording to the camera zoom. The
// additional uniform u_tubeSize allows the user to scale the tubes.
// We clamp the value to ensure a minimum width of the quadstrip of 1px on screen:
worldScale = clamp( u_tubeSize * worldScale, 1.0, 1000000.0 );
......@@ -122,7 +109,8 @@ void main()
#endif
// Apply the offset and scale correctly.
vertex.xyz += 0.1 * worldScale * offset;
v_vertex.xyz += 0.1 * worldScale * offset;
v_diameter = 0.1 * worldScale;
#endif // TUBE_ENABLED
// with the tangent and the view vector we got the offset vector. We can noch get the normal using the tangent and the offset.
......@@ -131,7 +119,7 @@ void main()
#endif // ( defined ILLUMINATION_ENABLED || defined TUBE_ENABLED )
// Simply project the vertex afterwards
gl_Position = gl_ProjectionMatrix * vertex;
gl_Position = gl_ProjectionMatrix * v_vertex;
gl_FrontColor = gl_Color;
}
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment