private bool is3ds; // usd to shwo that the 4D4D magic number has been found public IOReadResult Read(BinaryReader reader, ReadOptions options, IMeshBuilder builder) { ushort ChunkID; String ChnkID = ""; UInt32 Clength; MeshName = ""; hasMesh = false; is3ds = false; // Process the file - fails very politely when there is no more data while (true) { //Get the Id of the next Chunk try { ChunkID = reader.ReadUInt16(); } catch { break; } ChnkID = ChunkID.ToString("X"); //Get the size of the next chunk in chars Clength = reader.ReadUInt32(); //Process based on Chunk ID switch (ChnkID) { case "4D4D": //This is a new file header is3ds = true; reader.ReadChars(10); break; case "3D3D": //This is a new Object Header reader.ReadChars(10); break; case "4000": //This is an object Block. Store the name temporarily in case it is a mesh List <char> name = new List <char>(); while (true) { char next = reader.ReadChar(); if (next == 0) { break; } name.Add(next); } MeshName = new String(name.ToArray <char>()); break; case "4100": // This is a new Mesh. Retrieve the name and add if the builder supports Metadata builder.AppendNewMesh(false, false, false, false); if (builder.SupportsMetaData) { builder.AppendMetaData("name", MeshName); } break; case "4110": // List of Vertexes ushort VertexCount = reader.ReadUInt16(); for (int x = 0; x < VertexCount; x++) { double X = reader.ReadSingle(); double Y = reader.ReadSingle(); double Z = reader.ReadSingle(); builder.AppendVertex(X, Y, Z); } break; case "4120": // List of Triangles ushort PolygonCount = reader.ReadUInt16(); for (int j = 0; j < PolygonCount; j++) { int a = reader.ReadInt16(); int b = reader.ReadInt16(); int c = reader.ReadInt16(); int flags = reader.ReadUInt16(); builder.AppendTriangle(a, b, c); } break; case "4130": // Mapping from Vertex to Material - retrieved but not currently used List <char> mname = new List <char>(); while (true) { char next = reader.ReadChar(); if (next == 0) { break; } mname.Add(next); } string MatName = new String(mname.ToArray <char>()); ushort entries = reader.ReadUInt16(); for (int i = 0; i < entries; i++) { ushort face = reader.ReadUInt16(); } break; case "4140": // List of UVs per vertex ushort uvCount = reader.ReadUInt16(); for (ushort y = 0; y < uvCount; y++) { Vector2f UV = new Vector2f(reader.ReadSingle(), reader.ReadSingle()); builder.SetVertexUV(y, UV); } break; default: // Any other chunk - retrieved and not used - held in dump temporarily for debug char[] dump = reader.ReadChars((int)Clength - 6); break; } } if (!is3ds) { return(new IOReadResult(IOCode.FileAccessError, "File is not in .3DS format")); } else if (!hasMesh) { return(new IOReadResult(IOCode.FileParsingError, "no mesh found in file")); } else { return(new IOReadResult(IOCode.Ok, "")); } }