1 // Created on: 2013-09-20
2 // Created by: Denis BOGOLEPOV
3 // Copyright (c) 2013-2014 OPEN CASCADE SAS
5 // This file is part of Open CASCADE Technology software library.
7 // This library is free software; you can redistribute it and/or modify it under
8 // the terms of the GNU Lesser General Public License version 2.1 as published
9 // by the Free Software Foundation, with special exception defined in the file
10 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
11 // distribution for complete text of the license and disclaimer of any warranty.
13 // Alternatively, this file may be used under the terms of Open CASCADE
14 // commercial license or contractual agreement.
16 #include <Standard_Atomic.hxx>
17 #include <Standard_Assert.hxx>
19 #include <Graphic3d_GraphicDriver.hxx>
20 #include <Graphic3d_ShaderObject.hxx>
21 #include <Graphic3d_ShaderProgram.hxx>
22 #include <OSD_Directory.hxx>
23 #include <OSD_Environment.hxx>
24 #include <OSD_File.hxx>
25 #include <OSD_Path.hxx>
27 IMPLEMENT_STANDARD_RTTIEXT(Graphic3d_ShaderProgram,Standard_Transient)
31 static volatile Standard_Integer THE_PROGRAM_OBJECT_COUNTER = 0;
35 // =======================================================================
36 // function : ShadersFolder
38 // =======================================================================
39 const TCollection_AsciiString& Graphic3d_ShaderProgram::ShadersFolder()
41 static Standard_Boolean THE_IS_DEFINED = Standard_False;
42 static TCollection_AsciiString THE_SHADERS_FOLDER;
45 THE_IS_DEFINED = Standard_True;
46 OSD_Environment aDirEnv ("CSF_ShadersDirectory");
47 THE_SHADERS_FOLDER = aDirEnv.Value();
48 if (THE_SHADERS_FOLDER.IsEmpty())
50 OSD_Environment aCasRootEnv ("CASROOT");
51 THE_SHADERS_FOLDER = aCasRootEnv.Value();
52 if (!THE_SHADERS_FOLDER.IsEmpty())
54 THE_SHADERS_FOLDER += "/src/Shaders";
58 if (THE_SHADERS_FOLDER.IsEmpty())
60 std::cerr << "Both environment variables CSF_ShadersDirectory and CASROOT are undefined!\n"
61 << "At least one should be defined to use standard GLSL programs.\n";
62 Standard_Failure::Raise ("CSF_ShadersDirectory and CASROOT are undefined");
63 return THE_SHADERS_FOLDER;
66 const OSD_Path aDirPath (THE_SHADERS_FOLDER);
67 OSD_Directory aDir (aDirPath);
68 const TCollection_AsciiString aProgram = THE_SHADERS_FOLDER + "/Declarations.glsl";
69 OSD_File aProgramFile (aProgram);
71 || !aProgramFile.Exists())
73 std::cerr << "Standard GLSL programs are not found in: " << THE_SHADERS_FOLDER.ToCString() << std::endl;
74 Standard_Failure::Raise ("CSF_ShadersDirectory or CASROOT is set incorrectly");
75 return THE_SHADERS_FOLDER;
78 return THE_SHADERS_FOLDER;
81 // =======================================================================
82 // function : Graphic3d_ShaderProgram
83 // purpose : Creates new empty program object
84 // =======================================================================
85 Graphic3d_ShaderProgram::Graphic3d_ShaderProgram()
87 myID = TCollection_AsciiString ("Graphic3d_ShaderProgram_")
88 + TCollection_AsciiString (Standard_Atomic_Increment (&THE_PROGRAM_OBJECT_COUNTER));
91 // =======================================================================
92 // function : Graphic3d_ShaderProgram
94 // =======================================================================
95 Graphic3d_ShaderProgram::Graphic3d_ShaderProgram (const Graphic3d_ShaderProgram::ShaderName theName)
97 const TCollection_AsciiString& aShadersRoot = Graphic3d_ShaderProgram::ShadersFolder();
100 case ShaderName_Phong:
102 myID = TCollection_AsciiString ("Graphic3d_ShaderProgram_Phong");
103 const TCollection_AsciiString aSrcVert = aShadersRoot + "/PhongShading.vs";
104 const TCollection_AsciiString aSrcFrag = aShadersRoot + "/PhongShading.fs";
106 if (!aSrcVert.IsEmpty()
107 && !OSD_File (aSrcVert).Exists())
109 Standard_Failure::Raise ("Graphic3d_ShaderProgram, PhongShading.vs is not found");
112 if (!aSrcFrag.IsEmpty()
113 && !OSD_File (aSrcFrag).Exists())
115 Standard_Failure::Raise ("Graphic3d_ShaderProgram, PhongShading.fs is not found");
119 AttachShader (Graphic3d_ShaderObject::CreateFromFile (Graphic3d_TOS_VERTEX, aSrcVert));
120 AttachShader (Graphic3d_ShaderObject::CreateFromFile (Graphic3d_TOS_FRAGMENT, aSrcFrag));
123 case ShaderName_UNKNOWN:
126 Standard_Failure::Raise ("Graphic3d_ShaderProgram, unknown program name");
132 // =======================================================================
133 // function : ~Graphic3d_ShaderProgram
134 // purpose : Releases resources of program object
135 // =======================================================================
136 Graphic3d_ShaderProgram::~Graphic3d_ShaderProgram()
141 // =======================================================================
142 // function : Destroy
143 // purpose : Releases resources of program object
144 // =======================================================================
145 void Graphic3d_ShaderProgram::Destroy() const
148 // =======================================================================
150 // purpose : Checks if the program object is valid or not
151 // =======================================================================
152 Standard_Boolean Graphic3d_ShaderProgram::IsDone() const
154 if (myShaderObjects.IsEmpty())
156 return Standard_False;
159 for (Graphic3d_ShaderObjectList::Iterator anIt (myShaderObjects); anIt.More(); anIt.Next())
161 if (!anIt.Value()->IsDone())
162 return Standard_False;
165 return Standard_True;
168 // =======================================================================
169 // function : AttachShader
170 // purpose : Attaches shader object to the program object
171 // =======================================================================
172 Standard_Boolean Graphic3d_ShaderProgram::AttachShader (const Handle(Graphic3d_ShaderObject)& theShader)
174 if (theShader.IsNull())
176 return Standard_False;
179 for (Graphic3d_ShaderObjectList::Iterator anIt (myShaderObjects); anIt.More(); anIt.Next())
181 if (anIt.Value() == theShader)
182 return Standard_False;
185 myShaderObjects.Append (theShader);
186 return Standard_True;
189 // =======================================================================
190 // function : DetachShader
191 // purpose : Detaches shader object from the program object
192 // =======================================================================
193 Standard_Boolean Graphic3d_ShaderProgram::DetachShader (const Handle(Graphic3d_ShaderObject)& theShader)
195 if (theShader.IsNull())
197 return Standard_False;
200 for (Graphic3d_ShaderObjectList::Iterator anIt (myShaderObjects); anIt.More(); anIt.Next())
202 if (anIt.Value() == theShader)
204 myShaderObjects.Remove (anIt);
205 return Standard_True;
209 return Standard_False;
212 // =======================================================================
213 // function : ClearVariables
214 // purpose : Removes all custom uniform variables from the program
215 // =======================================================================
216 void Graphic3d_ShaderProgram::ClearVariables()