X-Git-Url: http://git.dev.opencascade.org/gitweb/?p=occt.git;a=blobdiff_plain;f=src%2FOpenGl%2FOpenGl_ShaderProgram.cxx;h=a539ac7aa8d646e14a0f925e3c6fc34f2a705333;hp=7a7ffcd646c279aaf103273b2c401bbc826d383d;hb=af99433e4ea0658d2c4d8b7274e6de22853f4f81;hpb=bd0b3e60979f776c5a2719dac4a2db67c8d427dc diff --git a/src/OpenGl/OpenGl_ShaderProgram.cxx b/src/OpenGl/OpenGl_ShaderProgram.cxx old mode 100644 new mode 100755 index 7a7ffcd646..a539ac7aa8 --- a/src/OpenGl/OpenGl_ShaderProgram.cxx +++ b/src/OpenGl/OpenGl_ShaderProgram.cxx @@ -1,25 +1,22 @@ // Created on: 2013-09-19 // Created by: Denis BOGOLEPOV -// Copyright (c) 2013 OPEN CASCADE SAS +// Copyright (c) 2013-2014 OPEN CASCADE SAS // -// The content of this file is subject to the Open CASCADE Technology Public -// License Version 6.5 (the "License"). You may not use the content of this file -// except in compliance with the License. Please obtain a copy of the License -// at http://www.opencascade.org and read it completely before using this file. +// This file is part of Open CASCADE Technology software library. // -// The Initial Developer of the Original Code is Open CASCADE S.A.S., having its -// main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France. +// This library is free software; you can redistribute it and/or modify it under +// the terms of the GNU Lesser General Public License version 2.1 as published +// by the Free Software Foundation, with special exception defined in the file +// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT +// distribution for complete text of the license and disclaimer of any warranty. // -// The Original Code and all software distributed under the License is -// distributed on an "AS IS" basis, without warranty of any kind, and the -// Initial Developer hereby disclaims all such warranties, including without -// limitation, any warranties of merchantability, fitness for a particular -// purpose or non-infringement. Please see the License for the specific terms -// and conditions governing the rights and limitations under the License. +// Alternatively, this file may be used under the terms of Open CASCADE +// commercial license or contractual agreement. #include #include +#include #include #include #include @@ -27,6 +24,7 @@ #include #include #include +#include IMPLEMENT_STANDARD_HANDLE (OpenGl_ShaderProgram, OpenGl_Resource) IMPLEMENT_STANDARD_RTTIEXT(OpenGl_ShaderProgram, OpenGl_Resource) @@ -36,153 +34,36 @@ OpenGl_VariableSetterSelector OpenGl_ShaderProgram::mySetterSelector = OpenGl_Va // Declare OCCT-specific OpenGL/GLSL shader variables Standard_CString OpenGl_ShaderProgram::PredefinedKeywords[] = { - /* OpenGl_OCC_MODEL_WORLD_MATRIX */ "occModelWorldMatrix", - /* OpenGl_OCC_WORLD_VIEW_MATRIX */ "occWorldViewMatrix", - /* OpenGl_OCC_PROJECTION_MATRIX */ "occProjectionMatrix", - /* OpenGl_OCC_MODEL_WORLD_MATRIX_INVERSE */ "occModelWorldMatrixInverse", - /* OpenGl_OCC_WORLD_VIEW_MATRIX_INVERSE */ "occWorldViewMatrixInverse", - /* OpenGl_OCC_PROJECTION_MATRIX_INVERSE */ "occProjectionMatrixInverse", - /* OpenGl_OCC_MODEL_WORLD_MATRIX_TRANSPOSE */ "occModelWorldMatrixTranspose", - /* OpenGl_OCC_WORLD_VIEW_MATRIX_TRANSPOSE */ "occWorldViewMatrixTranspose", - /* OpenGl_OCC_PROJECTION_MATRIX_TRANSPOSE */ "occProjectionMatrixTranspose", - /* OpenGl_OCC_MODEL_WORLD_MATRIX_INVERSE_TRANSPOSE */ "occModelWorldMatrixInverseTranspose", - /* OpenGl_OCC_WORLD_VIEW_MATRIX_INVERSE_TRANSPOSE */ "occWorldViewMatrixInverseTranspose", - /* OpenGl_OCC_PROJECTION_MATRIX_INVERSE_TRANSPOSE */ "occProjectionMatrixInverseTranspose", - - /* OpenGl_OCC_CLIP_PLANE_0_EQUATION */ "occClipPlanes[0].Equation", - /* OpenGl_OCC_CLIP_PLANE_1_EQUATION */ "occClipPlanes[1].Equation", - /* OpenGl_OCC_CLIP_PLANE_2_EQUATION */ "occClipPlanes[2].Equation", - /* OpenGl_OCC_CLIP_PLANE_3_EQUATION */ "occClipPlanes[3].Equation", - /* OpenGl_OCC_CLIP_PLANE_4_EQUATION */ "occClipPlanes[4].Equation", - /* OpenGl_OCC_CLIP_PLANE_5_EQUATION */ "occClipPlanes[5].Equation", - /* OpenGl_OCC_CLIP_PLANE_6_EQUATION */ "occClipPlanes[6].Equation", - /* OpenGl_OCC_CLIP_PLANE_7_EQUATION */ "occClipPlanes[7].Equation", - - /* OpenGl_OCC_CLIP_PLANE_0_SPACE */ "occClipPlanes[0].Space", - /* OpenGl_OCC_CLIP_PLANE_1_SPACE */ "occClipPlanes[1].Space", - /* OpenGl_OCC_CLIP_PLANE_2_SPACE */ "occClipPlanes[2].Space", - /* OpenGl_OCC_CLIP_PLANE_3_SPACE */ "occClipPlanes[3].Space", - /* OpenGl_OCC_CLIP_PLANE_4_SPACE */ "occClipPlanes[4].Space", - /* OpenGl_OCC_CLIP_PLANE_5_SPACE */ "occClipPlanes[5].Space", - /* OpenGl_OCC_CLIP_PLANE_6_SPACE */ "occClipPlanes[6].Space", - /* OpenGl_OCC_CLIP_PLANE_7_SPACE */ "occClipPlanes[7].Space", - - /* OpenGl_OCC_LIGHT_SOURCE_COUNT */ "occLightSourcesCount", - - /* OpenGl_OCC_LIGHT_SOURCE_0_TYPE */ "occLightSources[0].Type", - /* OpenGl_OCC_LIGHT_SOURCE_1_TYPE */ "occLightSources[1].Type", - /* OpenGl_OCC_LIGHT_SOURCE_2_TYPE */ "occLightSources[2].Type", - /* OpenGl_OCC_LIGHT_SOURCE_3_TYPE */ "occLightSources[3].Type", - /* OpenGl_OCC_LIGHT_SOURCE_4_TYPE */ "occLightSources[4].Type", - /* OpenGl_OCC_LIGHT_SOURCE_5_TYPE */ "occLightSources[5].Type", - /* OpenGl_OCC_LIGHT_SOURCE_6_TYPE */ "occLightSources[6].Type", - /* OpenGl_OCC_LIGHT_SOURCE_7_TYPE */ "occLightSources[7].Type", - - /* OpenGl_OCC_LIGHT_SOURCE_0_HEAD */ "occLightSources[0].Head", - /* OpenGl_OCC_LIGHT_SOURCE_1_HEAD */ "occLightSources[1].Head", - /* OpenGl_OCC_LIGHT_SOURCE_2_HEAD */ "occLightSources[2].Head", - /* OpenGl_OCC_LIGHT_SOURCE_3_HEAD */ "occLightSources[3].Head", - /* OpenGl_OCC_LIGHT_SOURCE_4_HEAD */ "occLightSources[4].Head", - /* OpenGl_OCC_LIGHT_SOURCE_5_HEAD */ "occLightSources[5].Head", - /* OpenGl_OCC_LIGHT_SOURCE_6_HEAD */ "occLightSources[6].Head", - /* OpenGl_OCC_LIGHT_SOURCE_7_HEAD */ "occLightSources[7].Head", - - /* OpenGl_OCC_LIGHT_SOURCE_0_AMBIENT */ "occLightSources[0].Ambient", - /* OpenGl_OCC_LIGHT_SOURCE_1_AMBIENT */ "occLightSources[1].Ambient", - /* OpenGl_OCC_LIGHT_SOURCE_2_AMBIENT */ "occLightSources[2].Ambient", - /* OpenGl_OCC_LIGHT_SOURCE_3_AMBIENT */ "occLightSources[3].Ambient", - /* OpenGl_OCC_LIGHT_SOURCE_4_AMBIENT */ "occLightSources[4].Ambient", - /* OpenGl_OCC_LIGHT_SOURCE_5_AMBIENT */ "occLightSources[5].Ambient", - /* OpenGl_OCC_LIGHT_SOURCE_6_AMBIENT */ "occLightSources[6].Ambient", - /* OpenGl_OCC_LIGHT_SOURCE_7_AMBIENT */ "occLightSources[7].Ambient", - - /* OpenGl_OCC_LIGHT_SOURCE_0_DIFFUSE */ "occLightSources[0].Diffuse", - /* OpenGl_OCC_LIGHT_SOURCE_1_DIFFUSE */ "occLightSources[1].Diffuse", - /* OpenGl_OCC_LIGHT_SOURCE_2_DIFFUSE */ "occLightSources[2].Diffuse", - /* OpenGl_OCC_LIGHT_SOURCE_3_DIFFUSE */ "occLightSources[3].Diffuse", - /* OpenGl_OCC_LIGHT_SOURCE_4_DIFFUSE */ "occLightSources[4].Diffuse", - /* OpenGl_OCC_LIGHT_SOURCE_5_DIFFUSE */ "occLightSources[5].Diffuse", - /* OpenGl_OCC_LIGHT_SOURCE_6_DIFFUSE */ "occLightSources[6].Diffuse", - /* OpenGl_OCC_LIGHT_SOURCE_7_DIFFUSE */ "occLightSources[7].Diffuse", - - /* OpenGl_OCC_LIGHT_SOURCE_0_SPECULAR */ "occLightSources[0].Specular", - /* OpenGl_OCC_LIGHT_SOURCE_1_SPECULAR */ "occLightSources[1].Specular", - /* OpenGl_OCC_LIGHT_SOURCE_2_SPECULAR */ "occLightSources[2].Specular", - /* OpenGl_OCC_LIGHT_SOURCE_3_SPECULAR */ "occLightSources[3].Specular", - /* OpenGl_OCC_LIGHT_SOURCE_4_SPECULAR */ "occLightSources[4].Specular", - /* OpenGl_OCC_LIGHT_SOURCE_5_SPECULAR */ "occLightSources[5].Specular", - /* OpenGl_OCC_LIGHT_SOURCE_6_SPECULAR */ "occLightSources[6].Specular", - /* OpenGl_OCC_LIGHT_SOURCE_7_SPECULAR */ "occLightSources[7].Specular", - - /* OpenGl_OCC_LIGHT_SOURCE_0_POSITION */ "occLightSources[0].Position", - /* OpenGl_OCC_LIGHT_SOURCE_1_POSITION */ "occLightSources[1].Position", - /* OpenGl_OCC_LIGHT_SOURCE_2_POSITION */ "occLightSources[2].Position", - /* OpenGl_OCC_LIGHT_SOURCE_3_POSITION */ "occLightSources[3].Position", - /* OpenGl_OCC_LIGHT_SOURCE_4_POSITION */ "occLightSources[4].Position", - /* OpenGl_OCC_LIGHT_SOURCE_5_POSITION */ "occLightSources[5].Position", - /* OpenGl_OCC_LIGHT_SOURCE_6_POSITION */ "occLightSources[6].Position", - /* OpenGl_OCC_LIGHT_SOURCE_7_POSITION */ "occLightSources[7].Position", - - /* OpenGl_OCC_LIGHT_SOURCE_0_SPOT_CUTOFF */ "occLightSources[0].SpotCutoff", - /* OpenGl_OCC_LIGHT_SOURCE_1_SPOT_CUTOFF */ "occLightSources[1].SpotCutoff", - /* OpenGl_OCC_LIGHT_SOURCE_2_SPOT_CUTOFF */ "occLightSources[2].SpotCutoff", - /* OpenGl_OCC_LIGHT_SOURCE_3_SPOT_CUTOFF */ "occLightSources[3].SpotCutoff", - /* OpenGl_OCC_LIGHT_SOURCE_4_SPOT_CUTOFF */ "occLightSources[4].SpotCutoff", - /* OpenGl_OCC_LIGHT_SOURCE_5_SPOT_CUTOFF */ "occLightSources[5].SpotCutoff", - /* OpenGl_OCC_LIGHT_SOURCE_6_SPOT_CUTOFF */ "occLightSources[6].SpotCutoff", - /* OpenGl_OCC_LIGHT_SOURCE_7_SPOT_CUTOFF */ "occLightSources[7].SpotCutoff", - - /* OpenGl_OCC_LIGHT_SOURCE_0_SPOT_EXPONENT */ "occLightSources[0].SpotExponent", - /* OpenGl_OCC_LIGHT_SOURCE_1_SPOT_EXPONENT */ "occLightSources[1].SpotExponent", - /* OpenGl_OCC_LIGHT_SOURCE_2_SPOT_EXPONENT */ "occLightSources[2].SpotExponent", - /* OpenGl_OCC_LIGHT_SOURCE_3_SPOT_EXPONENT */ "occLightSources[3].SpotExponent", - /* OpenGl_OCC_LIGHT_SOURCE_4_SPOT_EXPONENT */ "occLightSources[4].SpotExponent", - /* OpenGl_OCC_LIGHT_SOURCE_5_SPOT_EXPONENT */ "occLightSources[5].SpotExponent", - /* OpenGl_OCC_LIGHT_SOURCE_6_SPOT_EXPONENT */ "occLightSources[6].SpotExponent", - /* OpenGl_OCC_LIGHT_SOURCE_7_SPOT_EXPONENT */ "occLightSources[7].SpotExponent", - - /* OpenGl_OCC_LIGHT_SOURCE_0_SPOT_DIRECTION */ "occLightSources[0].SpotDirection", - /* OpenGl_OCC_LIGHT_SOURCE_1_SPOT_DIRECTION */ "occLightSources[1].SpotDirection", - /* OpenGl_OCC_LIGHT_SOURCE_2_SPOT_DIRECTION */ "occLightSources[2].SpotDirection", - /* OpenGl_OCC_LIGHT_SOURCE_3_SPOT_DIRECTION */ "occLightSources[3].SpotDirection", - /* OpenGl_OCC_LIGHT_SOURCE_4_SPOT_DIRECTION */ "occLightSources[4].SpotDirection", - /* OpenGl_OCC_LIGHT_SOURCE_5_SPOT_DIRECTION */ "occLightSources[5].SpotDirection", - /* OpenGl_OCC_LIGHT_SOURCE_6_SPOT_DIRECTION */ "occLightSources[6].SpotDirection", - /* OpenGl_OCC_LIGHT_SOURCE_7_SPOT_DIRECTION */ "occLightSources[7].SpotDirection", - - /* OpenGl_OCC_LIGHT_SOURCE_0_CONST_ATTENUATION */ "occLightSources[0].ConstAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_1_CONST_ATTENUATION */ "occLightSources[1].ConstAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_2_CONST_ATTENUATION */ "occLightSources[2].ConstAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_3_CONST_ATTENUATION */ "occLightSources[3].ConstAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_4_CONST_ATTENUATION */ "occLightSources[4].ConstAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_5_CONST_ATTENUATION */ "occLightSources[5].ConstAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_6_CONST_ATTENUATION */ "occLightSources[6].ConstAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_7_CONST_ATTENUATION */ "occLightSources[7].ConstAttenuation", - - /* OpenGl_OCC_LIGHT_SOURCE_0_LINEAR_ATTENUATION */ "occLightSources[0].LinearAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_1_LINEAR_ATTENUATION */ "occLightSources[1].LinearAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_2_LINEAR_ATTENUATION */ "occLightSources[2].LinearAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_3_LINEAR_ATTENUATION */ "occLightSources[3].LinearAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_4_LINEAR_ATTENUATION */ "occLightSources[4].LinearAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_5_LINEAR_ATTENUATION */ "occLightSources[5].LinearAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_6_LINEAR_ATTENUATION */ "occLightSources[6].LinearAttenuation", - /* OpenGl_OCC_LIGHT_SOURCE_7_LINEAR_ATTENUATION */ "occLightSources[7].LinearAttenuation", - - /* OpenGl_OCCT_ACTIVE_SAMPLER */ "occActiveSampler", - /* OpenGl_OCCT_TEXTURE_ENABLE */ "occTextureEnable", - /* OpenGl_OCCT_DISTINGUISH_MODE */ "occDistinguishingMode", - /* OpenGl_OCCT_FRONT_MATERIAL_AMBIENT */ "occFrontMaterial.Ambient", - /* OpenGl_OCCT_BACK_MATERIAL_AMBIENT */ "occBackMaterial.Ambient", - /* OpenGl_OCCT_FRONT_MATERIAL_DIFFUSE */ "occFrontMaterial.Diffuse", - /* OpenGl_OCCT_BACK_MATERIAL_DIFFUSE */ "occBackMaterial.Diffuse", - /* OpenGl_OCCT_FRONT_MATERIAL_SPECULAR */ "occFrontMaterial.Specular", - /* OpenGl_OCCT_BACK_MATERIAL_SPECULAR */ "occBackMaterial.Specular", - /* OpenGl_OCCT_FRONT_MATERIAL_EMISSION */ "occFrontMaterial.Emission", - /* OpenGl_OCCT_BACK_MATERIAL_EMISSION */ "occBackMaterial.Emission", - /* OpenGl_OCCT_FRONT_MATERIAL_SHININESS */ "occFrontMaterial.Shininess", - /* OpenGl_OCCT_BACK_MATERIAL_SHININESS */ "occBackMaterial.Shininess", - /* OpenGl_OCCT_FRONT_MATERIAL_TRANSPARENCY */ "occFrontMaterial.Transparency", - /* OpenGl_OCCT_BACK_MATERIAL_TRANSPARENCY */ "occBackMaterial.Transparency" + "occModelWorldMatrix", // OpenGl_OCC_MODEL_WORLD_MATRIX + "occWorldViewMatrix", // OpenGl_OCC_WORLD_VIEW_MATRIX + "occProjectionMatrix", // OpenGl_OCC_PROJECTION_MATRIX + "occModelWorldMatrixInverse", // OpenGl_OCC_MODEL_WORLD_MATRIX_INVERSE + "occWorldViewMatrixInverse", // OpenGl_OCC_WORLD_VIEW_MATRIX_INVERSE + "occProjectionMatrixInverse", // OpenGl_OCC_PROJECTION_MATRIX_INVERSE + "occModelWorldMatrixTranspose", // OpenGl_OCC_MODEL_WORLD_MATRIX_TRANSPOSE + "occWorldViewMatrixTranspose", // OpenGl_OCC_WORLD_VIEW_MATRIX_TRANSPOSE + "occProjectionMatrixTranspose", // OpenGl_OCC_PROJECTION_MATRIX_TRANSPOSE + "occModelWorldMatrixInverseTranspose", // OpenGl_OCC_MODEL_WORLD_MATRIX_INVERSE_TRANSPOSE + "occWorldViewMatrixInverseTranspose", // OpenGl_OCC_WORLD_VIEW_MATRIX_INVERSE_TRANSPOSE + "occProjectionMatrixInverseTranspose", // OpenGl_OCC_PROJECTION_MATRIX_INVERSE_TRANSPOSE + + "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 + "occLightSources", // OpenGl_OCC_LIGHT_SOURCE_PARAMS + "occLightAmbient", // OpenGl_OCC_LIGHT_AMBIENT + + "occActiveSampler", // OpenGl_OCCT_ACTIVE_SAMPLER + "occTextureEnable", // OpenGl_OCCT_TEXTURE_ENABLE + "occDistinguishingMode", // OpenGl_OCCT_DISTINGUISH_MODE + "occFrontMaterial", // OpenGl_OCCT_FRONT_MATERIAL + "occBackMaterial", // OpenGl_OCCT_BACK_MATERIAL + "occColor", // OpenGl_OCCT_COLOR + + "occPointSize" // OpenGl_OCCT_POINT_SIZE }; @@ -238,7 +119,8 @@ void OpenGl_VariableSetterSelector::Set (const Handle(OpenGl_Context)& // ======================================================================= OpenGl_ShaderProgram::OpenGl_ShaderProgram (const Handle(Graphic3d_ShaderProgram)& theProxy) : myProgramID (NO_PROGRAM), - myProxy (theProxy) + myProxy (theProxy), + myShareCount(1) { memset (myCurrentState, 0, sizeof (myCurrentState)); for (GLint aVar = 0; aVar < OpenGl_OCCT_NUMBER_OF_STATE_VARIABLES; ++aVar) @@ -259,53 +141,42 @@ Standard_Boolean OpenGl_ShaderProgram::Initialize (const Handle(OpenGl_Context)& return Standard_False; } - GLchar *aShaderDir = getenv ("CSF_ShadersDirectory"); - if (aShaderDir == NULL) + OSD_File aDeclFile (Graphic3d_ShaderProgram::ShadersFolder() + "/Declarations.glsl"); + OSD_File aDeclImplFile (Graphic3d_ShaderProgram::ShadersFolder() + "/DeclarationsImpl.glsl"); + if (!aDeclFile.Exists() + || !aDeclImplFile.Exists()) { - TCollection_ExtendedString aMsg = "Error! Failed to get OCCT shaders directory"; - + const TCollection_ExtendedString aMsg = "Error! Failed to load OCCT shader declarations file"; theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMsg); - - return Standard_False; - } - - OSD_File aDeclFile (TCollection_AsciiString (aShaderDir) + "/Declarations.glsl"); - if (!aDeclFile.Exists()) - { - TCollection_ExtendedString aMsg = "Error! Failed to load OCCT shader declarations file"; - - theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, - GL_DEBUG_TYPE_ERROR_ARB, - 0, - GL_DEBUG_SEVERITY_HIGH_ARB, - aMsg); - return Standard_False; } TCollection_AsciiString aDeclarations; - aDeclFile.Open (OSD_ReadOnly, OSD_Protection()); aDeclFile.Read (aDeclarations, (int)aDeclFile.Size()); aDeclFile.Close(); + TCollection_AsciiString aDeclImpl; + aDeclImplFile.Open (OSD_ReadOnly, OSD_Protection()); + aDeclImplFile.Read (aDeclImpl, (int)aDeclImplFile.Size()); + aDeclImplFile.Close(); + aDeclarations += aDeclImpl; + for (Graphic3d_ShaderObjectList::Iterator anIter (theShaders); anIter.More(); anIter.Next()) { if (!anIter.Value()->IsDone()) { - TCollection_ExtendedString aMsg = "Error! Failed to get shader source"; - + const TCollection_ExtendedString aMsg = "Error! Failed to get shader source"; theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMsg); - return Standard_False; } @@ -326,99 +197,124 @@ Standard_Boolean OpenGl_ShaderProgram::Initialize (const Handle(OpenGl_Context)& if (aShader.IsNull()) { TCollection_ExtendedString aMsg = "Error! Unsupported shader type"; - theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMsg); - return Standard_False; } if (!aShader->Create (theCtx)) { + aShader->Release (theCtx.operator->()); return Standard_False; } TCollection_AsciiString aSource = aDeclarations + anIter.Value()->Source(); - - if (anIter.Value()->Type() == Graphic3d_TOS_VERTEX) + switch (anIter.Value()->Type()) { - aSource = TCollection_AsciiString ("#define VERTEX_SHADER\n") + aSource; + case Graphic3d_TOS_VERTEX: + { + aSource = TCollection_AsciiString ("#define VERTEX_SHADER\n") + aSource; + break; + } + case Graphic3d_TOS_FRAGMENT: + { + #if defined(GL_ES_VERSION_2_0) + TCollection_AsciiString aPrefix (theCtx->hasHighp + ? "precision highp float;\n" + : "precision mediump float;\n"); + aSource = aPrefix + aSource; + #endif + break; + } } if (!aShader->LoadSource (theCtx, aSource)) { - TCollection_ExtendedString aMsg = "Error! Failed to set shader source"; - + const TCollection_ExtendedString aMsg = "Error! Failed to set shader source"; theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMsg); - + aShader->Release (theCtx.operator->()); return Standard_False; } if (!aShader->Compile (theCtx)) { - TCollection_ExtendedString aMsg = "Error! Failed to compile shader object"; - + TCollection_AsciiString aLog; + aShader->FetchInfoLog (theCtx, aLog); + if (aLog.IsEmpty()) + { + aLog = "Compilation log is empty."; + } theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, - aMsg); - - if (theCtx->caps->contextDebug) + TCollection_ExtendedString ("Failed to compile shader object. Compilation log:\n") + aLog); + aShader->Release (theCtx.operator->()); + return Standard_False; + } + else if (theCtx->caps->glslWarnings) + { + TCollection_AsciiString aLog; + aShader->FetchInfoLog (theCtx, aLog); + if (!aLog.IsEmpty() + && !aLog.IsEqual ("No errors.\n")) { - TCollection_AsciiString aLog; - aShader->FetchInfoLog (theCtx, aLog); - if (!aLog.IsEmpty()) - { - std::cout << aLog.ToCString() << std::endl << std::flush; - } - else - { - std::cout << "Information log is empty" << std::endl; - } + theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, + GL_DEBUG_TYPE_PORTABILITY_ARB, + 0, + GL_DEBUG_SEVERITY_LOW_ARB, + TCollection_ExtendedString ("Shader compilation log:\n") + aLog); } - - return Standard_False; } if (!AttachShader (theCtx, aShader)) { + aShader->Release (theCtx.operator->()); return Standard_False; } } + // bind locations for pre-defined Vertex Attributes + SetAttributeName (theCtx, Graphic3d_TOA_POS, "occVertex"); + SetAttributeName (theCtx, Graphic3d_TOA_NORM, "occNormal"); + SetAttributeName (theCtx, Graphic3d_TOA_UV, "occTexCoord"); + SetAttributeName (theCtx, Graphic3d_TOA_COLOR, "occVertColor"); + if (!Link (theCtx)) { - TCollection_ExtendedString aMsg = "Error! Failed to link program object"; - + TCollection_AsciiString aLog; + FetchInfoLog (theCtx, aLog); + if (aLog.IsEmpty()) + { + aLog = "Linker log is empty."; + } theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, - aMsg); - - if (theCtx->caps->contextDebug) + TCollection_ExtendedString ("Failed to link program object! Linker log:\n") + aLog); + return Standard_False; + } + else if (theCtx->caps->glslWarnings) + { + TCollection_AsciiString aLog; + FetchInfoLog (theCtx, aLog); + if (!aLog.IsEmpty() + && !aLog.IsEqual ("No errors.\n")) { - TCollection_AsciiString aLog; - FetchInfoLog (theCtx, aLog); - if (!aLog.IsEmpty()) - { - std::cout << aLog.ToCString() << std::endl; - } - else - { - std::cout << "Information log is empty" << std::endl; - } + theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, + GL_DEBUG_TYPE_PORTABILITY_ARB, + 0, + GL_DEBUG_SEVERITY_LOW_ARB, + TCollection_ExtendedString ("GLSL linker log:\n") + aLog); } - - return Standard_False; } return Standard_True; @@ -503,17 +399,19 @@ Standard_Boolean OpenGl_ShaderProgram::Link (const Handle(OpenGl_Context)& theCt return Standard_False; } - theCtx->core20->glLinkProgram (myProgramID); - GLint aStatus = GL_FALSE; + theCtx->core20->glLinkProgram (myProgramID); theCtx->core20->glGetProgramiv (myProgramID, GL_LINK_STATUS, &aStatus); + if (aStatus == GL_FALSE) + { + return Standard_False; + } for (GLint aVar = 0; aVar < OpenGl_OCCT_NUMBER_OF_STATE_VARIABLES; ++aVar) { myStateLocations[aVar] = GetUniformLocation (theCtx, PredefinedKeywords[aVar]); } - - return aStatus != GL_FALSE; + return Standard_True; } // ======================================================================= @@ -540,21 +438,6 @@ Standard_Boolean OpenGl_ShaderProgram::FetchInfoLog (const Handle(OpenGl_Context return Standard_True; } -// ======================================================================= -// function : Bind -// purpose : Sets the program object as part of current rendering state -// ======================================================================= -void OpenGl_ShaderProgram::Bind (const Handle(OpenGl_Context)& theCtx) const -{ - if (myProgramID == NO_PROGRAM) - { - return; - } - - theCtx->core20->glUseProgram (myProgramID); - theCtx->ShaderManager()->myIsPP = Standard_True; -} - // ======================================================================= // function : ApplyVariables // purpose : Fetches uniform variables from proxy shader program @@ -575,29 +458,6 @@ Standard_Boolean OpenGl_ShaderProgram::ApplyVariables(const Handle(OpenGl_Contex return Standard_True; } -// ======================================================================= -// function : BindWithVariables -// purpose : Binds the program object and applies variables -// ======================================================================= -Standard_Boolean OpenGl_ShaderProgram::BindWithVariables (const Handle(OpenGl_Context)& theCtx) -{ - Bind (theCtx); - return ApplyVariables (theCtx); -} - -// ======================================================================= -// function : Unbind -// purpose : Reverts to fixed-function graphics pipeline (FFP) -// ======================================================================= -void OpenGl_ShaderProgram::Unbind (const Handle(OpenGl_Context)& theCtx) -{ - if (theCtx->ShaderManager()->myIsPP) - { - theCtx->core20->glUseProgram (NO_PROGRAM); - theCtx->ShaderManager()->myIsPP = Standard_False; - } -} - // ======================================================================= // function : ActiveState // purpose : Returns index of last modification for specified state type @@ -773,6 +633,130 @@ Standard_Boolean OpenGl_ShaderProgram::GetAttribute (const Handle(OpenGl_Context return Standard_True; } +// ======================================================================= +// function : SetAttributeName +// purpose : +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetAttributeName (const Handle(OpenGl_Context)& theCtx, + GLint theIndex, + const GLchar* theName) +{ + theCtx->core20fwd->glBindAttribLocation (myProgramID, theIndex, theName); + return Standard_True; +} + +// ======================================================================= +// function : SetAttribute +// purpose : +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetAttribute (const Handle(OpenGl_Context)& theCtx, + const GLchar* theName, + GLfloat theValue) +{ + return SetAttribute (theCtx, GetAttributeLocation (theCtx, theName), theValue); +} + +// ======================================================================= +// function : SetAttribute +// purpose : +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetAttribute (const Handle(OpenGl_Context)& theCtx, + GLint theIndex, + GLfloat theValue) +{ + if (myProgramID == NO_PROGRAM || theIndex == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20fwd->glVertexAttrib1f (theIndex, theValue); + return Standard_True; +} + +// ======================================================================= +// function : SetAttribute +// purpose : +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetAttribute (const Handle(OpenGl_Context)& theCtx, + const GLchar* theName, + const OpenGl_Vec2& theValue) +{ + return SetAttribute (theCtx, GetAttributeLocation (theCtx, theName), theValue); +} + +// ======================================================================= +// function : SetAttribute +// purpose : +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetAttribute (const Handle(OpenGl_Context)& theCtx, + GLint theIndex, + const OpenGl_Vec2& theValue) +{ + if (myProgramID == NO_PROGRAM || theIndex == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20fwd->glVertexAttrib2fv (theIndex, theValue); + return Standard_True; +} + +// ======================================================================= +// function : SetAttribute +// purpose : +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetAttribute (const Handle(OpenGl_Context)& theCtx, + const GLchar* theName, + const OpenGl_Vec3& theValue) +{ + return SetAttribute (theCtx, GetAttributeLocation (theCtx, theName), theValue); +} + +// ======================================================================= +// function : SetAttribute +// purpose : +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetAttribute (const Handle(OpenGl_Context)& theCtx, + GLint theIndex, + const OpenGl_Vec3& theValue) +{ + if (myProgramID == NO_PROGRAM || theIndex == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20fwd->glVertexAttrib3fv (theIndex, theValue); + return Standard_True; +} + +// ======================================================================= +// function : SetAttribute +// purpose : +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetAttribute (const Handle(OpenGl_Context)& theCtx, + const GLchar* theName, + const OpenGl_Vec4& theValue) +{ + return SetAttribute (theCtx, GetAttributeLocation (theCtx, theName), theValue); +} + +// ======================================================================= +// function : SetAttribute +// purpose : +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetAttribute (const Handle(OpenGl_Context)& theCtx, + GLint theIndex, + const OpenGl_Vec4& theValue) +{ + if (myProgramID == NO_PROGRAM || theIndex == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20fwd->glVertexAttrib4fv (theIndex, theValue); + return Standard_True; +} + // ======================================================================= // function : SetUniform // purpose : Specifies the value of the integer uniform variable @@ -801,6 +785,70 @@ Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& return Standard_True; } +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the 64-bit unsigned uniform variable +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + const GLchar* theName, + GLuint64 theValue) +{ + return SetUniform (theCtx, GetUniformLocation (theCtx, theName), theValue); +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the 64-bit unsigned uniform variable +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + GLuint64 theValue) +{ + if (theCtx->arbTexBindless == NULL || myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) + { + return Standard_False; + } + +#if !defined(GL_ES_VERSION_2_0) + theCtx->arbTexBindless->glUniformHandleui64ARB (theLocation, theValue); +#endif + + return Standard_True; +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the 64-bit unsigned uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + const GLchar* theName, + const GLsizei theCount, + const GLuint64* theValue) +{ + return SetUniform (theCtx, GetUniformLocation (theCtx, theName), theCount, theValue); +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the 64-bit unsigned uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + const GLsizei theCount, + const GLuint64* theValue) +{ + if (theCtx->arbTexBindless == NULL || myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) + { + return Standard_False; + } + +#if !defined(GL_ES_VERSION_2_0) + theCtx->arbTexBindless->glUniformHandleui64vARB (theLocation, theCount, theValue); +#endif + + return Standard_True; +} + // ======================================================================= // function : SetUniform // purpose : Specifies the value of the floating-point uniform variable @@ -1003,7 +1051,7 @@ Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& // ======================================================================= Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, const GLchar* theName, - const OpenGl_Matrix& theValue, + const OpenGl_Mat4& theValue, GLboolean theTranspose) { return SetUniform (theCtx, GetUniformLocation (theCtx, theName), theValue, theTranspose); @@ -1015,7 +1063,7 @@ Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& // ======================================================================= Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, GLint theLocation, - const OpenGl_Matrix& theValue, + const OpenGl_Mat4& theValue, GLboolean theTranspose) { if (myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) @@ -1023,7 +1071,7 @@ Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& return Standard_False; } - theCtx->core20->glUniformMatrix4fv (theLocation, 1, theTranspose, *theValue.mat); + theCtx->core20->glUniformMatrix4fv (theLocation, 1, GL_FALSE, theTranspose ? theValue.Transposed() : theValue); return Standard_True; } @@ -1033,7 +1081,7 @@ Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& // ======================================================================= Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, const GLchar* theName, - const Tmatrix3& theValue, + const OpenGl_Matrix& theValue, GLboolean theTranspose) { return SetUniform (theCtx, GetUniformLocation (theCtx, theName), theValue, theTranspose); @@ -1045,15 +1093,153 @@ Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& // ======================================================================= Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, GLint theLocation, - const Tmatrix3& theValue, + const OpenGl_Matrix& theValue, GLboolean theTranspose) +{ + return SetUniform (theCtx, theLocation, OpenGl_Mat4::Map (*theValue.mat), theTranspose); +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the float uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + GLuint theCount, + const Standard_ShortReal* theData) +{ + if (myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20->glUniform1fv (theLocation, theCount, theData); + return Standard_True; +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the float2 uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + GLuint theCount, + const OpenGl_Vec2* theData) +{ + if (myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20->glUniform2fv (theLocation, theCount, theData[0].GetData()); + return Standard_True; +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the float3 uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + GLuint theCount, + const OpenGl_Vec3* theData) { if (myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) { return Standard_False; } - theCtx->core20->glUniformMatrix4fv (theLocation, 1, theTranspose, *theValue); + theCtx->core20->glUniform3fv (theLocation, theCount, theData[0].GetData()); + return Standard_True; +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the float4 uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + GLuint theCount, + const OpenGl_Vec4* theData) +{ + if (myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20->glUniform4fv (theLocation, theCount, theData[0].GetData()); + return Standard_True; +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the integer uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + GLuint theCount, + const Standard_Integer* theData) +{ + if (myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20->glUniform1iv (theLocation, theCount, theData); + return Standard_True; +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the int2 uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + GLuint theCount, + const OpenGl_Vec2i* theData) +{ + if (myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20->glUniform2iv (theLocation, theCount, theData[0].GetData()); + return Standard_True; +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the int3 uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + GLuint theCount, + const OpenGl_Vec3i* theData) +{ + if (myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20->glUniform3iv (theLocation, theCount, theData[0].GetData()); + return Standard_True; +} + +// ======================================================================= +// function : SetUniform +// purpose : Specifies the value of the int4 uniform array +// ======================================================================= +Standard_Boolean OpenGl_ShaderProgram::SetUniform (const Handle(OpenGl_Context)& theCtx, + GLint theLocation, + GLuint theCount, + const OpenGl_Vec4i* theData) +{ + if (myProgramID == NO_PROGRAM || theLocation == INVALID_LOCATION) + { + return Standard_False; + } + + theCtx->core20->glUniform4iv (theLocation, theCount, theData[0].GetData()); return Standard_True; } @@ -1104,7 +1290,7 @@ Standard_Boolean OpenGl_ShaderProgram::Create (const Handle(OpenGl_Context)& the // function : Release // purpose : Destroys shader program // ======================================================================= -void OpenGl_ShaderProgram::Release (const OpenGl_Context* theCtx) +void OpenGl_ShaderProgram::Release (OpenGl_Context* theCtx) { if (myProgramID == NO_PROGRAM) { @@ -1116,11 +1302,15 @@ void OpenGl_ShaderProgram::Release (const OpenGl_Context* theCtx) for (OpenGl_ShaderList::Iterator anIter (myShaderObjects); anIter.More(); anIter.Next()) { - anIter.ChangeValue()->Release (theCtx); - anIter.ChangeValue().Nullify(); + if (!anIter.Value().IsNull()) + { + anIter.ChangeValue()->Release (theCtx); + anIter.ChangeValue().Nullify(); + } } - if (theCtx->core20 != NULL) + if (theCtx->core20 != NULL + && theCtx->IsValid()) { theCtx->core20->glDeleteProgram (myProgramID); }