Commit | Line | Data |
---|---|---|
b311480e | 1 | // Created on: 2011-09-20 |
2 | // Created by: Sergey ZERCHANINOV | |
973c2be1 | 3 | // Copyright (c) 2011-2014 OPEN CASCADE SAS |
b311480e | 4 | // |
973c2be1 | 5 | // This file is part of Open CASCADE Technology software library. |
b311480e | 6 | // |
d5f74e42 | 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 | |
973c2be1 | 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. | |
b311480e | 12 | // |
973c2be1 | 13 | // Alternatively, this file may be used under the terms of Open CASCADE |
14 | // commercial license or contractual agreement. | |
b311480e | 15 | |
2166f0fa SK |
16 | #include <stdio.h> |
17 | #include <stdlib.h> | |
18 | ||
5f8b738e | 19 | #include <OpenGl_GlCore11.hxx> |
2166f0fa | 20 | #include <OpenGl_tgl_funcs.hxx> |
2166f0fa | 21 | |
0b0320e7 | 22 | #include <Graphic3d_TextureParams.hxx> |
23 | #include <Graphic3d_Texture2Dmanual.hxx> | |
c04c30b3 | 24 | #include <Graphic3d_GraphicDriver.hxx> |
3c3131a0 | 25 | #include <Image_AlienPixMap.hxx> |
2166f0fa | 26 | |
30f0ad28 | 27 | #include <NCollection_Mat4.hxx> |
28 | ||
2166f0fa | 29 | #include <OpenGl_AspectLine.hxx> |
30f0ad28 | 30 | #include <OpenGl_Context.hxx> |
30f0ad28 | 31 | #include <OpenGl_Matrix.hxx> |
2166f0fa SK |
32 | #include <OpenGl_Workspace.hxx> |
33 | #include <OpenGl_View.hxx> | |
34 | #include <OpenGl_Trihedron.hxx> | |
35 | #include <OpenGl_GraduatedTrihedron.hxx> | |
0b0320e7 | 36 | #include <OpenGl_PrimitiveArray.hxx> |
2166f0fa | 37 | #include <OpenGl_PrinterContext.hxx> |
30f0ad28 | 38 | #include <OpenGl_ShaderManager.hxx> |
39 | #include <OpenGl_ShaderProgram.hxx> | |
59f45b7c | 40 | #include <OpenGl_Structure.hxx> |
91c60b57 | 41 | #include <OpenGl_ArbFBO.hxx> |
2166f0fa | 42 | |
2166f0fa SK |
43 | #define EPSI 0.0001 |
44 | ||
12381341 | 45 | namespace |
46 | { | |
47 | ||
48 | static const GLfloat THE_DEFAULT_AMBIENT[4] = { 0.0f, 0.0f, 0.0f, 1.0f }; | |
49 | static const GLfloat THE_DEFAULT_SPOT_DIR[3] = { 0.0f, 0.0f, -1.0f }; | |
50 | static const GLfloat THE_DEFAULT_SPOT_EXPONENT = 0.0f; | |
51 | static const GLfloat THE_DEFAULT_SPOT_CUTOFF = 180.0f; | |
52 | ||
53 | }; | |
2166f0fa | 54 | |
30f0ad28 | 55 | extern void InitLayerProp (const int theListId); //szvgl: defined in OpenGl_GraphicDriver_Layer.cxx |
2166f0fa | 56 | |
2166f0fa SK |
57 | /*----------------------------------------------------------------------*/ |
58 | /* | |
59 | * Fonctions privees | |
60 | */ | |
61 | ||
ca3c13d1 | 62 | #if !defined(GL_ES_VERSION_2_0) |
2166f0fa SK |
63 | /*-----------------------------------------------------------------*/ |
64 | /* | |
65 | * Set des lumieres | |
66 | */ | |
c827ea3a | 67 | static void bindLight (const OpenGl_Light& theLight, |
68 | GLenum& theLightGlId, | |
69 | Graphic3d_Vec4& theAmbientColor, | |
70 | const Handle(OpenGl_Workspace)& theWorkspace) | |
2166f0fa SK |
71 | { |
72 | // Only 8 lights in OpenGL... | |
12381341 | 73 | if (theLightGlId > GL_LIGHT7) |
2166f0fa | 74 | { |
12381341 | 75 | return; |
2166f0fa SK |
76 | } |
77 | ||
12381341 | 78 | if (theLight.Type == Visual3d_TOLS_AMBIENT) |
2166f0fa | 79 | { |
4fe9ad57 | 80 | // add RGBA intensity of the ambient light |
81 | theAmbientColor += theLight.Color; | |
12381341 | 82 | return; |
83 | } | |
2166f0fa | 84 | |
c827ea3a | 85 | const Handle(OpenGl_Context)& aContext = theWorkspace->GetGlContext(); |
86 | ||
12381341 | 87 | // the light is a headlight? |
12381341 | 88 | if (theLight.IsHeadlight) |
89 | { | |
c827ea3a | 90 | |
91 | aContext->WorldViewState.Push(); | |
92 | aContext->WorldViewState.SetIdentity(); | |
93 | ||
94 | aContext->ApplyWorldViewMatrix(); | |
2166f0fa SK |
95 | } |
96 | ||
12381341 | 97 | // setup light type |
98 | switch (theLight.Type) | |
3c3131a0 | 99 | { |
12381341 | 100 | case Visual3d_TOLS_DIRECTIONAL: |
101 | { | |
102 | // if the last parameter of GL_POSITION, is zero, the corresponding light source is a Directional one | |
103 | const OpenGl_Vec4 anInfDir = -theLight.Direction; | |
104 | ||
105 | // to create a realistic effect, set the GL_SPECULAR parameter to the same value as the GL_DIFFUSE. | |
106 | glLightfv (theLightGlId, GL_AMBIENT, THE_DEFAULT_AMBIENT); | |
107 | glLightfv (theLightGlId, GL_DIFFUSE, theLight.Color.GetData()); | |
108 | glLightfv (theLightGlId, GL_SPECULAR, theLight.Color.GetData()); | |
109 | glLightfv (theLightGlId, GL_POSITION, anInfDir.GetData()); | |
110 | glLightfv (theLightGlId, GL_SPOT_DIRECTION, THE_DEFAULT_SPOT_DIR); | |
111 | glLightf (theLightGlId, GL_SPOT_EXPONENT, THE_DEFAULT_SPOT_EXPONENT); | |
112 | glLightf (theLightGlId, GL_SPOT_CUTOFF, THE_DEFAULT_SPOT_CUTOFF); | |
113 | break; | |
114 | } | |
115 | case Visual3d_TOLS_POSITIONAL: | |
116 | { | |
117 | // to create a realistic effect, set the GL_SPECULAR parameter to the same value as the GL_DIFFUSE | |
118 | glLightfv (theLightGlId, GL_AMBIENT, THE_DEFAULT_AMBIENT); | |
119 | glLightfv (theLightGlId, GL_DIFFUSE, theLight.Color.GetData()); | |
120 | glLightfv (theLightGlId, GL_SPECULAR, theLight.Color.GetData()); | |
121 | glLightfv (theLightGlId, GL_POSITION, theLight.Position.GetData()); | |
122 | glLightfv (theLightGlId, GL_SPOT_DIRECTION, THE_DEFAULT_SPOT_DIR); | |
123 | glLightf (theLightGlId, GL_SPOT_EXPONENT, THE_DEFAULT_SPOT_EXPONENT); | |
124 | glLightf (theLightGlId, GL_SPOT_CUTOFF, THE_DEFAULT_SPOT_CUTOFF); | |
125 | glLightf (theLightGlId, GL_CONSTANT_ATTENUATION, theLight.ConstAttenuation()); | |
126 | glLightf (theLightGlId, GL_LINEAR_ATTENUATION, theLight.LinearAttenuation()); | |
127 | glLightf (theLightGlId, GL_QUADRATIC_ATTENUATION, 0.0); | |
128 | break; | |
129 | } | |
130 | case Visual3d_TOLS_SPOT: | |
131 | { | |
132 | glLightfv (theLightGlId, GL_AMBIENT, THE_DEFAULT_AMBIENT); | |
133 | glLightfv (theLightGlId, GL_DIFFUSE, theLight.Color.GetData()); | |
134 | glLightfv (theLightGlId, GL_SPECULAR, theLight.Color.GetData()); | |
135 | glLightfv (theLightGlId, GL_POSITION, theLight.Position.GetData()); | |
136 | glLightfv (theLightGlId, GL_SPOT_DIRECTION, theLight.Direction.GetData()); | |
137 | glLightf (theLightGlId, GL_SPOT_EXPONENT, theLight.Concentration() * 128.0f); | |
138 | glLightf (theLightGlId, GL_SPOT_CUTOFF, (theLight.Angle() * 180.0f) / GLfloat(M_PI)); | |
139 | glLightf (theLightGlId, GL_CONSTANT_ATTENUATION, theLight.ConstAttenuation()); | |
140 | glLightf (theLightGlId, GL_LINEAR_ATTENUATION, theLight.LinearAttenuation()); | |
141 | glLightf (theLightGlId, GL_QUADRATIC_ATTENUATION, 0.0f); | |
142 | break; | |
143 | } | |
2166f0fa SK |
144 | } |
145 | ||
12381341 | 146 | // restore matrix in case of headlight |
147 | if (theLight.IsHeadlight) | |
2166f0fa | 148 | { |
c827ea3a | 149 | aContext->WorldViewState.Pop(); |
2166f0fa | 150 | } |
12381341 | 151 | |
152 | glEnable (theLightGlId++); | |
2166f0fa | 153 | } |
ca3c13d1 | 154 | #endif |
2166f0fa | 155 | |
2166f0fa SK |
156 | /*----------------------------------------------------------------------*/ |
157 | ||
0b0320e7 | 158 | void OpenGl_View::DrawBackground (const Handle(OpenGl_Workspace)& theWorkspace) |
2166f0fa | 159 | { |
0b0320e7 | 160 | const Handle(OpenGl_Context)& aCtx = theWorkspace->GetGlContext(); |
2166f0fa | 161 | |
0b0320e7 | 162 | if ((theWorkspace->NamedStatus & OPENGL_NS_WHITEBACK) != 0 // no background |
163 | || (!myBgTextureArray->IsDefined() // no texture | |
164 | && !myBgGradientArray->IsDefined())) // no gradient | |
165 | { | |
166 | return; | |
167 | } | |
2166f0fa | 168 | |
eae454e3 | 169 | const Standard_Boolean wasUsedZBuffer = theWorkspace->SetUseZBuffer (Standard_False); |
170 | if (wasUsedZBuffer) | |
171 | { | |
172 | aCtx->core11fwd->glDisable (GL_DEPTH_TEST); | |
173 | } | |
c827ea3a | 174 | |
0b0320e7 | 175 | aCtx->ProjectionState.Push(); |
e43a4f2b | 176 | aCtx->WorldViewState.Push(); |
177 | aCtx->ModelWorldState.Push(); | |
0b0320e7 | 178 | aCtx->ProjectionState.SetIdentity(); |
e43a4f2b | 179 | aCtx->WorldViewState.SetIdentity(); |
180 | aCtx->ModelWorldState.SetIdentity(); | |
0b0320e7 | 181 | aCtx->ApplyProjectionMatrix(); |
e43a4f2b | 182 | aCtx->ApplyModelViewMatrix(); |
c827ea3a | 183 | |
0b0320e7 | 184 | // Drawing background gradient if: |
185 | // - gradient fill type is not Aspect_GFM_NONE and | |
186 | // - either background texture is no specified or it is drawn in Aspect_FM_CENTERED mode | |
187 | if (myBgGradientArray->IsDefined() | |
d5846489 | 188 | && (!myTextureParams->DoTextureMap() |
0b0320e7 | 189 | || myBgTextureArray->TextureFillMethod() == Aspect_FM_CENTERED |
190 | || myBgTextureArray->TextureFillMethod() == Aspect_FM_NONE)) | |
191 | { | |
192 | #if !defined(GL_ES_VERSION_2_0) | |
193 | GLint aShadingModelOld = GL_SMOOTH; | |
194 | if (aCtx->core11 != NULL) | |
195 | { | |
196 | aCtx->core11fwd->glDisable (GL_LIGHTING); | |
197 | aCtx->core11fwd->glGetIntegerv (GL_SHADE_MODEL, &aShadingModelOld); | |
198 | aCtx->core11->glShadeModel (GL_SMOOTH); | |
199 | } | |
200 | #endif | |
c827ea3a | 201 | |
0b0320e7 | 202 | if (myBgGradientArray->IsDataChanged()) |
203 | { | |
204 | myBgGradientArray->Init (theWorkspace); | |
205 | } | |
2166f0fa | 206 | |
0b0320e7 | 207 | myBgGradientArray->Render (theWorkspace); |
2166f0fa | 208 | |
0b0320e7 | 209 | #if !defined(GL_ES_VERSION_2_0) |
210 | if (aCtx->core11 != NULL) | |
2166f0fa | 211 | { |
0b0320e7 | 212 | aCtx->core11->glShadeModel (aShadingModelOld); |
213 | } | |
214 | #endif | |
215 | } | |
2166f0fa | 216 | |
0b0320e7 | 217 | // Drawing background image if it is defined |
218 | // (texture is defined and fill type is not Aspect_FM_NONE) | |
219 | if (myBgTextureArray->IsDefined() | |
220 | && myTextureParams->DoTextureMap()) | |
221 | { | |
222 | aCtx->core11fwd->glDisable (GL_BLEND); | |
2166f0fa | 223 | |
0b0320e7 | 224 | const OpenGl_AspectFace* anOldAspectFace = theWorkspace->SetAspectFace (myTextureParams); |
2166f0fa | 225 | |
0b0320e7 | 226 | if (myBgTextureArray->IsDataChanged() |
227 | || myBgTextureArray->IsViewSizeChanged (theWorkspace)) | |
f8b2ed36 | 228 | { |
0b0320e7 | 229 | myBgTextureArray->Init (theWorkspace); |
f8b2ed36 | 230 | } |
2166f0fa | 231 | |
0b0320e7 | 232 | myBgTextureArray->Render (theWorkspace); |
c827ea3a | 233 | |
0b0320e7 | 234 | // restore aspects |
235 | theWorkspace->SetAspectFace (anOldAspectFace); | |
236 | } | |
2166f0fa | 237 | |
e43a4f2b | 238 | aCtx->ModelWorldState.Pop(); |
0b0320e7 | 239 | aCtx->WorldViewState.Pop(); |
240 | aCtx->ProjectionState.Pop(); | |
241 | aCtx->ApplyProjectionMatrix(); | |
e43a4f2b | 242 | aCtx->ApplyModelViewMatrix(); |
2166f0fa | 243 | |
eae454e3 | 244 | if (wasUsedZBuffer) |
0b0320e7 | 245 | { |
eae454e3 | 246 | theWorkspace->SetUseZBuffer (Standard_True); |
0b0320e7 | 247 | aCtx->core11fwd->glEnable (GL_DEPTH_TEST); |
2166f0fa | 248 | } |
e276548b | 249 | } |
250 | ||
251 | /*----------------------------------------------------------------------*/ | |
252 | ||
253 | //call_func_redraw_all_structs_proc | |
254 | void OpenGl_View::Render (const Handle(OpenGl_PrinterContext)& thePrintContext, | |
a1954302 | 255 | const Handle(OpenGl_Workspace)& theWorkspace, |
38a0206f | 256 | OpenGl_FrameBuffer* theOutputFBO, |
257 | Graphic3d_Camera::Projection theProjection, | |
a1954302 | 258 | const Graphic3d_CView& theCView, |
a1954302 | 259 | const Standard_Boolean theToDrawImmediate) |
e276548b | 260 | { |
b5ac8292 | 261 | // ================================== |
262 | // Step 1: Prepare for redraw | |
263 | // ================================== | |
264 | ||
265 | const Handle(OpenGl_Context)& aContext = theWorkspace->GetGlContext(); | |
266 | ||
ca3c13d1 | 267 | #if !defined(GL_ES_VERSION_2_0) |
42f8ba56 | 268 | // Disable current clipping planes |
8625ef7e | 269 | if (aContext->core11 != NULL) |
e276548b | 270 | { |
42f8ba56 | 271 | const Standard_Integer aMaxPlanes = aContext->MaxClipPlanes(); |
272 | for (Standard_Integer aClipPlaneId = GL_CLIP_PLANE0; aClipPlaneId < GL_CLIP_PLANE0 + aMaxPlanes; ++aClipPlaneId) | |
e276548b | 273 | { |
42f8ba56 | 274 | aContext->core11fwd->glDisable (aClipPlaneId); |
e276548b | 275 | } |
276 | } | |
ca3c13d1 | 277 | #endif |
e276548b | 278 | |
825aa485 | 279 | Graphic3d_WorldViewProjState aWVPState = myCamera->WorldViewProjState(); |
b7cd4ba7 | 280 | |
825aa485 | 281 | // Update states of OpenGl_BVHTreeSelector (frustum culling algorithm). |
282 | myBVHSelector.SetViewVolume (myCamera); | |
c827ea3a | 283 | |
825aa485 | 284 | const Handle(OpenGl_ShaderManager)& aManager = aContext->ShaderManager(); |
256f9ac0 | 285 | if (StateInfo (myCurrLightSourceState, aManager->LightSourceState().Index()) != myLastLightSourceState) |
392ac980 | 286 | { |
256f9ac0 | 287 | aManager->UpdateLightSourceStateTo (&myLights); |
288 | myLastLightSourceState = StateInfo (myCurrLightSourceState, aManager->LightSourceState().Index()); | |
289 | } | |
b5ac8292 | 290 | |
825aa485 | 291 | if (myWorldViewProjState != aWVPState) |
256f9ac0 | 292 | { |
c827ea3a | 293 | aContext->ProjectionState.SetCurrent (myCamera->ProjectionMatrixF()); |
c827ea3a | 294 | aContext->WorldViewState.SetCurrent (myCamera->OrientationMatrixF()); |
825aa485 | 295 | aContext->ApplyProjectionMatrix(); |
c827ea3a | 296 | aContext->ApplyWorldViewMatrix(); |
825aa485 | 297 | myWorldViewProjState = aWVPState; |
256f9ac0 | 298 | } |
b5ac8292 | 299 | |
256f9ac0 | 300 | if (aManager->ModelWorldState().Index() == 0) |
301 | { | |
c827ea3a | 302 | aContext->ShaderManager()->UpdateModelWorldStateTo (OpenGl_Mat4()); |
b7cd4ba7 | 303 | } |
304 | ||
825aa485 | 305 | |
b5ac8292 | 306 | // ==================================== |
307 | // Step 2: Redraw background | |
308 | // ==================================== | |
e276548b | 309 | |
310 | // Render background | |
91c60b57 | 311 | if (!theToDrawImmediate) |
a89742cf | 312 | { |
0b0320e7 | 313 | DrawBackground (theWorkspace); |
a89742cf | 314 | } |
2166f0fa | 315 | |
ca3c13d1 | 316 | #if !defined(GL_ES_VERSION_2_0) |
2166f0fa | 317 | // Switch off lighting by default |
4e1523ef | 318 | if (aContext->core11 != NULL) |
319 | { | |
320 | glDisable(GL_LIGHTING); | |
321 | } | |
ca3c13d1 | 322 | #endif |
2166f0fa | 323 | |
b5ac8292 | 324 | // ================================= |
27f85086 | 325 | // Step 3: Redraw main plane |
b5ac8292 | 326 | // ================================= |
2166f0fa SK |
327 | |
328 | // Setup face culling | |
329 | GLboolean isCullFace = GL_FALSE; | |
330 | if ( myBackfacing ) | |
331 | { | |
332 | isCullFace = glIsEnabled( GL_CULL_FACE ); | |
333 | if ( myBackfacing < 0 ) | |
334 | { | |
335 | glEnable( GL_CULL_FACE ); | |
336 | glCullFace( GL_BACK ); | |
337 | } | |
b5ac8292 | 338 | else |
2166f0fa SK |
339 | glDisable( GL_CULL_FACE ); |
340 | } | |
341 | ||
ca3c13d1 | 342 | #if !defined(GL_ES_VERSION_2_0) |
b5ac8292 | 343 | // if the view is scaled normal vectors are scaled to unit |
344 | // length for correct displaying of shaded objects | |
345 | const gp_Pnt anAxialScale = myCamera->AxialScale(); | |
7d9e854b | 346 | if (anAxialScale.X() != 1.F || |
347 | anAxialScale.Y() != 1.F || | |
348 | anAxialScale.Z() != 1.F) | |
349 | { | |
350 | aContext->SetGlNormalizeEnabled (Standard_True); | |
351 | } | |
352 | else | |
353 | { | |
354 | aContext->SetGlNormalizeEnabled (Standard_False); | |
355 | } | |
2166f0fa | 356 | |
2166f0fa | 357 | // Apply Fog |
4e1523ef | 358 | if (myFog.IsOn |
359 | && aContext->core11 != NULL) | |
2166f0fa | 360 | { |
b5ac8292 | 361 | Standard_Real aFogFrontConverted = (Standard_Real )myFog.Front + myCamera->Distance(); |
362 | if (myCamera->ZFar() < aFogFrontConverted) | |
2166f0fa | 363 | { |
b5ac8292 | 364 | aFogFrontConverted = myCamera->ZFar(); |
365 | myFog.Front = (Standard_ShortReal )(aFogFrontConverted - myCamera->Distance()); | |
12381341 | 366 | } |
4fe9ad57 | 367 | |
b5ac8292 | 368 | Standard_Real aFogBackConverted = (Standard_Real )myFog.Back + myCamera->Distance(); |
369 | if (myCamera->ZFar() < aFogFrontConverted) | |
12381341 | 370 | { |
b5ac8292 | 371 | aFogBackConverted = myCamera->ZFar(); |
372 | myFog.Back = (Standard_ShortReal )(aFogBackConverted - myCamera->Distance()); | |
12381341 | 373 | } |
b5ac8292 | 374 | |
375 | if (aFogFrontConverted > aFogBackConverted) | |
12381341 | 376 | { |
b5ac8292 | 377 | myFog.Front = (Standard_ShortReal )(aFogFrontConverted - myCamera->Distance()); |
378 | myFog.Back = (Standard_ShortReal )(aFogBackConverted - myCamera->Distance()); | |
ca3c13d1 | 379 | } |
b5ac8292 | 380 | |
381 | glFogi(GL_FOG_MODE, GL_LINEAR); | |
382 | glFogf(GL_FOG_START, (Standard_ShortReal )aFogFrontConverted); | |
383 | glFogf(GL_FOG_END, (Standard_ShortReal )aFogBackConverted); | |
384 | glFogfv(GL_FOG_COLOR, myFog.Color.rgb); | |
385 | glEnable(GL_FOG); | |
2166f0fa | 386 | } |
4e1523ef | 387 | else if (aContext->core11 != NULL) |
388 | { | |
389 | glDisable (GL_FOG); | |
390 | } | |
2166f0fa SK |
391 | |
392 | // Apply InteriorShadingMethod | |
4e1523ef | 393 | if (aContext->core11 != NULL) |
394 | { | |
395 | aContext->core11->glShadeModel (myShadingModel == Visual3d_TOM_FACET | |
396 | || myShadingModel == Visual3d_TOM_NONE ? GL_FLAT : GL_SMOOTH); | |
397 | } | |
ca3c13d1 | 398 | #endif |
2166f0fa | 399 | |
8625ef7e | 400 | aManager->SetShadingModel (myShadingModel); |
401 | ||
b5ac8292 | 402 | // Apply AntiAliasing |
403 | if (myAntiAliasing) | |
404 | theWorkspace->NamedStatus |= OPENGL_NS_ANTIALIASING; | |
405 | else | |
406 | theWorkspace->NamedStatus &= ~OPENGL_NS_ANTIALIASING; | |
407 | ||
408 | if (!aManager->IsEmpty()) | |
2166f0fa | 409 | { |
b5ac8292 | 410 | aManager->UpdateClippingState(); |
411 | } | |
2166f0fa | 412 | |
b5ac8292 | 413 | // Redraw 3d scene |
38a0206f | 414 | if (theProjection == Graphic3d_Camera::Projection_MonoLeftEye) |
b5ac8292 | 415 | { |
c827ea3a | 416 | aContext->ProjectionState.SetCurrent (myCamera->ProjectionStereoLeftF()); |
417 | aContext->ApplyProjectionMatrix(); | |
38a0206f | 418 | } |
419 | else if (theProjection == Graphic3d_Camera::Projection_MonoRightEye) | |
420 | { | |
c827ea3a | 421 | aContext->ProjectionState.SetCurrent (myCamera->ProjectionStereoRightF()); |
422 | aContext->ApplyProjectionMatrix(); | |
2166f0fa | 423 | } |
38a0206f | 424 | RedrawScene (thePrintContext, theWorkspace, theOutputFBO, theCView, theToDrawImmediate); |
2166f0fa | 425 | |
b5ac8292 | 426 | // =============================== |
27f85086 | 427 | // Step 4: Trihedron |
b5ac8292 | 428 | // =============================== |
2166f0fa | 429 | |
26395493 | 430 | // Resetting GL parameters according to the default aspects |
431 | // in order to synchronize GL state with the graphic driver state | |
432 | // before drawing auxiliary stuff (trihedrons, overlayer) | |
433 | // and invoking optional callbacks | |
b5ac8292 | 434 | theWorkspace->ResetAppliedAspect(); |
2166f0fa | 435 | |
b859a34d | 436 | aContext->ChangeClipping().RemoveAll(); |
2166f0fa | 437 | |
392ac980 | 438 | if (!aManager->IsEmpty()) |
30f0ad28 | 439 | { |
392ac980 | 440 | aManager->ResetMaterialStates(); |
441 | aManager->RevertClippingState(); | |
442 | ||
443 | // We need to disable (unbind) all shaders programs to ensure | |
444 | // that all objects without specified aspect will be drawn | |
445 | // correctly (such as background) | |
7d3e64ef | 446 | aContext->BindProgram (NULL); |
30f0ad28 | 447 | } |
448 | ||
a89742cf | 449 | // Render trihedron |
91c60b57 | 450 | if (!theToDrawImmediate) |
a174a3c5 | 451 | { |
a89742cf | 452 | RedrawTrihedron (theWorkspace); |
2166f0fa | 453 | |
a89742cf | 454 | // Restore face culling |
455 | if ( myBackfacing ) | |
2166f0fa | 456 | { |
a89742cf | 457 | if ( isCullFace ) |
458 | { | |
459 | glEnable ( GL_CULL_FACE ); | |
460 | glCullFace ( GL_BACK ); | |
461 | } | |
462 | else | |
463 | glDisable ( GL_CULL_FACE ); | |
2166f0fa | 464 | } |
2166f0fa SK |
465 | } |
466 | ||
e6804ff7 | 467 | // ============================================================== |
27f85086 | 468 | // Step 5: Keep shader manager informed about last View |
e6804ff7 | 469 | // ============================================================== |
470 | ||
471 | if (!aManager.IsNull()) | |
472 | { | |
473 | aManager->SetLastView (this); | |
474 | } | |
2166f0fa SK |
475 | } |
476 | ||
b7cd4ba7 | 477 | // ======================================================================= |
478 | // function : InvalidateBVHData | |
479 | // purpose : | |
480 | // ======================================================================= | |
a1954302 | 481 | void OpenGl_View::InvalidateBVHData (const Graphic3d_ZLayerId theLayerId) |
b7cd4ba7 | 482 | { |
483 | myZLayers.InvalidateBVHData (theLayerId); | |
484 | } | |
485 | ||
2166f0fa SK |
486 | /*----------------------------------------------------------------------*/ |
487 | ||
488 | //ExecuteViewDisplay | |
b34efb62 | 489 | void OpenGl_View::RenderStructs (const Handle(OpenGl_Workspace)& theWorkspace, |
38a0206f | 490 | OpenGl_FrameBuffer* theReadDrawFbo, |
91c60b57 | 491 | const Graphic3d_CView& theCView, |
a1954302 | 492 | const Standard_Boolean theToDrawImmediate) |
2166f0fa | 493 | { |
59f45b7c | 494 | if ( myZLayers.NbStructures() <= 0 ) |
495 | return; | |
2166f0fa | 496 | |
b34efb62 | 497 | const Handle(OpenGl_Context)& aCtx = theWorkspace->GetGlContext(); |
2166f0fa | 498 | |
b34efb62 | 499 | if ( (theWorkspace->NamedStatus & OPENGL_NS_2NDPASSNEED) == 0 ) |
2166f0fa | 500 | { |
ca3c13d1 | 501 | #if !defined(GL_ES_VERSION_2_0) |
b34efb62 | 502 | const int anAntiAliasingMode = theWorkspace->AntiAliasingMode(); |
ca3c13d1 | 503 | #endif |
2166f0fa SK |
504 | |
505 | if ( !myAntiAliasing ) | |
506 | { | |
ca3c13d1 | 507 | #if !defined(GL_ES_VERSION_2_0) |
4e1523ef | 508 | if (aCtx->core11 != NULL) |
509 | { | |
510 | glDisable (GL_POINT_SMOOTH); | |
511 | } | |
2166f0fa | 512 | glDisable(GL_LINE_SMOOTH); |
b34efb62 | 513 | if( anAntiAliasingMode & 2 ) glDisable(GL_POLYGON_SMOOTH); |
ca3c13d1 | 514 | #endif |
2166f0fa SK |
515 | glBlendFunc (GL_ONE, GL_ZERO); |
516 | glDisable (GL_BLEND); | |
517 | } | |
518 | else | |
519 | { | |
ca3c13d1 | 520 | #if !defined(GL_ES_VERSION_2_0) |
4e1523ef | 521 | if (aCtx->core11 != NULL) |
522 | { | |
523 | glEnable(GL_POINT_SMOOTH); | |
524 | } | |
2166f0fa | 525 | glEnable(GL_LINE_SMOOTH); |
b34efb62 | 526 | if( anAntiAliasingMode & 2 ) glEnable(GL_POLYGON_SMOOTH); |
ca3c13d1 | 527 | #endif |
3c3131a0 | 528 | glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); |
2166f0fa SK |
529 | glEnable (GL_BLEND); |
530 | } | |
531 | } | |
532 | ||
91c60b57 | 533 | Standard_Boolean toRenderGL = theToDrawImmediate || |
c3282ec1 | 534 | theCView.RenderParams.Method != Graphic3d_RM_RAYTRACING || |
535 | myRaytraceInitStatus == OpenGl_RT_FAIL || | |
536 | aCtx->IsFeedback(); | |
91c60b57 | 537 | |
538 | if (!toRenderGL) | |
539 | { | |
540 | toRenderGL = !initRaytraceResources (theCView, aCtx) || | |
541 | !updateRaytraceGeometry (OpenGl_GUM_CHECK, theWorkspace->ActiveViewId(), aCtx); | |
542 | ||
5682a029 | 543 | toRenderGL |= !myIsRaytraceDataValid; // if no ray-trace data use OpenGL |
91c60b57 | 544 | |
5682a029 | 545 | if (!toRenderGL) |
91c60b57 | 546 | { |
38a0206f | 547 | const Standard_Integer aSizeX = theReadDrawFbo != NULL ? |
548 | theReadDrawFbo->GetVPSizeX() : theWorkspace->Width(); | |
549 | const Standard_Integer aSizeY = theReadDrawFbo != NULL ? | |
550 | theReadDrawFbo->GetVPSizeY() : theWorkspace->Height(); | |
91c60b57 | 551 | |
552 | if (myOpenGlFBO.IsNull()) | |
553 | myOpenGlFBO = new OpenGl_FrameBuffer; | |
554 | ||
555 | if (myOpenGlFBO->GetVPSizeX() != aSizeX | |
556 | || myOpenGlFBO->GetVPSizeY() != aSizeY) | |
557 | { | |
558 | myOpenGlFBO->Init (aCtx, aSizeX, aSizeY); | |
559 | } | |
560 | ||
561 | if (myRaytraceFilter.IsNull()) | |
562 | myRaytraceFilter = new OpenGl_RaytraceFilter; | |
563 | ||
564 | myRaytraceFilter->SetPrevRenderFilter (theWorkspace->GetRenderFilter()); | |
565 | ||
38a0206f | 566 | if (theReadDrawFbo != NULL) |
567 | theReadDrawFbo->UnbindBuffer (aCtx); | |
91c60b57 | 568 | |
569 | // Prepare preliminary OpenGL output | |
570 | if (aCtx->arbFBOBlit != NULL) | |
571 | { | |
572 | // Render bottom OSD layer | |
573 | myZLayers.Render (theWorkspace, theToDrawImmediate, OpenGl_LF_Bottom); | |
574 | ||
575 | theWorkspace->SetRenderFilter (myRaytraceFilter); | |
576 | { | |
38a0206f | 577 | if (theReadDrawFbo != NULL) |
91c60b57 | 578 | { |
38a0206f | 579 | theReadDrawFbo->BindReadBuffer (aCtx); |
91c60b57 | 580 | } |
581 | else | |
582 | { | |
583 | aCtx->arbFBO->glBindFramebuffer (GL_READ_FRAMEBUFFER, 0); | |
584 | } | |
585 | ||
586 | myOpenGlFBO->BindDrawBuffer (aCtx); | |
587 | ||
588 | aCtx->arbFBOBlit->glBlitFramebuffer (0, 0, aSizeX, aSizeY, | |
589 | 0, 0, aSizeX, aSizeY, | |
590 | GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT, | |
591 | GL_NEAREST); | |
592 | ||
593 | // Render non-polygonal elements in default layer | |
594 | myZLayers.Render (theWorkspace, theToDrawImmediate, OpenGl_LF_Default); | |
595 | } | |
596 | theWorkspace->SetRenderFilter (myRaytraceFilter->PrevRenderFilter()); | |
597 | } | |
598 | ||
38a0206f | 599 | if (theReadDrawFbo != NULL) |
91c60b57 | 600 | { |
38a0206f | 601 | theReadDrawFbo->BindBuffer (aCtx); |
91c60b57 | 602 | } |
603 | else | |
604 | { | |
605 | aCtx->arbFBO->glBindFramebuffer (GL_FRAMEBUFFER, 0); | |
606 | } | |
607 | ||
608 | // Ray-tracing polygonal primitive arrays | |
38a0206f | 609 | raytrace (theCView, aSizeX, aSizeY, theReadDrawFbo, aCtx); |
91c60b57 | 610 | |
611 | // Render upper (top and topmost) OpenGL layers | |
612 | myZLayers.Render (theWorkspace, theToDrawImmediate, OpenGl_LF_Upper); | |
613 | } | |
614 | } | |
615 | ||
616 | // Redraw 3D scene using OpenGL in standard | |
617 | // mode or in case of ray-tracing failure | |
618 | if (toRenderGL) | |
619 | { | |
620 | myZLayers.Render (theWorkspace, theToDrawImmediate, OpenGl_LF_All); | |
621 | ||
622 | // Set flag that scene was redrawn by standard pipeline | |
623 | theCView.WasRedrawnGL = Standard_True; | |
624 | } | |
2166f0fa SK |
625 | } |
626 | ||
627 | /*----------------------------------------------------------------------*/ | |
628 | ||
a89742cf | 629 | void OpenGl_View::RedrawTrihedron (const Handle(OpenGl_Workspace) &theWorkspace) |
630 | { | |
631 | // display global trihedron | |
536d98e2 | 632 | if (myToShowTrihedron) |
a89742cf | 633 | { |
536d98e2 | 634 | myTrihedron.Render (theWorkspace); |
a89742cf | 635 | } |
536d98e2 | 636 | if (myToShowGradTrihedron) |
a89742cf | 637 | { |
536d98e2 | 638 | myGraduatedTrihedron.Render (theWorkspace); |
a89742cf | 639 | } |
640 | } | |
641 | ||
642 | /*----------------------------------------------------------------------*/ | |
643 | ||
2166f0fa | 644 | //call_togl_create_bg_texture |
3c3131a0 | 645 | void OpenGl_View::CreateBackgroundTexture (const Standard_CString theFilePath, |
646 | const Aspect_FillMethod theFillStyle) | |
2166f0fa | 647 | { |
0b0320e7 | 648 | // Prepare aspect for texture storage |
649 | Handle(Graphic3d_AspectFillArea3d) anAspect = new Graphic3d_AspectFillArea3d(); | |
650 | Handle(Graphic3d_Texture2Dmanual) aTextureMap = new Graphic3d_Texture2Dmanual (TCollection_AsciiString (theFilePath)); | |
651 | aTextureMap->EnableRepeat(); | |
652 | aTextureMap->DisableModulate(); | |
653 | aTextureMap->GetParams()->SetGenMode (Graphic3d_TOTM_MANUAL, | |
654 | Graphic3d_Vec4 (0.0f, 0.0f, 0.0f, 0.0f), | |
655 | Graphic3d_Vec4 (0.0f, 0.0f, 0.0f, 0.0f)); | |
656 | anAspect->SetTextureMap (aTextureMap); | |
657 | anAspect->SetInteriorStyle (Aspect_IS_SOLID); | |
658 | // Enable texture mapping | |
659 | if (aTextureMap->IsDone()) | |
660 | { | |
661 | anAspect->SetTextureMapOn(); | |
3c3131a0 | 662 | } |
663 | else | |
664 | { | |
0b0320e7 | 665 | anAspect->SetTextureMapOff(); |
666 | return; | |
3c3131a0 | 667 | |
3c3131a0 | 668 | } |
2166f0fa | 669 | |
0b0320e7 | 670 | // Set texture parameters |
671 | myTextureParams->SetAspect (anAspect); | |
2166f0fa | 672 | |
0b0320e7 | 673 | myBgTextureArray->SetTextureParameters (theFillStyle); |
2166f0fa SK |
674 | } |
675 | ||
676 | /*----------------------------------------------------------------------*/ | |
677 | ||
678 | //call_togl_set_bg_texture_style | |
0b0320e7 | 679 | void OpenGl_View::SetBackgroundTextureStyle (const Aspect_FillMethod theFillStyle) |
2166f0fa | 680 | { |
0b0320e7 | 681 | myBgTextureArray->SetTextureFillMethod (theFillStyle); |
2166f0fa SK |
682 | } |
683 | ||
684 | /*----------------------------------------------------------------------*/ | |
685 | ||
686 | //call_togl_gradient_background | |
0b0320e7 | 687 | void OpenGl_View::SetBackgroundGradient (const Quantity_Color& theColor1, |
688 | const Quantity_Color& theColor2, | |
689 | const Aspect_GradientFillMethod theType) | |
2166f0fa | 690 | { |
0b0320e7 | 691 | myBgGradientArray->SetGradientParameters (theColor1, theColor2, theType); |
2166f0fa SK |
692 | } |
693 | ||
694 | /*----------------------------------------------------------------------*/ | |
695 | ||
696 | //call_togl_set_gradient_type | |
0b0320e7 | 697 | void OpenGl_View::SetBackgroundGradientType (const Aspect_GradientFillMethod theType) |
2166f0fa | 698 | { |
0b0320e7 | 699 | myBgGradientArray->SetGradientFillMethod (theType); |
2166f0fa SK |
700 | } |
701 | ||
59f45b7c | 702 | //======================================================================= |
703 | //function : AddZLayer | |
3c3131a0 | 704 | //purpose : |
59f45b7c | 705 | //======================================================================= |
706 | ||
a1954302 | 707 | void OpenGl_View::AddZLayer (const Graphic3d_ZLayerId theLayerId) |
59f45b7c | 708 | { |
709 | myZLayers.AddLayer (theLayerId); | |
710 | } | |
711 | ||
712 | //======================================================================= | |
713 | //function : RemoveZLayer | |
3c3131a0 | 714 | //purpose : |
59f45b7c | 715 | //======================================================================= |
716 | ||
a1954302 | 717 | void OpenGl_View::RemoveZLayer (const Graphic3d_ZLayerId theLayerId) |
59f45b7c | 718 | { |
719 | myZLayers.RemoveLayer (theLayerId); | |
720 | } | |
721 | ||
722 | //======================================================================= | |
723 | //function : DisplayStructure | |
3c3131a0 | 724 | //purpose : |
59f45b7c | 725 | //======================================================================= |
726 | ||
a1954302 | 727 | void OpenGl_View::DisplayStructure (const Handle(Graphic3d_Structure)& theStructure, |
728 | const Standard_Integer thePriority) | |
59f45b7c | 729 | { |
a1954302 | 730 | const OpenGl_Structure* aStruct = reinterpret_cast<const OpenGl_Structure*> (theStructure->CStructure().operator->()); |
731 | const Graphic3d_ZLayerId aZLayer = aStruct->ZLayer(); | |
732 | myZLayers.AddStructure (aStruct, aZLayer, thePriority); | |
59f45b7c | 733 | } |
734 | ||
735 | //======================================================================= | |
736 | //function : EraseStructure | |
3c3131a0 | 737 | //purpose : |
59f45b7c | 738 | //======================================================================= |
739 | ||
a1954302 | 740 | void OpenGl_View::EraseStructure (const Handle(Graphic3d_Structure)& theStructure) |
59f45b7c | 741 | { |
a1954302 | 742 | myZLayers.RemoveStructure (theStructure); |
59f45b7c | 743 | } |
744 | ||
679ecdee | 745 | //======================================================================= |
59f45b7c | 746 | //function : ChangeZLayer |
747 | //purpose : | |
748 | //======================================================================= | |
749 | ||
a1954302 | 750 | void OpenGl_View::ChangeZLayer (const OpenGl_Structure* theStructure, |
751 | const Graphic3d_ZLayerId theNewLayerId) | |
59f45b7c | 752 | { |
a1954302 | 753 | const Graphic3d_ZLayerId anOldLayer = theStructure->ZLayer(); |
59f45b7c | 754 | myZLayers.ChangeLayer (theStructure, anOldLayer, theNewLayerId); |
755 | } | |
b5ac8292 | 756 | |
c5751993 | 757 | //======================================================================= |
758 | //function : SetZLayerSettings | |
759 | //purpose : | |
760 | //======================================================================= | |
a1954302 | 761 | void OpenGl_View::SetZLayerSettings (const Graphic3d_ZLayerId theLayerId, |
762 | const Graphic3d_ZLayerSettings& theSettings) | |
c5751993 | 763 | { |
a1954302 | 764 | myZLayers.SetLayerSettings (theLayerId, theSettings); |
c5751993 | 765 | } |
766 | ||
b7cd4ba7 | 767 | //======================================================================= |
768 | //function : ChangePriority | |
769 | //purpose : | |
770 | //======================================================================= | |
771 | void OpenGl_View::ChangePriority (const OpenGl_Structure *theStructure, | |
772 | const Standard_Integer theNewPriority) | |
773 | { | |
a1954302 | 774 | const Graphic3d_ZLayerId aLayerId = theStructure->ZLayer(); |
b7cd4ba7 | 775 | myZLayers.ChangePriority (theStructure, aLayerId, theNewPriority); |
776 | } | |
c5751993 | 777 | |
b5ac8292 | 778 | //======================================================================= |
779 | //function : RedrawScene | |
780 | //purpose : | |
781 | //======================================================================= | |
782 | ||
783 | void OpenGl_View::RedrawScene (const Handle(OpenGl_PrinterContext)& thePrintContext, | |
a1954302 | 784 | const Handle(OpenGl_Workspace)& theWorkspace, |
38a0206f | 785 | OpenGl_FrameBuffer* theReadDrawFbo, |
91c60b57 | 786 | const Graphic3d_CView& theCView, |
a1954302 | 787 | const Standard_Boolean theToDrawImmediate) |
b5ac8292 | 788 | { |
789 | const Handle(OpenGl_Context)& aContext = theWorkspace->GetGlContext(); | |
790 | ||
791 | if (myZClip.Back.IsOn || myZClip.Front.IsOn) | |
792 | { | |
793 | Handle(Graphic3d_ClipPlane) aPlaneBack; | |
794 | Handle(Graphic3d_ClipPlane) aPlaneFront; | |
795 | ||
796 | if (myZClip.Back.IsOn) | |
797 | { | |
798 | Standard_Real aClipBackConverted = (Standard_Real )myZClip.Front.Limit + myCamera->Distance(); | |
799 | if (myCamera->ZFar() < aClipBackConverted) | |
800 | { | |
801 | aClipBackConverted = myCamera->ZFar(); | |
802 | myZClip.Back.Limit = (Standard_ShortReal )(aClipBackConverted - myCamera->Distance()); | |
803 | } | |
804 | const Graphic3d_ClipPlane::Equation aBackEquation (0.0, 0.0, 1.0, (Standard_ShortReal )aClipBackConverted); | |
805 | aPlaneBack = new Graphic3d_ClipPlane (aBackEquation); | |
806 | } | |
807 | ||
808 | if (myZClip.Front.IsOn) | |
809 | { | |
810 | Standard_Real aClipFrontConverted = (Standard_Real )myZClip.Front.Limit + myCamera->Distance(); | |
811 | if (myCamera->ZNear() > aClipFrontConverted) | |
812 | { | |
813 | aClipFrontConverted = myCamera->ZNear(); | |
814 | myZClip.Front.Limit = (Standard_ShortReal )(aClipFrontConverted - myCamera->Distance()); | |
815 | } | |
816 | const Graphic3d_ClipPlane::Equation aFrontEquation (0.0, 0.0, -1.0, (Standard_ShortReal )-aClipFrontConverted); | |
817 | aPlaneFront = new Graphic3d_ClipPlane (aFrontEquation); | |
818 | } | |
819 | ||
cddbf6a9 | 820 | // Specify slicing planes with identity transformation |
b5ac8292 | 821 | if (!aPlaneBack.IsNull() || !aPlaneFront.IsNull()) |
822 | { | |
823 | Graphic3d_SequenceOfHClipPlane aSlicingPlanes; | |
824 | if (!aPlaneBack.IsNull()) | |
825 | { | |
826 | aSlicingPlanes.Append (aPlaneBack); | |
827 | } | |
828 | ||
829 | if (!aPlaneFront.IsNull()) | |
830 | { | |
831 | aSlicingPlanes.Append (aPlaneFront); | |
832 | } | |
833 | ||
834 | // add planes at loaded view matrix state | |
835 | aContext->ChangeClipping().AddView (aSlicingPlanes, theWorkspace); | |
836 | } | |
837 | } | |
838 | ||
b5ac8292 | 839 | #ifdef _WIN32 |
c827ea3a | 840 | // set printing scale/tiling transformation |
b5ac8292 | 841 | if (!thePrintContext.IsNull()) |
842 | { | |
c827ea3a | 843 | aContext->ProjectionState.Push(); |
844 | aContext->ProjectionState.SetCurrent (thePrintContext->ProjTransformation() * aContext->ProjectionState.Current()); | |
845 | aContext->ApplyProjectionMatrix(); | |
b5ac8292 | 846 | } |
ca3c13d1 | 847 | #endif |
b5ac8292 | 848 | |
cddbf6a9 | 849 | // Specify clipping planes in view transformation space |
850 | if (!myClipPlanes.IsEmpty()) | |
851 | { | |
852 | Graphic3d_SequenceOfHClipPlane aUserPlanes; | |
853 | Graphic3d_SequenceOfHClipPlane::Iterator aClippingIt (myClipPlanes); | |
854 | for (; aClippingIt.More(); aClippingIt.Next()) | |
855 | { | |
856 | const Handle(Graphic3d_ClipPlane)& aClipPlane = aClippingIt.Value(); | |
857 | if (aClipPlane->IsOn()) | |
858 | { | |
859 | aUserPlanes.Append (aClipPlane); | |
860 | } | |
861 | } | |
862 | ||
863 | if (!aUserPlanes.IsEmpty()) | |
864 | { | |
865 | aContext->ChangeClipping().AddWorld (aUserPlanes); | |
866 | } | |
867 | ||
868 | if (!aContext->ShaderManager()->IsEmpty()) | |
869 | { | |
870 | aContext->ShaderManager()->UpdateClippingState(); | |
871 | } | |
872 | } | |
873 | ||
ca3c13d1 | 874 | #if !defined(GL_ES_VERSION_2_0) |
b5ac8292 | 875 | // Apply Lights |
4e1523ef | 876 | if (aContext->core11 != NULL) |
b5ac8292 | 877 | { |
878 | // setup lights | |
879 | Graphic3d_Vec4 anAmbientColor (THE_DEFAULT_AMBIENT[0], | |
880 | THE_DEFAULT_AMBIENT[1], | |
881 | THE_DEFAULT_AMBIENT[2], | |
882 | THE_DEFAULT_AMBIENT[3]); | |
883 | GLenum aLightGlId = GL_LIGHT0; | |
884 | for (OpenGl_ListOfLight::Iterator aLightIt (myLights); | |
885 | aLightIt.More(); aLightIt.Next()) | |
886 | { | |
c827ea3a | 887 | bindLight (aLightIt.Value(), aLightGlId, anAmbientColor, theWorkspace); |
b5ac8292 | 888 | } |
889 | ||
890 | // apply accumulated ambient color | |
891 | anAmbientColor.a() = 1.0f; | |
892 | glLightModelfv (GL_LIGHT_MODEL_AMBIENT, anAmbientColor.GetData()); | |
893 | ||
894 | if (aLightGlId != GL_LIGHT0) | |
895 | { | |
896 | glEnable (GL_LIGHTING); | |
897 | } | |
898 | // switch off unused lights | |
899 | for (; aLightGlId <= GL_LIGHT7; ++aLightGlId) | |
900 | { | |
901 | glDisable (aLightGlId); | |
902 | } | |
903 | } | |
ca3c13d1 | 904 | #endif |
b5ac8292 | 905 | |
906 | // Clear status bitfields | |
907 | theWorkspace->NamedStatus &= ~(OPENGL_NS_2NDPASSNEED | OPENGL_NS_2NDPASSDO); | |
908 | ||
e135a155 | 909 | // Update state of surface detail level |
910 | theWorkspace->GetGlContext()->ShaderManager()->UpdateSurfaceDetailStateTo (mySurfaceDetail); | |
911 | ||
b5ac8292 | 912 | // Added PCT for handling of textures |
913 | switch (mySurfaceDetail) | |
914 | { | |
915 | case Visual3d_TOD_NONE: | |
916 | theWorkspace->NamedStatus |= OPENGL_NS_FORBIDSETTEX; | |
917 | theWorkspace->DisableTexture(); | |
918 | // Render the view | |
38a0206f | 919 | RenderStructs (theWorkspace, theReadDrawFbo, theCView, theToDrawImmediate); |
b5ac8292 | 920 | break; |
921 | ||
922 | case Visual3d_TOD_ENVIRONMENT: | |
923 | theWorkspace->NamedStatus |= OPENGL_NS_FORBIDSETTEX; | |
47e9c178 | 924 | if (theCView.RenderParams.Method != Graphic3d_RM_RAYTRACING) |
925 | { | |
926 | theWorkspace->EnableTexture (myTextureEnv); | |
927 | } | |
b5ac8292 | 928 | // Render the view |
38a0206f | 929 | RenderStructs (theWorkspace, theReadDrawFbo, theCView, theToDrawImmediate); |
b5ac8292 | 930 | theWorkspace->DisableTexture(); |
931 | break; | |
932 | ||
933 | case Visual3d_TOD_ALL: | |
934 | // First pass | |
935 | theWorkspace->NamedStatus &= ~OPENGL_NS_FORBIDSETTEX; | |
936 | // Render the view | |
38a0206f | 937 | RenderStructs (theWorkspace, theReadDrawFbo, theCView, theToDrawImmediate); |
b5ac8292 | 938 | theWorkspace->DisableTexture(); |
939 | ||
940 | // Second pass | |
941 | if (theWorkspace->NamedStatus & OPENGL_NS_2NDPASSNEED) | |
942 | { | |
943 | theWorkspace->NamedStatus |= OPENGL_NS_2NDPASSDO; | |
47e9c178 | 944 | if (theCView.RenderParams.Method != Graphic3d_RM_RAYTRACING) |
945 | { | |
946 | theWorkspace->EnableTexture (myTextureEnv); | |
947 | } | |
b5ac8292 | 948 | |
949 | // Remember OpenGl properties | |
ca3c13d1 | 950 | GLint aSaveBlendDst = GL_ONE_MINUS_SRC_ALPHA, aSaveBlendSrc = GL_SRC_ALPHA; |
b5ac8292 | 951 | GLint aSaveZbuffFunc; |
952 | GLboolean aSaveZbuffWrite; | |
953 | glGetBooleanv (GL_DEPTH_WRITEMASK, &aSaveZbuffWrite); | |
954 | glGetIntegerv (GL_DEPTH_FUNC, &aSaveZbuffFunc); | |
ca3c13d1 | 955 | #if !defined(GL_ES_VERSION_2_0) |
b5ac8292 | 956 | glGetIntegerv (GL_BLEND_DST, &aSaveBlendDst); |
957 | glGetIntegerv (GL_BLEND_SRC, &aSaveBlendSrc); | |
ca3c13d1 | 958 | #endif |
b5ac8292 | 959 | GLboolean wasZbuffEnabled = glIsEnabled (GL_DEPTH_TEST); |
960 | GLboolean wasBlendEnabled = glIsEnabled (GL_BLEND); | |
961 | ||
962 | // Change the properties for second rendering pass | |
963 | glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); | |
964 | glEnable (GL_BLEND); | |
965 | ||
966 | glDepthFunc (GL_EQUAL); | |
967 | glDepthMask (GL_FALSE); | |
968 | glEnable (GL_DEPTH_TEST); | |
969 | ||
970 | theWorkspace->NamedStatus |= OPENGL_NS_FORBIDSETTEX; | |
971 | ||
972 | // Render the view | |
38a0206f | 973 | RenderStructs (theWorkspace, theReadDrawFbo, theCView, theToDrawImmediate); |
b5ac8292 | 974 | theWorkspace->DisableTexture(); |
975 | ||
976 | // Restore properties back | |
977 | glBlendFunc (aSaveBlendSrc, aSaveBlendDst); | |
978 | if (!wasBlendEnabled) | |
979 | glDisable (GL_BLEND); | |
980 | ||
981 | glDepthFunc (aSaveZbuffFunc); | |
982 | glDepthMask (aSaveZbuffWrite); | |
983 | if (!wasZbuffEnabled) | |
984 | glDisable (GL_DEPTH_FUNC); | |
985 | } | |
986 | break; | |
987 | } | |
c827ea3a | 988 | |
989 | // Apply restored view matrix. | |
990 | aContext->ApplyWorldViewMatrix(); | |
991 | ||
992 | #ifdef _WIN32 | |
993 | // set printing scale/tiling transformation | |
994 | if (!thePrintContext.IsNull()) | |
995 | { | |
996 | aContext->ProjectionState.Pop(); | |
997 | aContext->ApplyProjectionMatrix(); | |
998 | } | |
999 | #endif | |
1000 | ||
b5ac8292 | 1001 | } |