1 // Created on: 2011-07-13
2 // Created by: Sergey ZERCHANINOV
3 // Copyright (c) 2011-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 <Aspect_PolygonOffsetMode.hxx>
17 #include <NCollection_Vec3.hxx>
19 #include <OpenGl_AspectFace.hxx>
20 #include <OpenGl_Context.hxx>
21 #include <OpenGl_ShaderManager.hxx>
22 #include <OpenGl_ShaderProgram.hxx>
23 #include <OpenGl_Texture.hxx>
24 #include <OpenGl_Workspace.hxx>
26 #include <Graphic3d_ShaderProgram.hxx>
27 #include <Graphic3d_TextureMap.hxx>
28 #include <Graphic3d_TextureParams.hxx>
29 #include <Graphic3d_TypeOfReflection.hxx>
30 #include <Graphic3d_MaterialAspect.hxx>
32 #include <Image_PixMap.hxx>
36 //! Initialize default material in this way for backward compatibility.
37 inline Graphic3d_MaterialAspect initDefaultMaterial()
39 Graphic3d_MaterialAspect aMat;
40 aMat.SetMaterialType (Graphic3d_MATERIAL_ASPECT);
41 aMat.SetAmbient (0.2);
42 aMat.SetDiffuse (0.8);
43 aMat.SetSpecular (0.1);
44 aMat.SetEmissive (0.0);
45 aMat.SetAmbientColor (Quantity_NOC_WHITE);
46 aMat.SetDiffuseColor (Quantity_NOC_WHITE);
47 aMat.SetEmissiveColor(Quantity_NOC_WHITE);
48 aMat.SetSpecularColor(Quantity_NOC_WHITE);
49 aMat.SetShininess (10.0 / 128.0);
50 aMat.SetRefractionIndex (1.0);
54 static const TCollection_AsciiString THE_EMPTY_KEY;
55 static const Graphic3d_MaterialAspect THE_DEFAULT_MATERIAL = initDefaultMaterial();
58 // =======================================================================
59 // function : OpenGl_AspectFace
61 // =======================================================================
62 OpenGl_AspectFace::OpenGl_AspectFace()
63 : myAspect (new Graphic3d_AspectFillArea3d (Aspect_IS_SOLID, Quantity_NOC_WHITE,
64 Quantity_NOC_WHITE, Aspect_TOL_SOLID, 1.0,
65 THE_DEFAULT_MATERIAL, THE_DEFAULT_MATERIAL)),
66 myIsNoLighting (false)
68 myAspect->SetHatchStyle (Handle(Graphic3d_HatchStyle)());
71 // =======================================================================
72 // function : OpenGl_AspectFace
74 // =======================================================================
75 OpenGl_AspectFace::OpenGl_AspectFace (const Handle(Graphic3d_AspectFillArea3d)& theAspect)
76 : myIsNoLighting (false)
78 SetAspect (theAspect);
81 // =======================================================================
82 // function : SetAspect
84 // =======================================================================
85 void OpenGl_AspectFace::SetAspect (const Handle(Graphic3d_AspectFillArea3d)& theAspect)
89 const Graphic3d_MaterialAspect& aMat = theAspect->FrontMaterial();
90 myIsNoLighting = !aMat.ReflectionMode (Graphic3d_TOR_AMBIENT)
91 && !aMat.ReflectionMode (Graphic3d_TOR_DIFFUSE)
92 && !aMat.ReflectionMode (Graphic3d_TOR_SPECULAR)
93 && !aMat.ReflectionMode (Graphic3d_TOR_EMISSION);
95 myAspectEdge.Aspect()->SetColor (theAspect->EdgeColor());
96 myAspectEdge.Aspect()->SetType (theAspect->EdgeLineType());
97 myAspectEdge.Aspect()->SetWidth (theAspect->EdgeWidth());
99 // update texture binding
100 const TCollection_AsciiString& aTextureKey = myAspect->TextureMap().IsNull() ? THE_EMPTY_KEY : myAspect->TextureMap()->GetId();
101 if (aTextureKey.IsEmpty() || myResources.TextureId != aTextureKey)
103 myResources.ResetTextureReadiness();
105 else if (!myResources.Texture.IsNull()
106 && !myAspect->TextureMap().IsNull()
107 && myResources.Texture->Revision() != myAspect->TextureMap()->Revision())
109 myResources.ResetTextureReadiness();
112 // update shader program binding
113 const TCollection_AsciiString& aShaderKey = myAspect->ShaderProgram().IsNull() ? THE_EMPTY_KEY : myAspect->ShaderProgram()->GetId();
114 if (aShaderKey.IsEmpty() || myResources.ShaderProgramId != aShaderKey)
116 myResources.ResetShaderReadiness();
120 // =======================================================================
123 // =======================================================================
124 void OpenGl_AspectFace::Render (const Handle(OpenGl_Workspace)& theWorkspace) const
126 theWorkspace->SetAspectFace (this);
129 // =======================================================================
130 // function : Release
132 // =======================================================================
133 void OpenGl_AspectFace::Release (OpenGl_Context* theContext)
135 if (!myResources.Texture.IsNull())
139 if (myResources.TextureId.IsEmpty())
141 theContext->DelayedRelease (myResources.Texture);
145 myResources.Texture.Nullify(); // we need nullify all handles before ReleaseResource() call
146 theContext->ReleaseResource (myResources.TextureId, Standard_True);
149 myResources.Texture.Nullify();
151 myResources.TextureId.Clear();
152 myResources.ResetTextureReadiness();
154 if (!myResources.ShaderProgram.IsNull()
157 theContext->ShaderManager()->Unregister (myResources.ShaderProgramId,
158 myResources.ShaderProgram);
160 myResources.ShaderProgramId.Clear();
161 myResources.ResetShaderReadiness();
164 // =======================================================================
165 // function : BuildTexture
167 // =======================================================================
168 void OpenGl_AspectFace::Resources::BuildTexture (const Handle(OpenGl_Context)& theCtx,
169 const Handle(Graphic3d_TextureMap)& theTexture)
171 // release old texture resource
172 if (!Texture.IsNull())
174 if (!theTexture.IsNull()
175 && theTexture->GetId() == TextureId
176 && theTexture->Revision() != Texture->Revision())
178 Handle(Image_PixMap) anImage = theTexture->GetImage();
179 if (!anImage.IsNull())
181 Texture->Init (theCtx, *anImage.operator->(), theTexture->Type());
182 Texture->SetRevision (Texture->Revision());
187 if (TextureId.IsEmpty())
189 theCtx->DelayedRelease (Texture);
194 Texture.Nullify(); // we need nullify all handles before ReleaseResource() call
195 theCtx->ReleaseResource (TextureId, Standard_True);
199 TextureId = theTexture.IsNull() ? THE_EMPTY_KEY : theTexture->GetId();
201 if (!theTexture.IsNull())
203 if (TextureId.IsEmpty() || !theCtx->GetResource<Handle(OpenGl_Texture)> (TextureId, Texture))
205 Texture = new OpenGl_Texture (theTexture->GetParams());
206 Handle(Image_PixMap) anImage = theTexture->GetImage();
207 if (!anImage.IsNull())
209 Texture->Init (theCtx, *anImage.operator->(), theTexture->Type());
210 Texture->SetRevision (Texture->Revision());
212 if (!TextureId.IsEmpty())
214 theCtx->ShareResource (TextureId, Texture);
220 // =======================================================================
221 // function : BuildShader
223 // =======================================================================
224 void OpenGl_AspectFace::Resources::BuildShader (const Handle(OpenGl_Context)& theCtx,
225 const Handle(Graphic3d_ShaderProgram)& theShader)
227 if (theCtx->core20fwd == NULL)
232 // release old shader program resources
233 if (!ShaderProgram.IsNull())
235 theCtx->ShaderManager()->Unregister (ShaderProgramId, ShaderProgram);
236 ShaderProgramId.Clear();
237 ShaderProgram.Nullify();
239 if (theShader.IsNull())
244 theCtx->ShaderManager()->Create (theShader, ShaderProgramId, ShaderProgram);