Example #1
0
        public void Load(string continent)
        {
            var wdlPath = string.Format(@"World\Maps\{0}\{0}.wdl", continent);
            using (var strm = FileManager.Instance.Provider.OpenFile(wdlPath))
            {
                if (strm == null)
                    return;

                var reader = new BinaryReader(strm);
                var signature = 0u;
                while (signature != 0x4D414F46)
                {
                    signature = reader.ReadUInt32();
                    var size = reader.ReadInt32();
                    if (signature == 0x4D414F46)
                        break;

                    reader.ReadBytes(size);
                }

                var tileOffsets = reader.ReadArray<int>(4096);
                for(var i = 0; i < 4096; ++i)
                {
                    if (tileOffsets[i] <= 0)
                        continue;

                    strm.Position = tileOffsets[i] + 8;
                    mEntries.Add(i, reader.Read<MareEntry>());
                }
            }
        }
Example #2
0
        private static void ParseUncompressedLayer(int layer, ref uint[] palette, BinaryReader baseReader, ref BlpHeader header, TextureLoadInfo loadInfo)
        {
            if (header.Compression == 3)
                return;

            if (palette.Length == 0)
            {
                baseReader.BaseStream.Position = SizeCache<BlpHeader>.Size;
                palette = baseReader.ReadArray<uint>(256);
            }

            var w = Math.Max(header.Width >> layer, 1);
            var h = Math.Max(header.Height >> layer, 1);
            var indices = loadInfo.Layers[layer];
            var colors = new byte[w * h * 4];

            if (header.AlphaDepth == 8)
                DecompPaletteFastPath(ref palette, ref indices, ref colors);
            else
                DecompPaletteA8R8G8B8(header.AlphaDepth, ref palette, ref indices, ref colors);

            loadInfo.Layers[layer] = colors;
        }
 private static ParameterMetadata ReadParameterList(BinaryReader reader)
 {
     return new ParameterMetadata(null, DataType.Object, reader.ReadArray(r =>
     {
         var type = (DataType) r.ReadByte();
         var name = r.ReadUtfString();
         return new ParameterMetadata(name, type);
     }));
 }
Example #4
0
 /// <summary>
 /// Reads a <see cref="Portal"/>
 /// </summary>
 /// <param name="br">The <see cref="BinaryReader"/> used to read the <see cref="Portal"/></param>
 /// <returns>A <see cref="Portal"/></returns>
 public static Portal Read(BinaryReader br)
 {
     return new Portal(br.ReadUInt16(), Vertex.Read16(br), br.ReadArray(4, () => Vertex.Read16(br)));
 }
Example #5
0
        /// <summary>
        /// Reads a <see cref="ObjectTexture"/>
        /// </summary>
        /// <param name="br">The <see cref="BinaryReader"/> used to read the <see cref="ObjectTexture"/></param>
        /// <param name="ver">The game version</param>
        /// <returns>A <see cref="ObjectTexture"/></returns>
        public static ObjectTexture Read(BinaryReader br, Engine ver = Engine.Unknown)
        {
            var ret = new ObjectTexture();

            ret.TransparencyFlags = (BlendingMode) br.ReadUInt16();
            ret.TileAndFlag = br.ReadUInt16();

            if (ver >= Engine.TR4)
            {
                if ((ret.TileAndFlag & 0x7FFF) > 128)
                    Cerr.Write("ObjectTexture.Read[" + ver + "]: TileAndFlag > 128");

                ret.NewFlags = br.ReadUInt16();
            }
            else
            {
                if (ret.TileAndFlag > 64)
                    Cerr.Write("ObjectTexture.Read[" + ver + "]: TileAndFlag > 64");

                if ((ret.TileAndFlag & (1 << 15)) != 0)
                    Cerr.Write("ObjectTexture.Read[" + ver + "]: TileAndFlag has top bit set");
            }

            ret.Vertices = br.ReadArray(4, () => ObjectTextureVertex.Read(br, ver));

            if (ver >= Engine.TR4)
            {
                ret.OriginalU = br.ReadUInt32();
                ret.OriginalV = br.ReadUInt32();

                ret.Width = br.ReadUInt32();
                ret.Height = br.ReadUInt32();
            }

            if (ver == Engine.TR5)
            {
                var filler = br.ReadUInt16();

                if (filler != 0)
                    Cerr.Write("ObjectTexture.Read[TR5]: filler: Expected 0, Found 0x" + filler.ToString("X4"));
            }

            return ret;
        }
