#include <OpenGl_Workspace.hxx>
-#include <NCollection_Mat4.hxx>
-#include <OpenGl_ArbFBO.hxx>
+#include <Graphic3d_TextureParams.hxx>
#include <OpenGl_FrameBuffer.hxx>
#include <OpenGl_PrimitiveArray.hxx>
-#include <OpenGl_Texture.hxx>
#include <OpenGl_VertexBuffer.hxx>
#include <OpenGl_View.hxx>
#include <OSD_File.hxx>
#include <OSD_Protection.hxx>
-#include <Standard_Assert.hxx>
using namespace OpenGl_Raytrace;
#include <OSD_Timer.hxx>
#endif
-// =======================================================================
-// function : MatVecMult
-// purpose : Multiples 4x4 matrix by 4D vector
-// =======================================================================
-template<typename T>
-BVH_Vec4f MatVecMult (const T m[16], const BVH_Vec4f& v)
-{
- return BVH_Vec4f (
- static_cast<float> (m[ 0] * v.x() + m[ 4] * v.y() +
- m[ 8] * v.z() + m[12] * v.w()),
- static_cast<float> (m[ 1] * v.x() + m[ 5] * v.y() +
- m[ 9] * v.z() + m[13] * v.w()),
- static_cast<float> (m[ 2] * v.x() + m[ 6] * v.y() +
- m[10] * v.z() + m[14] * v.w()),
- static_cast<float> (m[ 3] * v.x() + m[ 7] * v.y() +
- m[11] * v.z() + m[15] * v.w()));
-}
-
// =======================================================================
// function : UpdateRaytraceGeometry
// purpose : Updates 3D scene geometry for ray tracing
for (OpenGl_SequenceOfLayers::Iterator anLayerIt (aList.Layers()); anLayerIt.More(); anLayerIt.Next())
{
- const OpenGl_PriorityList& aPriorityList = anLayerIt.Value().PriorityList();
-
- if (aPriorityList.NbStructures() == 0)
+ const OpenGl_Layer& aLayer = anLayerIt.Value();
+ if (aLayer.NbStructures() == 0)
continue;
- const OpenGl_ArrayOfStructure& aStructArray = aPriorityList.ArrayOfStructures();
-
+ const OpenGl_ArrayOfStructure& aStructArray = aLayer.ArrayOfStructures();
for (Standard_Integer anIndex = 0; anIndex < aStructArray.Length(); ++anIndex)
{
- OpenGl_SequenceOfStructure::Iterator aStructIt;
-
- for (aStructIt.Init (aStructArray (anIndex)); aStructIt.More(); aStructIt.Next())
+ for (OpenGl_SequenceOfStructure::Iterator aStructIt (aStructArray (anIndex)); aStructIt.More(); aStructIt.Next())
{
const OpenGl_Structure* aStructure = aStructIt.Value();
{
return UpdateRaytraceGeometry (OpenGl_GUM_PREPARE);
}
- }
+ }
else if (theMode == OpenGl_GUM_PREPARE)
{
if (!aStructure->IsRaytracable()
|| !aStructure->IsVisible())
+ {
continue;
+ }
+ else if (!aStructure->ViewAffinity.IsNull()
+ && !aStructure->ViewAffinity->IsVisible (myViewId))
+ {
+ continue;
+ }
for (OpenGl_Structure::GroupIterator aGroupIter (aStructure->DrawGroups()); aGroupIter.More(); aGroupIter.Next())
{
}
}
}
- }
+ }
else if (theMode == OpenGl_GUM_UPDATE)
{
if (!aStructure->IsRaytracable())
if (theMode == OpenGl_GUM_PREPARE)
{
- BVH_ObjectSet<Standard_ShortReal, 4>::BVH_ObjectList anUnchangedObjects;
+ BVH_ObjectSet<Standard_ShortReal, 3>::BVH_ObjectList anUnchangedObjects;
// Leave only unchanged objects in myRaytraceGeometry so only their transforms and materials will be updated
// Objects which not in myArrayToTrianglesMap will be built from scratch.
myRaytraceSceneRadius = 2.f /* scale factor */ * Max (aMinRadius, aMaxRadius);
- const BVH_Vec4f aSize = myRaytraceGeometry.Box().Size();
+ const BVH_Vec3f aSize = myRaytraceGeometry.Box().Size();
myRaytraceSceneEpsilon = Max (1e-6f, 1e-4f * sqrtf (
aSize.x() * aSize.x() + aSize.y() * aSize.y() + aSize.z() * aSize.z()));
// =======================================================================
// function : CheckRaytraceStructure
-// purpose : Checks to see if the structure is modified
+// purpose : Checks to see if the structure is modified
// =======================================================================
Standard_Boolean OpenGl_Workspace::CheckRaytraceStructure (const OpenGl_Structure* theStructure)
{
return Standard_True;
}
+// =======================================================================
+// function : BuildTexTransform
+// purpose : Constructs texture transformation matrix
+// =======================================================================
+void BuildTexTransform (const Handle(Graphic3d_TextureParams)& theParams, BVH_Mat4f& theMatrix)
+{
+ theMatrix.InitIdentity();
+
+ // Apply scaling
+ const Graphic3d_Vec2& aScale = theParams->Scale();
+
+ theMatrix.ChangeValue (0, 0) *= aScale.x();
+ theMatrix.ChangeValue (1, 0) *= aScale.x();
+ theMatrix.ChangeValue (2, 0) *= aScale.x();
+ theMatrix.ChangeValue (3, 0) *= aScale.x();
+
+ theMatrix.ChangeValue (0, 1) *= aScale.y();
+ theMatrix.ChangeValue (1, 1) *= aScale.y();
+ theMatrix.ChangeValue (2, 1) *= aScale.y();
+ theMatrix.ChangeValue (3, 1) *= aScale.y();
+
+ // Apply translation
+ const Graphic3d_Vec2 aTrans = -theParams->Translation();
+
+ theMatrix.ChangeValue (0, 3) = theMatrix.GetValue (0, 0) * aTrans.x() +
+ theMatrix.GetValue (0, 1) * aTrans.y();
+
+ theMatrix.ChangeValue (1, 3) = theMatrix.GetValue (1, 0) * aTrans.x() +
+ theMatrix.GetValue (1, 1) * aTrans.y();
+
+ theMatrix.ChangeValue (2, 3) = theMatrix.GetValue (2, 0) * aTrans.x() +
+ theMatrix.GetValue (2, 1) * aTrans.y();
+
+ // Apply rotation
+ const Standard_ShortReal aSin = std::sin (
+ -theParams->Rotation() * static_cast<Standard_ShortReal> (M_PI / 180.0));
+ const Standard_ShortReal aCos = std::cos (
+ -theParams->Rotation() * static_cast<Standard_ShortReal> (M_PI / 180.0));
+
+ BVH_Mat4f aRotationMat;
+ aRotationMat.SetValue (0, 0, aCos);
+ aRotationMat.SetValue (1, 1, aCos);
+ aRotationMat.SetValue (0, 1, -aSin);
+ aRotationMat.SetValue (1, 0, aSin);
+
+ theMatrix = theMatrix * aRotationMat;
+}
+
// =======================================================================
// function : CreateMaterial
// purpose : Creates ray-tracing material properties
// =======================================================================
-void CreateMaterial (const OPENGL_SURF_PROP& theProp, OpenGl_RaytraceMaterial& theMaterial)
+Standard_Boolean OpenGl_Workspace::CreateMaterial (const OpenGl_AspectFace* theAspect, OpenGl_RaytraceMaterial& theMaterial)
{
- const float* aSrcAmb = theProp.isphysic ? theProp.ambcol.rgb : theProp.matcol.rgb;
- theMaterial.Ambient = BVH_Vec4f (aSrcAmb[0] * theProp.amb,
- aSrcAmb[1] * theProp.amb,
- aSrcAmb[2] * theProp.amb,
- 1.0f);
-
- const float* aSrcDif = theProp.isphysic ? theProp.difcol.rgb : theProp.matcol.rgb;
- theMaterial.Diffuse = BVH_Vec4f (aSrcDif[0] * theProp.diff,
- aSrcDif[1] * theProp.diff,
- aSrcDif[2] * theProp.diff,
- 1.0f);
-
- const float aDefSpecCol[4] = {1.0f, 1.0f, 1.0f, 1.0f};
- const float* aSrcSpe = theProp.isphysic ? theProp.speccol.rgb : aDefSpecCol;
- theMaterial.Specular = BVH_Vec4f (aSrcSpe[0] * theProp.spec,
- aSrcSpe[1] * theProp.spec,
- aSrcSpe[2] * theProp.spec,
- theProp.shine);
-
- const float* aSrcEms = theProp.isphysic ? theProp.emscol.rgb : theProp.matcol.rgb;
- theMaterial.Emission = BVH_Vec4f (aSrcEms[0] * theProp.emsv,
- aSrcEms[1] * theProp.emsv,
- aSrcEms[2] * theProp.emsv,
- 1.0f);
+ const OPENGL_SURF_PROP& aProperties = theAspect->IntFront();
+
+ const Standard_ShortReal* aSrcAmbient =
+ aProperties.isphysic ? aProperties.ambcol.rgb : aProperties.matcol.rgb;
+
+ theMaterial.Ambient = BVH_Vec4f (aSrcAmbient[0] * aProperties.amb,
+ aSrcAmbient[1] * aProperties.amb,
+ aSrcAmbient[2] * aProperties.amb,
+ 1.f);
+
+ const Standard_ShortReal* aSrcDiffuse =
+ aProperties.isphysic ? aProperties.difcol.rgb : aProperties.matcol.rgb;
+
+ theMaterial.Diffuse = BVH_Vec4f (aSrcDiffuse[0] * aProperties.diff,
+ aSrcDiffuse[1] * aProperties.diff,
+ aSrcDiffuse[2] * aProperties.diff,
+ -1.f /* no texture */);
+
+ theMaterial.Specular = BVH_Vec4f (
+ (aProperties.isphysic ? aProperties.speccol.rgb[0] : 1.f) * aProperties.spec,
+ (aProperties.isphysic ? aProperties.speccol.rgb[1] : 1.f) * aProperties.spec,
+ (aProperties.isphysic ? aProperties.speccol.rgb[2] : 1.f) * aProperties.spec,
+ aProperties.shine);
+
+ const Standard_ShortReal* aSrcEmission =
+ aProperties.isphysic ? aProperties.emscol.rgb : aProperties.matcol.rgb;
+
+ theMaterial.Emission = BVH_Vec4f (aSrcEmission[0] * aProperties.emsv,
+ aSrcEmission[1] * aProperties.emsv,
+ aSrcEmission[2] * aProperties.emsv,
+ 1.f);
// Note: Here we use sub-linear transparency function
// to produce realistic-looking transparency effect
- theMaterial.Transparency = BVH_Vec4f (powf (theProp.trans, 0.75f),
- 1.f - theProp.trans,
- theProp.index == 0 ? 1.f : theProp.index,
- theProp.index == 0 ? 1.f : 1.f / theProp.index);
+ theMaterial.Transparency = BVH_Vec4f (powf (aProperties.trans, 0.75f),
+ 1.f - aProperties.trans,
+ aProperties.index == 0 ? 1.f : aProperties.index,
+ aProperties.index == 0 ? 1.f : 1.f / aProperties.index);
+
+ const Standard_ShortReal aMaxRefl = Max (theMaterial.Diffuse.x() + theMaterial.Specular.x(),
+ Max (theMaterial.Diffuse.y() + theMaterial.Specular.y(),
+ theMaterial.Diffuse.z() + theMaterial.Specular.z()));
- const float aMaxRefl = Max (theMaterial.Diffuse.x() + theMaterial.Specular.x(),
- Max (theMaterial.Diffuse.y() + theMaterial.Specular.y(),
- theMaterial.Diffuse.z() + theMaterial.Specular.z()));
+ const Standard_ShortReal aReflectionScale = 0.75f / aMaxRefl;
- const float aReflectionScale = 0.75f / aMaxRefl;
+ theMaterial.Reflection = BVH_Vec4f (
+ aProperties.speccol.rgb[0] * aProperties.spec * aReflectionScale,
+ aProperties.speccol.rgb[1] * aProperties.spec * aReflectionScale,
+ aProperties.speccol.rgb[2] * aProperties.spec * aReflectionScale,
+ 0.f);
- theMaterial.Reflection = BVH_Vec4f (theProp.speccol.rgb[0] * theProp.spec * aReflectionScale,
- theProp.speccol.rgb[1] * theProp.spec * aReflectionScale,
- theProp.speccol.rgb[2] * theProp.spec * aReflectionScale,
- 0.f);
+ if (theAspect->DoTextureMap())
+ {
+ if (myGlContext->arbTexBindless != NULL)
+ {
+ BuildTexTransform (theAspect->TextureParams(), theMaterial.TextureTransform);
+ theMaterial.Diffuse.w() = static_cast<Standard_ShortReal> (
+ myRaytraceGeometry.AddTexture (theAspect->TextureRes (myGlContext)));
+ }
+ else if (!myIsRaytraceWarnTextures)
+ {
+ myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
+ GL_DEBUG_TYPE_PORTABILITY_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB,
+ "Warning: texturing in Ray-Trace requires GL_ARB_bindless_texture extension which is missing. "
+ "Textures will be ignored.");
+ myIsRaytraceWarnTextures = Standard_True;
+ }
+ }
+
+ return Standard_True;
}
// =======================================================================
aStructMatID = static_cast<Standard_Integer> (myRaytraceGeometry.Materials.size());
OpenGl_RaytraceMaterial aStructMaterial;
- CreateMaterial (theStructure->AspectFace()->IntFront(), aStructMaterial);
+ CreateMaterial (theStructure->AspectFace(), aStructMaterial);
myRaytraceGeometry.Materials.push_back (aStructMaterial);
}
aGroupMatID = static_cast<Standard_Integer> (myRaytraceGeometry.Materials.size());
OpenGl_RaytraceMaterial aGroupMaterial;
- CreateMaterial (aGroupIter.Value()->AspectFace()->IntFront(), aGroupMaterial);
+ CreateMaterial (aGroupIter.Value()->AspectFace(), aGroupMaterial);
myRaytraceGeometry.Materials.push_back (aGroupMaterial);
}
aMatID = static_cast<Standard_Integer> (myRaytraceGeometry.Materials.size());
OpenGl_RaytraceMaterial aMaterial;
- CreateMaterial (anAspect->IntFront(), aMaterial);
+ CreateMaterial (anAspect, aMaterial);
myRaytraceGeometry.Materials.push_back (aMaterial);
}
if (aSetIter != myArrayToTrianglesMap.end())
{
OpenGl_TriangleSet* aSet = aSetIter->second;
-
+
BVH_Transform<Standard_ShortReal, 4>* aTransform = new BVH_Transform<Standard_ShortReal, 4>();
if (theTransform != NULL)
aSet->SetProperties (aTransform);
- if (aSet->MaterialIndex() != OpenGl_TriangleSet::INVALID_MATERIAL && aSet->MaterialIndex() != aMatID )
+ if (aSet->MaterialIndex() != OpenGl_TriangleSet::INVALID_MATERIAL && aSet->MaterialIndex() != aMatID)
{
aSet->SetMaterialIndex (aMatID);
}
}
else
{
- NCollection_Handle<BVH_Object<Standard_ShortReal, 4> > aSet =
+ NCollection_Handle<BVH_Object<Standard_ShortReal, 3> > aSet =
AddRaytracePrimitiveArray (aPrimArray, aMatID, 0);
if (!aSet.IsNull())
// =======================================================================
OpenGl_TriangleSet* OpenGl_Workspace::AddRaytracePrimitiveArray (const OpenGl_PrimitiveArray* theArray,
Standard_Integer theMatID,
- const Standard_ShortReal* theTransform)
+ const OpenGl_Mat4* theTransform)
{
const Handle(Graphic3d_IndexBuffer)& anIndices = theArray->Indices();
const Handle(Graphic3d_Buffer)& anAttribs = theArray->Attributes();
}
#endif
+ OpenGl_Mat4 aNormalMatrix;
+
+ if (theTransform != NULL)
+ {
+ Standard_ASSERT_RETURN (theTransform->Inverted (aNormalMatrix),
+ "Error: Failed to compute normal transformation matrix", NULL);
+
+ aNormalMatrix.Transpose();
+ }
+
OpenGl_TriangleSet* aSet = new OpenGl_TriangleSet (theArray->GetUID());
{
aSet->Vertices.reserve (anAttribs->NbElements);
aSet->Normals .reserve (anAttribs->NbElements);
+ aSet->TexCrds .reserve (anAttribs->NbElements);
+
const size_t aVertFrom = aSet->Vertices.size();
for (Standard_Integer anAttribIter = 0; anAttribIter < anAttribs->NbAttributes; ++anAttribIter)
{
{
for (Standard_Integer aVertIter = 0; aVertIter < anAttribs->NbElements; ++aVertIter)
{
- const Graphic3d_Vec3& aVert = *reinterpret_cast<const Graphic3d_Vec3* >(anAttribs->value (aVertIter) + anOffset);
- aSet->Vertices.push_back (BVH_Vec4f (aVert.x(), aVert.y(), aVert.z(), 1.0f));
+ aSet->Vertices.push_back (
+ *reinterpret_cast<const Graphic3d_Vec3* >(anAttribs->value (aVertIter) + anOffset));
}
}
else if (anAttrib.DataType == Graphic3d_TOD_VEC2)
for (Standard_Integer aVertIter = 0; aVertIter < anAttribs->NbElements; ++aVertIter)
{
const Graphic3d_Vec2& aVert = *reinterpret_cast<const Graphic3d_Vec2* >(anAttribs->value (aVertIter) + anOffset);
- aSet->Vertices.push_back (BVH_Vec4f (aVert.x(), aVert.y(), 0.0f, 1.0f));
+ aSet->Vertices.push_back (BVH_Vec3f (aVert.x(), aVert.y(), 0.0f));
}
}
}
{
for (Standard_Integer aVertIter = 0; aVertIter < anAttribs->NbElements; ++aVertIter)
{
- const Graphic3d_Vec3& aNorm = *reinterpret_cast<const Graphic3d_Vec3* >(anAttribs->value (aVertIter) + anOffset);
- aSet->Normals.push_back (BVH_Vec4f (aNorm.x(), aNorm.y(), aNorm.z(), 0.0f));
+ aSet->Normals.push_back (
+ *reinterpret_cast<const Graphic3d_Vec3* >(anAttribs->value (aVertIter) + anOffset));
+ }
+ }
+ }
+ else if (anAttrib.Id == Graphic3d_TOA_UV)
+ {
+ if (anAttrib.DataType == Graphic3d_TOD_VEC2)
+ {
+ for (Standard_Integer aVertIter = 0; aVertIter < anAttribs->NbElements; ++aVertIter)
+ {
+ aSet->TexCrds.push_back (
+ *reinterpret_cast<const Graphic3d_Vec2* >(anAttribs->value (aVertIter) + anOffset));
}
}
}
{
for (Standard_Integer aVertIter = 0; aVertIter < anAttribs->NbElements; ++aVertIter)
{
- aSet->Normals.push_back (BVH_Vec4f());
+ aSet->Normals.push_back (BVH_Vec3f());
+ }
+ }
+
+ if (aSet->TexCrds.size() != aSet->Vertices.size())
+ {
+ for (Standard_Integer aVertIter = 0; aVertIter < anAttribs->NbElements; ++aVertIter)
+ {
+ aSet->TexCrds.push_back (BVH_Vec2f());
}
}
- if (theTransform)
+ if (theTransform != NULL)
{
for (size_t aVertIter = aVertFrom; aVertIter < aSet->Vertices.size(); ++aVertIter)
{
- BVH_Vec4f& aVertex = aSet->Vertices[aVertIter];
- aVertex = MatVecMult (theTransform, aVertex);
+ BVH_Vec3f& aVertex = aSet->Vertices[aVertIter];
+
+ BVH_Vec4f aTransVertex =
+ *theTransform * BVH_Vec4f (aVertex.x(), aVertex.y(), aVertex.z(), 1.f);
+
+ aVertex = BVH_Vec3f (aTransVertex.x(), aTransVertex.y(), aTransVertex.z());
}
for (size_t aVertIter = aVertFrom; aVertIter < aSet->Normals.size(); ++aVertIter)
{
- BVH_Vec4f& aNorm = aSet->Normals[aVertIter];
- aNorm = MatVecMult (theTransform, aNorm);
+ BVH_Vec3f& aNormal = aSet->Normals[aVertIter];
+
+ BVH_Vec4f aTransNormal =
+ aNormalMatrix * BVH_Vec4f (aNormal.x(), aNormal.y(), aNormal.z(), 0.f);
+
+ aNormal = BVH_Vec3f (aTransNormal.x(), aTransNormal.y(), aTransNormal.z());
}
}
if (!aBounds.IsNull())
{
- #ifdef RAY_TRACE_PRINT_INFO
+#ifdef RAY_TRACE_PRINT_INFO
std::cout << "\tNumber of bounds = " << aBounds->NbBounds << std::endl;
- #endif
+#endif
Standard_Integer aBoundStart = 0;
for (Standard_Integer aBound = 0; aBound < aBounds->NbBounds; ++aBound)
{
const Standard_Integer aVertNum = aBounds->Bounds[aBound];
- #ifdef RAY_TRACE_PRINT_INFO
+#ifdef RAY_TRACE_PRINT_INFO
std::cout << "\tAdding indices from bound " << aBound << ": " <<
aBoundStart << " .. " << aVertNum << std::endl;
- #endif
+#endif
if (!AddRaytraceVertexIndices (*aSet, *theArray, aBoundStart, aVertNum, theMatID))
{
// function : UpdateRaytraceLightSources
// purpose : Updates 3D scene light sources for ray-tracing
// =======================================================================
-Standard_Boolean OpenGl_Workspace::UpdateRaytraceLightSources (const GLdouble theInvModelView[16])
+Standard_Boolean OpenGl_Workspace::UpdateRaytraceLightSources (const OpenGl_Mat4& theInvModelView)
{
myRaytraceGeometry.Sources.clear();
}
if (aLight.IsHeadlight)
- aPosition = MatVecMult (theInvModelView, aPosition);
+ {
+ aPosition = theInvModelView * aPosition;
+ }
-
myRaytraceGeometry.Sources.push_back (OpenGl_RaytraceLight (aDiffuse, aPosition));
}
myGlContext, GL_TEXTURE0 + OpenGl_RT_EnvironmentMapTexture);
aProgram->SetUniform (myGlContext,
- myUniformLocations[anIdx][OpenGl_RT_uEnvironmentEnable], 1);
+ myUniformLocations[anIdx][OpenGl_RT_uEnvMapEnable], 1);
}
else
{
aProgram->SetUniform (myGlContext,
- myUniformLocations[anIdx][OpenGl_RT_uEnvironmentEnable], 0);
+ myUniformLocations[anIdx][OpenGl_RT_uEnvMapEnable], 0);
}
}
}
if (!aShader->Create (myGlContext))
{
- const TCollection_ExtendedString aMessage = "Error: Failed to create shader object";
-
+ const TCollection_ExtendedString aMessage = TCollection_ExtendedString ("Error: Failed to create ") +
+ (theType == GL_VERTEX_SHADER ? "vertex" : "fragment") + " shader object";
+
myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMessage);
if (!aShader->LoadSource (myGlContext, theSource.Source()))
{
- const TCollection_ExtendedString aMessage = "Error: Failed to set shader source";
-
+ const TCollection_ExtendedString aMessage = TCollection_ExtendedString ("Error: Failed to set ") +
+ (theType == GL_VERTEX_SHADER ? "vertex" : "fragment") + " shader source";
+
myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMessage);
if (!aShader->Compile (myGlContext))
{
- if (aShader->FetchInfoLog (myGlContext, aBuildLog))
- {
- const TCollection_ExtendedString aMessage =
- TCollection_ExtendedString ("Error: Failed to compile shader object:\n") + aBuildLog;
+ aShader->FetchInfoLog (myGlContext, aBuildLog);
-#ifdef RAY_TRACE_PRINT_INFO
- std::cout << aBuildLog << std::endl;
-#endif
+ const TCollection_ExtendedString aMessage = TCollection_ExtendedString ("Error: Failed to compile ") +
+ (theType == GL_VERTEX_SHADER ? "vertex" : "fragment") + " shader object:\n" + aBuildLog;
+
+ myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
+ GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMessage);
- myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
- GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMessage);
- }
-
aShader->Release (myGlContext.operator->());
return Handle(OpenGl_ShaderObject)();
}
-
-#ifdef RAY_TRACE_PRINT_INFO
- if (aShader->FetchInfoLog (myGlContext, aBuildLog))
+ else if (myGlContext->caps->glslWarnings)
{
- if (!aBuildLog.IsEmpty())
- {
- std::cout << aBuildLog << std::endl;
- }
- else
+ aShader->FetchInfoLog (myGlContext, aBuildLog);
+
+ if (!aBuildLog.IsEmpty() && !aBuildLog.IsEqual ("No errors.\n"))
{
- std::cout << "Info: shader build log is empty" << std::endl;
+ const TCollection_ExtendedString aMessage = TCollection_ExtendedString (theType == GL_VERTEX_SHADER ?
+ "Vertex" : "Fragment") + " shader was compiled with following warnings:\n" + aBuildLog;
+
+ myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
+ GL_DEBUG_TYPE_PORTABILITY_ARB, 0, GL_DEBUG_SEVERITY_LOW_ARB, aMessage);
}
- }
-#endif
+ }
return aShader;
}
myComputeInitStatus = OpenGl_RT_FAIL;
ReleaseRaytraceResources();
-
+
return Standard_False;
}
+// =======================================================================
+// function : GenerateShaderPrefix
+// purpose : Generates shader prefix based on current ray-tracing options
+// =======================================================================
+TCollection_AsciiString OpenGl_Workspace::GenerateShaderPrefix()
+{
+ TCollection_AsciiString aPrefixString =
+ TCollection_AsciiString ("#define STACK_SIZE ") + TCollection_AsciiString (myRaytraceParameters.StackSize) + "\n" +
+ TCollection_AsciiString ("#define NB_BOUNCES ") + TCollection_AsciiString (myRaytraceParameters.NbBounces);
+
+ if (myRaytraceParameters.TransparentShadows)
+ {
+ aPrefixString += TCollection_AsciiString ("\n#define TRANSPARENT_SHADOWS");
+ }
+
+ // If OpenGL driver supports bindless textures
+ // activate texturing in ray-tracing mode
+ if (myGlContext->arbTexBindless != NULL)
+ {
+ aPrefixString += TCollection_AsciiString ("\n#define USE_TEXTURES") +
+ TCollection_AsciiString ("\n#define MAX_TEX_NUMBER ") + TCollection_AsciiString (OpenGl_RaytraceGeometry::MAX_TEX_NUMBER);
+ }
+
+ return aPrefixString;
+}
+
// =======================================================================
// function : InitRaytraceResources
// purpose : Initializes OpenGL/GLSL shader programs
// =======================================================================
Standard_Boolean OpenGl_Workspace::InitRaytraceResources (const Graphic3d_CView& theCView)
{
+ if (myComputeInitStatus == OpenGl_RT_FAIL)
+ {
+ return Standard_False;
+ }
+
Standard_Boolean aToRebuildShaders = Standard_False;
if (myComputeInitStatus == OpenGl_RT_INIT)
}
}
- if (theCView.RenderParams.RaytracingDepth != myRaytraceParameters.TraceDepth)
+ if (theCView.RenderParams.RaytracingDepth != myRaytraceParameters.NbBounces)
{
- myRaytraceParameters.TraceDepth = theCView.RenderParams.RaytracingDepth;
+ myRaytraceParameters.NbBounces = theCView.RenderParams.RaytracingDepth;
aToRebuildShaders = Standard_True;
}
// Change state to force update all uniforms
++myViewModificationStatus;
- TCollection_AsciiString aPrefixString =
- TCollection_AsciiString ("#define STACK_SIZE ") + TCollection_AsciiString (myRaytraceParameters.StackSize) + "\n" +
- TCollection_AsciiString ("#define TRACE_DEPTH ") + TCollection_AsciiString (myRaytraceParameters.TraceDepth);
-
- if (myRaytraceParameters.TransparentShadows)
- {
- aPrefixString += TCollection_AsciiString ("\n#define TRANSPARENT_SHADOWS");
- }
+ TCollection_AsciiString aPrefixString = GenerateShaderPrefix();
#ifdef RAY_TRACE_PRINT_INFO
std::cout << "GLSL prefix string:" << std::endl << aPrefixString << std::endl;
if (!myRaytraceShader->LoadSource (myGlContext, myRaytraceShaderSource.Source())
|| !myPostFSAAShader->LoadSource (myGlContext, myPostFSAAShaderSource.Source()))
{
- return Standard_False;
+ return SafeFailBack ("Failed to load source into ray-tracing fragment shaders");
}
if (!myRaytraceShader->Compile (myGlContext)
|| !myPostFSAAShader->Compile (myGlContext))
{
- return Standard_False;
+ return SafeFailBack ("Failed to compile ray-tracing fragment shaders");
}
myRaytraceProgram->SetAttributeName (myGlContext, Graphic3d_TOA_POS, "occVertex");
if (!myRaytraceProgram->Link (myGlContext)
|| !myPostFSAAProgram->Link (myGlContext))
{
- return Standard_False;
+ return SafeFailBack ("Failed to initialize vertex attributes for ray-tracing program");
}
}
}
{
if (!myGlContext->IsGlGreaterEqual (3, 1))
{
- const TCollection_ExtendedString aMessage = "Ray-tracing requires OpenGL 3.1 and higher";
-
- myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
- GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMessage);
-
- return Standard_False;
+ return SafeFailBack ("Ray-tracing requires OpenGL 3.1 and higher");
+ }
+ else if (!myGlContext->arbTboRGB32)
+ {
+ return SafeFailBack ("Ray-tracing requires OpenGL 4.0+ or GL_ARB_texture_buffer_object_rgb32 extension");
}
- myRaytraceParameters.TraceDepth = theCView.RenderParams.RaytracingDepth;
+ myRaytraceParameters.NbBounces = theCView.RenderParams.RaytracingDepth;
TCollection_AsciiString aFolder = Graphic3d_ShaderProgram::ShadersFolder();
if (aFolder.IsEmpty())
{
- const TCollection_ExtendedString aMessage = "Failed to locate shaders directory";
-
- myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
- GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMessage);
-
- return Standard_False;
+ return SafeFailBack ("Failed to locate shaders directory");
}
if (myIsRaytraceDataValid)
myRaytraceGeometry.HighLevelTreeDepth() + myRaytraceGeometry.BottomLevelTreeDepth());
}
- TCollection_AsciiString aPrefixString =
- TCollection_AsciiString ("#define STACK_SIZE ") + TCollection_AsciiString (myRaytraceParameters.StackSize) + "\n" +
- TCollection_AsciiString ("#define TRACE_DEPTH ") + TCollection_AsciiString (myRaytraceParameters.TraceDepth);
-
- if (myRaytraceParameters.TransparentShadows)
- {
- aPrefixString += TCollection_AsciiString ("\n#define TRANSPARENT_SHADOWS");
- }
+ TCollection_AsciiString aPrefixString = GenerateShaderPrefix();
#ifdef RAY_TRACE_PRINT_INFO
std::cout << "GLSL prefix string:" << std::endl << aPrefixString << std::endl;
if (aBasicVertShader.IsNull())
{
- return SafeFailBack ("Failed to set vertex shader source");
+ return SafeFailBack ("Failed to initialize ray-trace vertex shader");
}
- TCollection_AsciiString aFiles[] = { aFolder + "/RaytraceBase.fs", aFolder + "/RaytraceRender.fs" };
+ TCollection_AsciiString aFiles[] = { aFolder + "/RaytraceBase.fs",
+ aFolder + "/RaytraceRender.fs" };
myRaytraceShaderSource.Load (aFiles, 2);
{
aBasicVertShader->Release (myGlContext.operator->());
- return SafeFailBack ("Failed to set ray-trace fragment shader source");
+ return SafeFailBack ("Failed to initialize ray-trace fragment shader");
}
myRaytraceProgram = new OpenGl_ShaderProgram;
}
myRaytraceProgram->SetAttributeName (myGlContext, Graphic3d_TOA_POS, "occVertex");
+
+ TCollection_AsciiString aLinkLog;
+
if (!myRaytraceProgram->Link (myGlContext))
{
- TCollection_AsciiString aLinkLog;
+ myRaytraceProgram->FetchInfoLog (myGlContext, aLinkLog);
- if (myRaytraceProgram->FetchInfoLog (myGlContext, aLinkLog))
+ return SafeFailBack (TCollection_ExtendedString (
+ "Failed to link ray-trace shader program:\n") + aLinkLog);
+ }
+ else if (myGlContext->caps->glslWarnings)
+ {
+ myRaytraceProgram->FetchInfoLog (myGlContext, aLinkLog);
+
+ if (!aLinkLog.IsEmpty() && !aLinkLog.IsEqual ("No errors.\n"))
{
- #ifdef RAY_TRACE_PRINT_INFO
- std::cout << aLinkLog << std::endl;
- #endif
- }
+ const TCollection_ExtendedString aMessage = TCollection_ExtendedString (
+ "Ray-trace shader program was linked with following warnings:\n") + aLinkLog;
- return SafeFailBack ("Failed to link ray-trace shader program");
+ myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
+ GL_DEBUG_TYPE_PORTABILITY_ARB, 0, GL_DEBUG_SEVERITY_LOW_ARB, aMessage);
+ }
}
}
if (aBasicVertShader.IsNull())
{
- return SafeFailBack ("Failed to set vertex shader source");
+ return SafeFailBack ("Failed to initialize FSAA vertex shader");
}
- TCollection_AsciiString aFiles[] = { aFolder + "/RaytraceBase.fs", aFolder + "/RaytraceSmooth.fs" };
+ TCollection_AsciiString aFiles[] = { aFolder + "/RaytraceBase.fs",
+ aFolder + "/RaytraceSmooth.fs" };
myPostFSAAShaderSource.Load (aFiles, 2);
{
aBasicVertShader->Release (myGlContext.operator->());
- return SafeFailBack ("Failed to set FSAA fragment shader source");
+ return SafeFailBack ("Failed to initialize FSAA fragment shader");
}
myPostFSAAProgram = new OpenGl_ShaderProgram;
}
myPostFSAAProgram->SetAttributeName (myGlContext, Graphic3d_TOA_POS, "occVertex");
+
+ TCollection_AsciiString aLinkLog;
+
if (!myPostFSAAProgram->Link (myGlContext))
{
- TCollection_AsciiString aLinkLog;
+ myPostFSAAProgram->FetchInfoLog (myGlContext, aLinkLog);
+
+ return SafeFailBack (TCollection_ExtendedString (
+ "Failed to link FSAA shader program:\n") + aLinkLog);
+ }
+ else if (myGlContext->caps->glslWarnings)
+ {
+ myPostFSAAProgram->FetchInfoLog (myGlContext, aLinkLog);
- if (myPostFSAAProgram->FetchInfoLog (myGlContext, aLinkLog))
+ if (!aLinkLog.IsEmpty() && !aLinkLog.IsEqual ("No errors.\n"))
{
- #ifdef RAY_TRACE_PRINT_INFO
- std::cout << aLinkLog << std::endl;
- #endif
+ const TCollection_ExtendedString aMessage = TCollection_ExtendedString (
+ "FSAA shader program was linked with following warnings:\n") + aLinkLog;
+
+ myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
+ GL_DEBUG_TYPE_PORTABILITY_ARB, 0, GL_DEBUG_SEVERITY_LOW_ARB, aMessage);
}
-
- return SafeFailBack ("Failed to link FSAA shader program");
}
}
}
"uSceneMaxPointTexture", OpenGl_RT_SceneMaxPointTexture);
aShaderProgram->SetSampler (myGlContext,
"uSceneNodeInfoTexture", OpenGl_RT_SceneNodeInfoTexture);
- aShaderProgram->SetSampler (myGlContext,
- "uObjectMinPointTexture", OpenGl_RT_ObjectMinPointTexture);
- aShaderProgram->SetSampler (myGlContext,
- "uObjectMaxPointTexture", OpenGl_RT_ObjectMaxPointTexture);
- aShaderProgram->SetSampler (myGlContext,
- "uObjectNodeInfoTexture", OpenGl_RT_ObjectNodeInfoTexture);
aShaderProgram->SetSampler (myGlContext,
"uGeometryVertexTexture", OpenGl_RT_GeometryVertexTexture);
aShaderProgram->SetSampler (myGlContext,
"uGeometryNormalTexture", OpenGl_RT_GeometryNormalTexture);
aShaderProgram->SetSampler (myGlContext,
- "uGeometryTriangTexture", OpenGl_RT_GeometryTriangTexture);
+ "uGeometryTexCrdTexture", OpenGl_RT_GeometryTexCrdTexture);
aShaderProgram->SetSampler (myGlContext,
- "uRaytraceMaterialTexture", OpenGl_RT_RaytraceMaterialTexture);
- aShaderProgram->SetSampler (myGlContext,
- "uRaytraceLightSrcTexture", OpenGl_RT_RaytraceLightSrcTexture);
+ "uGeometryTriangTexture", OpenGl_RT_GeometryTriangTexture);
aShaderProgram->SetSampler (myGlContext,
"uSceneTransformTexture", OpenGl_RT_SceneTransformTexture);
aShaderProgram->SetSampler (myGlContext,
"uEnvironmentMapTexture", OpenGl_RT_EnvironmentMapTexture);
+ aShaderProgram->SetSampler (myGlContext,
+ "uRaytraceMaterialTexture", OpenGl_RT_RaytraceMaterialTexture);
+ aShaderProgram->SetSampler (myGlContext,
+ "uRaytraceLightSrcTexture", OpenGl_RT_RaytraceLightSrcTexture);
aShaderProgram->SetSampler (myGlContext,
"uOpenGlColorTexture", OpenGl_RT_OpenGlColorTexture);
aShaderProgram->GetUniformLocation (myGlContext, "uDirectLT");
myUniformLocations[anIndex][OpenGl_RT_uDirectRT] =
aShaderProgram->GetUniformLocation (myGlContext, "uDirectRT");
- myUniformLocations[anIndex][OpenGl_RT_uInvModelProj] =
- aShaderProgram->GetUniformLocation (myGlContext, "uInvModelProj");
-
- myUniformLocations[anIndex][OpenGl_RT_uLightCount] =
- aShaderProgram->GetUniformLocation (myGlContext, "uLightCount");
- myUniformLocations[anIndex][OpenGl_RT_uLightAmbnt] =
- aShaderProgram->GetUniformLocation (myGlContext, "uGlobalAmbient");
+ myUniformLocations[anIndex][OpenGl_RT_uUnviewMat] =
+ aShaderProgram->GetUniformLocation (myGlContext, "uUnviewMat");
myUniformLocations[anIndex][OpenGl_RT_uSceneRad] =
aShaderProgram->GetUniformLocation (myGlContext, "uSceneRadius");
myUniformLocations[anIndex][OpenGl_RT_uSceneEps] =
aShaderProgram->GetUniformLocation (myGlContext, "uSceneEpsilon");
-
- myUniformLocations[anIndex][OpenGl_RT_uShadEnabled] =
- aShaderProgram->GetUniformLocation (myGlContext, "uShadowsEnable");
- myUniformLocations[anIndex][OpenGl_RT_uReflEnabled] =
- aShaderProgram->GetUniformLocation (myGlContext, "uReflectionsEnable");
+ myUniformLocations[anIndex][OpenGl_RT_uLightCount] =
+ aShaderProgram->GetUniformLocation (myGlContext, "uLightCount");
+ myUniformLocations[anIndex][OpenGl_RT_uLightAmbnt] =
+ aShaderProgram->GetUniformLocation (myGlContext, "uGlobalAmbient");
myUniformLocations[anIndex][OpenGl_RT_uOffsetX] =
aShaderProgram->GetUniformLocation (myGlContext, "uOffsetX");
aShaderProgram->GetUniformLocation (myGlContext, "uOffsetY");
myUniformLocations[anIndex][OpenGl_RT_uSamples] =
aShaderProgram->GetUniformLocation (myGlContext, "uSamples");
+ myUniformLocations[anIndex][OpenGl_RT_uWinSizeX] =
+ aShaderProgram->GetUniformLocation (myGlContext, "uWinSizeX");
+ myUniformLocations[anIndex][OpenGl_RT_uWinSizeY] =
+ aShaderProgram->GetUniformLocation (myGlContext, "uWinSizeY");
- myUniformLocations[anIndex][OpenGl_RT_uEnvironmentEnable] =
+ myUniformLocations[anIndex][OpenGl_RT_uTextures] =
+ aShaderProgram->GetUniformLocation (myGlContext, "uTextureSamplers");
+
+ myUniformLocations[anIndex][OpenGl_RT_uShadEnabled] =
+ aShaderProgram->GetUniformLocation (myGlContext, "uShadowsEnable");
+ myUniformLocations[anIndex][OpenGl_RT_uReflEnabled] =
+ aShaderProgram->GetUniformLocation (myGlContext, "uReflectionsEnable");
+ myUniformLocations[anIndex][OpenGl_RT_uEnvMapEnable] =
aShaderProgram->GetUniformLocation (myGlContext, "uEnvironmentEnable");
}
NullifyResource (myGlContext, mySceneMinPointTexture);
NullifyResource (myGlContext, mySceneMaxPointTexture);
- NullifyResource (myGlContext, myObjectNodeInfoTexture);
- NullifyResource (myGlContext, myObjectMinPointTexture);
- NullifyResource (myGlContext, myObjectMaxPointTexture);
-
NullifyResource (myGlContext, myGeometryVertexTexture);
NullifyResource (myGlContext, myGeometryNormalTexture);
+ NullifyResource (myGlContext, myGeometryTexCrdTexture);
NullifyResource (myGlContext, myGeometryTriangTexture);
NullifyResource (myGlContext, mySceneTransformTexture);
}
/////////////////////////////////////////////////////////////////////////////
- // Create OpenGL texture buffers
+ // Prepare OpenGL textures
- if (mySceneNodeInfoTexture.IsNull()) // create hight-level BVH buffers
+ if (myGlContext->arbTexBindless != NULL)
{
- mySceneNodeInfoTexture = new OpenGl_TextureBufferArb;
- mySceneMinPointTexture = new OpenGl_TextureBufferArb;
- mySceneMaxPointTexture = new OpenGl_TextureBufferArb;
- mySceneTransformTexture = new OpenGl_TextureBufferArb;
-
- if (!mySceneNodeInfoTexture->Create (myGlContext)
- || !mySceneMinPointTexture->Create (myGlContext)
- || !mySceneMaxPointTexture->Create (myGlContext)
- || !mySceneTransformTexture->Create (myGlContext))
+ // If OpenGL driver supports bindless textures we need
+ // to get unique 64- bit handles for using on the GPU
+ if (!myRaytraceGeometry.UpdateTextureHandles (myGlContext))
{
#ifdef RAY_TRACE_PRINT_INFO
- std::cout << "Error: Failed to create buffers for high-level scene BVH" << std::endl;
+ std::cout << "Error: Failed to get OpenGL texture handles" << std::endl;
#endif
return Standard_False;
}
}
- if (myObjectNodeInfoTexture.IsNull()) // create bottom-level BVH buffers
+ /////////////////////////////////////////////////////////////////////////////
+ // Create OpenGL BVH buffers
+
+ if (mySceneNodeInfoTexture.IsNull()) // create scene BVH buffers
{
- myObjectNodeInfoTexture = new OpenGl_TextureBufferArb;
- myObjectMinPointTexture = new OpenGl_TextureBufferArb;
- myObjectMaxPointTexture = new OpenGl_TextureBufferArb;
+ mySceneNodeInfoTexture = new OpenGl_TextureBufferArb;
+ mySceneMinPointTexture = new OpenGl_TextureBufferArb;
+ mySceneMaxPointTexture = new OpenGl_TextureBufferArb;
+ mySceneTransformTexture = new OpenGl_TextureBufferArb;
- if (!myObjectNodeInfoTexture->Create (myGlContext)
- || !myObjectMinPointTexture->Create (myGlContext)
- || !myObjectMaxPointTexture->Create (myGlContext))
+ if (!mySceneNodeInfoTexture->Create (myGlContext)
+ || !mySceneMinPointTexture->Create (myGlContext)
+ || !mySceneMaxPointTexture->Create (myGlContext)
+ || !mySceneTransformTexture->Create (myGlContext))
{
#ifdef RAY_TRACE_PRINT_INFO
- std::cout << "Error: Failed to create buffers for bottom-level scene BVH" << std::endl;
+ std::cout << "Error: Failed to create scene BVH buffers" << std::endl;
#endif
return Standard_False;
}
}
- if (myGeometryVertexTexture.IsNull()) // create geometry buffers
+ if (myGeometryVertexTexture.IsNull()) // create geometry buffers
{
myGeometryVertexTexture = new OpenGl_TextureBufferArb;
myGeometryNormalTexture = new OpenGl_TextureBufferArb;
+ myGeometryTexCrdTexture = new OpenGl_TextureBufferArb;
myGeometryTriangTexture = new OpenGl_TextureBufferArb;
if (!myGeometryVertexTexture->Create (myGlContext)
- || !myGeometryNormalTexture->Create (myGlContext)
- || !myGeometryTriangTexture->Create (myGlContext))
+ || !myGeometryNormalTexture->Create (myGlContext)
+ || !myGeometryTexCrdTexture->Create (myGlContext)
+ || !myGeometryTriangTexture->Create (myGlContext))
{
#ifdef RAY_TRACE_PRINT_INFO
std::cout << "Error: Failed to create buffers for triangulation data" << std::endl;
}
}
- if (myRaytraceMaterialTexture.IsNull()) // create material buffer
+ if (myRaytraceMaterialTexture.IsNull()) // create material buffer
{
myRaytraceMaterialTexture = new OpenGl_TextureBufferArb;
return Standard_False;
}
}
-
- /////////////////////////////////////////////////////////////////////////////
- // Write top-level BVH buffers
-
- const NCollection_Handle<BVH_Tree<Standard_ShortReal, 4> >& aBVH = myRaytraceGeometry.BVH();
-
- bool aResult = true;
- if (!aBVH->NodeInfoBuffer().empty())
- {
- aResult &= mySceneNodeInfoTexture->Init (myGlContext, 4, GLsizei (aBVH->NodeInfoBuffer().size()),
- reinterpret_cast<const GLuint*> (&aBVH->NodeInfoBuffer().front()));
- aResult &= mySceneMinPointTexture->Init (myGlContext, 4, GLsizei (aBVH->MinPointBuffer().size()),
- reinterpret_cast<const GLfloat*> (&aBVH->MinPointBuffer().front()));
- aResult &= mySceneMaxPointTexture->Init (myGlContext, 4, GLsizei (aBVH->MaxPointBuffer().size()),
- reinterpret_cast<const GLfloat*> (&aBVH->MaxPointBuffer().front()));
- }
- if (!aResult)
- {
-#ifdef RAY_TRACE_PRINT_INFO
- std::cout << "Error: Failed to upload buffers for high-level scene BVH" << std::endl;
-#endif
- return Standard_False;
- }
-
+
/////////////////////////////////////////////////////////////////////////////
// Write transform buffer
BVH_Mat4f* aNodeTransforms = new BVH_Mat4f[myRaytraceGeometry.Size()];
- BVH_Mat4f anIdentity;
+
+ bool aResult = true;
for (Standard_Integer anElemIndex = 0; anElemIndex < myRaytraceGeometry.Size(); ++anElemIndex)
{
"OpenGl_TriangleSet does not contain transform", Standard_False);
aNodeTransforms[anElemIndex] = aTransform->Inversed();
-
}
aResult &= mySceneTransformTexture->Init (myGlContext, 4,
myRaytraceGeometry.Size() * 4, reinterpret_cast<const GLfloat*> (aNodeTransforms));
- delete[] aNodeTransforms;
+ delete [] aNodeTransforms;
/////////////////////////////////////////////////////////////////////////////
// Write geometry and bottom-level BVH buffers
aTotalBVHNodesNb += aTriangleSet->BVH()->NodeInfoBuffer().size();
}
+ aTotalBVHNodesNb += myRaytraceGeometry.BVH()->NodeInfoBuffer().size();
+
if (aTotalBVHNodesNb != 0)
{
- aResult &= myObjectNodeInfoTexture->Init (myGlContext, 4, GLsizei (aTotalBVHNodesNb), static_cast<const GLuint*> (NULL));
- aResult &= myObjectMinPointTexture->Init (myGlContext, 4, GLsizei (aTotalBVHNodesNb), static_cast<const GLfloat*> (NULL));
- aResult &= myObjectMaxPointTexture->Init (myGlContext, 4, GLsizei (aTotalBVHNodesNb), static_cast<const GLfloat*> (NULL));
+ aResult &= mySceneNodeInfoTexture->Init (
+ myGlContext, 4, GLsizei (aTotalBVHNodesNb), static_cast<const GLuint*> (NULL));
+ aResult &= mySceneMinPointTexture->Init (
+ myGlContext, 3, GLsizei (aTotalBVHNodesNb), static_cast<const GLfloat*> (NULL));
+ aResult &= mySceneMaxPointTexture->Init (
+ myGlContext, 3, GLsizei (aTotalBVHNodesNb), static_cast<const GLfloat*> (NULL));
}
if (!aResult)
if (aTotalElementsNb != 0)
{
- aResult &= myGeometryTriangTexture->Init (myGlContext, 4, GLsizei (aTotalElementsNb), static_cast<const GLuint*> (NULL));
+ aResult &= myGeometryTriangTexture->Init (
+ myGlContext, 4, GLsizei (aTotalElementsNb), static_cast<const GLuint*> (NULL));
}
if (aTotalVerticesNb != 0)
{
- aResult &= myGeometryVertexTexture->Init (myGlContext, 4, GLsizei (aTotalVerticesNb), static_cast<const GLfloat*> (NULL));
- aResult &= myGeometryNormalTexture->Init (myGlContext, 4, GLsizei (aTotalVerticesNb), static_cast<const GLfloat*> (NULL));
+ aResult &= myGeometryVertexTexture->Init (
+ myGlContext, 3, GLsizei (aTotalVerticesNb), static_cast<const GLfloat*> (NULL));
+ aResult &= myGeometryNormalTexture->Init (
+ myGlContext, 3, GLsizei (aTotalVerticesNb), static_cast<const GLfloat*> (NULL));
+ aResult &= myGeometryTexCrdTexture->Init (
+ myGlContext, 2, GLsizei (aTotalVerticesNb), static_cast<const GLfloat*> (NULL));
}
if (!aResult)
return Standard_False;
}
+ const NCollection_Handle<BVH_Tree<Standard_ShortReal, 3> >& aBVH = myRaytraceGeometry.BVH();
+ const Standard_Integer aBvhLength = aBVH->Length();
+ if (aBvhLength > 0)
+ {
+ aResult &= mySceneNodeInfoTexture->SubData (myGlContext, 0, aBVH->Length(),
+ reinterpret_cast<const GLuint*> (&aBVH->NodeInfoBuffer().front()));
+ aResult &= mySceneMinPointTexture->SubData (myGlContext, 0, aBVH->Length(),
+ reinterpret_cast<const GLfloat*> (&aBVH->MinPointBuffer().front()));
+ aResult &= mySceneMaxPointTexture->SubData (myGlContext, 0, aBVH->Length(),
+ reinterpret_cast<const GLfloat*> (&aBVH->MaxPointBuffer().front()));
+ }
+
for (Standard_Integer aNodeIdx = 0; aNodeIdx < aBVH->Length(); ++aNodeIdx)
{
if (!aBVH->IsOuter (aNodeIdx))
Standard_ASSERT_RETURN (aTriangleSet != NULL,
"Error: Failed to get triangulation of OpenGL element", Standard_False);
- const Standard_Integer aBVHOffset = myRaytraceGeometry.AccelerationOffset (aNodeIdx);
+ Standard_Integer aBVHOffset = myRaytraceGeometry.AccelerationOffset (aNodeIdx);
Standard_ASSERT_RETURN (aBVHOffset != OpenGl_RaytraceGeometry::INVALID_OFFSET,
"Error: Failed to get offset for bottom-level BVH", Standard_False);
- const size_t aBVHBuffserSize = aTriangleSet->BVH()->NodeInfoBuffer().size();
+ const Standard_Integer aBvhBuffersSize = aTriangleSet->BVH()->Length();
- if (aBVHBuffserSize != 0)
+ if (aBvhBuffersSize != 0)
{
- aResult &= myObjectNodeInfoTexture->SubData (myGlContext, aBVHOffset, GLsizei (aBVHBuffserSize),
+ aResult &= mySceneNodeInfoTexture->SubData (myGlContext, aBVHOffset, aBvhBuffersSize,
reinterpret_cast<const GLuint*> (&aTriangleSet->BVH()->NodeInfoBuffer().front()));
- aResult &= myObjectMinPointTexture->SubData (myGlContext, aBVHOffset, GLsizei (aBVHBuffserSize),
+ aResult &= mySceneMinPointTexture->SubData (myGlContext, aBVHOffset, aBvhBuffersSize,
reinterpret_cast<const GLfloat*> (&aTriangleSet->BVH()->MinPointBuffer().front()));
- aResult &= myObjectMaxPointTexture->SubData (myGlContext, aBVHOffset, GLsizei (aBVHBuffserSize),
+ aResult &= mySceneMaxPointTexture->SubData (myGlContext, aBVHOffset, aBvhBuffersSize,
reinterpret_cast<const GLfloat*> (&aTriangleSet->BVH()->MaxPointBuffer().front()));
if (!aResult)
{
{
aResult &= myGeometryNormalTexture->SubData (myGlContext, aVerticesOffset, GLsizei (aTriangleSet->Normals.size()),
reinterpret_cast<const GLfloat*> (&aTriangleSet->Normals.front()));
+ aResult &= myGeometryTexCrdTexture->SubData (myGlContext, aVerticesOffset, GLsizei (aTriangleSet->TexCrds.size()),
+ reinterpret_cast<const GLfloat*> (&aTriangleSet->TexCrds.front()));
aResult &= myGeometryVertexTexture->SubData (myGlContext, aVerticesOffset, GLsizei (aTriangleSet->Vertices.size()),
reinterpret_cast<const GLfloat*> (&aTriangleSet->Vertices.front()));
}
}
}
+ /////////////////////////////////////////////////////////////////////////////
+ // Write material buffer
+
if (myRaytraceGeometry.Materials.size() != 0)
{
- const GLfloat* aDataPtr = myRaytraceGeometry.Materials.front().Packed();
- aResult &= myRaytraceMaterialTexture->Init (myGlContext, 4, GLsizei (myRaytraceGeometry.Materials.size() * 7), aDataPtr);
+ aResult &= myRaytraceMaterialTexture->Init (myGlContext, 4,
+ GLsizei (myRaytraceGeometry.Materials.size() * 11), myRaytraceGeometry.Materials.front().Packed());
+
if (!aResult)
{
#ifdef RAY_TRACE_PRINT_INFO
myRaytraceGeometry.Objects().ChangeValue (anElemIdx).operator->());
aMemUsed += static_cast<Standard_ShortReal> (
- aTriangleSet->Vertices.size() * sizeof (BVH_Vec4f));
+ aTriangleSet->Vertices.size() * sizeof (BVH_Vec3f));
+ aMemUsed += static_cast<Standard_ShortReal> (
+ aTriangleSet->Normals.size() * sizeof (BVH_Vec3f));
aMemUsed += static_cast<Standard_ShortReal> (
- aTriangleSet->Normals.size() * sizeof (BVH_Vec4f));
+ aTriangleSet->TexCrds.size() * sizeof (BVH_Vec2f));
aMemUsed += static_cast<Standard_ShortReal> (
aTriangleSet->Elements.size() * sizeof (BVH_Vec4i));
aMemUsed += static_cast<Standard_ShortReal> (
aTriangleSet->BVH()->NodeInfoBuffer().size() * sizeof (BVH_Vec4i));
aMemUsed += static_cast<Standard_ShortReal> (
- aTriangleSet->BVH()->MinPointBuffer().size() * sizeof (BVH_Vec4f));
+ aTriangleSet->BVH()->MinPointBuffer().size() * sizeof (BVH_Vec3f));
aMemUsed += static_cast<Standard_ShortReal> (
- aTriangleSet->BVH()->MaxPointBuffer().size() * sizeof (BVH_Vec4f));
+ aTriangleSet->BVH()->MaxPointBuffer().size() * sizeof (BVH_Vec3f));
}
aMemUsed += static_cast<Standard_ShortReal> (
myRaytraceGeometry.BVH()->NodeInfoBuffer().size() * sizeof (BVH_Vec4i));
aMemUsed += static_cast<Standard_ShortReal> (
- myRaytraceGeometry.BVH()->MinPointBuffer().size() * sizeof (BVH_Vec4f));
+ myRaytraceGeometry.BVH()->MinPointBuffer().size() * sizeof (BVH_Vec3f));
aMemUsed += static_cast<Standard_ShortReal> (
- myRaytraceGeometry.BVH()->MaxPointBuffer().size() * sizeof (BVH_Vec4f));
+ myRaytraceGeometry.BVH()->MaxPointBuffer().size() * sizeof (BVH_Vec3f));
std::cout << "GPU Memory Used (MB): ~" << aMemUsed / 1048576 << std::endl;
// function : UpdateCamera
// purpose : Generates viewing rays for corners of screen quad
// =======================================================================
-void OpenGl_Workspace::UpdateCamera (const NCollection_Mat4<GLdouble>& theOrientation,
- const NCollection_Mat4<GLdouble>& theViewMapping,
- OpenGl_Vec3 theOrigins[4],
- OpenGl_Vec3 theDirects[4],
- NCollection_Mat4<GLdouble>& theInvModelProj)
+void OpenGl_Workspace::UpdateCamera (const OpenGl_Mat4& theOrientation,
+ const OpenGl_Mat4& theViewMapping,
+ OpenGl_Vec3 theOrigins[4],
+ OpenGl_Vec3 theDirects[4],
+ OpenGl_Mat4& theInvModelProj)
{
// compute inverse model-view-projection matrix
(theViewMapping * theOrientation).Inverted (theInvModelProj);
{
for (Standard_Integer aX = -1; aX <= 1; aX += 2)
{
- OpenGl_Vec4d aOrigin (GLdouble(aX),
- GLdouble(aY),
- -1.0,
- 1.0);
+ OpenGl_Vec4 aOrigin (GLfloat(aX),
+ GLfloat(aY),
+ -1.0f,
+ 1.0f);
aOrigin = theInvModelProj * aOrigin;
aOrigin.y() = aOrigin.y() / aOrigin.w();
aOrigin.z() = aOrigin.z() / aOrigin.w();
- OpenGl_Vec4d aDirect (GLdouble(aX),
- GLdouble(aY),
- 1.0,
- 1.0);
+ OpenGl_Vec4 aDirect (GLfloat(aX),
+ GLfloat(aY),
+ 1.0f,
+ 1.0f);
aDirect = theInvModelProj * aDirect;
}
}
+// =======================================================================
+// function : SetUniformState
+// purpose : Sets uniform state for the given ray-tracing shader program
+// =======================================================================
+Standard_Boolean OpenGl_Workspace::SetUniformState (const Graphic3d_CView& theCView,
+ const Standard_Integer theSizeX,
+ const Standard_Integer theSizeY,
+ const OpenGl_Vec3* theOrigins,
+ const OpenGl_Vec3* theDirects,
+ const OpenGl_Mat4& theUnviewMat,
+ const Standard_Integer theProgramIndex,
+ Handle(OpenGl_ShaderProgram)& theRaytraceProgram)
+{
+ if (theRaytraceProgram.IsNull())
+ {
+ return Standard_False;
+ }
+
+ Standard_Integer aLightSourceBufferSize =
+ static_cast<Standard_Integer> (myRaytraceGeometry.Sources.size());
+
+ Standard_Boolean aResult = Standard_True;
+
+ // Set camera state
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uOriginLB], theOrigins[0]);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uOriginRB], theOrigins[1]);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uOriginLT], theOrigins[2]);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uOriginRT], theOrigins[3]);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uDirectLB], theDirects[0]);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uDirectRB], theDirects[1]);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uDirectLT], theDirects[2]);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uDirectRT], theDirects[3]);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uUnviewMat], theUnviewMat);
+
+ // Set window size
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uWinSizeX], theSizeX);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uWinSizeY], theSizeY);
+
+ // Set scene parameters
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uSceneRad], myRaytraceSceneRadius);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uSceneEps], myRaytraceSceneEpsilon);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uLightCount], aLightSourceBufferSize);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uLightAmbnt], myRaytraceGeometry.Ambient);
+
+ // Set rendering options
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uShadEnabled], theCView.RenderParams.IsShadowEnabled ? 1 : 0);
+ aResult &= theRaytraceProgram->SetUniform (myGlContext,
+ myUniformLocations[theProgramIndex][OpenGl_RT_uReflEnabled], theCView.RenderParams.IsReflectionEnabled ? 1 : 0);
+
+ // Set array of 64-bit texture handles
+ if (myGlContext->arbTexBindless != NULL && myRaytraceGeometry.HasTextures())
+ {
+ aResult &= theRaytraceProgram->SetUniform (myGlContext, "uTextureSamplers",
+ static_cast<GLsizei> (myRaytraceGeometry.TextureHandles().size()), &myRaytraceGeometry.TextureHandles()[0]);
+ }
+
+ if (!aResult)
+ {
+#ifdef RAY_TRACE_PRINT_INFO
+ std::cout << "Info: Not all uniforms were detected (for program " << theProgramIndex << ")" << std::endl;
+#endif
+ }
+
+ return aResult;
+}
+
// =======================================================================
// function : RunRaytraceShaders
// purpose : Runs ray-tracing shader programs
const Standard_Integer theSizeY,
const OpenGl_Vec3 theOrigins[4],
const OpenGl_Vec3 theDirects[4],
- const OpenGl_Matrix& theInvModelProj,
+ const OpenGl_Mat4& theUnviewMat,
OpenGl_FrameBuffer* theFrameBuffer)
{
mySceneMinPointTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMinPointTexture);
mySceneMaxPointTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMaxPointTexture);
mySceneNodeInfoTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneNodeInfoTexture);
- myObjectMinPointTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_ObjectMinPointTexture);
- myObjectMaxPointTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_ObjectMaxPointTexture);
- myObjectNodeInfoTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_ObjectNodeInfoTexture);
myGeometryVertexTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryVertexTexture);
myGeometryNormalTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryNormalTexture);
+ myGeometryTexCrdTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryTexCrdTexture);
myGeometryTriangTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryTriangTexture);
mySceneTransformTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneTransformTexture);
myRaytraceMaterialTexture->BindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_RaytraceMaterialTexture);
myGlContext->BindProgram (myRaytraceProgram);
- Standard_Integer aLightSourceBufferSize =
- static_cast<Standard_Integer> (myRaytraceGeometry.Sources.size());
-
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uOriginLB], theOrigins[0]);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uOriginRB], theOrigins[1]);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uOriginLT], theOrigins[2]);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uOriginRT], theOrigins[3]);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uDirectLB], theDirects[0]);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uDirectRB], theDirects[1]);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uDirectLT], theDirects[2]);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uDirectRT], theDirects[3]);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uInvModelProj], theInvModelProj);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uSceneRad], myRaytraceSceneRadius);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uSceneEps], myRaytraceSceneEpsilon);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uLightCount], aLightSourceBufferSize);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uLightAmbnt], myRaytraceGeometry.Ambient);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uShadEnabled], theCView.RenderParams.IsShadowEnabled ? 1 : 0);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[0][OpenGl_RT_uReflEnabled], theCView.RenderParams.IsReflectionEnabled ? 1 : 0);
+ SetUniformState (theCView,
+ theSizeX,
+ theSizeY,
+ theOrigins,
+ theDirects,
+ theUnviewMat,
+ 0, // ID of RT program
+ myRaytraceProgram);
myGlContext->core20fwd->glEnableVertexAttribArray (Graphic3d_TOA_POS);
{
myGlContext->core15fwd->glDrawArrays (GL_TRIANGLES, 0, 6);
}
myGlContext->core20fwd->glDisableVertexAttribArray (Graphic3d_TOA_POS);
-
+
if (!theCView.RenderParams.IsAntialiasingEnabled)
{
myGlContext->BindProgram (NULL);
myOpenGlFBO->ColorTexture()->Unbind (myGlContext, GL_TEXTURE0 + OpenGl_RT_OpenGlColorTexture);
myOpenGlFBO->DepthStencilTexture()->Unbind (myGlContext, GL_TEXTURE0 + OpenGl_RT_OpenGlDepthTexture);
- mySceneMinPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMinPointTexture);
- mySceneMaxPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMaxPointTexture);
- mySceneNodeInfoTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneNodeInfoTexture);
- myObjectMinPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_ObjectMinPointTexture);
- myObjectMaxPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_ObjectMaxPointTexture);
- myObjectNodeInfoTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_ObjectNodeInfoTexture);
+ mySceneMinPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMinPointTexture);
+ mySceneMaxPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMaxPointTexture);
+ mySceneNodeInfoTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneNodeInfoTexture);
myGeometryVertexTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryVertexTexture);
myGeometryNormalTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryNormalTexture);
+ myGeometryTexCrdTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryTexCrdTexture);
myGeometryTriangTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryTriangTexture);
+ mySceneTransformTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneTransformTexture);
myRaytraceMaterialTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_RaytraceMaterialTexture);
myRaytraceLightSrcTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_RaytraceLightSrcTexture);
- mySceneTransformTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneTransformTexture);
myGlContext->core15fwd->glActiveTexture (GL_TEXTURE0);
myGlContext->BindProgram (myPostFSAAProgram);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uOriginLB], theOrigins[0]);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uOriginRB], theOrigins[1]);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uOriginLT], theOrigins[2]);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uOriginRT], theOrigins[3]);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uDirectLB], theDirects[0]);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uDirectRB], theDirects[1]);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uDirectLT], theDirects[2]);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uDirectRT], theDirects[3]);
- myRaytraceProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uInvModelProj], theInvModelProj);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uSceneRad], myRaytraceSceneRadius);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uSceneEps], myRaytraceSceneEpsilon);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uLightCount], aLightSourceBufferSize);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uLightAmbnt], myRaytraceGeometry.Ambient);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uShadEnabled], theCView.RenderParams.IsShadowEnabled ? 1 : 0);
- myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uReflEnabled], theCView.RenderParams.IsReflectionEnabled ? 1 : 0);
-
- const Standard_ShortReal aMaxOffset = 0.559017f;
- const Standard_ShortReal aMinOffset = 0.186339f;
+ SetUniformState (theCView,
+ theSizeX,
+ theSizeY,
+ theOrigins,
+ theDirects,
+ theUnviewMat,
+ 1, // ID of FSAA program
+ myPostFSAAProgram);
myGlContext->core20fwd->glEnableVertexAttribArray (Graphic3d_TOA_POS);
myGlContext->core20fwd->glVertexAttribPointer (Graphic3d_TOA_POS, 3, GL_FLOAT, GL_FALSE, 0, NULL);
- // Perform multi-pass adaptive FSAA using ping-pong technique
- // rotated grid AA always uses 4 samples
- for (Standard_Integer anIt = 0; anIt < 4; ++anIt)
+ // Perform multi-pass adaptive FSAA using ping-pong technique.
+ // We use 'FLIPTRI' sampling pattern changing for every pixel
+ // (3 additional samples per pixel, the 1st sample is already
+ // available from initial ray-traced image).
+ for (Standard_Integer anIt = 1; anIt < 4; ++anIt)
{
GLfloat aOffsetX = 1.f / theSizeX;
GLfloat aOffsetY = 1.f / theSizeY;
- if (anIt < 2)
+ if (anIt == 1)
{
- aOffsetX *= anIt < 1 ? aMinOffset : -aMaxOffset;
- aOffsetY *= anIt < 1 ? aMaxOffset : aMinOffset;
+ aOffsetX *= -0.55f;
+ aOffsetY *= 0.55f;
}
- else
+ else if (anIt == 2)
{
- aOffsetX *= anIt > 2 ? aMaxOffset : -aMinOffset;
- aOffsetY *= anIt > 2 ? -aMinOffset : -aMaxOffset;
+ aOffsetX *= 0.00f;
+ aOffsetY *= -0.55f;
}
-
+ else if (anIt == 3)
+ {
+ aOffsetX *= 0.55f;
+ aOffsetY *= 0.00f;
+ }
+
myPostFSAAProgram->SetUniform (myGlContext,
- myUniformLocations[1][OpenGl_RT_uSamples], anIt + 2);
+ myUniformLocations[1][OpenGl_RT_uSamples], anIt + 1);
myPostFSAAProgram->SetUniform (myGlContext,
myUniformLocations[1][OpenGl_RT_uOffsetX], aOffsetX);
myPostFSAAProgram->SetUniform (myGlContext,
myUniformLocations[1][OpenGl_RT_uOffsetY], aOffsetY);
- Handle(OpenGl_FrameBuffer)& aFramebuffer = anIt % 2 ? myRaytraceFBO1 : myRaytraceFBO2;
+ Handle(OpenGl_FrameBuffer)& aFramebuffer = anIt % 2 ? myRaytraceFBO2 : myRaytraceFBO1;
if (anIt == 3) // disable FBO on last iteration
{
{
aFramebuffer->BindBuffer (myGlContext);
}
-
+
myGlContext->core15fwd->glDrawArrays (GL_TRIANGLES, 0, 6);
if (anIt != 3) // set input for the next pass
myRaytraceFBO1->ColorTexture()->Unbind (myGlContext, GL_TEXTURE0 + OpenGl_RT_FSAAInputTexture);
myOpenGlFBO->ColorTexture()->Unbind (myGlContext, GL_TEXTURE0 + OpenGl_RT_OpenGlColorTexture);
myOpenGlFBO->DepthStencilTexture()->Unbind (myGlContext, GL_TEXTURE0 + OpenGl_RT_OpenGlDepthTexture);
- mySceneMinPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMinPointTexture);
- mySceneMaxPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMaxPointTexture);
- mySceneNodeInfoTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneNodeInfoTexture);
- myObjectMinPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_ObjectMinPointTexture);
- myObjectMaxPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_ObjectMaxPointTexture);
- myObjectNodeInfoTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_ObjectNodeInfoTexture);
+ mySceneMinPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMinPointTexture);
+ mySceneMaxPointTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneMaxPointTexture);
+ mySceneNodeInfoTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneNodeInfoTexture);
myGeometryVertexTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryVertexTexture);
myGeometryNormalTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryNormalTexture);
+ myGeometryTexCrdTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryTexCrdTexture);
myGeometryTriangTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_GeometryTriangTexture);
+ mySceneTransformTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneTransformTexture);
myRaytraceMaterialTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_RaytraceMaterialTexture);
myRaytraceLightSrcTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_RaytraceLightSrcTexture);
- mySceneTransformTexture->UnbindTexture (myGlContext, GL_TEXTURE0 + OpenGl_RT_SceneTransformTexture);
myGlContext->core15fwd->glActiveTexture (GL_TEXTURE0);
Standard_Boolean OpenGl_Workspace::Raytrace (const Graphic3d_CView& theCView,
const Standard_Integer theSizeX,
const Standard_Integer theSizeY,
- const Standard_Boolean theToSwap,
const Aspect_CLayer2d& theCOverLayer,
const Aspect_CLayer2d& theCUnderLayer,
OpenGl_FrameBuffer* theFrameBuffer)
{
- if (!InitRaytraceResources (theCView))
- return Standard_False;
-
if (!ResizeRaytraceBuffers (theSizeX, theSizeY))
return Standard_False;
return Standard_False;
// Get model-view and projection matrices
- TColStd_Array2OfReal theOrientation (0, 3, 0, 3);
- TColStd_Array2OfReal theViewMapping (0, 3, 0, 3);
-
- myView->GetMatrices (theOrientation, theViewMapping);
+ OpenGl_Mat4 aOrientationMatrix;
+ OpenGl_Mat4 aViewMappingMatrix;
- NCollection_Mat4<GLdouble> aOrientationMatrix;
- NCollection_Mat4<GLdouble> aViewMappingMatrix;
+ myView->GetMatrices (aOrientationMatrix,
+ aViewMappingMatrix);
- for (Standard_Integer j = 0; j < 4; ++j)
- {
- for (Standard_Integer i = 0; i < 4; ++i)
- {
- aOrientationMatrix [4 * j + i] = theOrientation (i, j);
- aViewMappingMatrix [4 * j + i] = theViewMapping (i, j);
- }
- }
-
- NCollection_Mat4<GLdouble> aInvOrientationMatrix;
+ OpenGl_Mat4 aInvOrientationMatrix;
aOrientationMatrix.Inverted (aInvOrientationMatrix);
if (!UpdateRaytraceLightSources (aInvOrientationMatrix))
OpenGl_Vec3 aOrigins[4];
OpenGl_Vec3 aDirects[4];
- NCollection_Mat4<GLdouble> anInvModelProj;
+ OpenGl_Mat4 anUnviewMat;
UpdateCamera (aOrientationMatrix,
aViewMappingMatrix,
aOrigins,
aDirects,
- anInvModelProj);
-
- OpenGl_Matrix anInvModelProjMatrix;
- for (Standard_Integer j = 0; j < 4; ++j)
- {
- for (Standard_Integer i = 0; i < 4; ++i)
- {
- anInvModelProjMatrix.mat[j][i] = static_cast<GLfloat>(anInvModelProj.GetValue(i,j));
- }
- }
+ anUnviewMat);
Standard_Boolean wasBlendingEnabled = glIsEnabled (GL_BLEND);
Standard_Boolean wasDepthTestEnabled = glIsEnabled (GL_DEPTH_TEST);
glClear (GL_COLOR_BUFFER_BIT);
- myView->DrawBackground (*this);
+ myView->DrawBackground (this);
- myView->RedrawLayer2d (myPrintContext, theCView, theCUnderLayer);
+ myView->RedrawLayer2d (myPrintContext, this, theCView, theCUnderLayer);
-#if !defined(GL_ES_VERSION_2_0)
- // Generate ray-traced image
- glMatrixMode (GL_PROJECTION);
- glPushMatrix();
- glLoadIdentity();
+ myGlContext->WorldViewState.Push();
+ myGlContext->ProjectionState.Push();
- glMatrixMode (GL_MODELVIEW);
- glPushMatrix();
- glLoadIdentity();
-#endif
+ myGlContext->WorldViewState.SetIdentity();
+ myGlContext->ProjectionState.SetIdentity();
+
+ myGlContext->ApplyProjectionMatrix();
+ myGlContext->ApplyWorldViewMatrix();
glEnable (GL_BLEND);
glBlendFunc (GL_ONE, GL_SRC_ALPHA);
+ // Generate ray-traced image
if (myIsRaytraceDataValid)
{
myRaytraceScreenQuad.Bind (myGlContext);
+ if (!myRaytraceGeometry.AcquireTextures (myGlContext))
+ {
+ const TCollection_ExtendedString aMessage = "Error: Failed to acquire OpenGL image textures";
+
+ myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
+ GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_MEDIUM_ARB, aMessage);
+ }
+
RunRaytraceShaders (theCView,
theSizeX,
theSizeY,
aOrigins,
aDirects,
- anInvModelProjMatrix,
+ anUnviewMat,
theFrameBuffer);
+ if (!myRaytraceGeometry.ReleaseTextures (myGlContext))
+ {
+ const TCollection_ExtendedString aMessage = "Error: Failed to release OpenGL image textures";
+
+ myGlContext->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB,
+ GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_MEDIUM_ARB, aMessage);
+ }
+
myRaytraceScreenQuad.Unbind (myGlContext);
}
if (wasDepthTestEnabled)
glEnable (GL_DEPTH_TEST);
-#if !defined(GL_ES_VERSION_2_0)
- glMatrixMode (GL_PROJECTION);
- glPopMatrix();
- glMatrixMode (GL_MODELVIEW);
- glPopMatrix();
-#endif
+ myGlContext->WorldViewState.Pop();
+ myGlContext->ProjectionState.Pop();
+
+ myGlContext->ApplyProjectionMatrix();
// Redraw trihedron
myView->RedrawTrihedron (this);
// Redraw overlay
const int aMode = 0;
DisplayCallback (theCView, (aMode | OCC_PRE_OVERLAY));
- myView->RedrawLayer2d (myPrintContext, theCView, theCOverLayer);
+ myView->RedrawLayer2d (myPrintContext, this, theCView, theCOverLayer);
DisplayCallback (theCView, aMode);
-
- // Swap the buffers
- if (theToSwap)
- {
- GetGlContext()->SwapBuffers();
- myBackBufferRestored = Standard_False;
- }
- else
- {
- glFlush();
- }
-
return Standard_True;
}