00001
00002 #include <Mesh_object_loader.h>
00003
00004
00005 Mesh_object_loader::Mesh_object_loader(){}
00006 Mesh_object_loader::~Mesh_object_loader(){}
00007
00008
00009
00010 int Mesh_object_loader::load_obj_texture(const std::string& filename,Mesh_object* mesh) const
00011 {
00012
00013
00014
00015
00016 #define SIZE_BUFFER 2048
00017 char buffer[SIZE_BUFFER]={'\0'};
00018 char buffer2[SIZE_BUFFER]={'\0'};
00019
00020 FILE *fid=NULL;
00021 fid=fopen(filename.data(),"r");
00022 if(fid==NULL)
00023 {printf("ERROR loading %s in load_obj_texture in Mesh_object_helper\n",filename.data());exit(-1);}
00024
00025 float X[2];
00026 while(fscanf(fid,"%s",buffer)!=EOF)
00027 {
00028 if(strcmp(buffer,"vt")==0)
00029 {
00030 if(fscanf(fid,"%f %f\n",X,X+1)!=2)
00031 {printf("Error reading texture in load_obj_texture in Mesh_object_loader\n");exit(-1);}
00032 mesh->add_intermediate_texture(X[0],X[1]);
00033 }
00034 else
00035 fgets(buffer,sizeof(buffer),fid);
00036 }
00037
00038
00039 rewind(fid);
00040
00041
00042
00043 std::vector <int> poly;
00044 int ct=0;
00045 int one=-1;
00046 while(fscanf(fid,"%s",buffer)!=EOF)
00047 {
00048 switch(buffer[0])
00049 {
00050 case 'f':
00051 poly.resize(0);
00052 strcpy(buffer2,"\0");
00053 fscanf(fid,"%s",buffer2);
00054
00055 if(sscanf(buffer2,"%*d/%d/%*d",&ct)==1)
00056 {
00057 poly.push_back(ct+one);
00058 while(fscanf(fid,"%*d/%d/%*d",&ct)==1)
00059 poly.push_back(ct+one);
00060 mesh->add_polygon_texture(poly);
00061 }
00062 else if(sscanf(buffer2,"%*d/%d",&ct)==1)
00063 {
00064 poly.push_back(ct+one);
00065 while(fscanf(fid,"%d/%*d",&ct)==1)
00066 poly.push_back(ct+one);
00067 mesh->add_polygon_texture(poly);
00068 }
00069 else
00070 fgets(buffer,sizeof(buffer),fid);
00071 break;
00072 }
00073 }
00074
00075
00076
00077
00078
00079 if(fclose(fid)!=0)
00080 {printf("ERROR closing %s in load_obj_texture in Mesh_object_loader\n",filename.data());exit(-1);}
00081 return 0;
00082 }
00083
00084 int Mesh_object_loader::load_obj_texture(const char* filename,Mesh_object* mesh) const
00085 {std::string file=filename;return load_obj_texture(file,mesh);}
00086
00087
00088
00089 int Mesh_object_loader::load_collada_texture(const std::string& filename,Mesh_object* mesh,const std::string& name,const std::string& texture_source) const
00090 {
00091
00092 TiXmlDocument doc(filename);
00093 if(!doc.LoadFile())
00094 {
00095 printf("ERROR opening %s\n",filename.data());
00096 cerr << "error #" << doc.ErrorId() << " : " << doc.ErrorDesc() << endl;
00097 exit(-1);
00098 }
00099
00100
00101 TiXmlHandle root(doc.RootElement());
00102 TiXmlNode *lib_geometry=NULL;lib_geometry=root.ToNode();
00103 if(lib_geometry==NULL)
00104 {printf("Error reading file %s in load_collada_texture in Connectivity\n",filename.data());exit(-1);}
00105
00106
00107
00108 lib_geometry = lib_geometry->FirstChild("library_geometries");
00109
00110
00111 if(lib_geometry==NULL)
00112 {printf("Error in file %s, cannot find library_geometries in load_collada_texture in Mesh_object_loader\n",filename.data());exit(-1);}
00113
00114
00115 TiXmlNode* geometry=NULL;
00116 geometry=lib_geometry->FirstChild("geometry");
00117 if(geometry==NULL)
00118 {printf("Error in gile %s, cannot find geometry in load_collada_texture in Mesh_object_loader\n",filename.data());exit(-1);}
00119
00120 std::string geometry_id;
00121 int is_find=0;
00122 do
00123 {
00124 if(geometry->ToElement()->Attribute("id")==NULL)
00125 {printf("Error in file %s, geometry does not have id \n",filename.data());exit(-1);}
00126 geometry_id = geometry->ToElement()->Attribute("id");
00127 if(geometry_id==name || name=="_ALL_")
00128 {
00129 load_collada_mesh_texture(geometry,mesh,filename,texture_source);
00130 if(name!="_ALL_")
00131 is_find=1;
00132 }
00133 geometry=geometry->NextSiblingElement("geometry");
00134 }while(geometry!=NULL && is_find==0);
00135
00136
00138 int N_polygon_texture=mesh->get_texture_polygon_number();
00139 int N_polygon=mesh->polygon_number();
00140 if(N_polygon!=N_polygon_texture)
00141 {printf("Error in load_collada_texture in Mesh_object_loader for file %s, N_polygon=%d and N_texture_polygon=%d, loading texture failed\n",filename.data(),N_polygon,N_polygon_texture);exit(-1);}
00142
00143
00144 return 0;
00145 }
00146
00147 int Mesh_object_loader::load_collada_mesh_texture(TiXmlNode* geometry_node,Mesh_object* mesh,const std::string& filename,const std::string& texture_source) const
00148 {
00149
00150 TiXmlNode *mesh_node=NULL;
00151
00152 mesh_node=geometry_node->FirstChild("mesh");
00153
00154 if(mesh_node==NULL)
00155 {printf("Error in Connectivity in load_collada_mesh_connectivity for file %s\n",filename.data());exit(-1);}
00156
00157
00158
00159
00160
00161
00162 TiXmlNode* source_node=NULL;
00163 source_node=mesh_node->FirstChild("source");
00164
00165
00166 std::string name_source;
00167 std::vector <double> array_texture;
00168
00169 int to_continue=1;
00170
00171 int count=0;
00172 int N_texture=0;
00173 do
00174 {
00175
00176 if(source_node->ToElement()->Attribute("name")==NULL)
00177 {printf("Error in Mesh_object_loader in load_collada_mesh_texture for file %s, no name attribute for source entry\n",filename.data());exit(-1);}
00178 name_source = source_node->ToElement()->Attribute("id");
00179
00180 if(name_source==texture_source)
00181 {
00182 array_texture=load_collada_float_array(source_node,filename);
00183 to_continue=0;
00184
00185 N_texture = array_texture.size();
00186 if(N_texture%2!=0)
00187 {printf("Error in Mesh_object_loader, in load_collada_texture, N_texture does not divide by two \n ");exit(-1);}
00188
00189 for(count=0;count<N_texture/2;count++)
00190 mesh->add_intermediate_texture(array_texture[2*count+0],array_texture[2*count+1]);
00191
00192
00193 }
00194
00195 source_node=source_node->NextSiblingElement("source");
00196
00197 }while(source_node!=NULL && to_continue==1);
00198
00199
00200
00201
00202
00203
00204
00205
00206 TiXmlNode* polylist_node=NULL;
00207 polylist_node=mesh_node->FirstChild("polylist");
00208 while(polylist_node!=NULL)
00209 {
00210 load_polylist_texture(polylist_node,mesh,filename,texture_source);
00211
00212 polylist_node=polylist_node->NextSiblingElement("polylist");
00213 };
00214
00215
00216
00217
00218
00219 TiXmlNode* triangles_node=NULL;
00220 triangles_node=mesh_node->FirstChild("triangles");
00221 while(triangles_node!=NULL)
00222 {
00223 load_triangles_texture(triangles_node,mesh,filename,texture_source);
00224
00225 triangles_node=triangles_node->NextSiblingElement("triangles");
00226 };
00227
00228 return 0;
00229 }
00230
00231
00232
00233 std::vector <double> Mesh_object_loader::load_collada_float_array(TiXmlNode *mesh_source,const std::string& filename) const
00234 {
00235 TiXmlElement *float_array_node=NULL;
00236 float_array_node = mesh_source->FirstChild("float_array")->ToElement();
00237 if(float_array_node==NULL)
00238 {printf("Error cannot find float_array in load_collada_float_array in Point_set in file %s\n",filename.data());exit(-1);}
00239
00240 int count=0;
00241 float_array_node->QueryIntAttribute("count",&count);
00242 if(float_array_node->FirstChild()==NULL)
00243 {printf("Error in load_collada_float_array in Point_set in file %s\n",filename.data());exit(-1);}
00244 std::string full_array = float_array_node->FirstChild()->ToText()->ValueStr();
00245
00246
00247 std::vector <double> array;
00248 int c=0,k1=0,k0=0;
00249 string X;
00250 for(c=0;c<count;c++)
00251 {
00252 k1= full_array.find(" ",k1+1);
00253 X = full_array.substr(k0,k1-k0);
00254 array.push_back(atof(X.data()));
00255 k0=k1+1;
00256 }
00257
00258 return array;
00259 }
00260
00261 int Mesh_object_loader::load_polylist_texture(TiXmlNode* polylist_node,Mesh_object *mesh,const std::string& filename,const std::string& texture_source) const
00262 {
00263
00264
00265 TiXmlNode* input_node=NULL;
00266
00267
00268 input_node=polylist_node->FirstChild("input");
00269 if(input_node==NULL)
00270 {printf("Error in load_polylist_connectivity of file %s, no input entry in the polylist source\n",filename.data());exit(-1);}
00271
00272 int total_offset=0,vertex_offset=-1;
00273 std::string semantic_string;
00274 std::string source_string;
00275 std::string pointer_texture_source="#";pointer_texture_source+=texture_source;
00276
00277 while(input_node!=NULL)
00278 {
00279 if(input_node->ToElement()->Attribute("semantic")==NULL)
00280 {printf("Error in load_polylist_texture for file %s, no semantic entry in input of polylist\n",filename.data());exit(-1);}
00281 if(input_node->ToElement()->Attribute("source")==NULL)
00282 {printf("Error in load_polylist_texture for file %s, no source name entry in input of polylist\n",filename.data());exit(-1);}
00283
00284 semantic_string= input_node->ToElement()->Attribute("semantic");
00285 source_string = input_node->ToElement()->Attribute("source");
00286
00287 if(semantic_string=="TEXCOORD" && source_string==pointer_texture_source)
00288 {
00289
00290 if(input_node->ToElement()->QueryIntAttribute("offset",&vertex_offset)!=TIXML_SUCCESS)
00291 {printf("Error in load_polylist_texture, offset vertex is wrong for file %s in Mesh_object_loader\n",filename.data());exit(-1);}
00292 }
00293 total_offset++;
00294 input_node=input_node->NextSiblingElement("input");
00295
00296 };
00297
00298
00299
00300
00301 TiXmlNode* vcount_node=NULL;
00302 vcount_node=polylist_node->FirstChild("vcount");
00303 if(vcount_node==NULL)
00304 {printf("Error, no vcount found in polylist in file %s in Connectivity\n",filename.data());exit(-1);}
00305 std::vector <int> vcount_entry=load_collada_int_entry(vcount_node);
00306
00307
00308 int polylist_count=0;
00309 if(polylist_node->ToElement()->QueryIntAttribute("count",&polylist_count)!=TIXML_SUCCESS)
00310 {printf("Error in polylist in Mesh_object_loader for file %s, no count in polylist\n",filename.data());exit(-1);}
00311 if(polylist_count!=int(vcount_entry.size()))
00312 {printf("Error in file %s in Mesh_object_loader, in loading polylist: size(vcount)=%d and given size=%d\n",filename.data(),vcount_entry.size(),polylist_count);exit(-1);}
00313
00314
00315
00316
00317 TiXmlNode* p_node=NULL;
00318 p_node=polylist_node->FirstChild("p");
00319 if(p_node==NULL)
00320 {printf("Error, no <p> found in polylist in file %s in Mesh_object_loader in load_texture\n",filename.data());exit(-1);}
00321 std::vector <int> p_entry=load_collada_int_entry(p_node);
00322
00323
00325 std::vector <int> texture_array;
00326 int count=0;
00327 for(int k_poly=0;k_poly<polylist_count;k_poly++)
00328 for(int k_vertex=0;k_vertex<vcount_entry[k_poly];k_vertex++)
00329 for(int k_offset=0;k_offset<total_offset;k_offset++)
00330 {
00331 if(k_offset==vertex_offset)
00332 texture_array.push_back(p_entry[count]);
00333 count++;
00334 }
00335
00336
00337
00338
00339
00340 std::vector <int> current_polygon;
00341 int k_polygon=0,k_index=0;
00342 count=0;
00343 for(k_polygon=0;k_polygon<polylist_count;k_polygon++)
00344 {
00345 current_polygon.resize(0);
00346 for(k_index=0;k_index<vcount_entry[k_polygon];k_index++,count++)
00347 current_polygon.push_back(texture_array[count]);
00348 mesh->add_polygon_texture(current_polygon);
00349 }
00350
00351
00352
00353
00354 return 0;
00355 }
00356
00357
00358 std::vector <int> Mesh_object_loader::load_collada_int_entry(TiXmlNode* vcount_node) const
00359 {
00360 std::vector <int> vcount_entry;
00361 if(vcount_node==NULL)
00362 {printf("Error in load_collada_vcount_entry in Connectivity, pointer is null\n");exit(-1);}
00363 if(vcount_node->FirstChild()==NULL)
00364 {printf("Error no child in load_collada_vcount_entry in Connectivity\n");exit(-1);}
00365
00366 std::string full_string = vcount_node->FirstChild()->ToText()->ValueStr();
00367
00368
00369 int k1=0,k0=0;
00370 string X;
00371 do
00372 {
00373 k1= full_string.find(" ",k1+1);
00374 X = full_string.substr(k0,k1-k0);
00375 vcount_entry.push_back(atoi(X.data()));
00376 k0=k1+1;
00377 }while(k1>0);
00378
00379 return vcount_entry;
00380 }
00381
00382
00383
00384
00385
00386
00387 int Mesh_object_loader::load_triangles_texture(TiXmlNode* triangles_node,Mesh_object *mesh,const std::string& filename,const std::string& texture_source) const
00388 {
00389
00390
00391 TiXmlNode* input_node=NULL;
00392
00393
00394 input_node=triangles_node->FirstChild("input");
00395 if(input_node==NULL)
00396 {printf("Error in load_triangles_connectivity of file %s, no input entry in the polylist source\n",filename.data());exit(-1);}
00397
00398 int total_offset=0,vertex_offset=-1;
00399 std::string semantic_string;
00400 std::string source_string;
00401 std::string pointer_texture_source="#";pointer_texture_source+=texture_source;
00402
00403 while(input_node!=NULL)
00404 {
00405 if(input_node->ToElement()->Attribute("semantic")==NULL)
00406 {printf("Error in load_triangles_texture for file %s, no semantic entry in input of triangles\n",filename.data());exit(-1);}
00407 if(input_node->ToElement()->Attribute("source")==NULL)
00408 {printf("Error in load_triangles_texture for file %s, no source name entry in input of triangles\n",filename.data());exit(-1);}
00409
00410 semantic_string= input_node->ToElement()->Attribute("semantic");
00411 source_string = input_node->ToElement()->Attribute("source");
00412
00413 if(semantic_string=="TEXCOORD" && source_string==pointer_texture_source)
00414 {
00415
00416 if(input_node->ToElement()->QueryIntAttribute("offset",&vertex_offset)!=TIXML_SUCCESS)
00417 {printf("Error in load_triangles_texture, offset vertex is wrong for file %s in Mesh_object_loader\n",filename.data());exit(-1);}
00418 }
00419 total_offset++;
00420 input_node=input_node->NextSiblingElement("input");
00421
00422 };
00423
00424
00425
00426
00427
00428
00429
00430 TiXmlNode* p_node=NULL;
00431 p_node=triangles_node->FirstChild("p");
00432 if(p_node==NULL)
00433 {printf("Error, no <p> found in polylist triangles in file %s in Mesh_object_loader in load_texture\n",filename.data());exit(-1);}
00434 std::vector <int> p_entry=load_collada_int_entry(p_node);
00435
00436
00437 int triangle_count=0;
00438 if(triangles_node->ToElement()->QueryIntAttribute("count",&triangle_count)!=TIXML_SUCCESS)
00439 {printf("Error in load_triangles_texture in Mesh_object_loader for file %s, no count in triangles\n",filename.data());exit(-1);}
00440
00441
00443 std::vector <int> texture_array;
00444 int count=0;
00445 for(int k_poly=0;k_poly<triangle_count;k_poly++)
00446 for(int k_vertex=0;k_vertex<3;k_vertex++)
00447 for(int k_offset=0;k_offset<total_offset;k_offset++)
00448 {
00449 if(k_offset==vertex_offset)
00450 texture_array.push_back(p_entry[count]);
00451 count++;
00452 }
00453
00454
00455
00457 if(3*triangle_count!=int(texture_array.size()))
00458 {printf("Error in file %s in load_triangles_texture in Mesh_object_loader, size(texture_array)=%d and given size=3x%d=%d\n",filename.data(),texture_array.size(),triangle_count,3*triangle_count);exit(-1);}
00459
00460
00461
00462
00463 std::vector <int> current_polygon;
00464 int k_polygon=0,k_index=0;
00465 count=0;
00466 for(k_polygon=0;k_polygon<triangle_count;k_polygon++)
00467 {
00468 current_polygon.resize(0);
00469 for(k_index=0;k_index<3;k_index++,count++)
00470 current_polygon.push_back(texture_array[count]);
00471 mesh->add_polygon_texture(current_polygon);
00472 }
00473
00474
00475
00476
00477 return 0;
00478 }