mirror of
https://github.com/ClassiCube/ClassiCube.git
synced 2025-10-10 14:48:48 -04:00
73 lines
2.0 KiB
C#
73 lines
2.0 KiB
C#
// ClassicalSharp copyright 2014-2016 UnknownShadow200 | Licensed under MIT
|
|
using System;
|
|
using System.IO;
|
|
using System.IO.Compression;
|
|
|
|
namespace ClassicalSharp.Map {
|
|
|
|
public sealed class MapSchematicExporter : IMapFormatExporter {
|
|
|
|
public void Save(Stream stream, Game game) {
|
|
using (GZipStream wrapper = new GZipStream(stream, CompressionMode.Compress)) {
|
|
BinaryWriter writer = new BinaryWriter(wrapper);
|
|
NbtFile nbt = new NbtFile(writer);
|
|
World map = game.World;
|
|
|
|
nbt.Write(NbtTagType.Compound); nbt.Write("Schematic");
|
|
|
|
nbt.Write(NbtTagType.String);
|
|
nbt.Write("Materials"); nbt.Write("Classic");
|
|
|
|
nbt.Write(NbtTagType.Int16);
|
|
nbt.Write("Width"); nbt.WriteInt16((short)map.Width);
|
|
|
|
nbt.Write(NbtTagType.Int16);
|
|
nbt.Write("Height"); nbt.WriteInt16((short)map.Height);
|
|
|
|
nbt.Write(NbtTagType.Int16);
|
|
nbt.Write("Length"); nbt.WriteInt16((short)map.Length);
|
|
|
|
WriteBlocks(nbt, map.blocks);
|
|
|
|
WriteBlockData(nbt, map.blocks);
|
|
|
|
nbt.Write(NbtTagType.List);
|
|
nbt.Write("Entities");
|
|
nbt.Write(NbtTagType.Compound); nbt.WriteInt32(0);
|
|
|
|
nbt.Write(NbtTagType.List);
|
|
nbt.Write("TileEntities");
|
|
nbt.Write(NbtTagType.Compound); nbt.WriteInt32(0);
|
|
|
|
nbt.Write(NbtTagType.End);
|
|
}
|
|
}
|
|
|
|
|
|
void WriteBlocks(NbtFile nbt, byte[] blocks) {
|
|
const int chunkSize = 64 * 1024 * 32;
|
|
nbt.Write(NbtTagType.Int8Array);
|
|
nbt.Write("Blocks");
|
|
nbt.WriteInt32(blocks.Length);
|
|
|
|
for (int i = 0; i < blocks.Length; i += chunkSize) {
|
|
int count = Math.Min(chunkSize, blocks.Length - i);
|
|
nbt.WriteBytes(blocks, i, count);
|
|
}
|
|
}
|
|
|
|
void WriteBlockData(NbtFile nbt, byte[] blocks) {
|
|
const int chunkSize = 64 * 1024;
|
|
byte[] chunk = new byte[chunkSize];
|
|
nbt.Write(NbtTagType.Int8Array);
|
|
nbt.Write("Data");
|
|
nbt.WriteInt32(blocks.Length);
|
|
|
|
for (int i = 0; i < blocks.Length; i += chunkSize) {
|
|
// All 0 so we can skip this.
|
|
int count = Math.Min(chunkSize, blocks.Length - i);
|
|
nbt.WriteBytes(chunk, 0, count);
|
|
}
|
|
}
|
|
}
|
|
} |