1 // Created on: 2011-07-13
2 // Created by: Sergey ZERCHANINOV
3 // Copyright (c) 2011-2012 OPEN CASCADE SAS
5 // The content of this file is subject to the Open CASCADE Technology Public
6 // License Version 6.5 (the "License"). You may not use the content of this file
7 // except in compliance with the License. Please obtain a copy of the License
8 // at http://www.opencascade.org and read it completely before using this file.
10 // The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
11 // main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
13 // The Original Code and all software distributed under the License is
14 // distributed on an "AS IS" basis, without warranty of any kind, and the
15 // Initial Developer hereby disclaims all such warranties, including without
16 // limitation, any warranties of merchantability, fitness for a particular
17 // purpose or non-infringement. Please see the License for the specific terms
18 // and conditions governing the rights and limitations under the License.
20 #include <OpenGl_AspectFace.hxx>
21 #include <OpenGl_Texture.hxx>
22 #include <OpenGl_Workspace.hxx>
23 #include <OpenGl_Context.hxx>
25 #include <Aspect_PolygonOffsetMode.hxx>
26 #include <Graphic3d_CGroup.hxx>
27 #include <Graphic3d_TextureMap.hxx>
28 #include <Graphic3d_TypeOfReflection.hxx>
29 #include <Graphic3d_MaterialAspect.hxx>
31 #include <NCollection_Vec3.hxx>
36 static OPENGL_SURF_PROP THE_DEFAULT_MATERIAL =
38 0.2F, 0.8F, 0.1F, 0.0F, // amb, diff, spec, emsv
39 1.0F, 10.0F, 0.0F, // trans, shine, env_reflexion
41 (OPENGL_AMBIENT_MASK | OPENGL_DIFFUSE_MASK | OPENGL_SPECULAR_MASK), // color_mask
42 {{ 1.0F, 1.0F, 1.0F, 1.0F }}, // ambient color
43 {{ 1.0F, 1.0F, 1.0F, 1.0F }}, // diffuse color
44 {{ 1.0F, 1.0F, 1.0F, 1.0F }}, // specular color
45 {{ 1.0F, 1.0F, 1.0F, 1.0F }}, // emissive color
46 {{ 1.0F, 1.0F, 1.0F, 1.0F }} // material color
49 static TEL_POFFSET_PARAM THE_DEFAULT_POFFSET = { Aspect_POM_Fill, 1.0F, 0.0F };
50 static const TCollection_AsciiString THE_EMPTY_KEY;
54 // =======================================================================
55 // function : convertMaterial
57 // =======================================================================
58 void OpenGl_AspectFace::convertMaterial (const CALL_DEF_MATERIAL& theMat,
59 OPENGL_SURF_PROP& theSurf)
61 theSurf.amb = theMat.IsAmbient ? theMat.Ambient : 0.0f;
62 theSurf.diff = theMat.IsDiffuse ? theMat.Diffuse : 0.0f;
63 theSurf.spec = theMat.IsSpecular ? theMat.Specular : 0.0f;
64 theSurf.emsv = theMat.IsEmission ? theMat.Emission : 0.0f;
66 theSurf.isphysic = theMat.IsPhysic ? 1 : 0; // type of material
69 theSurf.color_mask = 0;
72 theSurf.color_mask |= OPENGL_AMBIENT_MASK;
76 theSurf.color_mask |= OPENGL_DIFFUSE_MASK;
78 if (theMat.IsSpecular)
80 theSurf.color_mask |= OPENGL_SPECULAR_MASK;
82 if (theMat.IsEmission)
84 theSurf.color_mask |= OPENGL_EMISSIVE_MASK;
88 theSurf.ambcol.rgb[0] = theMat.ColorAmb.r;
89 theSurf.ambcol.rgb[1] = theMat.ColorAmb.g;
90 theSurf.ambcol.rgb[2] = theMat.ColorAmb.b;
91 theSurf.ambcol.rgb[3] = 1.0f;
94 theSurf.difcol.rgb[0] = theMat.ColorDif.r;
95 theSurf.difcol.rgb[1] = theMat.ColorDif.g;
96 theSurf.difcol.rgb[2] = theMat.ColorDif.b;
97 theSurf.difcol.rgb[3] = 1.0f;
100 theSurf.speccol.rgb[0] = theMat.ColorSpec.r;
101 theSurf.speccol.rgb[1] = theMat.ColorSpec.g;
102 theSurf.speccol.rgb[2] = theMat.ColorSpec.b;
103 theSurf.speccol.rgb[3] = 1.0f;
106 theSurf.emscol.rgb[0] = theMat.ColorEms.r;
107 theSurf.emscol.rgb[1] = theMat.ColorEms.g;
108 theSurf.emscol.rgb[2] = theMat.ColorEms.b;
109 theSurf.emscol.rgb[3] = 1.0f;
111 theSurf.shine = 128.0f * float(theMat.Shininess);
112 theSurf.env_reflexion = theMat.EnvReflexion;
114 // trans = 0. => opaque
115 // trans = 1. => transparent
116 // in OpenGl it is opposite.
117 theSurf.trans = 1.0f - theMat.Transparency;
120 // =======================================================================
121 // function : OpenGl_AspectFace
123 // =======================================================================
124 OpenGl_AspectFace::OpenGl_AspectFace()
125 : myInteriorStyle (Aspect_IS_SOLID),
127 myHatch (TEL_HS_SOLID),
128 myDistinguishingMode (TOff),
129 myCullingMode (TelCullNone),
130 myIntFront (THE_DEFAULT_MATERIAL),
131 myIntBack (THE_DEFAULT_MATERIAL),
132 myPolygonOffset (THE_DEFAULT_POFFSET),
133 myDoTextureMap (false),
135 myIsTextureInit (Standard_False),
140 // =======================================================================
141 // function : SetAspect
143 // =======================================================================
144 void OpenGl_AspectFace::SetAspect (const CALL_DEF_CONTEXTFILLAREA& theAspect)
146 myInteriorStyle = (Aspect_InteriorStyle )theAspect.Style;
147 myEdge = theAspect.Edge ? TOn : TOff;
149 //TelInteriorStyleIndex
150 switch (theAspect.Hatch)
152 case 0: /* Aspect_HS_HORIZONTAL */
153 myHatch = TEL_HS_HORIZONTAL;
155 case 1: /* Aspect_HS_HORIZONTAL_WIDE */
156 myHatch = TEL_HS_HORIZONTAL_SPARSE;
158 case 2: /* Aspect_HS_VERTICAL */
159 myHatch = TEL_HS_VERTICAL;
161 case 3: /* Aspect_HS_VERTICAL_WIDE */
162 myHatch = TEL_HS_VERTICAL_SPARSE;
164 case 4: /* Aspect_HS_DIAGONAL_45 */
165 myHatch = TEL_HS_DIAG_45;
167 case 5: /* Aspect_HS_DIAGONAL_45_WIDE */
168 myHatch = TEL_HS_DIAG_45_SPARSE;
170 case 6: /* Aspect_HS_DIAGONAL_135 */
171 myHatch = TEL_HS_DIAG_135;
173 case 7: /* Aspect_HS_DIAGONAL_135_WIDE */
174 myHatch = TEL_HS_DIAG_135_SPARSE;
176 case 8: /* Aspect_HS_GRID */
177 myHatch = TEL_HS_GRID;
179 case 9: /* Aspect_HS_GRID_WIDE */
180 myHatch = TEL_HS_GRID_SPARSE;
182 case 10: /* Aspect_HS_GRID_DIAGONAL */
183 myHatch = TEL_HS_CROSS;
185 case 11: /* Aspect_HS_GRID_DIAGONAL_WIDE */
186 myHatch = TEL_HS_CROSS_SPARSE;
193 myDistinguishingMode = theAspect.Distinguish ? TOn : TOff;
194 myCullingMode = theAspect.BackFace ? TelCullBack : TelCullNone;
196 convertMaterial (theAspect.Front, myIntFront);
197 convertMaterial (theAspect.Back, myIntBack);
200 myIntFront.matcol.rgb[0] = (float )theAspect.IntColor.r;
201 myIntFront.matcol.rgb[1] = (float )theAspect.IntColor.g;
202 myIntFront.matcol.rgb[2] = (float )theAspect.IntColor.b;
203 myIntFront.matcol.rgb[3] = 1.0f;
205 //TelBackInteriorColour
206 myIntBack.matcol.rgb[0] = (float )theAspect.BackIntColor.r;
207 myIntBack.matcol.rgb[1] = (float )theAspect.BackIntColor.g;
208 myIntBack.matcol.rgb[2] = (float )theAspect.BackIntColor.b;
209 myIntBack.matcol.rgb[3] = 1.0f;
211 myDoTextureMap = (theAspect.Texture.doTextureMap != 0);
212 myTextureMap = theAspect.Texture.TextureMap;
214 const TCollection_AsciiString& aNewKey = myTextureMap.IsNull() ? THE_EMPTY_KEY : myTextureMap->GetId();
215 myIsTextureInit = (!aNewKey.IsEmpty() && myTextureId == aNewKey);
218 myPolygonOffset.mode = (Aspect_PolygonOffsetMode )theAspect.PolygonOffsetMode;
219 myPolygonOffset.factor = theAspect.PolygonOffsetFactor;
220 myPolygonOffset.units = theAspect.PolygonOffsetUnits;
222 CALL_DEF_CONTEXTLINE anEdgeAspect;
223 anEdgeAspect.Color.r = (float )theAspect.EdgeColor.r;
224 anEdgeAspect.Color.g = (float )theAspect.EdgeColor.g;
225 anEdgeAspect.Color.b = (float )theAspect.EdgeColor.b;
226 anEdgeAspect.LineType = (Aspect_TypeOfLine )theAspect.LineType;
227 anEdgeAspect.Width = (float )theAspect.Width;
228 myAspectEdge.SetAspect (anEdgeAspect);
231 // =======================================================================
232 // function : SetAspect
234 // =======================================================================
235 void OpenGl_AspectFace::SetAspect (const Handle(Graphic3d_AspectFillArea3d)& theAspect)
237 CALL_DEF_CONTEXTFILLAREA aFaceContext;
238 Standard_Real aWidth;
239 Quantity_Color aBackIntColor;
240 Quantity_Color aEdgeColor;
241 Aspect_TypeOfLine aLType;
242 Quantity_Color aIntColor;
243 Aspect_InteriorStyle aIntStyle;
244 NCollection_Vec3<Standard_Real> aColor;
246 theAspect->Values (aIntStyle, aIntColor, aBackIntColor, aEdgeColor, aLType, aWidth);
247 aIntColor.Values (aColor.r(), aColor.g(), aColor.b(), Quantity_TOC_RGB);
249 aFaceContext.Style = int (aIntStyle);
250 aFaceContext.IntColor.r = float (aColor.r());
251 aFaceContext.IntColor.g = float (aColor.g());
252 aFaceContext.IntColor.b = float (aColor.b());
254 if (theAspect->Distinguish())
256 aBackIntColor.Values (aColor.r(), aColor.g(), aColor.b(), Quantity_TOC_RGB);
259 aFaceContext.BackIntColor.r = float (aColor.r());
260 aFaceContext.BackIntColor.g = float (aColor.g());
261 aFaceContext.BackIntColor.b = float (aColor.b());
263 aFaceContext.Edge = theAspect->Edge () ? 1:0;
264 aEdgeColor.Values (aColor.r(), aColor.g(), aColor.b(), Quantity_TOC_RGB);
266 aFaceContext.EdgeColor.r = float (aColor.r());
267 aFaceContext.EdgeColor.g = float (aColor.g());
268 aFaceContext.EdgeColor.b = float (aColor.b());
269 aFaceContext.LineType = int (aLType);
270 aFaceContext.Width = float (aWidth);
271 aFaceContext.Hatch = int (theAspect->HatchStyle ());
273 aFaceContext.Distinguish = theAspect->Distinguish () ? 1:0;
274 aFaceContext.BackFace = theAspect->BackFace () ? 1:0;
276 aFaceContext.Back.Shininess = float ((theAspect->BackMaterial ()).Shininess ());
277 aFaceContext.Back.Ambient = float ((theAspect->BackMaterial ()).Ambient ());
278 aFaceContext.Back.Diffuse = float ((theAspect->BackMaterial ()).Diffuse ());
279 aFaceContext.Back.Specular = float ((theAspect->BackMaterial ()).Specular ());
280 aFaceContext.Back.Transparency = float ((theAspect->BackMaterial ()).Transparency ());
281 aFaceContext.Back.Emission = float ((theAspect->BackMaterial ()).Emissive ());
284 aFaceContext.Back.IsAmbient = ((theAspect->BackMaterial ()).ReflectionMode (Graphic3d_TOR_AMBIENT) ? 1 : 0 );
285 aFaceContext.Back.IsDiffuse = ((theAspect->BackMaterial ()).ReflectionMode (Graphic3d_TOR_DIFFUSE) ? 1 : 0 );
286 aFaceContext.Back.IsSpecular = ((theAspect->BackMaterial ()).ReflectionMode (Graphic3d_TOR_SPECULAR) ? 1 : 0 );
287 aFaceContext.Back.IsEmission = ((theAspect->BackMaterial ()).ReflectionMode (Graphic3d_TOR_EMISSION) ? 1 : 0 );
290 const Graphic3d_MaterialAspect aBackMat = theAspect->BackMaterial ();
291 Standard_Boolean isBackPhys = aBackMat.MaterialType (Graphic3d_MATERIAL_PHYSIC);
292 aFaceContext.Back.IsPhysic = (isBackPhys ? 1 : 0 );
295 aFaceContext.Back.ColorSpec.r = float (((theAspect->BackMaterial ()).SpecularColor ()).Red ());
296 aFaceContext.Back.ColorSpec.g = float (((theAspect->BackMaterial ()).SpecularColor ()).Green ());
297 aFaceContext.Back.ColorSpec.b = float (((theAspect->BackMaterial ()).SpecularColor ()).Blue ());
300 aFaceContext.Back.ColorAmb.r = float (((theAspect->BackMaterial ()).AmbientColor ()).Red ());
301 aFaceContext.Back.ColorAmb.g = float (((theAspect->BackMaterial ()).AmbientColor ()).Green ());
302 aFaceContext.Back.ColorAmb.b = float (((theAspect->BackMaterial ()).AmbientColor ()).Blue ());
305 aFaceContext.Back.ColorDif.r = float (((theAspect->BackMaterial ()).DiffuseColor ()).Red ());
306 aFaceContext.Back.ColorDif.g = float (((theAspect->BackMaterial ()).DiffuseColor ()).Green ());
307 aFaceContext.Back.ColorDif.b = float (((theAspect->BackMaterial ()).DiffuseColor ()).Blue ());
310 aFaceContext.Back.ColorEms.r = float (((theAspect->BackMaterial ()).EmissiveColor ()).Red ());
311 aFaceContext.Back.ColorEms.g = float (((theAspect->BackMaterial ()).EmissiveColor ()).Green ());
312 aFaceContext.Back.ColorEms.b = float (((theAspect->BackMaterial ()).EmissiveColor ()).Blue ());
314 aFaceContext.Back.EnvReflexion = float ((theAspect->BackMaterial ()).EnvReflexion());
316 aFaceContext.Front.Shininess = float ((theAspect->FrontMaterial ()).Shininess ());
317 aFaceContext.Front.Ambient = float ((theAspect->FrontMaterial ()).Ambient ());
318 aFaceContext.Front.Diffuse = float ((theAspect->FrontMaterial ()).Diffuse ());
319 aFaceContext.Front.Specular = float ((theAspect->FrontMaterial ()).Specular ());
320 aFaceContext.Front.Transparency = float ((theAspect->FrontMaterial ()).Transparency ());
321 aFaceContext.Front.Emission = float ((theAspect->FrontMaterial ()).Emissive ());
324 aFaceContext.Front.IsAmbient = ((theAspect->FrontMaterial ()).ReflectionMode (Graphic3d_TOR_AMBIENT) ? 1 : 0);
325 aFaceContext.Front.IsDiffuse = ((theAspect->FrontMaterial ()).ReflectionMode (Graphic3d_TOR_DIFFUSE) ? 1 : 0);
326 aFaceContext.Front.IsSpecular = ((theAspect->FrontMaterial ()).ReflectionMode (Graphic3d_TOR_SPECULAR) ? 1 : 0);
327 aFaceContext.Front.IsEmission = ((theAspect->FrontMaterial ()).ReflectionMode (Graphic3d_TOR_EMISSION) ? 1 : 0);
330 const Graphic3d_MaterialAspect aFrontMat = theAspect->FrontMaterial ();
331 Standard_Boolean isFrontPhys = aFrontMat.MaterialType (Graphic3d_MATERIAL_PHYSIC);
332 aFaceContext.Front.IsPhysic = (isFrontPhys ? 1 : 0 );
335 aFaceContext.Front.ColorSpec.r = float (((theAspect->FrontMaterial ()).SpecularColor ()).Red ());
336 aFaceContext.Front.ColorSpec.g = float (((theAspect->FrontMaterial ()).SpecularColor ()).Green ());
337 aFaceContext.Front.ColorSpec.b = float (((theAspect->FrontMaterial ()).SpecularColor ()).Blue ());
340 aFaceContext.Front.ColorAmb.r = float (((theAspect->FrontMaterial ()).AmbientColor ()).Red ());
341 aFaceContext.Front.ColorAmb.g = float (((theAspect->FrontMaterial ()).AmbientColor ()).Green ());
342 aFaceContext.Front.ColorAmb.b = float (((theAspect->FrontMaterial ()).AmbientColor ()).Blue ());
345 aFaceContext.Front.ColorDif.r = float (((theAspect->FrontMaterial ()).DiffuseColor ()).Red ());
346 aFaceContext.Front.ColorDif.g = float (((theAspect->FrontMaterial ()).DiffuseColor ()).Green ());
347 aFaceContext.Front.ColorDif.b = float (((theAspect->FrontMaterial ()).DiffuseColor ()).Blue ());
350 aFaceContext.Front.ColorEms.r = float (((theAspect->FrontMaterial ()).EmissiveColor ()).Red ());
351 aFaceContext.Front.ColorEms.g = float (((theAspect->FrontMaterial ()).EmissiveColor ()).Green ());
352 aFaceContext.Front.ColorEms.b = float (((theAspect->FrontMaterial ()).EmissiveColor ()).Blue ());
354 aFaceContext.Front.EnvReflexion = float ((theAspect->FrontMaterial ()).EnvReflexion());
355 aFaceContext.IsDef = 1;
356 aFaceContext.Texture.TextureMap = theAspect->TextureMap();
357 aFaceContext.Texture.doTextureMap = theAspect->TextureMapState() ? 1 : 0;
359 Standard_Integer aPolyMode;
360 Standard_ShortReal aPolyFactor, aPolyUnits;
361 theAspect->PolygonOffsets (aPolyMode, aPolyFactor, aPolyUnits);
362 aFaceContext.PolygonOffsetMode = aPolyMode;
363 aFaceContext.PolygonOffsetFactor = (Standard_ShortReal)aPolyFactor;
364 aFaceContext.PolygonOffsetUnits = (Standard_ShortReal)aPolyUnits;
366 SetAspect (aFaceContext);
369 // =======================================================================
372 // =======================================================================
373 void OpenGl_AspectFace::Render (const Handle(OpenGl_Workspace)& theWorkspace) const
375 theWorkspace->SetAspectFace (this);
378 // =======================================================================
379 // function : Release
381 // =======================================================================
382 void OpenGl_AspectFace::Release (const Handle(OpenGl_Context)& theContext)
384 if (!myTextureRes.IsNull())
386 if (!theContext.IsNull())
388 if (myTextureId.IsEmpty())
390 theContext->DelayedRelease (myTextureRes);
394 myTextureRes.Nullify(); // we need nullify all handles before ReleaseResource() call
395 theContext->ReleaseResource (myTextureId);
398 myTextureRes.Nullify();
403 // =======================================================================
404 // function : buildTexure
406 // =======================================================================
407 void OpenGl_AspectFace::buildTexture (const Handle(OpenGl_Workspace)& theWorkspace) const
409 const Handle(OpenGl_Context)& aContext = theWorkspace->GetGlContext();
411 const TCollection_AsciiString& aNewKey = myTextureMap.IsNull() ? THE_EMPTY_KEY : myTextureMap->GetId();
412 if (aNewKey.IsEmpty() || myTextureId != aNewKey)
414 if (!myTextureRes.IsNull())
416 if (myTextureId.IsEmpty())
418 aContext->DelayedRelease (myTextureRes);
419 myTextureRes.Nullify();
423 myTextureRes.Nullify(); // we need nullify all handles before ReleaseResource() call
424 aContext->ReleaseResource (myTextureId);
427 myTextureId = aNewKey;
429 if (!myTextureMap.IsNull())
431 if (aNewKey.IsEmpty() || !aContext->GetResource<Handle(OpenGl_Texture)> (aNewKey, myTextureRes))
433 myTextureRes = new OpenGl_Texture (myTextureMap->GetParams());
434 Handle(Image_PixMap) anImage = myTextureMap->GetImage();
435 if (!anImage.IsNull())
437 myTextureRes->Init (aContext, *anImage.operator->(), myTextureMap->Type());
439 if (!aNewKey.IsEmpty())
441 aContext->ShareResource (aNewKey, myTextureRes);