0026676: Visualization, Ray Tracing - correct rendering if stereo pair
[occt.git] / src / OpenGl / OpenGl_View_Raytrace.cxx
index f7bd08b..653e2c2 100644 (file)
 // Alternatively, this file may be used under the terms of Open CASCADE
 // commercial license or contractual agreement.
 
-#include <Graphic3d_TextureParams.hxx>
+#include <OpenGl_View.hxx>
 
-#include <OpenGl_FrameBuffer.hxx>
+#include <Graphic3d_TextureParams.hxx>
 #include <OpenGl_PrimitiveArray.hxx>
 #include <OpenGl_VertexBuffer.hxx>
-#include <OpenGl_View.hxx>
-#include <Graphic3d_GraphicDriver.hxx>
-
 #include <OSD_Protection.hxx>
 #include <OSD_File.hxx>
 
@@ -1216,8 +1213,7 @@ Handle(OpenGl_ShaderProgram) OpenGl_View::initProgram (const Handle(OpenGl_Conte
   }
   else if (theGlContext->caps->glslWarnings)
   {
-    myRaytraceProgram->FetchInfoLog (theGlContext, aLinkLog);
-
+    aProgram->FetchInfoLog (theGlContext, aLinkLog);
     if (!aLinkLog.IsEmpty() && !aLinkLog.IsEqual ("No errors.\n"))
     {
       const TCollection_ExtendedString aMessage = TCollection_ExtendedString (
@@ -1235,7 +1231,7 @@ Handle(OpenGl_ShaderProgram) OpenGl_View::initProgram (const Handle(OpenGl_Conte
 // function : initRaytraceResources
 // purpose  : Initializes OpenGL/GLSL shader programs
 // =======================================================================
-Standard_Boolean OpenGl_View::initRaytraceResources (const Graphic3d_CView& theCView, const Handle(OpenGl_Context)& theGlContext)
+Standard_Boolean OpenGl_View::initRaytraceResources (const Handle(OpenGl_Context)& theGlContext)
 {
   if (myRaytraceInitStatus == OpenGl_RT_FAIL)
   {
@@ -1270,9 +1266,9 @@ Standard_Boolean OpenGl_View::initRaytraceResources (const Graphic3d_CView& theC
       }
     }
 
-    if (theCView.RenderParams.RaytracingDepth != myRaytraceParameters.NbBounces)
+    if (myRenderParams.RaytracingDepth != myRaytraceParameters.NbBounces)
     {
-      myRaytraceParameters.NbBounces = theCView.RenderParams.RaytracingDepth;
+      myRaytraceParameters.NbBounces = myRenderParams.RaytracingDepth;
       aToRebuildShaders = Standard_True;
     }
 
@@ -1282,15 +1278,15 @@ Standard_Boolean OpenGl_View::initRaytraceResources (const Graphic3d_CView& theC
       aToRebuildShaders = Standard_True;
     }
 
-    if (theCView.RenderParams.IsTransparentShadowEnabled != myRaytraceParameters.TransparentShadows)
+    if (myRenderParams.IsTransparentShadowEnabled != myRaytraceParameters.TransparentShadows)
     {
-      myRaytraceParameters.TransparentShadows = theCView.RenderParams.IsTransparentShadowEnabled;
+      myRaytraceParameters.TransparentShadows = myRenderParams.IsTransparentShadowEnabled;
       aToRebuildShaders = Standard_True;
     }
 
-    if (theCView.RenderParams.IsGlobalIlluminationEnabled != myRaytraceParameters.GlobalIllumination)
+    if (myRenderParams.IsGlobalIlluminationEnabled != myRaytraceParameters.GlobalIllumination)
     {
-      myRaytraceParameters.GlobalIllumination = theCView.RenderParams.IsGlobalIlluminationEnabled;
+      myRaytraceParameters.GlobalIllumination = myRenderParams.IsGlobalIlluminationEnabled;
       aToRebuildShaders = Standard_True;
     }
 
@@ -1348,7 +1344,7 @@ Standard_Boolean OpenGl_View::initRaytraceResources (const Graphic3d_CView& theC
       return safeFailBack ("Ray-tracing requires EXT_framebuffer_blit extension", theGlContext);
     }
 
-    myRaytraceParameters.NbBounces = theCView.RenderParams.RaytracingDepth;
+    myRaytraceParameters.NbBounces = myRenderParams.RaytracingDepth;
 
     TCollection_AsciiString aFolder = Graphic3d_ShaderProgram::ShadersFolder();
 
@@ -1658,6 +1654,8 @@ void OpenGl_View::releaseRaytraceResources (const Handle(OpenGl_Context)& theGlC
   nullifyResource (theGlContext, myRaytraceLightSrcTexture);
   nullifyResource (theGlContext, myRaytraceMaterialTexture);
 
+  myRaytraceGeometry.ReleaseResources (theGlContext);
+
   if (myRaytraceScreenQuad.IsValid())
     myRaytraceScreenQuad.Release (theGlContext.operator->());
 }
@@ -1724,17 +1722,13 @@ void OpenGl_View::updateCamera (const OpenGl_Mat4& theOrientation,
 
       aDirect = aDirect - aOrigin;
 
-      GLdouble aInvLen = 1.0 / sqrt (aDirect.x() * aDirect.x() +
-                                     aDirect.y() * aDirect.y() +
-                                     aDirect.z() * aDirect.z());
-
       theOrigins[aOriginIndex++] = OpenGl_Vec3 (static_cast<GLfloat> (aOrigin.x()),
                                                 static_cast<GLfloat> (aOrigin.y()),
                                                 static_cast<GLfloat> (aOrigin.z()));
 
-      theDirects[aDirectIndex++] = OpenGl_Vec3 (static_cast<GLfloat> (aDirect.x() * aInvLen),
-                                                static_cast<GLfloat> (aDirect.y() * aInvLen),
-                                                static_cast<GLfloat> (aDirect.z() * aInvLen));
+      theDirects[aDirectIndex++] = OpenGl_Vec3 (static_cast<GLfloat> (aDirect.x()),
+                                                static_cast<GLfloat> (aDirect.y()),
+                                                static_cast<GLfloat> (aDirect.z()));
     }
   }
 }
@@ -2070,11 +2064,12 @@ Standard_Boolean OpenGl_View::updateRaytraceLightSources (const OpenGl_Mat4& the
 
   myRaytraceGeometry.Ambient = BVH_Vec4f (0.0f, 0.0f, 0.0f, 0.0f);
 
-  for (OpenGl_ListOfLight::Iterator aLightIter (myLights); aLightIter.More(); aLightIter.Next())
+  OpenGl_ListOfLight::Iterator aLightIter (myShadingModel == Graphic3d_TOSM_NONE ? OpenGl_NoShadingLight() : myLights);
+  for (; aLightIter.More(); aLightIter.Next())
   {
     const OpenGl_Light& aLight = aLightIter.Value();
 
-    if (aLight.Type == Visual3d_TOLS_AMBIENT)
+    if (aLight.Type == Graphic3d_TOLS_AMBIENT)
     {
       myRaytraceGeometry.Ambient += BVH_Vec4f (aLight.Color.r() * aLight.Intensity,
                                                aLight.Color.g() * aLight.Intensity,
@@ -2093,7 +2088,7 @@ Standard_Boolean OpenGl_View::updateRaytraceLightSources (const OpenGl_Mat4& the
                          -aLight.Direction.z(),
                          0.0f);
 
-    if (aLight.Type != Visual3d_TOLS_DIRECTIONAL)
+    if (aLight.Type != Graphic3d_TOLS_DIRECTIONAL)
     {
       aPosition = BVH_Vec4f (aLight.Position.x(),
                              aLight.Position.y(),
@@ -2167,7 +2162,7 @@ Standard_Boolean OpenGl_View::updateRaytraceEnvironmentMap (const Handle(OpenGl_
     {
       aResult &= theGlContext->BindProgram (aProgram);
 
-      if (!myTextureEnv.IsNull() && mySurfaceDetail != Visual3d_TOD_NONE)
+      if (!myTextureEnv.IsNull() && mySurfaceDetail != Graphic3d_TOD_NONE)
       {
         myTextureEnv->Bind (theGlContext,
           GL_TEXTURE0 + OpenGl_RT_EnvironmentMapTexture);
@@ -2194,8 +2189,7 @@ Standard_Boolean OpenGl_View::updateRaytraceEnvironmentMap (const Handle(OpenGl_
 // function : setUniformState
 // purpose  : Sets uniform state for the given ray-tracing shader program
 // =======================================================================
-Standard_Boolean OpenGl_View::setUniformState (const Graphic3d_CView&        theCView,
-                                               const OpenGl_Vec3*            theOrigins,
+Standard_Boolean OpenGl_View::setUniformState (const OpenGl_Vec3*            theOrigins,
                                                const OpenGl_Vec3*            theDirects,
                                                const OpenGl_Mat4&            theUnviewMat,
                                                const Standard_Integer        theProgramId,
@@ -2244,21 +2238,23 @@ Standard_Boolean OpenGl_View::setUniformState (const Graphic3d_CView&        the
 
   // Set run-time rendering options
   theProgram->SetUniform (theGlContext,
-    myUniformLocations[theProgramId][OpenGl_RT_uShadowsEnabled], theCView.RenderParams.IsShadowEnabled ?  1 : 0);
+    myUniformLocations[theProgramId][OpenGl_RT_uShadowsEnabled], myRenderParams.IsShadowEnabled ?  1 : 0);
   theProgram->SetUniform (theGlContext,
-    myUniformLocations[theProgramId][OpenGl_RT_uReflectEnabled], theCView.RenderParams.IsReflectionEnabled ?  1 : 0);
+    myUniformLocations[theProgramId][OpenGl_RT_uReflectEnabled], myRenderParams.IsReflectionEnabled ?  1 : 0);
 
-  if (theCView.RenderParams.IsGlobalIlluminationEnabled)
+  if (myRenderParams.IsGlobalIlluminationEnabled)
   {
     theProgram->SetUniform (theGlContext,
-      myUniformLocations[theProgramId][OpenGl_RT_uBlockedRngEnabled], theCView.RenderParams.CoherentPathTracingMode ?  1 : 0);
+      myUniformLocations[theProgramId][OpenGl_RT_uBlockedRngEnabled], myRenderParams.CoherentPathTracingMode ?  1 : 0);
   }
 
   // Set array of 64-bit texture handles
   if (theGlContext->arbTexBindless != NULL && myRaytraceGeometry.HasTextures())
   {
+    const std::vector<GLuint64>& aTextures = myRaytraceGeometry.TextureHandles();
+
     theProgram->SetUniform (theGlContext, myUniformLocations[theProgramId][OpenGl_RT_uTexSamplersArray],
-      static_cast<GLsizei> (myRaytraceGeometry.TextureHandles().size()), &myRaytraceGeometry.TextureHandles()[0]);
+      static_cast<GLsizei> (aTextures.size()), (OpenGl_Vec2u* )&aTextures.front());
   }
 
   // Set background colors (only gradient background supported)
@@ -2272,9 +2268,9 @@ Standard_Boolean OpenGl_View::setUniformState (const Graphic3d_CView&        the
   }
   else
   {
-    const OpenGl_Vec4 aBackColor (theCView.DefWindow.Background.r,
-                                  theCView.DefWindow.Background.g,
-                                  theCView.DefWindow.Background.b,
+    const OpenGl_Vec4 aBackColor (myBgColor.rgb[0],
+                                  myBgColor.rgb[1],
+                                  myBgColor.rgb[2],
                                   1.0f);
     theProgram->SetUniform (theGlContext,
       myUniformLocations[theProgramId][OpenGl_RT_uBackColorTop], aBackColor);
@@ -2283,7 +2279,7 @@ Standard_Boolean OpenGl_View::setUniformState (const Graphic3d_CView&        the
   }
 
   theProgram->SetUniform (theGlContext,
-    myUniformLocations[theProgramId][OpenGl_RT_uSphereMapForBack], theCView.RenderParams.UseEnvironmentMapBackground ?  1 : 0);
+    myUniformLocations[theProgramId][OpenGl_RT_uSphereMapForBack], myRenderParams.UseEnvironmentMapBackground ?  1 : 0);
 
   return Standard_True;
 }
@@ -2342,8 +2338,7 @@ void OpenGl_View::unbindRaytraceTextures (const Handle(OpenGl_Context)& theGlCon
 // function : runRaytraceShaders
 // purpose  : Runs ray-tracing shader programs
 // =======================================================================
-Standard_Boolean OpenGl_View::runRaytraceShaders (const Graphic3d_CView&        theCView,
-                                                  const Standard_Integer        theSizeX,
+Standard_Boolean OpenGl_View::runRaytraceShaders (const Standard_Integer        theSizeX,
                                                   const Standard_Integer        theSizeY,
                                                   const OpenGl_Vec3*            theOrigins,
                                                   const OpenGl_Vec3*            theDirects,
@@ -2378,7 +2373,7 @@ Standard_Boolean OpenGl_View::runRaytraceShaders (const Graphic3d_CView&
 
     aRenderFramebuffer->BindBuffer (theGlContext);
   }
-  else if (theCView.RenderParams.IsAntialiasingEnabled) // if 2-pass ray-tracing is used
+  else if (myRenderParams.IsAntialiasingEnabled) // if 2-pass ray-tracing is used
   {
     myRaytraceFBO1->BindBuffer (theGlContext);
 
@@ -2387,8 +2382,7 @@ Standard_Boolean OpenGl_View::runRaytraceShaders (const Graphic3d_CView&
 
   Standard_Boolean aResult = theGlContext->BindProgram (myRaytraceProgram);
 
-  aResult &= setUniformState (theCView,
-                              theOrigins,
+  aResult &= setUniformState (theOrigins,
                               theDirects,
                               theUnviewMat,
                               0, // ID of RT program
@@ -2396,6 +2390,11 @@ Standard_Boolean OpenGl_View::runRaytraceShaders (const Graphic3d_CView&
 
   if (myRaytraceParameters.GlobalIllumination)
   {
+    if (myAccumFrames == 0)
+    {
+      myRNG.SetSeed();
+    }
+
     // Set frame accumulation weight
     myRaytraceProgram->SetUniform (theGlContext,
       myUniformLocations[0][OpenGl_RT_uSampleWeight], 1.f / (myAccumFrames + 1));
@@ -2430,14 +2429,13 @@ Standard_Boolean OpenGl_View::runRaytraceShaders (const Graphic3d_CView&
 
     ++myAccumFrames;
   }
-  else if (theCView.RenderParams.IsAntialiasingEnabled)
+  else if (myRenderParams.IsAntialiasingEnabled)
   {
     myRaytraceFBO1->ColorTexture()->Bind (theGlContext, GL_TEXTURE0 + OpenGl_RT_FsaaInputTexture);
 
     aResult &= theGlContext->BindProgram (myPostFSAAProgram);
 
-    aResult &= setUniformState (theCView,
-                                theOrigins,
+    aResult &= setUniformState (theOrigins,
                                 theDirects,
                                 theUnviewMat,
                                 1, // ID of FSAA program
@@ -2513,13 +2511,12 @@ Standard_Boolean OpenGl_View::runRaytraceShaders (const Graphic3d_CView&
 // function : raytrace
 // purpose  : Redraws the window using OpenGL/GLSL ray-tracing
 // =======================================================================
-Standard_Boolean OpenGl_View::raytrace (const Graphic3d_CView&        theCView,
-                                        const Standard_Integer        theSizeX,
+Standard_Boolean OpenGl_View::raytrace (const Standard_Integer        theSizeX,
                                         const Standard_Integer        theSizeY,
                                         OpenGl_FrameBuffer*           theReadDrawFbo,
                                         const Handle(OpenGl_Context)& theGlContext)
 {
-  if (!initRaytraceResources (theCView, theGlContext))
+  if (!initRaytraceResources (theGlContext))
   {
     return Standard_False;
   }
@@ -2574,8 +2571,7 @@ Standard_Boolean OpenGl_View::raytrace (const Graphic3d_CView&        theCView,
         0, GL_DEBUG_SEVERITY_MEDIUM_ARB, "Error: Failed to acquire OpenGL image textures");
     }
 
-    Standard_Boolean aResult = runRaytraceShaders (theCView,
-                                                   theSizeX,
+    Standard_Boolean aResult = runRaytraceShaders (theSizeX,
                                                    theSizeY,
                                                    aOrigins,
                                                    aDirects,