Main Page   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Namespace Members   Compound Members   File Members   Related Pages  

Geometry.cpp

Go to the documentation of this file.
00001 
00002 /*
00003     TEDDY - General graphics application library
00004     Copyright (C) 1999-2002  Timo Suoranta
00005     tksuoran@cc.helsinki.fi
00006 
00007     This library is free software; you can redistribute it and/or
00008     modify it under the terms of the GNU Lesser General Public
00009     License as published by the Free Software Foundation; either
00010     version 2.1 of the License, or (at your option) any later version.
00011 
00012     This library is distributed in the hope that it will be useful,
00013     but WITHOUT ANY WARRANTY; without even the implied warranty of
00014     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015     Lesser General Public License for more details.
00016 
00017     You should have received a copy of the GNU Lesser General Public
00018     License along with this library; if not, write to the Free Software
00019     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00020 
00021     $Id: Geometry.cpp,v 1.7 2002/02/16 12:41:39 tksuoran Exp $
00022 */
00023 
00024 
00025 #include "Teddy/TeddyConfig.h"
00026 #include "Teddy/Graphics/Device.h"
00027 #include "Teddy/Models/Element.h"
00028 #include "Teddy/Models/Geometry.h"
00029 #include "Teddy/SysSupport/Messages.h"
00030 using namespace Teddy::SysSupport;
00031 
00032 
00033 namespace Teddy  {
00034 namespace Models {
00035 
00036 
00037 int Geometry::draw_count = 0;
00038 
00039 
00041 Geometry::Geometry(){
00042     gl_list_id = glGenLists( 1 );
00043     dirty      = true;
00044 }
00045 
00046 
00048 void Geometry::beginUpdate( Projection *p ){
00049     glNewList( gl_list_id, GL_COMPILE );
00050 }
00051 
00052 
00054 void Geometry::endUpdate( Projection *p ){
00055     glEndList();
00056     dirty = false;
00057 }
00058 
00059 
00061 void Geometry::draw( Projection *p ){
00062     Geometry::draw_count++;
00063     if( dirty==true ){
00064         beginUpdate ( p );
00065         drawElements( p );
00066         endUpdate   ( p );
00067     }
00068     if( dirty==false ){
00069         glCallList( gl_list_id );
00070     }
00071 }
00072 
00073 
00074 void Geometry::clearTraversal(){
00075     list<Element*>::const_iterator e_it = elements.begin();
00076     while( e_it!=elements.end() ){
00077         (*e_it)->clearTraversal();
00078         e_it++;
00079     }
00080 }
00081 
00083 void Geometry::transformVertices( const Matrix &m, const Matrix &normal_matrix, const bool reverse ){
00084     list<Element*>::const_iterator e_it = elements.begin();
00085     while( e_it!=elements.end() ){
00086         (*e_it)->transformVertices( m, normal_matrix, reverse );
00087         e_it++;
00088     }
00089     dirty = true;
00090 }
00091 
00092 
00094 double Geometry::getMaxVector(){
00095     double max_len = 0;
00096     list<Element*>::const_iterator e_it = elements.begin();
00097     while( e_it!=elements.end() ){
00098         double len = (*e_it)->getMaxVector();
00099         if( len > max_len ){
00100             max_len = len;
00101         }
00102         e_it++;
00103     }
00104     return max_len;
00105 }
00106 
00107 
00112 Geometry::~Geometry(){
00113 #if !defined( USE_TINY_GL )
00114     glDeleteLists( gl_list_id, 1 );
00115 #endif
00116 }
00117 
00119 
00123 void Geometry::insert( Element *e ){
00124     elements.push_back( e );
00125 }
00126 
00127 
00132 /*virtual*/ void Geometry::beginElements( Projection *p ){
00133 }
00134 
00135 
00140 /*virtual*/ void Geometry::drawElements( Projection *p ){
00141     beginElements( p );
00142 
00143     list<Element*>::const_iterator e_it = elements.begin();
00144     while( e_it!=elements.end() ){
00145         (*e_it)->draw( p );
00146         e_it++;
00147     }
00148 
00149     endElements( p );
00150 }
00151 
00152 
00157 /*virtual*/ void Geometry::endElements( Projection *p ){
00158 }
00159 
00160 
00167 void Geometry::smooth( float max_smoothing_angle ){
00168     list<Element*>::iterator  e_it;
00169     Element                  *element;
00170     int                       element_smooth = 0;
00171 
00172     //  Ror each Face element, smooth it.
00173     e_it = elements.begin();
00174     while( e_it != elements.end() ){
00175         element = (*e_it);
00176         if( element != NULL ){
00177             element->smooth( max_smoothing_angle );
00178             element_smooth++;
00179         }
00180         e_it++;
00181     }
00182 
00183     dmsg( M_TMAP, "Elements smoothed: %d", element_smooth );
00184 }
00185 
00186 
00187 
00188 
00189 
00190 
00191 
00192 
00193 
00194 
00195 
00196 
00197 
00198 
00199 #if 0
00200 
00201 
00202 class GeometryIterator {
00203 public:
00204     GeometryIterator( Geometry *g ){
00205         geometry = g;
00206         e_it = g->geometry->
00207     }
00208     int  faceItDone   (){
00209         // NO-OP
00210     }
00211 
00212     void faceItFill   ( CSG_IFace *face ){
00213         e_it->csgFill( face );
00214     }
00215 
00216     void faceItStep   (){
00217         bool same_element = e_it->csgStep();
00218         if( same_element == false ){
00219             e_it++;
00220             e_it->csgPrepare();
00221         }
00222     }
00223     void faceItReset  (){
00224 
00225     }
00226     int  vertexItDone ();
00227     void vertexItFill ( CSG_IVertex *face );
00228     void vertexItStep ();
00229     void vertexItReset();
00230 
00231 protected:
00232     Geometry                  *geometry;  //  what geometry
00233     list<Element*>::iterator   e_it;      //  what element  -> face
00234     list<Vertex*> ::iterator   v_it;
00235 };
00236 
00237 
00238 /*
00239 typedef struct  {
00240     int    vertex_index[4];
00241     int    vertex_number;
00242 
00243     void  *user_face_vertex_data[4];
00244     void  *user_face_data;
00245 } CSG_IFace;
00246 typedef struct  {
00247     float position[3];
00248 } CSG_IVertex;
00249 */
00250 
00251 bool ObjectManager::csg(){
00252 
00253     // Create a boolean operation handle
00254     CSG_BooleanOperation *operation = CSG_NewBooleanFunction();
00255     if( operation == NULL ){
00256         // deal with low memory exception
00257         return;
00258     }
00259 
00260     // Describe each mesh operand to the module.
00261     // NOTE: example properties!
00262     CSG_MeshPropertyDescriptor propA;
00263     CSG_MeshPropertyDescriptor propB;
00264     propA.user_data_size        = 0;
00265     propA.user_face_vertex_data = 0;
00266     propB.user_data_size        = 0;
00267     propB.user_face_vertex_data = 0;
00268 
00269     // Get the output properties of the mesh.
00270     CSG_MeshPropertyDescriptor output_properties = CSG_DescibeOperands( operation, propA, propB );
00271 
00272     // Report to the user if they will loose any data!
00273     ...;
00274 
00275     // Get some mesh iterators for your mesh data structures
00276     CSG_FaceIteratorDescriptor   face_it_desc;
00277     CSG_VertexIteratorDescriptor vertex_it_desc;
00278     face_it_desc  .it           = NULL;
00279     face_it_desc  .Done         = FaceItDone;
00280     face_it_desc  .Fill         = FaceItFill;
00281     face_it_desc  .Step         = FaceItStep;
00282     face_it_desc  .Reset        = FaceItReset;
00283     face_it_desc  .num_elements = 0;
00284     vertex_it_desc.it           = NULL;
00285     vertex_it_desc.Done         = VertexItDone;
00286     vertex_it_desc.Fill         = VertexItFill;
00287     vertex_it_desc.Step         = VertexItStep;
00288     vertex_it_desc.Reset        = VertexItReset;
00289     vertex_it_desc.num_elements = 0;
00290 
00291     CSG_FaceIteratorDescriptor   obA_faces = ...;
00292     CSG_VertexIteratorDescriptor obA_verts = ...;
00293 
00294     // same for object B
00295     CSG_FaceIteratorDescriptor   obB_faces = ...;
00296     CSG_VertexIteratorDescriptor obB_verts = ...;
00297 
00298     // perform the operation...!
00299 
00300     int success = CSG_PerformBooleanOperation( operation, e_csg_intersection, obA_faces, obA_vertices, obB_faces, obB_vertices );
00301 
00302     // if the operation fails, report miserable failure to user
00303     // and clear up data structures.
00304     if( !success ){
00305         ...;
00306         CSG_FreeBooleanOperation( operation );
00307         return;
00308     }
00309 
00310     // read the new mesh vertices back from the module
00311     // and assign to your own mesh structure.
00312 
00313     // First we need to create a CSG_IVertex so the module can fill it in.
00314     CSG_IVertex vertex;
00315     CSG_VertexIteratorDescriptor *verts_it = CSG_OutputVertexDescriptor( operation );
00316 
00317     // initialize your vertex container with the number of verts (verts_it->num_elements)
00318 
00319     while( !verts_it->Done(verts_it->it) ){
00320         verts_it->Fill( verts_it->it, &vertex );
00321 
00322         // create a new vertex of your own type and add it
00323         // to your mesh structure.
00324 
00325         verts_it->Step( verts_it->it );
00326     }
00327     // Free the vertex iterator
00328     CSG_FreeVertexDescriptor( verts_it );
00329   
00330     // similarly for faces.
00331     CSG_IFace face;
00332 
00333     // you may need to reserve some memory in face->user_data here.
00334 
00335     // initialize your face container with the number of faces (faces_it->num_elements)
00336 
00337     CSG_FaceIteratorDescriptor *faces_it = CSG_OutputFaceDescriptor( operation );
00338     while( !faces_it->Done(faces_it->it) ){
00339         faces_it->Fill( faces_it->it, &face );
00340 
00341         // create a new face of your own type and add it
00342         // to your mesh structure.
00343         faces_it->Step( &faces_it->it );
00344     }
00345 
00346     // Free the face iterator
00347     CSG_FreeVertexDescriptor( faces_it );
00348 
00349     // that's it free the operation.
00350     CSG_FreeBooleanOperation( operation );
00351     return;
00352 }
00353 
00354 
00355 
00356 
00357 
00358 
00359 
00360 
00361 
00362 
00363 
00364 
00365 
00366 
00367 
00368 
00369 /*
00370  * CSG_IFace -- an interface polygon structure.
00371  *
00372  * vertex_index    is a fixed size array of 4 elements containing indices into
00373  *                 an abstract vertex container. 3 or 4 of these elements may be used to
00374  *                 describe either quads or triangles.
00375  * vertex_number   is the number of vertices in this face - either 3 or 4.
00376  * vertex_colors   is an array of {r,g,b} triplets one for each vertex index.
00377  * tex_coords      is an array of {u,v} triplets one for each vertex index.
00378  * user_data       is a pointer to arbitary data of fixed width,
00379  *                 this data is copied around with the face, and duplicated if a face is
00380  *                  split. Contains things like material index.
00381  */
00382 
00383 typedef struct  {
00384     int    vertex_index[4];
00385     int    vertex_number;
00386 
00387     void  *user_face_vertex_data[4];
00388     void  *user_face_data;
00389 } CSG_IFace;
00390 
00391 
00392 typedef struct  {
00393     float position[3];
00394 } CSG_IVertex;
00395 
00396 
00397 /* Descibes the data stored in a mesh available through the
00398  * CSG_IFace interface.
00399  *
00400  * user_data_size              is the number of bytes of user_data associated with each CSG_IFace
00401  * user_face_vertex_data_size  is the number of bytes of user data associated with
00402  *                             every face vertex tuple.
00403  */
00404 
00405 typedef struct CSG_MeshPropertyDescriptor{
00406     unsigned int user_face_vertex_data_size;
00407     unsigned int user_data_size;
00408 } CSG_MeshPropertyDescriptor;
00409 
00410 
00411 
00412 /* The iterator is used in the following manner.
00413  * 
00414  *   MyIterator *iterator = ...
00415  *   DataType    data;
00416  * 
00417  *   while (!IsDone(iterator)) {
00418  *      Fill(iterator,&data);
00419  *      //process information pointed to by data 
00420  *      ...
00421  *      Step(iterator);
00422  *   } 
00423  * 
00424  * The CSG module does not want to know about the implementation of these
00425  * functions  so we use the c function ptr mechanism to hide them. Our
00426  * iterator descriptor now looks like this.
00427  */
00428 
00429 typedef void * CSG_IteratorPtr;
00430 typedef int  (*CSG_FaceItDoneFunc )(CSG_IteratorPtr it);
00431 typedef void (*CSG_FaceItFillFunc )(CSG_IteratorPtr it,CSG_IFace *face);
00432 typedef void (*CSG_FaceItStepFunc )(CSG_IteratorPtr it);
00433 typedef void (*CSG_FaceItResetFunc)(CSG_IteratorPtr it);
00434 
00435 
00436 //  Similarly to walk through the vertex arrays we have.
00437 typedef int  (*CSG_VertexItDoneFunc )(CSG_IteratorPtr it);
00438 typedef void (*CSG_VertexItFillFunc )(CSG_IteratorPtr it,CSG_IVertex *face);
00439 typedef void (*CSG_VertexItStepFunc )(CSG_IteratorPtr it);
00440 typedef void (*CSG_VertexItResetFunc)(CSG_IteratorPtr it);
00441 
00442 typedef struct CSG_VertexIteratorDescriptor {
00443     CSG_IteratorPtr        it;
00444     CSG_VertexItDoneFunc   Done;
00445     CSG_VertexItFillFunc   Fill;
00446     CSG_VertexItStepFunc   Step;
00447     CSG_VertexItResetFunc  Reset;
00448     unsigned int           num_elements;
00449 } CSG_VertexIteratorDescriptor;
00450 
00451 /* The actual iterator structures are not exposed to the CSG module, they
00452  * will contain datatypes specific to blender. */
00453 
00454 /* The functions below are to be used in the following way:
00455  * 
00456  *  // Create a boolean operation handle
00457  *  CSG_BooleanOperation *operation = CSG_NewBooleanFunction();
00458  *  if (operation == NULL) {
00459  *     // deal with low memory exception
00460  *  }
00461  *
00462  *  // Describe each mesh operand to the module.
00463  *  // NOTE: example properties!
00464  *  CSG_MeshPropertyDescriptor propA,propB;
00465  *  propA.user_data_size = 0;
00466  *  propA.user_face_vertex_data = 0;
00467  *  propB.user_face_vertex_data = 0;
00468  *  propB.user_data_size = 0;
00469  *
00470  *  // Get the output properties of the mesh.
00471  *  CSG_MeshPropertyDescriptor output_properties;
00472  *  output_properties = CSG_DescibeOperands(
00473  *    operation,
00474  *    propA,
00475  *    propB
00476  *  );
00477  * 
00478  *  // Report to the user if they will loose any data!
00479  *  ...
00480  * 
00481  *  // Get some mesh iterators for your mesh data structures
00482  *  CSG_FaceIteratorDescriptor obA_faces = ...
00483  *  CSG_VertexIteratorDescriptor obA_verts = ...
00484  *  
00485  *  // same for object B
00486  *  CSG_FaceIteratorDescriptor obB_faces = ...
00487  *  CSG_VertexIteratorDescriptor obB_verts = ...
00488  *  
00489  *  // perform the operation...!
00490  *
00491  *  int success = CSG_PerformBooleanOperation(
00492  *     operation,
00493  *     e_csg_intersection,
00494  *     obA_faces,
00495  *     obA_vertices,
00496  *     obB_faces,
00497  *     obB_vertices
00498  *  );
00499  *
00500  *  // if the operation fails report miserable failure to user
00501  *  // and clear up data structures.
00502  *  if (!success) {
00503  *    ...
00504  *    CSG_FreeBooleanOperation(operation);
00505  *    return;
00506  *  }
00507  *
00508  *  // read the new mesh vertices back from the module
00509  *  // and assign to your own mesh structure.
00510  *
00511  *  // First we need to create a CSG_IVertex so the module can fill it in.
00512  *  CSG_IVertex vertex;
00513  *  CSG_VertexIteratorDescriptor * verts_it = CSG_OutputVertexDescriptor(operation);
00514  *
00515  *  // initialize your vertex container with the number of verts (verts_it->num_elements)
00516  * 
00517  *  while (!verts_it->Done(verts_it->it)) {
00518  *      verts_it->Fill(verts_it->it,&vertex);
00519  *
00520  *      // create a new vertex of your own type and add it
00521  *      // to your mesh structure.
00522  *      verts_it->Step(verts_it->it);
00523  *  }
00524  *  // Free the vertex iterator
00525  *  CSG_FreeVertexDescriptor(verts_it);
00526  * 
00527  *  // similarly for faces.
00528  *  CSG_IFace face;
00529  *
00530  *  // you may need to reserve some memory in face->user_data here.
00531  * 
00532  *  // initialize your face container with the number of faces (faces_it->num_elements)
00533  * 
00534  *  CSG_FaceIteratorDescriptor * faces_it = CSG_OutputFaceDescriptor(operation);
00535  * 
00536  *  while (!faces_it->Done(faces_it->it)) {
00537  *      faces_it->Fill(faces_it->it,&face);
00538  *
00539  *      // create a new face of your own type and add it
00540  *      // to your mesh structure.
00541  *      faces_it->Step(&faces_it->it);
00542  *  }
00543  *  
00544  *  // Free the face iterator
00545  *  CSG_FreeVertexDescriptor(faces_it);
00546  *
00547  *  // that's it free the operation.
00548  *
00549  *  CSG_FreeBooleanOperation(operation);
00550  *  return;
00551  *  
00552  */
00553 
00558 typedef enum {
00559     e_csg_union,
00560     e_csg_intersection,
00561     e_csg_difference,
00562     e_csg_classify
00563 } CSG_OperationType;
00564 
00571 typedef struct {
00572     void *CSG_info;
00573 } CSG_BooleanOperation;
00574 
00580     CSG_BooleanOperation * 
00581 CSG_NewBooleanFunction(
00582     void
00583 );
00584 
00585 
00586 #endif
00587 
00588 
00589 
00590 
00591 
00592 };  //  namespace Models
00593 };  //  namespace Teddy
00594 
00595