MeshNode2T.cc 49.4 KB
Newer Older
1
2
3
/*===========================================================================*\
 *                                                                           *
 *                              OpenFlipper                                  *
Jan Möbius's avatar
Jan Möbius committed
4
 *      Copyright (C) 2001-2010 by Computer Graphics Group, RWTH Aachen      *
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
 *                           www.openflipper.org                             *
 *                                                                           *
 *---------------------------------------------------------------------------*
 *  This file is part of OpenFlipper.                                        *
 *                                                                           *
 *  OpenFlipper is free software: you can redistribute it and/or modify      *
 *  it under the terms of the GNU Lesser General Public License as           *
 *  published by the Free Software Foundation, either version 3 of           *
 *  the License, or (at your option) any later version with the              *
 *  following exceptions:                                                    *
 *                                                                           *
 *  If other files instantiate templates or use macros                       *
 *  or inline functions from this file, or you compile this file and         *
 *  link it with other files to produce an executable, this file does        *
 *  not by itself cause the resulting executable to be covered by the        *
 *  GNU Lesser General Public License. This exception does not however       *
 *  invalidate any other reasons why the executable file might be            *
 *  covered by the GNU Lesser General Public License.                        *
 *                                                                           *
 *  OpenFlipper is distributed in the hope that it will be useful,           *
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of           *
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the            *
 *  GNU Lesser General Public License for more details.                      *
 *                                                                           *
 *  You should have received a copy of the GNU LesserGeneral Public          *
 *  License along with OpenFlipper. If not,                                  *
 *  see <http://www.gnu.org/licenses/>.                                      *
 *                                                                           *
\*===========================================================================*/

/*===========================================================================*\
 *                                                                           *
Jan Möbius's avatar
Jan Möbius committed
37
38
39
 *   $Revision$                                                       *
 *   $Author$                                                      *
 *   $Date$                   *
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
 *                                                                           *
\*===========================================================================*/




//=============================================================================
//
//  CLASS MeshNodeT - IMPLEMENTATION
//
//=============================================================================

#define ACG_MESHNODE_C

//== NAMESPACES ===============================================================


