00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "ac3dobject.h"
00021
00022 #include "macros.h"
00023 #include "ac3dmacros.h"
00024
00025 #include <cstring>
00026
00027
00028 namespace AC3D {
00029
00030
00031
00032 AC3DObject::AC3DObject():
00033 strName(""),
00034 fCrease(45),
00035 uiNumVert(0),
00036 uiNumSurf(0),
00037 uiKids(0)
00038 {
00039
00040 OPENCITY_DEBUG("ctor1");
00041
00042 this->ac3dSetDefault();
00043 }
00044
00045
00046
00047 AC3DObject::AC3DObject
00048 (
00049 stringstream& data
00050 ):
00051 strName(""),
00052 fCrease(45),
00053 uiNumVert(0),
00054 uiNumSurf(0),
00055 uiKids(0)
00056 {
00057
00058
00059 this->ac3dSetDefault();
00060 this->Parse( data );
00061 }
00062
00063
00064
00065 AC3DObject::~AC3DObject()
00066 {
00067
00068 vector<AC3DObject*>::size_type pos, size;
00069
00070
00071 size = this->vpObject.size();
00072 for (pos = 0; pos < size; pos++)
00073 delete vpObject[pos];
00074
00075 size = this->vpSurface.size();
00076 for (pos = 0; pos < size; pos++)
00077 delete vpSurface[pos];
00078 }
00079
00080
00081
00082 void
00083 AC3DObject::AddKid
00084 (
00085 AC3DObject* kid
00086 )
00087 {
00088 this->vpObject.push_back( kid );
00089 }
00090
00091
00092
00093 bool
00094 AC3DObject::IsTranslucent() const
00095 {
00096 return (this->strName.find("alpha") != string::npos);
00097 }
00098
00099
00100
00101 string
00102 AC3DObject::GetName() const
00103 {
00104 return this->strName;
00105 }
00106
00107
00108
00109 unsigned int
00110 AC3DObject::GetNumberKid() const
00111 {
00112 return this->uiKids;
00113 }
00114
00115
00116
00117 const string&
00118 AC3DObject::GetTextureFile() const
00119 {
00120 return this->strTexture;
00121 }
00122
00123
00124
00125 const float*
00126 AC3DObject::GetLoc() const
00127 {
00128 return this->fLoc;
00129 }
00130
00131
00132
00133 const vector<Vertex>&
00134 AC3DObject::GetVVertex() const
00135 {
00136 return this->vVertex;
00137 }
00138
00139
00140
00141 const vector<AC3DSurface*>&
00142 AC3DObject::GetVPSurface() const
00143 {
00144 return this->vpSurface;
00145 }
00146
00147
00148
00149 const vector<AC3DObject*>&
00150 AC3DObject::GetVPObject() const
00151 {
00152 return this->vpObject;
00153 }
00154
00155
00156
00157 void
00158 AC3DObject::Parse(
00159 stringstream& data
00160 )
00161 {
00162 char line[AC3D_MAX_LINE_LENGTH];
00163 char cstr[AC3D_MAX_LINE_LENGTH];
00164
00165
00166
00167 data.getline( line, AC3D_MAX_LINE_LENGTH );
00168 while (data.good()) {
00169 if ( strncmp( line, AC3D_TOKEN_OBJECT, AC3D_TOKEN_OBJECT_L ) == 0 ) {
00170 sscanf( line, "OBJECT %s", cstr );
00171 if (strncmp( cstr, "world", 5 ) == 0)
00172 this->type = OBJECT_WORLD;
00173 else if (strncmp( cstr, "poly", 5 ) == 0)
00174 this->type = OBJECT_POLYGON;
00175 else if (strncmp( cstr, "group", 5 ) == 0)
00176 this->type = OBJECT_GROUP;
00177 data.getline( line, AC3D_MAX_LINE_LENGTH );
00178 } else
00179 if ( strncmp( line, AC3D_TOKEN_NAME, AC3D_TOKEN_NAME_L ) == 0 ) {
00180 sscanf( line, "name %s", cstr );
00181 this->strName = cstr;
00182 data.getline( line, AC3D_MAX_LINE_LENGTH );
00183 } else
00184 if ( strncmp( line, AC3D_TOKEN_TEXTURE, AC3D_TOKEN_TEXTURE_L ) == 0 ) {
00185 sscanf( line, "texture %s", cstr );
00186 this->strTexture = cstr;
00187
00188 if (this->strTexture.size() >= 2) {
00189 this->strTexture = this->strTexture.substr( 1, this->strTexture.size()-2 );
00190 } else {
00191 OPENCITY_DEBUG("Unable to strip doublequotes");
00192 }
00193 data.getline( line, AC3D_MAX_LINE_LENGTH );
00194 } else
00195 if ( strncmp( line, AC3D_TOKEN_TEXREP, AC3D_TOKEN_TEXREP_L ) == 0 ) {
00196 sscanf( line, "texrep %f %f", this->fTexRep, this->fTexRep+1 );
00197 data.getline( line, AC3D_MAX_LINE_LENGTH );
00198 } else
00199 if ( strncmp( line, AC3D_TOKEN_ROT, AC3D_TOKEN_ROT_L ) == 0 ) {
00200 sscanf(
00201 line,
00202 "rot %f %f %f %f %f %f %f %f %f",
00203 this->fRot , this->fRot+1, this->fRot+2,
00204 this->fRot+3, this->fRot+4, this->fRot+5,
00205 this->fRot+6, this->fRot+7, this->fRot+8
00206 );
00207 data.getline( line, AC3D_MAX_LINE_LENGTH );
00208 } else
00209 if ( strncmp( line, AC3D_TOKEN_LOC, AC3D_TOKEN_LOC_L ) == 0 ) {
00210 sscanf( line, "loc %f %f %f", this->fLoc, this->fLoc+1, this->fLoc+2 );
00211 data.getline( line, AC3D_MAX_LINE_LENGTH );
00212 } else
00213 if ( strncmp( line, AC3D_TOKEN_CREASE, AC3D_TOKEN_CREASE_L ) == 0 ) {
00214 sscanf( line, "crease %f", &(this->fCrease) );
00215 data.getline( line, AC3D_MAX_LINE_LENGTH );
00216 } else
00217 if ( strncmp( line, AC3D_TOKEN_URL, AC3D_TOKEN_URL_L ) == 0 ) {
00218 sscanf( line, "url %s", cstr );
00219 this->strURL = cstr;
00220 data.getline( line, AC3D_MAX_LINE_LENGTH );
00221 } else
00222 if ( strncmp( line, AC3D_TOKEN_KIDS, AC3D_TOKEN_KIDS_L ) == 0 ) {
00223 sscanf( line, "kids %u", &(this->uiKids) );
00224 data.getline( line, AC3D_MAX_LINE_LENGTH );
00225 } else
00226 if ( strncmp( line, AC3D_TOKEN_NUMVERT, AC3D_TOKEN_NUMVERT_L ) == 0 ) {
00227 sscanf( line, "numvert %u", &(this->uiNumVert) );
00228 ac3dobjectParseVertex( this->uiNumVert, data, line );
00229 } else
00230 if ( strncmp( line, AC3D_TOKEN_NUMSURF, AC3D_TOKEN_NUMSURF_L ) == 0 ) {
00231 sscanf( line, "numsurf %u", &(this->uiNumSurf) );
00232 ac3dobjectParseSurface( this->uiNumSurf, data, line );
00233 } else {
00234 OPENCITY_DEBUG("WARNING: unknown command discarded. See below: ");
00235 OPENCITY_DEBUG( line );
00236 data.getline( line, AC3D_MAX_LINE_LENGTH );
00237 }
00238 }
00239
00240 data.clear();
00241 }
00242
00243
00244
00245 string
00246 AC3DObject::ToStr() const
00247 {
00248 stringstream ss;
00249 vector<AC3DObject*>::size_type pos, size;
00250
00251
00252 ss << "OBJECT ";
00253 switch (this->type) {
00254 case OBJECT_WORLD: ss << "world"; break;
00255 case OBJECT_POLYGON: ss << "poly"; break;
00256 case OBJECT_GROUP: ss << "group"; break;
00257 }
00258 ss << endl;
00259
00260 ss << ((this->strName != "") ? "name " + this->strName + "\n" : "")
00261 << "loc " << this->fLoc[0] << " "
00262 << this->fLoc[1] << " "
00263 << this->fLoc[2] << endl
00264 << "texrep " << this->fTexRep[0] << " "
00265 << this->fTexRep[1] << endl;
00266
00267 ss << ((this->strTexture != "") ? "texture " + this->strTexture + "\n" : "")
00268 << "crease " << this->fCrease << endl
00269 << "numvert " << this->uiNumVert << endl;
00270
00271 size = this->vVertex.size();
00272 for (pos = 0; pos < size; pos++) {
00273 ss << this->vVertex[pos].x << " "
00274 << this->vVertex[pos].y << " "
00275 << this->vVertex[pos].z << endl;
00276 }
00277
00278 ss << "numsurf " << this->uiNumSurf << endl;
00279
00280 size = this->vpSurface.size();
00281 for (pos = 0; pos < size; pos++)
00282 ss << this->vpSurface[pos]->ToStr();
00283
00284 ss << "kids " << this->uiKids << endl;
00285
00286 size = this->vpObject.size();
00287 for (pos = 0; pos < size; pos++)
00288 ss << this->vpObject[pos]->ToStr();
00289
00290 return ss.str();
00291 }
00292
00293
00294
00295
00296
00297 void
00298 AC3DObject::ac3dSetDefault()
00299 {
00300
00301 this->fTexRep[0] = 1.;
00302 this->fTexRep[1] = 1.;
00303
00304
00305 this->fLoc[0] = 0.; this->fLoc[1] = 0.; this->fLoc[2] = 0.;
00306
00307
00308 this->fRot[0] = 1.; this->fRot[1] = 0.; this->fRot[2] = 0.;
00309 this->fRot[3] = 0.; this->fRot[4] = 1.; this->fRot[5] = 0.;
00310 this->fRot[3] = 0.; this->fRot[4] = 0.; this->fRot[5] = 1.;
00311 }
00312
00313
00314
00315 void
00316 AC3DObject::ac3dobjectParseVertex
00317 (
00318 unsigned int nb,
00319 stringstream& data,
00320 char* buffer
00321 )
00322 {
00323 Vertex newVertex;
00324
00325
00326 data.getline( buffer, AC3D_MAX_LINE_LENGTH );
00327 while (data.good() && (nb-- > 0)) {
00328 sscanf( buffer, "%f %f %f", &newVertex.x, &newVertex.y, &newVertex.z );
00329 this->vVertex.push_back( newVertex );
00330 data.getline( buffer, AC3D_MAX_LINE_LENGTH );
00331 }
00332 }
00333
00334
00335
00336 void
00337 AC3DObject::ac3dobjectParseSurface
00338 (
00339 unsigned int nb,
00340 stringstream& data,
00341 char* buffer
00342 )
00343 {
00344 stringstream ss;
00345
00346 bool endBlock = false;
00347 bool endSurf = false;
00348
00349 AC3DSurface* pSurf = NULL;
00350
00351 data.getline( buffer, AC3D_MAX_LINE_LENGTH );
00352 while (data.good() && !endSurf) {
00353 if ( strncmp( buffer, AC3D_TOKEN_SURF, AC3D_TOKEN_SURF_L ) == 0 ) {
00354 ss << buffer << endl;
00355 data.getline( buffer, AC3D_MAX_LINE_LENGTH );
00356 } else
00357 if ( strncmp( buffer, AC3D_TOKEN_MAT, AC3D_TOKEN_MAT_L ) == 0 ) {
00358 ss << buffer << endl;
00359 data.getline( buffer, AC3D_MAX_LINE_LENGTH );
00360 } else
00361 if ( strncmp( buffer, AC3D_TOKEN_KIDS, AC3D_TOKEN_KIDS_L ) == 0 ) {
00362 endSurf = true;
00363 } else
00364 if ( strncmp( buffer, AC3D_TOKEN_REFS, AC3D_TOKEN_REFS_L ) == 0 ) {
00365 ss << buffer << endl;
00366 data.getline( buffer, AC3D_MAX_LINE_LENGTH );
00367
00368 endBlock = false;
00369 while (data.good() && !endBlock) {
00370
00371
00372 if ((strncmp( buffer, AC3D_TOKEN_SURF, AC3D_TOKEN_SURF_L ) == 0 )
00373 || (strncmp( buffer, AC3D_TOKEN_MAT, AC3D_TOKEN_MAT_L ) == 0 )
00374 || (strncmp( buffer, AC3D_TOKEN_REFS, AC3D_TOKEN_REFS_L ) == 0 )
00375 || (strncmp( buffer, AC3D_TOKEN_KIDS, AC3D_TOKEN_KIDS_L ) == 0 )) {
00376 endBlock = true;
00377 }
00378 else {
00379
00380 ss << buffer << endl;
00381 data.getline( buffer, AC3D_MAX_LINE_LENGTH );
00382 }
00383 }
00384
00385
00386 pSurf = new AC3DSurface( ss );
00387 this->vpSurface.push_back( pSurf );
00388 ss.str("");
00389 }
00390 }
00391
00392 }
00393
00394
00395 }
00396
00397
00398
00399
00400
00401
00402
00403
00404
00405
00406
00407
00408
00409
00410
00411
00412
00413
00414
00415
00416
00417
00418
00419
00420