|
IrrlichtEngine
|
00001 // Copyright (C) 2007-2011 Nikolaus Gebhardt / Thomas Alten 00002 // This file is part of the "Irrlicht Engine". 00003 // For conditions of distribution and use, see copyright notice in irrlicht.h 00004 00005 #ifndef __I_ANIMATED_MESH_MD3_H_INCLUDED__ 00006 #define __I_ANIMATED_MESH_MD3_H_INCLUDED__ 00007 00008 #include "IAnimatedMesh.h" 00009 #include "IQ3Shader.h" 00010 #include "quaternion.h" 00011 00012 namespace irr 00013 { 00014 namespace scene 00015 { 00016 00017 enum eMD3Models 00018 { 00019 EMD3_HEAD = 0, 00020 EMD3_UPPER, 00021 EMD3_LOWER, 00022 EMD3_WEAPON, 00023 EMD3_NUMMODELS 00024 }; 00025 00027 enum EMD3_ANIMATION_TYPE 00028 { 00029 // Animations for both lower and upper parts of the player 00030 EMD3_BOTH_DEATH_1 = 0, 00031 EMD3_BOTH_DEAD_1, 00032 EMD3_BOTH_DEATH_2, 00033 EMD3_BOTH_DEAD_2, 00034 EMD3_BOTH_DEATH_3, 00035 EMD3_BOTH_DEAD_3, 00036 00037 // Animations for the upper part 00038 EMD3_TORSO_GESTURE, 00039 EMD3_TORSO_ATTACK_1, 00040 EMD3_TORSO_ATTACK_2, 00041 EMD3_TORSO_DROP, 00042 EMD3_TORSO_RAISE, 00043 EMD3_TORSO_STAND_1, 00044 EMD3_TORSO_STAND_2, 00045 00046 // Animations for the lower part 00047 EMD3_LEGS_WALK_CROUCH, 00048 EMD3_LEGS_WALK, 00049 EMD3_LEGS_RUN, 00050 EMD3_LEGS_BACK, 00051 EMD3_LEGS_SWIM, 00052 EMD3_LEGS_JUMP_1, 00053 EMD3_LEGS_LAND_1, 00054 EMD3_LEGS_JUMP_2, 00055 EMD3_LEGS_LAND_2, 00056 EMD3_LEGS_IDLE, 00057 EMD3_LEGS_IDLE_CROUCH, 00058 EMD3_LEGS_TURN, 00059 00061 EMD3_ANIMATION_COUNT 00062 }; 00063 00064 struct SMD3AnimationInfo 00065 { 00067 s32 first; 00069 s32 num; 00071 s32 looping; 00073 s32 fps; 00074 }; 00075 00076 00077 // byte-align structures 00078 #if defined(_MSC_VER) || defined(__BORLANDC__) || defined (__BCPLUSPLUS__) 00079 # pragma pack( push, packing ) 00080 # pragma pack( 1 ) 00081 # define PACK_STRUCT 00082 #elif defined( __GNUC__ ) 00083 # define PACK_STRUCT __attribute__((packed)) 00084 #else 00085 # error compiler not supported 00086 #endif 00087 00089 struct SMD3Header 00090 { 00091 c8 headerID[4]; //id of file, always "IDP3" 00092 s32 Version; //this is a version number, always 15 00093 s8 fileName[68]; //sometimes left Blank... 65 chars, 32bit aligned == 68 chars 00094 s32 numFrames; //number of KeyFrames 00095 s32 numTags; //number of 'tags' per frame 00096 s32 numMeshes; //number of meshes/skins 00097 s32 numMaxSkins; //maximum number of unique skins used in md3 file. artefact md2 00098 s32 frameStart; //starting position of frame-structur 00099 s32 tagStart; //starting position of tag-structures 00100 s32 tagEnd; //ending position of tag-structures/starting position of mesh-structures 00101 s32 fileSize; 00102 }; 00103 00105 struct SMD3MeshHeader 00106 { 00107 c8 meshID[4]; //id, must be IDP3 00108 c8 meshName[68]; //name of mesh 65 chars, 32 bit aligned == 68 chars 00109 00110 s32 numFrames; //number of meshframes in mesh 00111 s32 numShader; //number of skins in mesh 00112 s32 numVertices; //number of vertices 00113 s32 numTriangles; //number of Triangles 00114 00115 s32 offset_triangles; //starting position of Triangle data, relative to start of Mesh_Header 00116 s32 offset_shaders; //size of header 00117 s32 offset_st; //starting position of texvector data, relative to start of Mesh_Header 00118 s32 vertexStart; //starting position of vertex data,relative to start of Mesh_Header 00119 s32 offset_end; 00120 }; 00121 00122 00124 struct SMD3Vertex 00125 { 00126 s16 position[3]; 00127 u8 normal[2]; 00128 }; 00129 00131 struct SMD3TexCoord 00132 { 00133 f32 u; 00134 f32 v; 00135 }; 00136 00138 struct SMD3Face 00139 { 00140 s32 Index[3]; 00141 }; 00142 00143 00144 // Default alignment 00145 #if defined(_MSC_VER) || defined(__BORLANDC__) || defined (__BCPLUSPLUS__) 00146 # pragma pack( pop, packing ) 00147 #endif 00148 00149 #undef PACK_STRUCT 00150 00152 struct SMD3MeshBuffer : public IReferenceCounted 00153 { 00154 SMD3MeshHeader MeshHeader; 00155 00156 core::stringc Shader; 00157 core::array < s32 > Indices; 00158 core::array < SMD3Vertex > Vertices; 00159 core::array < SMD3TexCoord > Tex; 00160 }; 00161 00163 00164 struct SMD3QuaternionTag 00165 { 00166 virtual ~SMD3QuaternionTag() 00167 { 00168 position.X = 0.f; 00169 } 00170 00171 // construct copy constructor 00172 SMD3QuaternionTag( const SMD3QuaternionTag & copyMe ) 00173 { 00174 *this = copyMe; 00175 } 00176 00177 // construct for searching 00178 SMD3QuaternionTag( const core::stringc& name ) 00179 : Name ( name ) {} 00180 00181 // construct from a matrix 00182 SMD3QuaternionTag ( const core::stringc& name, const core::matrix4 &m ) 00183 : Name(name), position(m.getTranslation()), rotation(m) {} 00184 00185 // construct from a position and euler angles in degrees 00186 SMD3QuaternionTag ( const core::vector3df &pos, const core::vector3df &angle ) 00187 : position(pos), rotation(angle * core::DEGTORAD) {} 00188 00189 // set to matrix 00190 void setto ( core::matrix4 &m ) 00191 { 00192 rotation.getMatrix ( m, position ); 00193 } 00194 00195 bool operator == ( const SMD3QuaternionTag &other ) const 00196 { 00197 return Name == other.Name; 00198 } 00199 00200 SMD3QuaternionTag & operator=( const SMD3QuaternionTag & copyMe ) 00201 { 00202 Name = copyMe.Name; 00203 position = copyMe.position; 00204 rotation = copyMe.rotation; 00205 return *this; 00206 } 00207 00208 core::stringc Name; 00209 core::vector3df position; 00210 core::quaternion rotation; 00211 }; 00212 00214 struct SMD3QuaternionTagList 00215 { 00216 SMD3QuaternionTagList() 00217 { 00218 Container.setAllocStrategy(core::ALLOC_STRATEGY_SAFE); 00219 } 00220 00221 // construct copy constructor 00222 SMD3QuaternionTagList(const SMD3QuaternionTagList& copyMe) 00223 { 00224 *this = copyMe; 00225 } 00226 00227 virtual ~SMD3QuaternionTagList() {} 00228 00229 SMD3QuaternionTag* get(const core::stringc& name) 00230 { 00231 SMD3QuaternionTag search ( name ); 00232 s32 index = Container.linear_search ( search ); 00233 if ( index >= 0 ) 00234 return &Container[index]; 00235 return 0; 00236 } 00237 00238 u32 size () const 00239 { 00240 return Container.size(); 00241 } 00242 00243 void set_used(u32 new_size) 00244 { 00245 s32 diff = (s32) new_size - (s32) Container.allocated_size(); 00246 if ( diff > 0 ) 00247 { 00248 SMD3QuaternionTag e(""); 00249 for ( s32 i = 0; i < diff; ++i ) 00250 Container.push_back(e); 00251 } 00252 } 00253 00254 const SMD3QuaternionTag& operator[](u32 index) const 00255 { 00256 return Container[index]; 00257 } 00258 00259 SMD3QuaternionTag& operator[](u32 index) 00260 { 00261 return Container[index]; 00262 } 00263 00264 void push_back(const SMD3QuaternionTag& other) 00265 { 00266 Container.push_back(other); 00267 } 00268 00269 SMD3QuaternionTagList& operator = (const SMD3QuaternionTagList & copyMe) 00270 { 00271 Container = copyMe.Container; 00272 return *this; 00273 } 00274 00275 private: 00276 core::array < SMD3QuaternionTag > Container; 00277 }; 00278 00279 00281 struct SMD3Mesh: public IReferenceCounted 00282 { 00283 SMD3Mesh () 00284 { 00285 MD3Header.numFrames = 0; 00286 } 00287 00288 virtual ~SMD3Mesh() 00289 { 00290 for (u32 i=0; i<Buffer.size(); ++i) 00291 Buffer[i]->drop(); 00292 } 00293 00294 core::stringc Name; 00295 core::array<SMD3MeshBuffer*> Buffer; 00296 SMD3QuaternionTagList TagList; 00297 SMD3Header MD3Header; 00298 }; 00299 00300 00302 class IAnimatedMeshMD3 : public IAnimatedMesh 00303 { 00304 public: 00305 00307 virtual void setInterpolationShift(u32 shift, u32 loopMode) =0; 00308 00310 virtual SMD3QuaternionTagList* getTagList(s32 frame, s32 detailLevel, s32 startFrameLoop, s32 endFrameLoop) =0; 00311 00313 virtual SMD3Mesh* getOriginalMesh() =0; 00314 }; 00315 00316 } // end namespace scene 00317 } // end namespace irr 00318 00319 #endif 00320