namespace ACG {
namespace SceneGraph {
    

//== INCLUDES =================================================================


#include "MeshNode2T.hh"

template<class Mesh>
Jan Möbius's avatar
Jan Möbius committed
67
68
MeshNodeT<Mesh>::
MeshNodeT(Mesh&        _mesh,
69
              BaseNode*    _parent,
Jan Möbius's avatar
Jan Möbius committed
70
71
              std::string  _name ): 
  BaseNode(_parent, _name),
72
  mesh_(_mesh),
73
74
  stripProcessor_(_mesh),
  vertexBuffer_(0),
75
  vertexBufferInitialized_(false),
76
  enableNormals_(true),
77
78
  normalVertexBuffer_(0),
  normalVertexBufferInitialized_(false),
79
  enableColors_(true),
80
81
  colorVertexbuffer_(0),
  colorVertexBufferInitialized_(false),
82
  enableTexCoords_(true),
83
84
  lineIndexBuffer_(0),
  lineIndexBufferInitialized_(false),
Jan Möbius's avatar
Jan Möbius committed
85
86
87
  enabled_arrays_(0),
  updateVertexPickingList_(true),
  vertexPickingBaseIndex_(0),
Jan Möbius's avatar
Jan Möbius committed
88
89
90
  vertexPickingList_(0),
  updateEdgePickingList_(true),
  edgePickingBaseIndex_(0),
Jan Möbius's avatar
Jan Möbius committed
91
92
93
  edgePickingList_(0),
  updateFacePickingList_(true),
  facePickingBaseIndex_(0),
94
95
96
  facePickingList_(0),
  updateAnyPickingList_(true),
  anyPickingBaseIndex_(0),
97
98
  anyPickingList_(0),
  perFaceTextureIndexAvailable_(false),
99
  perFaceTextureCoordsAvailable_(false),
100
  textureMap_(0)
101
{
Jan Möbius's avatar
Jan Möbius committed
102
  
103
104
105
106
  /// \todo : Handle vbo not supported
  if ( ! GLEW_ARB_vertex_buffer_object ) {
    std::cerr << "Error! Vertex buffer objects are not supported! The meshNode will not work without them!" << std::endl;
  }
Jan Möbius's avatar
Jan Möbius committed
107
  
108
  
Jan Möbius's avatar
Jan Möbius committed
109
110
111
  vertexPickingList_ = glGenLists(1);
  edgePickingList_   = glGenLists(1);
  facePickingList_   = glGenLists(1);
112
  anyPickingList_    = glGenLists(3);
113
114
115
116

}  

template<class Mesh>
Jan Möbius's avatar
Jan Möbius committed
117
MeshNodeT<Mesh>::
118
119
120
~MeshNodeT()
{
  // Delete all allocated buffers
121
122
  if (vertexBuffer_)
    glDeleteBuffersARB(1, &vertexBuffer_);
123
  
124
125
  if (normalVertexBuffer_)
    glDeleteBuffersARB(1, &normalVertexBuffer_);  
126
  
127
128
  if (colorVertexbuffer_)
    glDeleteBuffersARB(1, &colorVertexbuffer_);    
Jan Möbius's avatar
Jan Möbius committed
129
  
130
131
  if (lineIndexBuffer_)
    glDeleteBuffersARB(1, &lineIndexBuffer_);     
132
  
133
134
135
136
137
138
139
140
141
142
143
144
  if (vertexPickingList_)
    glDeleteLists (vertexPickingList_, 1);
  
  if (edgePickingList_)
    glDeleteLists (edgePickingList_, 1);
  
  if (facePickingList_)
    glDeleteLists (facePickingList_, 1);
  
  if (anyPickingList_)
    glDeleteLists (anyPickingList_, 3);
  
145
146
147
}

template<class Mesh>
Jan Möbius's avatar
Jan Möbius committed
148
DrawModes::DrawMode
Jan Möbius's avatar
Jan Möbius committed
149
MeshNodeT<Mesh>::
150
availableDrawModes() const {
Jan Möbius's avatar
Jan Möbius committed
151
  DrawModes::DrawMode drawModes(DrawModes::NONE);
152
  
153
  // We can always render points and a wireframe.
154
  drawModes |= DrawModes::POINTS;
Jan Möbius's avatar
Jan Möbius committed
155
  drawModes |= DrawModes::HIDDENLINE;
156
  drawModes |= DrawModes::WIREFRAME;
157
  drawModes |= DrawModes::HALFEDGES;
158
  
159
160
  if (mesh_.has_vertex_normals())
  {
161
162
    drawModes |= DrawModes::POINTS_SHADED;  
    drawModes |= DrawModes::SOLID_SMOOTH_SHADED;
Jan Möbius's avatar
Jan Möbius committed
163
    drawModes |= DrawModes::SOLID_PHONG_SHADED;
164
165
  }
  
166
167
168
  if (mesh_.has_face_normals())
    drawModes |= DrawModes::SOLID_FLAT_SHADED;
  
169
170
171
  if (mesh_.has_vertex_colors())
  {
    drawModes |= DrawModes::POINTS_COLORED;
172
    drawModes |= DrawModes::SOLID_POINTS_COLORED;
173
  }
174
175
176
177
178

  if(mesh_.has_edge_colors())
  {
    drawModes |= DrawModes::EDGES_COLORED;
  }
179
180
181
182
183

  if(mesh_.has_halfedge_colors())
  {
    drawModes |= DrawModes::HALFEDGES_COLORED;
  }
184
  
185
186
187
188
189
190
191
  if (mesh_.has_face_colors()) {
    drawModes |= DrawModes::SOLID_FACES_COLORED;
    
    if( mesh_.has_face_normals() )
      drawModes |= DrawModes::SOLID_FACES_COLORED_FLAT_SHADED;
  }
  
192
193
194
  if ( mesh_.has_vertex_texcoords2D() ) {
    drawModes |= DrawModes::SOLID_TEXTURED;
    
195
196
    if (mesh_.has_vertex_normals())
      drawModes |= DrawModes::SOLID_TEXTURED_SHADED; 
197
198
  }
  
199
  if ( perFaceTextureCoordsAvailable_ ) {
200
201
202
203
204
205
    drawModes |= DrawModes::SOLID_2DTEXTURED_FACE;
    
    if (mesh_.has_face_normals())
      drawModes |= DrawModes::SOLID_2DTEXTURED_FACE_SHADED;
  }
  
206
207
208
209
210
  return drawModes;
}

template<class Mesh>
void
Jan Möbius's avatar
Jan Möbius committed
211
MeshNodeT<Mesh>::
212
boundingBox(Vec3d& _bbMin, Vec3d& _bbMax) {
Jan Möbius's avatar
Jan Möbius committed
213
214
  _bbMin.minimize(bbMin_);
  _bbMax.maximize(bbMax_);
215
216
217
218
}

template<class Mesh>
void
Jan Möbius's avatar
Jan Möbius committed
219
MeshNodeT<Mesh>::
Jan Möbius's avatar
Jan Möbius committed
220
draw(GLState& _state, DrawModes::DrawMode _drawMode) {
Jan Möbius's avatar
Jan Möbius committed
221
  
222
223
224
  // Update strips if necessary
  stripProcessor_.stripify();
  
225
226
  GLint prev_depth;
  glGetIntegerv (GL_DEPTH_FUNC, &prev_depth);
227

228
229
  unsigned int arrays = VERTEX_ARRAY;
  
230
  glPushAttrib(GL_ENABLE_BIT);
231
 
232
  if ( (_drawMode & DrawModes::POINTS) || (_drawMode & DrawModes::POINTS_COLORED) || (_drawMode & DrawModes::POINTS_SHADED )  ) {
233
    
234
    glShadeModel(GL_FLAT);
235
236
237
238
239
    
    if ( _drawMode & DrawModes::POINTS_SHADED  ) {
      glEnable(GL_LIGHTING);
    } else
      glDisable(GL_LIGHTING);
240
  
241
242
    // Use Colors in this mode if allowed
    if ( enableColors_ && (_drawMode & DrawModes::POINTS_COLORED) )
243
      arrays |= COLOR_VERTEX_ARRAY;
244
    
245
246
    // Use Normals in this mode if allowed
    if ( enableNormals_ && (_drawMode & DrawModes::POINTS_SHADED ) ) {
247
      arrays |= NORMAL_VERTEX_ARRAY;
248
249
      
      // If we have colors and lighting with normals, we have to use colormaterial
250
      if ( (arrays & COLOR_VERTEX_ARRAY) )
251
252
253
254
        glEnable(GL_COLOR_MATERIAL);
      else 
        glDisable(GL_COLOR_MATERIAL);
    }
255
    
256
257
258
259
    // Bring the arrays online
    enable_arrays(arrays);
    
    // Draw vertices
260
261
262
    draw_vertices();
  }
  
263
264
  
  /// \todo We can render also wireframe shaded and with vertex colors
265
266
  if (_drawMode & DrawModes::WIREFRAME)
  {
267
    enable_arrays( VERTEX_ARRAY | LINE_INDEX_ARRAY );
268
269
270
    glDisable(GL_LIGHTING);
    glShadeModel(GL_FLAT);
    draw_lines();
Jan Möbius's avatar
Jan Möbius committed
271
  }  
272
  
Jan Möbius's avatar
Jan Möbius committed
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
  if (_drawMode & DrawModes::HIDDENLINE)
  {
    enable_arrays(VERTEX_ARRAY);
    
    // First:
    // Render all faces in background color to initialize z-buffer
    Vec4f  clear_color = _state.clear_color();
    Vec4f  base_color  = _state.base_color();
    clear_color[3] = 1.0;
    
    glDisable(GL_LIGHTING);
    glShadeModel(GL_FLAT);
    glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
    _state.set_base_color(clear_color);
    
    glDepthRange(0.01, 1.0);
    draw_faces(PER_VERTEX);
    glDepthRange(0.0, 1.0);
    
    // Second
    // Render the lines. All lines not on the front will be skipped in z-test
    enable_arrays(VERTEX_ARRAY|LINE_INDEX_ARRAY);
    glDepthFunc(GL_LEQUAL);
    _state.set_base_color(base_color);
    draw_lines();
298
299
300
    
    //restore depth buffer comparison function for the next draw calls inside this function
    glDepthFunc(prev_depth);
Jan Möbius's avatar
Jan Möbius committed
301
302
    glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
  }
303
304
305
306
307
308
309
310
311
312


  if (_drawMode & DrawModes::EDGES_COLORED)
  {
    enable_arrays( PER_EDGE_VERTEX_ARRAY | PER_EDGE_COLOR_ARRAY );
    glDisable(GL_LIGHTING);
    glShadeModel(GL_FLAT);
    draw_lines();
  }  

313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
  if (_drawMode & DrawModes::HALFEDGES)
  {
    enable_arrays( PER_HALFEDGE_VERTEX_ARRAY);
    glDisable(GL_LIGHTING);
    glShadeModel(GL_FLAT);
    draw_halfedges();
  }  

  if (_drawMode & DrawModes::HALFEDGES_COLORED)
  {
    enable_arrays( PER_HALFEDGE_VERTEX_ARRAY | PER_HALFEDGE_COLOR_ARRAY );
    glDisable(GL_LIGHTING);
    glShadeModel(GL_FLAT);
    draw_halfedges();
  }  
Jan Möbius's avatar
Jan Möbius committed
328
  
329
330
  if ( ( _drawMode & DrawModes::SOLID_POINTS_COLORED ) && mesh_.has_vertex_colors() )
  {
331
    glEnable(GL_LIGHTING);
332
333
    glShadeModel(GL_SMOOTH);
    glDepthRange(0.01, 1.0);
334
335
336
337
338
339
340
    if ( enableNormals_ ) {
       glEnable(GL_COLOR_MATERIAL);
       enable_arrays( VERTEX_ARRAY | COLOR_VERTEX_ARRAY | NORMAL_VERTEX_ARRAY  );
    } else {
      glDisable(GL_COLOR_MATERIAL);
      enable_arrays( VERTEX_ARRAY | COLOR_VERTEX_ARRAY  );
    }
341
342
343
344
    draw_faces(PER_VERTEX);
    glDepthRange(0.0, 1.0);
  }
  
345
346
347
348
349
350
351
352
353
354
355
  if ( ( _drawMode & DrawModes::SOLID_FLAT_SHADED ) && mesh_.has_face_normals())
  {
    glEnable(GL_LIGHTING);
    glShadeModel(GL_FLAT);
    glDepthRange(0.01, 1.0);
    enable_arrays(PER_FACE_VERTEX_ARRAY | PER_FACE_NORMAL_ARRAY);
    draw_faces(PER_FACE);
    glDepthRange(0.0, 1.0);
  }
  
  
Jan Möbius's avatar
Jan Möbius committed
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
  if ( ( _drawMode & DrawModes::SOLID_SMOOTH_SHADED ) && mesh_.has_vertex_normals() )
  {
    enable_arrays( VERTEX_ARRAY | NORMAL_VERTEX_ARRAY );
    glEnable(GL_LIGHTING);
    glShadeModel(GL_SMOOTH);
    glDepthRange(0.01, 1.0);
    draw_faces(PER_VERTEX);
    glDepthRange(0.0, 1.0);
  }
  
  if ( ( _drawMode & DrawModes::SOLID_PHONG_SHADED ) && mesh_.has_vertex_normals() )
  {
    ///\todo Integrate shader here! 
    //     if ( parent() != 0 ) {
    //       if ( parent()->className() == "ShaderNode" ) {
    //
    //         ShaderNode* node = dynamic_cast< ShaderNode* > ( parent() );
    //
    //         GLSL::PtrProgram program = node->getShader( DrawModes::SOLID_PHONG_SHADED );
    //
    //         // Enable own Phong shader
    //         program->use();
    
    enable_arrays(VERTEX_ARRAY | NORMAL_VERTEX_ARRAY );
    glEnable(GL_LIGHTING);
    glShadeModel(GL_SMOOTH);
    glDepthRange(0.01, 1.0);
    draw_faces(PER_VERTEX);
    glDepthRange(0.0, 1.0);
    
    //disable own Phong shader
    //         program->disable();
    //       }
    //     }
  }
  
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
  
  if ( ( _drawMode & DrawModes::SOLID_FACES_COLORED )&& mesh_.has_face_colors())
  {
    Vec4f base_color_backup = _state.base_color();
    
    glDisable(GL_LIGHTING);
    glShadeModel(GL_FLAT);
    glDepthRange(0.01, 1.0);
    enable_arrays(PER_FACE_VERTEX_ARRAY | PER_FACE_COLOR_ARRAY);    
    draw_faces(PER_FACE);
    glDepthRange(0.0, 1.0);
    
    _state.set_base_color(base_color_backup);
  }
  
  
  if ( ( _drawMode & DrawModes::SOLID_FACES_COLORED_FLAT_SHADED ) && mesh_.has_face_colors() && mesh_.has_face_normals())
  {
    Vec4f base_color_backup = _state.base_color();
    glEnable(GL_LIGHTING);
    
    glShadeModel(GL_FLAT);
    glDepthRange(0.01, 1.0);
    enable_arrays(PER_FACE_VERTEX_ARRAY | PER_FACE_COLOR_ARRAY | PER_FACE_NORMAL_ARRAY );
    draw_faces(PER_FACE);
    glDepthRange(0.0, 1.0);
    
    _state.set_base_color(base_color_backup);
  }
  
  
423
  if ( ( _drawMode & DrawModes::SOLID_TEXTURED )  && mesh_.has_vertex_texcoords2D())
424
425
426
427
428
429
430
431
432
433
434
435
  {
    ///\todo enableTexCoords_
    enable_arrays(VERTEX_ARRAY | TEXCOORD_VERTEX_ARRAY );
    glEnable(GL_TEXTURE_2D);
    glDisable(GL_LIGHTING);
    glShadeModel(GL_FLAT);
    glDepthRange(0.01, 1.0);
    draw_faces(PER_VERTEX);
    glDepthRange(0.0, 1.0);
    glDisable(GL_TEXTURE_2D);
  }
  
436
437
438
439
440
441
442
443
444
445
446
447
  if ( ( _drawMode & DrawModes::SOLID_TEXTURED_SHADED ) && mesh_.has_vertex_texcoords2D() && mesh_.has_vertex_normals())
  {
    enable_arrays(VERTEX_ARRAY | NORMAL_VERTEX_ARRAY | TEXCOORD_VERTEX_ARRAY);
    glEnable(GL_TEXTURE_2D);
    glEnable(GL_LIGHTING);
    glShadeModel(GL_SMOOTH);
    glDepthRange(0.01, 1.0);
    draw_faces(PER_VERTEX);
    glDepthRange(0.0, 1.0);
    glDisable(GL_TEXTURE_2D);
  }
  
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
  
  
  // Textured by using coordinates stored in halfedges ... arrays generated by stripprocessor
  if ( _drawMode & DrawModes::SOLID_2DTEXTURED_FACE )
  {
    glEnable(GL_TEXTURE_2D);
    
    enable_arrays( PER_FACE_VERTEX_ARRAY | PER_FACE_TEXCOORD_ARRAY );
    
    glDisable(GL_LIGHTING);
    glShadeModel(GL_FLAT);
    glDepthRange(0.01, 1.0);
    draw_faces(PER_FACE);
    glDepthRange(0.0, 1.0);
    
    glDisable(GL_TEXTURE_2D);
  }
  
  // Textured by using coordinates stored in halfedges
  if ( ( _drawMode & DrawModes::SOLID_2DTEXTURED_FACE_SHADED ) && mesh_.has_face_normals())
  {
    glEnable(GL_TEXTURE_2D);
    
471
472
473
474
    enable_arrays( PER_FACE_VERTEX_ARRAY | PER_FACE_TEXCOORD_ARRAY | PER_FACE_PER_VERTEX_NORMAL_ARRAY );

    glEnable(GL_LIGHTING);
    glShadeModel(GL_SMOOTH);
475
476
477
478
479
480
481
    glDepthRange(0.01, 1.0);
    draw_faces(PER_FACE);
    glDepthRange(0.0, 1.0);
    glDisable(GL_TEXTURE_2D);
    
  }
  
Jan Möbius's avatar
Jan Möbius committed
482
483
  enable_arrays(0);
  
484
485
486
  // Unbind all remaining buffers
  glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB , 0 );
  
487
  glPopAttrib();
488
489
490
491
}

template<class Mesh>
void
Jan Möbius's avatar
Jan Möbius committed
492
MeshNodeT<Mesh>::
493
draw_vertices() {
Jan Möbius's avatar
Jan Möbius committed
494
  if ( !vertexBufferInitialized_ || ( mesh_.n_vertices() == 0 ))
Jan Möbius's avatar
Jan Möbius committed
495
    return;
Jan Möbius's avatar
Jan Möbius committed
496

497
498
499
  glDrawArrays(GL_POINTS, 0, mesh_.n_vertices());
}

500
501
template<class Mesh>
void
Jan Möbius's avatar
Jan Möbius committed
502
MeshNodeT<Mesh>::
503
draw_lines() {
504
505
506
507
508
509

  if ( enabled_arrays_ & LINE_INDEX_ARRAY )
    
    // Check if array is set up correctly
    if ( lineIndexBufferInitialized_ )
      glDrawElements(GL_LINES, mesh_.n_edges() * 2, GL_UNSIGNED_INT, 0 );
Jan Möbius's avatar
Jan Möbius committed
510
511
    else 
      return;
512
513
514
515
    
  // If we are rendering per edge per vertex attributes, we need to use a seperated vertex buffer!
  else if ( enabled_arrays_ & PER_EDGE_VERTEX_ARRAY )
    glDrawArrays(GL_LINES, 0, mesh_.n_edges() * 2);
516
  
517
518
519
  // Something went wrong here!
  else
    std::cerr << "Unable to Draw! array configuration is invalid!!" << std::endl;
520
521
}

522
523
524
525
526
527
528
529
530
531
532
533
534

template<class Mesh>
void
MeshNodeT<Mesh>::
draw_halfedges() {
  // If we are rendering per edge per vertex attributes, we need to use a seperated vertex buffer!
  if ( enabled_arrays_ & PER_HALFEDGE_VERTEX_ARRAY )
    glDrawArrays(GL_LINES, 0, mesh_.n_halfedges() * 2);
  // Something went wrong here!
  else
    std::cerr << "Unable to Draw! halfedge array configuration is invalid!!" << std::endl;
}

535
536
template<class Mesh>
void
Jan Möbius's avatar
Jan Möbius committed
537
MeshNodeT<Mesh>::
538
draw_faces(FaceMode _mode) {
Jan Möbius's avatar
Jan Möbius committed
539
  
540
541
542
543
544
545
  // If we have all properties per Vertex, we can render with index array from triangle strips!
  if (_mode == PER_VERTEX) {
    
    typename StripProcessorT<Mesh>::StripsIterator strip_it   = stripProcessor_.begin();
    typename StripProcessorT<Mesh>::StripsIterator strip_last = stripProcessor_.end();
    
546
    
547
548
549
550
551
552
553
554
555
556
557
558
559
    
    for (; strip_it!=strip_last; ++strip_it) {
      glDrawElements(GL_TRIANGLE_STRIP,
                    strip_it->indexArray.size(),
                    GL_UNSIGNED_INT,
                      &(strip_it->indexArray)[0]  );
    }
  } else if ( _mode ==  PER_FACE ) {
    
    if ( stripProcessor_.perFaceTextureIndexAvailable()  && (textureMap_ != 0) ) {

      int lastTexture = -1;
      int texture = 0;
560
      
561
562
563
564
565
566
567
568
569
570
571
572
573
574
      for ( uint i = 0 ; i < stripProcessor_.textureRenderData()->size() ; ++i ) {
        int texture =  (*stripProcessor_.textureRenderData())[i].textureId;
        if ( texture != lastTexture) {

          if ( textureMap_->find(texture) == textureMap_->end() ) {
            std::cerr << "Illegal texture index ... trying to access " << texture << std::endl;
            lastTexture = -1;
            continue;
          }
          
          glBindTexture( GL_TEXTURE_2D, (*textureMap_)[texture] );          
          
          lastTexture = texture;
        }
575
        
576
577
        // We need per face attributes so we have to use seperate vertices per face
        glDrawArrays(GL_TRIANGLES, (*stripProcessor_.textureRenderData())[i].startOffset , (*stripProcessor_.textureRenderData())[i].faceCount * 3 );
578
      }
579
580
      
    } else {
581
      // We need per face attributes so we have to use seperate vertices per face
582
      glDrawArrays(GL_TRIANGLES, 0, stripProcessor_.perFaceVertexBufferSize() );
583
584
    }
  }
585

586
587
}

588
589
template<class Mesh>
void
Jan Möbius's avatar
Jan Möbius committed
590
MeshNodeT<Mesh>::
591
enable_arrays(unsigned int _arrays) {
Jan Möbius's avatar
Jan Möbius committed
592
  
Jan Möbius's avatar
Jan Möbius committed
593
594
595
596
  // Unbind everything to ensure sane settings
  glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
  glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0);
  
597
598
599
  //===================================================================
  // Vertex Array
  //===================================================================
600
601
  
