Implement Partial Types (Types which require constructing with info), Implement Items, Implement NBT, add exceptions so they go down the tree!

This commit is contained in:
Myles 2016-03-14 16:09:50 +00:00
parent 55335944e3
commit 0357d8e6aa
31 changed files with 346 additions and 46 deletions

View File

@ -1,10 +1,9 @@
package us.myles.ViaVersion.chunks;
import lombok.AccessLevel;
import lombok.Getter;
import lombok.RequiredArgsConstructor;
@RequiredArgsConstructor(access = AccessLevel.PROTECTED)
@RequiredArgsConstructor
@Getter
public class Chunk {
private final int x;
@ -21,7 +20,7 @@ public class Chunk {
* @param x coord
* @param z coord
*/
protected Chunk(int x, int z) {
public Chunk(int x, int z) {
this(x, z, true, 0, new ChunkSection[16], null);
this.unloadPacket = true;
}

View File

@ -92,7 +92,7 @@ public enum PacketType {
PLAY_UNLOAD_CHUNK(State.PLAY, Direction.OUTGOING, -1, 0x1D),
PLAY_CHANGE_GAME_STATE(State.PLAY, Direction.OUTGOING, 0x2B, 0x1E),
PLAY_KEEP_ALIVE(State.PLAY, Direction.OUTGOING, 0x00, 0x1F), // Mapped
PLAY_CHUNK_DATA(State.PLAY, Direction.OUTGOING, 0x21, 0x20), // TODO
PLAY_CHUNK_DATA(State.PLAY, Direction.OUTGOING, 0x21, 0x20), // Mapped
PLAY_EFFECT(State.PLAY, Direction.OUTGOING, 0x28, 0x21), // Mapped
PLAY_PARTICLE(State.PLAY, Direction.OUTGOING, 0x2A, 0x22), // Mapped
PLAY_JOIN_GAME(State.PLAY, Direction.OUTGOING, 0x01, 0x23), // Mapped

View File

@ -45,7 +45,7 @@ public class PacketWrapper {
throw new ArrayIndexOutOfBoundsException("Could not find type " + type.getTypeName() + " at " + index);
}
public <T> T read(Type<T> type) {
public <T> T read(Type<T> type) throws Exception {
System.out.println("Reading: " + type.getTypeName());
// We could in the future log input read values, but honestly for things like bulk maps, mem waste D:
return type.read(inputBuffer);
@ -57,13 +57,13 @@ public class PacketWrapper {
packetValues.add(new Pair<Type, Object>(type, value));
}
public <T> T passthrough(Type<T> type) {
public <T> T passthrough(Type<T> type) throws Exception {
T value = read(type);
write(type, value);
return value;
}
public void writeToBuffer(ByteBuf buffer) {
public void writeToBuffer(ByteBuf buffer) throws Exception {
for (Pair<Type, Object> packetValue : packetValues) {
packetValue.getKey().write(buffer, packetValue.getValue());
}

View File

@ -1,4 +1,14 @@
package us.myles.ViaVersion2.api.item;
import lombok.Getter;
import lombok.Setter;
import org.spacehq.opennbt.tag.builtin.CompoundTag;
@Getter
@Setter
public class Item {
private short id;
private byte amount;
private short data;
private CompoundTag tag;
}

View File

@ -47,7 +47,7 @@ public abstract class Protocol {
outgoing.put(new Pair<>(state, oldPacketID), protocolPacket);
}
public void transform(Direction direction, State state, int packetID, PacketWrapper packetWrapper, ByteBuf output) {
public void transform(Direction direction, State state, int packetID, PacketWrapper packetWrapper, ByteBuf output) throws Exception {
Pair<State, Integer> statePacket = new Pair<>(state, packetID);
Map<Pair<State, Integer>, ProtocolPacket> packetMap = (direction == Direction.OUTGOING ? outgoing : incoming);
ProtocolPacket protocolPacket;

View File

@ -7,6 +7,7 @@ import us.myles.ViaVersion2.api.data.UserConnection;
import us.myles.ViaVersion2.api.metadata.Metadata;
import us.myles.ViaVersion2.api.protocol.Protocol;
import us.myles.ViaVersion2.api.protocol1_9to1_8.packets.*;
import us.myles.ViaVersion2.api.protocol1_9to1_8.storage.ClientChunks;
import us.myles.ViaVersion2.api.protocol1_9to1_8.storage.EntityTracker;
import us.myles.ViaVersion2.api.protocol1_9to1_8.types.MetadataListType;
import us.myles.ViaVersion2.api.protocol1_9to1_8.types.MetadataType;
@ -57,5 +58,7 @@ public class Protocol1_9TO1_8 extends Protocol {
public void init(UserConnection userConnection) {
// Entity tracker
userConnection.put(new EntityTracker());
// Chunk tracker
userConnection.put(new ClientChunks());
}
}

View File

@ -174,7 +174,7 @@ public class EntityPackets {
map(Type.VAR_INT); // 1 - Action Type
handler(new PacketHandler() {
@Override
public void handle(PacketWrapper wrapper) {
public void handle(PacketWrapper wrapper) throws Exception {
int type = wrapper.get(Type.VAR_INT, 1);
if (type == 2) {
wrapper.passthrough(Type.FLOAT); // 2 - X

View File

@ -49,7 +49,7 @@ public class PlayerPackets {
// We only handle if the title or subtitle is set then just write through.
handler(new PacketHandler() {
@Override
public void handle(PacketWrapper wrapper) {
public void handle(PacketWrapper wrapper) throws Exception {
int action = wrapper.get(Type.VAR_INT, 0);
if (action == 0 || action == 1) {
Protocol1_9TO1_8.FIX_JSON.write(wrapper, wrapper.read(Type.STRING));
@ -90,7 +90,7 @@ public class PlayerPackets {
map(Type.BYTE);
handler(new PacketHandler() {
@Override
public void handle(PacketWrapper wrapper) {
public void handle(PacketWrapper wrapper) throws Exception {
byte mode = wrapper.get(Type.BYTE, 1);
if (mode == 0 || mode == 2) {
wrapper.passthrough(Type.STRING);
@ -152,7 +152,7 @@ public class PlayerPackets {
handler(new PacketHandler() {
@Override
public void handle(PacketWrapper wrapper) {
public void handle(PacketWrapper wrapper) throws Exception {
int action = wrapper.get(Type.VAR_INT, 0);
int count = wrapper.get(Type.VAR_INT, 1);

View File

@ -61,7 +61,7 @@ public class SpawnPackets {
// Create last 3 shorts
create(new ValueCreator() {
@Override
public void write(PacketWrapper wrapper) {
public void write(PacketWrapper wrapper) throws Exception {
int data = wrapper.get(Type.INT, 3); // Data (4th Integer)
short vX = 0, vY = 0, vZ = 0;

View File

@ -1,8 +1,12 @@
package us.myles.ViaVersion2.api.protocol1_9to1_8.packets;
import us.myles.ViaVersion.packets.State;
import us.myles.ViaVersion2.api.PacketWrapper;
import us.myles.ViaVersion2.api.protocol.Protocol;
import us.myles.ViaVersion2.api.protocol1_9to1_8.Protocol1_9TO1_8;
import us.myles.ViaVersion2.api.protocol1_9to1_8.storage.ClientChunks;
import us.myles.ViaVersion2.api.protocol1_9to1_8.types.ChunkType;
import us.myles.ViaVersion2.api.remapper.PacketHandler;
import us.myles.ViaVersion2.api.remapper.PacketRemapper;
import us.myles.ViaVersion2.api.type.Type;
@ -43,6 +47,20 @@ public class WorldPackets {
}
});
// Chunk Packet
protocol.registerOutgoing(State.PLAY, 0x21, 0x20, new PacketRemapper() {
@Override
public void registerMap() {
handler(new PacketHandler() {
@Override
public void handle(PacketWrapper wrapper) throws Exception{
ClientChunks clientChunks = wrapper.user().get(ClientChunks.class);
wrapper.passthrough(new ChunkType(clientChunks));
}
});
}
});
/* Packets which do not have any field remapping or handlers */
protocol.registerOutgoing(State.PLAY, 0x25, 0x08); // Block Break Animation Packet
@ -58,8 +76,6 @@ public class WorldPackets {
protocol.registerOutgoing(State.PLAY, 0x03, 0x44); // Update Time Packet
protocol.registerOutgoing(State.PLAY, 0x44, 0x35); // World Border Packet
// TODO: Chunk Data, Bulk Chunk :)
/* Incoming Packets */
// Sign Update Request Packet

View File

@ -0,0 +1,13 @@
package us.myles.ViaVersion2.api.protocol1_9to1_8.storage;
import com.google.common.collect.Sets;
import lombok.Getter;
import us.myles.ViaVersion2.api.data.StoredObject;
import java.util.Set;
@Getter
public class ClientChunks extends StoredObject {
private final Set<Long> loadedChunks = Sets.newConcurrentHashSet();
private final Set<Long> bulkChunks = Sets.newConcurrentHashSet();
}

View File

@ -0,0 +1,162 @@
package us.myles.ViaVersion2.api.protocol1_9to1_8.types;
import io.netty.buffer.ByteBuf;
import io.netty.buffer.Unpooled;
import org.bukkit.Bukkit;
import us.myles.ViaVersion.chunks.Chunk;
import us.myles.ViaVersion.chunks.ChunkSection;
import us.myles.ViaVersion.util.PacketUtil;
import us.myles.ViaVersion2.api.protocol1_9to1_8.storage.ClientChunks;
import us.myles.ViaVersion2.api.type.PartialType;
import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.nio.ShortBuffer;
import java.util.BitSet;
import java.util.logging.Level;
public class ChunkType extends PartialType<Chunk, ClientChunks> {
/**
* Amount of sections in a chunk.
*/
private static final int SECTION_COUNT = 16;
/**
* size of each chunk section (16x16x16).
*/
private static final int SECTION_SIZE = 16;
/**
* Length of biome data.
*/
private static final int BIOME_DATA_LENGTH = 256;
public ChunkType(ClientChunks chunks) {
super(chunks, Chunk.class);
}
@Override
public Chunk read(ByteBuf input, ClientChunks param) {
int chunkX = input.readInt();
int chunkZ = input.readInt();
long chunkHash = toLong(chunkX, chunkZ);
boolean groundUp = input.readByte() != 0;
int bitmask = input.readUnsignedShort();
int dataLength = PacketUtil.readVarInt(input);
// Data to be read
BitSet usedSections = new BitSet(16);
ChunkSection[] sections = new ChunkSection[16];
byte[] biomeData = null;
// Calculate section count from bitmask
for (int i = 0; i < 16; i++) {
if ((bitmask & (1 << i)) != 0) {
usedSections.set(i);
}
}
int sectionCount = usedSections.cardinality(); // the amount of sections set
// If the chunk is from a chunk bulk, it is never an unload packet
// Other wise, if it has no data, it is :)
boolean isBulkPacket = param.getBulkChunks().remove(chunkHash);
if (sectionCount == 0 && groundUp && !isBulkPacket && param.getLoadedChunks().contains(chunkHash)) {
// This is a chunk unload packet
param.getLoadedChunks().remove(chunkHash);
return new Chunk(chunkX, chunkZ);
}
int startIndex = input.readerIndex();
param.getLoadedChunks().add(chunkHash); // mark chunk as loaded
// Read blocks
for (int i = 0; i < SECTION_COUNT; i++) {
if (!usedSections.get(i)) continue; // Section not set
ChunkSection section = new ChunkSection();
sections[i] = section;
// Read block data and convert to short buffer
byte[] blockData = new byte[ChunkSection.SIZE * 2];
input.readBytes(blockData);
ShortBuffer blockBuf = ByteBuffer.wrap(blockData).order(ByteOrder.LITTLE_ENDIAN).asShortBuffer();
for (int j = 0; j < ChunkSection.SIZE; j++) {
int mask = blockBuf.get();
int type = mask >> 4;
int data = mask & 0xF;
section.setBlock(j, type, data);
}
}
// Read block light
for (int i = 0; i < SECTION_COUNT; i++) {
if (!usedSections.get(i)) continue; // Section not set, has no light
byte[] blockLightArray = new byte[ChunkSection.LIGHT_LENGTH];
input.readBytes(blockLightArray);
sections[i].setBlockLight(blockLightArray);
}
// Read sky light
int bytesLeft = dataLength - (input.readerIndex() - startIndex);
if (bytesLeft >= ChunkSection.LIGHT_LENGTH) {
for (int i = 0; i < SECTION_COUNT; i++) {
if (!usedSections.get(i)) continue; // Section not set, has no light
byte[] skyLightArray = new byte[ChunkSection.LIGHT_LENGTH];
input.readBytes(skyLightArray);
sections[i].setSkyLight(skyLightArray);
bytesLeft -= ChunkSection.LIGHT_LENGTH;
}
}
// Read biome data
if (bytesLeft >= BIOME_DATA_LENGTH) {
biomeData = new byte[BIOME_DATA_LENGTH];
input.readBytes(biomeData);
bytesLeft -= BIOME_DATA_LENGTH;
}
// Check remaining bytes
if (bytesLeft > 0) {
Bukkit.getLogger().log(Level.WARNING, bytesLeft + " Bytes left after reading chunk! (" + groundUp + ")");
}
// Return chunk
return new Chunk(chunkX, chunkZ, groundUp, bitmask, sections, biomeData);
}
@Override
public void write(ByteBuf output, ClientChunks param, Chunk chunk) {
if(chunk.isUnloadPacket()) {
output.clear();
PacketUtil.writeVarInt(0x1D, output); // Unload packet ID
}
// Write primary info
output.writeInt(chunk.getX());
output.writeInt(chunk.getZ());
if(chunk.isUnloadPacket()) return;
output.writeByte(chunk.isGroundUp() ? 0x01 : 0x00);
PacketUtil.writeVarInt(chunk.getPrimaryBitmask(), output);
ByteBuf buf = Unpooled.buffer();
for(int i = 0; i < SECTION_COUNT; i++) {
ChunkSection section = chunk.getSections()[i];
if(section == null) continue; // Section not set
section.writeBlocks(buf);
section.writeBlockLight(buf);
if(!section.hasSkyLight()) continue; // No sky light, we're done here.
section.writeSkyLight(buf);
}
buf.readerIndex(0);
PacketUtil.writeVarInt(buf.readableBytes() + (chunk.hasBiomeData() ? 256 : 0), output);
output.writeBytes(buf);
buf.release(); // release buffer
// Write biome data
if(chunk.hasBiomeData()) {
output.writeBytes(chunk.getBiomeData());
}
}
private static long toLong(int msw, int lsw) {
return ((long) msw << 32) + lsw - -2147483648L;
}
}

View File

@ -14,7 +14,7 @@ public class MetadataListType extends Type<List<Metadata>> {
}
@Override
public List<Metadata> read(ByteBuf buffer) {
public List<Metadata> read(ByteBuf buffer) throws Exception {
List<Metadata> list = new ArrayList<>();
Metadata m;
do {
@ -28,8 +28,8 @@ public class MetadataListType extends Type<List<Metadata>> {
}
@Override
public void write(ByteBuf buffer, List<Metadata> object) {
for(Metadata m:object){
public void write(ByteBuf buffer, List<Metadata> object) throws Exception {
for (Metadata m : object) {
Protocol1_9TO1_8.METADATA.write(buffer, m);
}
// Write end of list

View File

@ -13,7 +13,7 @@ public class MetadataType extends Type<Metadata> {
}
@Override
public Metadata read(ByteBuf buffer) {
public Metadata read(ByteBuf buffer) throws Exception {
byte item = buffer.readByte();
if (item == 127) return null; // end of metadata
MetadataTypes type = MetadataTypes.byId((item & 0xE0) >> 5);
@ -22,7 +22,7 @@ public class MetadataType extends Type<Metadata> {
}
@Override
public void write(ByteBuf buffer, Metadata object) {
public void write(ByteBuf buffer, Metadata object) throws Exception {
if (object == null) {
buffer.writeByte(127);
} else {

View File

@ -3,10 +3,10 @@ package us.myles.ViaVersion2.api.remapper;
import us.myles.ViaVersion2.api.PacketWrapper;
public abstract class PacketHandler implements ValueWriter {
public abstract void handle(PacketWrapper wrapper);
public abstract void handle(PacketWrapper wrapper) throws Exception;
@Override
public void write(PacketWrapper writer, Object inputValue) {
public void write(PacketWrapper writer, Object inputValue) throws Exception {
handle(writer);
}
}

View File

@ -41,7 +41,7 @@ public abstract class PacketRemapper {
public abstract void registerMap();
public void remap(PacketWrapper packetWrapper) {
public void remap(PacketWrapper packetWrapper) throws Exception{
// Read all the current values
for (Pair<ValueReader, ValueWriter> valueRemapper : valueRemappers) {
Object object = valueRemapper.getKey().read(packetWrapper);

View File

@ -11,7 +11,7 @@ public class TypeRemapper<T> implements ValueReader<T>, ValueWriter<T> {
}
@Override
public T read(PacketWrapper wrapper) {
public T read(PacketWrapper wrapper) throws Exception {
return wrapper.read(type);
}

View File

@ -3,10 +3,10 @@ package us.myles.ViaVersion2.api.remapper;
import us.myles.ViaVersion2.api.PacketWrapper;
public abstract class ValueCreator implements ValueWriter {
public abstract void write(PacketWrapper wrapper);
public abstract void write(PacketWrapper wrapper) throws Exception;
@Override
public void write(PacketWrapper writer, Object inputValue) {
public void write(PacketWrapper writer, Object inputValue) throws Exception {
write(writer);
}
}

View File

@ -4,5 +4,5 @@ import io.netty.buffer.ByteBuf;
import us.myles.ViaVersion2.api.PacketWrapper;
public interface ValueReader<T> {
public T read(PacketWrapper wrapper);
public T read(PacketWrapper wrapper) throws Exception;
}

View File

@ -3,5 +3,5 @@ package us.myles.ViaVersion2.api.remapper;
import us.myles.ViaVersion2.api.PacketWrapper;
public interface ValueWriter<T> {
public void write(PacketWrapper writer, T inputValue);
public void write(PacketWrapper writer, T inputValue) throws Exception;
}

View File

@ -3,5 +3,5 @@ package us.myles.ViaVersion2.api.type;
import io.netty.buffer.ByteBuf;
public interface ByteBufReader<T> {
public T read(ByteBuf buffer);
public T read(ByteBuf buffer) throws Exception;
}

View File

@ -3,5 +3,5 @@ package us.myles.ViaVersion2.api.type;
import io.netty.buffer.ByteBuf;
public interface ByteBufWriter<T> {
public void write(ByteBuf buffer, T object);
public void write(ByteBuf buffer, T object) throws Exception;
}

View File

@ -0,0 +1,26 @@
package us.myles.ViaVersion2.api.type;
import io.netty.buffer.ByteBuf;
public abstract class PartialType<T, X> extends Type<T> {
private final X param;
public PartialType(X param, Class<T> type) {
super(type);
this.param = param;
}
public abstract T read(ByteBuf buffer, X param);
public abstract void write(ByteBuf buffer, X param, T object);
@Override
public T read(ByteBuf buffer) {
return read(buffer, this.param);
}
@Override
public void write(ByteBuf buffer, T object) {
write(buffer, this.param, object);
}
}

View File

@ -4,6 +4,7 @@ package us.myles.ViaVersion2.api.type;
import lombok.Getter;
import org.bukkit.util.EulerAngle;
import org.bukkit.util.Vector;
import org.spacehq.opennbt.tag.builtin.CompoundTag;
import us.myles.ViaVersion2.api.item.Item;
import us.myles.ViaVersion2.api.type.types.*;
import us.myles.ViaVersion2.api.type.types.minecraft.*;
@ -57,7 +58,9 @@ public abstract class Type<T> implements ByteBufReader<T>, ByteBufWriter<T> {
public static final Type<Position> POSITION = new PositionType();
public static final Type<EulerAngle> ROTATION = new EulerAngleType();
public static final Type<Vector> VECTOR = new VectorType();
public static final Type<Item> ITEM = new ItemType(); // TODO
public static final Type<CompoundTag> NBT = new NBTType();
public static final Type<Item> ITEM = new ItemType();
public static final Type<Item[]> ITEM_ARRAY = new ItemArrayType();
/* Actual Class */

View File

@ -12,7 +12,7 @@ public class ArrayType<T> extends Type<T[]> {
}
@Override
public T[] read(ByteBuf buffer) {
public T[] read(ByteBuf buffer) throws Exception{
int amount = Type.VAR_INT.read(buffer);
Object[] array = new Object[amount];
for (int i = 0; i < amount; i++) {
@ -22,7 +22,7 @@ public class ArrayType<T> extends Type<T[]> {
}
@Override
public void write(ByteBuf buffer, T[] object) {
public void write(ByteBuf buffer, T[] object) throws Exception{
Type.VAR_INT.write(buffer, object.length);
for (T o : object) {
elementType.write(buffer, o);

View File

@ -11,7 +11,7 @@ public class StringType extends Type<String> {
}
@Override
public String read(ByteBuf buffer) {
public String read(ByteBuf buffer) throws Exception {
int len = Type.VAR_INT.read(buffer);
Preconditions.checkArgument(len <= Short.MAX_VALUE, "Cannot receive string longer than Short.MAX_VALUE (got %s characters)", len);
@ -22,7 +22,7 @@ public class StringType extends Type<String> {
}
@Override
public void write(ByteBuf buffer, String object) {
public void write(ByteBuf buffer, String object) throws Exception {
Preconditions.checkArgument(object.length() <= Short.MAX_VALUE, "Cannot send string longer than Short.MAX_VALUE (got %s characters)", object.length());
byte[] b = object.getBytes(Charsets.UTF_8);

View File

@ -11,7 +11,7 @@ public class EulerAngleType extends Type<EulerAngle> {
}
@Override
public EulerAngle read(ByteBuf buffer) {
public EulerAngle read(ByteBuf buffer) throws Exception {
float x = Type.FLOAT.read(buffer);
float y = Type.FLOAT.read(buffer);
float z = Type.FLOAT.read(buffer);
@ -20,7 +20,7 @@ public class EulerAngleType extends Type<EulerAngle> {
}
@Override
public void write(ByteBuf buffer, EulerAngle object) {
public void write(ByteBuf buffer, EulerAngle object) throws Exception {
Type.FLOAT.write(buffer, (float) object.getX());
Type.FLOAT.write(buffer, (float) object.getY());
Type.FLOAT.write(buffer, (float) object.getZ());

View File

@ -11,7 +11,7 @@ public class ItemArrayType extends Type<Item[]> {
}
@Override
public Item[] read(ByteBuf buffer) {
public Item[] read(ByteBuf buffer) throws Exception {
int amount = Type.SHORT.read(buffer);
Item[] array = new Item[amount];
for (int i = 0; i < amount; i++) {
@ -21,7 +21,7 @@ public class ItemArrayType extends Type<Item[]> {
}
@Override
public void write(ByteBuf buffer, Item[] object) {
public void write(ByteBuf buffer, Item[] object) throws Exception {
Type.VAR_INT.write(buffer, object.length);
for (Item o : object) {
Type.ITEM.write(buffer, o);

View File

@ -4,19 +4,35 @@ import io.netty.buffer.ByteBuf;
import us.myles.ViaVersion2.api.item.Item;
import us.myles.ViaVersion2.api.type.Type;
// TODO: Implement this class
public class ItemType extends Type<Item> {
public ItemType() {
super(Item.class);
}
@Override
public Item read(ByteBuf buffer) {
return null;
public Item read(ByteBuf buffer) throws Exception {
short id = buffer.readShort();
if (id < 0) {
return null;
} else {
Item item = new Item();
item.setId(id);
item.setAmount(buffer.readByte());
item.setData(buffer.readShort());
item.setTag(Type.NBT.read(buffer));
return item;
}
}
@Override
public void write(ByteBuf buffer, Item object) {
public void write(ByteBuf buffer, Item object) throws Exception {
if (object == null) {
buffer.writeShort(-1);
} else {
buffer.writeShort(object.getId());
buffer.writeByte(object.getAmount());
buffer.writeShort(object.getData());
Type.NBT.write(buffer, object.getTag());
}
}
}

View File

@ -0,0 +1,52 @@
package us.myles.ViaVersion2.api.type.types.minecraft;
import com.google.common.base.Preconditions;
import io.netty.buffer.ByteBuf;
import io.netty.buffer.ByteBufInputStream;
import io.netty.buffer.ByteBufOutputStream;
import org.spacehq.opennbt.NBTIO;
import org.spacehq.opennbt.tag.builtin.CompoundTag;
import us.myles.ViaVersion2.api.type.Type;
import java.io.DataInputStream;
import java.io.DataOutputStream;
public class NBTType extends Type<CompoundTag> {
public NBTType() {
super(CompoundTag.class);
}
@Override
public CompoundTag read(ByteBuf buffer) throws Exception {
Preconditions.checkArgument(buffer.readableBytes() <= 2097152, "Cannot read NBT (got %s bytes)", buffer.readableBytes());
int readerIndex = buffer.readerIndex();
byte b = buffer.readByte();
if (b == 0) {
return null;
} else {
buffer.readerIndex(readerIndex);
ByteBufInputStream bytebufStream = new ByteBufInputStream(buffer);
DataInputStream dataInputStream = new DataInputStream(bytebufStream);
try {
return (CompoundTag) NBTIO.readTag(dataInputStream);
} finally {
dataInputStream.close();
}
}
}
@Override
public void write(ByteBuf buffer, CompoundTag object) throws Exception {
if (object == null) {
buffer.writeByte(0);
} else {
ByteBufOutputStream bytebufStream = new ByteBufOutputStream(buffer);
DataOutputStream dataOutputStream = new DataOutputStream(bytebufStream);
NBTIO.writeTag(dataOutputStream, object);
dataOutputStream.close();
}
}
}

View File

@ -10,7 +10,7 @@ public class VectorType extends Type<Vector> {
}
@Override
public Vector read(ByteBuf buffer) {
public Vector read(ByteBuf buffer) throws Exception {
int x = Type.INT.read(buffer);
int y = Type.INT.read(buffer);
int z = Type.INT.read(buffer);
@ -19,7 +19,7 @@ public class VectorType extends Type<Vector> {
}
@Override
public void write(ByteBuf buffer, Vector object) {
public void write(ByteBuf buffer, Vector object) throws Exception {
Type.INT.write(buffer, object.getBlockX());
Type.INT.write(buffer, object.getBlockY());
Type.INT.write(buffer, object.getBlockZ());