/// <summary> /// Initializes a new legacy <see cref="InibinSet"/> from a <see cref="BinaryReader"/> /// </summary> /// <param name="br">The <see cref="BinaryReader"/> to read from</param> /// <param name="type">The type of this <see cref="InibinSet"/></param> /// <param name="stringOffset">Offset to the string data</param> /// <param name="valueCount">Amount of values in this <see cref="InibinSet"/></param> public InibinSet(BinaryReader br, InibinFlags type, uint stringOffset, uint?valueCount = null) { this.Type = type; List <uint> hashes = new List <uint>(); if (valueCount == null) { valueCount = br.ReadUInt16(); for (int i = 0; i < valueCount; i++) { uint hash = br.ReadUInt32(); this.Properties.Add(hash, null); hashes.Add(hash); } } for (int i = 0; i < valueCount; i++) { uint offset = br.ReadUInt16(); long oldPos = br.BaseStream.Position; br.BaseStream.Seek(offset + stringOffset, SeekOrigin.Begin); string s = ""; char c; while ((c = br.ReadChar()) != '\u0000') { s += c; } this.Properties[hashes[i]] = s; br.BaseStream.Seek(oldPos, SeekOrigin.Begin); } }
/// <summary> /// Initializes a new <see cref="InibinFile"/> from a <see cref="Stream"/> /// </summary> /// <param name="stream">The <see cref="Stream"/> to read from</param> public InibinFile(Stream stream) { using (BinaryReader br = new BinaryReader(stream)) { uint version = br.ReadByte(); uint stringDataLength = 0; InibinFlags flags = 0; if (version == 1) { br.ReadBytes(3); uint valueCount = br.ReadUInt32(); stringDataLength = br.ReadUInt32(); this.Sets.Add(InibinFlags.StringList, new InibinSet(br, InibinFlags.StringList, (uint)br.BaseStream.Length - stringDataLength, valueCount)); } else if (version == 2) { stringDataLength = br.ReadUInt16(); flags = (InibinFlags)br.ReadUInt16(); if (flags.HasFlag(InibinFlags.Int32List)) { this.Sets.Add(InibinFlags.Int32List, new InibinSet(br, InibinFlags.Int32List)); } if (flags.HasFlag(InibinFlags.Float32List)) { this.Sets.Add(InibinFlags.Float32List, new InibinSet(br, InibinFlags.Float32List)); } if (flags.HasFlag(InibinFlags.FixedPointFloatList)) { this.Sets.Add(InibinFlags.FixedPointFloatList, new InibinSet(br, InibinFlags.FixedPointFloatList)); } if (flags.HasFlag(InibinFlags.Int16List)) { this.Sets.Add(InibinFlags.Int16List, new InibinSet(br, InibinFlags.Int16List)); } if (flags.HasFlag(InibinFlags.Int8List)) { this.Sets.Add(InibinFlags.Int8List, new InibinSet(br, InibinFlags.Int8List)); } if (flags.HasFlag(InibinFlags.BitList)) { this.Sets.Add(InibinFlags.BitList, new InibinSet(br, InibinFlags.BitList)); } if (flags.HasFlag(InibinFlags.FixedPointFloatListVec3)) { this.Sets.Add(InibinFlags.FixedPointFloatListVec3, new InibinSet(br, InibinFlags.FixedPointFloatListVec3)); } if (flags.HasFlag(InibinFlags.Float32ListVec3)) { this.Sets.Add(InibinFlags.Float32ListVec3, new InibinSet(br, InibinFlags.Float32ListVec3)); } if (flags.HasFlag(InibinFlags.FixedPointFloatListVec2)) { this.Sets.Add(InibinFlags.FixedPointFloatListVec2, new InibinSet(br, InibinFlags.FixedPointFloatListVec2)); } if (flags.HasFlag(InibinFlags.Float32ListVec2)) { this.Sets.Add(InibinFlags.Float32ListVec2, new InibinSet(br, InibinFlags.Float32ListVec2)); } if (flags.HasFlag(InibinFlags.FixedPointFloatListVec4)) { this.Sets.Add(InibinFlags.FixedPointFloatListVec4, new InibinSet(br, InibinFlags.FixedPointFloatListVec4)); } if (flags.HasFlag(InibinFlags.Float32ListVec4)) { this.Sets.Add(InibinFlags.Float32ListVec4, new InibinSet(br, InibinFlags.Float32ListVec4)); } if (flags.HasFlag(InibinFlags.StringList)) { this.Sets.Add(InibinFlags.StringList, new InibinSet(br, InibinFlags.StringList, (uint)br.BaseStream.Length - stringDataLength)); } } else { throw new Exception("This version is not supported"); } } }
/// <summary> /// Writes this <see cref="InibinFile"/> to the specified <see cref="Stream"/> /// </summary> /// <param name="stream">The <see cref="Stream"/> to write to</param> public void Write(Stream stream) { using (BinaryWriter bw = new BinaryWriter(stream)) { ushort stringDataLength = 0; InibinFlags flags = 0; if (this.Sets.ContainsKey(InibinFlags.BitList)) { flags |= InibinFlags.BitList; } if (this.Sets.ContainsKey(InibinFlags.FixedPointFloatList)) { flags |= InibinFlags.FixedPointFloatList; } if (this.Sets.ContainsKey(InibinFlags.FixedPointFloatListVec2)) { flags |= InibinFlags.FixedPointFloatListVec2; } if (this.Sets.ContainsKey(InibinFlags.FixedPointFloatListVec3)) { flags |= InibinFlags.FixedPointFloatListVec3; } if (this.Sets.ContainsKey(InibinFlags.FixedPointFloatListVec4)) { flags |= InibinFlags.FixedPointFloatListVec4; } if (this.Sets.ContainsKey(InibinFlags.Float32List)) { flags |= InibinFlags.Float32List; } if (this.Sets.ContainsKey(InibinFlags.Float32ListVec2)) { flags |= InibinFlags.Float32ListVec2; } if (this.Sets.ContainsKey(InibinFlags.Float32ListVec3)) { flags |= InibinFlags.Float32ListVec3; } if (this.Sets.ContainsKey(InibinFlags.Float32ListVec4)) { flags |= InibinFlags.Float32ListVec4; } if (this.Sets.ContainsKey(InibinFlags.Int16List)) { flags |= InibinFlags.Int16List; } if (this.Sets.ContainsKey(InibinFlags.Int32List)) { flags |= InibinFlags.Int32List; } if (this.Sets.ContainsKey(InibinFlags.Int8List)) { flags |= InibinFlags.Int8List; } if (this.Sets.ContainsKey(InibinFlags.StringList)) { flags |= InibinFlags.StringList; foreach (string dataString in this.Sets[InibinFlags.StringList].Properties.Values) { stringDataLength += (ushort)(dataString.Length + 1); } } bw.Write((byte)2); bw.Write(stringDataLength); bw.Write((ushort)flags); foreach (KeyValuePair <InibinFlags, InibinSet> set in this.Sets) { set.Value.Write(bw); } } }
/// <summary> /// Initializes a new <see cref="InibinSet"/> from a <see cref="BinaryReader"/> /// </summary> /// <param name="br">The <see cref="BinaryReader"/> to read from</param> /// <param name="type">The type of this <see cref="InibinSet"/></param> public InibinSet(BinaryReader br, InibinFlags type) { this.Type = type; ushort valueCount = br.ReadUInt16(); List <uint> hashes = new List <uint>(); for (int i = 0; i < valueCount; i++) { uint hash = br.ReadUInt32(); this.Properties.Add(hash, null); hashes.Add(hash); } byte boolean = 0; for (int i = 0; i < valueCount; i++) { if (this.Type == InibinFlags.Int32List) { this.Properties[hashes[i]] = br.ReadInt32(); } else if (this.Type == InibinFlags.Float32List) { this.Properties[hashes[i]] = br.ReadSingle(); } else if (this.Type == InibinFlags.FixedPointFloatList) { this.Properties[hashes[i]] = br.ReadByte() * 0.1; } else if (this.Type == InibinFlags.Int16List) { this.Properties[hashes[i]] = br.ReadInt16(); } else if (this.Type == InibinFlags.Int8List) { this.Properties[hashes[i]] = br.ReadByte(); } else if (this.Type == InibinFlags.BitList) { boolean = (i % 8) == 0 ? br.ReadByte() : (byte)(boolean >> 1); this.Properties[hashes[i]] = Convert.ToBoolean(0x1 & boolean); } else if (this.Type == InibinFlags.FixedPointFloatListVec3) { this.Properties[hashes[i]] = new byte[] { br.ReadByte(), br.ReadByte(), br.ReadByte() }; } else if (this.Type == InibinFlags.Float32ListVec3) { this.Properties[hashes[i]] = new float[] { br.ReadSingle(), br.ReadSingle(), br.ReadSingle() }; } else if (this.Type == InibinFlags.FixedPointFloatListVec2) { this.Properties[hashes[i]] = new byte[] { br.ReadByte(), br.ReadByte() }; } else if (this.Type == InibinFlags.Float32ListVec2) { this.Properties[hashes[i]] = new float[] { br.ReadSingle(), br.ReadSingle() }; } else if (this.Type == InibinFlags.FixedPointFloatListVec4) { this.Properties[hashes[i]] = new byte[] { br.ReadByte(), br.ReadByte(), br.ReadByte(), br.ReadByte() }; } else if (this.Type == InibinFlags.Float32ListVec4) { this.Properties[hashes[i]] = new float[] { br.ReadSingle(), br.ReadSingle(), br.ReadSingle(), br.ReadSingle() }; } } }
/// <summary> /// Initializes a new <see cref="InibinSet"/> /// </summary> /// <param name="type">Type of this <see cref="InibinSet"/></param> /// <param name="properties">Values of this <see cref="InibinSet"/></param> public InibinSet(InibinFlags type, Dictionary <uint, object> properties) { this.Type = type; this.Properties = properties; }
/// <summary> /// Initializes a new <see cref="InibinSet"/> with the specified type /// </summary> /// <param name="type">Type of this <see cref="InibinSet"/></param> public InibinSet(InibinFlags type) { this.Type = type; }