Esempio n. 1
0
        public MTModel(BinaryReader Reader, MTMaterials MRLData, MTShaderEffects Shader) : this()
        {
            string Magic = Reader.ReadPaddedString(4);

            ushort Version               = Reader.ReadUInt16();
            ushort BonesCount            = Reader.ReadUInt16();
            ushort MeshesCount           = Reader.ReadUInt16();
            ushort MaterialsCount        = Reader.ReadUInt16();
            uint   TotalVerticesCount    = Reader.ReadUInt32();
            uint   TotalIndicesCount     = Reader.ReadUInt32();
            uint   TotalTrianglesCount   = Reader.ReadUInt32();
            uint   VerticesBufferLength  = Reader.ReadUInt32();
            uint   HeaderPadding1c       = Reader.ReadUInt32(); //?
            uint   MeshGroupsCount       = Reader.ReadUInt32();
            uint   BoneIndicesCount      = Reader.ReadUInt32();
            uint   SkeletonAddress       = Reader.ReadUInt32();
            uint   MeshGroupsAddr        = Reader.ReadUInt32();
            uint   MaterialNamesAddress  = Reader.ReadUInt32();
            uint   MeshesAddress         = Reader.ReadUInt32();
            uint   VerticesBufferAddress = Reader.ReadUInt32();
            uint   IndicesBufferAddress  = Reader.ReadUInt32();
            uint   ModelFileLength       = Reader.ReadUInt32();

            BoundingSphere = Reader.ReadVector4();
            BoundingBoxMin = Reader.ReadVector4();
            BoundingBoxMax = Reader.ReadVector4();

            string[] MaterialNames = new string[MaterialsCount];

            Reader.BaseStream.Seek(MaterialNamesAddress, SeekOrigin.Begin);

            for (int Index = 0; Index < MaterialsCount; Index++)
            {
                MaterialNames[Index] = Reader.ReadPaddedString(0x80);
            }

            for (int Index = 0; Index < MeshesCount; Index++)
            {
                Reader.BaseStream.Seek(MeshesAddress + Index * 0x30, SeekOrigin.Begin);

                MTMesh Mesh = new MTMesh(
                    Reader,
                    Shader,
                    VerticesBufferAddress,
                    IndicesBufferAddress);

                string MaterialName = MaterialNames[Mesh.MaterialIndex];

                uint MaterialHash = CRC32Hash.Hash(MaterialName);

                int MaterialIndex = Materials.FindIndex(x => x.NameHash == MaterialHash);

                if (MaterialIndex == -1)
                {
                    MTMaterial Mat = MRLData.Materials.FirstOrDefault(x => x.NameHash == MaterialHash);

                    if (Mat != null)
                    {
                        Mat.Name = MaterialName;

                        MaterialIndex = Materials.Count;

                        Materials.Add(Mat);
                    }
                    else
                    {
                        MaterialIndex = 0;
                    }
                }

                Mesh.MaterialIndex = (uint)MaterialIndex;

                Meshes.Add(Mesh);
            }

            for (int Index = 0; Index < BonesCount; Index++)
            {
                Reader.BaseStream.Seek(SkeletonAddress + Index * 0x18, SeekOrigin.Begin);

                sbyte BoneIndex = Reader.ReadSByte();
                sbyte Parent    = Reader.ReadSByte();
                sbyte Opposite  = Reader.ReadSByte();
                byte  Padding   = Reader.ReadByte();

                float ChildDistance  = Reader.ReadSingle();
                float ParentDistance = Reader.ReadSingle();

                Vector3 Position = Reader.ReadVector3();

                Skeleton.Add(new MTBone()
                {
                    ParentIndex    = Parent,
                    OppositeIndex  = Opposite,
                    ChildDistance  = ChildDistance,
                    ParentDistance = ParentDistance,
                    Position       = Position
                });
            }

            for (int Index = 0; Index < BonesCount; Index++)
            {
                Skeleton[Index].LocalTransform = Reader.ReadMatrix4x4RH();
            }

            for (int Index = 0; Index < BonesCount; Index++)
            {
                Skeleton[Index].WorldTransform = Reader.ReadMatrix4x4RH();
            }

            Reader.BaseStream.Seek(0x100, SeekOrigin.Current);

            BoneIndicesGroups = new byte[BoneIndicesCount][];

            for (int i = 0; i < BoneIndicesCount; i++)
            {
                int Count = Reader.ReadInt32();

                BoneIndicesGroups[i] = new byte[Count];

                for (int j = 0; j < Count; j++)
                {
                    BoneIndicesGroups[i][j] = Reader.ReadByte();
                }

                Reader.BaseStream.Seek(0x18 - Count, SeekOrigin.Current);
            }
        }
Esempio n. 2
0
        public MTShaderEffects(BinaryReader Reader)
        {
            string Magic = Reader.ReadNullTerminatedString(); //MFX

            Reader.BaseStream.Seek(8, SeekOrigin.Current);    //Unknown stuff

            uint DescriptorsCount = Reader.ReadUInt32();
            uint FragShaderCount  = Reader.ReadUInt32();
            uint VtxShaderCount   = Reader.ReadUInt32();
            uint FragShaderAddr   = Reader.ReadUInt32();
            uint VtxShaderAddr    = Reader.ReadUInt32();
            uint StringsTblAddr   = Reader.ReadUInt32();
            uint VtxProgramAddr   = Reader.ReadUInt32();

            long VtxFormatsAddr = Reader.BaseStream.Position;

            for (uint i = 0; i < DescriptorsCount; i++)
            {
                Reader.BaseStream.Seek(VtxFormatsAddr + i * 4, SeekOrigin.Begin);
                Reader.BaseStream.Seek(Reader.ReadUInt32(), SeekOrigin.Begin);

                if (Reader.BaseStream.Position == 0)
                {
                    continue;
                }

                string DescName = GetName(Reader, StringsTblAddr);
                string TypeName = GetName(Reader, StringsTblAddr);

                ushort DescType   = Reader.ReadUInt16();
                ushort MapLength  = Reader.ReadUInt16(); //Actual length is value / 2? Not sure
                ushort MapIndex   = Reader.ReadUInt16();
                ushort DescIndex  = Reader.ReadUInt16();
                uint   MapAddress = Reader.ReadUInt32(); //Not sure what this address actually points to

                uint Hash = (CRC32Hash.Hash(DescName) << 12) | DescIndex;

                MTShaderEffect Desc = new MTShaderEffect();

                if (TypeName == "__InputLayout")
                {
                    Desc = new MTAttributesGroup(Reader, StringsTblAddr);
                }
                else
                {
                    switch (DescType)
                    {
                    case 2: Desc = new MTTextureMap(Reader); break;

                    case 5: Desc = new MTAlphaBlend(Reader); break;

                    case 6: Desc = new MTDepthStencil(Reader); break;
                    }
                }

                Desc.Name = DescName;
                Desc.Type = TypeName;

                Descriptors.Add(Hash, Desc);
            }

            for (uint i = 0; i < FragShaderCount; i++)
            {
                Reader.BaseStream.Seek(FragShaderAddr + i * 4, SeekOrigin.Begin);
                Reader.BaseStream.Seek(Reader.ReadUInt32(), SeekOrigin.Begin);

                FragmentLighting.Add(new MTFragmentLighting(Reader));
            }
        }