  // Check if we should enable the vertex array
Jan Möbius's avatar
Jan Möbius committed
602
  if ( (_arrays & VERTEX_ARRAY ) && vertexBufferInitialized_ ) {
603
    
604
605
606
607
608
609
610
    // Check if its already enabled
    if (!(enabled_arrays_ & VERTEX_ARRAY)) {
      
      // Enable the vertex buffer
      enabled_arrays_ |= VERTEX_ARRAY;
   
      // Bind the Vertex buffer
611
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, vertexBuffer_);
612
613
614
      
      // As we ensure that buffers are converted to float before using them, use Float here
      glVertexPointer(3, GL_FLOAT, 0, 0);
Jan Möbius's avatar
Jan Möbius committed
615
      glEnableClientState(GL_VERTEX_ARRAY);
616
    }
617
  } else if (enabled_arrays_ & VERTEX_ARRAY) {
618
619
620
621
622
    // Disable the Vertex array
    enabled_arrays_ &= ~VERTEX_ARRAY;
    glDisableClientState(GL_VERTEX_ARRAY);
  }
  
623
624
625
626
627
628
  
  //===================================================================
  // Normal Array
  //===================================================================
  
  // Check if we should enable the normal array
Jan Möbius's avatar
Jan Möbius committed
629
  if ( mesh_.has_vertex_normals() && ( _arrays & NORMAL_VERTEX_ARRAY ) && normalVertexBufferInitialized_ ) {
630
631
    
    // Check if its already enabled
632
633
    if (!(enabled_arrays_ & NORMAL_VERTEX_ARRAY)) {
      enabled_arrays_ |= NORMAL_VERTEX_ARRAY;
634
      
635
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, normalVertexBuffer_);
636
637
638
      
      // As we ensure that buffers are converted to float before using them, use Float here
      glNormalPointer(GL_FLOAT, 0 , 0);
Jan Möbius's avatar
Jan Möbius committed
639
640
      
      glEnableClientState(GL_NORMAL_ARRAY);
641
    }
