0024402: TKOpenGl - Implement clipping planes in Phong GLSL program
authorduv <duv@opencascade.com>
Thu, 13 Feb 2014 09:06:51 +0000 (13:06 +0400)
committerapn <apn@opencascade.com>
Thu, 13 Feb 2014 10:04:39 +0000 (14:04 +0400)
Limit number of lights (breaks compatibility with old hardware).

src/OpenGl/OpenGl_ShaderManager.cxx
src/OpenGl/OpenGl_ShaderProgram.cxx
src/OpenGl/OpenGl_ShaderProgram.hxx
src/Shaders/Declarations.glsl
src/Shaders/PhongShading.fs
src/Shaders/PhongShading.vs

index d155c00..5660255 100755 (executable)
@@ -509,7 +509,7 @@ void OpenGl_ShaderManager::PushClippingState (const Handle(OpenGl_ShaderProgram)
     return;
   }
 
-  GLuint aPlanesNb = 0;
+  GLint aPlanesNb = 0;
   for (Graphic3d_SequenceOfHClipPlane::Iterator anIter (myContext->Clipping().Planes());
        anIter.More(); anIter.Next())
   {
@@ -526,8 +526,9 @@ void OpenGl_ShaderManager::PushClippingState (const Handle(OpenGl_ShaderProgram)
     return;
   }
 
-  OpenGl_Vec4* anEquations = new OpenGl_Vec4[aPlanesNb];
-  GLint*       aSpaces     = new GLint      [aPlanesNb];
+  const Standard_Size MAX_CLIP_PLANES = 8;
+  OpenGl_Vec4* anEquations = new OpenGl_Vec4[MAX_CLIP_PLANES];
+  GLint*       aSpaces     = new GLint      [MAX_CLIP_PLANES];
   GLuint aPlaneId = 0;
   for (Graphic3d_SequenceOfHClipPlane::Iterator anIter (myContext->Clipping().Planes());
        anIter.More(); anIter.Next())
@@ -546,8 +547,12 @@ void OpenGl_ShaderManager::PushClippingState (const Handle(OpenGl_ShaderProgram)
     aSpaces[aPlaneId] = myContext->Clipping().GetEquationSpace (aPlane);
     ++aPlaneId;
   }
-  theProgram->SetUniform (myContext, aLocEquations, aPlanesNb, anEquations[0].GetData());
-  theProgram->SetUniform (myContext, aLocSpaces,    aPlanesNb, aSpaces);
+
+  theProgram->SetUniform (myContext,
+                          theProgram->GetStateLocation (OpenGl_OCC_CLIP_PLANE_COUNT),
+                          aPlanesNb);
+  theProgram->SetUniform (myContext, aLocEquations, MAX_CLIP_PLANES, anEquations);
+  theProgram->SetUniform (myContext, aLocSpaces,    MAX_CLIP_PLANES, aSpaces);
 
   delete[] anEquations;
   delete[] aSpaces;
index 0bee9c3..61bb58d 100755 (executable)
@@ -47,6 +47,7 @@ Standard_CString OpenGl_ShaderProgram::PredefinedKeywords[] =
 
   "occClipPlaneEquations", // OpenGl_OCC_CLIP_PLANE_EQUATIONS
   "occClipPlaneSpaces",    // OpenGl_OCC_CLIP_PLANE_SPACES
+  "occClipPlaneCount",     // OpenGl_OCC_CLIP_PLANE_COUNT
 
   "occLightSourcesCount",  // OpenGl_OCC_LIGHT_SOURCE_COUNT
   "occLightSourcesTypes",  // OpenGl_OCC_LIGHT_SOURCE_TYPES
index 611d2ed..52c20c0 100755 (executable)
@@ -50,6 +50,7 @@ enum OpenGl_StateVariable
   // OpenGL clip planes state
   OpenGl_OCC_CLIP_PLANE_EQUATIONS,
   OpenGl_OCC_CLIP_PLANE_SPACES,
+  OpenGl_OCC_CLIP_PLANE_COUNT,
 
   // OpenGL light state
   OpenGl_OCC_LIGHT_SOURCE_COUNT,
index 382f106..a20dacf 100644 (file)
@@ -77,3 +77,4 @@ const int OccEquationCoords_World = 1; //!< world-space clipping plane
 //! Parameters of clipping planes
 uniform vec4 occClipPlaneEquations[THE_MAX_CLIP_PLANES];
 uniform int  occClipPlaneSpaces   [THE_MAX_CLIP_PLANES];
+uniform int  occClipPlaneCount;   //!< Total number of clip planes
index 0cb63e2..08df0f0 100755 (executable)
 // Alternatively, this file may be used under the terms of Open CASCADE
 // commercial license or contractual agreement.
 
-varying vec3 View;     //!< Direction to the viewer
-varying vec3 Normal;   //!< Vertex normal in view space
-varying vec4 Position; //!< Vertex position in view space.
+varying vec3 View;          //!< Direction to the viewer
+varying vec3 Normal;        //!< Vertex normal in view space
+varying vec4 Position;      //!< Vertex position in view space.
+varying vec4 PositionWorld; //!< Vertex position in world space
 
 vec3 Ambient;  //!< Ambient  contribution of light sources
 vec3 Diffuse;  //!< Diffuse  contribution of light sources
@@ -172,6 +173,27 @@ vec4 computeLighting (in vec3 theNormal,
 //! Entry point to the Fragment Shader
 void main()
 {
+  // process clipping planes
+  for (int anIndex = 0; anIndex < occClipPlaneCount; ++anIndex)
+  {
+    vec4 aClipEquation = occClipPlaneEquations[anIndex];
+    int  aClipSpace    = occClipPlaneSpaces[anIndex];
+    if (aClipSpace == OccEquationCoords_World)
+    {
+      if (dot (aClipEquation.xyz, PositionWorld.xyz) + aClipEquation.w < 0.0)
+      {
+        discard;
+      }
+    }
+    else if (aClipSpace == OccEquationCoords_View)
+    {
+      if (dot (aClipEquation.xyz, Position.xyz) + aClipEquation.w < 0.0)
+      {
+        discard;
+      }
+    }
+  }
+
   gl_FragColor = computeLighting (normalize (Normal),
                                   normalize (View),
                                   Position);
index ada2d29..4a86a1a 100755 (executable)
 // Alternatively, this file may be used under the terms of Open CASCADE
 // commercial license or contractual agreement.
 
-varying vec3 View;     //!< Direction to the viewer
-varying vec3 Normal;   //!< Vertex normal   in view space
-varying vec4 Position; //!< Vertex position in view space
+varying vec3 View;          //!< Direction to the viewer
+varying vec3 Normal;        //!< Vertex normal in view space
+varying vec4 Position;      //!< Vertex position in view space
+varying vec4 PositionWorld; //!< Vertex position in world space
 
 //! Computes the normal in view space
 vec3 TransformNormal (in vec3 theNormal)
@@ -29,8 +30,9 @@ vec3 TransformNormal (in vec3 theNormal)
 //! Entry point to the Vertex Shader
 void main()
 {
-  Position = occWorldViewMatrix * occModelWorldMatrix * occVertex; // position in the view space
-  Normal   = TransformNormal (occNormal);                          // normal   in the view space
+  PositionWorld = occModelWorldMatrix * occVertex;
+  Position      = occWorldViewMatrix * PositionWorld;
+  Normal        = TransformNormal (occNormal);
 
   // Note: The specified view vector is absolutely correct only for the orthogonal projection.
   // For perspective projection it will be approximate, but it is in good agreement with the OpenGL calculations.