$search
00001 00002 #include <blort/Tracker/ModelLoader.h> 00003 #include <stdexcept> 00004 00005 using namespace Tracking; 00006 using namespace TomGine; 00007 using namespace std; 00008 00009 // *** PRIVATE *** 00010 00011 // Tests if property of file is available in list (data structure) 00012 bool ModelLoader::propertyIsInList(PlyProperty* prop, PlyProperty* list, int n, int* index){ 00013 00014 for(int i=0; i<n; i++){ 00015 if(equal_strings(prop->name, list[i].name)){ 00016 *index = i; 00017 return true; 00018 } 00019 } 00020 return false; 00021 } 00022 00023 // *** PUBLIC *** 00024 00025 ModelLoader::ModelLoader(){ 00026 } 00027 00028 ModelLoader::~ModelLoader(){ 00029 00030 } 00031 00032 // read ply file 00033 bool ModelLoader::LoadPly(TomGine::tgModel &model, const char* filename){ 00034 PlyFile* plyfile; 00035 int i,j; 00036 int nelems; 00037 char **elist; 00038 int file_type; 00039 float version; 00040 char *elem_name; 00041 //PlyElement *elem_ptr; 00042 PlyProperty **plist; 00043 //PlyProperty* prop_ptr; 00044 int num_elems; 00045 int nprops; 00046 int index; 00047 char** obj_info; 00048 int num_obj_info; 00049 00050 int num_vertices = 0; 00051 int num_faces = 0; 00052 // int num_edges; 00053 PlyVertex* plyvertexlist = 0; 00054 PlyFace* plyfacelist = 0; 00055 PlyEdge* plyedgelist = 0; 00056 vector<string> texFilenames; 00057 string strFilename(filename); 00058 00059 00060 // ********************************************** 00061 // Read data from ply file 00062 00063 // open file 00064 plyfile = ply_open_for_reading((char*)filename, &nelems, &elist, &file_type, &version); 00065 if(plyfile==0){ 00066 char errmsg[128]; 00067 sprintf(errmsg, "[ModelLoader::LoadPly] Error loading ply file %s\n", filename); 00068 throw std::runtime_error(errmsg); 00069 } 00070 // sprintf(model.m_modelname, "%s", filename); 00071 00072 // Load texture files from obj_info (=texture-filename) 00073 obj_info = ply_get_obj_info(plyfile, &num_obj_info); 00074 if(num_obj_info < 1){ 00075 //printf("[ModelLoader::read] Warning no texture found in model %s\n", filename); 00076 }else if(num_obj_info >= 1){ 00077 for(i=0; i<num_obj_info; i++){ 00078 texFilenames.push_back(""); 00079 texFilenames[i].append(filename, 0, strFilename.find_last_of("/")+1); 00080 texFilenames[i].append(obj_info[i]); 00081 // printf("[ModelLoader::read] obj_info: %s\n", texFilenames[i].c_str()); 00082 } 00083 } 00084 00085 // list of property information for a vertex 00086 PlyProperty vert_props[] = { 00087 {(char*)"x", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,x), 0, 0, 0, 0}, 00088 {(char*)"y", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,y), 0, 0, 0, 0}, 00089 {(char*)"z", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,z), 0, 0, 0, 0}, 00090 {(char*)"nx", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,nx), 0, 0, 0, 0}, 00091 {(char*)"ny", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,ny), 0, 0, 0, 0}, 00092 {(char*)"nz", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,nz), 0, 0, 0, 0}, 00093 {(char*)"s", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,s), 0, 0, 0, 0}, 00094 {(char*)"t", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,t), 0, 0, 0, 0}, 00095 {(char*)"red", PLY_UCHAR, PLY_UCHAR, offsetof(PlyVertex,r), 0, 0, 0, 0}, 00096 {(char*)"green", PLY_UCHAR, PLY_UCHAR, offsetof(PlyVertex,g), 0, 0, 0, 0}, 00097 {(char*)"blue", PLY_UCHAR, PLY_UCHAR, offsetof(PlyVertex,b), 0, 0, 0, 0} 00098 }; 00099 00100 // list of property information for a face 00101 PlyProperty face_props[] = { /* list of property information for a vertex */ 00102 {(char*)"vertex_indices", PLY_USHORT, PLY_UINT, offsetof(PlyFace,v), 00103 1, PLY_USHORT, PLY_UINT, offsetof(PlyFace,nverts)}, 00104 }; 00105 00106 // list of property information for an edge 00107 PlyProperty edge_props[] = { 00108 {(char*)"start", PLY_USHORT, PLY_USHORT, offsetof(PlyEdge,start), 0, 0, 0, 0}, 00109 {(char*)"end", PLY_USHORT, PLY_USHORT, offsetof(PlyEdge,end), 0, 0, 0, 0} 00110 }; 00111 00112 for(i=0; i<nelems; i++){ 00113 // get description of element 00114 elem_name = elist[i]; 00115 plist = ply_get_element_description (plyfile, elem_name, &num_elems, &nprops); 00116 00117 // *** Read Vertices *** 00118 if (equal_strings ((char*)"vertex", elem_name)) { 00119 // allocate memory for vertices 00120 num_vertices = num_elems; 00121 plyvertexlist = (PlyVertex*)malloc(sizeof(PlyVertex) * num_vertices); 00122 00123 // setup property specification for elements 00124 for(j=0; j<nprops; j++){ 00125 if(propertyIsInList(plist[j], vert_props, 11, &index)) 00126 ply_get_property(plyfile, elem_name, &vert_props[index]); 00127 } 00128 00129 // grab all vertex elements 00130 for(j=0; j<num_elems; j++){ 00131 ply_get_element(plyfile, &plyvertexlist[j]); 00132 } 00133 00134 } 00135 00136 // *** Read Faces *** 00137 if (equal_strings ((char*)"face", elem_name)) { 00138 // allocate memory for faces 00139 num_faces = num_elems; 00140 plyfacelist = (PlyFace*)malloc(sizeof(PlyFace)*num_faces); 00141 00142 // setup property specification for elements 00143 for(j=0; j<nprops && j<1; j++){ 00144 ply_get_property(plyfile, elem_name, &face_props[j]); 00145 } 00146 00147 // grab all face elements 00148 for(j=0; j<num_elems; j++){ 00149 ply_get_element(plyfile, &plyfacelist[j]); 00150 //printf ("face: %d %d %d %d\n", m_facelist[j].v[0], m_facelist[j].v[1], m_facelist[j].v[2], m_facelist[j].v[3]); 00151 } 00152 } 00153 00154 // *** Read Edges *** 00155 if (equal_strings ((char*)"edge", elem_name)) { 00156 // allocate memory for edges 00157 plyedgelist = (PlyEdge*)malloc(sizeof(PlyEdge)*num_elems); 00158 //num_edges = num_elems; 00159 00160 // setup property specification for elements 00161 for(j=0; j<nprops && j<2; j++){ 00162 ply_get_property(plyfile, elem_name, &edge_props[j]); 00163 } 00164 00165 // grab all edge elements 00166 for(j=0; j<num_elems; j++){ 00167 ply_get_element(plyfile, &plyedgelist[j]); 00168 //printf("edge: %d %d\n", m_edgelist[j].start, m_edgelist[j].end); 00169 } 00170 } 00171 } 00172 ply_close(plyfile); 00173 00174 00175 // ********************************************** 00176 // Convert ply to model 00177 00178 // Parse through vertex list 00179 for(i=0; i<num_vertices; i++){ 00180 tgVertex v; 00181 v.pos.x = plyvertexlist[i].x; 00182 v.pos.y = plyvertexlist[i].y; 00183 v.pos.z = plyvertexlist[i].z; 00184 v.normal.x = plyvertexlist[i].nx; 00185 v.normal.y = plyvertexlist[i].ny; 00186 v.normal.z = plyvertexlist[i].nz; 00187 v.texCoord.x = plyvertexlist[i].s; 00188 v.texCoord.y = plyvertexlist[i].t; 00189 model.add(v); 00190 } 00191 00192 // Parse through face list 00193 for(i=0; i<num_faces; i++){ 00194 tgFace f; 00195 for(j=0; j<plyfacelist[i].nverts; j++){ 00196 f.v.push_back(plyfacelist[i].v[j]); 00197 } 00198 model.add(f); 00199 } 00200 00201 // for(i=0; i<num_edges; i++){ 00202 // Model::Edge e; 00203 // e.start = plyedgelist[i].start; 00204 // e.end = plyedgelist[i].end; 00205 // model.m_edgelist.push_back(e); 00206 // } 00207 00208 model.ComputeFaceNormals(); 00209 00210 // ********************************************** 00211 // Clean up 00212 if(plyvertexlist) free(plyvertexlist); 00213 if(plyfacelist) free(plyfacelist); 00214 if(plyedgelist) free(plyedgelist); 00215 00216 return true; 00217 } 00218 00219 bool ModelLoader::LoadPly(TrackerModel &model, const char* filename){ 00220 PlyFile* plyfile; 00221 int i,j; 00222 int nelems; 00223 char **elist; 00224 int file_type; 00225 float version; 00226 char *elem_name; 00227 //PlyElement *elem_ptr; 00228 PlyProperty **plist; 00229 //PlyProperty* prop_ptr; 00230 int num_elems; 00231 int nprops; 00232 int index; 00233 char** obj_info; 00234 int num_obj_info; 00235 00236 int num_vertices = 0; 00237 int num_faces = 0; 00238 // int num_edges; 00239 int num_passes = 0; 00240 PlyVertex* plyvertexlist = 0; 00241 PlyFace* plyfacelist = 0; 00242 PlyEdge* plyedgelist = 0; 00243 PlyPass* plypasslist = 0; 00244 vector<string> texFilenames; 00245 string strFilename(filename); 00246 00247 // ********************************************** 00248 // Read data from ply file 00249 // open file 00250 plyfile = ply_open_for_reading((char*)filename, &nelems, &elist, &file_type, &version); 00251 if(plyfile==0){ 00252 ROS_DEBUG("[ModelLoader::LoadPly] Failed to load ply file '%s'", filename); 00253 return false; 00254 } 00255 00256 // sprintf(model.m_modelname, "%s", filename); 00257 00258 // Load texture files from obj_info (=texture-filename) 00259 obj_info = ply_get_obj_info(plyfile, &num_obj_info); 00260 if(num_obj_info < 1){ 00261 //printf("[ModelLoader::read] Warning no texture found in model %s\n", filename); 00262 }else if(num_obj_info >= 1){ 00263 for(i=0; i<num_obj_info; i++){ 00264 texFilenames.push_back(""); 00265 texFilenames[i].append(filename, 0, strFilename.find_last_of("/")+1); 00266 texFilenames[i].append(obj_info[i]); 00267 // printf("[ModelLoader::read] obj_info: %s\n", texFilenames[i].c_str()); 00268 } 00269 } 00270 // list of property information for a vertex 00271 PlyProperty vert_props[] = { 00272 {(char*)"x", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,x), 0, 0, 0, 0}, 00273 {(char*)"y", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,y), 0, 0, 0, 0}, 00274 {(char*)"z", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,z), 0, 0, 0, 0}, 00275 {(char*)"nx", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,nx), 0, 0, 0, 0}, 00276 {(char*)"ny", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,ny), 0, 0, 0, 0}, 00277 {(char*)"nz", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,nz), 0, 0, 0, 0}, 00278 {(char*)"s", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,s), 0, 0, 0, 0}, 00279 {(char*)"t", PLY_FLOAT, PLY_FLOAT, offsetof(PlyVertex,t), 0, 0, 0, 0}, 00280 {(char*)"red", PLY_UCHAR, PLY_UCHAR, offsetof(PlyVertex,r), 0, 0, 0, 0}, 00281 {(char*)"green", PLY_UCHAR, PLY_UCHAR, offsetof(PlyVertex,g), 0, 0, 0, 0}, 00282 {(char*)"blue", PLY_UCHAR, PLY_UCHAR, offsetof(PlyVertex,b), 0, 0, 0, 0} 00283 }; 00284 00285 // list of property information for a face 00286 PlyProperty face_props[] = { /* list of property information for a vertex */ 00287 {(char*)"vertex_indices", PLY_USHORT, PLY_UINT, offsetof(PlyFace,v), 00288 1, PLY_USHORT, PLY_UINT, offsetof(PlyFace,nverts)}, 00289 }; 00290 00291 // list of property information for an edge 00292 PlyProperty edge_props[] = { 00293 {(char*)"start", PLY_USHORT, PLY_USHORT, offsetof(PlyEdge,start), 0, 0, 0, 0}, 00294 {(char*)"end", PLY_USHORT, PLY_USHORT, offsetof(PlyEdge,end), 0, 0, 0, 0} 00295 }; 00296 00297 PlyProperty pass_props[] = { 00298 {(char*)"face_indices", PLY_USHORT, PLY_UINT, offsetof(PlyPass,f), 00299 1, PLY_USHORT, PLY_UINT, offsetof(PlyPass,nfaces)}, 00300 {(char*)"m0", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m0), 0, 0, 0, 0}, 00301 {(char*)"m1", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m1), 0, 0, 0, 0}, 00302 {(char*)"m2", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m2), 0, 0, 0, 0}, 00303 {(char*)"m3", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m3), 0, 0, 0, 0}, 00304 {(char*)"m4", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m4), 0, 0, 0, 0}, 00305 {(char*)"m5", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m5), 0, 0, 0, 0}, 00306 {(char*)"m6", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m6), 0, 0, 0, 0}, 00307 {(char*)"m7", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m7), 0, 0, 0, 0}, 00308 {(char*)"m8", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m8), 0, 0, 0, 0}, 00309 {(char*)"m9", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m9), 0, 0, 0, 0}, 00310 {(char*)"m10", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m10), 0, 0, 0, 0}, 00311 {(char*)"m11", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m11), 0, 0, 0, 0}, 00312 {(char*)"m12", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m12), 0, 0, 0, 0}, 00313 {(char*)"m13", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m13), 0, 0, 0, 0}, 00314 {(char*)"m14", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m14), 0, 0, 0, 0}, 00315 {(char*)"m15", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,m15), 0, 0, 0, 0}, 00316 {(char*)"x", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,x), 0, 0, 0, 0}, 00317 {(char*)"y", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,y), 0, 0, 0, 0}, 00318 {(char*)"w", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,w), 0, 0, 0, 0}, 00319 {(char*)"h", PLY_FLOAT, PLY_FLOAT, offsetof(PlyPass,h), 0, 0, 0, 0}, 00320 {(char*)"tex_index", PLY_UCHAR, PLY_UCHAR, offsetof(PlyPass,tex), 0, 0, 0, 0} 00321 }; 00322 00323 for(i=0; i<nelems; i++){ 00324 // get description of element 00325 elem_name = elist[i]; 00326 plist = ply_get_element_description (plyfile, elem_name, &num_elems, &nprops); 00327 00328 // *** Read Vertices *** 00329 if (equal_strings ((char*)"vertex", elem_name)) { 00330 // allocate memory for vertices 00331 num_vertices = num_elems; 00332 plyvertexlist = (PlyVertex*)malloc(sizeof(PlyVertex) * num_vertices); 00333 00334 // setup property specification for elements 00335 for(j=0; j<nprops; j++){ 00336 if(propertyIsInList(plist[j], vert_props, 11, &index)) 00337 ply_get_property(plyfile, elem_name, &vert_props[index]); 00338 } 00339 00340 // grab all vertex elements 00341 for(j=0; j<num_elems; j++){ 00342 ply_get_element(plyfile, &plyvertexlist[j]); 00343 } 00344 00345 } 00346 00347 // *** Read Faces *** 00348 if (equal_strings ((char*)"face", elem_name)) { 00349 // allocate memory for faces 00350 num_faces = num_elems; 00351 plyfacelist = (PlyFace*)malloc(sizeof(PlyFace)*num_faces); 00352 00353 // setup property specification for elements 00354 for(j=0; j<nprops && j<1; j++){ 00355 ply_get_property(plyfile, elem_name, &face_props[j]); 00356 } 00357 00358 // grab all face elements 00359 for(j=0; j<num_elems; j++){ 00360 ply_get_element(plyfile, &plyfacelist[j]); 00361 //printf ("face: %d %d %d %d\n", m_facelist[j].v[0], m_facelist[j].v[1], m_facelist[j].v[2], m_facelist[j].v[3]); 00362 } 00363 } 00364 00365 // *** Read Edges *** 00366 if (equal_strings ((char*)"edge", elem_name)) { 00367 // allocate memory for edges 00368 plyedgelist = (PlyEdge*)malloc(sizeof(PlyEdge)*num_elems); 00369 //num_edges = num_elems; 00370 00371 // setup property specification for elements 00372 for(j=0; j<nprops && j<2; j++){ 00373 ply_get_property(plyfile, elem_name, &edge_props[j]); 00374 } 00375 00376 // grab all edge elements 00377 for(j=0; j<num_elems; j++){ 00378 ply_get_element(plyfile, &plyedgelist[j]); 00379 //printf("edge: %d %d\n", m_edgelist[j].start, m_edgelist[j].end); 00380 } 00381 } 00382 00383 // *** Read Pass *** 00384 if (equal_strings ((char*)"pass", elem_name)) { 00385 num_passes = num_elems; 00386 plypasslist = (PlyPass*)malloc(sizeof(PlyPass)*num_passes); 00387 00388 for(j=0; j<nprops; j++){ 00389 ply_get_property(plyfile, elem_name, &pass_props[j]); 00390 } 00391 00392 // grab all face elements 00393 for(j=0; j<num_passes; j++){ 00394 ply_get_element(plyfile, &plypasslist[j]); 00395 //printf ("face: %d %d %d %d\n", m_facelist[j].v[0], m_facelist[j].v[1], m_facelist[j].v[2], m_facelist[j].v[3]); 00396 } 00397 } 00398 00399 } 00400 ply_close(plyfile); 00401 00402 // ********************************************** 00403 // Convert ply to model 00404 00405 // Parse through vertex list 00406 for(i=0; i<num_vertices; i++){ 00407 tgVertex v; 00408 v.pos.x = plyvertexlist[i].x; 00409 v.pos.y = plyvertexlist[i].y; 00410 v.pos.z = plyvertexlist[i].z; 00411 v.normal.x = plyvertexlist[i].nx; 00412 v.normal.y = plyvertexlist[i].ny; 00413 v.normal.z = plyvertexlist[i].nz; 00414 v.texCoord.x = plyvertexlist[i].s; 00415 v.texCoord.y = plyvertexlist[i].t; 00416 model.add(v); 00417 } 00418 00419 // Parse through face list 00420 for(i=0; i<num_faces; i++){ 00421 tgFace f; 00422 for(j=0; j<plyfacelist[i].nverts; j++){ 00423 f.v.push_back(plyfacelist[i].v[j]); 00424 } 00425 model.add(f); 00426 } 00427 00428 // for(i=0; i<num_edges; i++){ 00429 // Model::Edge e; 00430 // e.start = plyedgelist[i].start; 00431 // e.end = plyedgelist[i].end; 00432 // model.m_edgelist.push_back(e); 00433 // } 00434 00435 for(i=0; i<num_passes; i++){ 00436 TrackerModel::Pass* p = new TrackerModel::Pass; 00437 00438 for(j=0; j<plypasslist[i].nfaces; j++){ 00439 p->f.push_back(plypasslist[i].f[j]); 00440 } 00441 00442 p->modelviewprojection.mat[0] = plypasslist[i].m0; 00443 p->modelviewprojection.mat[1] = plypasslist[i].m1; 00444 p->modelviewprojection.mat[2] = plypasslist[i].m2; 00445 p->modelviewprojection.mat[3] = plypasslist[i].m3; 00446 p->modelviewprojection.mat[4] = plypasslist[i].m4; 00447 p->modelviewprojection.mat[5] = plypasslist[i].m5; 00448 p->modelviewprojection.mat[6] = plypasslist[i].m6; 00449 p->modelviewprojection.mat[7] = plypasslist[i].m7; 00450 p->modelviewprojection.mat[8] = plypasslist[i].m8; 00451 p->modelviewprojection.mat[9] = plypasslist[i].m9; 00452 p->modelviewprojection.mat[10] = plypasslist[i].m10; 00453 p->modelviewprojection.mat[11] = plypasslist[i].m11; 00454 p->modelviewprojection.mat[12] = plypasslist[i].m12; 00455 p->modelviewprojection.mat[13] = plypasslist[i].m13; 00456 p->modelviewprojection.mat[14] = plypasslist[i].m14; 00457 p->modelviewprojection.mat[15] = plypasslist[i].m15; 00458 00459 p->x = plypasslist[i].x; 00460 p->y = plypasslist[i].y; 00461 p->w = plypasslist[i].w; 00462 p->h = plypasslist[i].h; 00463 00464 p->texture->load(texFilenames[i].c_str()); 00465 00466 model.m_passlist.push_back(p); 00467 } 00468 00469 if(!model.m_passlist.empty()) 00470 model.m_textured = true; 00471 00472 model.ComputeFaceNormals(); 00473 model.computeEdges(); 00474 model.Update(); 00475 00476 // ********************************************** 00477 // Clean up 00478 if(plyvertexlist) free(plyvertexlist); 00479 if(plyfacelist) free(plyfacelist); 00480 if(plyedgelist) free(plyedgelist); 00481 if(plypasslist) free(plypasslist); 00482 return true; 00483 } 00484 00485 bool ModelLoader::SavePly(TomGine::tgModel &model, const char* filename){ 00486 FILE* pFile; 00487 pFile = fopen(filename, "w"); 00488 //fputs("[ModelLoader::SavePly(Model)] Warning not implemented, use ModelLoader::SavePly(TrackerModel)", pFile); 00489 ROS_DEBUG("[ModelLoader::SavePly(Model)] Warning not implemented, use ModelLoader::SavePly(TrackerModel)"); 00490 00491 fclose(pFile); 00492 return true; 00493 } 00494 00495 bool ModelLoader::SavePly(TrackerModel &model, const char* name){ 00496 ROS_INFO("Saving model to %s", name); 00497 FILE* pFile = 0; 00498 unsigned i,j; 00499 string filename(name); 00500 string texname; 00501 string texfilename; 00502 char number[512]; 00503 00504 filename.append(".ply"); 00505 pFile = fopen(filename.c_str(), "w"); 00506 00507 if(!pFile){ 00508 ROS_ERROR("[ModelLoader::SavePly] Can not create file '%s'! Path existing?", name); 00509 throw std::runtime_error("[ModelLoader::SavePly] Can not create file! Path existing?"); 00510 } 00511 00512 // **************************************************** 00513 // Header 00514 fputs("ply\n", pFile); 00515 fputs("format ascii 1.0\n", pFile); 00516 00517 // Save filenames of textures (relative to ply file) 00518 for(i=0; i<model.m_passlist.size(); i++){ 00519 texname = string(""); 00520 texfilename = string(""); 00521 unsigned int start = filename.find_last_of("/"); 00522 if(start!=filename.npos){ 00523 string modelname(name); 00524 texname.append(modelname.begin()+start+1, modelname.end()); 00525 texfilename.append(modelname.begin(), modelname.begin()+start+1); 00526 }else{ 00527 texname = string(name); 00528 } 00529 00530 texname.append("-"); 00531 sprintf(number, "%.5d", i); 00532 texname.append(number); 00533 texname.append(".jpg"); 00534 texfilename.append(texname); 00535 fputs("obj_info ", pFile); 00536 fputs(texname.c_str(), pFile); 00537 fputs("\n", pFile); 00538 model.m_passlist[i]->texture->save(texfilename.c_str()); 00539 } 00540 00541 // Header of vertex 00542 sprintf(number, "%d", model.getVertexSize()); 00543 fputs("element vertex ", pFile); 00544 fputs(number, pFile); 00545 fputs("\n", pFile); 00546 fputs("property float x\n", pFile); 00547 fputs("property float y\n", pFile); 00548 fputs("property float z\n", pFile); 00549 fputs("property float nx\n", pFile); 00550 fputs("property float ny\n", pFile); 00551 fputs("property float nz\n", pFile); 00552 00553 // Header of face 00554 sprintf(number, "%d", model.getFaceSize()); 00555 fputs("element face ", pFile); 00556 fputs(number, pFile); 00557 fputs("\n", pFile); 00558 fputs("property list uchar uint vertex_indices\n", pFile); 00559 00560 00561 // Header of pass 00562 if(!model.m_passlist.empty()){ 00563 sprintf(number, "%d", (int)model.m_passlist.size()); 00564 fputs("element pass ", pFile); 00565 fputs(number, pFile); 00566 fputs("\n", pFile); 00567 fputs("property list uchar uint face_indices\n", pFile); // f 00568 fputs("property float m0\n", pFile); 00569 fputs("property float m1\n", pFile); 00570 fputs("property float m2\n", pFile); 00571 fputs("property float m3\n", pFile); 00572 fputs("property float m4\n", pFile); 00573 fputs("property float m5\n", pFile); 00574 fputs("property float m6\n", pFile); 00575 fputs("property float m7\n", pFile); 00576 fputs("property float m8\n", pFile); 00577 fputs("property float m9\n", pFile); 00578 fputs("property float m10\n", pFile); 00579 fputs("property float m11\n", pFile); 00580 fputs("property float m12\n", pFile); 00581 fputs("property float m13\n", pFile); 00582 fputs("property float m14\n", pFile); 00583 fputs("property float m15\n", pFile); 00584 fputs("property float x\n", pFile); 00585 fputs("property float y\n", pFile); 00586 fputs("property float w\n", pFile); 00587 fputs("property float h\n", pFile); 00588 fputs("property uchar tex_index\n", pFile); 00589 } 00590 00591 fputs("end_header\n",pFile); 00592 00593 // Data of vertex 00594 for(i=0; i<model.getVertexSize(); i++){ 00595 tgVertex v = model.getVertex(i); 00596 sprintf( number, "%f %f %f %f %f %f\n", 00597 v.pos.x, v.pos.y, v.pos.z, 00598 v.normal.x, v.normal.y, v.normal.z); 00599 fputs(number, pFile); 00600 } 00601 00602 // Data of face 00603 for(i=0; i<model.getFaceSize(); i++){ 00604 tgFace f = model.getFace(i); 00605 sprintf(number, "%d", (int)f.v.size()); 00606 fputs(number, pFile); 00607 for(j=0; j<f.v.size(); j++){ 00608 sprintf( number, " %d", f.v[j]); 00609 fputs(number, pFile); 00610 } 00611 fputs("\n", pFile); 00612 } 00613 00614 // Data of pass 00615 for(i=0; i<model.m_passlist.size(); i++){ 00616 TrackerModel::Pass* p = model.m_passlist[i]; 00617 sprintf(number, "%d", (int)p->f.size()); 00618 fputs(number, pFile); 00619 for(j=0; j<p->f.size(); j++){ // Facelist 00620 sprintf(number, " %d", p->f[j]); 00621 fputs(number, pFile); 00622 } 00623 for(j=0; j<16; j++){ 00624 sprintf(number, " %f", p->modelviewprojection.mat[j]); 00625 fputs(number, pFile); 00626 } 00627 sprintf(number, " %f %f %f %f", p->x, p->y, p->w, p->h); 00628 fputs(number, pFile); 00629 sprintf(number, " %d", i); 00630 fputs(number, pFile); 00631 fputs("\n", pFile); 00632 } 00633 00634 fclose(pFile); 00635 00636 printf("saved: %s\n", filename.c_str()); 00637 00638 return true; 00639 } 00640