Пример #1
0
        internal static W3dMesh Parse(BinaryReader reader, W3dParseContext context)
        {
            return(ParseChunk(reader, context, header =>
            {
                var result = new W3dMesh();

                ParseChunks(reader, context.CurrentEndPosition, chunkType =>
                {
                    switch (chunkType)
                    {
                    case W3dChunkType.W3D_CHUNK_MESH_HEADER3:
                        result.Header = W3dMeshHeader3.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_VERTICES:
                        result.Vertices = W3dVector3List.Parse(reader, context, chunkType);
                        break;

                    case W3dChunkType.W3D_CHUNK_VERTEX_NORMALS:
                        result.Normals = W3dVector3List.Parse(reader, context, chunkType);
                        break;

                    case W3dChunkType.W3D_CHUNK_VERTEX_INFLUENCES:
                        result.Influences = W3dVertexInfluences.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_TRIANGLES:
                        result.Triangles = W3dTriangles.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_VERTEX_SHADE_INDICES:
                        result.ShadeIndices = W3dUInt32List.Parse(reader, context, chunkType);
                        break;

                    case W3dChunkType.W3D_CHUNK_MATERIAL_INFO:
                        result.MaterialInfo = W3dMaterialInfo.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_VERTEX_MATERIALS:
                        result.VertexMaterials = W3dVertexMaterials.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_SHADERS:
                        result.Shaders = W3dShaders.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_PS2_SHADERS:
                        result.ShadersPs2 = W3dShadersPs2.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_TEXTURES:
                        result.Textures = W3dTextures.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_MATERIAL_PASS:
                        result.MaterialPasses.Add(W3dMaterialPass.Parse(reader, context));
                        break;

                    case W3dChunkType.W3D_CHUNK_AABTREE:
                        result.AabTree = W3dMeshAabTree.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_MESH_USER_TEXT:
                        result.UserText = W3dMeshUserText.Parse(reader, context);
                        break;

                    case W3dChunkType.W3D_CHUNK_VERTICES_2:
                        result.Vertices2 = W3dVector3List.Parse(reader, context, chunkType);
                        break;

                    case W3dChunkType.W3D_CHUNK_NORMALS_2:
                        result.Normals2 = W3dVector3List.Parse(reader, context, chunkType);
                        break;

                    case W3dChunkType.W3D_CHUNK_TANGENTS:
                        result.Tangents = W3dVector3List.Parse(reader, context, chunkType);
                        break;

                    case W3dChunkType.W3D_CHUNK_BITANGENTS:
                        result.Bitangents = W3dVector3List.Parse(reader, context, chunkType);
                        break;

                    case W3dChunkType.W3D_CHUNK_SHADER_MATERIALS:
                        result.ShaderMaterials = W3dShaderMaterials.Parse(reader, context);
                        break;

                    default:
                        throw CreateUnknownChunkException(chunkType);
                    }
                });

                return result;
            }));
        }
