00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052 #define ACG_MESHNODE_C
00053
00054
00055
00056
00057 #include "MeshNodeT.hh"
00058 #include "ShaderNode.hh"
00059 #include "DrawModes.hh"
00060 #include "../GL/gl.hh"
00061 #include "../GL/ColorTranslator.hh"
00062
00063 #include <OpenMesh/Core/System/omstream.hh>
00064 #include <OpenMesh/Core/Utils/Property.hh>
00065
00066
00067
00068
00069 namespace ACG {
00070 namespace SceneGraph {
00071
00072
00073
00074
00075
00076 template<class Mesh>
00077 MeshNodeT<Mesh>::
00078 MeshNodeT(const Mesh& _mesh,
00079 BaseNode* _parent,
00080 std::string _name)
00081 : BaseNode(_parent, _name),
00082 mesh_(_mesh),
00083 textureMap_(0),
00084 propertyMap_(0),
00085 default_halfedge_textcoord_property_("h:texcoords2D"),
00086 bbMin_(FLT_MAX, FLT_MAX, FLT_MAX),
00087 bbMax_(-FLT_MAX, -FLT_MAX, -FLT_MAX)
00088 {
00089
00090 }
00091
00092
00093
00094
00095
00096 template<class Mesh>
00097 MeshNodeT<Mesh>::
00098 ~MeshNodeT()
00099 {
00100
00101 }
00102
00103
00104
00105
00106 template<class Mesh>
00107 DrawModes::DrawMode
00108 MeshNodeT<Mesh>::
00109 availableDrawModes() const
00110 {
00111 DrawModes::DrawMode drawModes(DrawModes::NONE);
00112
00113 drawModes |= DrawModes::SOLID_SHADER;
00114
00115 if (mesh_.has_vertex_texcoords1D())
00116 {
00117 drawModes |= DrawModes::SOLID_1DTEXTURED;
00118
00119 if (mesh_.has_vertex_normals())
00120 drawModes |= DrawModes::SOLID_1DTEXTURED_SHADED;
00121 }
00122
00123 if (mesh_.has_vertex_texcoords3D())
00124 {
00125 drawModes |= DrawModes::SOLID_3DTEXTURED;
00126
00127 if (mesh_.has_vertex_normals())
00128 drawModes |= DrawModes::SOLID_3DTEXTURED_SHADED;
00129 }
00130
00131
00132
00133 return drawModes;
00134 }
00135
00136
00137
00138
00139
00140 template<class Mesh>
00141 void
00142 MeshNodeT<Mesh>::
00143 enable_arrays(unsigned int _arrays)
00144 {
00145
00146 if (_arrays & TEXTURE_COORD_1D_ARRAY)
00147 {
00148 if (!(enabled_arrays_ & TEXTURE_COORD_1D_ARRAY))
00149 {
00150 enabled_arrays_ |= TEXTURE_COORD_1D_ARRAY;
00151 glEnableClientState(GL_TEXTURE_COORD_ARRAY);
00152 glTexCoordPointer(mesh_.texcoords1D());
00153 }
00154 }
00155 else if (enabled_arrays_ & TEXTURE_COORD_1D_ARRAY)
00156 {
00157 enabled_arrays_ &= ~TEXTURE_COORD_1D_ARRAY;
00158 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
00159 }
00160
00161
00162 if (_arrays & TEXTURE_COORD_2D_ARRAY)
00163 {
00164 if (!(enabled_arrays_ & TEXTURE_COORD_2D_ARRAY))
00165 {
00166 enabled_arrays_ |= TEXTURE_COORD_2D_ARRAY;
00167 glEnableClientState(GL_TEXTURE_COORD_ARRAY);
00168 glTexCoordPointer(mesh_.texcoords2D());
00169 }
00170 }
00171 else if (enabled_arrays_ & TEXTURE_COORD_2D_ARRAY)
00172 {
00173 enabled_arrays_ &= ~TEXTURE_COORD_2D_ARRAY;
00174 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
00175 }
00176
00177
00178 if (_arrays & TEXTURE_COORD_3D_ARRAY)
00179 {
00180 if (!(enabled_arrays_ & TEXTURE_COORD_3D_ARRAY))
00181 {
00182 enabled_arrays_ |= TEXTURE_COORD_3D_ARRAY;
00183 glEnableClientState(GL_TEXTURE_COORD_ARRAY);
00184 glTexCoordPointer(mesh_.texcoords3D());
00185 }
00186 }
00187 else if (enabled_arrays_ & TEXTURE_COORD_3D_ARRAY)
00188 {
00189 enabled_arrays_ &= ~TEXTURE_COORD_3D_ARRAY;
00190 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
00191 }
00192
00193
00194 glCheckErrors();
00195 }
00196
00197
00198
00199
00200
00201 template<class Mesh>
00202 void
00203 MeshNodeT<Mesh>::
00204 draw(GLState& _state, DrawModes::DrawMode _drawMode)
00205 {
00206 glDepthFunc(depthFunc());
00207
00208 if ( ( _drawMode & DrawModes::SOLID_ENV_MAPPED ) && mesh_.has_vertex_normals())
00209 {
00210 enable_arrays(VERTEX_ARRAY | NORMAL_ARRAY);
00211 glEnable(GL_LIGHTING);
00212 glShadeModel(GL_SMOOTH);
00213 glDepthRange(0.01, 1.0);
00214 draw_faces(PER_VERTEX);
00215 glDepthRange(0.0, 1.0);
00216 }
00217
00218
00219 if ( ( _drawMode & DrawModes::SOLID_1DTEXTURED ) && mesh_.has_vertex_texcoords1D())
00220 {
00221 enable_arrays(VERTEX_ARRAY | TEXTURE_COORD_1D_ARRAY);
00222 glEnable(GL_TEXTURE_1D);
00223 glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
00224 glDisable(GL_LIGHTING);
00225 glShadeModel(GL_SMOOTH);
00226 glDepthRange(0.01, 1.0);
00227 draw_faces(PER_VERTEX);
00228 glDepthRange(0.0, 1.0);
00229 glDisable(GL_TEXTURE_1D);
00230 }
00231
00232
00233 if ( ( _drawMode & DrawModes::SOLID_1DTEXTURED_SHADED ) && mesh_.has_vertex_texcoords1D() && mesh_.has_vertex_normals())
00234 {
00235
00236 const Vec4f ambient = _state.ambient_color();
00237 const Vec4f diffuse = _state.diffuse_color();
00238 const Vec4f specular = _state.specular_color();
00239 _state.set_ambient_color (Vec4f(0.1, 0.1, 0.1, 1.0));
00240 _state.set_diffuse_color (Vec4f(0.8, 0.8, 0.8, 1.0));
00241 _state.set_specular_color (Vec4f(1.0, 1.0, 1.0, 1.0));
00242
00243
00244 GLint texmode;
00245 glGetTexEnviv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, &texmode);
00246 glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
00247
00248 enable_arrays(VERTEX_ARRAY | NORMAL_ARRAY | TEXTURE_COORD_1D_ARRAY);
00249 glEnable(GL_TEXTURE_1D);
00250 glEnable(GL_LIGHTING);
00251 glShadeModel(GL_SMOOTH);
00252 glDepthRange(0.01, 1.0);
00253 draw_faces(PER_VERTEX);
00254 glDepthRange(0.0, 1.0);
00255 glDisable(GL_TEXTURE_1D);
00256
00257
00258 _state.set_ambient_color(ambient);
00259 _state.set_diffuse_color(diffuse);
00260 _state.set_specular_color(specular);
00261
00262
00263 glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, texmode);
00264 }
00265
00266
00267
00268 if ( ( _drawMode & DrawModes::SOLID_3DTEXTURED ) && mesh_.has_vertex_texcoords3D())
00269 {
00270 enable_arrays(VERTEX_ARRAY | TEXTURE_COORD_3D_ARRAY);
00271 glEnable(GL_TEXTURE_3D);
00272 glDisable(GL_LIGHTING);
00273 glShadeModel(GL_FLAT);
00274 glDepthRange(0.01, 1.0);
00275 draw_faces(PER_VERTEX);
00276 glDepthRange(0.0, 1.0);
00277 glDisable(GL_TEXTURE_3D);
00278 }
00279
00280
00281 if ( ( _drawMode & DrawModes::SOLID_3DTEXTURED_SHADED ) && mesh_.has_vertex_texcoords3D() && mesh_.has_vertex_normals())
00282 {
00283 enable_arrays(VERTEX_ARRAY | NORMAL_ARRAY | TEXTURE_COORD_3D_ARRAY);
00284 glEnable(GL_TEXTURE_3D);
00285 glEnable(GL_LIGHTING);
00286 glShadeModel(GL_SMOOTH);
00287 glDepthRange(0.01, 1.0);
00288 draw_faces(PER_VERTEX);
00289 glDepthRange(0.0, 1.0);
00290 glDisable(GL_TEXTURE_3D);
00291 }
00292
00293
00294
00295
00296 if ( (_drawMode & DrawModes::SOLID_SHADER ) ) {
00297
00298 if ( mesh_.has_face_normals() )
00299 enable_arrays( VERTEX_ARRAY | NORMAL_ARRAY);
00300 else
00301 enable_arrays( VERTEX_ARRAY );
00302
00303 glEnable(GL_LIGHTING);
00304 glShadeModel(GL_SMOOTH);
00305 glDepthRange(0.01, 1.0);
00306 draw_faces(PER_VERTEX);
00307 glDepthRange(0.0, 1.0);
00308 }
00309
00310
00311
00312 }
00313
00314
00315
00316
00317
00318 template<class Mesh>
00319 void
00320 MeshNodeT<Mesh>::
00321 draw_faces(FaceMode _mode)
00322 {
00323 typename Mesh::ConstFaceIter f_it(mesh_.faces_sbegin()),
00324 f_end(mesh_.faces_end());
00325 typename Mesh::ConstFaceVertexIter fv_it;
00326 typename Mesh::ConstFaceHalfedgeIter fh_it;
00327
00328 switch (_mode)
00329 {
00330
00331
00332
00333
00334 case FACE_HALFEDGE_TEXTURED:
00335 {
00336 if (mesh_.is_trimesh())
00337 {
00338
00339 OpenMesh::FPropHandleT< int > texture_index_property;
00340 if ( !mesh_.get_property_handle(texture_index_property,indexPropertyName_) ) {
00341 if( indexPropertyName_ != "No Texture Index")
00342 std::cerr << "Unable to get per face texture Index property named " << indexPropertyName_ << std::endl;
00343 if ( !mesh_.get_property_handle(texture_index_property,"f:textureindex") ) {
00344 std::cerr << "Unable to get standard per face texture Index property" << std::endl;
00345 texture_index_property.reset();
00346 }
00347 }
00348
00349
00350
00351
00352
00353
00354 if ( !textureMap_ || !texture_index_property.is_valid() ) {
00355
00356
00357 OpenMesh::HPropHandleT< typename Mesh::TexCoord2D > texture_coord_property;
00358 if ( !mesh_.get_property_handle(texture_coord_property,default_halfedge_textcoord_property_) ) {
00359 std::cerr << "Error: Unable to get per face texture coordinate property named "
00360 << default_halfedge_textcoord_property_ << std::endl;
00361 std::cerr << "Unable to texture without texture coordinates" << std::endl;
00362 return;
00363 }
00364
00365 typename Mesh::Point point;
00366 typename Mesh::TexCoord2D tex2d;
00367 glBegin(GL_TRIANGLES);
00368 for (; f_it!=f_end; ++f_it) {
00369 glNormal(mesh_.normal(f_it));
00370 for (fh_it = mesh_.cfh_iter(f_it.handle());fh_it;++fh_it) {
00371 point = mesh_.point(mesh_.to_vertex_handle(fh_it));
00372 tex2d = mesh_.property(texture_coord_property,fh_it);
00373 glTexCoord2f(tex2d[0], tex2d[1]);
00374 glVertex(point);
00375 }
00376 }
00377 glEnd();
00378 } else {
00379
00380 OpenMesh::HPropHandleT< typename Mesh::TexCoord2D > texture_coord_property;
00381 int last_texture = -1;
00382
00383 typename Mesh::Point point;
00384 typename Mesh::TexCoord2D tex2d;
00385
00386 for (; f_it!=f_end; ++f_it)
00387 {
00388 int texture = mesh_.property(texture_index_property,f_it);
00389
00390 if (texture == -1)
00391 continue;
00392
00393 if ( last_texture != texture ) {
00394
00395 if ( textureMap_->find(texture) == textureMap_->end() ) {
00396 std::cerr << "Illegal texture index ... trying to access " << texture << std::endl;
00397 last_texture = -1;
00398 continue;
00399 }
00400
00401
00402 if ( !propertyMap_ || !mesh_.get_property_handle(texture_coord_property,(*propertyMap_)[texture]) ) {
00403 if ( propertyMap_)
00404 std::cerr << "Error: Unable to get per face texture coordinate property named "
00405 << (*propertyMap_)[texture] << std::endl;
00406 if ( !mesh_.get_property_handle(texture_coord_property,"h:texcoords2D") ) {
00407 std::cerr << "Fallback: Unable to get standard Property for per halfedge texcoords" << std::endl;
00408 std::cerr << "Unable to texture face without texture coordinates" << std::endl;
00409 last_texture = -1;
00410 continue;
00411 }
00412 }
00413
00414 glBindTexture( GL_TEXTURE_2D, (*textureMap_)[texture] );
00415
00416
00417 last_texture = texture;
00418
00419 }
00420
00421 glBegin(GL_TRIANGLES);
00422
00423 glNormal(mesh_.normal(f_it));
00424 glColor(mesh_.color(f_it.handle()));
00425
00426 for (fh_it = mesh_.cfh_iter(f_it.handle());fh_it;++fh_it)
00427 {
00428 point = mesh_.point(mesh_.to_vertex_handle(fh_it));
00429 tex2d = mesh_.property(texture_coord_property,fh_it);
00430 glTexCoord2f(tex2d[0], tex2d[1]);
00431 glVertex(point);
00432 }
00433
00434 glEnd();
00435
00436 }
00437 }
00438 }
00439 else
00440 {
00441
00442 }
00443 break;
00444 }
00445
00446 }
00447 }
00448
00449
00450
00451 }
00452 }
00453