From 10d5163ef543d4cb60c6f2b4be8247075434b7ad Mon Sep 17 00:00:00 2001 From: "Kristian S. Stangeland" Date: Wed, 9 Jan 2013 14:45:00 +0100 Subject: [PATCH] Added the ability to save int arrays in configurations. --- .../nbt/io/NbtConfigurationSerializer.java | 56 +++++++++++++++++-- .../io/NbtConfigurationSerializerTest.java | 1 + 2 files changed, 52 insertions(+), 5 deletions(-) diff --git a/ProtocolLib/src/main/java/com/comphenix/protocol/wrappers/nbt/io/NbtConfigurationSerializer.java b/ProtocolLib/src/main/java/com/comphenix/protocol/wrappers/nbt/io/NbtConfigurationSerializer.java index acdf3271..7ddc9f1c 100644 --- a/ProtocolLib/src/main/java/com/comphenix/protocol/wrappers/nbt/io/NbtConfigurationSerializer.java +++ b/ProtocolLib/src/main/java/com/comphenix/protocol/wrappers/nbt/io/NbtConfigurationSerializer.java @@ -1,5 +1,7 @@ package com.comphenix.protocol.wrappers.nbt.io; +import java.nio.ByteBuffer; +import java.nio.IntBuffer; import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; @@ -129,10 +131,10 @@ public class NbtConfigurationSerializer { String name = getEncodedName(node, listIndex); // Save member - current.set(name, node.getValue()); + current.set(name, fromNodeValue(node)); } else { - currentList.add(node.getValue()); + currentList.add(fromNodeValue(node)); } return true; } @@ -261,7 +263,7 @@ public class NbtConfigurationSerializer { list.setElementType(type); for (Object value : (List) node) { - list.addClosest(value); + list.addClosest(toNodeValue(value, type)); } // Add the list @@ -269,7 +271,7 @@ public class NbtConfigurationSerializer { } else { // Normal node - return NbtFactory.ofWrapper(type, decoded[0], node); + return NbtFactory.ofWrapper(type, decoded[0], toNodeValue(node, type)); } } } @@ -290,7 +292,51 @@ public class NbtConfigurationSerializer { return sorted; } - private String[] getDecodedName(String nodeName) { + // Ensure that int arrays are converted to byte arrays + private Object fromNodeValue(NbtBase base) { + if (base.getType() == NbtType.TAG_INT_ARRAY) + return toByteArray((int[]) base.getValue()); + else + return base.getValue(); + } + + // Convert them back + public Object toNodeValue(Object value, NbtType type) { + if (type == NbtType.TAG_INT_ARRAY) + return toIntegerArray((byte[]) value); + else + return value; + } + + /** + * Convert an integer array to an equivalent byte array. + * @param data - the integer array with the data. + * @return An equivalent byte array. + */ + private static byte[] toByteArray(int[] data) { + ByteBuffer byteBuffer = ByteBuffer.allocate(data.length * 4); + IntBuffer intBuffer = byteBuffer.asIntBuffer(); + + intBuffer.put(data); + return byteBuffer.array(); + } + + /** + * Convert a byte array to the equivalent integer array. + *

+ * Note that the number of byte elements are only perserved if the byte size is a multiple of four. + * @param data - the byte array to convert. + * @return The equivalent integer array. + */ + private static int[] toIntegerArray(byte[] data) { + IntBuffer source = ByteBuffer.wrap(data).asIntBuffer(); + IntBuffer copy = IntBuffer.allocate(source.capacity()); + + copy.put(source); + return copy.array(); + } + + private static String[] getDecodedName(String nodeName) { int delimiter = nodeName.lastIndexOf('$'); if (delimiter > 0) diff --git a/ProtocolLib/src/test/java/com/comphenix/protocol/wrappers/nbt/io/NbtConfigurationSerializerTest.java b/ProtocolLib/src/test/java/com/comphenix/protocol/wrappers/nbt/io/NbtConfigurationSerializerTest.java index 3b3888a3..916875ab 100644 --- a/ProtocolLib/src/test/java/com/comphenix/protocol/wrappers/nbt/io/NbtConfigurationSerializerTest.java +++ b/ProtocolLib/src/test/java/com/comphenix/protocol/wrappers/nbt/io/NbtConfigurationSerializerTest.java @@ -23,6 +23,7 @@ public class NbtConfigurationSerializerTest { NbtCompound compound = NbtFactory.ofCompound("hello"); compound.put("age", (short) 30); compound.put("name", "test"); + compound.put("values", new int[] { 1, 2, 3}); compound.put(NbtFactory.ofList("telephone", "12345678", "81549300")); compound.put(NbtFactory.ofList("lists", NbtFactory.ofList("", "a", "a", "b", "c")));