public ObjectEntry(BinaryReader bin) { RotationVector = Short3Coord.ReadShort3Coord64(bin); OriginPosition = Short3Coord.ReadShort3Coord64(bin); ObjtType = bin.ReadInt16(); FlagUnknown = StreamUtils.ReadByteFlag(bin); IsSolid = StreamUtils.ReadByteFlag(bin); ShortUnknown = bin.ReadInt16(); }
public WeaponEntry(BinaryReader bin) { try { WeaponType = (eWeaponType)bin.ReadInt16(); } catch (InvalidCastException e) { throw new DeserialisationException("Unrecognised weapon type: " + e, bin.BaseStream.Position); } ShortUnknown = bin.ReadInt16(); OriginPosition = Short3Coord.ReadShort3Coord64(bin); }
public override void Deserialise(System.IO.Stream inStr) { long lStartingOffset = inStr.Position; // magic number BinaryReader bin = new BinaryReader(inStr); int lTMDMagicNumber = bin.ReadInt32(); if (TMD_MAGIC_NUMBER != lTMDMagicNumber) { throw new DeserialisationException(string.Format("TMD should start with 4 byte magic number 0x41, found {0:x8}", lTMDMagicNumber), inStr.Position - 4); } //mode int lTMDFlags = bin.ReadInt32(); if (lTMDFlags != (int)TMDFlags.None) { throw new DeserialisationException(string.Format("Only TMDs with no flags are supported. Found {0:x8}", lTMDFlags), inStr.Position - 4); } //obj count int lObjectCount = bin.ReadInt32(); if (lObjectCount != 1) { throw new DeserialisationException(string.Format("Only TMDs with one object are supported. Found {0}", lObjectCount), inStr.Position - 4); } ObjectCount = lObjectCount; // array pointers // (not stored, as they're derivable from the lengths of the arrays) int lVertPtr = bin.ReadInt32(); int lVertCount = bin.ReadInt32(); int lNormPtr = bin.ReadInt32(); int lNormCount = bin.ReadInt32(); int lPrimPtr = bin.ReadInt32(); int lPrimCount = bin.ReadInt32(); //obj scale ObjScale = bin.ReadInt32(); if (ObjScale != 0) { throw new DeserialisationException(string.Format("Only TMDs with ObjScale == 0 are supported. Found {0}", ObjScale), inStr.Position - 4); } // Faces if (lPrimPtr + 12 != inStr.Position - lStartingOffset) { throw new DeserialisationException(string.Format("Expecting Prim array to begin immediately after TMD header. Found PrimPtr={0}", lPrimPtr), inStr.Position); } Faces = new Face[lPrimCount]; for (int i = 0; i < lPrimCount; i++) { Faces[i] = new Face(); Faces[i].Deserialise(bin); } // Verts if (lVertPtr + 12 != inStr.Position - lStartingOffset) { throw new DeserialisationException(string.Format("Expecting Vert array to begin immediately after Prim array. Found VertPtr={0} but expecting", lVertPtr, 12 + inStr.Position - lStartingOffset), inStr.Position); } Vertices = new Short3Coord[lVertCount]; for (int i = 0; i < lVertCount; i++) { Vertices[i] = Short3Coord.ReadShort3Coord64(bin); } // Norms if (lNormPtr + 12 != inStr.Position - lStartingOffset) { throw new DeserialisationException(string.Format("Expecting Norm array to begin immediately after Vert array. Found NormPtr={0} but expecting", lNormPtr, 12 + inStr.Position - lStartingOffset), inStr.Position); } Normals = new Short3Coord[lNormCount]; for (int i = 0; i < lNormCount; i++) { Normals[i] = Short3Coord.ReadShort3Coord64(bin); } //record data length //qq this restricts editing somewhat mDataLength = (int)(inStr.Position - lStartingOffset); }
public void Deserialise(BinaryReader bin) { //header DeclaredIdx = bin.ReadInt16(); DeclaredName = StreamUtils.ReadASCIINullTermString(bin.BaseStream); if (DeclaredName.Length != 8) { throw new DeserialisationException("Expecting name to be length 8 & null-terminated", bin.BaseStream.Position); } //more header: OriginPosition = Short3Coord.ReadShort3Coord64(bin); RotationVector = Short3Coord.ReadShort3Coord64(bin); Width = bin.ReadInt16(); Height = bin.ReadInt16(); ScaleX = bin.ReadInt16(); ScaleY = bin.ReadInt16(); //every flat has a tex array: TextureIds = new short[Width][]; //not allowed 2d initalisers!!! TerrainHeight = new short[Width][]; for (int x = 0; x < Width; x++) { TextureIds[x] = new short[Height]; TerrainHeight[x] = new short[Height]; for (int y = 0; y < Height; y++) { TextureIds[x][y] = bin.ReadInt16(); TerrainHeight[x][y] = bin.ReadInt16(); } } //General flags HasMetaData = StreamUtils.ReadShortFlag(bin); FlgB = StreamUtils.ReadShortFlag(bin); FlgC = StreamUtils.ReadShortFlag(bin); Visible = StreamUtils.ReadShortFlag(bin); FlgE = StreamUtils.ReadByteFlag(bin); //qq that looks wrong to me, but it works! //what do these mean? NextN = bin.ReadBytes(HasMetaData ? 2 : 6); //unless (HasMetaData), we're done... if (HasMetaData) { //load the tex metadata TexMetaData = new Byte[Width][][]; for (int x = 0; x < Width; x++) { TexMetaData[x] = new Byte[Height][]; for (int y = 0; y < Height; y++) { TexMetaData[x][y] = bin.ReadBytes(8); } } //objects: short objectCount = bin.ReadInt16(); Objects = new ObjectEntry[objectCount]; for (int i = 0; i < objectCount; i++) { Objects[i] = new ObjectEntry(bin); } //weapons: short weapCount = bin.ReadInt16(); Weapons = new WeaponEntry[weapCount]; for (int i = 0; i < weapCount; i++) { Weapons[i] = new WeaponEntry(bin); } } else if (Utils.ArrayCompare(NextN, new byte[] { 156, 255, 1, 0, 4, 0 })) { //applying POOL5 hack!! qqq Console.Error.WriteLine("Warning: applying POOL5 specific hack to trailing bytes of jumprmp3 Flat"); TrailingData = bin.ReadBytes(22); } else if (Utils.ArrayCompare(NextN, new byte[] { 106, 255, 1, 0, 243, 255 })) { //applying GARDEN3 hack!! qqq Console.Error.WriteLine("Warning: applying GARDEN3 specific hack to trailing bytes of grasssht Flat"); TrailingData = bin.ReadBytes(22); } }