Esempio n. 1
0
        private static object ReadValue(
            BinaryReader inputReader,
            MemoryStream ms,
            bool isLittleEndian,
            ushort fieldType,
            int count,
            long baseOffset)
        {
            switch (fieldType)
            {
                case 1:
                    {
                        var valueOrOffset = inputReader.ReadUInt32(isLittleEndian);

                        if (count == 1)
                        {
                            var value = inputReader.ReadByte();
                            var x = inputReader.ReadBytes(3);
                            return value;
                        }

                        if (count < 4)
                        {
                            var value = inputReader.ReadBytes(count);
                            if (count < 4)
                            {
                                var x = inputReader.ReadBytes(4 - count);
                            }

                            return value;
                        }

                        ms.Position = baseOffset + valueOrOffset;
                        return inputReader.ReadBytes(count);
                    }

                case 2:
                    {
                        if (count <= 4)
                        {
                            var value = inputReader.ReadString(count).Trim('\0');
                            if (count < 4)
                            {
                                inputReader.ReadBytes(4 - count);
                            }

                            return value;
                        }

                        var valueOrOffset = inputReader.ReadUInt32(isLittleEndian);
                        ms.Position = baseOffset + valueOrOffset;
                        return inputReader.ReadString(count).Trim('\0');
                    }

                case 3:
                    {
                        if (count == 1)
                        {
                            var value = inputReader.ReadUInt16(isLittleEndian);
                            var x = inputReader.ReadUInt16(isLittleEndian);
                            return value;
                        }

                        if (count == 2)
                        {
                            return inputReader.ReadUInt16Array(count, isLittleEndian);
                        }

                        var valueOrOffset = inputReader.ReadUInt32(isLittleEndian);
                        ms.Position = baseOffset + valueOrOffset;
                        return inputReader.ReadUInt16Array(count, isLittleEndian);
                    }
                case 4:
                    {
                        if (count == 1)
                        {
                            return inputReader.ReadUInt32(isLittleEndian);
                        }

                        var valueOrOffset = inputReader.ReadUInt32(isLittleEndian);
                        ms.Position = baseOffset + valueOrOffset;
                        return inputReader.ReadUInt32Array(count, isLittleEndian);
                    }

                case 5:
                    {
                        var valueOrOffset = inputReader.ReadUInt32(isLittleEndian);
                        ms.Position = baseOffset + valueOrOffset;
                        if (count == 1)
                        {
                            var nominator = inputReader.ReadUInt32(isLittleEndian);
                            var denominator = inputReader.ReadUInt32(isLittleEndian);
                            return (double)nominator / denominator;
                        }

                        throw new NotImplementedException();
                    }

                case 10:
                    {
                        var valueOrOffset = inputReader.ReadInt32(isLittleEndian);
                        ms.Position = baseOffset + valueOrOffset;
                        if (count == 1)
                        {
                            var nominator = inputReader.ReadInt32(isLittleEndian);
                            var denominator = inputReader.ReadInt32(isLittleEndian);
                            return (double)nominator / denominator;
                        }

                        throw new NotImplementedException();
                    }
            }

            throw new NotImplementedException();
        }
Esempio n. 2
0
 /// <summary>
 /// Reads a <see cref="WordTexture"/>
 /// </summary>
 /// <param name="br">The <see cref="BinaryReader"/> used to read the <see cref="WordTexture"/></param>
 /// <returns>A <see cref="WordTexture"/></returns>
 public static WordTexture Read(BinaryReader br)
 {
     var ret = new WordTexture
     {
         Pixels = new ushort[256][]
     };
     for (var i = 0; i < 256; i++)
     {
         ret.Pixels[i] = br.ReadUInt16Array(256);
     }
     return ret;
 }
Esempio n. 3
0
 // Private Methods
 private void Read(BinaryReader reader)
 {
     _id = reader.ReadUInt32();
     _flags = reader.ReadUInt32();
     for (int i = 16; i < 31; i++)
     {
         if (BitHelper.IsBitSet(_flags, i))
         {
             switch (i)
             {
                 case 16:
                     _color1 = Color.FromArgb(reader.ReadInt32());
                     break;
                 case 17:
                     _color2 = Color.FromArgb(reader.ReadInt32());
                     break;
                 case 18:
                     _textureID = reader.ReadUInt32();
                     break;
                 case 19:
                     _floatArray1 = reader.ReadFloatArray(5);
                     break;
                 case 20:
                     _color3 = Color.FromArgb(reader.ReadInt32());
                     break;
                 case 21:
                     _shortArray1 = reader.ReadUInt16Array(2);
                     break;
                 case 22:
                     _floatArray2 = reader.ReadFloatArray(5);
                     break;
                 case 23:
                     _color4 = Color.FromArgb(reader.ReadInt32());
                     break;
                 case 25:
                     _float1 = reader.ReadSingle();
                     break;
                 case 26:
                     _floatArray3 = reader.ReadFloatArray(2);
                     break;
                 default:
                     throw new NotImplementedException("Unknown material flag bit set");
             }
         }
     }
 }