642
  } else if (enabled_arrays_ & NORMAL_VERTEX_ARRAY) {
643
    // Disable Normal array
644
    enabled_arrays_ &= ~NORMAL_VERTEX_ARRAY;
645
    glDisableClientState(GL_NORMAL_ARRAY);
646
  } 
647
  
648
  //===================================================================
649
  // per Vertex Color Array
650
  //===================================================================  
651
  
652
653
  /// \todo This is different to normal and vertex buffer since it uses openmesh colors directly! Check for different color representations in OpenMesh!
  // Check if we should enable the color array
654
  if ( mesh_.has_vertex_colors() && ( _arrays & COLOR_VERTEX_ARRAY ))  {
655
656
    
    // Check if its already enabled
657
658
    if (!(enabled_arrays_ & COLOR_VERTEX_ARRAY)) {
      enabled_arrays_ |= COLOR_VERTEX_ARRAY;
Jan Möbius's avatar
Jan Möbius committed
659
      
660
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, colorVertexbuffer_);
Jan Möbius's avatar
Jan Möbius committed
661
      
Jan Möbius's avatar
Jan Möbius committed
662
      // Explicitly give the pointer as we uploaded the data ourself!
663
      glColorPointer(4, GL_FLOAT , 0 , 0);
Jan Möbius's avatar
Jan Möbius committed
664
      
665
      glEnableClientState(GL_COLOR_ARRAY);
Jan Möbius's avatar
Jan Möbius committed
666
      
667
    }
