diff --git a/eco-core/core-nms/v1_16_R1/src/main/java/com/willfp/eco/proxy/v1_16_R1/VillagerTrade.java b/eco-core/core-nms/v1_16_R1/src/main/java/com/willfp/eco/proxy/v1_16_R1/VillagerTrade.java new file mode 100644 index 00000000..27a66a5e --- /dev/null +++ b/eco-core/core-nms/v1_16_R1/src/main/java/com/willfp/eco/proxy/v1_16_R1/VillagerTrade.java @@ -0,0 +1,40 @@ +package com.willfp.eco.proxy.v1_16_R1; + +import com.willfp.eco.core.display.Display; +import com.willfp.eco.proxy.proxies.VillagerTradeProxy; +import org.bukkit.craftbukkit.v1_16_R1.inventory.CraftItemStack; +import org.bukkit.craftbukkit.v1_16_R1.inventory.CraftMerchantRecipe; +import org.bukkit.inventory.ItemStack; +import org.bukkit.inventory.MerchantRecipe; +import org.jetbrains.annotations.NotNull; + +import java.lang.reflect.Field; + +public final class VillagerTrade implements VillagerTradeProxy { + @Override + public void displayTrade(@NotNull final MerchantRecipe merchantRecipe) { + try { + // Bukkit MerchantRecipe result + Field fResult = MerchantRecipe.class.getDeclaredField("result"); + fResult.setAccessible(true); + ItemStack result = merchantRecipe.getResult().clone(); + Display.display(result); + fResult.set(merchantRecipe, result); + + // Get NMS MerchantRecipe from CraftMerchantRecipe + Field fHandle = CraftMerchantRecipe.class.getDeclaredField("handle"); + fHandle.setAccessible(true); + net.minecraft.server.v1_16_R1.MerchantRecipe handle = (net.minecraft.server.v1_16_R1.MerchantRecipe) fHandle.get(merchantRecipe); // NMS RecipeR + + Field fSelling = net.minecraft.server.v1_16_R1.MerchantRecipe.class.getDeclaredField("sellingItem"); + fSelling.setAccessible(true); + + ItemStack selling = CraftItemStack.asBukkitCopy(handle.sellingItem).clone(); + Display.display(selling); + + fSelling.set(handle, CraftItemStack.asNMSCopy(selling)); + } catch (IllegalAccessException | NoSuchFieldException e) { + e.printStackTrace(); + } + } +} diff --git a/eco-core/core-nms/v1_16_R2/src/main/java/com/willfp/eco/proxy/v1_16_R2/VillagerTrade.java b/eco-core/core-nms/v1_16_R2/src/main/java/com/willfp/eco/proxy/v1_16_R2/VillagerTrade.java new file mode 100644 index 00000000..3cbb338f --- /dev/null +++ b/eco-core/core-nms/v1_16_R2/src/main/java/com/willfp/eco/proxy/v1_16_R2/VillagerTrade.java @@ -0,0 +1,40 @@ +package com.willfp.eco.proxy.v1_16_R2; + +import com.willfp.eco.core.display.Display; +import com.willfp.eco.proxy.proxies.VillagerTradeProxy; +import org.bukkit.craftbukkit.v1_16_R2.inventory.CraftItemStack; +import org.bukkit.craftbukkit.v1_16_R2.inventory.CraftMerchantRecipe; +import org.bukkit.inventory.ItemStack; +import org.bukkit.inventory.MerchantRecipe; +import org.jetbrains.annotations.NotNull; + +import java.lang.reflect.Field; + +public final class VillagerTrade implements VillagerTradeProxy { + @Override + public void displayTrade(@NotNull final MerchantRecipe merchantRecipe) { + try { + // Bukkit MerchantRecipe result + Field fResult = MerchantRecipe.class.getDeclaredField("result"); + fResult.setAccessible(true); + ItemStack result = merchantRecipe.getResult().clone(); + Display.display(result); + fResult.set(merchantRecipe, result); + + // Get NMS MerchantRecipe from CraftMerchantRecipe + Field fHandle = CraftMerchantRecipe.class.getDeclaredField("handle"); + fHandle.setAccessible(true); + net.minecraft.server.v1_16_R2.MerchantRecipe handle = (net.minecraft.server.v1_16_R2.MerchantRecipe) fHandle.get(merchantRecipe); // NMS RecipeR + + Field fSelling = net.minecraft.server.v1_16_R2.MerchantRecipe.class.getDeclaredField("sellingItem"); + fSelling.setAccessible(true); + + ItemStack selling = CraftItemStack.asBukkitCopy(handle.sellingItem).clone(); + Display.display(selling); + + fSelling.set(handle, CraftItemStack.asNMSCopy(selling)); + } catch (IllegalAccessException | NoSuchFieldException e) { + e.printStackTrace(); + } + } +} diff --git a/eco-core/core-nms/v1_16_R3/src/main/java/com/willfp/eco/proxy/v1_16_R3/VillagerTrade.java b/eco-core/core-nms/v1_16_R3/src/main/java/com/willfp/eco/proxy/v1_16_R3/VillagerTrade.java new file mode 100644 index 00000000..c799ee0d --- /dev/null +++ b/eco-core/core-nms/v1_16_R3/src/main/java/com/willfp/eco/proxy/v1_16_R3/VillagerTrade.java @@ -0,0 +1,40 @@ +package com.willfp.eco.proxy.v1_16_R3; + +import com.willfp.eco.core.display.Display; +import com.willfp.eco.proxy.proxies.VillagerTradeProxy; +import org.bukkit.craftbukkit.v1_16_R3.inventory.CraftItemStack; +import org.bukkit.craftbukkit.v1_16_R3.inventory.CraftMerchantRecipe; +import org.bukkit.inventory.ItemStack; +import org.bukkit.inventory.MerchantRecipe; +import org.jetbrains.annotations.NotNull; + +import java.lang.reflect.Field; + +public final class VillagerTrade implements VillagerTradeProxy { + @Override + public void displayTrade(@NotNull final MerchantRecipe merchantRecipe) { + try { + // Bukkit MerchantRecipe result + Field fResult = MerchantRecipe.class.getDeclaredField("result"); + fResult.setAccessible(true); + ItemStack result = merchantRecipe.getResult().clone(); + Display.display(result); + fResult.set(merchantRecipe, result); + + // Get NMS MerchantRecipe from CraftMerchantRecipe + Field fHandle = CraftMerchantRecipe.class.getDeclaredField("handle"); + fHandle.setAccessible(true); + net.minecraft.server.v1_16_R3.MerchantRecipe handle = (net.minecraft.server.v1_16_R3.MerchantRecipe) fHandle.get(merchantRecipe); // NMS RecipeR + + Field fSelling = net.minecraft.server.v1_16_R3.MerchantRecipe.class.getDeclaredField("sellingItem"); + fSelling.setAccessible(true); + + ItemStack selling = CraftItemStack.asBukkitCopy(handle.sellingItem).clone(); + Display.display(selling); + + fSelling.set(handle, CraftItemStack.asNMSCopy(selling)); + } catch (IllegalAccessException | NoSuchFieldException e) { + e.printStackTrace(); + } + } +} diff --git a/eco-core/core-plugin/src/main/java/com/willfp/eco/spigot/display/PacketOpenWindowMerchant.java b/eco-core/core-plugin/src/main/java/com/willfp/eco/spigot/display/PacketOpenWindowMerchant.java index 84a71620..ee1ffda3 100644 --- a/eco-core/core-plugin/src/main/java/com/willfp/eco/spigot/display/PacketOpenWindowMerchant.java +++ b/eco-core/core-plugin/src/main/java/com/willfp/eco/spigot/display/PacketOpenWindowMerchant.java @@ -6,14 +6,14 @@ import com.comphenix.protocol.events.PacketContainer; import com.comphenix.protocol.events.PacketEvent; import com.willfp.eco.core.AbstractPacketAdapter; import com.willfp.eco.core.EcoPlugin; -import com.willfp.eco.core.display.Display; +import com.willfp.eco.proxy.proxies.VillagerTradeProxy; +import com.willfp.eco.spigot.InternalProxyUtils; import org.bukkit.entity.Player; -import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.MerchantRecipe; import org.jetbrains.annotations.NotNull; -import java.util.ArrayList; import java.util.List; +import java.util.stream.Collectors; public class PacketOpenWindowMerchant extends AbstractPacketAdapter { /** @@ -29,24 +29,10 @@ public class PacketOpenWindowMerchant extends AbstractPacketAdapter { public void onSend(@NotNull final PacketContainer packet, @NotNull final Player player, @NotNull final PacketEvent event) { - List recipes = new ArrayList<>(); + List recipes = packet.getMerchantRecipeLists().readSafely(0); - for (MerchantRecipe recipe : packet.getMerchantRecipeLists().read(0)) { - MerchantRecipe newRecipe = new MerchantRecipe( - Display.display(recipe.getResult().clone()), - recipe.getUses(), - recipe.getMaxUses(), - recipe.hasExperienceReward(), - recipe.getVillagerExperience(), - recipe.getPriceMultiplier() - ); + recipes = recipes.stream().peek(merchantRecipe -> InternalProxyUtils.getProxy(VillagerTradeProxy.class).displayTrade(merchantRecipe)).collect(Collectors.toList()); - for (ItemStack ingredient : recipe.getIngredients()) { - newRecipe.addIngredient(Display.display(ingredient.clone())); - } - recipes.add(newRecipe); - } - - packet.getMerchantRecipeLists().write(0, recipes); + packet.getMerchantRecipeLists().writeSafely(0, recipes); } } diff --git a/eco-core/core-proxy/src/main/java/com/willfp/eco/proxy/proxies/VillagerTradeProxy.java b/eco-core/core-proxy/src/main/java/com/willfp/eco/proxy/proxies/VillagerTradeProxy.java new file mode 100644 index 00000000..8a256c6f --- /dev/null +++ b/eco-core/core-proxy/src/main/java/com/willfp/eco/proxy/proxies/VillagerTradeProxy.java @@ -0,0 +1,14 @@ +package com.willfp.eco.proxy.proxies; + +import com.willfp.eco.core.proxy.AbstractProxy; +import org.bukkit.inventory.MerchantRecipe; +import org.jetbrains.annotations.NotNull; + +public interface VillagerTradeProxy extends AbstractProxy { + /** + * Display a MerchantRecipe without creating a new one. + * + * @param recipe The recipe. + */ + void displayTrade(@NotNull MerchantRecipe recipe); +}