Esempio n. 4
0
        /// <summary>
        /// Reads a <see cref="Zone"/>
        /// </summary>
        /// <param name="br">The <see cref="BinaryReader"/> used to read the <see cref="Zone"/></param>
        /// <param name="ver">The game version</param>
        /// <returns>A <see cref="Zone"/></returns>
        public static Zone Read(BinaryReader br, Engine ver = Engine.Unknown)
        {
            var ret = new Zone();

            var arrSize = ver < Engine.TR2 ? 2 : 4;

            ret.FlyZoneNormal = br.ReadUInt16();
            ret.GroundZonesNormal = br.ReadUInt16Array(arrSize);
            ret.GroundZonesAlternate = br.ReadUInt16Array(arrSize);
            ret.FlyZoneAlternate = br.ReadUInt16();

            return ret;
        }
Esempio n. 5
0
 /// <summary>
 /// Reads a <see cref="QuadFace"/>
 /// </summary>
 /// <param name="br">The <see cref="BinaryReader"/> used to read the <see cref="QuadFace"/></param>
 /// <param name="ver">The game version</param>
 /// <returns>A <see cref="QuadFace"/></returns>
 public static QuadFace Read(BinaryReader br, Engine ver = Engine.Unknown)
 {
     var ret = new QuadFace
     {
         Vertices = br.ReadUInt16Array(4),
         Texture = br.ReadUInt16()
     };
     if (ver >= Engine.TR4) ret.Lighting = br.ReadUInt16();
     return ret;
 }
Esempio n. 6
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);
            }
        }
Esempio n. 7
0
        public static TR4LanguageFile Read(BinaryReader br)
        {
            var ret = new TR4LanguageFile();

            ret.NumGenericStrings = br.ReadUInt16();
            ret.NumPSXStrings = br.ReadUInt16();
            ret.NumPCStrings = br.ReadUInt16();

            var genericStringsLen = br.ReadUInt16();
            var psxStringsLen = br.ReadUInt16();
            var pcStringsLen = br.ReadUInt16();

            var stringOffsetTable = br.ReadUInt16Array(ret.NumGenericStrings + ret.NumPSXStrings + ret.NumPCStrings);
            ret.StringTable = br.ReadStringArray(stringOffsetTable, ret.XORbyte);

            if (br.BaseStream.Position < br.BaseStream.Length)
            {
                Cerr.Write("Warning: " + (br.BaseStream.Length - br.BaseStream.Position) +
                           " bytes of data after end of language file");
            }

            return ret;
        }
Esempio n. 8
0
        public void LoadFrom(Stream stream)
        {
            BinaryReader reader = new BinaryReader(stream);
            texture = new PPtr<Texture2D>(stream, file);

            int numVertices = reader.ReadInt32();
            vertices = new SpriteVertex[numVertices];
            for (int i = 0; i < numVertices; i++)
            {
                vertices[i] = new SpriteVertex(stream);
            }

            int numIndices = reader.ReadInt32();
            indices = reader.ReadUInt16Array(numIndices);
            if ((numIndices & 1) > 0)
            {
                reader.ReadBytes(2);
            }

            textureRect = new Rectf(stream);
            textureRectOffset = reader.ReadVector2();
            settingsRaw = reader.ReadUInt32();
            uvTransform = reader.ReadVector4();
        }
