MayaParser.cc

Go to the documentation of this file.
00001 #include <esg/parser/MayaParser.h>
00002 #include <esg/Shape.h>
00003 #include <esg/Group.h>
00004 #include <esg/spacesorting/BVH.h>
00005 
00006 #include <assert.h>
00007 #include <time.h>
00008 
00009 using namespace esg;
00010 
00011 void MayaParser::_set_material(const GLMmaterial& glmMat)
00012 {
00013     Vector3  ambient(glmMat.ambient[0] * glmMat.ambient[3],
00014                      glmMat.ambient[1] * glmMat.ambient[3],
00015                      glmMat.ambient[2] * glmMat.ambient[3]);
00016     Vector3  diffuse(glmMat.diffuse[0] * glmMat.diffuse[3],
00017                      glmMat.diffuse[1] * glmMat.diffuse[3],
00018                      glmMat.diffuse[2] * glmMat.diffuse[3]);
00019     Vector3  specular(glmMat.specular[0] * glmMat.specular[3],
00020                       glmMat.specular[1] * glmMat.specular[3],
00021                       glmMat.specular[2] * glmMat.specular[3]);
00022     float shininess = glmMat.shininess; // in the range of [0,128] !
00023 
00024 #ifndef WIN32
00025 #warning "TODO: Shared material insted of privite"
00026 #else
00027 //#pragma warning "TODO: Shared material insted of privite"
00028 #endif
00029     _pParsedObject->appendPrivateMaterial(new Specular(specular));
00030     _pParsedObject->appendPrivateMaterial(new Diffuse(diffuse));
00031     _pParsedObject->appendPrivateMaterial(new Ambient(ambient));
00032     _pParsedObject->appendPrivateMaterial(new Roughness((int)shininess));
00033 }
00034 
00035 bool MayaParser::_parse_triangle(Surface* pSurface, GLMtriangle* pGLMTri)
00036 {
00037     pSurface->normal(Vector3(_pGLMModel->facetnorms[3 * pGLMTri->findex + 0],
00038                              _pGLMModel->facetnorms[3 * pGLMTri->findex + 1],
00039                              _pGLMModel->facetnorms[3 * pGLMTri->findex + 2]));
00040 
00041     // The reason of index decrementaion is explained in
00042     // attention comment in constructor's source code.
00043     if (!pSurface->vertex(pGLMTri->vindices[0]-1,
00044                           pGLMTri->nindices[0]-1,
00045                           pGLMTri->tindices[0]-1)) return false;
00046     if (!pSurface->vertex(pGLMTri->vindices[1]-1,
00047                           pGLMTri->nindices[1]-1,
00048                           pGLMTri->tindices[1]-1)) return false;
00049     if (!pSurface->vertex(pGLMTri->vindices[2]-1,
00050                           pGLMTri->nindices[2]-1,
00051                           pGLMTri->tindices[2]-1)) return false;
00052 
00053     if (_pStat) _pStat->primitives++; // increment counter
00054 
00055     return true;
00056 }
00057 
00058 void MayaParser::_init_model(bool unitize) const
00059 {
00060     glmFacetNormals(_pGLMModel);
00061     glmVertexNormals(_pGLMModel, VERT_NORMAL_DEGREE_TRESHOLD);
00062     if (unitize) glmUnitize(_pGLMModel);
00063     if (!_pGLMModel->texcoords) glmSpheremapTexture(_pGLMModel);
00064     assert(_pGLMModel);
00065     assert(_pGLMModel->vertices);
00066 }
00067 
00068 MayaParser::MayaParser(const char*           path,
00069                        const SDS&            proto,
00070                        SceneGraphObject::OID firstOID,
00071                        Parser::Statistics*   pStat,
00072                        bool                  unitize,
00073                        bool                  fastMesh)
00074     : Parser(path, proto, firstOID, pStat)
00075 {
00076     _pGLMModel = glmReadOBJ(path);
00077     _pGLMGroup = _pGLMModel->groups;
00078     _fastMesh  = fastMesh;
00079 
00080     if (_pGLMModel) _init_model(unitize);
00081 
00082     // set global arrays
00083     // ATTENTION: glm stores vertices and normals absolutely unreaseonably.
00084     //            It stores them in the range
00085     //            [3, 3*numvertices+1] and the first coordinates
00086     //            (that is index 0,1 and 2) are not used!!!
00087     //            Therefore such a strange indexing here.
00088     Vertex3* vertArray = new Vertex3 [_pGLMModel->numvertices];
00089     Vector3* normArray = new Vector3 [_pGLMModel->numnormals];
00090     Vector2* texArray  = new Vector2 [_pGLMModel->numtexcoords];
00091     for (unsigned i = 1; i <= _pGLMModel->numvertices; i++) {
00092         vertArray[i-1].x = _pGLMModel->vertices[3*i+0];
00093         vertArray[i-1].y = _pGLMModel->vertices[3*i+1];
00094         vertArray[i-1].z = _pGLMModel->vertices[3*i+2];
00095         //fprintf(stderr,"%i: %f %f %f\n",i,vertArray[i].x,vertArray[i].y,vertArray[i].z);
00096     }
00097     for (unsigned i = 1; i <= _pGLMModel->numnormals; i++) {
00098         normArray[i-1].x = _pGLMModel->normals[3*i+0];
00099         normArray[i-1].y = _pGLMModel->normals[3*i+1];
00100         normArray[i-1].z = _pGLMModel->normals[3*i+2];
00101     }
00102     for (unsigned i = 1; i <= _pGLMModel->numtexcoords; i++) {
00103         texArray[i-1].x = _pGLMModel->texcoords[2*i+0];
00104         texArray[i-1].y = _pGLMModel->texcoords[2*i+1];
00105     }
00106     _pAutoVertices  = new AutoArray<Vertex3>(vertArray);
00107     _pAutoNormals   = new AutoArray<Vector3>(normArray);
00108     _pAutoTexCoords = new AutoArray<Vector2>(texArray);
00109     _pAutoVertices->registerReferer(this);
00110     _pAutoNormals->registerReferer(this);
00111     _pAutoTexCoords->registerReferer(this);
00112 
00113     if (_pStat) {
00114         _pStat->vertices    = _pGLMModel->numvertices;
00115         _pStat->vertNormals = _pGLMModel->numnormals;
00116     }
00117 }
00118 
00119 MayaParser::~MayaParser()
00120 {
00121     if (_pGLMModel) delete _pGLMModel;
00122     AutoArray<Vertex3>::destroy(_pAutoVertices, this);
00123     AutoArray<Vector3>::destroy(_pAutoNormals, this);
00124     AutoArray<Vector2>::destroy(_pAutoTexCoords, this);
00125 }
00126 
00127 bool MayaParser::parseObject(void)
00128 {
00129     if (!_pGLMModel || !_pGLMGroup || !_pSSProto) {
00130         _pParsedObject = NULL;
00131         return false;
00132     }
00133 
00134     if (_pGLMGroup->numtriangles) {
00135         GLMtriangle* pGLMTri;
00136 
00137         if (_pGLMGroup->name)
00138             _pParsedObject = new Shape(_oid++, _pGLMGroup->name);
00139         else
00140             _pParsedObject = new Shape(_oid++, "Polygonal Surface");
00141 
00142         // set materials of _pParsedObject
00143         _set_material(_pGLMModel->materials[_pGLMGroup->material]);
00144 
00145         // set geometry
00146         Surface * pS = new Surface(*_pSSProto,
00147                                    _pAutoVertices,
00148                                    _pGLMModel->numvertices,
00149                                    _pAutoNormals,
00150                                    _pGLMModel->numnormals,
00151                                    _pAutoTexCoords,
00152                                    _pGLMModel->numtexcoords,
00153                                    Surface::TRIANGLES,
00154                                    new AutoPtr<Intersector>(new Intersector),
00155                                    _fastMesh);
00156         
00157         for (register unsigned i = 0; i < _pGLMGroup->numtriangles; i++) {
00158             // get actual triangle in group
00159             pGLMTri = &(_pGLMModel->triangles[_pGLMGroup->triangles[i]]);
00160             if (!_parse_triangle(pS, pGLMTri)) {
00161                 fprintf(stderr,"MayaParser Error: Wrong data format\n");
00162                 delete pS;
00163                 return false;
00164             }
00165         }
00166 
00167         pS->done();
00168         _pParsedObject->setPrivateGeometry(pS);
00169         _pGLMGroup = _pGLMGroup->next;
00170         return true;
00171     } else {
00172         _pParsedObject = NULL;
00173         _pGLMGroup = _pGLMGroup->next;
00174         return false;
00175     }
00176 }

Generated on Wed Jun 28 12:24:31 2006 for esg by  doxygen 1.4.6