Table <\/a>7.1 Common 3ds Chunks and Their Uses<\/p>\nID Number Use<\/p>\n
0x4D4D Used at the start of the file to signify that the file is a 3ds file.<\/p>\n
0x0002 Holds the version number of the file.<\/p>\n
0x4000 Contains an \u201cobject\u201d such as a mesh, camera, or light.<\/p>\n
Each 0x4000 chunk contains sub-chunks with vertex, texture coordinate, and other information.<\/p>\n
0x4100 A sub-chunk of 0x4000. A 0x4100 chunk contains every\u00ad<\/p>\n
thing needed to build a mesh of triangles.<\/p>\n
0x4110 Contains the vertices for the object. It is a sub-chunk of<\/p>\n
0x4100.<\/p>\n
0x4120 Also a sub-chunk of 0x4100, a 0x4120 chunk contains the<\/p>\n
face information, including the vertex indexes that tell which vertices make up each face.<\/p>\n
0x4130 Another sub-chunk of 0x4100, 0x4130 contains informa\u00ad<\/p>\n
tion on which materials are to be applied to which faces.<\/p>\n
0x4140 Even another sub-chunk of 0x4100, this chunk contains the<\/p>\n
texture coordinates that allow a face to be texture mapped.<\/p>\n
0xAFFF A material definition is found inside 0xAFFF, colors for<\/p>\n
ambient, diffuse, and specular materials, as well as shininess and transparency are in this chunk.<\/p>\n
0xA000 A sub-chunk of 0xAFFF that contains the material’s name.<\/p>\n
0xA010 A sub-chunk of 0xAFFF as well, contains the ambient<\/p>\n
color for the material.<\/p>\n
0xA020 Another sub-chunk of 0xAFF, 0xA020 contains the diffuse<\/p>\n
color of the material.<\/p>\n
0xA030 A fourth sub-chunk of 0xAFF, this contains the specular<\/p>\n
highlight colors for the specific material.<\/p>\n
0xA040 Yet another 0xAFFF sub-chunk, this time contains the<\/p>\n
shininess of the material.<\/p>\n
0xA050 Again, a sub-chunk of 0xAFFF that controls how transpar\u00ad<\/p>\n
ent or opaque a material is.<\/p>\n
0xA200 0xA200 is also a sub-chunk of the 0xAFFF chunk. This<\/p>\n
chunk stores the filename of the texture map or skin for the current material.<\/p>\n<\/p>\n
meshes. Loading lights and cameras could interfere with other parts of your game and lead to some very strange looking visual artifacts. How\u00adever, you might want to look into loading and using the lights if you are interested in using the 3ds format for a level or world format.<\/p>\n
The 0x4000 chunk contains a little bit of data by itself; the rest is wrapped up within sub-chunks. It contains a null-terminated string that stores the mesh name. Because the string\u2019s length is not set, it must be null terminated. Using strcpy on the data buffer can extract this name. However, if you are using a temporary pointer to move through the array, make sure you move it strlen(m_cName) + 1 bytes to account for the null terminator on the end of the string. After the string is read, the rest of the data length is full of sub-chunks. Keep in mind there may be a lot of meshes in the same file, so be sure to keep track of where you are.<\/p>\n
\/\/pseudocode to begin reading the 0x4000 chunk<\/p>\n
if chunkID is 0x4000<\/p>\n
read null terminated string (strcpy)<\/p>\n
advance pointer past string and null pointer (strlen+1)<\/p>\n
Triangular Mesh 0x4100<\/a><\/p>\nThis is where the data you really want is. A triangular mesh chunk holds just that, a mesh containing triangles. A mesh is a group of polygons that make up a surface; a triangular mesh is the same except it consists of only triangles. In the 0x4100 chunk are the vertices, face, and texture coordinates, as well as the face material information.<\/p>\n
Before you worry about reading in this data, you need a place to store it. That is where the S3dsMesh structure comes in. Each S3dsMesh struc\u00adture holds one triangular mesh. Because the file does not reveal how many meshes there are total, you can call on the power of STL and std::vector to create a place to store any number of meshes.<\/p>\n
Here is the mesh structure:<\/p>\n
\/\/—————————————————————————-<\/p>\n
\/\/- S3dsMesh \/\/- Group Mesh Data struct S3dsMesh {<\/p>\n
char m_cName[256];<\/p>\n
<\/p>\n
};<\/p>\n
The first variable (m_cName) is the mesh name. This should be set when you first enter the 0x4000 chunk, because that is where the name string is located. You need to be careful here. The string within the 3ds model is unrestricted; it can be any length. However, in your structure there is only 256 bytes of storage. Hopefully, this will be enough to hold any of the mesh names, but be sure to check first. If the length of the string in the file exceeds 256 characters, you will need to truncate it before storing.<\/p>\n
The rest of the data is contained in sub-chunks of the 0x4100 chunk. (Yes, you can have sub-chunks of sub-chunks!) Because you do not know how many vertices, faces, or materials there will be, you may want to use a std::vector. This is essentially a resizable array. Using std::vectors, you can add as many objects to your array as you like without allocating or resizing it. If you aren\u2019t sure about how to use std::vectors, I suggest you skip to Appendix B.<\/p>\n
In the next section, you learn about the sub-chunks of the 0x4100 chunk. These chunks hold information about vertices, texture coordi\u00adnates, faces, and materials. A particular object can have all of these sub-chunks, or just a few. An object doesn\u2019t have to contain texture coordinate and material information.<\/p>\n
Vertices 0x4110<\/a><\/p>\nThe 0x4110 sub-chunk of the 0x4100 chunk contains all of the vertex information for the mesh. This includes the X, Y, and Z coordinates for each vertex. (Thankfully, it does not contain another level of sub\u00adchunks.) The vertices are stored in the mesh structure in the m_vVertices vector array.<\/p>\n
Each vector is simply three floating-point values, wrapped in a structure for clarity. Here is the very simple, fairly boring S3dsVertex structure. You may notice that the vertex class here contains three floats, rather than a CVector3 class like the MS3D vertices did. I chose to do this for a reason. Because the vertices do not need to be transformed like those from<\/p>\n
<\/p>\n