1 /* 2 Open Asset Import Library (assimp) 3 ---------------------------------------------------------------------- 4 5 Copyright (c) 2006-2017, assimp team 6 7 All rights reserved. 8 9 Redistribution and use of this software in source and binary forms, 10 with or without modification, are permitted provided that the 11 following conditions are met: 12 13 * Redistributions of source code must retain the above 14 copyright notice, this list of conditions and the 15 following disclaimer. 16 17 * Redistributions in binary form must reproduce the above 18 copyright notice, this list of conditions and the 19 following disclaimer in the documentation and/or other 20 materials provided with the distribution. 21 22 * Neither the name of the assimp team, nor the names of its 23 contributors may be used to endorse or promote products 24 derived from this software without specific prior 25 written permission of the assimp team. 26 27 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 28 "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 29 LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 30 A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 31 OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 32 SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 33 LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 34 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 35 THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 36 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 37 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 38 39 ---------------------------------------------------------------------- 40 */ 41 42 /** @file Defines helper data structures for the import of 3DS files */ 43 44 #ifndef AI_3DSFILEHELPER_H_INC 45 #define AI_3DSFILEHELPER_H_INC 46 47 #include "SpatialSort.h" 48 #include "SmoothingGroups.h" 49 #include "StringUtils.h" 50 #include "qnan.h" 51 #include <assimp/material.h> 52 #include <assimp/camera.h> 53 #include <assimp/light.h> 54 #include <assimp/anim.h> 55 #include <stdio.h> //sprintf 56 57 namespace Assimp { 58 namespace D3DS { 59 60 #include "./../include/assimp/Compiler/pushpack1.h" 61 62 // --------------------------------------------------------------------------- 63 /** Discreet3DS class: Helper class for loading 3ds files. Defines chunks 64 * and data structures. 65 */ 66 class Discreet3DS { 67 private: Discreet3DS()68 Discreet3DS() { 69 // empty 70 } 71 ~Discreet3DS()72 ~Discreet3DS() { 73 // empty 74 } 75 76 public: 77 //! data structure for a single chunk in a .3ds file 78 struct Chunk { 79 uint16_t Flag; 80 uint32_t Size; 81 } PACK_STRUCT; 82 83 84 //! Used for shading field in material3ds structure 85 //! From AutoDesk 3ds SDK 86 typedef enum 87 { 88 // translated to gouraud shading with wireframe active 89 Wire = 0x0, 90 91 // if this material is set, no vertex normals will 92 // be calculated for the model. Face normals + gouraud 93 Flat = 0x1, 94 95 // standard gouraud shading 96 Gouraud = 0x2, 97 98 // phong shading 99 Phong = 0x3, 100 101 // cooktorrance or anistropic phong shading ... 102 // the exact meaning is unknown, if you know it 103 // feel free to tell me ;-) 104 Metal = 0x4, 105 106 // required by the ASE loader 107 Blinn = 0x5 108 } shadetype3ds; 109 110 // Flags for animated keys 111 enum 112 { 113 KEY_USE_TENS = 0x1, 114 KEY_USE_CONT = 0x2, 115 KEY_USE_BIAS = 0x4, 116 KEY_USE_EASE_TO = 0x8, 117 KEY_USE_EASE_FROM = 0x10 118 } ; 119 120 enum 121 { 122 123 // ******************************************************************** 124 // Basic chunks which can be found everywhere in the file 125 CHUNK_VERSION = 0x0002, 126 CHUNK_RGBF = 0x0010, // float4 R; float4 G; float4 B 127 CHUNK_RGBB = 0x0011, // int1 R; int1 G; int B 128 129 // Linear color values (gamma = 2.2?) 130 CHUNK_LINRGBF = 0x0013, // float4 R; float4 G; float4 B 131 CHUNK_LINRGBB = 0x0012, // int1 R; int1 G; int B 132 133 CHUNK_PERCENTW = 0x0030, // int2 percentage 134 CHUNK_PERCENTF = 0x0031, // float4 percentage 135 CHUNK_PERCENTD = 0x0032, // float8 percentage 136 // ******************************************************************** 137 138 // Prj master chunk 139 CHUNK_PRJ = 0xC23D, 140 141 // MDLI master chunk 142 CHUNK_MLI = 0x3DAA, 143 144 // Primary main chunk of the .3ds file 145 CHUNK_MAIN = 0x4D4D, 146 147 // Mesh main chunk 148 CHUNK_OBJMESH = 0x3D3D, 149 150 // Specifies the background color of the .3ds file 151 // This is passed through the material system for 152 // viewing purposes. 153 CHUNK_BKGCOLOR = 0x1200, 154 155 // Specifies the ambient base color of the scene. 156 // This is added to all materials in the file 157 CHUNK_AMBCOLOR = 0x2100, 158 159 // Specifies the background image for the whole scene 160 // This value is passed through the material system 161 // to the viewer 162 CHUNK_BIT_MAP = 0x1100, 163 CHUNK_BIT_MAP_EXISTS = 0x1101, 164 165 // ******************************************************************** 166 // Viewport related stuff. Ignored 167 CHUNK_DEFAULT_VIEW = 0x3000, 168 CHUNK_VIEW_TOP = 0x3010, 169 CHUNK_VIEW_BOTTOM = 0x3020, 170 CHUNK_VIEW_LEFT = 0x3030, 171 CHUNK_VIEW_RIGHT = 0x3040, 172 CHUNK_VIEW_FRONT = 0x3050, 173 CHUNK_VIEW_BACK = 0x3060, 174 CHUNK_VIEW_USER = 0x3070, 175 CHUNK_VIEW_CAMERA = 0x3080, 176 // ******************************************************************** 177 178 // Mesh chunks 179 CHUNK_OBJBLOCK = 0x4000, 180 CHUNK_TRIMESH = 0x4100, 181 CHUNK_VERTLIST = 0x4110, 182 CHUNK_VERTFLAGS = 0x4111, 183 CHUNK_FACELIST = 0x4120, 184 CHUNK_FACEMAT = 0x4130, 185 CHUNK_MAPLIST = 0x4140, 186 CHUNK_SMOOLIST = 0x4150, 187 CHUNK_TRMATRIX = 0x4160, 188 CHUNK_MESHCOLOR = 0x4165, 189 CHUNK_TXTINFO = 0x4170, 190 CHUNK_LIGHT = 0x4600, 191 CHUNK_CAMERA = 0x4700, 192 CHUNK_HIERARCHY = 0x4F00, 193 194 // Specifies the global scaling factor. This is applied 195 // to the root node's transformation matrix 196 CHUNK_MASTER_SCALE = 0x0100, 197 198 // ******************************************************************** 199 // Material chunks 200 CHUNK_MAT_MATERIAL = 0xAFFF, 201 202 // asciiz containing the name of the material 203 CHUNK_MAT_MATNAME = 0xA000, 204 CHUNK_MAT_AMBIENT = 0xA010, // followed by color chunk 205 CHUNK_MAT_DIFFUSE = 0xA020, // followed by color chunk 206 CHUNK_MAT_SPECULAR = 0xA030, // followed by color chunk 207 208 // Specifies the shininess of the material 209 // followed by percentage chunk 210 CHUNK_MAT_SHININESS = 0xA040, 211 CHUNK_MAT_SHININESS_PERCENT = 0xA041 , 212 213 // Specifies the shading mode to be used 214 // followed by a short 215 CHUNK_MAT_SHADING = 0xA100, 216 217 // NOTE: Emissive color (self illumination) seems not 218 // to be a color but a single value, type is unknown. 219 // Make the parser accept both of them. 220 // followed by percentage chunk (?) 221 CHUNK_MAT_SELF_ILLUM = 0xA080, 222 223 // Always followed by percentage chunk (?) 224 CHUNK_MAT_SELF_ILPCT = 0xA084, 225 226 // Always followed by percentage chunk 227 CHUNK_MAT_TRANSPARENCY = 0xA050, 228 229 // Diffuse texture channel 0 230 CHUNK_MAT_TEXTURE = 0xA200, 231 232 // Contains opacity information for each texel 233 CHUNK_MAT_OPACMAP = 0xA210, 234 235 // Contains a reflection map to be used to reflect 236 // the environment. This is partially supported. 237 CHUNK_MAT_REFLMAP = 0xA220, 238 239 // Self Illumination map (emissive colors) 240 CHUNK_MAT_SELFIMAP = 0xA33d, 241 242 // Bumpmap. Not specified whether it is a heightmap 243 // or a normal map. Assme it is a heightmap since 244 // artist normally prefer this format. 245 CHUNK_MAT_BUMPMAP = 0xA230, 246 247 // Specular map. Seems to influence the specular color 248 CHUNK_MAT_SPECMAP = 0xA204, 249 250 // Holds shininess data. 251 CHUNK_MAT_MAT_SHINMAP = 0xA33C, 252 253 // Scaling in U/V direction. 254 // (need to gen separate UV coordinate set 255 // and do this by hand) 256 CHUNK_MAT_MAP_USCALE = 0xA354, 257 CHUNK_MAT_MAP_VSCALE = 0xA356, 258 259 // Translation in U/V direction. 260 // (need to gen separate UV coordinate set 261 // and do this by hand) 262 CHUNK_MAT_MAP_UOFFSET = 0xA358, 263 CHUNK_MAT_MAP_VOFFSET = 0xA35a, 264 265 // UV-coordinates rotation around the z-axis 266 // Assumed to be in radians. 267 CHUNK_MAT_MAP_ANG = 0xA35C, 268 269 // Tiling flags for 3DS files 270 CHUNK_MAT_MAP_TILING = 0xa351, 271 272 // Specifies the file name of a texture 273 CHUNK_MAPFILE = 0xA300, 274 275 // Specifies whether a materail requires two-sided rendering 276 CHUNK_MAT_TWO_SIDE = 0xA081, 277 // ******************************************************************** 278 279 // Main keyframer chunk. Contains translation/rotation/scaling data 280 CHUNK_KEYFRAMER = 0xB000, 281 282 // Supported sub chunks 283 CHUNK_TRACKINFO = 0xB002, 284 CHUNK_TRACKOBJNAME = 0xB010, 285 CHUNK_TRACKDUMMYOBJNAME = 0xB011, 286 CHUNK_TRACKPIVOT = 0xB013, 287 CHUNK_TRACKPOS = 0xB020, 288 CHUNK_TRACKROTATE = 0xB021, 289 CHUNK_TRACKSCALE = 0xB022, 290 291 // ******************************************************************** 292 // Keyframes for various other stuff in the file 293 // Partially ignored 294 CHUNK_AMBIENTKEY = 0xB001, 295 CHUNK_TRACKMORPH = 0xB026, 296 CHUNK_TRACKHIDE = 0xB029, 297 CHUNK_OBJNUMBER = 0xB030, 298 CHUNK_TRACKCAMERA = 0xB003, 299 CHUNK_TRACKFOV = 0xB023, 300 CHUNK_TRACKROLL = 0xB024, 301 CHUNK_TRACKCAMTGT = 0xB004, 302 CHUNK_TRACKLIGHT = 0xB005, 303 CHUNK_TRACKLIGTGT = 0xB006, 304 CHUNK_TRACKSPOTL = 0xB007, 305 CHUNK_FRAMES = 0xB008, 306 // ******************************************************************** 307 308 // light sub-chunks 309 CHUNK_DL_OFF = 0x4620, 310 CHUNK_DL_OUTER_RANGE = 0x465A, 311 CHUNK_DL_INNER_RANGE = 0x4659, 312 CHUNK_DL_MULTIPLIER = 0x465B, 313 CHUNK_DL_EXCLUDE = 0x4654, 314 CHUNK_DL_ATTENUATE = 0x4625, 315 CHUNK_DL_SPOTLIGHT = 0x4610, 316 317 // camera sub-chunks 318 CHUNK_CAM_RANGES = 0x4720 319 }; 320 }; 321 322 // --------------------------------------------------------------------------- 323 /** Helper structure representing a 3ds mesh face */ 324 struct Face : public FaceWithSmoothingGroup 325 { 326 }; 327 328 // --------------------------------------------------------------------------- 329 /** Helper structure representing a texture */ 330 struct Texture 331 { 332 //! Default constructor TextureTexture333 Texture() 334 : mOffsetU (0.0) 335 , mOffsetV (0.0) 336 , mScaleU (1.0) 337 , mScaleV (1.0) 338 , mRotation (0.0) 339 , mMapMode (aiTextureMapMode_Wrap) 340 , bPrivate() 341 , iUVSrc (0) 342 { 343 mTextureBlend = get_qnan(); 344 } 345 346 //! Specifies the blend factor for the texture 347 ai_real mTextureBlend; 348 349 //! Specifies the filename of the texture 350 std::string mMapName; 351 352 //! Specifies texture coordinate offsets/scaling/rotations 353 ai_real mOffsetU; 354 ai_real mOffsetV; 355 ai_real mScaleU; 356 ai_real mScaleV; 357 ai_real mRotation; 358 359 //! Specifies the mapping mode to be used for the texture 360 aiTextureMapMode mMapMode; 361 362 //! Used internally 363 bool bPrivate; 364 int iUVSrc; 365 }; 366 367 #include "./../include/assimp/Compiler/poppack1.h" 368 369 // --------------------------------------------------------------------------- 370 /** Helper structure representing a 3ds material */ 371 struct Material 372 { 373 //! Default constructor. Builds a default name for the material MaterialMaterial374 Material() 375 : mDiffuse ( ai_real( 0.6 ), ai_real( 0.6 ), ai_real( 0.6 ) ) // FIX ... we won't want object to be black 376 , mSpecularExponent ( ai_real( 0.0 ) ) 377 , mShininessStrength ( ai_real( 1.0 ) ) 378 , mShading(Discreet3DS::Gouraud) 379 , mTransparency ( ai_real( 1.0 ) ) 380 , mBumpHeight ( ai_real( 1.0 ) ) 381 , mTwoSided (false) 382 { 383 static int iCnt = 0; 384 385 char szTemp[128]; 386 ai_snprintf(szTemp, 128, "UNNAMED_%i",iCnt++); 387 mName = szTemp; 388 } 389 390 //! Name of the material 391 std::string mName; 392 //! Diffuse color of the material 393 aiColor3D mDiffuse; 394 //! Specular exponent 395 ai_real mSpecularExponent; 396 //! Shininess strength, in percent 397 ai_real mShininessStrength; 398 //! Specular color of the material 399 aiColor3D mSpecular; 400 //! Ambient color of the material 401 aiColor3D mAmbient; 402 //! Shading type to be used 403 Discreet3DS::shadetype3ds mShading; 404 //! Opacity of the material 405 ai_real mTransparency; 406 //! Diffuse texture channel 407 Texture sTexDiffuse; 408 //! Opacity texture channel 409 Texture sTexOpacity; 410 //! Specular texture channel 411 Texture sTexSpecular; 412 //! Reflective texture channel 413 Texture sTexReflective; 414 //! Bump texture channel 415 Texture sTexBump; 416 //! Emissive texture channel 417 Texture sTexEmissive; 418 //! Shininess texture channel 419 Texture sTexShininess; 420 //! Scaling factor for the bump values 421 ai_real mBumpHeight; 422 //! Emissive color 423 aiColor3D mEmissive; 424 //! Ambient texture channel 425 //! (used by the ASE format) 426 Texture sTexAmbient; 427 //! True if the material must be rendered from two sides 428 bool mTwoSided; 429 }; 430 431 // --------------------------------------------------------------------------- 432 /** Helper structure to represent a 3ds file mesh */ 433 struct Mesh : public MeshWithSmoothingGroups<D3DS::Face> 434 { 435 //! Default constructor MeshMesh436 Mesh() 437 { 438 static int iCnt = 0; 439 440 // Generate a default name for the mesh 441 char szTemp[128]; 442 ai_snprintf(szTemp, 128, "UNNAMED_%i",iCnt++); 443 mName = szTemp; 444 } 445 446 //! Name of the mesh 447 std::string mName; 448 449 //! Texture coordinates 450 std::vector<aiVector3D> mTexCoords; 451 452 //! Face materials 453 std::vector<unsigned int> mFaceMaterials; 454 455 //! Local transformation matrix 456 aiMatrix4x4 mMat; 457 }; 458 459 // --------------------------------------------------------------------------- 460 /** Float key - quite similar to aiVectorKey and aiQuatKey. Both are in the 461 C-API, so it would be difficult to make them a template. */ 462 struct aiFloatKey 463 { 464 double mTime; ///< The time of this key 465 ai_real mValue; ///< The value of this key 466 467 #ifdef __cplusplus 468 469 // time is not compared 470 bool operator == (const aiFloatKey& o) const 471 {return o.mValue == this->mValue;} 472 473 bool operator != (const aiFloatKey& o) const 474 {return o.mValue != this->mValue;} 475 476 // Only time is compared. This operator is defined 477 // for use with std::sort 478 bool operator < (const aiFloatKey& o) const 479 {return mTime < o.mTime;} 480 481 bool operator > (const aiFloatKey& o) const 482 {return mTime > o.mTime;} 483 484 #endif 485 }; 486 487 // --------------------------------------------------------------------------- 488 /** Helper structure to represent a 3ds file node */ 489 struct Node 490 { NodeNode491 Node(): 492 mParent(NULL) 493 , mInstanceNumber(0) 494 , mHierarchyPos (0) 495 , mHierarchyIndex (0) 496 , mInstanceCount (1) 497 { 498 static int iCnt = 0; 499 500 // Generate a default name for the node 501 char szTemp[128]; 502 ::ai_snprintf(szTemp, 128, "UNNAMED_%i",iCnt++); 503 mName = szTemp; 504 505 aRotationKeys.reserve (20); 506 aPositionKeys.reserve (20); 507 aScalingKeys.reserve (20); 508 } 509 ~NodeNode510 ~Node() 511 { 512 for (unsigned int i = 0; i < mChildren.size();++i) 513 delete mChildren[i]; 514 } 515 516 //! Pointer to the parent node 517 Node* mParent; 518 519 //! Holds all child nodes 520 std::vector<Node*> mChildren; 521 522 //! Name of the node 523 std::string mName; 524 525 //! InstanceNumber of the node 526 int32_t mInstanceNumber; 527 528 //! Dummy nodes: real name to be combined with the $$$DUMMY 529 std::string mDummyName; 530 531 //! Position of the node in the hierarchy (tree depth) 532 int16_t mHierarchyPos; 533 534 //! Index of the node 535 int16_t mHierarchyIndex; 536 537 //! Rotation keys loaded from the file 538 std::vector<aiQuatKey> aRotationKeys; 539 540 //! Position keys loaded from the file 541 std::vector<aiVectorKey> aPositionKeys; 542 543 //! Scaling keys loaded from the file 544 std::vector<aiVectorKey> aScalingKeys; 545 546 547 // For target lights (spot lights and directional lights): 548 // The position of the target 549 std::vector< aiVectorKey > aTargetPositionKeys; 550 551 // For cameras: the camera roll angle 552 std::vector< aiFloatKey > aCameraRollKeys; 553 554 //! Pivot position loaded from the file 555 aiVector3D vPivot; 556 557 //instance count, will be kept only for the first node 558 int32_t mInstanceCount; 559 560 //! Add a child node, setup the right parent node for it 561 //! \param pc Node to be 'adopted' push_backNode562 inline Node& push_back(Node* pc) 563 { 564 mChildren.push_back(pc); 565 pc->mParent = this; 566 return *this; 567 } 568 }; 569 // --------------------------------------------------------------------------- 570 /** Helper structure analogue to aiScene */ 571 struct Scene 572 { 573 //! List of all materials loaded 574 //! NOTE: 3ds references materials globally 575 std::vector<Material> mMaterials; 576 577 //! List of all meshes loaded 578 std::vector<Mesh> mMeshes; 579 580 //! List of all cameras loaded 581 std::vector<aiCamera*> mCameras; 582 583 //! List of all lights loaded 584 std::vector<aiLight*> mLights; 585 586 //! Pointer to the root node of the scene 587 // --- moved to main class 588 // Node* pcRootNode; 589 }; 590 591 592 } // end of namespace D3DS 593 } // end of namespace Assimp 594 595 #endif // AI_XFILEHELPER_H_INC 596