668
  } else if (enabled_arrays_ & COLOR_VERTEX_ARRAY) {
669
    // Disable Color array
670
    enabled_arrays_ &= ~COLOR_VERTEX_ARRAY;
671
    glDisableClientState(GL_COLOR_ARRAY);
Jan Möbius's avatar
Jan Möbius committed
672
  } 
673
  
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
  //===================================================================
  // per Vertex Texture coordinate Array
  //===================================================================  
  
  // Check if we should enable the color array
  if ( mesh_.has_vertex_texcoords2D() && ( _arrays & TEXCOORD_VERTEX_ARRAY ))  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & TEXCOORD_VERTEX_ARRAY)) {
      enabled_arrays_ |= TEXCOORD_VERTEX_ARRAY;
      
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      
      // Explicitly give the pointer as we uploaded the data ourself!
      glTexCoordPointer(2, GL_FLOAT , 0 , mesh_.texcoords2D() );
      
      glEnableClientState(GL_TEXTURE_COORD_ARRAY);
      
    }
  } else if (enabled_arrays_ & TEXCOORD_VERTEX_ARRAY) {
    // Disable TexCoord array
    enabled_arrays_ &= ~TEXCOORD_VERTEX_ARRAY;
    glDisableClientState(GL_TEXTURE_COORD_ARRAY);
  }   
  
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
  //===================================================================
  // per Edge Vertex Array
  //===================================================================  
  
  // Check if we should enable the per face vertex array
  if (_arrays & PER_EDGE_VERTEX_ARRAY)  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & PER_EDGE_VERTEX_ARRAY)) {
      enabled_arrays_ |= PER_EDGE_VERTEX_ARRAY;
      
      // For this version we load the colors directly not from vbo
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      glVertexPointer( stripProcessor_.perEdgeVertexBuffer() );   
      
      glEnableClientState(GL_VERTEX_ARRAY);
      
    }
  } else if (enabled_arrays_ & PER_EDGE_VERTEX_ARRAY) {
    // Disable Vertex array
    enabled_arrays_ &= ~PER_EDGE_VERTEX_ARRAY;
    glDisableClientState(GL_VERTEX_ARRAY);
  } 
  
  //===================================================================
  // per Edge Color Array
  //===================================================================  
  
  // Check if we should enable the per face vertex array
  if ( mesh_.has_edge_colors()  && ( _arrays & PER_EDGE_COLOR_ARRAY) )  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & PER_EDGE_COLOR_ARRAY)) {
      enabled_arrays_ |= PER_EDGE_COLOR_ARRAY;
      
      // For this version we load the colors directly not from vbo
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      glColorPointer( stripProcessor_.perEdgeColorBuffer() );   
      
      glEnableClientState(GL_COLOR_ARRAY);
      
    }
  } else if (enabled_arrays_ & PER_EDGE_COLOR_ARRAY) {
    // Disable Vertex array
    enabled_arrays_ &= ~PER_EDGE_COLOR_ARRAY;
    glDisableClientState(GL_COLOR_ARRAY);
  }   
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794


  //===================================================================
  // per Halfedge Vertex Array
  //===================================================================  
  
  // Check if we should enable the per face vertex array
  if (_arrays & PER_HALFEDGE_VERTEX_ARRAY)  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & PER_HALFEDGE_VERTEX_ARRAY)) {
      enabled_arrays_ |= PER_HALFEDGE_VERTEX_ARRAY;
      
      // For this version we load the colors directly not from vbo
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      glVertexPointer( stripProcessor_.perHalfedgeVertexBuffer() );   
      
      glEnableClientState(GL_VERTEX_ARRAY);
      
    }
  } else if (enabled_arrays_ & PER_HALFEDGE_VERTEX_ARRAY) {
    // Disable Vertex array
    enabled_arrays_ &= ~PER_HALFEDGE_VERTEX_ARRAY;
    glDisableClientState(GL_VERTEX_ARRAY);
  } 
  
  //===================================================================
  // per Halfedge Color Array
  //===================================================================  
  
  // Check if we should enable the per face vertex array
  if ( mesh_.has_halfedge_colors()  && ( _arrays & PER_HALFEDGE_COLOR_ARRAY) )  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & PER_HALFEDGE_COLOR_ARRAY)) {
      enabled_arrays_ |= PER_HALFEDGE_COLOR_ARRAY;
      
      // For this version we load the colors directly not from vbo
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      glColorPointer( stripProcessor_.perHalfedgeColorBuffer() );
      
      glEnableClientState(GL_COLOR_ARRAY);
      
    }
  } else if (enabled_arrays_ & PER_HALFEDGE_COLOR_ARRAY) {
    // Disable Vertex array
    enabled_arrays_ &= ~PER_HALFEDGE_COLOR_ARRAY;
    glDisableClientState(GL_COLOR_ARRAY);
  }   
