Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/branches/terrain/src/lib/graphics/importer/static_model_data.cc

Last change on this file was 10141, checked in by bensch, 18 years ago

orxonox/trunk: ported the static_model to std::vectort.
Took me 90 minutes, and i hope everything is still working as it did before :)

File size: 23.7 KB
Line 
1/*
2   orxonox - the future of 3D-vertical-scrollers
3
4   Copyright (C) 2004 orx
5
6   This program is free software; you can redistribute it and/or modify
7   it under the terms of the GNU General Public License as published by
8   the Free Software Foundation; either version 2, or (at your option)
9   any later version.
10
11   ### File Specific:
12   main-programmer: Benjamin Grauer
13   co-programmer: ...
14
15   2005-07-06: (Patrick) added new function buildTriangleList()
16*/
17
18#define DEBUG_SPECIAL_MODULE DEBUG_MODULE_IMPORTER
19
20#include "static_model_data.h"
21
22#include "debug.h"
23#include <stdarg.h>
24#include <algorithm>
25
26
27
28////////////////////
29/// SUB-Elements ///
30////////////////////
31/**
32 * @brief creates a new ModelFaceElement
33 */
34StaticModelData::FaceElement::FaceElement()
35{
36  this->vertexNumber = -1;
37  this->normalNumber = -1;
38  this->texCoordNumber = -1;
39}
40
41
42/**
43 * @brief creates a new ModelFace
44 */
45StaticModelData::Face::Face()
46{
47  this->_material = NULL;
48}
49
50/**
51 * @brief Creates a new ModelGroup
52 */
53StaticModelData::Group::Group()
54{
55  PRINTF(4)("Adding new Group\n");
56  this->name = "";
57  this->faceMode = -1;
58  this->listNumber = 0;
59  this->indices = NULL;
60}
61
62/**
63 * @brief deletes a ModelGroup
64 */
65StaticModelData::Group::~Group()
66{
67  PRINTF(5)("Cleaning up group\n");
68  // deleting the glList
69  if (this->listNumber != 0)
70    glDeleteLists(this->listNumber, 1);
71}
72
73/**
74 * @brief cleans up a ModelGroup
75 *
76 * actually does the same as the delete Operator, but does not delete the predecessing group
77 */
78void StaticModelData::Group::cleanup()
79{
80  PRINTF(5)("Cleaning up group\n");
81  this->_faces.clear();
82}
83
84
85
86
87/////////////
88/// MODEL ///
89/////////////
90ObjectListDefinition(StaticModelData);
91
92/**
93 * @brief Creates a 3D-Model.
94 *
95 * assigns it a Name and a Type
96 */
97StaticModelData::StaticModelData(const std::string& modelName)
98{
99  this->registerObject(this, StaticModelData::_objectList);
100  PRINTF(4)("new 3D-Model is being created\n");
101  this->setName(modelName);
102
103  this->finalized = false;
104
105  // setting the start group;
106  this->_modelGroups.push_back(Group());
107  this->faceCount = 0;
108
109  this->scaleFactor = 1.0f;
110}
111
112/**
113 * @brief deletes an Model.
114 *
115 * Looks if any from model allocated space is still in use, and if so deleted it.
116 */
117StaticModelData::~StaticModelData()
118{
119  PRINTF(4)("Deleting Model %s\n", this->getCName());
120  this->cleanup();
121}
122
123/**
124 * @brief Finalizes an Object. This can be done outside of the Class.
125 */
126void StaticModelData::finalize()
127{
128  // this creates the display List.
129  this->importToDisplayList();
130  this->buildTriangleList();
131
132  this->finalized = true;
133}
134
135/**
136 * @brief rebuild the Model from the Information we got.
137 */
138void StaticModelData::rebuild()
139{
140  PRINTF(3)("Rebuilding Model '%s'\n", this->getCName());
141  this->finalize();
142}
143
144//////////
145// DRAW //
146//////////
147/**
148 * @brief Draws the Models of all Groups.
149 *
150 * It does this by just calling the Lists that must have been created earlier.
151 */
152void StaticModelData::draw () const
153{
154  PRINTF(4)("drawing the 3D-Models\n");
155
156  for(unsigned int i = 0; i < _modelGroups.size(); ++i )
157  {
158    PRINTF(5)("Drawing model %s\n", _modelGroups[i].name.c_str());
159    glCallList (_modelGroups[i].listNumber);
160  }
161}
162
163
164/**
165 * @brief Draws the Model number groupNumber
166 * @param groupNumber The number of the group that will be displayed.
167 *
168 * It does this by just calling the List that must have been created earlier.
169 */
170void StaticModelData::draw (unsigned int groupNumber) const
171{
172  if (unlikely(groupNumber >= _modelGroups.size()))
173  {
174    PRINTF(2)("You requested model number %i, but this File only contains of %i Models.\n", groupNumber-1, _modelGroups.size());
175    return;
176  }
177  else
178  {
179    PRINTF(4)("Drawing model number %i named %s\n", groupNumber, _modelGroups[groupNumber].name.c_str());
180    glCallList (_modelGroups[groupNumber].listNumber);
181  }
182}
183
184
185/**
186 * @brief Draws the Model with a specific groupName
187 * @param groupName The name of the group that will be displayed.
188 *
189 * It does this by just calling the List that must have been created earlier.
190 */
191void StaticModelData::draw (const std::string& groupName) const
192{
193  PRINTF(4)("drawing the requested 3D-Models if found.\n");
194  std::vector<Group>::const_iterator it = std::find(_modelGroups.begin(), _modelGroups.end(), groupName);
195
196  if (it != _modelGroups.end())
197  {
198    PRINTF(4)("Drawing model %s\n", (*it).name.c_str());
199    glCallList ((*it).listNumber);
200  }
201  else
202  {
203    PRINTF(2)("Model Named %s in %s not Found.\n", groupName.c_str(), this->getCName());
204  }
205}
206
207//////////
208// INIT //
209//////////
210
211/**
212 * @brief finalizes an Model.
213 *
214 * This funcion is needed, to delete all the Lists, and arrays that are no more
215 * needed because they are already imported into openGL.
216 * This will be applied at the end of the importing Process.
217*/
218bool StaticModelData::cleanup()
219{
220  PRINTF(4)("cleaning up the 3D-Model to save Memory.\n");
221  for (unsigned int i = 0; i < _modelGroups.size(); ++i)
222    _modelGroups[i].cleanup();
223  return true;
224}
225
226//////////
227// MESH //
228//////////
229/**
230 * @brief adds a new Material to the Material List
231 * @param material the Material to add
232 * @returns the added material
233 *
234 * this also tells this Model, that all the Materials are handled externally
235 * with this option set the Materials will not be deleted with the Model.
236 */
237Material* StaticModelData::addMaterial(const Material& material)
238{
239  this->materialList.push_back(material);
240  return &materialList.back();
241}
242
243/**
244 * @brief adds a new Material to the Material List
245 * @param materialName the name of the Material to add
246 * @returns the added material
247 */
248Material* StaticModelData::addMaterial(const std::string& materialName)
249{
250  // adding material to the List of materials
251  this->materialList.push_back(Material(materialName));
252  return &materialList.back();
253}
254
255/**
256 * @brief finds a Material by its name and returns it
257 * @param materialName the Name of the material to search for.
258 * @returns the Material if found, NULL otherwise
259 */
260Material* StaticModelData::findMaterialByName(const std::string& materialName)
261{
262  std::list<Material>::iterator it = std::find(materialList.begin(), materialList.end(), materialName);
263  if (it != materialList.end())
264    return &(*it);
265  else
266    return NULL;
267}
268
269/**
270 * @brief parses a group String
271 * @param groupString the new Group to create
272 *
273 * This function initializes a new Group.
274 * With it you should be able to create Models with more than one SubModel inside
275 */
276bool StaticModelData::addGroup(const std::string& groupString)
277{
278  PRINTF(5)("Read Group: %s.\n", groupString.c_str());
279  if (!_modelGroups.empty() && !_modelGroups.back()._faces.empty())
280    _modelGroups.push_back(Group());
281
282  if (groupString == "default")
283    _modelGroups.back().name = groupString;
284  // setting the group name if not default.
285  return true;
286}
287
288/**
289 * @brief parses a vertex-String
290 * @param vertexString The String that will be parsed.
291 *
292 *  If a vertex line is found this function will inject it into the vertex-Array
293 */
294bool StaticModelData::addVertex (const std::string& vertexString)
295{
296  float subbuffer1;
297  float subbuffer2;
298  float subbuffer3;
299  sscanf (vertexString.c_str(), "%f %f %f", &subbuffer1, &subbuffer2, &subbuffer3);
300  this->vertices.push_back(subbuffer1*scaleFactor);
301  this->vertices.push_back(subbuffer2*scaleFactor);
302  this->vertices.push_back(subbuffer3*scaleFactor);
303  return true;
304}
305
306/**
307 * @brief parses a vertex-String
308 * @param x the X-coordinate of the Vertex to add.
309 * @param y the Y-coordinate of the Vertex to add.
310 * @param z the Z-coordinate of the Vertex to add.
311 */
312bool StaticModelData::addVertex(float x, float y, float z)
313{
314  PRINTF(5)("reading in a vertex: %f %f %f\n", x, y, z);
315  this->vertices.push_back(x*scaleFactor);
316  this->vertices.push_back(y*scaleFactor);
317  this->vertices.push_back(z*scaleFactor);
318  return true;
319}
320
321/**
322 * @brief parses a vertexNormal-String
323 * @param normalString The String that will be parsed.
324 *
325 * If a vertexNormal line is found this function will inject it into the vertexNormal-Array
326 */
327bool StaticModelData::addVertexNormal (const std::string& normalString)
328{
329  float subbuffer1;
330  float subbuffer2;
331  float subbuffer3;
332  sscanf (normalString.c_str(), "%f %f %f", &subbuffer1, &subbuffer2, &subbuffer3);
333  this->normals.push_back(subbuffer1);
334  this->normals.push_back(subbuffer2);
335  this->normals.push_back(subbuffer3);
336  return true;
337}
338
339/**
340 * @brief adds a VertexNormal.
341 * @param x The x coordinate of the Normal.
342 * @param y The y coordinate of the Normal.
343 * @param z The z coordinate of the Normal.
344 *
345 * If a vertexNormal line is found this function will inject it into the vertexNormal-Array
346 */
347bool StaticModelData::addVertexNormal(float x, float y, float z)
348{
349  PRINTF(5)("found vertex-Normal %f, %f, %f\n", x, y, z);
350  this->normals.push_back(x);
351  this->normals.push_back(y);
352  this->normals.push_back(z);
353  return true;
354}
355
356/**
357 * @brief parses a vertexTextureCoordinate-String
358 * @param vTextureString The String that will be parsed.
359 *
360 * If a vertexTextureCoordinate line is found,
361 * this function will inject it into the vertexTexture-Array
362 *
363 * !! WARNING THIS IS DIFFERNT FROM addVervexTexture(float, float); because it changes the second entry to 1-v !!
364 */
365bool StaticModelData::addVertexTexture (const std::string& vTextureString)
366{
367  float subbuffer1;
368  float subbuffer2;
369  sscanf (vTextureString.c_str(), "%f %f", &subbuffer1, &subbuffer2);
370  this->vTexture.push_back(subbuffer1);
371  this->vTexture.push_back(1 - subbuffer2);
372  return true;
373}
374
375/**
376 * @brief adds a Texture Coordinate
377 * @param u The u coordinate of the TextureCoordinate.
378 * @param v The y coordinate of the TextureCoordinate.
379 *
380 * If a TextureCoordinate line is found this function will
381 *  inject it into the TextureCoordinate-Array
382 */
383bool StaticModelData::addVertexTexture(float u, float v)
384{
385  PRINTF(5)("found vertex-Texture %f, %f\n", u, v);
386  this->vTexture.push_back(u);
387  this->vTexture.push_back(v);
388  return true;
389}
390
391/**
392 * @brief parses a face-string
393 * @param faceString The String that will be parsed.
394 *
395 * If a face line is found this function will add it to the glList.
396 *
397 * String is different from the argument addFace,
398 * in this, that the first Vertex/Normal/Texcoord is 1 instead of 0
399 *
400 * @TODO make it std::string conform
401 */
402bool StaticModelData::addFace (const std::string& faceStringInput)
403{
404  const char* faceString = faceStringInput.c_str();
405  Face newFace;
406
407  while(strcmp (faceString, "\0"))
408  {
409    FaceElement newElem;
410
411    char tmpValue [50];
412    int tmpLen;
413    char* vertex = NULL;
414    char* texture = NULL;
415    char* normal = NULL;
416
417    sscanf (faceString, "%s", tmpValue);
418    tmpLen = strlen(tmpValue);
419    vertex = tmpValue;
420
421    if ((texture = strstr (vertex, "/")) != NULL)
422    {
423      texture[0] = '\0';
424      texture ++;
425
426      if ((normal = strstr (texture, "/")) !=NULL)
427      {
428        normal[0] = '\0';
429        normal ++;
430      }
431    }
432    if (vertex)
433      newElem.vertexNumber = atoi(vertex)-1;
434    if (texture)
435      newElem.texCoordNumber = atoi(texture)-1;
436    if (normal)
437      newElem.normalNumber = atoi(normal)-1;
438
439    faceString += tmpLen;
440    if (strcmp (faceString, "\0"))
441      faceString++;
442
443    newFace._elements.push_back(newElem);
444  }
445
446  //this->currentGroup->faceCount += this->currentGroup->currentFace->vertexCount -2;
447  _modelGroups.back()._faces.push_back(newFace);
448  this->faceCount += newFace._elements.size() - 2;
449  return true;
450}
451
452/**
453 * @brief adds a new Face
454 * @param faceElemCount the number of Vertices to add to the Face.
455 * @param type The information Passed with each Vertex
456*/
457bool StaticModelData::addFace(int faceElemCount, VERTEX_FORMAT type, va_list args)
458{
459  Face newFace;
460
461  for (int i = 0; i < faceElemCount; i++)
462  {
463    FaceElement newElem;
464
465    newElem.vertexNumber = va_arg (args, int);
466    if (type & TEXCOORD)
467      newElem.texCoordNumber = va_arg (args, int);
468    if (type & NORMAL)
469      newElem.normalNumber = va_arg(args, int);
470
471    newFace._elements.push_back(newElem);
472  }
473
474  //this->currentGroup->faceCount += this->currentGroup->currentFace->vertexCount -2;
475  _modelGroups.back()._faces.push_back(newFace);
476  this->faceCount += newFace._elements.size() - 2;
477  return true;
478}
479
480/**
481 * Function that selects a material, if changed in the obj file.
482 * @param matString the Material that will be set.
483*/
484bool StaticModelData::setMaterial(const std::string& matString)
485{
486  Face matFace;
487  matFace._material = this->findMaterialByName(matString);
488  _modelGroups.back()._faces.push_back(matFace);
489
490  return true;
491}
492
493/**
494 * Function that selects a material, if changed in the obj file.
495 * @param mtl the Material that will be set.
496*/
497bool StaticModelData::setMaterial(Material* mtl)
498{
499  Face matFace;
500  matFace._material = mtl;
501  _modelGroups.back()._faces.push_back(matFace);
502
503  return true;
504}
505
506/**
507 * @brief A routine that is able to create normals.
508 *
509 * The algorithm does the following:
510 * 1. It calculates creates Vectors for each normale, and sets them to zero.
511 * 2. It then Walks through a) all the Groups b) all the Faces c) all the FaceElements
512 * 3. It searches for a points two neighbours per Face, takes Vecotrs to them calculates FaceNormals and adds it to the Points Normal.
513 * 4. It goes through all the normale-Points and calculates the VertexNormale and includes it in the normals-Array.
514 */
515bool StaticModelData::buildVertexNormals ()
516{
517  PRINTF(4)("Normals are being calculated.\n");
518
519  Vector* normArray = new Vector [vertices.size()/3];
520  for (unsigned int i=0; i<vertices.size()/3;i++)
521    normArray[i] = Vector(.0,.0,.0);
522
523  Vector prevV;
524  Vector nextV;
525  Vector curV;
526
527  for (std::vector<Group>::iterator group = _modelGroups.begin();
528       group != _modelGroups.end();
529       ++group)
530  {
531    for (std::vector<Face>::iterator face = (*group)._faces.begin();
532         face != (*group)._faces.end();
533         ++face)
534    {
535      if (!(*face)._elements.empty())
536      {
537        std::vector<FaceElement>::iterator firstElem = (*face)._elements.begin();
538        std::vector<FaceElement>::iterator prevElem;
539        std::vector<FaceElement>::iterator curElem = firstElem;
540        std::vector<FaceElement>::iterator nextElem;
541        std::vector<FaceElement>::iterator lastElem;
542
543        // find last Element of the Chain.
544        while (curElem != (*face)._elements.end())
545        {
546          prevElem = curElem;
547          ++curElem;
548        }
549        lastElem = prevElem;
550
551        curElem = firstElem;
552        for (unsigned int j = 0; j < (*face)._elements.size(); j++)
553        {
554          nextElem = curElem;
555          nextElem++;
556          if (nextElem == (*face)._elements.end())
557            nextElem = firstElem;
558          (*curElem).normalNumber = (*curElem).vertexNumber;
559
560          curV = Vector (this->vertices[(*curElem).vertexNumber*3],
561                         this->vertices[(*curElem).vertexNumber*3+1],
562                         this->vertices[(*curElem).vertexNumber*3+2]);
563
564          prevV = Vector (this->vertices[(*prevElem).vertexNumber*3],
565                          this->vertices[(*prevElem).vertexNumber*3+1],
566                          this->vertices[(*prevElem).vertexNumber*3+2]) - curV;
567
568          nextV = Vector (this->vertices[(*nextElem).vertexNumber*3],
569                          this->vertices[(*nextElem).vertexNumber*3+1],
570                          this->vertices[(*nextElem).vertexNumber*3+2]) - curV;
571          normArray[(*curElem).vertexNumber] = normArray[(*curElem).vertexNumber] + nextV.cross(prevV);
572
573          prevElem = curElem;
574          ++curElem;
575        }
576      }
577    }
578  }
579
580  for (unsigned int i=0; i < this->vertices.size()/3;i++)
581  {
582    normArray[i].normalize();
583    PRINTF(5)("Found Normale number %d: (%f; %f, %f).\n", i, normArray[i].x, normArray[i].y, normArray[i].z);
584
585    this->addVertexNormal(normArray[i].x, normArray[i].y, normArray[i].z);
586
587  }
588  delete[] normArray;
589  return true;
590}
591
592////////////
593// openGL //
594////////////
595/**
596 *  reads and includes the Faces/Materials into the openGL state Machine
597*/
598bool StaticModelData::importToDisplayList()
599{
600  // finalize the Arrays
601  if (normals.size() == 0) // vertices-Array must be built for this
602    this->buildVertexNormals();
603
604  for (std::vector<Group>::iterator group = _modelGroups.begin();
605       group != _modelGroups.end();
606       ++group)
607  {
608
609    // creating a glList for the Group
610    if (((*group).listNumber = glGenLists(1)) == 0)
611    {
612      PRINTF(2)("glList could not be created for this Model\n");
613      return false;
614    }
615    glNewList ((*group).listNumber, GL_COMPILE);
616
617    // Putting Faces to GL
618    for (std::vector<Face>::const_iterator face = (*group)._faces.begin();
619         face != (*group)._faces.end();
620         ++face)
621    {
622      if ((*face)._elements.empty() && (*face)._material != NULL)
623      {
624        if ((*group).faceMode != -1)
625          glEnd();
626        (*group).faceMode = 0;
627        if ((*face)._material != NULL)
628        {
629          (*face)._material->select();
630          PRINTF(5)("using material %s for coming Faces.\n", (*face)._material->getCName());
631        }
632      }
633
634      else if ((*face)._elements.size() == 3)
635      {
636        if ((*group).faceMode != 3)
637        {
638          if ((*group).faceMode != -1)
639            glEnd();
640          glBegin(GL_TRIANGLES);
641        }
642
643        (*group).faceMode = 3;
644        PRINTF(5)("found triag.\n");
645      }
646
647      else if ((*face)._elements.size() == 4)
648      {
649        if ((*group).faceMode != 4)
650        {
651          if ((*group).faceMode != -1)
652            glEnd();
653          glBegin(GL_QUADS);
654        }
655        (*group).faceMode = 4;
656        PRINTF(5)("found quad.\n");
657      }
658
659      else if ((*face)._elements.size() > 4)
660      {
661        if ((*group).faceMode != -1)
662          glEnd();
663        glBegin(GL_POLYGON);
664        PRINTF(5)("Polygon with %i faces found.", (*face)._elements.size());
665        (*group).faceMode = (*face)._elements.size();
666      }
667
668      for (std::vector<FaceElement>::const_iterator elem = (*face)._elements.begin();
669           elem != (*face)._elements.end();
670           ++elem)
671      {
672        //      PRINTF(2)("%s\n", (*elem).value);
673        this->addGLElement(*elem);
674      }
675    }
676    glEnd();
677    glEndList();
678
679  }
680  return true;
681}
682
683
684/**
685 *  builds an array of triangles, that can later on be used for obb separation and octree separation
686 */
687bool StaticModelData::buildTriangleList()
688{
689  if( unlikely(!this->triangles.empty()))
690    return true;
691  /* make sure, that all the arrays are finalized */
692  if( normals.size() == 0) // vertices-Array must be built for this
693    this->buildVertexNormals();
694
695  int                index = 0;                   //!< the counter for the triangle array
696  unsigned int numTriangles = 0;
697  bool warned = false;
698
699  /* count the number of triangles */
700  /* now iterate through all groups and build up the triangle list */
701  for (std::vector<Group>::iterator group = _modelGroups.begin();
702       group != _modelGroups.end();
703       ++group)
704  {
705    for (std::vector<Face>::const_iterator face = (*group)._faces.begin();
706         face != (*group)._faces.end();
707         ++face)
708    {
709      /* if its a triangle just add it to the list */
710      if( (*face)._elements.size() == 3)
711      {
712        ++numTriangles;
713      } /* if the polygon is a quad */
714      else if((*face)._elements.size() == 4)
715      {
716        numTriangles += 2;
717      }
718      else if( (*face)._elements.size() > 4)
719      {
720        if (!warned)
721        {
722          PRINTF(2)("This model (%s) got over 4 vertices per face <=> conflicts in the CD engine!\n", this->getCName());
723          warned = true;
724        }
725      }
726    }
727  }
728
729  PRINTF(3)("got %i triangles, %i vertices\n", numTriangles, this->vertices.size());
730
731
732  /* write MODELINFO structure */
733
734  /* allocate memory for the new triangle structures */
735  this->triangles.resize(numTriangles);
736
737  /* now iterate through all groups and build up the triangle list */
738  for (std::vector<Group>::iterator group = _modelGroups.begin();
739       group != _modelGroups.end();
740       ++group)
741  {
742    for (std::vector<Face>::const_iterator face = (*group)._faces.begin();
743         face != (*group)._faces.end();
744         ++face)
745    {
746      /* if its a triangle just add it to the list */
747      if( (*face)._elements.size() == 3)
748      {
749        unsigned int j = 0;
750        for (std::vector<FaceElement>::const_iterator elem = (*face)._elements.begin();
751             elem != (*face)._elements.end();
752             ++elem)
753        {
754          this->triangles[index].indexToVertices[j] = (unsigned int)(*elem).vertexNumber * 3;
755          this->triangles[index].indexToNormals[j] = (unsigned int)(*elem).normalNumber * 3;
756          this->triangles[index].indexToTexCoor[j] = (unsigned int)(*elem).texCoordNumber * 3;
757          ++j;
758        }
759        ++index;
760      } /* if the polygon is a quad */
761
762      else if( (*face)._elements.size() == 4)
763      {
764        std::vector<FaceElement>::const_iterator elem = (*face)._elements.begin();
765
766        this->triangles[index].indexToVertices[0] = (unsigned int)(*elem).vertexNumber * 3;
767        this->triangles[index].indexToNormals[0] = (unsigned int)(*elem).normalNumber * 3;
768        this->triangles[index].indexToTexCoor[0] = (unsigned int)(*elem).texCoordNumber * 3;
769
770        this->triangles[index + 1].indexToVertices[0] = (unsigned int)(*elem).vertexNumber * 3;
771        this->triangles[index + 1].indexToNormals[0] = (unsigned int)(*elem).normalNumber * 3;
772        this->triangles[index + 1].indexToTexCoor[0] = (unsigned int)(*elem).texCoordNumber * 3;
773        ++elem;
774
775        this->triangles[index].indexToVertices[1] = (unsigned int)(*elem).vertexNumber * 3;
776        this->triangles[index].indexToNormals[1] = (unsigned int)(*elem).normalNumber * 3;
777        this->triangles[index].indexToTexCoor[1] = (unsigned int)(*elem).texCoordNumber * 3;
778        ++elem;
779
780        this->triangles[index].indexToVertices[2] = (unsigned int)(*elem).vertexNumber * 3;
781        this->triangles[index].indexToNormals[2] = (unsigned int)(*elem).normalNumber * 3;
782        this->triangles[index].indexToTexCoor[2] = (unsigned int)(*elem).texCoordNumber * 3;
783
784        this->triangles[index + 1].indexToVertices[2] = (unsigned int)(*elem).vertexNumber * 3;
785        this->triangles[index + 1].indexToNormals[2] = (unsigned int)(*elem).normalNumber * 3;
786        this->triangles[index + 1].indexToTexCoor[2] = (unsigned int)(*elem).texCoordNumber * 3;
787        ++elem;
788
789        this->triangles[index + 1].indexToVertices[1] = (unsigned int)(*elem).vertexNumber * 3;
790        this->triangles[index + 1].indexToNormals[1] = (unsigned int)(*elem).normalNumber * 3;
791        this->triangles[index + 1].indexToTexCoor[1] = (unsigned int)(*elem).texCoordNumber * 3;
792
793        index += 2;
794      }
795    }
796  }
797  return true;
798}
799
800
801/**
802 *  Adds a Face-element (one vertex of a face) with all its information.
803 * @param elem The FaceElement to add to the OpenGL-environment.
804
805   It does this by searching:
806   1. The Vertex itself
807   2. The VertexNormale
808   3. The VertexTextureCoordinate
809   merging this information, the face will be drawn.
810*/
811bool StaticModelData::addGLElement (const FaceElement& elem)
812{
813  PRINTF(5)("importing grafical Element to openGL.\n");
814
815  if (elem.texCoordNumber > -1)
816  {
817    if (likely((unsigned int)elem.texCoordNumber < this->vTexture.size()))
818      glTexCoord2fv(&this->vTexture[0] + elem.texCoordNumber * 2);
819    else
820      PRINTF(2)("TextureCoordinate %d is not in the List (max: %d)\nThe Model might be incomplete\n",
821                elem.texCoordNumber, this->vTexture.size());
822  }
823  if (elem.normalNumber > -1)
824  {
825    if (likely((unsigned int)elem.normalNumber < this->normals.size()))
826      glNormal3fv(&this->normals[0] + elem.normalNumber * 3);
827    else
828      PRINTF(2)("Normal %d is not in the List (max: %d)\nThe Model might be incomplete",
829                elem.normalNumber, this->normals.size());
830  }
831  if (elem.vertexNumber > -1)
832  {
833    if (likely((unsigned int)elem.vertexNumber < this->vertices.size()))
834      glVertex3fv(&this->vertices[0]+ elem.vertexNumber * 3);
835    else
836      PRINTF(2)("Vertex %d is not in the List (max: %d)\nThe Model might be incomplete",
837                elem.vertexNumber, this->vertices.size());
838  }
839
840  return true;
841}
Note: See TracBrowser for help on using the repository browser.