Пример #2
0
        public static W3dMesh Parse(BinaryReader reader, uint chunkSize)
        {
            var currentMaterialPass = 0;

            var textures = new List <W3dTexture>();

            var finalResult = ParseChunk <W3dMesh>(reader, chunkSize, (result, header) =>
            {
                switch (header.ChunkType)
                {
                case W3dChunkType.W3D_CHUNK_MESH_HEADER3:
                    result.Header       = W3dMeshHeader3.Parse(reader);
                    result.Vertices     = new Vector3[result.Header.NumVertices];
                    result.Normals      = new Vector3[result.Header.NumVertices];
                    result.ShadeIndices = new uint[result.Header.NumVertices];
                    result.Influences   = new W3dVertexInfluence[result.Header.NumVertices];
                    result.Triangles    = new W3dTriangle[result.Header.NumTris];
                    break;

                case W3dChunkType.W3D_CHUNK_VERTICES:
                    for (var count = 0; count < result.Header.NumVertices; count++)
                    {
                        result.Vertices[count] = reader.ReadVector3();
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_VERTEX_NORMALS:
                    for (var count = 0; count < result.Header.NumVertices; count++)
                    {
                        result.Normals[count] = reader.ReadVector3();
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_VERTEX_INFLUENCES:
                    for (var count = 0; count < result.Header.NumVertices; count++)
                    {
                        result.Influences[count] = W3dVertexInfluence.Parse(reader);
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_TRIANGLES:
                    for (var count = 0; count < result.Header.NumTris; count++)
                    {
                        result.Triangles[count] = W3dTriangle.Parse(reader);
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_VERTEX_SHADE_INDICES:
                    for (var count = 0; count < result.Header.NumVertices; count++)
                    {
                        result.ShadeIndices[count] = reader.ReadUInt32();
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_MATERIAL_INFO:
                    result.MaterialInfo   = W3dMaterialInfo.Parse(reader);
                    result.Materials      = new W3dMaterial[result.MaterialInfo.VertexMaterialCount];
                    result.Shaders        = new W3dShader[result.MaterialInfo.ShaderCount];
                    result.MaterialPasses = new W3dMaterialPass[result.MaterialInfo.PassCount];
                    break;

                case W3dChunkType.W3D_CHUNK_VERTEX_MATERIALS:
                    for (var count = 0; count < result.MaterialInfo.VertexMaterialCount; count++)
                    {
                        var innerChunk = W3dChunkHeader.Parse(reader);
                        if (innerChunk.ChunkType == W3dChunkType.W3D_CHUNK_VERTEX_MATERIAL)
                        {
                            result.Materials[count] = W3dMaterial.Parse(reader, innerChunk.ChunkSize);
                        }
                        else
                        {
                            throw CreateUnknownChunkException(innerChunk);
                        }
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_SHADERS:
                    for (var count = 0; count < result.MaterialInfo.ShaderCount; count++)
                    {
                        result.Shaders[count] = W3dShader.Parse(reader);
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_TEXTURES:
                    var startPosition = reader.BaseStream.Position;
                    while (reader.BaseStream.Position < startPosition + header.ChunkSize)
                    {
                        var innerChunk = W3dChunkHeader.Parse(reader);
                        if (innerChunk.ChunkType == W3dChunkType.W3D_CHUNK_TEXTURE)
                        {
                            textures.Add(W3dTexture.Parse(reader, innerChunk.ChunkSize));
                        }
                        else
                        {
                            throw CreateUnknownChunkException(innerChunk);
                        }
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_MATERIAL_PASS:
                    result.MaterialPasses[currentMaterialPass] = W3dMaterialPass.Parse(reader, header.ChunkSize);
                    currentMaterialPass++;
                    break;

                case W3dChunkType.W3D_CHUNK_AABTREE:
                    if (result.AabTree != null)
                    {
                        throw new InvalidDataException();
                    }
                    result.AabTree = W3dMeshAabTree.Parse(reader, header.ChunkSize);
                    break;

                case W3dChunkType.W3D_CHUNK_PS2_SHADERS:
                    // Don't need this.
                    reader.ReadBytes((int)header.ChunkSize);
                    break;

                case W3dChunkType.W3D_CHUNK_MESH_USER_TEXT:
                    // TODO: Do we need this? It has line-separated key/value pairs
                    // for things like mass, elasticity, friction, etc.
                    reader.ReadBytes((int)header.ChunkSize);
                    break;

                case W3dChunkType.W3D_CHUNK_VERTICES_2:
                    result.Vertices2 = new Vector3[result.Header.NumVertices];
                    for (var count = 0; count < result.Vertices2.Length; count++)
                    {
                        result.Vertices2[count] = reader.ReadVector3();
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_NORMALS_2:
                    result.Normals2 = new Vector3[result.Header.NumVertices];
                    for (var count = 0; count < result.Normals2.Length; count++)
                    {
                        result.Normals2[count] = reader.ReadVector3();
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_TANGENTS:
                    result.Tangents = new Vector3[result.Header.NumVertices];
                    for (var count = 0; count < result.Tangents.Length; count++)
                    {
                        result.Tangents[count] = reader.ReadVector3();
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_BITANGENTS:
                    result.Bitangents = new Vector3[result.Header.NumVertices];
                    for (var count = 0; count < result.Bitangents.Length; count++)
                    {
                        result.Bitangents[count] = reader.ReadVector3();
                    }
                    break;

                case W3dChunkType.W3D_CHUNK_SHADER_MATERIALS:
                    result.ShaderMaterials = W3dShaderMaterials.Parse(reader, header.ChunkSize);
                    break;

                default:
                    throw CreateUnknownChunkException(header);
                }
            });

            finalResult.Textures = textures;

            return(finalResult);
        }