795
  
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
  //===================================================================
  // per Face Vertex Array
  //===================================================================  
  
  // Check if we should enable the per face vertex array
  if (_arrays & PER_FACE_VERTEX_ARRAY)  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & PER_FACE_VERTEX_ARRAY)) {
      enabled_arrays_ |= PER_FACE_VERTEX_ARRAY;
      
      // For this version we load the colors directly not from vbo
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      glVertexPointer( stripProcessor_.perFaceVertexBuffer() );   
      
      glEnableClientState(GL_VERTEX_ARRAY);
      
    }
  } else if (enabled_arrays_ & PER_FACE_VERTEX_ARRAY) {
    // Disable Vertex array
    enabled_arrays_ &= ~PER_FACE_VERTEX_ARRAY;
    glDisableClientState(GL_VERTEX_ARRAY);
  } 

  //===================================================================
  // per Face Normal Array
  //===================================================================  

  // Check if we should enable the per face normal array
  if (mesh_.has_face_normals() && (_arrays & PER_FACE_NORMAL_ARRAY) )  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & PER_FACE_NORMAL_ARRAY)) {
      enabled_arrays_ |= PER_FACE_NORMAL_ARRAY;
      
      // For this version we load the colors directly not from vbo
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      glNormalPointer( stripProcessor_.perFaceNormalBuffer() );   
      
      glEnableClientState(GL_NORMAL_ARRAY);
      
    }
  } else if (enabled_arrays_ & PER_FACE_NORMAL_ARRAY) {
    // Disable Normal array
    enabled_arrays_ &= ~PER_FACE_NORMAL_ARRAY;
    glDisableClientState(GL_NORMAL_ARRAY);
  } 
  
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
  //===================================================================
  // per Face per vertex normal array
  //===================================================================  
  
  // Check if we should enable the per face normal array
  if (mesh_.has_vertex_normals() && (_arrays & PER_FACE_PER_VERTEX_NORMAL_ARRAY) )  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & PER_FACE_PER_VERTEX_NORMAL_ARRAY)) {
      enabled_arrays_ |= PER_FACE_PER_VERTEX_NORMAL_ARRAY;
      
      // For this version we load the colors directly not from vbo
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      glNormalPointer( stripProcessor_.perFacePerVertexNormalBuffer() );   
      
      glEnableClientState(GL_NORMAL_ARRAY);
      
    }
  } else if (enabled_arrays_ & PER_FACE_PER_VERTEX_NORMAL_ARRAY) {
    // Disable Normal array
    enabled_arrays_ &= ~PER_FACE_PER_VERTEX_NORMAL_ARRAY;
    glDisableClientState(GL_NORMAL_ARRAY);
  } 
  
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
  //===================================================================
  // per Face Color Array
  //===================================================================  
  
  // Check if we should enable the per face color array
  if (mesh_.has_face_colors() && (_arrays & PER_FACE_COLOR_ARRAY) )  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & PER_FACE_COLOR_ARRAY)) {
      enabled_arrays_ |= PER_FACE_COLOR_ARRAY;
      
      // For this version we load the colors directly not from vbo
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      glColorPointer( stripProcessor_.perFaceColorBuffer() );   
      
      glEnableClientState(GL_COLOR_ARRAY);
      
    }
  } else if (enabled_arrays_ & PER_FACE_COLOR_ARRAY) {
    // Disable Normal array
    enabled_arrays_ &= ~PER_FACE_COLOR_ARRAY;
    glDisableClientState(GL_COLOR_ARRAY);
  }   
  
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
  //===================================================================
  // per Face TexCoord Array
  //===================================================================  
  
  // Check if we should enable the per face color array
  if ( stripProcessor_.perFaceTextureCoordinateAvailable() && (_arrays & PER_FACE_TEXCOORD_ARRAY ) )  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & PER_FACE_TEXCOORD_ARRAY)) {
      enabled_arrays_ |= PER_FACE_TEXCOORD_ARRAY;
      
      // For this version we load the colors directly not from vbo
      glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
      glTexCoordPointer( stripProcessor_.perFacePerVertexTextureCoordBuffer() );   
      glEnableClientState(GL_TEXTURE_COORD_ARRAY );
    }
  } else if (enabled_arrays_ & PER_FACE_TEXCOORD_ARRAY) {
    // Disable Texture Coordinate array
    enabled_arrays_ &= ~PER_FACE_TEXCOORD_ARRAY;
    glDisableClientState(GL_TEXTURE_COORD_ARRAY);
  }   
  
