public void Write(DhBinaryWriter bw) { // Write name. bw.WriteFixedStr(Name, 28); // Write keyframe count. bw.WriteU32(KeyFrameCount); // Write start index. bw.WriteU16(StartIndex); // Write keyframe size. bw.WriteU16(KeyFrameSize); }
/// <summary> /// Write a single primitive vertex with specified Binary Writer. /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw) { // Write Primitive type. bw.Write(Type); // Write number of primitive vertices. bw.WriteS16((short)Vertices.Count); // Loop through primitive vertices. for (int i = 0; i < Vertices.Count; i++) { // Write primitive vertex. Vertices[i].Write(bw); } }
/// <summary> /// Write a single field to stream. /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw) { // Write the field's hash. bw.WriteU32(Hash); // Write the field's bitmask. bw.WriteU32(Bitmask); // Write the field's offset. bw.WriteU16(Offset); // Write the field's shift. bw.WriteS8(Shift); // Write the field's type. bw.WriteU8((byte)Type); }
/// <summary> /// Write a single texture with specified Binary Writer. /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw) { // Write texture width. bw.WriteU16(Width); // Write texture width. bw.WriteU16(Height); // Write texture format. bw.WriteU8((byte)Format); // Write texture unknown 1. (Flags?) bw.WriteU8(AlphaFlag); // Write texture unknown 2. (Padding) bw.WriteU16(Unknown1); // Write texture data offset. bw.WriteU32(DataOffset); }
/// <summary> /// Write a single material with specified Binary Writer. /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw) { // Write Index. bw.WriteS16(Index); // Write Unknown 1. (Unused index?) bw.WriteS16(Unknown1); // Write U-Wrapping. bw.Write(WrapU); // Write V-Wrapping. bw.Write(WrapV); // Write Unknown 2. (Flags?) bw.WriteS16(Unknown2); // Write Unknown 3. bw.WriteS32s(Unknown3); }
/// <summary> /// Creates a byte array from this PRM. /// </summary> /// <returns>The PRM as a byte array.</returns> public byte[] Write() { // Define a stream to hold our PRM data. MemoryStream stream = new MemoryStream(); // Define a binary writer to write with. DhBinaryWriter bw = new DhBinaryWriter(stream, DhEndian.Big); // Write parameter entry count. bw.WriteU32((uint)Entries.Count); // Loop through parameter entries. for (int i = 0; i < Entries.Count; i++) { // Write a parameter entry. Entries[i].Write(bw); } // Returns the PRM as a byte array. return(stream.ToArray()); }
/// <summary> /// Creates a stream from this GEB. /// </summary> /// <returns>The GEB as a stream.</returns> public Stream Write() { // Define a stream to hold our GEB data. Stream stream = new MemoryStream(); // Define a binary writer to write with. DhBinaryWriter bw = new DhBinaryWriter(stream, DhEndian.Big); // Write GEB's sprite count. bw.WriteU32((uint)Sprites.Count); // Loop through the sprite entries. for (int i = 0; i < Sprites.Count; i++) { // Write sprite. Sprites[i].Write(bw); } // Returns the GEB as a stream. return(stream); }
/// <summary> /// Creates a stream from this JMP. /// </summary> /// <returns>The JMP as a stream.</returns> public Stream Write() { // Define a stream to hold our GEB data. Stream stream = new MemoryStream(); // Define a binary writer to write with. DhBinaryWriter bw = new DhBinaryWriter(stream, DhEndian.Big); // Write JMP's Header bw.WriteU32((uint)Entries.Count); bw.WriteU32((uint)Fields.Count); bw.WriteU32(EntryOffset); bw.WriteU32(EntrySize); // Write JMP's Fields for (int i = 0; i < Fields.Count; i++) { Fields[i].Write(bw); } // Seek to beginning of file. bw.Goto(0); // Write JMP's Entries for (int i = 0; i < Entries.Count; i++) { bw.Goto(EntryOffset + (i * EntrySize)); Entries[i].Write(bw, Fields); } // Back up from the end of the file. bw.Back(0); // Pad file with @'s to nearest whole 32 bytes. bw.WritePadding32('@'); // Returns the JMP as a stream. return(stream); }
/// <summary> /// Write a single shader with specified Binary Writer. /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw) { // Write Dynamic Lighting Flag. bw.Write(UseDynamicLighting ? 1 : 0); // Write Unknown 2. bw.Write(Unknown2); // Write Unknown 3. bw.Write(Unknown3); // Write Tint. bw.WriteClr4(Tint); // Write Unknown 4. (Padding) bw.Write(Unknown4); // Write Material Indices. bw.WriteS16s(MaterialIndices); // Write Unknown 5. (Indices?) bw.WriteS16s(Unknown5); }
/// <summary> /// Write a single triangle data entry with specified Binary Writer. /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw) { // Write Vertex Indices. bw.WriteS16s(VertexIndices); // Write Normal Index. bw.WriteS16(NormalIndex); // Write Edge Tangent Indices. bw.WriteS16s(EdgeTangentIndices); // Write Plane Point Index. bw.WriteS16(PlanePointIndex); // Write PlaneD Value. bw.WriteF32(PlaneDValue); // Write Unknown 1. bw.WriteS16(Unknown1); // Write Unknown 2. bw.WriteS16(Unknown2); }
/// <summary> /// Write a single material with specified Binary Writer. /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw) { // Write Index. bw.WriteS16(Index); // Write Unknown 1. (Unused index?) bw.WriteS16(Unknown1); // Write U-Wrapping. bw.Write(WrapU); // Write V-Wrapping. bw.Write(WrapV); // Write Unknown 2. (Flags?) bw.WriteS16(Unknown2); // Loop through the Unknown 3 values. for (int i = 0; i < Unknown3.Length; i++) { // Write the current Unknown 3 value. bw.WriteS32(Unknown3[i]); } }
/// <summary> /// Write a single batch with specified Binary Writer. /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw) { // TODO: Implement this. }
/// <summary> /// Creates a byte array from this MP. TODO: Complete writing. /// </summary> /// <returns>The MP as a byte array.</returns> public byte[] Write() { // Define a stream to hold our MP data. MemoryStream stream = new MemoryStream(); // Define a binary writer to write with. DhBinaryWriter bw = new DhBinaryWriter(stream, DhEndian.Big); // Define a buffer to store our offsets. uint[] offsets = new uint[7]; // Write Grid Scale. bw.WriteVec3(GridScale); // Write Minimum Bounds. bw.WriteVec3(MinimumBounds); // Write Axis Lengths. bw.WriteVec3(AxisLengths); // Write offsets. (CALCULATED) bw.WriteU32s(offsets); // Set vertices offset. offsets[0] = (uint)bw.Position(); // Loop through vertices. for (int i = 0; i < Vertices.Count; i++) { // Write vertex. bw.WriteVec3(Vertices[i]); } // Set normals offset. offsets[1] = (uint)bw.Position(); // Loop through normals. for (int i = 0; i < Normals.Count; i++) { // Write normals. bw.WriteVec3(Normals[i]); } // Set triangle data offset. offsets[2] = (uint)bw.Position(); // Loop through triangle data. for (int i = 0; i < TriangleData.Count; i++) { // Write triangle data. TriangleData[i].Write(bw); } // Set triangle groups offset. offsets[3] = (uint)bw.Position(); // Write ushort to define beginning of triangle groups section. bw.WriteU16(0xFFFF); // Loop through triangle groups. for (int i = 0; i < TriangleGroups.Count; i++) { // Write triangle group. TriangleGroups[i].Write(bw); } // Write ushort to define ending of triangle groups section. bw.WriteU16(0xFFFF); // Set grid indices offset. offsets[4] = (uint)bw.Position(); // Set duplicated grid indices offset. offsets[5] = (uint)bw.Position(); // Loop through grid indices. for (int i = 0; i < GridIndices.Count; i++) { // Write grid index. GridIndices[i].Write(bw); } // Set unknown data offset. offsets[6] = (uint)bw.Position(); // Loop through unknown data. (3 bytes each) for (int i = 0; i < Unknowns.Count; i++) { // Write unknown data. Unknowns[i].Write(bw); } // Pad to nearest whole 32. bw.WritePadding32('@'); // Goto offsets section. bw.Goto(36); // Write offsets. bw.WriteU32s(offsets); // Return the MP as a byte array. return(stream.ToArray()); }
/// <summary> /// Write a single entry to stream. /// Credits for the 'packing' snippet goes to arookas: /// https://github.com/arookas/jmpman/blob/master/jmpman/jmp.cs /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw, List <JField> fields) { // Save the current position. long currentPosition = bw.Position(); // Define a buffer to hold packed int values. Dictionary <ushort, uint> buffer = new Dictionary <ushort, uint>(fields.Count); // Loop through each value in the entry. for (int i = 0; i < fields.Count; i++) { // Seek from the current position to value's offset in the entry. bw.Sail(fields[i].Offset); // Check which type the current value is. switch (fields[i].Type) { case JFieldType.INTEGER: // Write the value as a integer. TODO: Add pack values. int value = int.Parse(Values[i].ToString()); // Check if current field has a bitmask. if (fields[i].Bitmask == 0xFFFFFFFF) { // Value is not packed, write data directly. bw.WriteS32((value)); } else { // Value is packed, data will be added to the buffer. if (!buffer.ContainsKey(fields[i].Offset)) { // Since no key exists yet, create one. buffer[fields[i].Offset] = 0u; } // Add the packet int value to the buffer. buffer[fields[i].Offset] |= ((uint)(value << fields[i].Shift) & fields[i].Bitmask); } break; case JFieldType.STRING: // Write the value as a string. bw.WriteStr32(Values[i].ToString()); break; case JFieldType.FLOAT: // Write the value as a float32. bw.WriteF32(float.Parse(Values[i].ToString())); break; default: // Something went horribly wrong. throw new InvalidDataException(); } // Write out the packed int's buffer. foreach (var data in buffer) { // bw.Goto(currentPosition + data.Key); // Write the packed int value. bw.WriteU32(data.Value); } // Seek back to the position we saved earlier. bw.Goto(currentPosition); } }
/// <summary> /// Creates a stream from this BTI. /// </summary> /// <returns>The BTI as a stream.</returns> public Stream Write() { // Define a stream to hold our BTI data. Stream stream = new MemoryStream(); // Define a binary writer to write with. DhBinaryWriter bw = new DhBinaryWriter(stream, DhEndian.Big); // Write Texture Format. bw.Write((byte)Format); // Write Alpha Flag. bw.Write(AlphaFlag); // Write Width. bw.WriteU16(Width); // Write Height. bw.WriteU16(Height); // Write WrapS. bw.Write((byte)WrapS); // Write WrapT. bw.Write((byte)WrapT); // Write PaletteFormat. bw.WriteU16((ushort)PaletteFormat); // Write PaletteCount. bw.WriteU16(PaletteCount); // Write PaletteOffset. bw.WriteU32(PaletteOffset); // Write Unknown1. bw.WriteU32(Unknown1); // Write MagFilterMode. bw.Write((byte)MagFilterMode); // Write MinFilterMode. bw.Write((byte)MinFilterMode); // Write Min LOD. bw.WriteU16(MinLOD); // Write Mag LOD. bw.Write(MagLOD); // Write MipMap Count. bw.Write(MipMapCount); // Write LodBias. bw.WriteU16(LodBias); // Write Data Offset. bw.WriteU32(DataOffset); // Write Data. bw.Write(ToBTI()); // Return the BTI a as stream. return(stream); }
/// <summary> /// Creates a byte array from this BIN. /// </summary> /// <returns>The BIN as a byte array.</returns> public byte[] Write() { // Define a stream to hold our BIN data. MemoryStream stream = new MemoryStream(); // Define a binary writer to write with. DhBinaryWriter bw = new DhBinaryWriter(stream, DhEndian.Big); // Define a buffer to store our offsets. uint[] offsets = new uint[21]; // Write version. bw.Write(Version); // Write model Name. bw.WriteFixedStr(ModelName, 11); // Write offsets. bw.WriteU32s(Offsets); // Make sure bin has textures. if (Textures.Count > 0) { // Set textures offset. offsets[0] = (uint)bw.Position(); // Define a array to temporarily uint[] textureDataOffsets = new uint[Textures.Count]; // Write texture headers. (CALCULATED) bw.Write(new byte[Textures.Count * 0x0C]); // Pad to nearest whole 32. bw.WritePadding32(); // Loop through textures to write texture data. for (int i = 0; i < textureDataOffsets.Length; i++) { // Get actual offset of texture data. textureDataOffsets[i] = (uint)bw.Position() - offsets[0]; // Write texture data. bw.Write(Textures[i].Data); } // Store this so we can resume after writing the texture headers. long currentOffset = (uint)bw.Position(); // Pad to nearest whole 32. bw.WritePadding32(); // Goto textures offset. bw.Goto(offsets[0]); // Loop through textures to write texture headers. for (int i = 0; i < Textures.Count; i++) { // Write texture width. bw.WriteU16(Textures[i].Width); // Write texture height. bw.WriteU16(Textures[i].Height); // Write texture format. bw.Write((byte)Textures[i].Format); // Write texture alpha flag. bw.Write(Textures[i].AlphaFlag); // Write padding. bw.WriteU16(0); // Write texture dataoffset. bw.WriteU32(textureDataOffsets[i]); } // Goto resume point. bw.Goto(currentOffset); // Pad to nearest whole 32. bw.WritePadding32(); } // Make sure bin has materials. if (Materials.Count > 0) { // Set materials offset. offsets[1] = (uint)bw.Position(); // Loop through materials. for (int i = 0; i < Materials.Count; i++) { // Write material. Materials[i].Write(bw); } // Pad to nearest whole 32. bw.WritePadding32(); } // Make sure bin has positions. if (Positions.Count > 0) { // Set positions offset. offsets[2] = (uint)bw.Position(); // Loop through positions. for (int i = 0; i < Positions.Count; i++) { // Write position. bw.WriteS16s(new short[] { (short)(Positions[i].X * 256.0f), (short)(Positions[i].Y * 256.0f), (short)(Positions[i].Z * 256.0f) }); } // Pad to nearest whole 32. bw.WritePadding32(); } // Make sure bin has normals. if (Normals.Count > 0) { // Set normals offset. offsets[3] = (uint)bw.Position(); // Loop through normals. for (int i = 0; i < Normals.Count; i++) { // Write normal. bw.WriteVec3(Normals[i]); } // Pad to nearest whole 32. bw.WritePadding32(); } // SKIP COLOR0 offsets[4] = (uint)0; // SKIP COLOR1 offsets[5] = (uint)0; // Make sure bin has texture coordinates 0. if (TextureCoordinates0.Count > 0) { // Set texture coordinates 0 offset. offsets[6] = (uint)bw.Position(); // Loop through texture coordinates 0. for (int i = 0; i < TextureCoordinates0.Count; i++) { // Write texture coordinate 0. bw.WriteVec2(TextureCoordinates0[i]); } // Pad to nearest whole 32. bw.WritePadding32(); } // SKIP TEXTURE COORDINATES 1 offsets[7] = (uint)0; // SKIP TEXTURE COORDINATES 2 (?) offsets[8] = (uint)0; // SKIP TEXTURE COORDINATES 3 (?) offsets[9] = (uint)0; // Make sure bin has shaders. if (Shaders.Count > 0) { // Set shaders offset. offsets[10] = (uint)bw.Position(); // Loop through shaders. for (int i = 0; i < Shaders.Count; i++) { // Write shader. Shaders[i].Write(bw); } // Pad to nearest whole 32. bw.WritePadding32(); } // Make sure bin has batches. if (Batches.Count > 0) { // Set batches offset. offsets[11] = (uint)bw.Position(); // Loop through batches. for (int i = 0; i < Batches.Count; i++) { // Write batch headers. Batches[i].Write(bw); } // Pad to nearest whole 32. bw.WritePadding32(); // We need to store this stuff somewhere long[] listStarts = new long[Batches.Count]; long[] listEnds = new long[Batches.Count]; // Loop through batches. (Write primitives) for (int i = 0; i < Batches.Count; i++) { // We'll store this offset for later. listStarts[i] = bw.Position(); // Loop through primitives. for (int y = 0; y < Batches[i].Primitives.Count; y++) { // Write primitive. Batches[i].Primitives[y].Write(bw, Batches[i].VertexAttributes); } // We'll store this offset for later. listEnds[i] = bw.Position(); } // This offset is where we'll continue writing from. long currentOffset = bw.Position(); // Loop through batches. (Write offsets) for (int i = 0; i < Batches.Count; i++) { // Goto current batch's offset. bw.Goto(offsets[11] + i * 24); // Skip 2 bytes. bw.Sail(2); // Write list size represented as 32 byte blocks. bw.WriteS16((short)(Math.Ceiling((float)(listEnds[i] - listStarts[i]) / 32))); // Skip 8 bytes. bw.Sail(8); // Write primitive list offset. bw.WriteU32((uint)(listStarts[i] - offsets[11])); } // Goto continue point we saved earlier. bw.Goto(currentOffset); // Pad to nearest whole 32. bw.WritePadding32(); } // Make sure bin has graphobjects. if (GraphObjects.Count > 0) { // Set graphObjects offset. offsets[12] = (uint)bw.Position(); // Loop through graphObjects. for (int i = 0; i < GraphObjects.Count; i++) { // Write graphObject headers. GraphObjects[i].Write(bw); } // Pad to nearest whole 16. bw.WritePadding16(); // Array to hold graphobject's parts offset. long[] graphObjectsPartsOffsets = new long[GraphObjects.Count]; // Loop through graphObjects. (Write parts) for (int i = 0; i < GraphObjects.Count; i++) { // Store this graphobject's part offset. graphObjectsPartsOffsets[i] = bw.Position(); // Loop through graphobject's parts. for (int y = 0; y < GraphObjects[i].Parts.Count; y++) { // Write graphobject's parts. GraphObjects[i].Parts[y].Write(bw); } } // This offset is where we'll continue writing from. long currentOffset = bw.Position(); // Loop through graphObjects. (Write offsets) for (int i = 0; i < GraphObjects.Count; i++) { // Goto current graphobject's part offset. bw.Goto(offsets[12] + (i * 140)); // Skip 80 bytes. bw.Sail(80); // Write graphobject's part offset. bw.WriteU32((uint)(graphObjectsPartsOffsets[i] - offsets[12])); } // Goto continue point we saved earlier. bw.Goto(currentOffset); } // Goto offsets section. bw.Goto(12); // Write offsets. bw.WriteU32s(offsets); // Goto end of file. bw.Back(0); // Pad to nearest whole 16. bw.WritePadding16(); // Return the BIN as a byte array. return(stream.ToArray()); }
/// <summary> /// Creates a stream from this TXP. /// </summary> /// <returns>The TXP as a stream.</returns> public Stream Write() { // Buffer for new TXP File Stream stream = new MemoryStream(); // Define a binary writer to write with. DhBinaryWriter bw = new DhBinaryWriter(stream, DhEndian.Big); // Write Unknown 1. bw.WriteU16(Unknown1); // Write Unknown 2. bw.WriteU16(Unknown2); // Write Entry Count. bw.WriteU16((ushort)Entries.Count); // Check if Entry Count is greater than 0. if (Entries.Count > 0) { // Write Keyframe Count. bw.WriteU16((ushort)Entries[0].Indices.Count); } else { // Write 0. bw.WriteU16(0); } // Write Keyframe Offset. bw.WriteU32((uint)(12 + (Entries.Count * 12))); // Loop through entries. for (int i = 0; i < Entries.Count; i++) { // Write entry header. Entries[i].WriteHeader(bw); } // Define a list to hold the offsets for each keyframe offsets. List <uint> indicesOffsets = new List <uint>(); // Loop through entries. for (int i = 0; i < Entries.Count; i++) { // Save the current offset indicesOffsets.Add((uint)bw.Position()); // Write entry indices. Entries[i].WriteIndices(bw); } // Loop through entries. for (int i = 0; i < Entries.Count; i++) { // Go to current entry's indices offset value. bw.Goto(0x0C + (i * 12) + 8); // Write indices offset. bw.WriteU32(indicesOffsets[i]); } // Return to end of file. bw.Back(0); // Write padding to nearest whole 32 bytes. bw.WritePadding32(); // Return the TXP as a stream return(stream); }
/// <summary> /// Write a single unknown with specified Binary Writer. /// </summary> /// <param name="bw">Binary Writer to use.</param> public void Write(DhBinaryWriter bw) { // Write unknown 1. (3 bytes) bw.Write(Unknown1); }