public override void Read(RW4Model m, RW4Section s, Stream r) { if (s.type_code != type_code) { throw new ModelFormatException(r, "VA000 Bad type code", s.type_code); } var section_1 = r.ReadS32(); vertexFormatSection = section_1; this.unk2 = r.ReadU32(); r.expect(0, "VA001"); var vcount = r.ReadU32(); r.expect(8, "VA002"); vertexSize = r.ReadU32(); var section_number = r.ReadS32(); var section = m.Sections[section_number]; section.LoadObject(m, vertices = new VertexBuffer((int)vcount), r); section = m.Sections[section_1]; if (section.type_code != VertexFormat.type_code) { throw new ModelFormatException(r, "VA101 Bad section type code", section.type_code); } section.GetObject(m, r, out format); //get the stuff }
public override void Read(RW4Model m, RW4Section s, Stream r) { // TODO: some files have multiple meshes referencing the same vertex and/or triangle buffers r.expect(40, "ME001"); r.expect(4, "ME002"); var tri_section = r.ReadS32(); this.tri_count = r.ReadU32(); r.expect(1, "ME003"); r.expect(0, "ME004"); r.expect(tri_count * 3, "ME005"); r.expect(0, "ME006"); this.vert_count = r.ReadU32(); var vert_section = r.ReadS32(); m.Sections[tri_section].GetObject(m, r, out triangles); if (triangles.triangles.Length != tri_count) { throw new ModelFormatException(r, "ME100 Triangle count mismatch", new KeyValuePair <uint, int>(tri_count, triangles.triangles.Length)); } if (vert_section != 0x400000) { m.Sections[vert_section].GetObject(m, r, out vertices); if (vertices.vertices.Length != vert_count) { throw new ModelFormatException(r, "ME200 Vertex count mismatch", new KeyValuePair <uint, int>(vert_count, vertices.vertices.Length)); } //seperate the vertices Vertex previousVertex = new Vertex(); int element = 0; for (int j = 0; j < vertices.vertices.Length; j++) { if (previousVertex.VertexComponents != null) { bool isMatch = true; for (int i = 0; i < vertices.vertices[j].VertexComponents.Count; i++) { if (vertices.vertices[j].VertexComponents[i].DeclarationType == D3DDECLTYPE.D3DDECLTYPE_D3DCOLOR) { if (vertices.vertices[j].VertexComponents[i].Value != previousVertex.VertexComponents[i].Value) { isMatch = false; } } } if (!isMatch) { element++; } } Vertex newVertex = vertices.vertices[j]; newVertex.Element = element; vertices.vertices[j] = newVertex; previousVertex = vertices.vertices[j]; } vertices.section.obj = vertices; } }
public override void Read(RW4Model m, RW4Section s, Stream r) { if (s.type_code != type_code) { throw new ModelFormatException(r, "TA000 Bad type code", s.type_code); } unk1 = r.ReadU32(); r.expect(0, "TA001"); var ind_count = r.ReadU32(); r.expect(8, "TA002"); r.expect(101, "TA003"); r.expect(4, "TA004"); var section_number = r.ReadS32(); if (ind_count % 3 != 0) { throw new ModelFormatException(r, "TA010", ind_count); } var tri_count = ind_count / 3; var section = m.Sections[section_number]; section.LoadObject(m, triangles = new Buffer <Triangle>((int)tri_count), r); }
public override void Write(RW4Model m, RW4Section s, Stream w) { w.WriteU32(Size); if (Header != null) { w.Write(Header, 0, Header.Length); } if (VertexFormatData != null) { w.Write(VertexFormatData, 0, VertexFormatData.Length); } if (AdditionalData != null) { w.Write(AdditionalData, 0, AdditionalData.Length); } foreach (MaterialTextureReference mat in Materials) { w.WriteU32(mat.Unknown1); w.WriteU32(mat.Unknown2); w.WriteU32(mat.TextureInstanceId); w.WriteU32(mat.Unknown3); w.WriteU32(mat.Unknown4); w.WriteU32(mat.Unknown5); } if (Data != null) { w.Write(Data, 0, Data.Length); } }
public void LoadObject(RW4Model model, RW4Object o, Stream r) { if (obj != null) { throw new ModelFormatException(r, "Attempt to decode section twice.", Number); } long start = r.Position; obj = o; o.section = this; o.model = model; r.Seek(Pos, SeekOrigin.Begin); obj.Read(model, this, r); if (r.Position != Pos + Size) { throw new ModelFormatException(r, "Section incompletely read.", Number); } var cs = obj.ComputeSize(); if (cs != -1 && cs != Size) { throw new ModelFormatException(r, "Section Size doesn't match computed Size.", Number); } r.Seek(start, SeekOrigin.Begin); }
public override void Write(RW4Model m, RW4Section s, Stream w) { for (int i = 0; i < items.Length; i++) { items[i].Write(w); } }
public WriteableBitmap GetBitmap() { DatabaseIndex imageIndex = DatabaseManager.Instance.Indices.Find(idx => idx.InstanceId == this.TextureInstanceId && (idx.TypeId == PropertyConstants.RasterImageType || idx.TypeId == PropertyConstants.RW4ImageType)); if (imageIndex != null) { if (imageIndex.TypeId == PropertyConstants.RasterImageType) { using (MemoryStream imageByteStream = new MemoryStream(imageIndex.GetIndexData(true))) { RasterImage img = RasterImage.CreateFromStream(imageByteStream, RasterChannel.All); return(img.MipMaps[0]); } } else if (imageIndex.TypeId == PropertyConstants.RW4ImageType) { using (MemoryStream imageByteStream = new MemoryStream(imageIndex.GetIndexData(true))) { RW4Model mod = new RW4Model(); mod.Read(imageByteStream); RW4Section texSection = mod.Sections.First(s => s.TypeCode == SectionTypeCodes.Texture); return((texSection.obj as Texture).ToImage(false)); } } } return(null); }
public override void Read(RW4Model m, RW4Section s, Stream r) { if (!Relocatable()) { this.required_position = r.Position; } blob = r.ReadBytes((int)s.Size); }
public override void Write(RW4Model m, RW4Section s, Stream w) { if (this.required_position >= 0 && w.Position != this.required_position) { throw new ModelFormatException(w, "Unable to move Unknown2 section", null); } w.Write(blob, 0, blob.Length); }
public override void Write(RW4Model m, RW4Section s, Stream w) { w.WriteU32(0x400000); w.WriteU32(unk1); w.WriteU32(mat3.section.Number); w.WriteU32(jointInfo.section.Number); w.WriteU32(mat4.section.Number); }
public override void Write(RW4Model m, RW4Section s, Stream w) { w.WriteU32(mesh.section.Number); w.WriteU32((uint)mat.Length); foreach (var x in mat) { w.WriteU32(x.section.Number); } }
public override void Write(RW4Model m, RW4Section s, Stream w) { w.Write(unk_data_1, 0, unk_data_1.Length); w.WriteU32(texture.section.Number); for (int i = 0; i < unk_data_2.Length; i++) { w.WriteS32(unk_data_2[i]); } }
public override void Read(RW4Model m, RW4Section s, Stream r) { minx = r.ReadF32(); miny = r.ReadF32(); minz = r.ReadF32(); unk1 = r.ReadU32(); maxx = r.ReadF32(); maxy = r.ReadF32(); maxz = r.ReadF32(); unk2 = r.ReadU32(); if (minx > maxx || miny > maxy || minz > maxz) { throw new ModelFormatException(r, "BBOX011", null); } }
public void Write(Stream w, RW4Model model) { w.WritePadding(Pos - w.Position); obj.Write(model, this, w); if (w.Position != Pos + Size) { throw new ModelFormatException(w, "Section incompletely written.", Number); } }
public override void Write(RW4Model m, RW4Section s, Stream w) { w.WriteU32(unk1); w.WriteU32(0); w.WriteU32((uint)triangles.Length * 3); w.WriteU32(8); w.WriteU32(101); w.WriteU32(4); w.WriteU32(triangles.section.Number); }
public ModelUnpack(Stream input, string outputPath) { var model = new RW4Model(); model.Read(input); //if (model.FileType == RW4Model.FileTypes.Model) // unpackModel(model, outputPath + "\\model.mesh.xml"); // else unpackTexture(model, outputPath + "\\texture"); }
public override void Write(RW4Model m, RW4Section s, Stream w) { w.WriteU32((uint)this.vertexFormatSection); w.WriteU32(this.unk2); w.WriteU32(0); w.WriteU32((uint)vertices.Length); w.WriteU32(8); w.WriteU32(vertexSize); w.WriteU32(vertices.section.Number); }
public DDSPack(string inputFileName, Stream output) { using (var src = File.OpenRead(inputFileName)) { var model = new RW4Model(); model.New(); pack(src, model); model.Write(output); } }
public void GetObject <T>(RW4Model model, Stream r, out T o) where T : RW4Object, new() { if (obj != null) { o = (T)obj; return; } o = new T(); LoadObject(model, o, r); }
public override void Read(RW4Model m, RW4Section s, Stream r) { if (s.type_code != type_code) { throw new ModelFormatException(r, "VB000 Bad type code", s.type_code); } for (int i = 0; i < items.Length; i++) { items[i].Read(r); } }
public ModelPack(string inputFileName, Stream output) { var src_model = new OgreXmlReader(inputFileName); var model = new RW4Model(); model.New(); pack(src_model, model); model.Write(output); }
public override void Write(RW4Model m, RW4Section s, Stream w) { w.WriteU32(textureType); w.WriteU32(8); w.WriteU32(unk1); w.WriteU16(width); w.WriteU16(height); w.WriteU32(mipmapInfo); w.WriteU32(0); w.WriteU32(0); w.WriteU32(texData.section.Number); }
public override void Write(RW4Model m, RW4Section s, Stream w) { var p1 = (uint)w.Position + 16; w.WriteU32(p1); w.WriteU32((uint)items.Length); w.WriteU32(0); w.WriteU32(0); foreach (var i in items) { i.Write(w); } }
public UInt32 id; // hash or guid, referenced by Anim to specify which bones to animate? public override void Read(RW4Model m, RW4Section s, Stream r) { if (s.type_code != type_code) { throw new ModelFormatException(r, "HI000", s.type_code); } var p2 = r.ReadU32(); var p3 = r.ReadU32(); var p1 = r.ReadU32(); var c1 = r.ReadU32(); id = r.ReadU32(); r.expect(c1, "HI001"); if (p1 != r.Position) { throw new ModelFormatException(r, "HI010", p1); } if (p2 != p1 + 4 * c1) { throw new ModelFormatException(r, "HI011", p2); } if (p3 != p1 + 8 * c1) { throw new ModelFormatException(r, "HI012", p3); } items = new Item[c1]; for (int i = 0; i < c1; i++) { items[i] = new Item { index = i, name_fnv = r.ReadU32() } } ; for (int i = 0; i < c1; i++) { items[i].flags = r.ReadU32(); } for (int i = 0; i < c1; i++) { var pind = r.ReadS32(); if (pind == -1) { items[i].parent = null; } else { items[i].parent = items[pind]; } } }
public override void Read(RW4Model m, RW4Section s, Stream r) { var sn1 = r.ReadS32(); var count = r.ReadU32(); // always exactly 1, so I am guessing var sns = new Int32[count]; for (int i = 0; i < count; i++) { sns[i] = r.ReadS32(); } m.Sections[sn1].GetObject(m, r, out mesh); mat = new RW4TexMetadata[count]; //for (int i = 0; i < count; i++) // m.Sections[sns[i]].GetObject(m, r, out mat[i]); }
void pack(Stream src, RW4Model model) { // Read the DDS src.expect(0x20534444, "DDS000"); // 'DDS ' int headerSize = src.ReadS32(); if (headerSize < 0x7C) throw new ModelFormatException(src, "DDS001", headerSize); var flags = src.ReadU32(); var height = src.ReadS32(); var width = src.ReadS32(); var pitchOrLinearSize = src.ReadU32(); src.expect(0, "DDS002"); // < depth var mipmaps = src.ReadS32(); src.Seek(src.Position + 11 * 4, SeekOrigin.Begin); var pfsize = src.ReadS32(); if (pfsize < 32) throw new ModelFormatException(src, "DDS011", pfsize); var pf_flags = src.ReadU32(); if ((pf_flags & 4) == 0) throw new ModelFormatException(src, "DDS012", pf_flags); var fourcc = src.ReadU32(); if (fourcc != Texture.DXT5) throw new NotSupportedException("Texture packing currently only supports DXT5 compressed input textures."); src.Seek(headerSize+4, SeekOrigin.Begin); var sizes = (from i in Enumerable.Range(0, mipmaps) select Math.Max(width>>i,4)*Math.Max(height>>i,4) // DXT5: 16 bytes per 4x4=16 pixels ).ToArray(); var all_mipmaps = new byte[ sizes.Sum() ]; for (int offset=0, i = 0; i < mipmaps; i++) { if (src.Read( all_mipmaps, offset, sizes[i] ) != sizes[i]) throw new ModelFormatException(src, "Unexpected EOF reading .DDS file", null); offset += sizes[i]; } // Build the RW4 model.FileType = RW4Model.FileTypes.Texture; var texture = new Texture() { width = (ushort)width, height = (ushort)height, mipmapInfo = (uint)(0x100 * mipmaps + 0x08), textureType = fourcc, texData = new TextureBlob { blob = all_mipmaps }, unk1 = 0 }; model.AddObject(texture.texData, TextureBlob.type_code); model.AddObject(texture, Texture.type_code); }
public override void Read(RW4Model m, RW4Section s, Stream r) { var p1 = r.ReadU32(); var count = r.ReadU32(); r.expect(0, "MS001"); /// These bytes are padding to 16 bytes, but this structure is itself always aligned r.expect(0, "MS002"); if (p1 != r.Position) { throw new ModelFormatException(r, "MS001", p1); } items = new T[count]; for (int i = 0; i < count; i++) { items[i].Read(r); } }
public override void Read(RW4Model m, RW4Section s, Stream r) { int startingPosition = (int)r.Position; VertexElements = new List <VertexUsage>(); r.expect(0x00000000, "Not Zero VF001"); r.expect(0x00000000, "Not Zero VF002"); r.expect(0x00000000, "Not Zero VF003"); _vertexComponents = r.ReadU16(); //amount of 'items' in this vertex? VertexSize = r.ReadU16BE(); _unknown2 = r.ReadU32BE(); _unknown3 = r.ReadU32BE(); //uint _unknown4 = r.ReadU32BE(); //zero for (int i = 0; i < _vertexComponents; i++) { byte unk1 = r.ReadU8(); //always zero ushort _offset = r.ReadU16BE(); ushort _type = r.ReadU16BE(); ushort _usage = r.ReadU16BE(); byte _index = r.ReadU8(); byte _unknown = r.ReadU8(); ushort unk3 = r.ReadU16BE(); //always zero byte unk4 = r.ReadU8(); //always zero VertexElements.Add(new VertexUsage() { Unknown1 = unk1, Offset = _offset, Usage = (D3DDECLUSAGE)_usage, Index = _index, DeclarationType = (D3DDECLTYPE)_type, Unknown2 = _unknown, Unknown3 = unk3, Unknown4 = unk4 }); } size = (int)r.Position - startingPosition; }
public override void Read(RW4Model m, RW4Section s, Stream r) { Materials = new List <MaterialTextureReference>(); long pos = r.Position; Size = r.ReadU32(); Header = r.ReadBytes(28); //read the header //find the vertex format RW4Section vertexFormatSection = m.Sections.Find(sec => sec.TypeCode == SectionTypeCodes.VertexFormat); if (vertexFormatSection != null) { int vertexFormatSize = vertexFormatSection.obj.ComputeSize(); VertexFormatData = r.ReadBytes(vertexFormatSize); } long currentPos = r.Position; uint u2D = 0; while (u2D != 0x2D) { u2D = r.ReadU32(); } int additionalDataSize = (int)r.Position - (int)currentPos - 4; r.Seek(currentPos, SeekOrigin.Begin); AdditionalData = r.ReadBytes(additionalDataSize); for (int i = 0; i < 6; i++) { MaterialTextureReference mat = new MaterialTextureReference(); mat.Unknown1 = r.ReadU32(); mat.Unknown2 = r.ReadU32(); mat.TextureInstanceId = r.ReadU32(); mat.Unknown3 = r.ReadU32(); mat.Unknown4 = r.ReadU32(); mat.Unknown5 = r.ReadU32(); Materials.Add(mat); } Data = r.ReadBytes((int)Size - (int)(r.Position - pos)); }
/* * void unpackModel(RW4Model model, string outputFileName) * { * var meshes = model.GetObjects(RW4Mesh.type_code); * if (meshes.Count != 1) throw new NotSupportedException("Only exactly one mesh supported."); * var mesh = meshes[0] as RW4Mesh; * * if (mesh.vertices == null) throw new NotSupportedException("Only models with a vertex buffer can be unpacked."); * * new OgreXmlWriter(mesh.vertices.vertices.ToArray(), * mesh.triangles.triangles.ToArray(), * outputFileName); * type = "mesh"; * } * */ void unpackTexture(RW4Model model, string outputFileName) { var textures = model.GetObjects(Texture.type_code); // if (textures.Count != 1) // throw new NotSupportedException("Only exactly one texture supported in a texture rw4."); int j = 0; foreach (Texture texture in textures) { using (var stream = File.Create(outputFileName + j.ToString() + ".dds")) { stream.WriteU32(0x20534444); // 'DDS ' stream.WriteU32(0x7C); // header size stream.WriteU32(0xA1007); // flags: stream.WriteU32(texture.height); stream.WriteU32(texture.width); stream.WriteU32((uint)texture.height * (uint)texture.width); // size of top mipmap level... at least in DXT5 for >4x4 stream.WriteU32(0); stream.WriteU32(texture.mipmapInfo / 0x100); for (int i = 0; i < 11; i++) { stream.WriteU32(0); } // pixel format stream.WriteU32(32); stream.WriteU32(4); // DDPF_FOURCC? stream.WriteU32(texture.textureType); stream.WriteU32(32); stream.WriteU32(0xff0000); stream.WriteU32(0x00ff00); stream.WriteU32(0x0000ff); stream.WriteU32(0xff000000); stream.WriteU32(0); // 0x41008 for (int i = 0; i < 4; i++) { stream.WriteU32(0); } stream.Write(texture.texData.blob, 0, texture.texData.blob.Length); j++; } type = "texture"; } }