]> OCCT Git - occt-copy.git/commitdiff
0029337: Visualization, TKOpenGl - visual artifacts on Intel Broadwell GPU CR29337_720
authorapl <apl@opencascade.com>
Mon, 27 Nov 2017 12:16:21 +0000 (15:16 +0300)
committerapl <apl@opencascade.com>
Mon, 27 Nov 2017 12:16:21 +0000 (15:16 +0300)
Enable multiple draw buffers in shader program only if its required by specific application

src/Graphic3d/Graphic3d_ShaderProgram.cxx
src/Graphic3d/Graphic3d_ShaderProgram.hxx
src/OpenGl/OpenGl_Context.cxx
src/OpenGl/OpenGl_ShaderManager.cxx
src/OpenGl/OpenGl_ShaderProgram.cxx
src/Shaders/Declarations.glsl
src/Shaders/Shaders_Declarations_glsl.pxx

index 119d642d41f290186a526d58207bacf3d84919d7..23762e2a52e07f4f670b68084df82cd15c15ca5b 100755 (executable)
@@ -77,6 +77,7 @@ const TCollection_AsciiString& Graphic3d_ShaderProgram::ShadersFolder()
 // purpose  : Creates new empty program object
 // =======================================================================
 Graphic3d_ShaderProgram::Graphic3d_ShaderProgram()
