Esempio n. 1
0
        public void DeserializeNestedTypes_FromSpan()
        {
            var tagStruct = (StructTestTag)BlamSerializer.Deserialize(typeof(StructTestTag), testTagData, 0, 100, null);

            AssertData(tagStruct);

            tagStruct = BlamSerializer.Deserialize <StructTestTag>(testTagData, 0, 100, null);
            AssertData(tagStruct);

            var tagRef = (ClassTestTag)BlamSerializer.Deserialize(typeof(ClassTestTag), testTagData, 0, 100, null);

            AssertData(tagRef);

            tagRef = BlamSerializer.Deserialize <ClassTestTag>(testTagData, 0, 100, null);
            AssertData(tagRef);


            var tagStructInstance = new StructTestTag();

            tagStructInstance = (StructTestTag)BlamSerializer.DeserializeInto(tagStructInstance, typeof(StructTestTag), testTagData, 0, 100, null);
            AssertData(tagStructInstance);

            tagStructInstance = new StructTestTag();
            tagStructInstance = BlamSerializer.DeserializeInto <StructTestTag>(tagStructInstance, testTagData, 0, 100, null);
            AssertData(tagStructInstance);

            var tagRefInstance = new ClassTestTag();

            tagRefInstance = (ClassTestTag)BlamSerializer.DeserializeInto(tagRefInstance, typeof(ClassTestTag), testTagData, 0, 100, null);
            AssertData(tagRefInstance);

            tagRefInstance = new ClassTestTag();
            tagRefInstance = BlamSerializer.DeserializeInto <ClassTestTag>(tagRefInstance, testTagData, 0, 100, null);
            AssertData(tagRefInstance);
        }
Esempio n. 2
0
        public void Deserialize_WrapperUsingInPlaceObjec()
        {
            var tagRef = BlamSerializer.Deserialize <EmptyWrapper>(new MemoryStream(testTagData), 0, 100, null);

            AssertData(tagRef);

            var offsetData = new byte[24 + testTagData.Length];

            testTagData.CopyTo(offsetData, 20);

            tagRef = BlamSerializer.Deserialize <EmptyWrapper>(new MemoryStream(offsetData), 20, 80, null);
            AssertData(tagRef);
        }
Esempio n. 3
0
        public void Deserialize_ReferenceValue()
        {
            var tagRef = BlamSerializer.Deserialize <ReferenceValueHolderTag>(new MemoryStream(testTagData), 0, 100, null);

            AssertData(tagRef.SubValue);

            var offsetData = new byte[24 + testTagData.Length];

            testTagData.CopyTo(offsetData, 20);

            tagRef = BlamSerializer.Deserialize <ReferenceValueHolderTag>(new MemoryStream(offsetData), 20, 80, null);
            AssertData(tagRef.SubValue);
        }
