0025442: Visualization, TKOpenGl - prevent inclusion of system header glxext.h
[occt.git] / src / OpenGl / OpenGl_GraphicDriver.cxx
1 // Created on: 2011-10-20
2 // Created by: Sergey ZERCHANINOV
3 // Copyright (c) 2011-2013 OPEN CASCADE SAS
4 //
5 // This file is part of Open CASCADE Technology software library.
6 //
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.
12 //
13 // Alternatively, this file may be used under the terms of Open CASCADE
14 // commercial license or contractual agreement.
15
16 #include <OpenGl_GraphicDriver.hxx>
17 #include <OpenGl_Context.hxx>
18 #include <OpenGl_Flipper.hxx>
19 #include <OpenGl_GraduatedTrihedron.hxx>
20 #include <OpenGl_Group.hxx>
21 #include <OpenGl_CView.hxx>
22 #include <OpenGl_View.hxx>
23 #include <OpenGl_StencilTest.hxx>
24 #include <OpenGl_Text.hxx>
25 #include <OpenGl_Trihedron.hxx>
26 #include <OpenGl_Workspace.hxx>
27
28 #include <Aspect_GraphicDeviceDefinitionError.hxx>
29 #include <Message_Messenger.hxx>
30 #include <OSD_Environment.hxx>
31 #include <Standard_NotImplemented.hxx>
32
33 #if !defined(_WIN32) && !defined(__ANDROID__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX))
34   #include <X11/Xlib.h> // XOpenDisplay()
35 #endif
36
37 #if defined(HAVE_EGL) || defined(__ANDROID__)
38   #include <EGL/egl.h>
39 #endif
40
41 IMPLEMENT_STANDARD_HANDLE(OpenGl_GraphicDriver,Graphic3d_GraphicDriver)
42 IMPLEMENT_STANDARD_RTTIEXT(OpenGl_GraphicDriver,Graphic3d_GraphicDriver)
43
44 namespace
45 {
46   static const Handle(OpenGl_Context) TheNullGlCtx;
47 }
48
49 // =======================================================================
50 // function : OpenGl_GraphicDriver
51 // purpose  :
52 // =======================================================================
53 OpenGl_GraphicDriver::OpenGl_GraphicDriver (const Handle(Aspect_DisplayConnection)& theDisp,
54                                             const Standard_Boolean                  theToInitialize)
55 : Graphic3d_GraphicDriver (theDisp),
56   myIsOwnContext (Standard_False),
57 #if defined(HAVE_EGL) || defined(__ANDROID__)
58   myEglDisplay ((Aspect_Display )EGL_NO_DISPLAY),
59   myEglContext ((Aspect_RenderingContext )EGL_NO_CONTEXT),
60   myEglConfig  (NULL),
61 #endif
62   myCaps           (new OpenGl_Caps()),
63   myMapOfView      (1, NCollection_BaseAllocator::CommonBaseAllocator()),
64   myMapOfWS        (1, NCollection_BaseAllocator::CommonBaseAllocator()),
65   myMapOfStructure (1, NCollection_BaseAllocator::CommonBaseAllocator()),
66   myUserDrawCallback (NULL),
67   myTempText (new OpenGl_Text())
68 {
69 #if !defined(_WIN32) && !defined(__ANDROID__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX))
70   if (myDisplayConnection.IsNull())
71   {
72     //Aspect_GraphicDeviceDefinitionError::Raise ("OpenGl_GraphicDriver: cannot connect to X server!");
73     return;
74   }
75
76   Display* aDisplay = myDisplayConnection->GetDisplay();
77   Bool toSync = ::getenv ("CSF_GraphicSync") != NULL
78              || ::getenv ("CALL_SYNCHRO_X")  != NULL;
79   XSynchronize (aDisplay, toSync);
80
81 #if !defined(HAVE_EGL)
82   // does the server know about OpenGL & GLX?
83   int aDummy;
84   if (!XQueryExtension (aDisplay, "GLX", &aDummy, &aDummy, &aDummy))
85   {
86     ::Message::DefaultMessenger()->Send ("OpenGl_GraphicDriver, this system doesn't appear to support OpenGL!", Message_Warning);
87   }
88 #endif
89 #endif
90   if (theToInitialize
91   && !InitContext())
92   {
93     Aspect_GraphicDeviceDefinitionError::Raise ("OpenGl_GraphicDriver: default context can not be initialized!");
94   }
95 }
96
97 // =======================================================================
98 // function : ~OpenGl_GraphicDriver
99 // purpose  :
100 // =======================================================================
101 OpenGl_GraphicDriver::~OpenGl_GraphicDriver()
102 {
103   ReleaseContext();
104 }
105
106 // =======================================================================
107 // function : ReleaseContext
108 // purpose  :
109 // =======================================================================
110 void OpenGl_GraphicDriver::ReleaseContext()
111 {
112   Handle(OpenGl_Context) aCtxShared;
113   for (NCollection_DataMap<Standard_Integer, Handle(OpenGl_Workspace)>::Iterator aWindowIter (myMapOfWS);
114        aWindowIter.More(); aWindowIter.Next())
115   {
116     const Handle(OpenGl_Workspace)& aWindow = aWindowIter.ChangeValue();
117     const Handle(OpenGl_Context)&   aCtx    = aWindow->GetGlContext();
118     if (aCtx->MakeCurrent()
119      && aCtxShared.IsNull())
120     {
121       aCtxShared = aCtx;
122     }
123   }
124
125   if (!aCtxShared.IsNull())
126   {
127     aCtxShared->MakeCurrent();
128   }
129   for (NCollection_DataMap<Standard_Integer, Handle(OpenGl_View)>::Iterator aViewIter (myMapOfView);
130        aViewIter.More(); aViewIter.Next())
131   {
132     const Handle(OpenGl_View)& aView = aViewIter.ChangeValue();
133     aView->ReleaseGlResources (aCtxShared);
134   }
135
136   for (NCollection_DataMap<Standard_Integer, OpenGl_Structure*>::Iterator aStructIt (myMapOfStructure);
137        aStructIt.More (); aStructIt.Next())
138   {
139     OpenGl_Structure* aStruct = aStructIt.ChangeValue();
140     aStruct->ReleaseGlResources (aCtxShared);
141   }
142   myTempText->Release (aCtxShared.operator->());
143   myDeviceLostFlag = myDeviceLostFlag || !myMapOfStructure.IsEmpty();
144
145   for (NCollection_DataMap<Standard_Integer, Handle(OpenGl_Workspace)>::Iterator aWindowIter (myMapOfWS);
146        aWindowIter.More(); aWindowIter.Next())
147   {
148     const Handle(OpenGl_Workspace)& aWindow = aWindowIter.ChangeValue();
149     const Handle(OpenGl_Context)&   aCtx    = aWindow->GetGlContext();
150     aCtx->forcedRelease();
151   }
152
153 #if defined(HAVE_EGL) || defined(__ANDROID__)
154   if (myIsOwnContext)
155   {
156     if (myEglContext != (Aspect_RenderingContext )EGL_NO_CONTEXT)
157     {
158       if (eglMakeCurrent ((EGLDisplay )myEglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT) != EGL_TRUE)
159       {
160         ::Message::DefaultMessenger()->Send ("OpenGl_GraphicDriver, FAILED to release OpenGL context!", Message_Warning);
161       }
162       eglDestroyContext ((EGLDisplay )myEglDisplay, (EGLContext )myEglContext);
163     }
164
165     if (myEglDisplay != (Aspect_Display )EGL_NO_DISPLAY)
166     {
167       if (eglTerminate ((EGLDisplay )myEglDisplay) != EGL_TRUE)
168       {
169         ::Message::DefaultMessenger()->Send ("OpenGl_GraphicDriver, EGL, eglTerminate FAILED!", Message_Warning);
170       }
171     }
172   }
173
174   myEglDisplay = (Aspect_Display )EGL_NO_DISPLAY;
175   myEglContext = (Aspect_RenderingContext )EGL_NO_CONTEXT;
176   myEglConfig  = NULL;
177 #endif
178   myIsOwnContext = Standard_False;
179 }
180
181 // =======================================================================
182 // function : InitContext
183 // purpose  :
184 // =======================================================================
185 Standard_Boolean OpenGl_GraphicDriver::InitContext()
186 {
187   ReleaseContext();
188 #if defined(HAVE_EGL) || defined(__ANDROID__)
189
190 #if !defined(_WIN32) && !defined(__ANDROID__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX))
191   if (myDisplayConnection.IsNull())
192   {
193     return Standard_False;
194   }
195   Display* aDisplay = myDisplayConnection->GetDisplay();
196   myEglDisplay = (Aspect_Display )eglGetDisplay (aDisplay);
197 #else
198   myEglDisplay = (Aspect_Display )eglGetDisplay (EGL_DEFAULT_DISPLAY);
199 #endif
200   if ((EGLDisplay )myEglDisplay == EGL_NO_DISPLAY)
201   {
202     ::Message::DefaultMessenger()->Send ("Error: no EGL display!", Message_Fail);
203     return Standard_False;
204   }
205
206   EGLint aVerMajor = 0; EGLint aVerMinor = 0;
207   if (eglInitialize ((EGLDisplay )myEglDisplay, &aVerMajor, &aVerMinor) != EGL_TRUE)
208   {
209     ::Message::DefaultMessenger()->Send ("Error: EGL display is unavailable!", Message_Fail);
210     return Standard_False;
211   }
212
213   EGLint aConfigAttribs[] =
214   {
215     EGL_RED_SIZE,     8,
216     EGL_GREEN_SIZE,   8,
217     EGL_BLUE_SIZE,    8,
218     EGL_ALPHA_SIZE,   0,
219     EGL_DEPTH_SIZE,   24,
220     EGL_STENCIL_SIZE, 8,
221   #if defined(GL_ES_VERSION_2_0)
222     EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
223   #else
224     EGL_RENDERABLE_TYPE, EGL_OPENGL_BIT,
225   #endif
226     EGL_NONE
227   };
228
229   EGLint aNbConfigs = 0;
230   if (eglChooseConfig ((EGLDisplay )myEglDisplay, aConfigAttribs, &myEglConfig, 1, &aNbConfigs) != EGL_TRUE
231    || myEglConfig == NULL)
232   {
233     eglGetError();
234     aConfigAttribs[4 * 2 + 1] = 16; // try config with smaller depth buffer
235     if (eglChooseConfig ((EGLDisplay )myEglDisplay, aConfigAttribs, &myEglConfig, 1, &aNbConfigs) != EGL_TRUE
236      || myEglConfig == NULL)
237     {
238       ::Message::DefaultMessenger()->Send ("Error: EGL does not provide compatible configurations!", Message_Fail);
239       return Standard_False;
240     }
241   }
242
243 #if defined(GL_ES_VERSION_2_0)
244   EGLint anEglCtxAttribs[] =
245   {
246     EGL_CONTEXT_CLIENT_VERSION, 2,
247     EGL_NONE
248   };
249   if (eglBindAPI (EGL_OPENGL_ES_API) != EGL_TRUE)
250   {
251     ::Message::DefaultMessenger()->Send ("Error: EGL does not provide OpenGL ES client!", Message_Fail);
252     return Standard_False;
253   }
254 #else
255   EGLint* anEglCtxAttribs = NULL;
256   if (eglBindAPI (EGL_OPENGL_API) != EGL_TRUE)
257   {
258     ::Message::DefaultMessenger()->Send ("Error: EGL does not provide OpenGL client!", Message_Fail);
259     return Standard_False;
260   }
261 #endif
262
263   myEglContext = (Aspect_RenderingContext )eglCreateContext ((EGLDisplay )myEglDisplay, myEglConfig, EGL_NO_CONTEXT, anEglCtxAttribs);
264   if ((EGLContext )myEglContext == EGL_NO_CONTEXT)
265   {
266     ::Message::DefaultMessenger()->Send ("Error: EGL is unable to create OpenGL context!", Message_Fail);
267     return Standard_False;
268   }
269   if (eglMakeCurrent ((EGLDisplay )myEglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, (EGLContext )myEglContext) != EGL_TRUE)
270   {
271     ::Message::DefaultMessenger()->Send ("Error: EGL is unable bind OpenGL context!", Message_Fail);
272     return Standard_False;
273   }
274 #endif
275   myIsOwnContext = Standard_True;
276   return Standard_True;
277 }
278
279 #if defined(HAVE_EGL) || defined(__ANDROID__)
280 // =======================================================================
281 // function : InitEglContext
282 // purpose  :
283 // =======================================================================
284 Standard_Boolean OpenGl_GraphicDriver::InitEglContext (Aspect_Display          theEglDisplay,
285                                                        Aspect_RenderingContext theEglContext,
286                                                        void*                   theEglConfig)
287 {
288   ReleaseContext();
289 #if !defined(_WIN32) && !defined(__ANDROID__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX))
290   if (myDisplayConnection.IsNull())
291   {
292     return Standard_False;
293   }
294 #endif
295
296   if ((EGLDisplay )theEglDisplay == EGL_NO_DISPLAY
297    || (EGLContext )theEglContext == EGL_NO_CONTEXT
298    || theEglConfig == NULL)
299   {
300     return Standard_False;
301   }
302   myEglDisplay = theEglDisplay;
303   myEglContext = theEglContext;
304   myEglConfig  = theEglConfig;
305   return Standard_True;
306 }
307 #endif
308
309 // =======================================================================
310 // function : InquireLightLimit
311 // purpose  :
312 // =======================================================================
313 Standard_Integer OpenGl_GraphicDriver::InquireLightLimit()
314 {
315   return OpenGLMaxLights;
316 }
317
318 // =======================================================================
319 // function : InquireViewLimit
320 // purpose  :
321 // =======================================================================
322 Standard_Integer OpenGl_GraphicDriver::InquireViewLimit()
323 {
324   return 10000;
325 }
326
327 // =======================================================================
328 // function : InquirePlaneLimit
329 // purpose  :
330 // =======================================================================
331 Standard_Integer OpenGl_GraphicDriver::InquirePlaneLimit()
332 {
333   // NOTE the 2 first planes are reserved for ZClipping
334   const Handle(OpenGl_Context)& aCtx = GetSharedContext();
335   return aCtx.IsNull() ? 0 : Max (aCtx->MaxClipPlanes() - 2, 0);
336 }
337
338 // =======================================================================
339 // function : UserDrawCallback
340 // purpose  :
341 // =======================================================================
342 OpenGl_GraphicDriver::OpenGl_UserDrawCallback_t& OpenGl_GraphicDriver::UserDrawCallback()
343 {
344   return myUserDrawCallback;
345 }
346
347 // =======================================================================
348 // function : DefaultTextHeight
349 // purpose  :
350 // =======================================================================
351 Standard_ShortReal OpenGl_GraphicDriver::DefaultTextHeight() const
352 {
353   return 16.;
354 }
355
356 // =======================================================================
357 // function : EnableVBO
358 // purpose  :
359 // =======================================================================
360 void OpenGl_GraphicDriver::EnableVBO (const Standard_Boolean theToTurnOn)
361 {
362   myCaps->vboDisable = !theToTurnOn;
363 }
364
365 // =======================================================================
366 // function : GetSharedContext
367 // purpose  :
368 // =======================================================================
369 const Handle(OpenGl_Context)& OpenGl_GraphicDriver::GetSharedContext() const
370 {
371   if (myMapOfWS.IsEmpty())
372   {
373     return TheNullGlCtx;
374   }
375
376   NCollection_DataMap<Standard_Integer, Handle(OpenGl_Workspace)>::Iterator anIter (myMapOfWS);
377   return anIter.Value()->GetGlContext();
378 }
379
380 // =======================================================================
381 // function : MemoryInfo
382 // purpose  :
383 // =======================================================================
384 Standard_Boolean OpenGl_GraphicDriver::MemoryInfo (Standard_Size&           theFreeBytes,
385                                                    TCollection_AsciiString& theInfo) const
386 {
387   // this is extra work (for OpenGl_Context initialization)...
388   OpenGl_Context aGlCtx;
389   if (!aGlCtx.Init())
390   {
391     return Standard_False;
392   }
393   theFreeBytes = aGlCtx.AvailableMemory();
394   theInfo      = aGlCtx.MemoryInfo();
395   return !theInfo.IsEmpty();
396 }
397
398 // =======================================================================
399 // function : SetImmediateModeDrawToFront
400 // purpose  :
401 // =======================================================================
402 Standard_Boolean OpenGl_GraphicDriver::SetImmediateModeDrawToFront (const Graphic3d_CView& theCView,
403                                                                     const Standard_Boolean theDrawToFrontBuffer)
404 {
405   if (theCView.ViewId == -1)
406   {
407     return Standard_False;
408   }
409
410   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
411   if (aCView != NULL)
412   {
413     return aCView->WS->SetImmediateModeDrawToFront (theDrawToFrontBuffer);
414   }
415   return Standard_False;
416 }
417
418 // =======================================================================
419 // function : DisplayImmediateStructure
420 // purpose  :
421 // =======================================================================
422 void OpenGl_GraphicDriver::DisplayImmediateStructure (const Graphic3d_CView&      theCView,
423                                                       const Graphic3d_CStructure& theCStructure)
424 {
425   OpenGl_CView*     aCView     = (OpenGl_CView*     )theCView.ptrView;
426   OpenGl_Structure* aStructure = (OpenGl_Structure* )&theCStructure;
427   if (aCView == NULL)
428   {
429     return;
430   }
431
432   aCView->View->DisplayImmediateStructure (aStructure);
433 }
434
435 // =======================================================================
436 // function : EraseImmediateStructure
437 // purpose  :
438 // =======================================================================
439 void OpenGl_GraphicDriver::EraseImmediateStructure (const Graphic3d_CView&      theCView,
440                                                     const Graphic3d_CStructure& theCStructure)
441 {
442   OpenGl_CView*     aCView     = (OpenGl_CView*     )theCView.ptrView;
443   OpenGl_Structure* aStructure = (OpenGl_Structure* )&theCStructure;
444   if (aCView == NULL)
445   {
446     return;
447   }
448
449   aCView->View->EraseImmediateStructure (aStructure);
450 }
451
452
453 // =======================================================================
454 // function : Print
455 // purpose  :
456 // =======================================================================
457 Standard_Boolean OpenGl_GraphicDriver::Print (const Graphic3d_CView& theCView,
458                                               const Aspect_CLayer2d& theCUnderLayer,
459                                               const Aspect_CLayer2d& theCOverLayer,
460                                               const Aspect_Handle    thePrintDC,
461                                               const Standard_Boolean theToShowBackground,
462                                               const Standard_CString theFilename,
463                                               const Aspect_PrintAlgo thePrintAlgorithm,
464                                               const Standard_Real    theScaleFactor) const
465 {
466   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
467   if (aCView == NULL
468    || !myPrintContext.IsNull())
469   {
470     return Standard_False;
471   }
472
473   Standard_Boolean isPrinted = Standard_False;
474   myPrintContext = new OpenGl_PrinterContext();
475 #ifdef _WIN32
476   isPrinted = aCView->WS->Print (myPrintContext,
477                                  theCView,
478                                  theCUnderLayer,
479                                  theCOverLayer,
480                                  thePrintDC,
481                                  theToShowBackground,
482                                  theFilename,
483                                  thePrintAlgorithm,
484                                  theScaleFactor);
485 #else
486   Standard_NotImplemented::Raise ("OpenGl_GraphicDriver::Print is implemented only on Windows");
487 #endif
488   myPrintContext.Nullify();
489   return isPrinted;
490 }
491
492 // =======================================================================
493 // function : ZBufferTriedronSetup
494 // purpose  :
495 // =======================================================================
496 void OpenGl_GraphicDriver::ZBufferTriedronSetup (const Quantity_NameOfColor theXColor,
497                                                  const Quantity_NameOfColor theYColor,
498                                                  const Quantity_NameOfColor theZColor,
499                                                  const Standard_Real        theSizeRatio,
500                                                  const Standard_Real        theAxisDiametr,
501                                                  const Standard_Integer     theNbFacettes)
502 {
503   OpenGl_Trihedron::Setup (theXColor, theYColor, theZColor, theSizeRatio, theAxisDiametr, theNbFacettes);
504 }
505
506 // =======================================================================
507 // function : TriedronDisplay
508 // purpose  :
509 // =======================================================================
510 void OpenGl_GraphicDriver::TriedronDisplay (const Graphic3d_CView&              theCView,
511                                             const Aspect_TypeOfTriedronPosition thePosition,
512                                             const Quantity_NameOfColor          theColor,
513                                             const Standard_Real                 theScale,
514                                             const Standard_Boolean              theAsWireframe)
515 {
516   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
517   if (aCView != NULL)
518   {
519     aCView->View->TriedronDisplay (aCView->WS->GetGlContext(), thePosition, theColor, theScale, theAsWireframe);
520   }
521 }
522
523 // =======================================================================
524 // function : TriedronErase
525 // purpose  :
526 // =======================================================================
527 void OpenGl_GraphicDriver::TriedronErase (const Graphic3d_CView& theCView)
528 {
529   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
530   if (aCView != NULL)
531   {
532     aCView->View->TriedronErase (aCView->WS->GetGlContext());
533   }
534 }
535
536 // =======================================================================
537 // function : TriedronEcho
538 // purpose  :
539 // =======================================================================
540 void OpenGl_GraphicDriver::TriedronEcho (const Graphic3d_CView& ,
541                                          const Aspect_TypeOfTriedronEcho )
542 {
543   // do nothing
544 }
545
546 // =======================================================================
547 // function : Environment
548 // purpose  :
549 // =======================================================================
550 void OpenGl_GraphicDriver::Environment (const Graphic3d_CView& theCView)
551 {
552   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
553   if (aCView == NULL)
554   {
555     return;
556   }
557
558   aCView->View->SetTextureEnv    (aCView->WS->GetGlContext(), theCView.Context.TextureEnv);
559   aCView->View->SetSurfaceDetail ((Visual3d_TypeOfSurfaceDetail)theCView.Context.SurfaceDetail);
560 }
561
562 // =======================================================================
563 // function : BackgroundImage
564 // purpose  :
565 // =======================================================================
566 void OpenGl_GraphicDriver::BackgroundImage (const Standard_CString  theFileName,
567                                             const Graphic3d_CView&  theCView,
568                                             const Aspect_FillMethod theFillStyle)
569 {
570   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
571   if (aCView != NULL)
572   {
573     aCView->View->CreateBackgroundTexture (theFileName, theFillStyle);
574   }
575 }
576
577 // =======================================================================
578 // function : SetBgImageStyle
579 // purpose  :
580 // =======================================================================
581 void OpenGl_GraphicDriver::SetBgImageStyle (const Graphic3d_CView&  theCView,
582                                             const Aspect_FillMethod theFillStyle)
583 {
584   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
585   if (aCView != NULL)
586   {
587     aCView->View->SetBackgroundTextureStyle (theFillStyle);
588   }
589 }
590
591 // =======================================================================
592 // function : SetBgGradientStyle
593 // purpose  :
594 // =======================================================================
595 void OpenGl_GraphicDriver::SetBgGradientStyle (const Graphic3d_CView&          theCView,
596                                                const Aspect_GradientFillMethod theFillType)
597 {
598   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
599   if (aCView != NULL)
600   {
601     aCView->View->SetBackgroundGradientType (theFillType);
602   }
603 }
604
605 // =======================================================================
606 // function : GraduatedTrihedronDisplay
607 // purpose  :
608 // =======================================================================
609 void OpenGl_GraphicDriver::GraduatedTrihedronDisplay (const Graphic3d_CView&               theCView,
610                                                       const Graphic3d_CGraduatedTrihedron& theCubic)
611 {
612   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
613   if (aCView != NULL)
614   {
615     aCView->View->GraduatedTrihedronDisplay (aCView->WS->GetGlContext(), theCubic);
616   }
617 }
618
619 // =======================================================================
620 // function : GraduatedTrihedronErase
621 // purpose  :
622 // =======================================================================
623 void OpenGl_GraphicDriver::GraduatedTrihedronErase (const Graphic3d_CView& theCView)
624 {
625   const OpenGl_CView* aCView = (const OpenGl_CView* )theCView.ptrView;
626   if (aCView != NULL)
627   {
628     aCView->View->GraduatedTrihedronErase (aCView->WS->GetGlContext());
629   }
630 }
631
632 // =======================================================================
633 // function : GraduatedTrihedronMinMaxValues
634 // purpose  :
635 // =======================================================================
636 void OpenGl_GraphicDriver::GraduatedTrihedronMinMaxValues (const Standard_ShortReal theMinX,
637                                                            const Standard_ShortReal theMinY,
638                                                            const Standard_ShortReal theMinZ,
639                                                            const Standard_ShortReal theMaxX,
640                                                            const Standard_ShortReal theMaxY,
641                                                            const Standard_ShortReal theMaxZ)
642 {
643   OpenGl_GraduatedTrihedron::SetMinMax (theMinX, theMinY, theMinZ, theMaxX, theMaxY, theMaxZ);
644 }