914
915
916
917
918
919
920
921
922
923
924
  //===================================================================
  // Line Index Array
  //===================================================================  
  
  // Check if we should enable the color array
  if (_arrays & LINE_INDEX_ARRAY)  {
    
    // Check if its already enabled
    if (!(enabled_arrays_ & LINE_INDEX_ARRAY)) {
      enabled_arrays_ |= LINE_INDEX_ARRAY;
      
925
      glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, lineIndexBuffer_);
926
927
928
929
    }
  } else if (enabled_arrays_ & LINE_INDEX_ARRAY) {
    // Disable Color array
    enabled_arrays_ &= ~LINE_INDEX_ARRAY;
930
    glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0);
931
932
  } 
  
933
934
935
  if ( _arrays == 0 ) 
    glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
  
936
937
938
939
  //===================================================================
  // Check for OpenGL Errors
  //===================================================================    
  glCheckErrors();
940
941
942
943
}

template<class Mesh>
void
Jan Möbius's avatar
Jan Möbius committed
944
MeshNodeT<Mesh>::
945
pick(GLState& _state, PickTarget _target) {
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
  switch (_target)
  {
    case PICK_VERTEX:
    {
      pick_vertices(_state);
      break;
    }
    case PICK_FRONT_VERTEX:
    {
      pick_vertices(_state, true);
      break;
    }
    
    case PICK_ANYTHING:
    {
      pick_any(_state);
      break;
    }
    case PICK_FACE:
    {
      pick_faces(_state);
      break;
    }
    
    case PICK_EDGE:
    {
      pick_edges(_state);
      break;
    }
    
    case PICK_FRONT_EDGE:
    {
      pick_edges(_state, true);
      break;
    }
    
    default:
      break;
  }
}

template<class Mesh>
void
Jan Möbius's avatar
Jan Möbius committed
989
MeshNodeT<Mesh>::
990
991
pick_vertices(GLState& _state, bool _front)
{
992
993
994
  GLint prev_depth;
  glGetIntegerv (GL_DEPTH_FUNC, &prev_depth);
  
Jan Möbius's avatar
Jan Möbius committed
995
996
  typename Mesh::ConstVertexIter v_it(mesh_.vertices_begin()),
  v_end(mesh_.vertices_end());
997
  
Jan Möbius's avatar
Jan Möbius committed
998
  if (!_state.pick_set_maximum (mesh_.n_vertices())) {
999
    omerr() << "MeshNode::pick_vertices: color range too small, " << "picking failed\n";
Jan Möbius's avatar
Jan Möbius committed
1000
    return;