Esempio n. 4
0
        public IH2Map Load(string mapFileName)
        {
            Span <byte> header = new byte[2048];

            using (var peek = File.OpenRead(Path.Combine(this.mapRoot, mapFileName)))
            {
                peek.Read(header);
            }

            var baseHeader = BlamSerializer.Deserialize <H2HeaderBase>(header);

            return(baseHeader.Version switch
            {
                MapVersion.Halo2 => LoadH2Map(mapFileName, header),
                MapVersion.Halo2Mcc => LoadH2mccMap(mapFileName),
                _ => throw new NotSupportedException()
            });
Esempio n. 5
0
        public void DeserializeNestedTypes_FromStream()
        {
            var tagStruct = (StructTestTag)BlamSerializer.Deserialize(typeof(StructTestTag), new MemoryStream(testTagData), 0, 100, null);

            AssertData(tagStruct);

            tagStruct = BlamSerializer.Deserialize <StructTestTag>(new MemoryStream(testTagData), 0, 100, null);
            AssertData(tagStruct);

            var tagRef = (ClassTestTag)BlamSerializer.Deserialize(typeof(ClassTestTag), new MemoryStream(testTagData), 0, 100, null);

            AssertData(tagRef);

            tagRef = BlamSerializer.Deserialize <ClassTestTag>(new MemoryStream(testTagData), 0, 100, null);
            AssertData(tagRef);

            var offsetData = new byte[24 + testTagData.Length];

            testTagData.CopyTo(offsetData, 20);

            tagRef = BlamSerializer.Deserialize <ClassTestTag>(new MemoryStream(offsetData), 20, 80, null);
            AssertData(tagRef);

            var tagStructInstance = new StructTestTag();

            tagStructInstance = (StructTestTag)BlamSerializer.DeserializeInto(tagStructInstance, typeof(StructTestTag), new MemoryStream(testTagData), 0, 100, null);
            AssertData(tagStructInstance);

            tagStructInstance = new StructTestTag();
            tagStructInstance = BlamSerializer.DeserializeInto <StructTestTag>(tagStructInstance, new MemoryStream(testTagData), 0, 100, null);
            AssertData(tagStructInstance);

            var tagRefInstance = new ClassTestTag();

            tagRefInstance = (ClassTestTag)BlamSerializer.DeserializeInto(tagRefInstance, typeof(ClassTestTag), new MemoryStream(testTagData), 0, 100, null);
            AssertData(tagRefInstance);

            tagRefInstance = new ClassTestTag();
            tagRefInstance = BlamSerializer.DeserializeInto <ClassTestTag>(tagRefInstance, new MemoryStream(testTagData), 0, 100, null);
            AssertData(tagRefInstance);
        }
Esempio n. 6
0
        public override void PopulateExternalData(MapStream reader)
        {
            
            foreach (var part in Parts)
            {
                var headerOffset = new NormalOffset((int)part.DataBlockRawOffset);
                var mapData = reader.GetStream(headerOffset.Location);
                part.Header = BlamSerializer.Deserialize<ModelResourceBlockHeader>(mapData, headerOffset.Value);

                foreach (var resource in part.Resources)
                {
                    var dataOffset = part.DataBlockRawOffset + 8 + part.DataPreambleSize + resource.Offset;
                    mapData.Position = new NormalOffset((int)dataOffset).Value;

                    var resourceData = new byte[resource.Size];
                    var readCount = mapData.Read(resourceData, 0, resource.Size);

                    Debug.Assert(readCount == resource.Size);

                    resource.Data = resourceData;
                }

                var meshes = ModelResourceContainerProcessor.ProcessContainer(part, ModelShaderReferences);

                if(this.BoundingBoxes.Length > 0)
                {

                    var bbIndex = 0;

                    var maxBounds = new Vector3(
                        this.BoundingBoxes[bbIndex].MaxX,
                        this.BoundingBoxes[bbIndex].MaxY,
                        this.BoundingBoxes[bbIndex].MaxZ);

                    var minBounds = new Vector3(
                        this.BoundingBoxes[bbIndex].MinX,
                        this.BoundingBoxes[bbIndex].MinY,
                        this.BoundingBoxes[bbIndex].MinZ);

                    var maxUV = new Vector2(
                        this.BoundingBoxes[bbIndex].MaxU,
                        this.BoundingBoxes[bbIndex].MaxV);

                    var minUV = new Vector2(
                        this.BoundingBoxes[bbIndex].MinU,
                        this.BoundingBoxes[bbIndex].MinV);

                    var mesh = meshes[0];

                    for (var i = 0; i < mesh.Verticies.Length; i++)
                    {
                        var vert = mesh.Verticies[i];

                        var newPos = part.Flags.HasFlag(Properties.CompressedVerts) ? new Vector3(
                            Decompress(vert.Position.X, minBounds.X, maxBounds.X),
                            Decompress(vert.Position.Y, minBounds.Y, maxBounds.Y),
                            Decompress(vert.Position.Z, minBounds.Z, maxBounds.Z)
                            ) : vert.Position;

                        var newTex = part.Flags.HasFlag(Properties.CompressedTexCoords) ? new Vector2(
                            Decompress(vert.TexCoords.X, minUV.X, maxUV.X),
                            Decompress(vert.TexCoords.Y, minUV.Y, maxUV.Y)
                            ) : vert.TexCoords;

                        // Workaround for JIT issue
                        // https://github.com/dotnet/runtime/issues/1241
                        var newVert = new VertexFormat(newPos,
                            newTex,
                            vert.Normal,
                            vert.Tangent,
                            vert.Bitangent);

                        mesh.Verticies[i] = newVert;
                    }
                }

                part.Model = new MeshCollection(meshes);
            }
        }
Esempio n. 7
0
        //[InternalReferenceValue(540)]
        //public object[] MiscObject20Cao { get; set; }

        //[InternalReferenceValue(548)]
        //public object[] MiscObject21Cao { get; set; }

        //[InternalReferenceValue(556)]
        //public object[] MiscObject22Cao { get; set; }

        //[InternalReferenceValue(564)]
        //public object[] MiscObject23Cao { get; set; }


        public override void PopulateExternalData(MapStream reader)
        {
            foreach (var part in RenderChunks)
            {
                if (part.DataBlockRawOffset == uint.MaxValue)
                {
                    // TODO: determine why this happens, and if it's expected?
                    //Console.WriteLine("Bsp part with max DataBlock offset");
                    part.Model = new MeshCollection(new ModelMesh[0]);
                    continue;
                }

                var headerOffset = new NormalOffset((int)part.DataBlockRawOffset);
                var mapData      = reader.GetStream(headerOffset.Location);
                part.Header = BlamSerializer.Deserialize <ModelResourceBlockHeader>(mapData, headerOffset.Value);

                foreach (var resource in part.Resources)
                {
                    var dataOffset = part.DataBlockRawOffset + 8 + part.DataPreambleSize + resource.Offset;
                    mapData.Position = new NormalOffset((int)dataOffset).Value;
                    var resourceData = new byte[resource.Size];
                    var readCount    = mapData.Read(resourceData, 0, resource.Size);

                    Debug.Assert(readCount == resource.Size);

                    resource.Data = resourceData;
                }

                var meshes = ModelResourceContainerProcessor.ProcessContainer(part, ModelShaderReferences);
                part.Model = new MeshCollection(meshes);
            }

            foreach (var def in InstancedGeometryDefinitions)
            {
                if (def.DataBlockRawOffset == uint.MaxValue)
                {
                    Console.WriteLine("InstancedGeometry with max DataBlock offset");
                    def.Model = new MeshCollection(new ModelMesh[0]);
                    continue;
                }

                var headerOffset = new NormalOffset((int)def.DataBlockRawOffset);
                var mapData      = reader.GetStream(headerOffset.Location);
                def.Header = BlamSerializer.Deserialize <ModelResourceBlockHeader>(mapData, headerOffset.Value);

                foreach (var resource in def.Resources)
                {
                    var dataOffset = def.DataBlockRawOffset + 8 + def.DataPreambleSize + resource.Offset;
                    mapData.Position = new NormalOffset((int)dataOffset).Value;

                    var resourceData = new byte[resource.Size];
                    var readCount    = mapData.Read(resourceData, 0, resource.Size);

                    Debug.Assert(readCount == resource.Size);

                    resource.Data = resourceData;
                }

                var meshes = ModelResourceContainerProcessor.ProcessContainer(def, ModelShaderReferences, "InstancedGeometry_" + def.DataBlockRawOffset);
                def.Model = new MeshCollection(meshes);
            }
        }
Esempio n. 8
0
        /// <summary>
        /// Decompresses the provided stream into the other stream, if the map has not already been decompressed.
        /// If the provided stream has already been decompressed, it will simply return the original stream
        /// </summary>
        public static Stream DecompressInline(Stream input)
        {
            using var compressed = input;
            if (compressed.CanSeek == false)
            {
                throw new NotSupportedException("Must be able to seek on compressed");
            }

            var fourCC = compressed.ReadUInt32At(0);

            if (fourCC == DecompressedFourCC)
            {
                compressed.Position = 0;
                return(compressed);
            }

            if (fourCC != RealFourCC)
            {
                throw new Exception("Provided map stream was not valid");
            }

            var decompressTo = new MemoryStream();

            var info = BlamSerializer.Deserialize <H2mccCompressionSections>(compressed);

            var header = new Span <byte>(new byte[4096]);

            compressed.Position = 0;
            compressed.Read(header);
            decompressTo.WriteUInt32(DecompressedFourCC);
            decompressTo.Write(header.Slice(4));

            foreach (var section in info.Sections)
            {
                if (section.Offset == 0 || section.Count == 0)
                {
                    continue;
                }

                // Looks like compression is optional and count is negative when that happens
                if (section.Count < 0)
                {
                    var realCount = -section.Count;
                    var buf       = copyPool.Rent(realCount);
                    compressed.Position = section.Offset;
                    var readCount = compressed.Read(buf);

                    if (readCount != realCount)
                    {
                        copyPool.Return(buf);
                        throw new Exception("Unable to read the amount of data required");
                    }

                    decompressTo.Write(((Span <byte>)buf).Slice(0, readCount));
                    copyPool.Return(buf);
                }
                else
                {
                    compressed.Seek(section.Offset + 2, SeekOrigin.Begin);
                    using var deflate = new DeflateStream(compressed, CompressionMode.Decompress, leaveOpen: true);
                    deflate.CopyTo(decompressTo);
                }
            }

            decompressTo.Position = 0;

            return(decompressTo);
        }