Example #6
0
        public static Room Read(BinaryReader br, Engine ver = Engine.Unknown)
        {
            var r = new Room();

            if (ver == Engine.TR5)
            {
                var xela = br.ReadUInt32();
                if (xela != 0x414C4558)
                    Cerr.Write("Room.Read[TR5]: 'XELA' header: Expected 0x414C4558, Found 0x" + xela.ToString("X8"));

                var roomDataSize = br.ReadUInt32();
                var pos = br.BaseStream.Position;
                var endPos = pos + roomDataSize;

                r.Intensity1 = 32767;
                r.Intensity2 = 32767;
                r.LightMode = 0;

                var separator1 = br.ReadUInt32();
                if (separator1 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator1: Expected 0xCDCDCDCD, Found 0x" + separator1.ToString("X8"));

                var portalOffset = br.ReadInt32();
                var sectorDataOffset = br.ReadUInt32();

                var separator2 = br.ReadUInt32();
                if (separator2 != 0 && separator2 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator2: Expected 0 or 0xCDCDCDCD, Found 0x" + separator2.ToString("X8"));

                var staticMeshesOffset = br.ReadUInt32();

                r.Offset = new Vertex(br.ReadInt32(), br.ReadUInt32(), -br.ReadInt32());
                r.Y_Bottom = -br.ReadInt32();
                r.Y_Top = -br.ReadInt32();

                r.Num_Z_Sectors = br.ReadUInt16();
                r.Num_X_Sectors = br.ReadUInt16();

                var lc = FloatColor.Read(br);
                r.LightColor = new FloatColor(lc.B, lc.G, lc.R, 1.0f); // OpenTomb ignores the alpha channel (but not vt todo?), also B & R are inverted

                var numLights = br.ReadUInt16();
                if (numLights > 512)
                    Cerr.Write("Room.Read[TR5]: numLights > 512");

                var numStaticMeshes = br.ReadUInt16();
                if (numStaticMeshes > 512)
                    Cerr.Write("Room.Read[TR5]: numStaticMeshes > 512");

                r.ReverbInfo = (ReverbInfo) br.ReadByte();
                r.AlternateGroup = (sbyte) br.ReadByte();
                r.WaterScheme = (byte) br.ReadUInt16();

                var filler1 = br.ReadUInt32();
                if (filler1 != 0x00007FFF)
                    Cerr.Write("Room.Read[TR5]: filler1: Expected 0x00007FFF, Found 0x" + filler1.ToString("X8"));

                var filler2 = br.ReadUInt32();
                if (filler2 != 0x00007FFF)
                    Cerr.Write("Room.Read[TR5]: filler2: Expected 0x00007FFF, Found 0x" + filler2.ToString("X8"));

                var separator4 = br.ReadUInt32();
                if (separator4 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator4: Expected 0xCDCDCDCD, Found 0x" + separator4.ToString("X8"));

                var separator5 = br.ReadUInt32();
                if (separator5 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator5: Expected 0xCDCDCDCD, Found 0x" + separator5.ToString("X8"));

                var filler3 = br.ReadUInt32();
                if (filler3 != 0xFFFFFFFF)
                    Cerr.Write("Room.Read[TR5]: filler3: Expected 0xFFFFFFFF, Found 0x" + filler3.ToString("X8"));

                r.AlternateRoom = br.ReadInt16(); // todo weird TRosettaStone says it's an ushort

                r.Flags = br.ReadUInt16();

                r.Unknown_R1 = br.ReadUInt32();
                r.Unknown_R2 = br.ReadUInt32();
                r.Unknown_R3 = br.ReadUInt32();

                var separator7 = br.ReadUInt32();
                if (separator7 != 0 && separator7 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator7: Expected 0 or 0xCDCDCDCD, Found 0x" + separator7.ToString("X8"));

                r.Unknown_R4a = br.ReadUInt16();
                r.Unknown_R4b = br.ReadUInt16();

                r.Room_X = br.ReadSingle();
                r.Unknown_R5 = br.ReadUInt32();
                r.Room_Z = -br.ReadSingle();

                var separator8 = br.ReadUInt32();
                if (separator8 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator8: Expected 0xCDCDCDCD, Found 0x" + separator8.ToString("X8"));

                var separator9 = br.ReadUInt32();
                if (separator9 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator9: Expected 0xCDCDCDCD, Found 0x" + separator9.ToString("X8"));

                var separator10 = br.ReadUInt32();
                if (separator10 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator10: Expected 0xCDCDCDCD, Found 0x" + separator10.ToString("X8"));

                var separator11 = br.ReadUInt32();
                if (separator11 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator11: Expected 0xCDCDCDCD, Found 0x" + separator11.ToString("X8"));

                var separator12 = br.ReadUInt32();
                if (separator12 != 0 && separator12 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator12: Expected 0 or 0xCDCDCDCD, Found 0x" + separator12.ToString("X8"));

                var separator13 = br.ReadUInt32();
                if (separator13 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator13: Expected 0xCDCDCDCD, Found 0x" + separator13.ToString("X8"));

                var numTriangles = br.ReadUInt32();
                if (numTriangles == 0xCDCDCDCD) numTriangles = 0;
                if (numTriangles > 512)
                    Cerr.Write("Room.Read[TR5]: numTriangles > 512");
                r.Triangles = new Triangle[numTriangles];

                var numRectangles = br.ReadUInt32();
                if (numRectangles == 0xCDCDCDCD) numRectangles = 0;
                if (numRectangles > 1024)
                    Cerr.Write("Room.Read[TR5]: numRectangles > 1024");
                r.Rectangles = new QuadFace[numRectangles];

                var separator14 = br.ReadUInt32();
                if (separator14 != 0)
                    Cerr.Write("Room.Read[TR5]: separator14: Expected 0, Found 0x" + separator14.ToString("X8"));

                var lightSize = br.ReadUInt32();
                var numLights2 = br.ReadUInt32();
                if (numLights2 != numLights)
                    throw new ArgumentException("Room.Read[TR5]: Room.numLights2 != Room.numLights", nameof(numLights2));

                r.Unknown_R6 = br.ReadUInt32();
                r.Room_Y_Top = -br.ReadSingle();
                r.Room_Y_Bottom = -br.ReadSingle();

                var numLayers = br.ReadUInt32();

                var layerOffset = br.ReadUInt32();
                var verticesOffset = br.ReadUInt32();
                var polyOffset = br.ReadUInt32();
                var polyOffset2 = br.ReadUInt32();
                if (polyOffset != polyOffset2)
                    throw new ArgumentException("Room.Read[TR5]: Room.polyOffset2 != Room.polyOffset",
                        nameof(polyOffset2));

                var verticesSize = br.ReadUInt32();
                if (verticesSize % 28 != 0)
                    throw new ArgumentException(
                        "Room.Read[TR5]: verticesSize has wrong value: " + verticesSize, nameof(verticesSize));

                var separator15 = br.ReadUInt32();
                if (separator15 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator15: Expected 0xCDCDCDCD, Found 0x" + separator15.ToString("X8"));

                var separator16 = br.ReadUInt32();
                if (separator16 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator16: Expected 0xCDCDCDCD, Found 0x" + separator16.ToString("X8"));

                var separator17 = br.ReadUInt32();
                if (separator17 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator17: Expected 0xCDCDCDCD, Found 0x" + separator17.ToString("X8"));

                var separator18 = br.ReadUInt32();
                if (separator18 != 0xCDCDCDCD)
                    Cerr.Write("Room.Read[TR5]: separator18: Expected 0xCDCDCDCD, Found 0x" + separator18.ToString("X8"));

                r.Lights = br.ReadArray(numLights, () => Light.Read(br, Engine.TR5));

                br.BaseStream.Position = pos + 208 + sectorDataOffset;

                r.Sectors = br.ReadArray(r.Num_Z_Sectors * r.Num_X_Sectors, () => Sector.Read(br));

                var numPortals = br.ReadInt16();
                r.Portals = br.ReadArray(numPortals, () => Portal.Read(br));

                br.BaseStream.Position = pos + 208 + staticMeshesOffset;

                r.StaticMeshes = br.ReadArray(numStaticMeshes, () => RoomStaticMesh.Read(br, Engine.TR4));

                br.BaseStream.Position = pos + 208 + layerOffset;

                r.Layers = br.ReadArray(numLayers, () => Layer.Read(br));

                br.BaseStream.Position = pos + 208 + polyOffset;

                {
                    ushort vertexIndex = 0;
                    uint rectangleIndex = 0;
                    uint triangleIndex = 0;

                    foreach (var layer in r.Layers)
                    {
                        for (var j = 0; j < layer.NumRectangles; j++)
                        {
                            r.Rectangles[rectangleIndex] = QuadFace.Read(br, Engine.TR4);
                            r.Rectangles[rectangleIndex].Vertices[0] += vertexIndex;
                            r.Rectangles[rectangleIndex].Vertices[1] += vertexIndex;
                            r.Rectangles[rectangleIndex].Vertices[2] += vertexIndex;
                            r.Rectangles[rectangleIndex].Vertices[3] += vertexIndex;
                            rectangleIndex++;
                        }

                        for (var j = 0; j < layer.NumTriangles; j++)
                        {
                            r.Triangles[triangleIndex] = Triangle.Read(br, Engine.TR4);
                            r.Triangles[triangleIndex].Vertices[0] += vertexIndex;
                            r.Triangles[triangleIndex].Vertices[1] += vertexIndex;
                            r.Triangles[triangleIndex].Vertices[2] += vertexIndex;
                            triangleIndex++;
                        }

                        vertexIndex += layer.NumVertices;
                    }
                }

                br.BaseStream.Position = pos + 208 + verticesOffset;

                {
                    uint vertexIndex = 0;
                    r.Vertices = new RoomVertex[verticesSize / 28];

                    foreach (var layer in r.Layers)
                    {
                        for (var j = 0; j < layer.NumVertices; j++)
                        {
                            r.Vertices[vertexIndex++] = RoomVertex.Read(br, Engine.TR5);
                        }
                    }
                }

                br.BaseStream.Position = endPos;
            }
            else
            {
                r.Offset = new Vertex(br.ReadInt32(), 0, -br.ReadInt32());
                r.Y_Bottom = -br.ReadInt32();
                r.Y_Top = -br.ReadInt32();

                var numDataWords = br.ReadUInt32();
                var pos = br.BaseStream.Position;

                var numVertices = br.ReadUInt16();
                r.Vertices = br.ReadArray(numVertices, () => RoomVertex.Read(br, ver));
                var numRectangles = br.ReadUInt16();
                r.Rectangles = br.ReadArray(numRectangles, () => QuadFace.Read(br, Engine.TR1));
                var numTriangles = br.ReadUInt16();
                r.Triangles = br.ReadArray(numTriangles, () => Triangle.Read(br, Engine.TR1));
                var numSprites = br.ReadUInt16();
                r.Sprites = br.ReadArray(numSprites, () => Sprite.Read(br));

                br.BaseStream.Position = pos + numDataWords * 2;

                r.Portals = br.ReadArray(br.ReadUInt16(), () => Portal.Read(br));

                r.Num_Z_Sectors = br.ReadUInt16();
                r.Num_X_Sectors = br.ReadUInt16();

                r.Sectors = br.ReadArray(r.Num_Z_Sectors * r.Num_X_Sectors, () => Sector.Read(br));

                if (ver == Engine.TR4)
                {
                    //r.RoomColor = ByteColor.ReadARGB(br); todo
                }

                if (ver < Engine.TR3)
                {
                    r.Intensity1 = (short) ((8191 - br.ReadInt16()) << 2);
                    r.Intensity2 = ver < Engine.TR2 ? r.Intensity1 : (short) ((8191 - br.ReadInt16()) << 2);
                }
                else
                {
                    r.Intensity1 = br.ReadInt16();
                    r.Intensity2 = br.ReadInt16();
                }
                if (ver == Engine.TR2)
                {
                    r.LightMode = br.ReadInt16();
                }

                r.Lights = br.ReadArray(br.ReadUInt16(), () => Light.Read(br, ver));

                r.StaticMeshes = br.ReadArray(br.ReadUInt16(), () => RoomStaticMesh.Read(br, ver));

                r.AlternateRoom = br.ReadInt16();

                r.Flags = br.ReadUInt16(); // todo trosettastone says it's an int16 (signed)

                if (ver == Engine.TR1)
                {
                    r.ReverbInfo = ReverbInfo.MediumRoom;

                    var c = r.Intensity1 / 32767.0f;
                    r.LightColor = new FloatColor(c, c, c);
                }
                else if (ver == Engine.TR2)
                {
                    r.ReverbInfo =
                        r.Flags.HasFlagEx(RoomFlags.WindBlowPonytail)
                            ? ReverbInfo.Outside
                            : ReverbInfo.MediumRoom;

                    var c = r.Intensity1 / 16384.0f;
                    r.LightColor = new FloatColor(c, c, c);
                }
                else if (ver == Engine.TR3)
                {
                    if (r.Flags.HasFlagEx(RoomFlags.Quicksand))
                    {
                        // Move quicksand flag to another bit to avoid confusion with NL flag.
                        r.Flags = (ushort) ((r.Flags | 0x0002) ^ 0x0080);
                    }
                    r.WaterScheme = br.ReadByte();
                    r.ReverbInfo = (ReverbInfo) br.ReadByte();
                    r.Filler = br.ReadByte();

                    var c = r.Intensity1 / 65534.0f;
                    r.LightColor = new FloatColor(c, c, c);
                }
                else if (ver == Engine.TR4)
                {
                    r.WaterScheme = br.ReadByte();
                    r.ReverbInfo = (ReverbInfo) br.ReadByte();
                    r.AlternateGroup = br.ReadSByte(); // todo Trosettastone says it's an unsigned byte

                    r.LightColor = new FloatColor(
                        (r.Intensity2 & 0x00FF) / 255.0f,
                        ((r.Intensity1 & 0xFF00) >> 8) / 255.0f,
                        (r.Intensity1 & 0x00FF) / 255.0f,
                        ((r.Intensity2 & 0xFF00) >> 8) / 255.0f);
                }
            }

            return r;
        }
Example #7
0
 private void LoadVertices(BinaryReader reader, int size)
 {
     var numVertices = size / SizeCache<Vector3>.Size;
     mPositions = reader.ReadArray<Vector3>(numVertices);
     for(var i = 0; i < mPositions.Length; ++i)
     {
         mPositions[i] = new Vector3(mPositions[i].X, -mPositions[i].Y, mPositions[i].Z);
     }
 }
Example #8
0
        private void LoadTexCoords(BinaryReader reader, int size)
        {
            if (mTexCoordsLoaded && mTexCoords.Length > 0)
                return;

            mTexCoordsLoaded = true;

            var numTexCoords = size / SizeCache<Vector2>.Size;
            mTexCoords = reader.ReadArray<Vector2>(numTexCoords);
        }
Example #9
0
        private void LoadMcnr(BinaryReader reader)
        {
            var normals = reader.ReadArray<sbyte>(145 * 3);
            mNormalExtra = reader.ReadBytes(13);

            for (var i = 0; i < 145; ++i)
            {
                var nx = -(normals[i * 3] / 127.0f);
                var ny = -(normals[i * 3 + 1] / 127.0f);
                var nz = normals[i * 3 + 2] / 127.0f;

                Vertices[i].Normal = new Vector3(nx, ny, nz);
            }
        }
Example #10
0
        private void LoadMcvt(BinaryReader reader)
        {
            var heights = reader.ReadArray<float>(145);

            var posx = Metrics.MapMidPoint - mHeader.Position.Y;
            var posy = Metrics.MapMidPoint - mHeader.Position.X;
            var posz = mHeader.Position.Z;

            var counter = 0;

            var minPos = new Vector3(float.MaxValue, float.MaxValue, float.MaxValue);
            var maxPos = new Vector3(float.MinValue, float.MinValue, float.MinValue);

            for (var i = 0; i < 17; ++i)
            {
                for (var j = 0; j < (((i % 2) != 0) ? 8 : 9); ++j)
                {
                    var height = posz + heights[counter];
                    var x = posx + j * Metrics.UnitSize;
                    if ((i % 2) != 0)
                        x += 0.5f * Metrics.UnitSize;
                    var y = posy + i * Metrics.UnitSize * 0.5f;

                    Vertices[counter].Position = new Vector3(x, y, height);

                    if (height < minPos.Z)
                        minPos.Z = height;
                    if (height > maxPos.Z)
                        maxPos.Z = height;

                    if (x < minPos.X)
                        minPos.X = x;
                    if (x > maxPos.X)
                        maxPos.X = x;
                    if (y < minPos.Y)
                        minPos.Y = y;
                    if (y > maxPos.Y)
                        maxPos.Y = y;

                    Vertices[counter].TexCoordAlpha = new Vector2(j / 8.0f + ((i % 2) != 0 ? (0.5f / 8.0f) : 0), i / 16.0f);
                    Vertices[counter].TexCoord = new Vector2(j + ((i % 2) != 0 ? 0.5f : 0.0f), i * 0.5f);
                    ++counter;
                }
            }

            mMinHeight = minPos.Z;
            mMaxHeight = maxPos.Z;

            BoundingBox = new BoundingBox(minPos, maxPos);
            mMidPoint = minPos + (maxPos - minPos) / 2.0f;
        }
Example #11
0
        private void LoadRootFile()
        {
            var encKeyStr = mBuildConfig["root"].FirstOrDefault();
            if (encKeyStr == null) throw new InvalidOperationException("Build config is missing root key");
            var encodingKey = encKeyStr.HexToBytes().ToArray();

            EncodingEntry encEntry;
            if (mEncodingData.TryGetValue(new Binary(encodingKey), out encEntry) == false || encEntry.Keys.Length == 0)
                throw new InvalidOperationException("Unable to find encoding value for root file");

            IndexEntry entry;
            if (mIndexData.TryGetValue(new Binary(encEntry.Keys[0].ToArray().Take(9).ToArray()), out entry) == false)
                throw new InvalidOperationException("Unable to locate root file in index table");

            var strm = GetDataStream(entry.Index);
            using (var fileReader = new BinaryReader(strm.Stream, Encoding.UTF8, true))
            {
                fileReader.BaseStream.Position = entry.Offset + 30;
                using (var reader = new BinaryReader(BlteGetData(fileReader, entry.Size - 30)))
                {
                    try
                    {
                        while(true)
                        {
                            var count = reader.ReadInt32();
                            reader.ReadBytes(8 + count * 4);
                            var entries = reader.ReadArray<RootEntryFile>(count);
                            foreach (var e in entries)
                            {
                                var b = e.md5;
                                var rootEntry = new RootEntry
                                {
                                    Hash = e.hash,
                                    Md5 = new Binary(new[]
                                    {
                                        b.v1, b.v2, b.v3, b.v4, b.v5, b.v6, b.v7, b.v8, b.v9, b.v10, b.v11,
                                        b.v12, b.v13, b.v14, b.v15, b.v16
                                    })
                                };
                                if (mRootData.ContainsKey(e.hash))
                                    mRootData[e.hash].Add(rootEntry);
                                else
                                    mRootData.Add(e.hash, new List<RootEntry>(20) {rootEntry});
                            }
                        }
                    }
                    catch(EndOfStreamException)
                    {

                    }
                }
            }
        }
Example #12
0
        private void LoadIndexFile(string file)
        {
            using (var strm = File.OpenRead(file))
            {
                using (var reader = new BinaryReader(strm))
                {
                    var h2Len = reader.ReadInt32();
                    reader.ReadInt32();
                    var padded = (8 + h2Len + 0x0F) & 0xFFFFFFF0;
                    strm.Position = padded;
                    var dataLen = reader.ReadInt32();
                    reader.ReadInt32();
                    var numBlocks = dataLen / 18;
                    var blocks = reader.ReadArray<IndexFileEntry>(numBlocks);
                    foreach(var block in blocks)
                    {
                        var key = new Binary(new[]
                        {
                            block.key.v1, block.key.v2, block.key.v3, block.key.v4, block.key.v5,
                            block.key.v6, block.key.v7, block.key.v8, block.key.v9
                        });

                        if (mIndexData.ContainsKey(key))
                            continue;

                        var idxLowBe = block.indexLowBE;
                        var idxHigh = block.indexHigh;
                        var idxLow = idxLowBe >> 24;
                        idxLow |= ((idxLowBe >> 16) & 0xFF) << 8;
                        idxLow |= ((idxLowBe >> 8) & 0xFF) << 16;
                        idxLow |= ((idxLowBe >> 0) & 0xFF) << 24;

                        mIndexData.Add(key, new IndexEntry()
                        {
                            Index = (((byte)(idxHigh << 2)) | ((idxLow & 0xC0000000) >> 30)),
                            Offset = (idxLow & 0x3FFFFFFF),
                            Size = block.size
                        });
                    }
                }
            }
        }
Example #13
0
        private void InitWmoModels(BinaryReader reader)
        {
            if (SeekChunk(reader, 0x4D574D4F) == false)
                return;

            var size = reader.ReadInt32();
            var bytes = reader.ReadBytes(size);
            var modelNameLookup = new Dictionary<int, string>();
            var curOffset = 0;
            var curBytes = new List<byte>();

            for (var i = 0; i < bytes.Length; ++i)
            {
                if (bytes[i] == 0)
                {
                    if (curBytes.Count > 0)
                        modelNameLookup.Add(curOffset, Encoding.ASCII.GetString(curBytes.ToArray()));

                    curOffset = i + 1;
                    curBytes.Clear();
                }
                else
                    curBytes.Add(bytes[i]);
            }

            if (SeekChunk(reader, 0x4D574944) == false)
                return;

            size = reader.ReadInt32();
            var modelNameIds = reader.ReadArray<int>(size / 4);

            if (SeekChunk(reader, 0x4D4F4446) == false)
                return;

            size = reader.ReadInt32();
            var modf = reader.ReadArray<Modf>(size / SizeCache<Modf>.Size);

            foreach (var entry in modf)
            {
                if (entry.Mwid >= modelNameIds.Length)
                    continue;

                var nameId = modelNameIds[entry.Mwid];
                string modelName;
                if (modelNameLookup.TryGetValue(nameId, out modelName) == false)
                    continue;


                var position = new Vector3(entry.Position.X, entry.Position.Z, entry.Position.Y);
                var rotation = new Vector3(entry.Rotation.Z, -entry.Rotation.X, 90 - entry.Rotation.Y);

                WorldFrame.Instance.WmoManager.AddInstance(modelName, entry.UniqueId, position, rotation);
                mWmoInstances.Add(new LoadedModel(modelName, entry.UniqueId));
            }
        }
Example #14
0
        private void InitM2Models(BinaryReader reader)
        {
            if (SeekChunk(reader, 0x4D4D4458) == false)
                return;

            var size = reader.ReadInt32();
            var bytes = reader.ReadBytes(size);
            var fullString = Encoding.ASCII.GetString(bytes);
            var modelNames = fullString.Split('\0');
            var modelNameLookup = new Dictionary<int, string>();
            var curOffset = 0;
            foreach (var name in modelNames)
            {
                modelNameLookup.Add(curOffset, name);
                curOffset += name.Length + 1;
            }

            if (SeekChunk(reader, 0x4D4D4944) == false)
                return;

            size = reader.ReadInt32();
            var modelNameIds = reader.ReadArray<int>(size / 4);

            if (SeekChunk(reader, 0x4D444446) == false)
                return;

            size = reader.ReadInt32();
            mDoodadDefs = reader.ReadArray<Mddf>(size / SizeCache<Mddf>.Size);

            var index = -1;
            foreach (var entry in mDoodadDefs)
            {
                ++index;
                if (entry.Mmid >= modelNameIds.Length)
                    continue;

                var nameId = modelNameIds[entry.Mmid];
                string modelName;
                if (modelNameLookup.TryGetValue(nameId, out modelName) == false)
                    continue;

                var position = new Vector3(entry.Position.X, entry.Position.Z, entry.Position.Y);
                var rotation = new Vector3(-entry.Rotation.X, -entry.Rotation.Z, 90 - entry.Rotation.Y);
                var scale = entry.Scale / 1024.0f;

                var instance = WorldFrame.Instance.M2Manager.AddInstance(modelName, entry.UniqueId, position, rotation,
                    new Vector3(scale));

                DoodadInstances.Add(new M2Instance
                {
                    Hash = modelName.ToUpperInvariant().GetHashCode(),
                    Uuid = entry.UniqueId,
                    BoundingBox = (instance != null ? instance.BoundingBox : new BoundingBox(new Vector3(float.MaxValue), new Vector3(float.MinValue))),
                    RenderInstance = instance,
                    MddfIndex = index
                });
            }
        }
Example #15
0
        private void InitChunkInfos(BinaryReader reader)
        {
            if(SeekChunk(reader, 0x4D43494E))
                mChunkOffsets = reader.ReadArray<Mcin>(256);

            reader.BaseStream.Position = 0;
            for (var i = 0; i < 256; ++i)
            {
                if (SeekNextMcnk(reader) == false)
                    throw new InvalidOperationException("Area is missing chunks");

                mChunkInfos.Add(new ChunkInfo
                {
                    Offset = (int)(reader.BaseStream.Position),
                    Size = reader.ReadInt32()
                });

                reader.ReadBytes(mChunkInfos.Last().Size);
            }
        }
Example #16
0
 private void LoadIndices(BinaryReader reader, int size)
 {
     var numIndices = size / 2;
     mIndices = reader.ReadArray<ushort>(numIndices).ToList();
     Indices = mIndices.AsReadOnly();
 }
Example #17
0
 private void LoadColors(BinaryReader reader, int size)
 {
     var numColors = size / 4;
     mColors = reader.ReadArray<uint>(numColors);
 }
Example #18
0
        private void LoadMccv(BinaryReader reader)
        {
            var colors = reader.ReadArray<uint>(145);
            for (var i = 0; i < 145; ++i)
            {
                Vertices[i].Color = colors[i];
                var r = (colors[i] >> 16) & 0xFF;
                var g = (colors[i] >> 8) & 0xFF;
                var b = (colors[i]) & 0xFF;
                var a = (colors[i] >> 24) & 0xFF;

                mShadingFloats[i] = new Vector4(b * 2.0f / 255.0f, g * 2.0f / 255.0f, r * 2.0f / 255.0f, a * 2.0f / 255.0f);
            }
        }
Example #19
0
 private void LoadNormals(BinaryReader reader, int size)
 {
     var numNormals = size / SizeCache<Vector3>.Size;
     mNormals = reader.ReadArray<Vector3>(numNormals);
     for (var i = 0; i < mNormals.Length; ++i)
         mNormals[i] = new Vector3(mNormals[i].X, -mNormals[i].Y, mNormals[i].Z);
 }
Example #20
0
        private void LoadReferences(BinaryReader reader, int size)
        {
            var refs = reader.ReadArray<int>(size / 4);
            if (refs.Length < mHeader.NumDoodadRefs || mHeader.NumDoodadRefs == 0)
                return;

            DoodadReferences = refs.Take(mHeader.NumDoodadRefs).ToArray();
            var minPos = BoundingBox.Minimum;
            var maxPos = BoundingBox.Maximum;

            MapArea parent;
            if (mParent.TryGetTarget(out parent) == false)
                return;

            foreach (var reference in DoodadReferences)
            {
                var inst = parent.DoodadInstances[reference];
                var min = inst.BoundingBox.Minimum;
                var max = inst.BoundingBox.Maximum;

                if (min.X < minPos.X)
                    minPos.X = min.X;
                if (min.Y < minPos.Y)
                    minPos.Y = min.Y;
                if (min.Z < minPos.Z)
                    minPos.Z = min.Z;
                if (max.X > maxPos.X)
                    maxPos.X = max.X;
                if (max.Y > maxPos.Y)
                    maxPos.Y = max.Y;
                if (max.Z > maxPos.Z)
                    maxPos.Z = max.Z;
            }

            ModelBox = new BoundingBox(minPos, maxPos);
        }
Example #21
0
        private bool LoadBatches(BinaryReader reader, int size)
        {
            var numBatches = size / SizeCache<Moba>.Size;
            if (numBatches != (mHeader.numBatchesA + mHeader.numBatchesB + mHeader.numBatchesC))
            {
                Log.Error("Group has inconsistent amount of batches.");
                return false;
            }

            WmoRoot parent;
            if (!mParent.TryGetTarget(out parent))
            {
                Log.Fatal("FATAL ERROR! Parent of WMO group is null!!");
                return false;
            }

            var batches = reader.ReadArray<Moba>(numBatches);
            for (var i = 0; i < numBatches; ++i)
            {
                var b = batches[i];
                var batch = new WmoBatch
                {
                    NumIndices = b.numFaces,
                    StartIndex = b.firstFace,
                    MaterialId = b.material,
                    BlendMode = parent.GetMaterial(b.material).BlendMode,
                };

                mBatches.Add(batch);
            }

            Batches = mBatches.OrderBy(b => b.BlendMode).ToList().AsReadOnly();

            return true;
        }
Example #22
0
        private void LoadLayers(BinaryReader reader, int size)
        {
            mLayers = reader.ReadArray<Mcly>(size / SizeCache<Mcly>.Size);
            MapArea parent;
            if (mParent.TryGetTarget(out parent) == false)
            {
                Textures = new List<Graphics.Texture>();
                return;
            }

            Textures = mLayers.Select(l => parent.GetTexture(l.TextureId)).ToList().AsReadOnly();
        }
Example #23
0
        /// <summary>
        /// Reads a <see cref="Mesh"/>
        /// </summary>
        /// <param name="br">The <see cref="BinaryReader"/> used to read the <see cref="Mesh"/></param>
        /// <param name="ver">The game version</param>
        /// <returns>A <see cref="Mesh"/></returns>
        public static Mesh Read(BinaryReader br, Engine ver = Engine.Unknown)
        {
            var ret = new Mesh();

            ret.Centre = Vertex.Read16(br);
            ret.CollisionSize = br.ReadInt32();

            ret.Vertices = br.ReadArray(br.ReadInt16(), () => Vertex.Read16(br));

            ret.Normals = new Vertex[0];
            ret.Lights = new short[0];

            ret.NumNormals = br.ReadInt16();
            if (ret.NumNormals >= 0)
                ret.Normals = br.ReadArray(ret.NumNormals, () => Vertex.Read16(br));
            else
                ret.Lights = br.ReadInt16Array(-ret.NumNormals);

            ret.TexturedRectangles = br.ReadArray(br.ReadInt16(), () => QuadFace.Read(br, ver));
            ret.TexturedTriangles = br.ReadArray(br.ReadInt16(), () => Triangle.Read(br, ver));

            if (ver < Engine.TR4)
            {
                ret.ColouredRectangles = br.ReadArray(br.ReadInt16(), () => QuadFace.Read(br, ver));
                ret.ColouredTriangles = br.ReadArray(br.ReadInt16(), () => Triangle.Read(br, ver));
            }

            return ret;
        }
Example #24
0
        public bool AsyncLoad(BinaryReader reader, ChunkInfo chunkInfo)
        {
            // chunkInfo.Offset points to right after the MCNK signature, the offsets in the header are relative to the signature tho
            var basePosition = chunkInfo.Offset - 4;
            reader.BaseStream.Position = chunkInfo.Offset;
            reader.ReadInt32();
            mHeader = reader.Read<Mcnk>();
            reader.BaseStream.Position = basePosition + mHeader.Mcvt;
            var signature = reader.ReadUInt32();
            reader.ReadInt32();
            if (signature != 0x4D435654)
            {
                Log.Error("Chunk is missing valid MCVT sub chunk");
                return false;
            }

            LoadMcvt(reader);

            reader.BaseStream.Position = basePosition + mHeader.Mcnr;
            signature = reader.ReadUInt32();
            reader.ReadInt32();

            if (signature != 0x4D434E52)
            {
                Log.Error("Chunk is missing valid MCNR sub chunk");
                return false;
            }

            LoadMcnr(reader);

            if(mHeader.Mcrf > 0)
            {
                reader.BaseStream.Position = basePosition + mHeader.Mcrf;
                signature = reader.ReadUInt32();
                var chunkSize = reader.ReadInt32();
                if (signature == 0x4D435246)
                    LoadReferences(reader, chunkSize);
            }

            var hasMccv = false;
            if (mHeader.Mccv != 0)
            {
                reader.BaseStream.Position = basePosition + mHeader.Mccv;
                signature = reader.ReadUInt32();
                reader.ReadInt32();
                if (signature == 0x4D434356)
                {
                    LoadMccv(reader);
                    hasMccv = true;
                    HasMccv = true;
                }
            }

            reader.BaseStream.Position = basePosition + mHeader.Mcly;
            signature = reader.ReadUInt32();
            var size = reader.ReadInt32();

            if (signature != 0x4D434C59)
                return false;

            LoadLayers(reader, size);

            if (mHeader.SizeAlpha > 8)
            {
                reader.BaseStream.Position = basePosition + mHeader.Mcal;
                signature = reader.ReadUInt32();
                if (signature == 0x4D43414C)
                {
                    reader.ReadInt32();
                    mAlphaCompressed = reader.ReadBytes(mHeader.SizeAlpha - 8);
                }
            }

            InitLayerData();

            if(mHeader.SizeShadow > 8 && mHeader.Mcsh > 0)
            {
                reader.BaseStream.Position = basePosition + mHeader.Mcsh + 8;
                var curPtr = 0;
                for (var i = 0; i < 64; ++i)
                {
                    for (var j = 0; j < 8; ++j)
                    {
                        byte mask = reader.ReadByte();
                        for (var k = 0; k < 8; ++k)
                        {
                            AlphaValues[curPtr] &= 0xFFFFFF00;
                            AlphaValues[curPtr++] |= ((mask & (1 << k)) == 0) ? (byte)0xFF : (byte)0xCC;
                        }
                    }
                }
            }

            if(mHeader.Mclv > 0)
            {
                reader.BaseStream.Position = basePosition + mHeader.Mclv + 8;
                var colors = reader.ReadArray<uint>(145);
                for (var i = 0; i < 145; ++i)
                    Vertices[i].AdditiveColor = colors[i];
            }

            LoadHoles();

            if (hasMccv == false)
            {
                for (var i = 0; i < 145; ++i)
                    Vertices[i].Color = 0x7F7F7F7F;
            }

            if (mHeader.Mcrf > 0)
                LoadUnusedChunk(0x4D435246, basePosition + mHeader.Mcrf, (mHeader.NumDoodadRefs + mHeader.NumMapObjRefs) * 4, reader);
            if (mHeader.SizeShadow > 0)
                LoadUnusedChunk(0x4D435348, basePosition + mHeader.Mcsh, mHeader.SizeShadow, reader);
            if (mHeader.NumSoundEmitters > 0)
                LoadUnusedChunk(0x4D435345, basePosition + mHeader.Mcse, mHeader.NumSoundEmitters * 0x1C, reader);
            if (mHeader.SizeLiquid > 8)
                LoadUnusedChunk(0x4D434C51, basePosition + mHeader.Mclq, mHeader.SizeLiquid - 8, reader);

            if (mHeader.Mclv > 0)
                LoadUnusedChunk(0x4D434C56, basePosition + mHeader.Mclv, 0, reader);


            WorldFrame.Instance.MapManager.OnLoadProgress();

            return true;
        }
Example #25
0
 /// <summary>
 /// Reads a <see cref="Palette"/>
 /// </summary>
 /// <param name="br">The <see cref="BinaryReader"/> used to read the <see cref="Palette"/></param>
 /// <param name="ver">The game version</param>
 /// <returns>A <see cref="Palette"/></returns>
 public static Palette Read(BinaryReader br, Engine ver = Engine.Unknown)
 {
     return new Palette
     {
         Colour = br.ReadArray(256, () => ByteColor.Read(br, ver))
     };
 }
Example #26
0
        private void UpdateMapNoWdl(string continent)
        {
            var wdtPath = string.Format(@"World\Map\{0}\{0}.wdt", continent);
            var hasWdt = FileManager.Instance.Provider.Exists(wdtPath);
            if(hasWdt == false)
            {
                UpdateMapFallback(continent);
                return;
            }

            using(var strm = FileManager.Instance.Provider.OpenFile(wdtPath))
            {
                var reader = new BinaryReader(strm);
                var hasWdtData = false;
                while (true)
                {
                    try
                    {
                        var id = reader.ReadUInt32();
                        var size = reader.ReadInt32();
                        if (id == 0x4D41494E)
                        {
                            var adtFlags = reader.ReadArray<ulong>(size / 8);
                            var textureData = new uint[Width * Height];
                            for(var i = 0; i < 64; ++i)
                            {
                                for(var j = 0; j < 64; ++j)
                                {
                                    var idx = i * 64 + j;
                                    var exists = (adtFlags[idx] & 1) != 0;
                                    if(exists)
                                    {
                                        hasWdtData = true;
                                        for(var k = 0; k < 17; ++k)
                                        {
                                            for(var l = 0; l < 17; ++l)
                                                textureData[(i * 17 + k) * (64 * 17) + j * 17 + l] = 0xFFFFFFFF;
                                        }
                                    }
                                }
                            }

                            var bmpProps =
                                new BitmapProperties(new PixelFormat(SharpDX.DXGI.Format.B8G8R8A8_UNorm,
                                    AlphaMode.Ignore));

                            using (var dataStream = new DataStream(Width * Height * 4, true, true))
                            {
                                dataStream.WriteRange(textureData);
                                dataStream.Position = 0;

                                mImage = new Bitmap(InterfaceManager.Instance.Surface.RenderTarget, new Size2(Width, Height),
                                    new DataPointer(dataStream.DataPointer, Width * Height * 4), Width * 4, bmpProps);
                            }

                            break;
                        }

                        reader.ReadBytes(size);
                    }
                    catch (Exception)
                    {
                        UpdateMapFallback(continent);
                        return;
                    }
                }

                if (hasWdtData == false)
                    UpdateMapFallback(continent);
            }
        }
        private void RegisterDevice(byte[] data)
        {
            var registrationInfo = new DeviceRegistrationInfo();

            using (var stream = new MemoryStream(data))
            using (var reader = new BinaryReader(stream))
            {
                registrationInfo.Id = reader.ReadGuid();
                registrationInfo.Key = reader.ReadUtfString();
                registrationInfo.Name = reader.ReadUtfString();
                registrationInfo.ClassName = reader.ReadUtfString();
                registrationInfo.ClassVersion = reader.ReadUtfString();
                registrationInfo.Equipment = reader.ReadArray(ReadEquipmentInfo);
                registrationInfo.Notifications = reader.ReadArray(ReadNotificationInfo);
                registrationInfo.Commands = reader.ReadArray(ReadCommandInfo);
            }

            RegisterDeviceCore(registrationInfo);
        }
Example #28
0
        public static TOMBPCFile Parse(BinaryReader br, bool psx = false)
        {
            try
            {
                var lvl = new TOMBPCFile();
                lvl.IsPSX = psx;
                lvl.GameVersion = (TOMBPCGameVersion) br.ReadUInt32();
                lvl.CopyrightInfo = br.ParseString(256);
                var gameflowSize = br.ReadUInt16();
                if (gameflowSize != 128)
                {
                    throw new ArgumentOutOfRangeException("gameflowSize [UInt16]", gameflowSize, "Should be 128");
                }

                #region First options

                lvl.FirstOption = br.ReadInt32();
                lvl.TitleReplace = br.ReadInt32();
                lvl.OnDeathDemoMode = br.ReadInt32();
                lvl.OnDeathInGame = br.ReadInt32();
                lvl.DemoTime = br.ReadInt32();
                lvl.OnDemoInterrupt = br.ReadInt32();
                lvl.OnDemoEnd = br.ReadInt32();
                br.ReadBytes(36); // Unknown2
                lvl.NumLevels = br.ReadInt16();
                lvl.NumChapterScreens = br.ReadInt16();
                lvl.NumTitles = br.ReadInt16();
                lvl.NumFMVs = br.ReadInt16();
                lvl.NumCutscenes = br.ReadInt16();
                lvl.NumDemoLevels = br.ReadInt16();
                lvl.TitleSoundID = br.ReadInt16();
                lvl.SingleLevel = br.ReadInt16();
                br.ReadBytes(32); // Unknown3
                lvl.Flags = (TOMBPCFlags) br.ReadUInt16();
                br.ReadBytes(6); // Unknown4
                lvl.XORbyte = br.ReadByte();
                lvl.Language = (TOMBPCLanguage) br.ReadByte();
                lvl.SecretSoundID = br.ReadInt16();
                br.ReadBytes(4); // Unknown5

                #endregion

                #region Strings

                var xor = lvl.Flags.HasFlag(TOMBPCFlags.UseEncryption) ? lvl.XORbyte : (byte)0;
                lvl.LevelDisplayNames = br.ReadStringArray(lvl.NumLevels, xor);
                lvl.ChapterScreens = br.ReadStringArray(lvl.NumChapterScreens, xor);
                lvl.TitleFileNames = br.ReadStringArray(lvl.NumTitles, xor);
                lvl.FMVFileNames = br.ReadStringArray(lvl.NumFMVs, xor);
                lvl.LevelFileNames = br.ReadStringArray(lvl.NumLevels, xor);
                lvl.CutSceneFileNames = br.ReadStringArray(lvl.NumCutscenes, xor);

                #endregion

                #region Script

                // This code is partially from Script.cpp of OpenRaider project
                var v = new List<List<ushort>>();
                var n = lvl.NumLevels + 1;
                var offset = br.ReadUInt16Array(n);
                var numBytes = br.ReadUInt16();
                var list = new ushort[(numBytes + 6) / 2];
                for (ushort i = 0; i < numBytes / 2; i++)
                {
                    list[i] = br.ReadUInt16();
                }
                lvl.DemoLevelIDs = br.ReadUInt16Array(lvl.NumDemoLevels);
                br.BaseStream.Position -= lvl.NumDemoLevels * 2;
                var hack = br.ReadUInt16Array(3);
                if (hack[0] == 19 && hack[1] == 20 && hack[2] == 21
                    || hack[0] == 21 && hack[1] == 22 && hack[2] == 23)
                {
                    list[numBytes / 2] = hack[0];
                    list[numBytes / 2 + 1] = hack[1];
                    list[numBytes / 2 + 2] = hack[2];
                }
                else
                {
                    br.BaseStream.Position -= 6;
                }

                var numPCStrings = 0;
                hack = br.ReadUInt16Array(3);
                if ((hack[0] == 1) && (hack[1] == 0) && (hack[2] == 864))
                {
                    br.BaseStream.Position += 58;
                    numPCStrings = 80; // TR2 has 80 PSX Strings
                }
                else if ((hack[0] == 1) && (hack[1] == 0) && (hack[2] == 817))
                {
                    br.BaseStream.Position += 34;
                    numPCStrings = 80; // TR3 also has 80 PSX Strings
                }
                else
                {
                    br.BaseStream.Position -= 6;
                    numPCStrings = 41;
                }

                for (uint i = 0; i < n; i++)
                {
                    uint end = (uint) (offset[i] / 2);

                    var readingOp = false;
                    while (readingOp || (list[end] != (ushort) ScriptOpCode.OP_ENDSEQUENCE))
                    {
                        if (readingOp)
                        {
                            readingOp = false;
                            end++;
                        }
                        else
                        {
                            if (OpcodeHasOperand[list[end]])
                                readingOp = true;

                            end++;
                        }
                    }

                    end++;

                    var tmp = new List<ushort>();
                    for (uint a = (uint) (offset[i] / 2); a < end; a++)
                    {
                        tmp.Add(list[a]);
                    }

                    v.Add(tmp);
                }

                lvl.Script = v.Select(x => x.ToArray()).ToArray();

                #endregion

                if (psx)
                {
                    lvl.PSXFMVInfo = br.ReadArray(lvl.NumFMVs, () => Loader.PSXFMVInfo.Read(br));
                }

                var numGameStrings = br.ReadUInt16();
                lvl.GameStrings1 = br.ReadStringArray(numGameStrings, lvl.XORbyte);
                lvl.GameStrings2 = br.ReadStringArray(numPCStrings, lvl.XORbyte);
                lvl.Puzzles = new[]
                {
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte),
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte),
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte),
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte)
                };
                lvl.Pickups = new[]
                {
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte),
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte)
                };
                lvl.Keys = new[]
                {
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte),
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte),
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte),
                    br.ReadStringArray(lvl.NumLevels, lvl.XORbyte)
                };


                return lvl;
            }
            catch (Exception e)
            {
                throw new ScriptParseException(e, br.BaseStream.Position);
            }
        }
        private static JToken ReadParameterValue(BinaryReader reader, ParameterMetadata parameterMetadata)
        {
            switch (parameterMetadata.DataType)
            {
                case DataType.Null:
                    return null;

                case DataType.Byte:
                    return (int) reader.ReadByte();
                
                case DataType.Word:
                    return reader.ReadUInt16();

                case DataType.Dword:
                    return reader.ReadUInt32();

                case DataType.Qword:
                    return reader.ReadUInt64();

                case DataType.SignedByte:
                    return reader.ReadSByte();

                case DataType.SignedWord:
                    return reader.ReadInt16();

                case DataType.SignedDword:
                    return reader.ReadInt32();
                
                case DataType.SignedQword:
                    return reader.ReadInt64();

                case DataType.Single:
                    return reader.ReadSingle();

                case DataType.Double:
                    return reader.ReadDouble();

                case DataType.Boolean:
                    return reader.ReadByte() != 0;

                case DataType.Guid:
                    return reader.ReadGuid();

                case DataType.UtfString:
                    return reader.ReadUtfString();

                case DataType.Binary:
                    return reader.ReadBinary();

                case DataType.Array:
                    return new JArray(reader
                        .ReadArray(r => ReadParameterValue(r, parameterMetadata.Children[0]))
                        .Cast<object>()
                        .ToArray());

                case DataType.Object:
                    return new JObject(parameterMetadata.Children
                        .Select(p => new JProperty(p.Name, ReadParameterValue(reader, p)))
                        .Cast<object>()
                        .ToArray());

                default:
                    throw new NotSupportedException(parameterMetadata.DataType + " is not supported for parameters");
            }
        }
Example #30
0
 private void LoadVertices(BinaryReader reader, int size)
 {
     var numVertices = size / SizeCache<Vector3>.Size;
     mPositions = reader.ReadArray<Vector3>(numVertices);
 }