Esempio n. 9
0
        /// <summary>
        /// Initializes a new instance of the <see cref="SkinPartition"/> class.
        /// </summary>
        /// <param name="file">The file.</param>
        /// <param name="reader">The reader.</param>
        public SkinPartition(NiFile file, BinaryReader reader)
		{
			this.NumVertices = reader.ReadUInt16();
			this.NumTriangles = reader.ReadUInt16();
			this.NumBones = reader.ReadUInt16();
			this.NumStrips = reader.ReadUInt16();
			this.NumWeightsPerVertex = reader.ReadUInt16();
			this.Bones = reader.ReadUInt16Array((int)this.NumBones);
			this.HasVertexMap = true;
			this.HasVertexWeights = true;
			this.HasFaces = true;
			if (file.Version >= eNifVersion.VER_10_1_0_0)
			{
				this.HasVertexMap = reader.ReadBoolean(file.Version);
			}
			if (this.HasVertexMap)
			{
				this.VertexMap = reader.ReadUInt16Array((int)this.NumVertices);
			}
			if (file.Version >= eNifVersion.VER_10_1_0_0)
			{
				this.HasVertexWeights = reader.ReadBoolean(file.Version);
			}
			if (this.HasVertexWeights)
			{
				this.VertexWeights = new float[(int)this.NumVertices][];
				for (int i = 0; i < (int)this.NumVertices; i++)
				{
					this.VertexWeights[i] = reader.ReadFloatArray((int)this.NumWeightsPerVertex);
				}
			}
			this.StripLengths = reader.ReadUInt16Array((int)this.NumStrips);
			if (file.Version >= eNifVersion.VER_10_1_0_0)
			{
				this.HasFaces = reader.ReadBoolean(file.Version);
			}
			if (this.HasFaces && this.NumStrips != 0)
			{
				this.Strips = new ushort[(int)this.NumStrips][];
				for (int j = 0; j < (int)this.NumStrips; j++)
				{
					this.Strips[j] = reader.ReadUInt16Array((int)this.StripLengths[j]);
				}
			}
			else if (this.HasFaces && this.NumStrips == 0)
			{
				this.Triangles = new Triangle[(int)this.NumTriangles];
				for (int k = 0; k < this.Triangles.Length; k++)
				{
					this.Triangles[k] = new Triangle(reader);
				}
			}
			this.HasBoneIndicies = reader.ReadBoolean(file.Version);
			if (this.HasBoneIndicies)
			{
				this.BoneIndicies = new byte[(int)this.NumVertices][];
				for (int l = 0; l < this.BoneIndicies.Length; l++)
				{
					this.BoneIndicies[l] = new byte[(int)this.NumWeightsPerVertex];
					for (int m = 0; m < (int)this.NumWeightsPerVertex; m++)
					{
						this.BoneIndicies[l][m] = reader.ReadByte();
					}
				}
			}
			if (file.Header.UserVersion >= 12u)
			{
				this.UnkownShort = reader.ReadUInt16();
			}
			if (file.Version == eNifVersion.VER_10_2_0_0 && file.Header.UserVersion == 1u)
			{
				this.UnkownShort2 = reader.ReadUInt16();
				this.UnkownShort3 = reader.ReadUInt16();
				this.NumVertices2 = reader.ReadUInt16();
				this.UnkownShort4 = reader.ReadUInt16();
				this.UnkownShort5 = reader.ReadUInt16();
				this.UnkownShort6 = reader.ReadUInt16();
				this.UnkownArr = new SkinPartitionUnkownItem1[(int)this.NumVertices2];
				for (int n = 0; n < (int)this.NumVertices2; n++)
				{
					this.UnkownArr[n] = new SkinPartitionUnkownItem1(file, reader);
				}
			}
		}
Esempio n. 10
0
        private void InternalRead(BinaryReader reader)
        {
            int size = reader.ReadInt32();
            _numAssignedFrames = reader.ReadUInt16();
            _type = reader.ReadUInt16();

            _assignedFrameIndices = reader.ReadUInt16Array(_numAssignedFrames);

            // Align to 4 bytes
            reader.AlignPosition(4);

            _boneKeyData = new float[_numAssignedFrames][];
            for (int i = 0; i < _numAssignedFrames; i++)
            {
                switch (_type)
                {
                    case 0x04:
                        {
                            _boneKeyData[i] = new float[2];
                            for (int j = 0; j < 2; j++)
                            {
                                _boneKeyData[i][j] = (float)reader.ReadInt16() / FIXED_POINT;
                            }
                        }

                        break;
                    case 0x08:
                        {
                            _boneKeyData[i] = new float[4];
                            for (int j = 0; j < 4; j++)
                            {
                                _boneKeyData[i][j] = (float)reader.ReadInt16() / FIXED_POINT;
                            }
                        }

                        break;
                    case 0x0C:
                        {
                            _boneKeyData[i] = new float[3];
                            for (int j = 0; j < 3; j++)
                            {
                                _boneKeyData[i][j] = reader.ReadSingle();
                            }
                        }

                        break;
                    default:
                        break;
                }
            }
        }
