$search
00001 /* 00002 * Copyright (C) 2008 00003 * Robert Bosch LLC 00004 * Research and Technology Center North America 00005 * Palo Alto, California 00006 * 00007 * All rights reserved. 00008 * 00009 *------------------------------------------------------------------------------ 00010 * project ....: PUMA: Probablistic Unsupervised Model Acquisition 00011 * file .......: MeshSet3DVBONode.cpp 00012 * authors ....: Zhexi Wang 00013 * organization: Robert Bosch LLC 00014 * creation ...: 02/04/2009 00015 * modified ...: $Date: 2009-02-02 12:17:10 -0800 (Mon, 02 Feb 2009) $ 00016 * changed by .: $Author: wg75pal $ 00017 * revision ...: $Revision: 772 $ 00018 */ 00019 #include <GL/glew.h> 00020 #include "rtc/rtcMeshSet3DVBONode.h" 00021 00022 #define VBO_NORMAL 0x01 00023 #define VBO_COLOR 0x02 00024 #define VBO_TEXCOORD 0x04 00025 #define VBO_TEXTURE 0x08 00026 00027 #define CHECKGL while(true){int err=glGetError();if (err==0) break;else printf("OpenGL ERROR: %d, at %s, line %d\n",err,__FILE__,__LINE__);} 00028 00029 namespace rtc { 00030 MeshSet3DVBONode::MeshSet3DVBONode(Renderer* renderer, MeshSet3D* meshset) 00031 :RenderNode(renderer) 00032 { 00033 num_mesh=meshset->numMeshes(); 00034 meshvbos=new MeshVBO[num_mesh]; 00035 memset(meshvbos,0,sizeof(MeshVBO)*num_mesh); 00036 for (int m=0;m<num_mesh;m++) 00037 { 00038 Mesh3D *mesh=meshset->meshes[m]; 00039 MeshVBO *vbo=meshvbos+m; 00040 vbo->num_vertices = mesh->vertices.size(); 00041 vbo->num_faces = mesh->faces.size(); 00042 00043 vbo->position_size = vbo->num_vertices * 3; 00044 vbo->position_data = new GLfloat[vbo->position_size]; 00045 00046 vbo->index_size = vbo->num_faces * 3; 00047 vbo->index_data = new GLuint[vbo->index_size]; 00048 00049 vbo->normal_size = vbo->num_vertices * 3; 00050 vbo->normal_data = new GLfloat[vbo->normal_size]; 00051 vbo->flag|=VBO_NORMAL; 00052 00053 if(mesh->hasTexture()) 00054 { 00055 vbo->texcoord_size = vbo->num_vertices * 2; 00056 vbo->texcoord_data = new GLfloat[vbo->texcoord_size]; 00057 vbo->flag|=VBO_TEXCOORD; 00058 } 00059 00060 vbo->color_size = vbo->num_vertices * 3; 00061 vbo->color_data = new GLubyte[vbo->color_size]; 00062 vbo->flag|=VBO_COLOR; 00063 00064 for (unsigned int i=0; i<vbo->num_vertices; ++i) 00065 { 00066 vbo->position_data[i * 3] = (GLfloat)mesh->vertices[i]->p[0]; 00067 vbo->position_data[i * 3 + 1] = (GLfloat)mesh->vertices[i]->p[1]; 00068 vbo->position_data[i * 3 + 2] = (GLfloat)mesh->vertices[i]->p[2]; 00069 00070 vbo->normal_data[i * 3] = (GLfloat)mesh->vertices[i]->n[0]; 00071 vbo->normal_data[i * 3 + 1] = (GLfloat)mesh->vertices[i]->n[1]; 00072 vbo->normal_data[i * 3 + 2] = (GLfloat)mesh->vertices[i]->n[2]; 00073 00074 if(mesh->hasTexture()) 00075 { 00076 vbo->texcoord_data[i * 2] = (GLfloat)mesh->vertices[i]->t[0]; 00077 vbo->texcoord_data[i * 2 + 1] = (GLfloat)mesh->vertices[i]->t[1]; 00078 } 00079 00080 // copy color data 00081 vbo->color_data[i * 3] = (GLubyte)mesh->vertices[i]->c[0]; 00082 vbo->color_data[i * 3 + 1] = (GLubyte)mesh->vertices[i]->c[1]; 00083 vbo->color_data[i * 3 + 2] = (GLubyte)mesh->vertices[i]->c[2]; 00084 } 00085 00086 for (unsigned int i=0; i<vbo->num_faces; ++i) 00087 { 00088 vbo->index_data[i * 3 ] = mesh->faces[i]->v(0); 00089 vbo->index_data[i * 3 + 1] = mesh->faces[i]->v(1); 00090 vbo->index_data[i * 3 + 2] = mesh->faces[i]->v(2); 00091 } 00092 00093 if(mesh->hasTexture()) 00094 { 00095 vbo->texture_width=mesh->teximage.columns(); 00096 vbo->texture_height=mesh->teximage.rows(); 00097 vbo->texture_size=vbo->texture_width*vbo->texture_height*3; 00098 vbo->texture_data=new GLubyte[vbo->texture_size]; 00099 memcpy(vbo->texture_data,mesh->teximage.x,vbo->texture_size*sizeof(GLubyte)); 00100 vbo->flag|=VBO_TEXTURE; 00101 } 00102 } 00103 } 00104 00105 MeshSet3DVBONode::MeshSet3DVBONode( Renderer* renderer, const char* vbofilename ) 00106 :RenderNode(renderer) 00107 { 00108 size_t res = 0; 00109 FILE *fp=fopen(vbofilename,"rb"); 00110 if (fp==NULL) 00111 { 00112 printf("Open file %s failed\n",vbofilename); 00113 return; 00114 } 00115 res+=fread(&num_mesh,sizeof(num_mesh),1,fp); 00116 meshvbos=new MeshVBO[num_mesh]; 00117 memset(meshvbos,0,sizeof(MeshVBO)*num_mesh); 00118 for (int i=0;i<num_mesh;i++) 00119 meshvbos[i].read(fp); 00120 fclose(fp); 00121 } 00122 00123 MeshSet3DVBONode::MeshSet3DVBONode( Renderer* renderer, FILE* fp ) 00124 :RenderNode(renderer) 00125 { 00126 size_t res = 0; 00127 res+=fread(&num_mesh,sizeof(num_mesh),1,fp); 00128 meshvbos=new MeshVBO[num_mesh]; 00129 memset(meshvbos,0,sizeof(MeshVBO)*num_mesh); 00130 for (int i=0;i<num_mesh;i++) 00131 meshvbos[i].read(fp); 00132 } 00133 00134 MeshSet3DVBONode::~MeshSet3DVBONode() 00135 { 00136 delete[] meshvbos; 00137 meshvbos=NULL; 00138 } 00139 00140 void MeshSet3DVBONode::render() 00141 { 00142 glEnable(GL_COLOR_MATERIAL); 00143 // glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE); 00144 00145 00146 if(m_params->draw_vertices) 00147 drawPointsVBO(); 00148 CHECKGL 00149 00150 if(m_params->draw_wireframe) 00151 drawWireFrameVBO(); 00152 CHECKGL 00153 00154 if(m_params->draw_faces) 00155 drawFacesVBO(); 00156 CHECKGL 00157 // glDisable(GL_COLOR_MATERIAL); 00158 } 00159 00160 void MeshSet3DVBONode::drawFacesVBO() 00161 { 00162 glDisable(GL_LIGHTING); 00163 glLineWidth(2.0); 00164 glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); 00165 00166 int f=VBO_NORMAL; 00167 switch(m_params->color_mode) 00168 { 00169 case Parameters::NO_COLOR: break; 00170 case Parameters::VERTEX_COLOR: f|=VBO_COLOR; break; 00171 case Parameters::TEXTURE_COLOR: f|=VBO_TEXCOORD|VBO_TEXTURE;break; 00172 } 00173 00174 for (int i=0;i<num_mesh;i++) 00175 { 00176 meshvbos[i].bind(f); 00177 glDrawElements(GL_TRIANGLES, meshvbos[i].num_faces*3, GL_UNSIGNED_INT, 0); 00178 meshvbos[i].unbind(f); 00179 } 00180 glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); 00181 } 00182 00183 void MeshSet3DVBONode::drawPointsVBO() 00184 { 00185 glDisable(GL_LIGHTING); 00186 00187 int f=VBO_NORMAL; 00188 switch(m_params->color_mode) 00189 { 00190 case Parameters::NO_COLOR: break; 00191 case Parameters::VERTEX_COLOR: f|=VBO_COLOR; break; 00192 case Parameters::TEXTURE_COLOR: f|=VBO_TEXCOORD|VBO_TEXTURE;break; 00193 } 00194 00195 for (int i=0;i<num_mesh;i++) 00196 { 00197 meshvbos[i].bind(f); 00198 glDrawArrays(GL_POINTS, 0, meshvbos[i].num_vertices); 00199 meshvbos[i].unbind(f); 00200 } 00201 00202 } 00203 00204 void MeshSet3DVBONode::drawWireFrameVBO() 00205 { 00206 glDisable(GL_LIGHTING); 00207 glLineWidth(2.0); 00208 glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); 00209 00210 int f=VBO_NORMAL; 00211 switch(m_params->color_mode) 00212 { 00213 case Parameters::NO_COLOR: break; 00214 case Parameters::VERTEX_COLOR: f|=VBO_COLOR; break; 00215 case Parameters::TEXTURE_COLOR: f|=VBO_TEXCOORD|VBO_TEXTURE;break; 00216 } 00217 00218 for (int i=0;i<num_mesh;i++) 00219 { 00220 meshvbos[i].bind(f); 00221 glDrawElements(GL_TRIANGLES, meshvbos[i].num_faces*3, GL_UNSIGNED_INT, 0); 00222 meshvbos[i].unbind(f); 00223 } 00224 glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); 00225 } 00226 00227 void MeshSet3DVBONode::loadToGPU() 00228 { 00229 for (int i=0;i<num_mesh;i++) 00230 meshvbos[i].loadGPU(); 00231 } 00232 00233 void MeshSet3DVBONode::unloadGPU() 00234 { 00235 for (int i=0;i<num_mesh;i++) 00236 meshvbos[i].unloadGPU(); 00237 } 00238 00239 void MeshSet3DVBONode::writeToFile( const char *filename ) 00240 { 00241 FILE *fp=fopen(filename,"wb"); 00242 if (fp==NULL) 00243 { 00244 printf("Open file %s failed\n",filename); 00245 return; 00246 } 00247 write(fp); 00248 fclose(fp); 00249 } 00250 00251 void MeshSet3DVBONode::write( FILE* fp ) 00252 { 00253 fwrite(&num_mesh,sizeof(num_mesh),1,fp); 00254 for (int i=0;i<num_mesh;i++) 00255 meshvbos[i].write(fp); 00256 } 00257 00259 00260 void MeshSet3DVBONode::MeshVBO::read( FILE* fp ) 00261 { 00262 size_t res = 0; 00264 memset(this,0,sizeof(MeshSet3DVBONode::MeshVBO)); 00265 res+=fread(&flag,sizeof(flag),1,fp); 00266 res+=fread(&num_vertices,sizeof(num_vertices),1,fp); 00267 res+=fread(&num_faces,sizeof(num_faces),1,fp); 00268 00269 res+=fread(&position_size,sizeof(position_size),1,fp); 00270 position_data=new GLfloat[position_size]; 00271 res+=fread(position_data,sizeof(GLfloat),position_size,fp); 00272 00273 res+=fread(&index_size,sizeof(index_size),1,fp); 00274 index_data=new GLuint[index_size]; 00275 res+=fread(index_data,sizeof(GLuint),index_size,fp); 00276 00277 if ((flag&VBO_NORMAL)!=0) 00278 { 00279 res+=fread(&normal_size,sizeof(normal_size),1,fp); 00280 normal_data=new GLfloat[normal_size]; 00281 res+=fread(normal_data,sizeof(GLfloat),normal_size,fp); 00282 } 00283 if ((flag&VBO_COLOR)!=0) 00284 { 00285 res+=fread(&color_size,sizeof(color_size),1,fp); 00286 color_data=new GLubyte[color_size]; 00287 res+=fread(color_data,sizeof(GLubyte),color_size,fp); 00288 } 00289 if ((flag&VBO_TEXCOORD)!=0) 00290 { 00291 res+=fread(&texcoord_size,sizeof(texcoord_size),1,fp); 00292 texcoord_data=new GLfloat[texcoord_size]; 00293 res+=fread(texcoord_data,sizeof(GLfloat),texcoord_size,fp); 00294 } 00295 if ((flag&VBO_TEXTURE)!=0) 00296 { 00297 res+=fread(&texture_size,sizeof(texture_size),1,fp); 00298 texture_data=new GLubyte[texture_size]; 00299 res+=fread(texture_data,sizeof(GLubyte),texture_size,fp); 00300 res+=fread(&texture_width,sizeof(texture_width),1,fp); 00301 res+=fread(&texture_height,sizeof(texture_height),1,fp); 00302 } 00303 } 00304 00305 void MeshSet3DVBONode::MeshVBO::write( FILE* fp ) 00306 { 00307 fwrite(&flag,sizeof(flag),1,fp); 00308 fwrite(&num_vertices,sizeof(num_vertices),1,fp); 00309 fwrite(&num_faces,sizeof(num_faces),1,fp); 00310 fwrite(&position_size,sizeof(position_size),1,fp); 00311 fwrite(position_data,sizeof(GLfloat),position_size,fp); 00312 fwrite(&index_size,sizeof(index_size),1,fp); 00313 fwrite(index_data,sizeof(GLuint),index_size,fp); 00314 if ((flag&VBO_NORMAL)!=0) 00315 { 00316 fwrite(&normal_size,sizeof(normal_size),1,fp); 00317 fwrite(normal_data,sizeof(GLfloat),normal_size,fp); 00318 } 00319 if ((flag&VBO_COLOR)!=0) 00320 { 00321 fwrite(&color_size,sizeof(color_size),1,fp); 00322 fwrite(color_data,sizeof(GLubyte),color_size,fp); 00323 } 00324 if ((flag&VBO_TEXCOORD)!=0) 00325 { 00326 fwrite(&texcoord_size,sizeof(texcoord_size),1,fp); 00327 fwrite(texcoord_data,sizeof(GLfloat),texcoord_size,fp); 00328 } 00329 if ((flag&VBO_TEXTURE)!=0) 00330 { 00331 fwrite(&texture_size,sizeof(texture_size),1,fp); 00332 fwrite(texture_data,sizeof(GLubyte),texture_size,fp); 00333 fwrite(&texture_width,sizeof(texture_width),1,fp); 00334 fwrite(&texture_height,sizeof(texture_height),1,fp); 00335 } 00336 } 00337 00338 void MeshSet3DVBONode::MeshVBO::loadGPU() 00339 { 00340 CHECKGL 00341 getGPUBuffer(position_buffer); 00342 glBindBufferARB(GL_ARRAY_BUFFER_ARB, position_buffer); 00343 glBufferDataARB(GL_ARRAY_BUFFER_ARB, position_size*sizeof(GLfloat), position_data, GL_STATIC_DRAW_ARB); 00344 CHECKGL 00345 00346 getGPUBuffer(index_buffer); 00347 glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, index_buffer); 00348 glBufferDataARB(GL_ELEMENT_ARRAY_BUFFER_ARB, index_size*sizeof(GLuint), index_data, GL_STATIC_DRAW_ARB); 00349 glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0); 00350 CHECKGL 00351 00352 if ((flag&VBO_NORMAL)!=0) 00353 { 00354 getGPUBuffer(normal_buffer); 00355 glBindBufferARB(GL_ARRAY_BUFFER_ARB, normal_buffer); 00356 glBufferDataARB(GL_ARRAY_BUFFER_ARB, normal_size*sizeof(GLfloat), normal_data, GL_STATIC_DRAW_ARB); 00357 } 00358 CHECKGL 00359 00360 if ((flag&VBO_COLOR)!=0) 00361 { 00362 getGPUBuffer(color_buffer); 00363 glBindBufferARB(GL_ARRAY_BUFFER_ARB, color_buffer); 00364 glBufferDataARB(GL_ARRAY_BUFFER_ARB, color_size*sizeof(GLubyte), color_data, GL_STATIC_DRAW_ARB); 00365 } 00366 CHECKGL 00367 00368 if ((flag&VBO_TEXCOORD)!=0) 00369 { 00370 getGPUBuffer(texcoord_buffer); 00371 glBindBufferARB(GL_ARRAY_BUFFER_ARB, texcoord_buffer); 00372 glBufferDataARB(GL_ARRAY_BUFFER_ARB, texcoord_size*sizeof(GLfloat), texcoord_data, GL_STATIC_DRAW_ARB); 00373 } 00374 CHECKGL 00375 glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0); 00376 00377 if ((flag&VBO_TEXTURE)!=0) 00378 { 00379 getTextureId(texture_id); 00380 glPixelStorei(GL_UNPACK_ALIGNMENT, 1); 00381 glBindTexture(GL_TEXTURE_2D, texture_id); 00382 glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_WRAP_S,GL_CLAMP); 00383 glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_WRAP_T,GL_CLAMP); 00384 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 00385 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 00386 glTexImage2D(GL_TEXTURE_2D,0,GL_RGB,texture_width,texture_height,0,GL_RGB,GL_UNSIGNED_BYTE,texture_data); 00387 glDisable(GL_TEXTURE_2D); 00388 } 00389 CHECKGL 00390 00391 } 00392 00393 void MeshSet3DVBONode::MeshVBO::unloadGPU() 00394 { 00395 retGPUBuffer(position_buffer); 00396 retGPUBuffer(index_buffer); 00397 00398 if ((flag&VBO_NORMAL)!=0) 00399 { 00400 retGPUBuffer(normal_buffer); 00401 } 00402 00403 if ((flag&VBO_COLOR)!=0) 00404 { 00405 retGPUBuffer(color_buffer); 00406 } 00407 00408 if ((flag&VBO_TEXCOORD)!=0) 00409 { 00410 retGPUBuffer(texcoord_buffer); 00411 } 00412 00413 if ((flag&VBO_TEXTURE)!=0) 00414 { 00415 retTextureId(texture_id); 00416 } 00417 } 00418 00419 void MeshSet3DVBONode::MeshVBO::bind( unsigned int vbo ) 00420 { 00421 glEnableClientState(GL_VERTEX_ARRAY); 00422 glBindBufferARB(GL_ARRAY_BUFFER_ARB, position_buffer); 00423 glVertexPointer(3, GL_FLOAT, 0, 0); 00424 00425 glEnableClientState(GL_INDEX_ARRAY); 00426 glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, index_buffer); 00427 glIndexPointer(GL_INT, 0, 0); 00428 00429 if ((vbo&VBO_NORMAL)!=0 && (flag&VBO_NORMAL)!=0) 00430 { 00431 glEnableClientState(GL_NORMAL_ARRAY); 00432 glBindBufferARB(GL_ARRAY_BUFFER_ARB, normal_buffer); 00433 glNormalPointer(GL_FLOAT, 0, 0); 00434 } 00435 00436 if ((vbo&VBO_COLOR)!=0 && (flag&VBO_COLOR)!=0) 00437 { 00438 glDisable(GL_TEXTURE_2D); 00439 glEnableClientState(GL_COLOR_ARRAY); 00440 glBindBufferARB(GL_ARRAY_BUFFER_ARB, color_buffer); 00441 glColorPointer(3, GL_UNSIGNED_BYTE, 0, 0); 00442 } 00443 00444 if ((vbo&VBO_TEXCOORD)!=0 && (flag&VBO_TEXCOORD)!=0) 00445 { 00446 glEnableClientState(GL_TEXTURE_COORD_ARRAY); 00447 glBindBufferARB(GL_ARRAY_BUFFER_ARB, texcoord_buffer); 00448 glTexCoordPointer(2, GL_FLOAT, 0, 0); 00449 glColor3f(1,1,1); 00450 } 00451 00452 if ((vbo&VBO_TEXTURE)!=0 && (flag&VBO_TEXTURE)!=0) 00453 { 00454 glEnable(GL_TEXTURE_2D); 00455 glActiveTexture(GL_TEXTURE0); 00456 glBindTexture(GL_TEXTURE_2D, texture_id); 00457 } 00458 } 00459 00460 void MeshSet3DVBONode::MeshVBO::unbind( unsigned int vbo ) 00461 { 00462 glDisableClientState(GL_VERTEX_ARRAY); 00463 glDisableClientState(GL_INDEX_ARRAY); 00464 if ((vbo&VBO_NORMAL)!=0) 00465 { 00466 glDisableClientState(GL_NORMAL_ARRAY); 00467 } 00468 if ((vbo&VBO_COLOR)!=0) 00469 { 00470 glDisableClientState(GL_COLOR_ARRAY); 00471 } 00472 if ((vbo&VBO_TEXCOORD)!=0) 00473 { 00474 glDisableClientState(GL_TEXTURE_COORD_ARRAY); 00475 } 00476 if ((vbo&VBO_TEXTURE)!=0) 00477 { 00478 glActiveTexture(GL_TEXTURE0); 00479 glBindTexture(GL_TEXTURE_2D, 0); 00480 glDisable(GL_TEXTURE_2D); 00481 } 00482 } 00483 00484 MeshSet3DVBONode::MeshVBO::~MeshVBO() 00485 { 00486 delete position_data; 00487 delete normal_data; 00488 delete color_data; 00489 delete texcoord_data; 00490 delete index_data; 00491 delete texture_data; 00492 } 00494 std::vector<GLuint> MeshSet3DVBONode::gpubuffers; 00495 std::vector<GLuint> MeshSet3DVBONode::gputextures; 00496 void MeshSet3DVBONode::getGPUBuffer(GLuint &buffer) 00497 { 00498 if (gpubuffers.empty()) 00499 { 00500 glGenBuffersARB(1, &buffer); 00501 CHECKGL 00502 } 00503 else 00504 { 00505 buffer=gpubuffers.back(); 00506 gpubuffers.pop_back(); 00507 } 00508 } 00509 void MeshSet3DVBONode::retGPUBuffer(GLuint &buffer) 00510 { 00511 gpubuffers.push_back(buffer); 00512 glBindBufferARB(GL_ARRAY_BUFFER_ARB, buffer); 00513 glBufferDataARB(GL_ARRAY_BUFFER_ARB, 0, NULL, GL_STATIC_DRAW_ARB); 00514 glBindBufferARB(GL_ARRAY_BUFFER_ARB,0); 00515 buffer=0; 00516 } 00517 void MeshSet3DVBONode::getTextureId(GLuint &texid) 00518 { 00519 if (gputextures.empty()) 00520 { 00521 glGenTextures(1, &texid); 00522 } 00523 else 00524 { 00525 texid=gputextures.back(); 00526 gputextures.pop_back(); 00527 } 00528 } 00529 void MeshSet3DVBONode::retTextureId(GLuint &texid) 00530 { 00531 gputextures.push_back(texid); 00532 // glBindTexture(GL_TEXTURE_2D, texid); 00533 // glTexImage2D(GL_TEXTURE_2D,0,GL_RGB,0,0,0,GL_RGB,GL_UNSIGNED_BYTE,NULL); 00534 // glBindTexture(GL_TEXTURE_2D, 0); 00535 // glDisable(GL_TEXTURE_2D); 00536 texid=0; 00537 } 00538 00539 }