From dd5454d7fa0e1834a85b3ae515bb1bda07883624 Mon Sep 17 00:00:00 2001 From: SBPrime Date: Mon, 17 Apr 2017 19:34:47 +0200 Subject: [PATCH] Add support for API 1.11R1 --- ChestDrop/nbproject/project.properties | 4 +- .../utils/adapter/UtilsAdapters.java | 7 + .../adapter/v1_11_R1/Spigot_v1_11_R1.java | 336 ++++++++++++++++++ 3 files changed, 346 insertions(+), 1 deletion(-) create mode 100644 ChestDrop/src/org/primesoft/utils/adapter/v1_11_R1/Spigot_v1_11_R1.java diff --git a/ChestDrop/nbproject/project.properties b/ChestDrop/nbproject/project.properties index 47a7de5..20247b9 100644 --- a/ChestDrop/nbproject/project.properties +++ b/ChestDrop/nbproject/project.properties @@ -31,6 +31,7 @@ endorsed.classpath= excludes= file.reference.spigot-1.8.8.jar=lib/spigot-1.8.8.jar file.reference.Spigot_v1_10_R1.jar=lib/Spigot_v1_10_R1.jar +file.reference.Spigot_v1_11_R1.jar=lib/Spigot_v1_11_R1.jar file.reference.Spigot_v1_8_R3.jar=lib/Spigot_v1_8_R3.jar file.reference.Spigot_v1_9_R1.jar=lib/Spigot_v1_9_R1.jar file.reference.Spigot_v1_9_R2.jar=lib/Spigot_v1_9_R2.jar @@ -41,7 +42,8 @@ javac.classpath=\ ${file.reference.Spigot_v1_8_R3.jar}:\ ${file.reference.Spigot_v1_10_R1.jar}:\ ${file.reference.Spigot_v1_9_R1.jar}:\ - ${file.reference.Spigot_v1_9_R2.jar} + ${file.reference.Spigot_v1_9_R2.jar}:\ + ${file.reference.Spigot_v1_11_R1.jar} # Space-separated list of extra javac options javac.compilerargs= javac.deprecation=false diff --git a/ChestDrop/src/org/primesoft/utils/adapter/UtilsAdapters.java b/ChestDrop/src/org/primesoft/utils/adapter/UtilsAdapters.java index 5fc03dd..81983a7 100644 --- a/ChestDrop/src/org/primesoft/utils/adapter/UtilsAdapters.java +++ b/ChestDrop/src/org/primesoft/utils/adapter/UtilsAdapters.java @@ -43,6 +43,7 @@ import org.primesoft.utils.adapter.v1_8_R3.Spigot_v1_8_R3; import org.primesoft.utils.Func; import org.primesoft.utils.adapter.v1_10_R1.Spigot_v1_10_R1; +import org.primesoft.utils.adapter.v1_11_R1.Spigot_v1_11_R1; import org.primesoft.utils.adapter.v1_9_R1.Spigot_v1_9_R1; import org.primesoft.utils.adapter.v1_9_R2.Spigot_v1_9_R2; @@ -76,6 +77,12 @@ public IUtilsAdapter execute() { public IUtilsAdapter execute() { return Spigot_v1_10_R1.getInstance(); } + }), + v1_11_R1("v1_11_R1", new Func() { + @Override + public IUtilsAdapter execute() { + return Spigot_v1_11_R1.getInstance(); + } }) ; diff --git a/ChestDrop/src/org/primesoft/utils/adapter/v1_11_R1/Spigot_v1_11_R1.java b/ChestDrop/src/org/primesoft/utils/adapter/v1_11_R1/Spigot_v1_11_R1.java new file mode 100644 index 0000000..79cc9ab --- /dev/null +++ b/ChestDrop/src/org/primesoft/utils/adapter/v1_11_R1/Spigot_v1_11_R1.java @@ -0,0 +1,336 @@ +/* + * SBPrime plugin utils + * Copyright (c) 2017, SBPrime + * + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted free of charge provided that the following + * conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution, + * 3. Redistributions of source code, with or without modification, in any form + * other then free of charge is not allowed, + * 4. Redistributions in binary form in any form other then free of charge is + * not allowed. + * 5. Usage in closed source projects is not allowed + * 6. Any derived work based on or containing parts of this software must reproduce + * the above copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided with the + * derived work. + * 7. The original author of the software is allowed to change the license + * terms or the entire license of the software as he sees fit. + * 8. The original author of the software is allowed to sublicense the software + * or its parts using any license terms he sees fit. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR + * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +package org.primesoft.utils.adapter.v1_11_R1; + +import java.lang.reflect.Constructor; +import java.lang.reflect.Field; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import net.minecraft.server.v1_11_R1.ItemStack; +import net.minecraft.server.v1_11_R1.NBTBase; +import net.minecraft.server.v1_11_R1.NBTTagByte; +import net.minecraft.server.v1_11_R1.NBTTagByteArray; +import net.minecraft.server.v1_11_R1.NBTTagCompound; +import net.minecraft.server.v1_11_R1.NBTTagDouble; +import net.minecraft.server.v1_11_R1.NBTTagEnd; +import net.minecraft.server.v1_11_R1.NBTTagFloat; +import net.minecraft.server.v1_11_R1.NBTTagInt; +import net.minecraft.server.v1_11_R1.NBTTagIntArray; +import net.minecraft.server.v1_11_R1.NBTTagList; +import net.minecraft.server.v1_11_R1.NBTTagLong; +import net.minecraft.server.v1_11_R1.NBTTagShort; +import net.minecraft.server.v1_11_R1.NBTTagString; +import org.bukkit.craftbukkit.v1_11_R1.inventory.CraftItemStack; +import static org.primesoft.chestDrop.ChestDropMain.log; +import org.primesoft.utils.adapter.IUtilsAdapter; +import org.primesoft.utils.nbt.TagBase; +import org.primesoft.utils.nbt.TagArrayByte; +import org.primesoft.utils.nbt.TagArrayInt; +import org.primesoft.utils.nbt.TagByte; +import org.primesoft.utils.nbt.TagCompound; +import org.primesoft.utils.nbt.TagDouble; +import org.primesoft.utils.nbt.TagEnd; +import org.primesoft.utils.nbt.TagFloat; +import org.primesoft.utils.nbt.TagInt; +import org.primesoft.utils.nbt.TagList; +import org.primesoft.utils.nbt.TagLong; +import org.primesoft.utils.nbt.TagShort; +import org.primesoft.utils.nbt.TagString; +import org.primesoft.utils.nbt.TagType; +import org.primesoft.utils.Reflection; + +/** + * + * @author SBPrime + */ +public class Spigot_v1_11_R1 implements IUtilsAdapter { + + private static final IUtilsAdapter s_instance = new Spigot_v1_11_R1(); + + private static final Constructor s_tagEnd; + private static final Field s_itemStackHandle; + private static final boolean s_isInitialised; + + static { + s_itemStackHandle = Reflection.findTypedField(CraftItemStack.class, ItemStack.class, "handle", "Unable to get native handle from ItemStack"); + s_tagEnd = (Constructor) Reflection.findConstructor(NBTTagEnd.class, "Unable to get NBTTagEnd constructor"); + + + s_isInitialised = s_itemStackHandle != null && s_tagEnd != null; + } + + public static IUtilsAdapter getInstance() { + return s_instance; + } + + @Override + public TagBase getNbt(org.bukkit.inventory.ItemStack itemStack) { + CraftItemStack cItemStack = itemStack instanceof CraftItemStack ? (CraftItemStack) itemStack : null; + + if (cItemStack == null || !s_isInitialised) { + return null; + } + + ItemStack nStack = Reflection.get(cItemStack, ItemStack.class, s_itemStackHandle, "Unable to get ItemStack"); + + if (nStack == null) { + return null; + } + + NBTTagCompound nTag = nStack.getTag(); + return fromNative(nTag); + } + + + @Override + public org.bukkit.inventory.ItemStack setNbt(org.bukkit.inventory.ItemStack itemStack, TagBase nbt) { + if (!s_isInitialised || itemStack == null) { + return itemStack; + } + + + ItemStack nStack = CraftItemStack.asNMSCopy(itemStack); + + if (nStack == null) { + return itemStack; + } + + NBTBase nTag = nbt != null ? toNative(nbt) : null; + nStack.setTag(nTag instanceof NBTTagCompound ? (NBTTagCompound) nTag : null); + + return CraftItemStack.asBukkitCopy(nStack); + } + + /** + * Convert native NBT to internal NBT + * + * @param nTag + * @return + */ + private TagBase fromNative(NBTBase nbt) { + if (nbt == null || !s_isInitialised) { + return null; + } + + /** + * Convert the complex tag + */ + if ((nbt instanceof NBTTagCompound)) { + TagCompound tc = new TagCompound(); + HashMap childTags = tc.Tags(); + for (String key : ((NBTTagCompound) nbt).c()) { + TagBase subTag = fromNative(((NBTTagCompound) nbt).get(key)); + if (subTag != null) { + childTags.put(key, subTag); + } + } + return tc; + } + + /** + * Convert primitives + */ + if ((nbt instanceof NBTTagByte)) { + return new TagByte(((NBTTagByte) nbt).g()); + } + if ((nbt instanceof NBTTagShort)) { + return new TagShort(((NBTTagShort) nbt).f()); + } + if ((nbt instanceof NBTTagInt)) { + return new TagInt(((NBTTagInt) nbt).e()); + } + if ((nbt instanceof NBTTagLong)) { + return new TagLong(((NBTTagLong) nbt).d()); + } + if ((nbt instanceof NBTTagFloat)) { + return new TagFloat(((NBTTagFloat) nbt).i()); + } + if ((nbt instanceof NBTTagDouble)) { + return new TagDouble(((NBTTagDouble) nbt).asDouble()); + } + if ((nbt instanceof NBTTagString)) { + return new TagString(((NBTTagString) nbt).c_()); + } + + /** + * Convert arrays + */ + if ((nbt instanceof NBTTagByteArray)) { + return new TagArrayByte(((NBTTagByteArray) nbt).c()); + } + + if ((nbt instanceof NBTTagIntArray)) { + return new TagArrayInt(((NBTTagIntArray) nbt).d()); + } + if ((nbt instanceof NBTTagList)) { + NBTTagList nbtList = (NBTTagList) nbt; + List values = new ArrayList(); + TagType type = null; + + for (int idx = 0; idx < nbtList.size(); idx++) { + NBTBase nbtEntry = nbtList.h(idx); + if (nbtEntry instanceof NBTTagEnd) { + continue; + } + + TagBase entry = fromNative(nbtEntry); + + if (entry == null) { + continue; + } + + if (type == null) { + type = entry.getType(); + } else if (type != entry.getType()) { + log(String.format("NBTTagList contains multiple types of NBTTgs. Current: %1$s New: %2$s", + type, entry.getClass().getCanonicalName())); + continue; + } + + values.add(entry); + } + + //Class cls = NBTConstants.getClassFromType(nbtList.f()); + return new TagList(values, type); + } + + if ((nbt instanceof NBTTagEnd)) { + return new TagEnd(); + } + + log(String.format("Unknown NMS %1$s... skipping.", nbt.getClass().getCanonicalName())); + return null; + } + + /** + * Convert built in NBT to native NBT + * + * @param nbt + * @return + */ + private NBTBase toNative(TagBase nbt) { + if (nbt == null || !s_isInitialised) { + return null; + } + + /** + * Convert the complex tag + */ + if ((nbt instanceof TagCompound)) { + NBTTagCompound tc = new NBTTagCompound(); + HashMap childTags = ((TagCompound) nbt).Tags(); + + for (String key : childTags.keySet()) { + NBTBase subTag = toNative(childTags.get(key)); + + if (subTag != null) { + tc.set(key, subTag); + } + } + return tc; + } + + /** + * Convert primitives + */ + if ((nbt instanceof TagByte)) { + return new NBTTagByte(((TagByte) nbt).getValue()); + } + if ((nbt instanceof TagShort)) { + return new NBTTagShort(((TagShort) nbt).getValue()); + } + if ((nbt instanceof TagInt)) { + return new NBTTagInt(((TagInt) nbt).getValue()); + } + if ((nbt instanceof TagLong)) { + return new NBTTagLong(((TagLong) nbt).getValue()); + } + if ((nbt instanceof TagFloat)) { + return new NBTTagFloat(((TagFloat) nbt).getValue()); + } + if ((nbt instanceof TagDouble)) { + return new NBTTagDouble(((TagDouble) nbt).getValue()); + } + if ((nbt instanceof TagString)) { + return new NBTTagString(((TagString) nbt).getValue()); + } + + /** + * Convert arrays + */ + if ((nbt instanceof TagArrayByte)) { + return new NBTTagByteArray(((TagArrayByte) nbt).getValue()); + } + + if ((nbt instanceof TagArrayInt)) { + return new NBTTagIntArray(((TagArrayInt) nbt).getValue()); + } + if ((nbt instanceof TagList)) { + TagList nbtList = (TagList) nbt; + NBTTagList result = new NBTTagList(); + + for (TagBase child : nbtList.getValues()) { + if (child.getType() == TagType.NBT_END) { + continue; + } + + NBTBase entry = toNative(child); + + if (entry == null) { + continue; + } + + result.add(entry); + } + + //Class cls = NBTConstants.getClassFromType(nbtList.f()); + return result; + } + + if ((nbt instanceof TagEnd)) { + return Reflection.create(NBTTagEnd.class, s_tagEnd, "Unable to create NBTTagEnd"); + } + + log(String.format("Unknown NMS %1$s... skipping.", nbt.getClass().getCanonicalName())); + return null; + } +}