From f812c77cc9863d819e5e287df7f941c446cd6375 Mon Sep 17 00:00:00 2001 From: D3v1s0m <49519439+D3v1s0m@users.noreply.github.com> Date: Sun, 2 Jul 2023 10:51:54 +0530 Subject: [PATCH] Added shoulder entities for player npc --- .../lol/pyr/znpcsplus/util/ParrotVariant.java | 10 +++++++ .../java/lol/pyr/znpcsplus/ZNpcsPlus.java | 2 ++ .../commands/property/PropertySetCommand.java | 6 +++++ .../entity/EntityPropertyRegistryImpl.java | 4 +++ .../znpcsplus/entity/ParrotNBTCompound.java | 21 +++++++++++++++ .../znpcsplus/metadata/MetadataFactory.java | 7 ++++- .../metadata/V1_12MetadataFactory.java | 27 +++++++++++++++++++ .../metadata/V1_13MetadataFactory.java | 2 +- .../metadata/V1_14MetadataFactory.java | 11 ++++++++ .../metadata/V1_15MetadataFactory.java | 11 ++++++++ .../metadata/V1_17MetadataFactory.java | 11 ++++++++ .../metadata/V1_8MetadataFactory.java | 11 ++++++++ .../znpcsplus/npc/NpcTypeRegistryImpl.java | 2 +- .../znpcsplus/packets/V1_8PacketFactory.java | 2 ++ 14 files changed, 124 insertions(+), 3 deletions(-) create mode 100644 api/src/main/java/lol/pyr/znpcsplus/util/ParrotVariant.java create mode 100644 plugin/src/main/java/lol/pyr/znpcsplus/entity/ParrotNBTCompound.java create mode 100644 plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_12MetadataFactory.java diff --git a/api/src/main/java/lol/pyr/znpcsplus/util/ParrotVariant.java b/api/src/main/java/lol/pyr/znpcsplus/util/ParrotVariant.java new file mode 100644 index 0000000..5014e03 --- /dev/null +++ b/api/src/main/java/lol/pyr/znpcsplus/util/ParrotVariant.java @@ -0,0 +1,10 @@ +package lol.pyr.znpcsplus.util; + +public enum ParrotVariant { + RED_BLUE, + BLUE, + GREEN, + YELLOW_BLUE, + GRAY, + NONE // only used to set empty nbt compound +} diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/ZNpcsPlus.java b/plugin/src/main/java/lol/pyr/znpcsplus/ZNpcsPlus.java index d0ce041..7df4727 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/ZNpcsPlus.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/ZNpcsPlus.java @@ -242,6 +242,7 @@ public class ZNpcsPlus extends JavaPlugin { versions.put(ServerVersion.V_1_9, LazyLoader.of(V1_9MetadataFactory::new)); versions.put(ServerVersion.V_1_10, LazyLoader.of(V1_10MetadataFactory::new)); versions.put(ServerVersion.V_1_11, LazyLoader.of(V1_11MetadataFactory::new)); + versions.put(ServerVersion.V_1_12, LazyLoader.of(V1_12MetadataFactory::new)); versions.put(ServerVersion.V_1_13, LazyLoader.of(V1_13MetadataFactory::new)); versions.put(ServerVersion.V_1_14, LazyLoader.of(V1_14MetadataFactory::new)); versions.put(ServerVersion.V_1_15, LazyLoader.of(V1_15MetadataFactory::new)); @@ -282,6 +283,7 @@ public class ZNpcsPlus extends JavaPlugin { registerEnumParser(manager, DyeColor.class, incorrectUsageMessage); registerEnumParser(manager, CatVariant.class, incorrectUsageMessage); registerEnumParser(manager, CreeperState.class, incorrectUsageMessage); + registerEnumParser(manager, ParrotVariant.class, incorrectUsageMessage); manager.registerCommand("npc", new MultiCommand(loadHelpMessage("root")) .addSubcommand("create", new CreateCommand(npcRegistry, typeRegistry)) diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/commands/property/PropertySetCommand.java b/plugin/src/main/java/lol/pyr/znpcsplus/commands/property/PropertySetCommand.java index 23f422b..80b7bed 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/commands/property/PropertySetCommand.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/commands/property/PropertySetCommand.java @@ -14,6 +14,7 @@ import lol.pyr.znpcsplus.util.CatVariant; import lol.pyr.znpcsplus.util.CreeperState; import lol.pyr.znpcsplus.util.NpcPose; import lol.pyr.znpcsplus.util.Vector3f; +import lol.pyr.znpcsplus.util.ParrotVariant; import net.kyori.adventure.text.Component; import net.kyori.adventure.text.format.NamedTextColor; import org.bukkit.Color; @@ -60,6 +61,10 @@ public class PropertySetCommand implements CommandHandler { value = Color.BLACK; valueName = "NONE"; } + else if (type == ParrotVariant.class && context.argSize() < 1 && npc.getProperty(property) != null) { + value = ParrotVariant.NONE; + valueName = "NONE"; + } else { value = context.parse(type); valueName = String.valueOf(value); @@ -86,6 +91,7 @@ public class PropertySetCommand implements CommandHandler { if (type == DyeColor.class) return context.suggestEnum(DyeColor.values()); if (type == CatVariant.class) return context.suggestEnum(CatVariant.values()); if (type == CreeperState.class) return context.suggestEnum(CreeperState.values()); + if (type == ParrotVariant.class) return context.suggestEnum(ParrotVariant.values()); } } return Collections.emptyList(); diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/entity/EntityPropertyRegistryImpl.java b/plugin/src/main/java/lol/pyr/znpcsplus/entity/EntityPropertyRegistryImpl.java index f7411cc..38c7544 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/entity/EntityPropertyRegistryImpl.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/entity/EntityPropertyRegistryImpl.java @@ -10,6 +10,7 @@ import lol.pyr.znpcsplus.util.CatVariant; import lol.pyr.znpcsplus.util.CreeperState; import lol.pyr.znpcsplus.util.NpcPose; import lol.pyr.znpcsplus.util.Vector3f; +import lol.pyr.znpcsplus.util.ParrotVariant; import net.kyori.adventure.text.Component; import net.kyori.adventure.text.format.NamedTextColor; import org.bukkit.Color; @@ -39,6 +40,7 @@ public class EntityPropertyRegistryImpl implements EntityPropertyRegistry { registerEnumSerializer(DyeColor.class); registerEnumSerializer(CatVariant.class); registerEnumSerializer(CreeperState.class); + registerEnumSerializer(ParrotVariant.class); registerType("glow", NamedTextColor.class); registerType("fire", false); @@ -72,6 +74,8 @@ public class EntityPropertyRegistryImpl implements EntityPropertyRegistry { registerType("skin_left_leg", true); registerType("skin_right_leg", true); registerType("skin_hat", true); + registerType("shoulder_entity_left", ParrotVariant.NONE); + registerType("shoulder_entity_right", ParrotVariant.NONE); // End Crystal registerType("beam_target", null); // TODO: Make a block pos class for this diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/entity/ParrotNBTCompound.java b/plugin/src/main/java/lol/pyr/znpcsplus/entity/ParrotNBTCompound.java new file mode 100644 index 0000000..13eacf9 --- /dev/null +++ b/plugin/src/main/java/lol/pyr/znpcsplus/entity/ParrotNBTCompound.java @@ -0,0 +1,21 @@ +package lol.pyr.znpcsplus.entity; + +import com.github.retrooper.packetevents.protocol.nbt.NBTCompound; +import com.github.retrooper.packetevents.protocol.nbt.NBTInt; +import com.github.retrooper.packetevents.protocol.nbt.NBTString; +import lol.pyr.znpcsplus.util.ParrotVariant; + +// Not sure where to put this or even if it's needed +public class ParrotNBTCompound { + private final NBTCompound tag = new NBTCompound(); + + public ParrotNBTCompound(ParrotVariant variant) { + tag.setTag("id", new NBTString("minecraft:parrot")); + tag.setTag("Variant", new NBTInt(variant.ordinal())); + // other tags if needed, idk + } + + public NBTCompound getTag() { + return tag; + } +} diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/MetadataFactory.java b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/MetadataFactory.java index 33e03a2..82bf431 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/MetadataFactory.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/MetadataFactory.java @@ -4,6 +4,7 @@ import com.github.retrooper.packetevents.protocol.entity.data.EntityData; import com.github.retrooper.packetevents.protocol.entity.pose.EntityPose; import lol.pyr.znpcsplus.util.CatVariant; import lol.pyr.znpcsplus.util.CreeperState; +import lol.pyr.znpcsplus.util.ParrotVariant; import lol.pyr.znpcsplus.util.Vector3f; import net.kyori.adventure.text.Component; import org.bukkit.DyeColor; @@ -22,7 +23,6 @@ import org.bukkit.DyeColor; * 1.18-1.19 ... */ public interface MetadataFactory { - EntityData skinLayers(boolean cape, boolean jacket, boolean leftSleeve, boolean rightSleeve, boolean leftLeg, boolean rightLeg, boolean hat); EntityData effects(boolean onFire, boolean glowing, boolean invisible, boolean usingElytra, boolean usingItemLegacy); EntityData silent(boolean enabled); EntityData name(Component name); @@ -34,6 +34,11 @@ public interface MetadataFactory { EntityData potionColor(int color); EntityData potionAmbient(boolean ambient); + // Player + EntityData skinLayers(boolean cape, boolean jacket, boolean leftSleeve, boolean rightSleeve, boolean leftLeg, boolean rightLeg, boolean hat); + EntityData shoulderEntityLeft(ParrotVariant variant); + EntityData shoulderEntityRight(ParrotVariant variant); + // Armor Stand EntityData armorStandProperties(boolean small, boolean arms, boolean noBasePlate); EntityData armorStandHeadRotation(Vector3f headRotation); diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_12MetadataFactory.java b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_12MetadataFactory.java new file mode 100644 index 0000000..a60b0fc --- /dev/null +++ b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_12MetadataFactory.java @@ -0,0 +1,27 @@ +package lol.pyr.znpcsplus.metadata; + +import com.github.retrooper.packetevents.protocol.entity.data.EntityData; +import com.github.retrooper.packetevents.protocol.entity.data.EntityDataTypes; +import com.github.retrooper.packetevents.protocol.nbt.NBTCompound; +import lol.pyr.znpcsplus.entity.ParrotNBTCompound; +import lol.pyr.znpcsplus.util.ParrotVariant; + +public class V1_12MetadataFactory extends V1_11MetadataFactory { + @Override + public EntityData shoulderEntityLeft(ParrotVariant variant) { + return createShoulderEntityLeft(15, variant); + } + + public EntityData createShoulderEntityLeft(int index, ParrotVariant variant) { + return newEntityData(index, EntityDataTypes.NBT, variant == ParrotVariant.NONE ? new NBTCompound() : new ParrotNBTCompound(variant).getTag()); + } + + @Override + public EntityData shoulderEntityRight(ParrotVariant variant) { + return createShoulderEntityRight(16, variant); + } + + public EntityData createShoulderEntityRight(int index, ParrotVariant variant) { + return newEntityData(index, EntityDataTypes.NBT, variant == ParrotVariant.NONE ? new NBTCompound() : new ParrotNBTCompound(variant).getTag()); + } +} diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_13MetadataFactory.java b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_13MetadataFactory.java index 10606f0..854549c 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_13MetadataFactory.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_13MetadataFactory.java @@ -7,7 +7,7 @@ import net.kyori.adventure.text.Component; import java.util.Optional; -public class V1_13MetadataFactory extends V1_11MetadataFactory { +public class V1_13MetadataFactory extends V1_12MetadataFactory { @Override public EntityData name(Component name) { return newEntityData(2, EntityDataTypes.OPTIONAL_COMPONENT, Optional.of(AdventureSerializer.getGsonSerializer().serialize(name))); diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_14MetadataFactory.java b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_14MetadataFactory.java index 569b1af..c615182 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_14MetadataFactory.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_14MetadataFactory.java @@ -5,6 +5,7 @@ import com.github.retrooper.packetevents.protocol.entity.data.EntityDataTypes; import com.github.retrooper.packetevents.protocol.entity.pose.EntityPose; import lol.pyr.znpcsplus.util.CatVariant; import lol.pyr.znpcsplus.util.CreeperState; +import lol.pyr.znpcsplus.util.ParrotVariant; import lol.pyr.znpcsplus.util.Vector3f; import org.bukkit.DyeColor; @@ -34,6 +35,16 @@ public class V1_14MetadataFactory extends V1_13MetadataFactory { return newEntityData(10, EntityDataTypes.BOOLEAN, ambient); } + @Override + public EntityData shoulderEntityLeft(ParrotVariant variant) { + return createShoulderEntityLeft(17, variant); + } + + @Override + public EntityData shoulderEntityRight(ParrotVariant variant) { + return createShoulderEntityRight(18, variant); + } + @Override public EntityData armorStandProperties(boolean small, boolean arms, boolean noBasePlate) { return newEntityData(13, EntityDataTypes.BYTE, (byte) ((small ? 0x01 : 0) | (arms ? 0x04 : 0) | (noBasePlate ? 0x08 : 0))); diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_15MetadataFactory.java b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_15MetadataFactory.java index 617044b..411869e 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_15MetadataFactory.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_15MetadataFactory.java @@ -4,10 +4,21 @@ import com.github.retrooper.packetevents.protocol.entity.data.EntityData; import com.github.retrooper.packetevents.protocol.entity.data.EntityDataTypes; import lol.pyr.znpcsplus.util.CatVariant; import lol.pyr.znpcsplus.util.CreeperState; +import lol.pyr.znpcsplus.util.ParrotVariant; import lol.pyr.znpcsplus.util.Vector3f; import org.bukkit.DyeColor; public class V1_15MetadataFactory extends V1_14MetadataFactory { + @Override + public EntityData shoulderEntityLeft(ParrotVariant variant) { + return createShoulderEntityLeft(18, variant); + } + + @Override + public EntityData shoulderEntityRight(ParrotVariant variant) { + return createShoulderEntityRight(19, variant); + } + @Override public EntityData armorStandProperties(boolean small, boolean arms, boolean noBasePlate) { return newEntityData(14, EntityDataTypes.BYTE, (byte) ((small ? 0x01 : 0) | (arms ? 0x04 : 0) | (!noBasePlate ? 0x08 : 0))); diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_17MetadataFactory.java b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_17MetadataFactory.java index 165163e..741dbf2 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_17MetadataFactory.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_17MetadataFactory.java @@ -4,6 +4,7 @@ import com.github.retrooper.packetevents.protocol.entity.data.EntityData; import com.github.retrooper.packetevents.protocol.entity.data.EntityDataTypes; import lol.pyr.znpcsplus.util.CatVariant; import lol.pyr.znpcsplus.util.CreeperState; +import lol.pyr.znpcsplus.util.ParrotVariant; import lol.pyr.znpcsplus.util.Vector3f; import org.bukkit.DyeColor; @@ -38,6 +39,16 @@ public class V1_17MetadataFactory extends V1_16MetadataFactory { return newEntityData(11, EntityDataTypes.BOOLEAN, ambient); } + @Override + public EntityData shoulderEntityLeft(ParrotVariant variant) { + return createShoulderEntityLeft(19, variant); + } + + @Override + public EntityData shoulderEntityRight(ParrotVariant variant) { + return createShoulderEntityRight(20, variant); + } + @Override public EntityData armorStandProperties(boolean small, boolean arms, boolean noBasePlate) { return newEntityData(15, EntityDataTypes.BYTE, (byte) ((small ? 0x01 : 0) | (arms ? 0x04 : 0) | (noBasePlate ? 0x08 : 0))); diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_8MetadataFactory.java b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_8MetadataFactory.java index c6247f9..e5c0e39 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_8MetadataFactory.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/metadata/V1_8MetadataFactory.java @@ -7,6 +7,7 @@ import com.github.retrooper.packetevents.protocol.entity.pose.EntityPose; import com.github.retrooper.packetevents.util.adventure.AdventureSerializer; import lol.pyr.znpcsplus.util.CatVariant; import lol.pyr.znpcsplus.util.CreeperState; +import lol.pyr.znpcsplus.util.ParrotVariant; import lol.pyr.znpcsplus.util.Vector3f; import net.kyori.adventure.text.Component; import org.bukkit.DyeColor; @@ -62,6 +63,16 @@ public class V1_8MetadataFactory implements MetadataFactory { return newEntityData(8, EntityDataTypes.BYTE, (byte) (ambient ? 1 : 0)); } + @Override + public EntityData shoulderEntityLeft(ParrotVariant variant) { + throw new UnsupportedOperationException("The shoulder entity data isn't supported on this version"); + } + + @Override + public EntityData shoulderEntityRight(ParrotVariant variant) { + throw new UnsupportedOperationException("The shoulder entity data isn't supported on this version"); + } + @Override public EntityData armorStandProperties(boolean small, boolean arms, boolean noBasePlate) { return newEntityData(10, EntityDataTypes.BYTE, (byte) ((small ? 0x01 : 0) | (arms ? 0x04 : 0) | (noBasePlate ? 0x08 : 0))); diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/npc/NpcTypeRegistryImpl.java b/plugin/src/main/java/lol/pyr/znpcsplus/npc/NpcTypeRegistryImpl.java index 235ccde..bad1262 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/npc/NpcTypeRegistryImpl.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/npc/NpcTypeRegistryImpl.java @@ -36,7 +36,7 @@ public class NpcTypeRegistryImpl implements NpcTypeRegistry { register(builder(p, "player", EntityTypes.PLAYER) .setHologramOffset(-0.15D) .addEquipmentProperties() - .addProperties("skin_cape", "skin_jacket", "skin_left_sleeve", "skin_right_sleeve", "skin_left_leg", "skin_right_leg", "skin_hat")); + .addProperties("skin_cape", "skin_jacket", "skin_left_sleeve", "skin_right_sleeve", "skin_left_leg", "skin_right_leg", "skin_hat", "shoulder_entity_left", "shoulder_entity_right")); // Most hologram offsets generated using Entity#getHeight() in 1.19.4 diff --git a/plugin/src/main/java/lol/pyr/znpcsplus/packets/V1_8PacketFactory.java b/plugin/src/main/java/lol/pyr/znpcsplus/packets/V1_8PacketFactory.java index 567e1b8..4e8759b 100644 --- a/plugin/src/main/java/lol/pyr/znpcsplus/packets/V1_8PacketFactory.java +++ b/plugin/src/main/java/lol/pyr/znpcsplus/packets/V1_8PacketFactory.java @@ -149,6 +149,8 @@ public class V1_8PacketFactory implements PacketFactory { properties.getProperty(propertyRegistry.getByName("skin_right_leg", Boolean.class)), properties.getProperty(propertyRegistry.getByName("skin_hat", Boolean.class)) )); + add(data, metadataFactory.shoulderEntityLeft(properties.getProperty(propertyRegistry.getByName("shoulder_entity_left", ParrotVariant.class)))); + add(data, metadataFactory.shoulderEntityRight(properties.getProperty(propertyRegistry.getByName("shoulder_entity_right", ParrotVariant.class)))); } else if (entity.getType().equals(EntityTypes.ARMOR_STAND)) { add(data, metadataFactory.armorStandProperties(