public static LoadError LoadFromStream(Stream stream, out Cnk0 cnk0) { if (stream == null) { cnk0 = null; return LoadError.NullStream; } BinaryReader binaryReader = new BinaryReader(stream); //header char[] magic = binaryReader.ReadChars(4); if (magic[0] != 'C' || magic[1] != 'N' || magic[2] != 'K' || magic[3] != '0') { cnk0 = null; return LoadError.BadHeader; } int version = binaryReader.ReadInt32(); if (version != VERSION) { cnk0 = null; return LoadError.VersionMismatch; } uint uncompressedSize = binaryReader.ReadUInt32(); uint compressedSize = binaryReader.ReadUInt32(); byte[] inputBuffer = binaryReader.ReadBytes((int)compressedSize); binaryReader.Close(); byte[] outputBuffer = new byte[uncompressedSize]; Lzham.ZStream zStream = new Lzham.ZStream(); Lzham.ZInflateInit2(zStream, 20); zStream.AvailableInputBytes = compressedSize; zStream.AvailableOutputBytes = uncompressedSize; GCHandle inputBufferGCHandle = GCHandle.Alloc(inputBuffer, GCHandleType.Pinned); GCHandle outputBufferGCHandle = GCHandle.Alloc(outputBuffer, GCHandleType.Pinned); zStream.NextInputByte = inputBufferGCHandle.AddrOfPinnedObject(); zStream.NextOutputByte = outputBufferGCHandle.AddrOfPinnedObject(); Lzham.ZInflate(zStream, (int)Lzham.ZFlush.Finish); Lzham.ZInflateEnd(zStream); inputBufferGCHandle.Free(); outputBufferGCHandle.Free(); MemoryStream memoryStream = new MemoryStream(outputBuffer); binaryReader = new BinaryReader(memoryStream); cnk0 = new Cnk0(); //tiles uint tileCount = binaryReader.ReadUInt32(); cnk0.Tiles = new Tile[tileCount]; for (uint i = 0; i < tileCount; ++i) { Tile tile; if (Tile.LoadFromStream(memoryStream, out tile) != Tile.LoadError.None) { cnk0 = null; return LoadError.BadTile; } cnk0.Tiles[i] = tile; } //unknown block uint unknown0 = binaryReader.ReadUInt32(); uint unknown1 = binaryReader.ReadUInt32(); binaryReader.BaseStream.Seek(unknown1 * 4, SeekOrigin.Current); //indices uint indexCount = binaryReader.ReadUInt32(); cnk0.Indices = new ushort[indexCount]; for (int i = 0; i < indexCount; ++i) cnk0.Indices[i] = binaryReader.ReadUInt16(); //vertices uint vertexCount = binaryReader.ReadUInt32(); cnk0.Vertices = new Vertex[vertexCount]; for (int i = 0; i < vertexCount; ++i) { Vertex vertex; if (Vertex.LoadFromStream(binaryReader.BaseStream, out vertex) != Vertex.LoadError.None) { cnk0 = null; return LoadError.BadVertex; } cnk0.Vertices[i] = vertex; } //render batches uint renderBatchCount = binaryReader.ReadUInt32(); cnk0.RenderBatches = new RenderBatch[renderBatchCount]; for (uint i = 0; i < renderBatchCount; ++i) { RenderBatch renderBatch; if (RenderBatch.LoadFromStream(binaryReader.BaseStream, out renderBatch) != RenderBatch.LoadError.None) { cnk0 = null; return LoadError.BadRenderBatch; } cnk0.RenderBatches[i] = renderBatch; } binaryReader.Close(); return LoadError.None; }
public static LoadError LoadFromStream(Stream stream, out Cnk0 cnk0) { if (stream == null) { cnk0 = null; return(LoadError.NullStream); } BinaryReader binaryReader = new BinaryReader(stream); //header char[] magic = binaryReader.ReadChars(4); if (magic[0] != 'C' || magic[1] != 'N' || magic[2] != 'K' || magic[3] != '0') { cnk0 = null; return(LoadError.BadHeader); } int version = binaryReader.ReadInt32(); if (version != VERSION) { cnk0 = null; return(LoadError.VersionMismatch); } uint uncompressedSize = binaryReader.ReadUInt32(); uint compressedSize = binaryReader.ReadUInt32(); byte[] inputBuffer = binaryReader.ReadBytes((int)compressedSize); binaryReader.Close(); byte[] outputBuffer = new byte[uncompressedSize]; Lzham.ZStream zStream = new Lzham.ZStream(); Lzham.ZInflateInit2(zStream, 20); zStream.AvailableInputBytes = compressedSize; zStream.AvailableOutputBytes = uncompressedSize; GCHandle inputBufferGCHandle = GCHandle.Alloc(inputBuffer, GCHandleType.Pinned); GCHandle outputBufferGCHandle = GCHandle.Alloc(outputBuffer, GCHandleType.Pinned); zStream.NextInputByte = inputBufferGCHandle.AddrOfPinnedObject(); zStream.NextOutputByte = outputBufferGCHandle.AddrOfPinnedObject(); Lzham.ZInflate(zStream, (int)Lzham.ZFlush.Finish); Lzham.ZInflateEnd(zStream); inputBufferGCHandle.Free(); outputBufferGCHandle.Free(); MemoryStream memoryStream = new MemoryStream(outputBuffer); binaryReader = new BinaryReader(memoryStream); cnk0 = new Cnk0(); //tiles uint tileCount = binaryReader.ReadUInt32(); cnk0.Tiles = new Tile[tileCount]; for (uint i = 0; i < tileCount; ++i) { Tile tile; if (Tile.LoadFromStream(memoryStream, out tile) != Tile.LoadError.None) { cnk0 = null; return(LoadError.BadTile); } cnk0.Tiles[i] = tile; } //unknown block uint unknown0 = binaryReader.ReadUInt32(); uint unknown1 = binaryReader.ReadUInt32(); binaryReader.BaseStream.Seek(unknown1 * 4, SeekOrigin.Current); //indices uint indexCount = binaryReader.ReadUInt32(); cnk0.Indices = new ushort[indexCount]; for (int i = 0; i < indexCount; ++i) { cnk0.Indices[i] = binaryReader.ReadUInt16(); } //vertices uint vertexCount = binaryReader.ReadUInt32(); cnk0.Vertices = new Vertex[vertexCount]; for (int i = 0; i < vertexCount; ++i) { Vertex vertex; if (Vertex.LoadFromStream(binaryReader.BaseStream, out vertex) != Vertex.LoadError.None) { cnk0 = null; return(LoadError.BadVertex); } cnk0.Vertices[i] = vertex; } //render batches uint renderBatchCount = binaryReader.ReadUInt32(); cnk0.RenderBatches = new RenderBatch[renderBatchCount]; for (uint i = 0; i < renderBatchCount; ++i) { RenderBatch renderBatch; if (RenderBatch.LoadFromStream(binaryReader.BaseStream, out renderBatch) != RenderBatch.LoadError.None) { cnk0 = null; return(LoadError.BadRenderBatch); } cnk0.RenderBatches[i] = renderBatch; } binaryReader.Close(); return(LoadError.None); }