0024057: Eliminate compiler warning C4100 in MSVC++ with warning level 4
[occt.git] / src / OpenGl / OpenGl_Display.cxx
1 // Created on: 2011-09-20
2 // Created by: Sergey ZERCHANINOV
3 // Copyright (c) 2011-2012 OPEN CASCADE SAS
4 //
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.
9 //
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.
12 //
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.
19
20
21 #include <OpenGl_GlCore11.hxx>
22
23 #include <OpenGl_Display.hxx>
24
25 #include <OSD_Environment.hxx>
26 #include <TCollection_AsciiString.hxx>
27 #include <Aspect_GraphicDeviceDefinitionError.hxx>
28
29 #include <OpenGl_Light.hxx>
30
31 #if (!defined(_WIN32) && !defined(__WIN32__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)))
32   #include <X11/Xlib.h> // XOpenDisplay()
33 #endif
34
35 IMPLEMENT_STANDARD_HANDLE(OpenGl_Display,MMgt_TShared)
36 IMPLEMENT_STANDARD_RTTIEXT(OpenGl_Display,MMgt_TShared)
37
38 Handle(OpenGl_Display) openglDisplay;
39
40 namespace
41 {
42   #if (defined(_WIN32) || defined(__WIN32__)) || (defined(__APPLE__) && !defined(MACOSX_USE_GLX))
43     static char* TheDummyDisplay = "DISPLAY";
44   #endif
45
46   static const OpenGl_Facilities myDefaultFacilities = { 1, 1, 1, 1, OpenGLMaxLights, 10000 };
47 };
48
49 /*----------------------------------------------------------------------*/
50 #if (defined(_WIN32) || defined(__WIN32__)) || (defined(__APPLE__) && !defined(MACOSX_USE_GLX))
51 OpenGl_Display::OpenGl_Display (const Handle(Aspect_DisplayConnection)& )
52 #else
53 OpenGl_Display::OpenGl_Display (const Handle(Aspect_DisplayConnection)& theDisplayConnection)
54 #endif
55 : myDisplay(NULL),
56   myFacilities(myDefaultFacilities),
57   myDBuffer(Standard_True),
58   myDither(Standard_True),
59   myBackDither(Standard_False),
60   myWalkthrough(Standard_False),
61   mySymPerspective(Standard_False),
62   myOffsetFactor(1.F),
63   myOffsetUnits(0.F),
64   myAntiAliasingMode(3),
65   myLinestyleBase(0),
66   myPatternBase(0),
67   myMarkerBase(0)
68 {
69 #if (defined(_WIN32) || defined(__WIN32__)) || (defined(__APPLE__) && !defined(MACOSX_USE_GLX))
70   myDisplay = TheDummyDisplay;
71 #else
72   myDisplay = theDisplayConnection->GetDisplay();
73 #endif
74
75   Init();
76 }
77
78 /*----------------------------------------------------------------------*/
79
80 OpenGl_Display::~OpenGl_Display ()
81 {
82   // Delete line styles
83   if (myLinestyleBase)
84   {
85     glDeleteLists((GLuint)myLinestyleBase,5);
86     myLinestyleBase = 0;
87   }
88   // Delete surface patterns
89   if (myPatternBase)
90   {
91     glDeleteLists((GLuint)myPatternBase,TEL_HS_USER_DEF_START);
92     myPatternBase = 0;
93   }
94   // Delete markers
95   if (myMarkerBase)
96   {
97     glDeleteLists((GLuint)myMarkerBase,60);
98     myMarkerBase = 0;
99   }
100   // Delete user markers
101   OpenGl_MapOfUserMarker::Iterator itm(myMapOfUM);
102   for (; itm.More(); itm.Next())
103   {
104     const OPENGL_MARKER_DATA &aData = itm.Value();
105     if (aData.Array)
106     {
107       delete[] aData.Array;
108     }
109     else if (aData.ListId != 0)
110     {
111       glDeleteLists ( aData.ListId, 1 );
112     }
113   }
114   myDisplay = NULL;
115 }
116
117 /*----------------------------------------------------------------------*/
118
119 Handle(OpenGl_Window) OpenGl_Display::GetWindow (const Aspect_Drawable AParent) const
120 {
121   Handle(OpenGl_Window) aWindow;
122   if ( myMapOfWindows.IsBound( AParent ) )
123   {
124     aWindow = myMapOfWindows.Find( AParent );
125   }
126   return aWindow;
127 }
128
129 /*----------------------------------------------------------------------*/
130
131 void OpenGl_Display::SetWindow (const Aspect_Drawable AParent, const Handle(OpenGl_Window) &AWindow)
132 {
133   if ( !myMapOfWindows.IsBound( AParent ) )
134   {
135     myMapOfWindows.Bind( AParent, AWindow );
136   }
137 }
138
139 /*----------------------------------------------------------------------*/
140
141 //GenerateMarkerBitmap
142 void OpenGl_Display::AddUserMarker (const Standard_Integer AIndex,
143                                    const Standard_Integer AMarkWidth,
144                                    const Standard_Integer AMarkHeight,
145                                    const Handle(TColStd_HArray1OfByte)& ATexture)
146 {
147   if (!myMapOfUM.IsBound(AIndex))
148   {
149     const OPENGL_MARKER_DATA anEmptyData = { 0, 0, 0, NULL };
150     myMapOfUM.Bind(AIndex,anEmptyData);
151   }
152
153   OPENGL_MARKER_DATA &aData = myMapOfUM.ChangeFind(AIndex);
154
155   if (aData.Array)
156   {
157     delete[] aData.Array;
158     aData.Array = NULL;
159   }
160
161   unsigned char *anArray = new unsigned char[ATexture->Length()];
162
163   const int aByteWidth = AMarkWidth / 8;
164   int i, anIndex = ATexture->Upper() - ATexture->Lower() - aByteWidth + 1;
165   for ( ; anIndex >= 0; anIndex -= aByteWidth )
166     for ( i = 0; i < aByteWidth; i++ )
167       anArray[ATexture->Upper() - ATexture->Lower() - aByteWidth + 1 - anIndex + i ] = ATexture->Value( anIndex + i + 1 );
168
169   aData.Width = AMarkWidth;
170   aData.Height = AMarkHeight;
171   aData.Array = anArray;
172 }
173
174 /*----------------------------------------------------------------------*/
175
176 void OpenGl_Display::UpdateUserMarkers ()
177 {
178   OpenGl_MapOfUserMarker::Iterator itm(myMapOfUM);
179   for (; itm.More(); itm.Next())
180   {
181     OPENGL_MARKER_DATA &aData = itm.ChangeValue();
182     if (aData.Array)
183     {
184       if (aData.ListId == 0)
185         aData.ListId = glGenLists(1);
186
187       glNewList( (GLuint)aData.ListId, GL_COMPILE );
188
189       GLint w = ( GLsizei ) aData.Width;
190       GLint h = ( GLsizei ) aData.Height;
191       glBitmap( w, h,
192                 0.5F * ( float )aData.Width, 0.5F * ( float )aData.Height,
193                 ( float )30.0, ( float )30.0,
194                 ( GLubyte* )aData.Array );
195
196       glEndList();
197
198       delete[] aData.Array;
199       aData.Array = NULL;
200     }
201   }
202 }
203
204 /*----------------------------------------------------------------------*/
205
206 Standard_Integer OpenGl_Display::GetUserMarkerListIndex (const Standard_Integer AIndex) const
207 {
208   if (myMapOfUM.IsBound(AIndex))
209   {
210     const OPENGL_MARKER_DATA &aData = myMapOfUM.Find(AIndex);
211     if (!aData.Array)
212       return aData.ListId;
213   }
214   return -1;
215 }
216
217 /*----------------------------------------------------------------------*/
218
219 void OpenGl_Display::Init()
220 {
221   if (myDisplay != NULL)
222   {
223   #if (!defined(_WIN32) && !defined(__WIN32__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)))
224     XSynchronize ((Display* )myDisplay, (getenv("CALL_SYNCHRO_X") != NULL) ? 1 : 0);
225
226     if (getenv("CSF_GraphicSync") != NULL)
227       XSynchronize ((Display* )myDisplay, 1);
228
229     // does the server know about OpenGL & GLX?
230     int aDummy;
231     if (!XQueryExtension ((Display* )myDisplay, "GLX", &aDummy, &aDummy, &aDummy))
232     {
233     #ifdef DEBUG
234       std::cerr << "This system doesn't appear to support OpenGL\n";
235     #endif
236     }
237   #endif
238   }
239   else
240   {
241     TCollection_AsciiString msg("OpenGl_Display::Init");
242   #if (!defined(_WIN32) && !defined(__WIN32__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)))
243     msg += " : Cannot connect to X server ";
244     msg += XDisplayName ((char*) NULL);
245   #endif
246     Aspect_GraphicDeviceDefinitionError::Raise(msg.ToCString());
247   }
248
249   if (getenv("CALL_OPENGL_NO_DBF") != NULL)
250     myDBuffer = Standard_False;
251
252   if (getenv("CALL_OPENGL_NO_DITHER") != NULL)
253     myDither = Standard_False;
254
255   if (getenv("CALL_OPENGL_NO_BACKDITHER") != NULL)
256     myBackDither = Standard_False;
257
258   if (getenv("CSF_WALKTHROUGH") != NULL)
259     myWalkthrough = Standard_True;
260
261   /* OCC18942: Test if symmetric perspective projection should be turned on */
262   if (getenv("CSF_SYM_PERSPECTIVE") != NULL)
263     mySymPerspective = Standard_True;
264
265   const char* pvalue = getenv("CALL_OPENGL_POLYGON_OFFSET");
266   if (pvalue)
267   {
268     float v1, v2;
269     const int n = sscanf(pvalue, "%f %f", &v1, &v2);
270     if (n > 0) myOffsetFactor = v1;
271     if (n > 1) myOffsetUnits  = v2;
272   }
273
274   pvalue = getenv("CALL_OPENGL_ANTIALIASING_MODE");
275   if (pvalue)
276   {
277     int v;
278     if ( sscanf(pvalue,"%d",&v) > 0 ) myAntiAliasingMode = v;
279   }
280 }