0022922: Clean up warnings on uninitialized / unused variables
[occt.git] / src / OpenGl / OpenGl_QuadrangleStrip.cxx
1 // File:      OpenGl_QuadrangleStrip.cxx
2 // Created:   13 July 2011
3 // Author:    Sergey ZERCHANINOV
4 // Copyright: OPEN CASCADE 2011
5
6 #include <OpenGl_tgl_all.hxx>
7 #include <GL/gl.h>
8
9 #include <OpenGl_QuadrangleStrip.hxx>
10
11 #include <OpenGl_telem_util.hxx>
12 #include <OpenGl_TextureBox.hxx>
13
14 #include <OpenGl_AspectFace.hxx>
15 #include <OpenGl_Structure.hxx>
16
17 /*----------------------------------------------------------------------*/
18
19 #define OPENGL_RAND() ( ( unsigned )( s_Rand = s_Rand * 214013L + 2531011L ) )
20
21 /*----------------------------------------------------------------------*/
22
23 extern void draw_degenerates_as_points ( PDS_INTERNAL, tel_point, Tint, const Handle(OpenGl_Workspace) & );
24 extern void draw_degenerates_as_bboxs  ( PDS_INTERNAL, tel_point, Tint, const Handle(OpenGl_Workspace) & );
25 extern void set_drawable_items         ( GLboolean*, int, const float            );
26
27 /*----------------------------------------------------------------------*/
28
29 void OpenGl_QuadrangleStrip::draw_qstrip (const Tint front_lighting_model,
30                                          const Aspect_InteriorStyle interior_style,
31                                          const TEL_COLOUR *edge_colour,
32                                          const Handle(OpenGl_Workspace) &AWorkspace) const
33 {
34   Tint              i, m, newList = 0;
35   Tint              nf, nv, nr, nc;
36   Tint              lighting_model;
37
38   tel_colour pfc = myData.fcolours;
39   tel_point pv  = myData.vertices;
40   tel_colour pvc = myData.vcolours;
41   tel_point pvn = myData.vnormals;
42   tel_texture_coord pvt = myData.vtexturecoord;
43
44   if ( AWorkspace->NamedStatus & OPENGL_NS_HIGHLIGHT )
45   {
46     pvc = 0;
47     pfc = 0;
48   }
49
50   if ( AWorkspace->DegenerateModel < 2 && interior_style != Aspect_IS_EMPTY )
51   {
52     if ( front_lighting_model )
53       glEnable(GL_LIGHTING);
54     else
55       glDisable(GL_LIGHTING);
56
57     lighting_model = front_lighting_model;
58     nr             = myData.num_rows;
59     nc             = myData.num_columns;
60     nf             = nr * nc;
61     nv             = ( nr + 1 ) * ( nc + 1 );
62     if ( (AWorkspace->NamedStatus & OPENGL_NS_ANIMATION) == 0 )
63       goto doDraw; /* Disable object display list out of animation */
64     /*  window's context and bitmap's one   */
65     if ( myDS->model != front_lighting_model || !myDS->list || myDS->model == -1 ||
66         ( AWorkspace->DegenerateModel && myDS->skipRatio != AWorkspace->SkipRatio ) )
67     {
68         myDS->skipRatio = AWorkspace->SkipRatio;
69         myDS->model     = front_lighting_model;
70         myDS->degMode   = AWorkspace->DegenerateModel;
71
72         if ( AWorkspace->SkipRatio == 0.f ) {
73
74           if ( !myDS->list ) myDS->list = glGenLists ( 1 );
75
76           glNewList ( myDS->list, GL_COMPILE_AND_EXECUTE );
77           newList = 1;
78 doDraw:
79           if ( lighting_model )
80           {
81             if ( pvt && (AWorkspace->NamedStatus & OPENGL_NS_FORBIDSETTEX) == 0 )
82             {
83               for ( m = 0; m < nr; ++m )
84               {
85                 glBegin ( GL_QUAD_STRIP );
86                 glNormal3fv   ( pvn[         m * ( nc + 1 ) ].xyz );
87                 glTexCoord2fv ( pvt[         m * ( nc + 1 ) ].xy  );
88                 glVertex3fv   ( pv[          m * ( nc + 1 ) ].xyz );
89                 glNormal3fv   ( pvn[ ( m + 1 ) * ( nc + 1 ) ].xyz );
90                 glTexCoord2fv ( pvt[ ( m + 1 ) * ( nc + 1 ) ].xy  );
91                 glVertex3fv   ( pv[  ( m + 1 ) * ( nc + 1 ) ].xyz );
92                 for ( i = 1; i < nc + 1; ++i )
93                 {
94                   glNormal3fv   ( pvn[         i + m * ( nc + 1 ) ].xyz );
95                   glTexCoord2fv ( pvt[         i + m * ( nc + 1 ) ].xy  );
96                   glVertex3fv   ( pv[          i + m * ( nc + 1 ) ].xyz );
97                   glNormal3fv   ( pvn[ i + ( m + 1 ) * ( nc + 1 ) ].xyz );
98                   glTexCoord2fv ( pvt[ i + ( m + 1 ) * ( nc + 1 ) ].xy  );
99                   glVertex3fv   ( pv[  i + ( m + 1 ) * ( nc + 1 ) ].xyz );
100                 }
101                 glEnd ();
102               }
103             }
104             else
105             {
106               for ( m = 0; m < nr; ++m )
107               {
108                 glBegin ( GL_QUAD_STRIP );
109                 glNormal3fv ( pvn[         m * ( nc + 1 ) ].xyz );
110                 glVertex3fv ( pv[          m * ( nc + 1 ) ].xyz );
111                 glNormal3fv ( pvn[ ( m + 1 ) * ( nc + 1 ) ].xyz );
112                 glVertex3fv ( pv[  ( m + 1 ) * ( nc + 1 ) ].xyz );
113                 for ( i = 1; i < nc + 1; ++i )
114                 {
115                   glNormal3fv ( pvn[         i + m * ( nc + 1 ) ].xyz );
116                   glVertex3fv ( pv[          i + m * ( nc + 1 ) ].xyz );
117                   glNormal3fv ( pvn[ i + ( m + 1 ) * ( nc + 1 ) ].xyz );
118                   glVertex3fv ( pv[  i + ( m + 1 ) * ( nc + 1 ) ].xyz );
119                 }
120                 glEnd ();
121               }
122             }
123           }
124           else
125           {
126             if ( pvc )
127             {
128               for ( m = 0; m < nr; ++m )
129               {
130                 glBegin ( GL_QUAD_STRIP );
131                 glColor3fv  ( pvc[         m * ( nc + 1 ) ].rgb );
132                 glVertex3fv ( pv[          m * ( nc + 1 ) ].xyz );
133                 glColor3fv  ( pvc[ ( m + 1 ) * ( nc + 1 ) ].rgb );
134                 glVertex3fv ( pv[  ( m + 1 ) * ( nc + 1 ) ].xyz );
135                 for ( i = 1; i < nc + 1; ++i )
136                 {
137                   glColor3fv  ( pvc[         i + m * ( nc + 1 ) ].rgb );
138                   glVertex3fv ( pv[          i + m * ( nc + 1 ) ].xyz );
139                   glColor3fv  ( pvc[ i + ( m + 1 ) * ( nc + 1 ) ].rgb );
140                   glVertex3fv ( pv[  i + ( m + 1 ) * ( nc + 1 ) ].xyz );
141                 }
142                 glEnd ();
143               }
144             }
145             else if ( pfc )
146             {
147               glColor3fv ( pfc[ 0 ].rgb );
148               for ( m = 0; m < nr; ++m )
149               {
150                 glBegin ( GL_QUAD_STRIP );
151                 glColor3fv  ( pfc[                m * nc ].rgb );
152                 glVertex3fv ( pv[         m * ( nc + 1 ) ].xyz );
153                 glVertex3fv ( pv[ ( m + 1 ) * ( nc + 1 ) ].xyz );
154                 for ( i = 1; i < nc + 1; ++i )
155                 {
156                   glVertex3fv ( pv[         i + m * ( nc + 1 ) ].xyz );
157                   glColor3fv  ( pfc[            i - 1 + m * nc ].rgb );
158                   glVertex3fv ( pv[ i + ( m + 1 ) * ( nc + 1 ) ].xyz );
159                 }
160                 glEnd ();
161               }
162             }
163             else
164             {
165               for ( m = 0; m < nr; ++m )
166               {
167                 glBegin ( GL_QUAD_STRIP );
168                 glVertex3fv ( pv[         m * ( nc + 1 ) ].xyz );
169                 glVertex3fv ( pv[ ( m + 1 ) * ( nc + 1 ) ].xyz );
170                 for ( i = 1; i < nc + 1; ++i )
171                 {
172                   glVertex3fv( pv[         i + m * ( nc + 1 ) ].xyz );
173                   glVertex3fv( pv[ i + ( m + 1 ) * ( nc + 1 ) ].xyz );
174                 }
175                 glEnd ();
176               }
177             }
178           }
179         }
180         else if ( AWorkspace->SkipRatio < 1.f )
181         {
182           set_drawable_items ( myDS->bDraw, nr, AWorkspace->SkipRatio );
183
184           if ( !myDS->dlist ) myDS->dlist = glGenLists ( 1 );
185
186           glNewList ( myDS->dlist, GL_COMPILE_AND_EXECUTE );
187           newList = 1;
188
189           if ( lighting_model )
190           {
191             if ( pvt && (AWorkspace->NamedStatus & OPENGL_NS_FORBIDSETTEX) == 0 )
192             {
193               for ( m = 0; m < nr; ++m )
194               {
195                 if ( myDS->bDraw[ m ] )
196                 {
197                   glBegin ( GL_QUADS );
198                   glNormal3fv   ( pvn[         m * ( nc + 1 ) ].xyz );
199                   glTexCoord2fv ( pvt[         m * ( nc + 1 ) ].xy  );
200                   glVertex3fv   ( pv[          m * ( nc + 1 ) ].xyz );
201                   glNormal3fv   ( pvn[ ( m + 1 ) * ( nc + 1 ) ].xyz );
202                   glTexCoord2fv ( pvt[ ( m + 1 ) * ( nc + 1 ) ].xy  );
203                   glVertex3fv   ( pv[  ( m + 1 ) * ( nc + 1 ) ].xyz );
204                   for ( i = 1; i < nc + 1; ++i )
205                   {
206                     glNormal3fv   ( pvn[ i + ( m + 1 ) * ( nc + 1 ) ].xyz );
207                     glTexCoord2fv ( pvt[ i + ( m + 1 ) * ( nc + 1 ) ].xy  );
208                     glVertex3fv   ( pv[  i + ( m + 1 ) * ( nc + 1 ) ].xyz );
209                     glNormal3fv   ( pvn[         i + m * ( nc + 1 ) ].xyz );
210                     glTexCoord2fv ( pvt[         i + m * ( nc + 1 ) ].xy  );
211                     glVertex3fv   ( pv[          i + m * ( nc + 1 ) ].xyz );
212                   }
213                   glEnd ();
214                 }
215               }
216             }
217             else
218             {
219               for ( m = 0; m < nr; ++m )
220                           {
221                 if ( myDS->bDraw[ m ] )
222                 {
223                   glBegin ( GL_QUADS );
224                   glNormal3fv ( pvn[         m * ( nc + 1 ) ].xyz );
225                   glVertex3fv ( pv[          m * ( nc + 1 ) ].xyz );
226                   glNormal3fv ( pvn[ ( m + 1 ) * ( nc + 1 ) ].xyz );
227                   glVertex3fv ( pv[  ( m + 1 ) * ( nc + 1 ) ].xyz );
228                   for ( i = 1; i < nc + 1; ++i )
229                   {
230                     glNormal3fv ( pvn[ i + ( m + 1 ) * ( nc + 1 ) ].xyz );
231                     glVertex3fv ( pv[  i + ( m + 1 ) * ( nc + 1 ) ].xyz );
232                     glNormal3fv ( pvn[         i + m * ( nc + 1 ) ].xyz );
233                     glVertex3fv ( pv[          i + m * ( nc + 1 ) ].xyz );
234                   }
235                   glEnd ();
236                 }
237               }
238             }
239           }
240           else
241           {
242             if ( pvc )
243             {
244               for ( m = 0; m < nr; ++m )
245               {
246                 if ( myDS->bDraw[ m ] )
247                 {
248                   glBegin ( GL_QUAD_STRIP );
249                   glColor3fv  ( pvc[         m * ( nc + 1 ) ].rgb );
250                   glVertex3fv ( pv[          m * ( nc + 1 ) ].xyz );
251                   glColor3fv  ( pvc[ ( m + 1 ) * ( nc + 1 ) ].rgb );
252                   glVertex3fv ( pv[  ( m + 1 ) * ( nc + 1 ) ].xyz );
253                   for ( i = 1; i < nc + 1; ++i )
254                   {
255                     glColor3fv  ( pvc[ i + ( m + 1 ) * ( nc + 1 ) ].rgb );
256                     glVertex3fv ( pv[  i + ( m + 1 ) * ( nc + 1 ) ].xyz );
257                     glColor3fv  ( pvc[         i + m * ( nc + 1 ) ].rgb );
258                     glVertex3fv ( pv[          i + m * ( nc + 1 ) ].xyz );
259                   }
260                   glEnd ();
261                 }
262               }
263             }
264             else if ( pfc )
265             {
266               glColor3fv ( pfc[ 0 ].rgb );
267               for ( m = 0; m < nr; ++m )
268               {
269                 if ( myDS->bDraw[ m ] )
270                 {
271                   glBegin ( GL_QUADS );
272                   glColor3fv  ( pfc[                m * nc ].rgb );
273                   glVertex3fv ( pv[         m * ( nc + 1 ) ].xyz );
274                   glVertex3fv ( pv[ ( m + 1 ) * ( nc + 1 ) ].xyz );
275                   for ( i = 1; i < nc + 1; ++i )
276                   {
277                     glColor3fv  ( pfc[            i - 1 + m * nc ].rgb );
278                     glVertex3fv ( pv[ i + ( m + 1 ) * ( nc + 1 ) ].xyz );
279                     glVertex3fv ( pv[         i + m * ( nc + 1 ) ].xyz );
280                   }
281                   glEnd ();
282                 }
283               }
284             }
285             else
286             {
287               for ( m = 0; m < nr; ++m )
288               {
289                 if ( myDS->bDraw[ m ] )
290                 {
291                   glBegin ( GL_QUADS );
292                   glVertex3fv ( pv[         m * ( nc + 1 ) ].xyz );
293                   glVertex3fv ( pv[ ( m + 1 ) * ( nc + 1 ) ].xyz );
294                   for ( i = 1; i < nc + 1; ++i )
295                   {
296                     glVertex3fv( pv[ i + ( m + 1 ) * ( nc + 1 ) ].xyz );
297                     glVertex3fv( pv[         i + m * ( nc + 1 ) ].xyz );
298                   }
299                   glEnd ();
300                 }
301               }
302             }
303           }
304         }
305         else
306         {
307           if ( !myDS->dlist ) myDS->dlist = glGenLists ( 1 );
308
309           glNewList ( myDS->dlist, GL_COMPILE_AND_EXECUTE );
310           newList = 1;
311
312         }  /* end else */
313         if ( newList ) glEndList ();
314
315         if ( AWorkspace->DegenerateModel ) return;
316
317       } else {
318
319         glCallList ( AWorkspace->SkipRatio <= 0.f ? myDS->list : myDS->dlist );
320
321         if ( AWorkspace->DegenerateModel ) return;
322
323       }  /* end else */
324   }
325
326   i = 0;
327
328   /* OCC11904 -- Temporarily disable environment mapping */
329   glPushAttrib(GL_ENABLE_BIT);
330   glDisable(GL_TEXTURE_1D);
331   glDisable(GL_TEXTURE_2D);
332
333   switch ( AWorkspace->DegenerateModel )
334   {
335     default:
336       break;
337
338     case 2:  /* XXX_TDM_WIREFRAME */
339       i = 1;
340       break;
341
342     case 3:  /* XXX_TDM_MARKER */
343       draw_degenerates_as_points ( myDS, myData.vertices, ( myData.num_rows + 1 ) * ( myData.num_columns + 1 ), AWorkspace );
344       glPopAttrib();
345       return;
346
347     case 4:  /* XXX_TDM_BBOX */
348       draw_degenerates_as_bboxs ( myDS, myData.vertices, ( myData.num_rows + 1 ) * ( myData.num_columns + 1 ), AWorkspace );
349       glPopAttrib();
350       return;
351   }  /* end switch */
352
353   draw_edges ( edge_colour, interior_style, i, AWorkspace );
354
355   glPopAttrib();
356 }
357
358 /*----------------------------------------------------------------------*/
359
360 void OpenGl_QuadrangleStrip::draw_edges (const TEL_COLOUR *edge_colour, const Aspect_InteriorStyle interior_style,
361                                         Tint forceDraw, const Handle(OpenGl_Workspace) &AWorkspace) const
362 {
363   const OpenGl_AspectFace *aspect_face = AWorkspace->AspectFace( Standard_True );
364
365   if ( interior_style != Aspect_IS_HIDDENLINE && !forceDraw && aspect_face->Context().Edge == TOff )
366     return;
367
368   glDisable(GL_LIGHTING);
369   const GLboolean texture_on = IsTextureEnabled();
370   if ( texture_on ) DisableTexture();
371
372   // Setup line aspect
373   const OpenGl_AspectLine *aspect_line_old = AWorkspace->SetAspectLine( aspect_face->AspectEdge() );
374   AWorkspace->AspectLine( Standard_True );
375
376   Tint nc = myData.num_columns;
377   Tint nf = myData.num_rows * myData.num_columns;
378
379   Tint newList = 0;
380
381   if ( !forceDraw )
382     draw_line_strip ( edge_colour, nf, nc );
383   else
384   {
385     if ( (AWorkspace->NamedStatus & OPENGL_NS_ANIMATION) == 0 )
386       goto doDraw; /* Disable object display list out of animation */
387     if ( myDS->degMode != 2 || myDS->skipRatio != AWorkspace->SkipRatio || !myDS->dlist ) {
388
389       if ( !myDS->dlist ) myDS->dlist = glGenLists ( 1 );
390
391       myDS->degMode   = 2;
392       myDS->skipRatio = AWorkspace->SkipRatio;
393       glNewList ( myDS->dlist, GL_COMPILE_AND_EXECUTE );
394       newList = 1;
395 doDraw:
396       glPushAttrib ( GL_DEPTH_BUFFER_BIT );
397       glDisable ( GL_DEPTH_TEST );
398
399       if ( AWorkspace->SkipRatio <= 0.f )
400
401         draw_line_strip ( edge_colour, nf, nc );
402
403       else if ( AWorkspace->SkipRatio < 1.f ) {
404
405         int i, m1, m2, n1, n2, n3, n4;
406
407         set_drawable_items ( myDS->bDraw, nf, AWorkspace->SkipRatio );
408
409         glColor3fv ( edge_colour -> rgb );
410
411         for ( i = 0; i < nf; ++i )
412
413           if ( myDS->bDraw[ i ] ) {
414
415             glBegin ( GL_LINE_STRIP );
416             m1 = i / nc;
417             m2 = i % nc;
418             n1 = m1 * ( nc + 1 ) + m2;
419             n2 = n1 + nc + 1;
420             n3 = n2 + 1;
421             n4 = n1 + 1;
422
423             glVertex3fv ( myData.vertices[ n1 ].xyz );
424             glVertex3fv ( myData.vertices[ n2 ].xyz );
425             glVertex3fv ( myData.vertices[ n3 ].xyz );
426             glVertex3fv ( myData.vertices[ n4 ].xyz );
427             glVertex3fv ( myData.vertices[ n1 ].xyz );
428             glEnd();
429
430           }  /* end if */
431
432       }  /* end if */
433
434       glPopAttrib ();
435       if ( newList ) glEndList ();
436
437     } else glCallList ( myDS->dlist );
438
439   }  /* end else */
440
441   // Restore line context
442   AWorkspace->SetAspectLine( aspect_line_old );
443
444   if ( texture_on ) EnableTexture ();
445 }
446
447 void OpenGl_QuadrangleStrip::draw_line_strip (const TEL_COLOUR *c, Tint nf, Tint nc) const
448 {
449   int i, m1, m2, n1, n2, n3, n4;
450
451   glColor3fv ( c->rgb );
452
453   for ( i = 0; i < nf; ++i )
454   {
455     glBegin ( GL_LINE_STRIP );
456     m1 = i / nc;
457     m2 = i % nc;
458     n1 = m1 * ( nc + 1 ) + m2;
459     n2 = n1 + nc + 1;
460     n3 = n2 + 1;
461     n4 = n1 + 1;
462
463     glVertex3fv ( myData.vertices[ n1 ].xyz );
464     glVertex3fv ( myData.vertices[ n2 ].xyz );
465     glVertex3fv ( myData.vertices[ n3 ].xyz );
466     glVertex3fv ( myData.vertices[ n4 ].xyz );
467     glVertex3fv ( myData.vertices[ n1 ].xyz );
468     glEnd();
469   }
470 }
471
472 /*----------------------------------------------------------------------*/
473
474 OpenGl_QuadrangleStrip::OpenGl_QuadrangleStrip (const Graphic3d_Array2OfVertex& AListVertex)
475 {
476   const Standard_Integer nbr = AListVertex.RowLength ();
477   const Standard_Integer nbc = AListVertex.ColLength ();
478   const Standard_Integer nbf = nbr*nbc;
479
480   // Dynamic allocation
481   TEL_POINT *points = new TEL_POINT[nbf];
482
483   const Standard_Integer LowerRow = AListVertex.LowerRow ();
484   const Standard_Integer UpperRow = AListVertex.UpperRow ();
485   const Standard_Integer LowerCol = AListVertex.LowerCol ();
486   const Standard_Integer UpperCol = AListVertex.UpperCol ();
487
488   Standard_Integer i, j, k = 0;
489   Standard_Real X, Y, Z;
490   for (i=LowerRow; i<=UpperRow; i++)
491     for (j=LowerCol; j<=UpperCol; j++)
492     {
493       AListVertex (i, j).Coord (X, Y, Z);
494       points[k].xyz[0] = float (X);
495       points[k].xyz[1] = float (Y);
496       points[k].xyz[2] = float (Z);
497       k++;
498     }
499
500   Init(nbr,nbc,points,NULL,NULL,NULL,NULL,NULL,TEL_SHAPE_UNKNOWN);
501 }
502
503 /*----------------------------------------------------------------------*/
504
505 OpenGl_QuadrangleStrip::OpenGl_QuadrangleStrip (const Graphic3d_Array2OfVertexN& AListVertex)
506 {
507   const Standard_Integer nbr = AListVertex.RowLength ();
508   const Standard_Integer nbc = AListVertex.ColLength ();
509   const Standard_Integer nbf = nbr*nbc;
510
511   // Dynamic allocation
512   TEL_POINT *points = new TEL_POINT[nbf];
513   TEL_POINT *normals = new TEL_POINT[nbf];
514
515   const Standard_Integer LowerRow = AListVertex.LowerRow ();
516   const Standard_Integer UpperRow = AListVertex.UpperRow ();
517   const Standard_Integer LowerCol = AListVertex.LowerCol ();
518   const Standard_Integer UpperCol = AListVertex.UpperCol ();
519
520   Standard_Integer i, j, k = 0;
521   Standard_Real X, Y, Z;
522   for (i=LowerRow; i<=UpperRow; i++)
523     for (j=LowerCol; j<=UpperCol; j++)
524     {
525       AListVertex (i, j).Coord (X, Y, Z);
526       points[k].xyz[0] = float (X);
527       points[k].xyz[1] = float (Y);
528       points[k].xyz[2] = float (Z);
529       AListVertex (i, j).Normal (X, Y, Z);
530       normals[k].xyz[0] = float (X);
531       normals[k].xyz[1] = float (Y);
532       normals[k].xyz[2] = float (Z);
533       k++;
534     }
535
536   Init(nbr,nbc,points,normals,NULL,NULL,NULL,NULL,TEL_SHAPE_UNKNOWN);
537 }
538
539 /*----------------------------------------------------------------------*/
540
541 OpenGl_QuadrangleStrip::OpenGl_QuadrangleStrip (const Graphic3d_Array2OfVertexNT& AListVertex)
542 {
543   const Standard_Integer nbr = AListVertex.RowLength ();
544   const Standard_Integer nbc = AListVertex.ColLength ();
545   const Standard_Integer nbf = nbr*nbc;
546
547   // Dynamic allocation
548   TEL_POINT *points = new TEL_POINT[nbf];
549   TEL_POINT *normals = new TEL_POINT[nbf];
550   TEL_TEXTURE_COORD *tcoords = new TEL_TEXTURE_COORD[nbf];
551
552   const Standard_Integer LowerRow = AListVertex.LowerRow ();
553   const Standard_Integer UpperRow = AListVertex.UpperRow ();
554   const Standard_Integer LowerCol = AListVertex.LowerCol ();
555   const Standard_Integer UpperCol = AListVertex.UpperCol ();
556
557   Standard_Integer i, j, k = 0;
558   Standard_Real X, Y, Z;
559   for (i=LowerRow; i<=UpperRow; i++)
560     for (j=LowerCol; j<=UpperCol; j++)
561     {
562       AListVertex (i, j).Coord (X, Y, Z);
563       points[k].xyz[0] = float (X);
564       points[k].xyz[1] = float (Y);
565       points[k].xyz[2] = float (Z);
566       AListVertex (i, j).Normal (X, Y, Z);
567       normals[k].xyz[0] = float (X);
568       normals[k].xyz[1] = float (Y);
569       normals[k].xyz[2] = float (Z);
570       AListVertex (i, j).TextureCoordinate(X, Y);
571       tcoords[k].xy[0] = float(X);
572       tcoords[k].xy[1] = float(Y);
573       k++;
574     }
575
576   Init(nbr,nbc,points,normals,NULL,tcoords,NULL,NULL,TEL_SHAPE_UNKNOWN);
577 }
578
579 /*----------------------------------------------------------------------*/
580
581 void OpenGl_QuadrangleStrip::Init (const Tint ANbRows, const Tint ANbCols, tel_point AVertices,
582                                   tel_point AVNormals, tel_colour AVColors, tel_texture_coord ATCoords,
583                                   tel_point AFNormals, tel_colour AFColors, const Tint AShapeFlag)
584 {
585   myData.num_rows    = ANbRows;
586   myData.num_columns = ANbCols;
587
588   const Tint nf = ANbRows * ANbCols;
589   const Tint nv = ( ANbRows+1 ) * ( ANbCols+1 );
590
591   Tint i;
592
593   // Store vertices
594   myData.vertices = AVertices;
595
596   // Store or compute (based on vertices) facet normals
597   if (AFNormals)
598   {
599     myData.facet_flag = TEL_FA_NORMAL;
600     myData.fnormals = new TEL_POINT[nf];
601     memcpy( myData.fnormals, AFNormals, nf*sizeof(TEL_POINT) );
602     for( i = 0; i < nf; i++ )
603       vecnrm( myData.fnormals[i].xyz );
604   }
605   else
606   {
607     myData.facet_flag = TEL_FA_NONE;
608     myData.fnormals = new TEL_POINT[nf];
609     for( i = 0; i < nf; i++ )
610     {
611       const Tint r = i/ANbCols;
612       const Tint c = i%ANbCols;
613       const Tint id = r*(ANbCols+1) + c;
614
615       TEL_POINT  p1, p2, p3, p4;
616
617       p1 = myData.vertices[id];
618       p2 = myData.vertices[id+ANbCols+1];
619       p3 = myData.vertices[id+ANbCols+2];
620       p4 = myData.vertices[id+1];
621
622       p4.xyz[0] -= p2.xyz[0];
623       p4.xyz[1] -= p2.xyz[1];
624       p4.xyz[2] -= p2.xyz[2];
625
626       p4.xyz[0] += p1.xyz[0];
627       p4.xyz[1] += p1.xyz[1];
628       p4.xyz[2] += p1.xyz[2];
629
630       TelGetNormal( p4.xyz, p1.xyz, p3.xyz, myData.fnormals[i].xyz );
631     }
632   }
633
634   // Store or compute (based on facet normals) vertex normals
635   if (AVNormals)
636   {
637     myData.vertex_flag = TEL_VT_NORMAL;
638     myData.vnormals = AVNormals;
639     for( i = 0; i < nv; i++ )
640       vecnrm( myData.vnormals[i].xyz );
641   }
642   else
643   {
644     myData.vertex_flag = TEL_VT_NONE;
645     myData.vnormals = new TEL_POINT[nv];
646     Tint r, c, id;
647     for( i = 0; i < nv; i++ )
648     {
649       if( i == 0 )
650         myData.vnormals[i] = myData.fnormals[i];
651       else if( i == (nv-1) )
652         myData.vnormals[i] = myData.fnormals[nf-1];
653       else if( i == (nv-ANbCols-1) )
654         myData.vnormals[i] = myData.fnormals[nf-ANbCols];
655       else if( i == ANbCols )
656         myData.vnormals[i] = myData.fnormals[i-1];
657       else if( i%(ANbCols+1) == 0 )
658       {
659         r = i/(myData.num_columns+1);
660         myData.vnormals[i].xyz[0] = ( myData.fnormals[(r-1)*ANbCols].xyz[0] + myData.fnormals[r*ANbCols].xyz[0] ) / 2.0F;
661         myData.vnormals[i].xyz[1] = ( myData.fnormals[(r-1)*ANbCols].xyz[1] + myData.fnormals[r*ANbCols].xyz[1] ) / 2.0F;
662         myData.vnormals[i].xyz[2] = ( myData.fnormals[(r-1)*ANbCols].xyz[2] + myData.fnormals[r*ANbCols].xyz[2] ) / 2.0F;
663       }
664       else if( i <= ANbCols )
665       {
666         myData.vnormals[i].xyz[0] = ( myData.fnormals[i-1].xyz[0] + myData.fnormals[i].xyz[0] ) / 2.0F;
667         myData.vnormals[i].xyz[1] = ( myData.fnormals[i-1].xyz[1] + myData.fnormals[i].xyz[1] ) / 2.0F;
668         myData.vnormals[i].xyz[2] = ( myData.fnormals[i-1].xyz[2] + myData.fnormals[i].xyz[2] ) / 2.0F;
669       }
670       else if( i >= (nv-ANbCols-1 ) )
671       {
672         c = i%(ANbCols+1);
673         id = nf-ANbCols+c;
674
675         myData.vnormals[i].xyz[0] = ( myData.fnormals[id-1].xyz[0] + myData.fnormals[id].xyz[0] ) / 2.0F;
676         myData.vnormals[i].xyz[1] = ( myData.fnormals[id-1].xyz[1] + myData.fnormals[id].xyz[1] ) / 2.0F;
677         myData.vnormals[i].xyz[2] = ( myData.fnormals[id-1].xyz[2] + myData.fnormals[id].xyz[2] ) / 2.0F;
678       }
679       else if( (i+1)%(ANbCols+1) == 0 )
680       {
681         r = (i+1)/(ANbCols+1);
682         myData.vnormals[i].xyz[0] = ( myData.fnormals[(r-1)*ANbCols-1].xyz[0] + myData.fnormals[r*ANbCols-1].xyz[0] ) / 2.0F;
683         myData.vnormals[i].xyz[1] = ( myData.fnormals[(r-1)*ANbCols-1].xyz[1] + myData.fnormals[r*ANbCols-1].xyz[1] ) / 2.0F;
684         myData.vnormals[i].xyz[2] = ( myData.fnormals[(r-1)*ANbCols-1].xyz[2] + myData.fnormals[r*ANbCols-1].xyz[2] ) / 2.0F;
685       }
686       else
687       {
688         r = i/(ANbCols+1);
689         c = i%(ANbCols+1);
690
691         id = r*ANbCols+c;
692
693         myData.vnormals[i].xyz[0] = ( myData.fnormals[id].xyz[0] + myData.fnormals[id-ANbCols].xyz[0] + myData.fnormals[id-1].xyz[0] + myData.fnormals[id-ANbCols-1].xyz[0] ) / 4.0F;
694         myData.vnormals[i].xyz[1] = ( myData.fnormals[id].xyz[1] + myData.fnormals[id-ANbCols].xyz[1] + myData.fnormals[id-1].xyz[1] + myData.fnormals[id-ANbCols-1].xyz[1] ) / 4.0F;
695         myData.vnormals[i].xyz[2] = ( myData.fnormals[id].xyz[2] + myData.fnormals[id-ANbCols].xyz[2] + myData.fnormals[id-1].xyz[2] + myData.fnormals[id-ANbCols-1].xyz[2] ) / 4.0F;
696       }
697     }
698   }
699
700   myData.vcolours = AVColors;
701   myData.vtexturecoord = ATCoords;
702   myData.fcolours = AFColors;
703
704   myData.shape_flag = AShapeFlag;
705
706   myDS = new DS_INTERNAL;
707   myDS->list      =  0;
708   myDS->dlist     =  0;
709   myDS->degMode   =  0;
710   myDS->model     = -1;
711   myDS->skipRatio =  0.0F;
712   myDS->bDraw = new unsigned char[nv];
713 }
714
715 /*----------------------------------------------------------------------*/
716
717 OpenGl_QuadrangleStrip::~OpenGl_QuadrangleStrip ()
718 {
719   if( myData.fnormals )
720     delete[] myData.fnormals;
721   if( myData.fcolours )
722     delete[] myData.fcolours;
723   if( myData.vertices )
724     delete[] myData.vertices;
725   if( myData.vcolours )
726     delete[] myData.vcolours;
727   if( myData.vnormals )
728     delete[] myData.vnormals;
729   if ( myData.vtexturecoord )
730     delete[] myData.vtexturecoord;
731
732   if ( myDS )
733   {
734     if (  GET_GL_CONTEXT() != NULL  )
735     {
736       if ( myDS->list ) glDeleteLists ( myDS->list, 1 );
737       if ( myDS->dlist ) glDeleteLists ( myDS->dlist, 1 );
738     }
739     if ( myDS->bDraw )
740       delete[] myDS->bDraw;
741
742         delete myDS;
743   }
744 }
745
746 /*----------------------------------------------------------------------*/
747
748 void OpenGl_QuadrangleStrip::Render (const Handle(OpenGl_Workspace) &AWorkspace) const
749 {
750   const OpenGl_AspectFace *aspect_face = AWorkspace->AspectFace( Standard_True );
751
752   Tint front_lighting_model = aspect_face->Context().IntFront.color_mask;
753   const TEL_COLOUR *interior_colour = &aspect_face->Context().IntFront.matcol;
754   const TEL_COLOUR *edge_colour = &aspect_face->AspectEdge()->Color();
755
756   // Use highlight colors
757   if ( AWorkspace->NamedStatus & OPENGL_NS_HIGHLIGHT )
758   {                         
759     edge_colour = interior_colour = AWorkspace->HighlightColor;
760     front_lighting_model = 0;
761   }
762
763   glColor3fv( interior_colour->rgb );
764
765   draw_qstrip( front_lighting_model,
766                aspect_face->Context().InteriorStyle,
767                edge_colour,
768                AWorkspace );
769 }
770
771 /*----------------------------------------------------------------------*/