+: myIsMultiOutput (Standard_False)
 {
   myID = TCollection_AsciiString ("Graphic3d_ShaderProgram_")
        + TCollection_AsciiString (Standard_Atomic_Increment (&THE_PROGRAM_OBJECT_COUNTER));
@@ -172,3 +173,12 @@ void Graphic3d_ShaderProgram::SetVertexAttributes (const Graphic3d_ShaderAttribu
 {
   myAttributes = theAttributes;
 }
+
+// =======================================================================
+// function : SetMultipleDrawBuffers
+// purpose  :
+// =======================================================================
+void Graphic3d_ShaderProgram::SetUseMultipleDrawBuffers (const Standard_Boolean theIsMultiple)
+{
+  myIsMultiOutput = theIsMultiple;
+}
index 5118e177ffb254921bac597794b1345a6c7bc5c2..4fa3dd17520b5ef5868cef7b970d012838531241 100755 (executable)
@@ -81,6 +81,13 @@ public:
   //! Should be done before GLSL program initialization.
   Standard_EXPORT void SetVertexAttributes (const Graphic3d_ShaderAttributeList& theAttributes);
 
+  //! Returns true if shader program should write to multiple draw buffers.
+  Standard_Boolean UseMultipleDrawBuffers() const { return myIsMultiOutput; }
+
+  //! Sets a flag that shader program should write to multiple draw buffers (false by default, minimum 4 is supported).
+  //! Should be done before GLSL program initialization.
+  Standard_EXPORT void SetUseMultipleDrawBuffers (const Standard_Boolean theIsMultiple);
+
   //! Pushes custom uniform variable to the program.
   //! The list of pushed variables is automatically cleared after applying to GLSL program.
   //! Thus after program recreation even unchanged uniforms should be pushed anew.
@@ -132,7 +139,7 @@ private:
   Graphic3d_ShaderVariableList  myVariables;     //!< the list of custom uniform variables
   Graphic3d_ShaderAttributeList myAttributes;    //!< the list of custom vertex attributes
   TCollection_AsciiString       myHeader;        //!< GLSL header with version code and used extensions
-
+  Standard_Boolean              myIsMultiOutput; //!< indicates whether program should use multiple draw buffers.
 };
 
 DEFINE_STANDARD_HANDLE (Graphic3d_ShaderProgram, Standard_Transient)
index 52f9a160502af67981e81901b198193fb81b5ec3..b5084349951fbd81725e65216783dced01fa2ef5 100644 (file)
@@ -433,18 +433,13 @@ void OpenGl_Context::SetDrawBuffers (const Standard_Integer theNb, const Standar
   Standard_Boolean useDefaultFbo = Standard_False;
   for (Standard_Integer anI = 0; anI < theNb; ++anI)
   {
-#if !defined(GL_ES_VERSION_2_0)
-    const Standard_Integer aDrawBuffer = !myIsStereoBuffers ? stereoToMonoBuffer (theDrawBuffers[anI]) : theDrawBuffers[anI];
-#else
-    const Standard_Integer aDrawBuffer = theDrawBuffers[anI];
-#endif
-    if (aDrawBuffer < GL_COLOR_ATTACHMENT0 && aDrawBuffer != GL_NONE)
+    if (theDrawBuffers[anI] < GL_COLOR_ATTACHMENT0 && theDrawBuffers[anI] != GL_NONE)
     {
       useDefaultFbo = Standard_True;
     }
-    else if (aDrawBuffer != GL_NONE)
+    else if (theDrawBuffers[anI] != GL_NONE)
     {
-      myDrawBuffers.SetValue (anI, aDrawBuffer);
+      myDrawBuffers.SetValue (anI, theDrawBuffers[anI]);
     }
   }
   if (arbFBO != NULL && useDefaultFbo)
index e01e151343a8ebdf14eda6bba22983c35e05c54d..c3484cd6f41567f4ab009d8a848c6eba4a281222 100644 (file)
@@ -1483,6 +1483,8 @@ Standard_Boolean OpenGl_ShaderManager::prepareStdProgramFlat (Handle(OpenGl_Shad
   }
   if ((theBits & OpenGl_PO_WriteOit) != 0)
   {
+    aProgramSrc->SetUseMultipleDrawBuffers (Standard_True);
+
     aSrcFragWriteOit += THE_FRAG_write_oit_buffers;
   }
 
@@ -1782,6 +1784,8 @@ Standard_Boolean OpenGl_ShaderManager::prepareStdProgramGouraud (Handle(OpenGl_S
   }
   if ((theBits & OpenGl_PO_WriteOit) != 0)
   {
+    aProgramSrc->SetUseMultipleDrawBuffers (Standard_True);
+
     aSrcFragWriteOit += THE_FRAG_write_oit_buffers;
   }
 
@@ -1916,6 +1920,8 @@ Standard_Boolean OpenGl_ShaderManager::prepareStdProgramPhong (Handle(OpenGl_Sha
   }
   if ((theBits & OpenGl_PO_WriteOit) != 0)
   {
+    aProgramSrc->SetUseMultipleDrawBuffers (Standard_True);
+
     aSrcFragWriteOit += THE_FRAG_write_oit_buffers;
   }
 
index 74344dd8ecd293b284fffd67a4db261108fba694..8e21f87f7debb1559e42f8f1d2eb1ffde11aa457 100755 (executable)
@@ -155,6 +155,10 @@ Standard_Boolean OpenGl_ShaderProgram::Initialize (const Handle(OpenGl_Context)&
                                   ? (myProxy->Header() + "\n")
                                   : TCollection_AsciiString();
 
+  Standard_Boolean toEnableDrawBuffers = !myProxy.IsNull()
+                                       ? myProxy->UseMultipleDrawBuffers()
+                                       : Standard_False;
+
   TCollection_AsciiString aDeclarations = Shaders_Declarations_glsl;
   TCollection_AsciiString aDeclImpl = Shaders_DeclarationsImpl_glsl;
 
@@ -207,19 +211,33 @@ Standard_Boolean OpenGl_ShaderProgram::Initialize (const Handle(OpenGl_Context)&
 
     TCollection_AsciiString aSource = aDeclarations + anIter.Value()->Source();
     TCollection_AsciiString anExtensions = "// Enable extensions used in OCCT GLSL programs\n";
-    if (theCtx->hasDrawBuffers)
-    {
-      anExtensions += "#define OCC_ENABLE_draw_buffers\n";
-    }
-    if (theCtx->hasDrawBuffers == OpenGl_FeatureInExtensions)
+    if (toEnableDrawBuffers)
     {
-      if (theCtx->arbDrawBuffers)
+      if (theCtx->hasDrawBuffers)
+      {
+        anExtensions += "#define OCC_ENABLE_draw_buffers\n";
+      }
+      else
       {
-        anExtensions += "#extension GL_ARB_draw_buffers : enable\n";
+        TCollection_ExtendedString aMsg = "Error! Multiple draw buffers required by the program, but aren't supported by GL";
+        theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION,
+                             GL_DEBUG_TYPE_ERROR,
+                             0,
+                             GL_DEBUG_SEVERITY_HIGH,
+                             aMsg);
+        return Standard_False;
       }
-      else if (theCtx->extDrawBuffers)
+
+      if (theCtx->hasDrawBuffers == OpenGl_FeatureInExtensions)
       {
-        anExtensions += "#extension GL_EXT_draw_buffers : enable\n";
+        if (theCtx->arbDrawBuffers)
+        {
+          anExtensions += "#extension GL_ARB_draw_buffers : enable\n";
+        }
+        else if (theCtx->extDrawBuffers)
+        {
+          anExtensions += "#extension GL_EXT_draw_buffers : enable\n";
+        }
       }
     }
 
index efdfb2dbdf7f125177189a38d222f342fc86d962..47f5c3481892c9cea8b4340b8a0f417feb964afb 100644 (file)
   THE_ATTRIBUTE vec4 occVertColor;
 #elif (__VERSION__ >= 130)
   #ifdef OCC_ENABLE_draw_buffers
-    out vec4 occFragColorArray[2];
-    #define occFragColor    occFragColorArray[0]
-    #define occFragCoverage occFragColorArray[1]
+    out vec4 occFragColorArray[4];
+    // General purpose outputs notation
+    #define occFragColor0 occFragColorArray[0]
+    #define occFragColor1 occFragColorArray[1]
+    #define occFragColor2 occFragColorArray[2]
+    #define occFragColor3 occFragColorArray[3]
+    // Built-in outputs notation
+    #define occFragColor    occFragColor0
+    #define occFragCoverage occFragColor1
   #else
     out vec4 occFragColor;
   #endif
 #else
   #ifdef OCC_ENABLE_draw_buffers
-    #define occFragColor    gl_FragData[0]
-    #define occFragCoverage gl_FragData[1]
+    // General purpose outputs notation
+    #define occFragColor0 gl_FragData[0]
+    #define occFragColor1 gl_FragData[1]
+    #define occFragColor2 gl_FragData[2]
+    #define occFragColor3 gl_FragData[3]
+    // Built-in outputs notation
+    #define occFragColor    occFragColor0
+    #define occFragCoverage occFragColor1
   #else
     #define occFragColor gl_FragColor
   #endif
index 488d06d8e419c78130731ea3ac2f613adae5632f..b6a15b651d56f9c4b1a353478cca7d21d9f63707 100644 (file)
@@ -54,16 +54,28 @@ static const char Shaders_Declarations_glsl[] =
   "  THE_ATTRIBUTE vec4 occVertColor;\n"
   "#elif (__VERSION__ >= 130)\n"
   "  #ifdef OCC_ENABLE_draw_buffers\n"
-  "    out vec4 occFragColorArray[2];\n"
-  "    #define occFragColor    occFragColorArray[0]\n"
-  "    #define occFragCoverage occFragColorArray[1]\n"
+  "    out vec4 occFragColorArray[4];\n"
+  "    // General purpose outputs notation\n"
+  "    #define occFragColor0 occFragColorArray[0]\n"
+  "    #define occFragColor1 occFragColorArray[1]\n"
+  "    #define occFragColor2 occFragColorArray[2]\n"
+  "    #define occFragColor3 occFragColorArray[3]\n"
+  "    // Built-in outputs notation\n"
+  "    #define occFragColor    occFragColor0\n"
+  "    #define occFragCoverage occFragColor1\n"
   "  #else\n"
   "    out vec4 occFragColor;\n"
   "  #endif\n"
   "#else\n"
   "  #ifdef OCC_ENABLE_draw_buffers\n"
-  "    #define occFragColor    gl_FragData[0]\n"
-  "    #define occFragCoverage gl_FragData[1]\n"
+  "    // General purpose outputs notation\n"
+  "    #define occFragColor0 gl_FragData[0]\n"
+  "    #define occFragColor1 gl_FragData[1]\n"
+  "    #define occFragColor2 gl_FragData[2]\n"
+  "    #define occFragColor3 gl_FragData[3]\n"
+  "    // Built-in outputs notation\n"
+  "    #define occFragColor    occFragColor0\n"
+  "    #define occFragCoverage occFragColor1\n"
   "  #else\n"
   "    #define occFragColor gl_FragColor\n"
   "  #endif\n"