Esempio n. 11
0
        // Methods
        internal void InternalRead(MDChunk model, BinaryReader reader)
        {
            _batchSize = reader.ReadUInt16();
            _materialID = reader.ReadUInt16();
            _batchOffset = reader.ReadInt32();
            _numUsedNodes = reader.ReadInt32();
            _usedNodeIndices = reader.ReadUInt16Array(_numUsedNodes);
            _usedNodes = new MDNode[_numUsedNodes];
            for (int i = 0; i < _numUsedNodes; i++)
            {
                _usedNodes[i] = model.Nodes[_usedNodeIndices[i]];
            } 

            reader.BaseStream.Seek((int)model.offset + MDChunk.DATA_START_ADDRESS + _batchOffset, SeekOrigin.Begin);
            _vifPackets = VIFCodeEvaluator.EvaluateBlock(reader, _batchSize);
            _batches = MDSubMeshVifBatch.ParseBatches(_vifPackets, _numUsedNodes);

            foreach (MDSubMeshVifBatch batch in _batches)
            {
                batch.TransformedPositions = new Vector3[batch.VertexCount];
                batch.TransformedNormals = new Vector3[batch.VertexCount];
                for (int i = 0; i < batch.VertexCount; i++)
                {
                    if (batch.Weights[i] != 0)
                    {
                        batch.TransformedPositions[i] = Vector3.Transform(batch.Positions[i], UsedNodes[batch.UsedNodeArrayIndex].WorldMatrix * batch.Weights[i]);
                    }
                    else
                    {
                        batch.TransformedPositions[i] = Vector3.Zero;
                    }

                    if (batch.Weights[i] != 0)
                    {
                        batch.TransformedNormals[i] = Vector3.TransformNormal(batch.Normals[i], UsedNodes[batch.UsedNodeArrayIndex].WorldMatrix * batch.Weights[i]);
                    }
                    else
                    {
                        batch.TransformedNormals[i] = Vector3.Zero;
                    }
                }
            }

            List<MDSubMeshVifBatch> fixedBatches = new List<MDSubMeshVifBatch>();
            for (int i = 0; i < _batches.Count; i+=(int)_numUsedNodes)
            {
                Vector3[] pos = new Vector3[_batches[i].VertexCount];
                Vector3[] nrm = new Vector3[_batches[i].VertexCount];
                for (int k = 0; k < _batches[i].VertexCount; k++)
                {
                    for (int j = 0; j < _numUsedNodes; j++)
                    {
                        pos[k] += _batches[i + j].TransformedPositions[k];
                        nrm[k] += _batches[i + j].TransformedNormals[k];
                    }
                }
                for (int k = 0; k < _batches[i].VertexCount; k++)
                {
                    nrm[k].Normalize();
                }
                /*
                SubMeshVifBatch finalBatch = _batches[(int)_numUsedNodes - 1];
                finalBatch.TransformedPositions = pos;
                finalBatch.TransformedNormals = pos;
                finalBatch.NodeIndices = 
                fixedBatches.Add(finalBatch);
                */
                for (int j = 0; j < _numUsedNodes; j++)
                {
                    _batches[i + j].TransformedPositions = pos;
                    _batches[i + j].TransformedNormals = nrm;
                    _batches[i + j].Colors = _batches[(int)_numUsedNodes - 1].Colors;
                    _batches[i + j].TextureCoords = _batches[(int)_numUsedNodes - 1].TextureCoords;
                }     
            }
        }
Esempio n. 12
0
        public sviParser(Stream stream)
        {
            BinaryReader reader = new BinaryReader(stream);

            version = reader.ReadInt32();
            if (version != 100)
            {
                throw new Exception("SVI bad beginning: 0x" + version.ToString("X"));
            }
            meshName = reader.ReadName();
            submeshIdx = reader.ReadInt32();
            int numIndices = reader.ReadInt32();
            indices = reader.ReadUInt16Array(numIndices);

            positionsPresent = reader.ReadByte();
            if (positionsPresent == 1)
            {
                positions = reader.ReadVector3Array(numIndices);
            }

            bonesPresent = reader.ReadByte();
            if (bonesPresent == 1)
            {
                boneWeights3 = new float[numIndices][];
                for (ushort i = 0; i < numIndices; i++)
                {
                    boneWeights3[i] = reader.ReadSingleArray(3);
                }
                boneIndices = new byte[numIndices][];
                for (ushort i = 0; i < numIndices; i++)
                {
                    boneIndices[i] = reader.ReadBytes(4);
                }

                int numBones = reader.ReadInt32();
                bones = new sviBone[numBones];
                for (int i = 0; i < numBones; i++)
                {
                    bones[i] = new sviBone();
                    bones[i].name = reader.ReadName();
                    bones[i].boneIdx = reader.ReadInt32();
                    bones[i].matrix = reader.ReadMatrix();
                }
            }

            normalsPresent = reader.ReadByte();
            if (normalsPresent == 1)
            {
                normals = reader.ReadVector3Array(numIndices);
            }

            uvsPresent = reader.ReadByte();
            if (uvsPresent == 1)
            {
                uvs = reader.ReadVector2Array(numIndices);
            }

            futureSectionPresent = reader.ReadByte();
            if (futureSectionPresent != 0)
            {
                throw new Exception("SVI future section present");
            }
        }