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 #include "Teddy/Maths/Matrix.h"
00026 #include "Teddy/Models/Element.h"
00027 #include "Teddy/Models/GeometryIterator.h"
00028 #include "Teddy/Models/Vertex.h"
00029 #include "Teddy/SysSupport/Messages.h"
00030 #include <algorithm>
00031 using namespace std;
00032 using namespace Teddy::Maths;
00033 using namespace Teddy::SysSupport;
00034
00035
00036 namespace Teddy {
00037 namespace Models {
00038
00039
00040 const unsigned long Element::EL_HAS_ELEMENT_NORMAL = (1L<< 0L);
00041 const unsigned long Element::EL_USE_ELEMENT_NORMAL = (1L<< 1L);
00042 const unsigned long Element::EL_USE_VERTEX_NORMALS = (1L<< 2L);
00043
00044 const unsigned long Element::VX_HAS_PARENT = (1L<< 3L);
00045 const unsigned long Element::VX_HAS_VERTEX = (1L<< 4L);
00046 const unsigned long Element::VX_HAS_NORMAL = (1L<< 5L);
00047 const unsigned long Element::VX_HAS_COLOR = (1L<< 6L);
00048 const unsigned long Element::VX_HAS_TEXTURE = (1L<< 7L);
00049
00050 const unsigned long Element::VX_USE_THIS_VERTEX = (1L<< 8L);
00051 const unsigned long Element::VX_USE_THIS_NORMAL = (1L<< 9L);
00052 const unsigned long Element::VX_USE_THIS_COLOR = (1L<<10L);
00053 const unsigned long Element::VX_USE_THIS_TEXTURE = (1L<<11L);
00054
00055 const unsigned long Element::VX_USE_PARENT_VERTEX = (1L<<12L);
00056 const unsigned long Element::VX_USE_PARENT_NORMAL = (1L<<13L);
00057 const unsigned long Element::VX_USE_PARENT_COLOR = (1L<<14L);
00058 const unsigned long Element::VX_USE_PARENT_TEXTURE = (1L<<15L);
00059
00060 const unsigned long Element::VX_TRAVERSAL_VISITED = (1L<<16L);
00061
00062 const unsigned long Element::VX_USE_PARENT_ALL =
00063 Element::VX_USE_PARENT_VERTEX |
00064 Element::VX_USE_PARENT_NORMAL |
00065 Element::VX_USE_PARENT_COLOR |
00066 Element::VX_USE_PARENT_TEXTURE;
00067 ;
00068
00069
00070 Element::Element( unsigned long options )
00071 :
00072 Options( options ),
00073 normal ( 0, 1, 0 )
00074 {
00075 }
00076
00077
00079 Element::~Element(){
00080 }
00081
00082
00084 void Element::debug(){
00085 }
00086
00087
00089 void Element::add( Vertex *v ){
00090 vertices.push_front( v );
00091
00092 }
00093
00094
00096 void Element::add( const float x, const float y, const float z ){
00097 Vertex *v = new Vertex(x,y,z);
00098 vertices.push_front( v );
00099
00100 }
00101
00102
00104 void Element::append( Vertex *v ){
00105 vertices.push_back( v );
00106
00107 }
00108
00109
00111 void Element::append( const float x, const float y, const float z ){
00112 Vertex *v = new Vertex(x,y,z);
00113 vertices.push_back( v );
00114
00115 }
00116
00117
00119 void Element::setNormal( const Vector &normal ){
00120 enable( EL_HAS_ELEMENT_NORMAL );
00121 this->normal = normal;
00122 }
00123 void Element::setNormal( const float x, const float y, const float z ){
00124 enable( EL_HAS_ELEMENT_NORMAL );
00125 normal = Vector( x, y, z );
00126 }
00127
00128
00130 const Vector &Element::getNormal() const {
00131 return normal;
00132 }
00133
00134
00136 bool Element::contains( const Vertex *v ) const {
00137 if( find( vertices.begin(), vertices.end(), v ) != vertices.end() )
00138 {
00139 return true;
00140 }else{
00141 return false;
00142 }
00143 }
00144
00145
00150 void Element::reverse(){
00151 vertices.reverse();
00152 }
00153
00154
00160 void Element::makeNormal(){
00161 list<Vertex*>::iterator v_i1 = vertices.begin();
00162 list<Vertex*>::iterator v_i2 = v_i1;
00163
00164 if( vertices.size()<3 ){
00165 dmsg( M_WARN,
00166 "Element does not have enough vertices for normal calculation (%d vertices found)",
00167 vertices.size()
00168 );
00169 normal = Vector(0,1,0);
00170 return;
00171 }
00172
00173 float len;
00174
00175
00176
00177
00178
00179 int max_count = vertices.size() * 3;
00180 v_i1++;
00181 if( v_i1 == vertices.end() ) v_i1 = vertices.begin();
00182 v_i1++;
00183 if( v_i1 == vertices.end() ) v_i1 = vertices.begin();
00184 do{
00185 max_count--;
00186 if( max_count <=0 ){
00187 dmsg( M_WARN, "Element had not good vertices for normal calculation" );
00188 normal = Vector(0,1,0);
00189 return;
00190 }
00191 v_i2 = v_i1++;
00192 if( v_i1 == vertices.end() ) v_i1 = vertices.begin();
00193
00194 if( v_i2 == vertices.end() ) v_i2 = vertices.begin();
00195 Vector a = (*v_i2++)->getVertex();
00196
00197 if( v_i2 == vertices.end() ) v_i2 = vertices.begin();
00198 Vector b = (*v_i2++)->getVertex();
00199
00200 if( v_i2 == vertices.end() ) v_i2 = vertices.begin();
00201 Vector c = (*v_i2++)->getVertex();
00202
00203 Vector ac = a-c; ac.normalize();
00204 Vector ab = a-b; ab.normalize();
00205 if( (ac | ab) > 1 - 2*FLT_EPSILON ){
00206
00207 continue;
00208 }
00209 normal = ac^ab;
00210 normal.normalize();
00211 len = normal.magnitude();
00212 }while( len < 0.9f || len > 1.1f );
00213
00214 enable( EL_HAS_ELEMENT_NORMAL | EL_USE_ELEMENT_NORMAL );
00215 }
00216
00217
00218 void Element::makeConvexNormal(){
00219 makeNormal();
00220 list<Vertex*>::iterator v_it = vertices.begin();
00221
00222 Vector a = (*v_it)->getVertex();
00223 double dp = a | normal;
00224
00225 if( dp < 0 ){
00226 reverse ();
00227 makeNormal();
00228 }
00229 }
00230
00231
00233 void Element::smooth( float max_smoothing_angle ){
00234 }
00235
00236
00238 #if defined( TEDDY_INCLUDE_COLDET )
00239 int Element::addToCollisionModel( Teddy::ColDet::CollisionModel3D *collision_model ){
00240 return 0;
00241 }
00242 #endif
00243
00244
00245 void Element::clearTraversal(){
00246 list<Vertex*>::const_iterator v_it = vertices.begin();
00247 while( v_it != vertices.end() ){
00248 Vertex *vertex = *v_it;
00249 vertex->disable( VX_TRAVERSAL_VISITED );
00250 v_it++;
00251 }
00252 }
00253
00254
00255 double Element::getMaxVector() const {
00256 double max_len = 0;
00257 list<Vertex*>::const_iterator v_it = vertices.begin();
00258 while( v_it != vertices.end() ){
00259 Vertex *vertex = *v_it;
00260 double len = vertex->getVertex().magnitude();
00261 if( len > max_len ){
00262 max_len = len;
00263 }
00264 v_it++;
00265 }
00266 return max_len;
00267 }
00268
00269
00273 void Element::transformVertices( const Matrix &m, const Matrix &normal_matrix, const bool rev ){
00274 list<Vertex*>::iterator v_it = vertices.begin();
00275 while( v_it != vertices.end() ){
00276 Vertex *vertex = *v_it;
00277 if( vertex->isDisabled(VX_TRAVERSAL_VISITED) ){
00278 vertex->enable ( VX_TRAVERSAL_VISITED );
00279 vertex->transform( m, normal_matrix );
00280 }
00281 v_it++;
00282 }
00283 if( rev == true ){
00284 reverse();
00285 }
00286 if( isEnabled(EL_HAS_ELEMENT_NORMAL) ){
00287 normal = normal_matrix * normal;
00288 normal.normalize();
00289 }
00290 }
00291
00292
00293 #if 0
00294
00295 unsigned long Element::countCSGFaceElements(){
00296 return 1;
00297 }
00298
00299
00300
00301 unsigned long Element::countCSGVertexElements(){
00302 return vertices.size();
00303 }
00304
00305
00306 void Element::initCSGFace( GeometryIterator *gi ){
00307 gi->face_v_it = vertices.begin();
00308 gi->face_data = 0;
00309 }
00310
00311
00312 void Element::initCSGVertex( GeometryIterator *gi ){
00313 gi->vertex_v_it = vertices.begin();
00314 gi->vertex_data = 0;
00315 }
00316
00317
00318 bool Element::stepCSGVertex( GeometryIterator *gi ){
00319 gi->vertex_data++;
00320 gi->vertex_v_it++;
00321 if( gi->vertex_v_it == vertices.end() ){
00322 return false;
00323 }else{
00324 return true;
00325 }
00326 }
00327
00328
00329 void Element::fillCSGVertex( GeometryIterator *gi, CSG_IVertex *vertex ){
00330 Vertex *vx = *(gi->vertex_v_it);
00331 Vector &v = vx->getVertex();
00332 vertex->position[0] = v[0];
00333 vertex->position[1] = v[1];
00334 vertex->position[2] = v[2];
00335 }
00336
00337
00338 bool stepCSGFace( GeometryIterator *gi ){
00339 return false;
00340 }
00341
00342
00343 void fillCSGFace( GeometryIterator *gi, CSG_IFace *face ){
00344 return;
00345 }
00346 #endif
00347
00348
00349 };
00350 };
00351