diff --git a/src/main/java/net/minestom/server/item/ItemFlag.java b/src/main/java/net/minestom/server/item/ItemHideFlag.java similarity index 66% rename from src/main/java/net/minestom/server/item/ItemFlag.java rename to src/main/java/net/minestom/server/item/ItemHideFlag.java index c4a3d55de..5d05cbb28 100644 --- a/src/main/java/net/minestom/server/item/ItemFlag.java +++ b/src/main/java/net/minestom/server/item/ItemHideFlag.java @@ -1,9 +1,9 @@ package net.minestom.server.item; /** - * Represents a flag which can be applied to an {@link ItemStack} using {@link ItemStack#addItemFlags(ItemFlag...)}. + * Represents a hide flag which can be applied to an {@link ItemStack} using {@link ItemMetaBuilder#hideFlag(int)}. */ -public enum ItemFlag { +public enum ItemHideFlag { HIDE_ENCHANTS(1), HIDE_ATTRIBUTES(2), HIDE_UNBREAKABLE(4), @@ -13,7 +13,7 @@ public enum ItemFlag { private final int bitFieldPart; - ItemFlag(int bit) { + ItemHideFlag(int bit) { this.bitFieldPart = bit; } diff --git a/src/main/java/net/minestom/server/item/ItemMeta.java b/src/main/java/net/minestom/server/item/ItemMeta.java index 189a2be4c..e562da595 100644 --- a/src/main/java/net/minestom/server/item/ItemMeta.java +++ b/src/main/java/net/minestom/server/item/ItemMeta.java @@ -95,6 +95,15 @@ public class ItemMeta { return customModelData; } + @Contract("_, null -> null; _, !null -> !null") + public T getOrDefault(@NotNull ItemTag tag, @Nullable T defaultValue) { + return tag.read(toNBT()); + } + + public @Nullable T get(@NotNull ItemTag tag) { + return tag.read(toNBT()); + } + public @NotNull NBTCompound toNBT() { if (originalNbt != null) { // Return the nbt this meta has been created with @@ -127,6 +136,6 @@ public class ItemMeta { @Contract(value = "-> new", pure = true) protected @NotNull ItemMetaBuilder builder() { - return builder.clone(); + return ItemMetaBuilder.fromNBT(builder, toNBT()); } } diff --git a/src/main/java/net/minestom/server/item/ItemMetaBuilder.java b/src/main/java/net/minestom/server/item/ItemMetaBuilder.java index 3cca989cb..ed1a56f77 100644 --- a/src/main/java/net/minestom/server/item/ItemMetaBuilder.java +++ b/src/main/java/net/minestom/server/item/ItemMetaBuilder.java @@ -90,6 +90,22 @@ public abstract class ItemMetaBuilder implements Cloneable { return this; } + public @NotNull ItemMetaBuilder set(@NotNull ItemTag tag, @Nullable T value) { + if (originalNBT != null) { + // Item is from nbt + if (value != null) { + tag.write(originalNBT, value); + } else { + this.originalNBT.removeTag(tag.getKey()); + } + return this; + } else { + // Create item meta based on nbt + var currentNbt = build().toNBT(); + return fromNBT(this, currentNbt).set(tag, value); + } + } + @Contract("-> new") public abstract @NotNull ItemMeta build(); diff --git a/src/main/java/net/minestom/server/item/ItemTag.java b/src/main/java/net/minestom/server/item/ItemTag.java new file mode 100644 index 000000000..a0a19f28f --- /dev/null +++ b/src/main/java/net/minestom/server/item/ItemTag.java @@ -0,0 +1,36 @@ +package net.minestom.server.item; + +import org.jetbrains.annotations.NotNull; +import org.jglrxavpok.hephaistos.nbt.NBTCompound; + +public abstract class ItemTag { + + private final String key; + + private ItemTag(@NotNull String key) { + this.key = key; + } + + public @NotNull String getKey() { + return key; + } + + protected abstract T read(@NotNull NBTCompound nbtCompound); + + protected abstract void write(@NotNull NBTCompound nbtCompound, @NotNull T value); + + public static @NotNull ItemTag Integer(@NotNull String key) { + return new ItemTag<>(key) { + @Override + protected Integer read(@NotNull NBTCompound nbtCompound) { + return nbtCompound.getInt(key); + } + + @Override + protected void write(@NotNull NBTCompound nbtCompound, @NotNull Integer value) { + nbtCompound.setInt(key, value); + } + }; + } + +} diff --git a/src/test/java/demo/PlayerInit.java b/src/test/java/demo/PlayerInit.java index e318f2065..022b5d45f 100644 --- a/src/test/java/demo/PlayerInit.java +++ b/src/test/java/demo/PlayerInit.java @@ -27,6 +27,7 @@ import net.minestom.server.inventory.Inventory; import net.minestom.server.inventory.InventoryType; import net.minestom.server.inventory.PlayerInventory; import net.minestom.server.item.ItemStack; +import net.minestom.server.item.ItemTag; import net.minestom.server.item.Material; import net.minestom.server.item.meta.CompassMeta; import net.minestom.server.network.ConnectionManager; @@ -69,12 +70,10 @@ public class PlayerInit { .build(); ItemStack itemStack = ItemStack.builder(Material.COMPASS) - .amount(5) - .meta(compassMeta) .meta(CompassMeta.class, builder -> { builder.lodestonePosition(new Position(0, 0, 0)); + builder.set(ItemTag.Integer("int"), 25); }) - .displayName(Component.text("displayName")) .build(); itemStack = itemStack.with(itemBuilder -> itemBuilder @@ -225,8 +224,8 @@ public class PlayerInit { PlayerInventory inventory = player.getInventory(); ItemStack itemStack = ItemStack.of(Material.STONE, 64); - inventory.addItemStack(itemStack); - inventory.replaceItemStack(0, i -> i.withAmount(32)); + inventory.addItemStack(itemStack.withMeta(metaBuilder -> metaBuilder.set(ItemTag.Integer("int"), 25))); + //inventory.replaceItemStack(0, i -> i.withAmount(32)); { ItemStack item = ItemStack.builder(Material.DIAMOND_CHESTPLATE)