private void LoadGmdFile(GmdFile gmdFile) { Name = gmdFile.Name; Textures = gmdFile.Textures.Select(tex => tex.Name).ToArray(); Materials = gmdFile.Materials.Select(mat => { return(new Material { Id = mat.Id, Shader = gmdFile.Shaders[mat.ShaderIndex].ToString(), Textures = mat.TextureIndices.Select(texIdx => { if (texIdx >= 0 && texIdx < Textures.Length) { return Textures[texIdx]; } return null; }).ToArray() }); }).ToArray(); var bones = new Bone[gmdFile.BoneTransforms.Length]; foreach (var bt in gmdFile.BoneTransforms) { if (GmdUtils.GetParentBone(bt, gmdFile.BoneTransforms) == null) { LoadBone(bt, null, gmdFile, bones); } } Bones = bones.ToArray(); var nameList = new List <string>(); var meshes = new List <Mesh>(); foreach (var gmdMesh in gmdFile.Meshes) { var mesh = new Mesh(); meshes.Add(mesh); // Console.WriteLine($"------------"); foreach (var gmdSub in gmdFile.Submeshes.Where(s => s.MeshIndex == gmdMesh.MeshId)) { var submesh = new Submesh(); mesh.Submeshes.Add(submesh); submesh.Id = gmdSub.Id; submesh.Name = GetSubmeshName(Bones[gmdSub.BoneNo].Name, nameList); submesh.Transform = Bones[gmdSub.BoneNo].WorldMatrix; submesh.Material = Materials[gmdSub.MaterialIndex]; submesh.Vertices = ReadVertices(gmdSub, gmdMesh, gmdFile); submesh.Triangles = new int[gmdSub.IndicesCount / 3, 3]; // Console.WriteLine(submesh.Name.PadRight(25, ' ') // + submesh.Material.Shader.PadRight(25, ' ') // + $"{gmdMesh.HasFlag1} {gmdMesh.HasFlag2} {gmdMesh.HasFlag3}"); var offset = gmdSub.IndicesOffset; for (int i = 0; i < gmdSub.IndicesCount / 3; i++) { submesh.Triangles[i, 0] = gmdFile.Indices[offset + i * 3].Value - gmdSub.BufferOffset2; submesh.Triangles[i, 1] = gmdFile.Indices[offset + i * 3 + 1].Value - gmdSub.BufferOffset2; submesh.Triangles[i, 2] = gmdFile.Indices[offset + i * 3 + 2].Value - gmdSub.BufferOffset2; } } } Meshes = meshes.ToArray(); }
private int WriteVertices(BinaryWriter writer, Submesh submesh, int flagCount, List <int> boneIndices) { var startPosition = writer.BaseStream.Position; foreach (var v in submesh.Vertices) { GmdUtils.WriteVector3(v.Position, writer); if (v.BoneIndices != null) { writer.Write((byte)(v.BoneWeights[0] * 255)); writer.Write((byte)(v.BoneWeights[1] * 255)); writer.Write((byte)(v.BoneWeights[2] * 255)); writer.Write((byte)(v.BoneWeights[3] * 255)); writer.Write((byte)(boneIndices.IndexOf(v.BoneIndices[0]))); writer.Write((byte)(boneIndices.IndexOf(v.BoneIndices[1]))); writer.Write((byte)(boneIndices.IndexOf(v.BoneIndices[2]))); writer.Write((byte)(boneIndices.IndexOf(v.BoneIndices[3]))); } GmdUtils.WriteNormal(v.Normal, writer); writer.Write((byte)0); for (int i = 0; i < flagCount; i++) { writer.Write((byte)255); writer.Write((byte)255); writer.Write((byte)255); writer.Write((byte)255); } // writer.Write(100); // writer.Write((byte)0); // if ((mesh.Format >> 12 & 7L) == 7L) // { // writer.Write(0); // } // // if ((mesh.Format >> 21 & 7L) == 7L) // { // writer.Write(0); // } // // if ((mesh.Format >> 24 & 7L) == 7L) // { // writer.Write(0); // } writer.Write(Half.GetBits(new Half(v.Uv0.X))); writer.Write(Half.GetBits(new Half(1 - v.Uv0.Y))); if (v.Uv1.HasValue) { writer.Write(Half.GetBits(new Half(v.Uv1.Value.X))); writer.Write(Half.GetBits(new Half(1 - v.Uv1.Value.Y))); } if (v.Uv2.HasValue) { writer.Write(Half.GetBits(new Half(v.Uv2.Value.X))); writer.Write(Half.GetBits(new Half(1 - v.Uv2.Value.Y))); } if (v.Uv3.HasValue) { writer.Write(Half.GetBits(new Half(v.Uv3.Value.X))); writer.Write(Half.GetBits(new Half(1 - v.Uv3.Value.Y))); } } var endPosition = writer.BaseStream.Position; // Stride return((int)((endPosition - startPosition) / submesh.Vertices.Length)); }