diff options
author | Lulu13022002 <[email protected]> | 2024-06-30 19:04:14 +0200 |
---|---|---|
committer | Owen1212055 <[email protected]> | 2024-11-18 14:50:38 -0500 |
commit | aaf2caf6d7ae7186c7c7d9308b91cb1296c3961c (patch) | |
tree | 4ad2bcab0d2a40cb91313fc38c74baf230dc960b | |
parent | cab010912740af9a0ddfbd08aa08095b15ec8aa9 (diff) | |
download | Paper-aaf2caf6d7ae7186c7c7d9308b91cb1296c3961c.tar.gz Paper-aaf2caf6d7ae7186c7c7d9308b91cb1296c3961c.zip |
rename and re-implement direct methods without itemmeta
-rw-r--r-- | patches/api/0480-WIP-DataComponent-API.patch | 267 | ||||
-rw-r--r-- | patches/server/1026-WIP-DataComponent-API.patch | 549 |
2 files changed, 451 insertions, 365 deletions
diff --git a/patches/api/0480-WIP-DataComponent-API.patch b/patches/api/0480-WIP-DataComponent-API.patch index ae09b3ddb4..42d8067dfe 100644 --- a/patches/api/0480-WIP-DataComponent-API.patch +++ b/patches/api/0480-WIP-DataComponent-API.patch @@ -6,7 +6,7 @@ Subject: [PATCH] WIP DataComponent API diff --git a/src/main/java/io/papermc/paper/block/BlockPredicate.java b/src/main/java/io/papermc/paper/block/BlockPredicate.java new file mode 100644 -index 0000000000000000000000000000000000000000..ad7a6a260bc6903039ed3d0a961cec82b2f6fff7 +index 0000000000000000000000000000000000000000..3e4feb334ba3e2b5895b2db4dc29408398f5fa0a --- /dev/null +++ b/src/main/java/io/papermc/paper/block/BlockPredicate.java @@ -0,0 +1,54 @@ @@ -25,7 +25,7 @@ index 0000000000000000000000000000000000000000..ad7a6a260bc6903039ed3d0a961cec82 + + @NotNull + static Builder predicate() { -+ record BlockPredicateImpl(RegistryKeySet<@NotNull BlockType> blocks) implements BlockPredicate { ++ record BlockPredicateImpl(@Nullable RegistryKeySet<@NotNull BlockType> blocks) implements BlockPredicate { + + @Override + public @Nullable RegistryKeySet<@NotNull BlockType> blocks() { @@ -94,7 +94,7 @@ index 0000000000000000000000000000000000000000..6eb69eb0f220a3a5e63d8315802b4966 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/DataComponentType.java b/src/main/java/io/papermc/paper/datacomponent/DataComponentType.java new file mode 100644 -index 0000000000000000000000000000000000000000..e3fe89c9927d3b82ac7f6cadd51db565d8ab8aa5 +index 0000000000000000000000000000000000000000..798bbc5cd4ba5c04d4952ac5ec8815918d1ce9fd --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/DataComponentType.java @@ -0,0 +1,27 @@ @@ -108,9 +108,9 @@ index 0000000000000000000000000000000000000000..e3fe89c9927d3b82ac7f6cadd51db565 + + /** + * Checks if this data component type is persistent, or -+ * that it will be saved with any item stack it's attached to. ++ * that it will be saved with any itemstack it's attached to. + * -+ * @return {@code true} if persistent, false otherwise ++ * @return {@code true} if persistent, {@code false} otherwise + */ + boolean isPersistent(); + @@ -127,7 +127,7 @@ index 0000000000000000000000000000000000000000..e3fe89c9927d3b82ac7f6cadd51db565 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/DataComponentTypes.java b/src/main/java/io/papermc/paper/datacomponent/DataComponentTypes.java new file mode 100644 -index 0000000000000000000000000000000000000000..9529246c5f4d7b0e5a071a662850776a24b4380a +index 0000000000000000000000000000000000000000..9f4e76e44ed34c57132494cad46b2fade4ffe889 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/DataComponentTypes.java @@ -0,0 +1,322 @@ @@ -151,7 +151,7 @@ index 0000000000000000000000000000000000000000..9529246c5f4d7b0e5a071a662850776a +import io.papermc.paper.datacomponent.item.LockCode; +import io.papermc.paper.datacomponent.item.LodestoneTracker; +import io.papermc.paper.datacomponent.item.MapDecorations; -+import io.papermc.paper.datacomponent.item.MapID; ++import io.papermc.paper.datacomponent.item.MapId; +import io.papermc.paper.datacomponent.item.MapItemColor; +import io.papermc.paper.item.MapPostProcessing; +import io.papermc.paper.datacomponent.item.PotDecorations; @@ -330,7 +330,7 @@ index 0000000000000000000000000000000000000000..9529246c5f4d7b0e5a071a662850776a + /** + * References the shared map state holding map contents and markers for a Filled Map. + */ -+ public static final DataComponentType.Valued<MapID> MAP_ID = valued("map_id"); ++ public static final DataComponentType.Valued<MapId> MAP_ID = valued("map_id"); + /** + * Holds a list of markers to be placed on a Filled Map (used for Explorer Maps). + */ @@ -406,7 +406,7 @@ index 0000000000000000000000000000000000000000..9529246c5f4d7b0e5a071a662850776a + /** + * Controls the sound played by a Player Head when placed on a Note Block. + */ -+ public static final DataComponentType.Valued<NamespacedKey> NOTE_BLOCK_SOUND = valued("note_block_sound"); ++ public static final DataComponentType.Valued<Key> NOTE_BLOCK_SOUND = valued("note_block_sound"); + /** + * Stores the additional patterns applied to a Banner or Shield. + */ @@ -455,14 +455,15 @@ index 0000000000000000000000000000000000000000..9529246c5f4d7b0e5a071a662850776a +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/BannerPatternLayers.java b/src/main/java/io/papermc/paper/datacomponent/item/BannerPatternLayers.java new file mode 100644 -index 0000000000000000000000000000000000000000..c628b5aed20c4d8781e0ad19fdbc4a926fcfc0fa +index 0000000000000000000000000000000000000000..a45b80e610588b8f3f6578ee47cf95b4596f5820 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/BannerPatternLayers.java -@@ -0,0 +1,42 @@ +@@ -0,0 +1,43 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; +import java.util.Arrays; ++import java.util.Collection; +import java.util.List; +import org.bukkit.block.banner.Pattern; +import org.checkerframework.checker.nullness.qual.NonNull; @@ -479,7 +480,7 @@ index 0000000000000000000000000000000000000000..c628b5aed20c4d8781e0ad19fdbc4a92 + } + + @Contract(value = "_ -> new", pure = true) -+ static @NonNull BannerPatternLayers bannerPatternLayers(final @NonNull List<@NonNull Pattern> patterns) { ++ static @NonNull BannerPatternLayers bannerPatternLayers(final @NonNull Collection<@NonNull Pattern> patterns) { + return bannerPatternLayers().addAll(patterns).build(); + } + @@ -498,7 +499,7 @@ index 0000000000000000000000000000000000000000..c628b5aed20c4d8781e0ad19fdbc4a92 + @NonNull Builder add(@NonNull Pattern pattern); + + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAll(@NonNull List<@NonNull Pattern> patterns); ++ @NonNull Builder addAll(@NonNull Collection<@NonNull Pattern> patterns); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/BlockItemDataProperties.java b/src/main/java/io/papermc/paper/datacomponent/item/BlockItemDataProperties.java @@ -537,14 +538,15 @@ index 0000000000000000000000000000000000000000..270f98e95b1d0322a42bad52d492fa00 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/BundleContents.java b/src/main/java/io/papermc/paper/datacomponent/item/BundleContents.java new file mode 100644 -index 0000000000000000000000000000000000000000..d5b1718ae01d6ea73f75446240d169ba9f0d7778 +index 0000000000000000000000000000000000000000..756a47b72c82901f89ef5498b8315e3e1b342143 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/BundleContents.java -@@ -0,0 +1,62 @@ +@@ -0,0 +1,63 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; +import java.util.Arrays; ++import java.util.Collection; +import java.util.List; +import org.bukkit.inventory.ItemStack; +import org.checkerframework.checker.nullness.qual.NonNull; @@ -564,7 +566,7 @@ index 0000000000000000000000000000000000000000..d5b1718ae01d6ea73f75446240d169ba + } + + @Contract(value = "_ -> new", pure = true) -+ static @NonNull BundleContents bundleContents(final @NonNull List<@NonNull ItemStack> contents) { ++ static @NonNull BundleContents bundleContents(final @NonNull Collection<@NonNull ItemStack> contents) { + return ComponentTypesBridge.bridge().bundleContents().addAll(contents).build(); + } + @@ -600,19 +602,20 @@ index 0000000000000000000000000000000000000000..d5b1718ae01d6ea73f75446240d169ba + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAll(@NonNull List<@NonNull ItemStack> stacks); ++ @NonNull Builder addAll(@NonNull Collection<@NonNull ItemStack> stacks); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/ChargedProjectiles.java b/src/main/java/io/papermc/paper/datacomponent/item/ChargedProjectiles.java new file mode 100644 -index 0000000000000000000000000000000000000000..b8eea6dd890bfed0462cffb0aac48ee8010636f1 +index 0000000000000000000000000000000000000000..48319377a3038050ec4cebad73a3d5396c0008bd --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/ChargedProjectiles.java -@@ -0,0 +1,62 @@ +@@ -0,0 +1,63 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; +import java.util.Arrays; ++import java.util.Collection; +import java.util.List; +import org.bukkit.inventory.ItemStack; +import org.checkerframework.checker.nullness.qual.NonNull; @@ -632,7 +635,7 @@ index 0000000000000000000000000000000000000000..b8eea6dd890bfed0462cffb0aac48ee8 + } + + @Contract(value = "_ -> new", pure = true) -+ static @NonNull ChargedProjectiles chargedProjectiles(final @NonNull List<@NonNull ItemStack> projectiles) { ++ static @NonNull ChargedProjectiles chargedProjectiles(final @NonNull Collection<@NonNull ItemStack> projectiles) { + return chargedProjectiles().addAll(projectiles).build(); + } + @@ -668,17 +671,18 @@ index 0000000000000000000000000000000000000000..b8eea6dd890bfed0462cffb0aac48ee8 + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAll(@NonNull List<@NonNull ItemStack> stacks); ++ @NonNull Builder addAll(@NonNull Collection<@NonNull ItemStack> stacks); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/ComponentTypesBridge.java b/src/main/java/io/papermc/paper/datacomponent/item/ComponentTypesBridge.java new file mode 100644 -index 0000000000000000000000000000000000000000..1cbb8da68dcc0b2af271d6a4e8782bfa7459b7c6 +index 0000000000000000000000000000000000000000..7412a4259140707fbf7545f7c8a3da0ba76bab66 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/ComponentTypesBridge.java -@@ -0,0 +1,89 @@ +@@ -0,0 +1,92 @@ +package io.papermc.paper.datacomponent.item; + ++import com.destroystokyo.paper.profile.PlayerProfile; +import io.papermc.paper.registry.set.RegistryKeySet; +import io.papermc.paper.util.Filtered; +import java.util.Optional; @@ -730,7 +734,7 @@ index 0000000000000000000000000000000000000000..1cbb8da68dcc0b2af271d6a4e8782bfa + + MapItemColor.Builder mapItemColor(); + -+ MapID.Builder mapId(); ++ MapId.Builder mapId(); + + MapDecorations.Builder mapDecorations(); + @@ -750,6 +754,8 @@ index 0000000000000000000000000000000000000000..1cbb8da68dcc0b2af271d6a4e8782bfa + + ResolvableProfile.Builder resolvableProfile(); + ++ ResolvableProfile resolvableProfile(PlayerProfile profile); ++ + BannerPatternLayers.Builder bannerPatternLayers(); + + BlockItemDataProperties.Builder blockItemStateProperties(); @@ -762,13 +768,13 @@ index 0000000000000000000000000000000000000000..1cbb8da68dcc0b2af271d6a4e8782bfa + + Tool.Builder tool(); + -+ Tool.Rule rule(RegistryKeySet<BlockType> blockTypes, @Nullable Float speed, TriState correctForDrops); ++ Tool.Rule rule(RegistryKeySet<BlockType> blocks, @Nullable Float speed, TriState correctForDrops); + + ItemAdventurePredicate.Builder itemAdventurePredicate(); +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/CustomModelData.java b/src/main/java/io/papermc/paper/datacomponent/item/CustomModelData.java new file mode 100644 -index 0000000000000000000000000000000000000000..e93f962fc51c0f260719fccad7ccdadc114bfc31 +index 0000000000000000000000000000000000000000..90c9e272aaf6f122ec773da65a2366e9fb5be08f --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/CustomModelData.java @@ -0,0 +1,27 @@ @@ -793,7 +799,7 @@ index 0000000000000000000000000000000000000000..e93f962fc51c0f260719fccad7ccdadc + interface Builder { + + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder customModelData(int data); ++ @NonNull Builder data(int data); + + @Contract(value = "-> new", pure = true) + @NonNull CustomModelData build(); @@ -852,13 +858,14 @@ index 0000000000000000000000000000000000000000..93f419b8e4d9c87b3ad4fa570d3bfad4 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/Fireworks.java b/src/main/java/io/papermc/paper/datacomponent/item/Fireworks.java new file mode 100644 -index 0000000000000000000000000000000000000000..c59b57eab245e7c8de1c466aa535db4a4913ff17 +index 0000000000000000000000000000000000000000..3b9548c150f8592e171d7f9686baa3d6aec0720f --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/Fireworks.java -@@ -0,0 +1,74 @@ +@@ -0,0 +1,75 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; ++import java.util.Collection; +import java.util.List; +import org.bukkit.FireworkEffect; +import org.checkerframework.checker.nullness.qual.NonNull; @@ -874,8 +881,8 @@ index 0000000000000000000000000000000000000000..c59b57eab245e7c8de1c466aa535db4a +public interface Fireworks { + + @Contract(value = "_, _ -> new", pure = true) -+ static @NonNull Fireworks fireworks(final @NonNull List<@NonNull FireworkEffect> effects, final int flightDuration) { -+ return fireworks().addAll(effects).flightDuration(flightDuration).build(); ++ static @NonNull Fireworks fireworks(final @NonNull Collection<@NonNull FireworkEffect> effects, final int flightDuration) { ++ return fireworks().addEffects(effects).flightDuration(flightDuration).build(); + } + + @Contract(value = "-> new", pure = true) @@ -918,7 +925,7 @@ index 0000000000000000000000000000000000000000..c59b57eab245e7c8de1c466aa535db4a + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder add(@NonNull FireworkEffect effect); ++ @NonNull Builder addEffect(@NonNull FireworkEffect effect); + + /** + * Adds explosions to this builder. @@ -927,18 +934,19 @@ index 0000000000000000000000000000000000000000..c59b57eab245e7c8de1c466aa535db4a + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAll(@NonNull List<@NonNull FireworkEffect> effects); ++ @NonNull Builder addEffects(@NonNull Collection<@NonNull FireworkEffect> effects); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/FoodProperties.java b/src/main/java/io/papermc/paper/datacomponent/item/FoodProperties.java new file mode 100644 -index 0000000000000000000000000000000000000000..9d207063f794873acb22ce1e88b072b4952aadfc +index 0000000000000000000000000000000000000000..1a0ae9ba2451e89b113f1bbc729415b8415266ab --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/FoodProperties.java -@@ -0,0 +1,113 @@ +@@ -0,0 +1,114 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; ++import java.util.Collection; +import java.util.List; +import org.bukkit.inventory.ItemStack; +import org.bukkit.potion.PotionEffect; @@ -1046,7 +1054,7 @@ index 0000000000000000000000000000000000000000..9d207063f794873acb22ce1e88b072b4 + @NonNull Builder addEffect(@NonNull PossibleEffect effect); + + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAllEffects(@NonNull List<@NonNull PossibleEffect> effects); ++ @NonNull Builder addEffects(@NonNull Collection<@NonNull PossibleEffect> effects); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/ItemAdventurePredicate.java b/src/main/java/io/papermc/paper/datacomponent/item/ItemAdventurePredicate.java @@ -1150,7 +1158,7 @@ index 0000000000000000000000000000000000000000..e874f024a6a5493aad08db4a94dbfa58 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/ItemAttributeModifiers.java b/src/main/java/io/papermc/paper/datacomponent/item/ItemAttributeModifiers.java new file mode 100644 -index 0000000000000000000000000000000000000000..852259c5ec59f1aa32261d14fbb5c7608795f9ee +index 0000000000000000000000000000000000000000..633e9ea540cfff0bd270dc4ec4291ce930c40612 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/ItemAttributeModifiers.java @@ -0,0 +1,57 @@ @@ -1204,23 +1212,24 @@ index 0000000000000000000000000000000000000000..852259c5ec59f1aa32261d14fbb5c760 + * Adds a modifier to this builder. + * + * @param attribute attribute -+ * @param attributeModifier modifier ++ * @param modifier modifier + * @return the builder for chaining + */ + @Contract(value = "_, _ -> this", mutates = "this") -+ @NonNull Builder addModifier(@NonNull Attribute attribute, @NonNull AttributeModifier attributeModifier); ++ @NonNull Builder addModifier(@NonNull Attribute attribute, @NonNull AttributeModifier modifier); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/ItemContainerContents.java b/src/main/java/io/papermc/paper/datacomponent/item/ItemContainerContents.java new file mode 100644 -index 0000000000000000000000000000000000000000..1f44eac662f975ee123305eb935e068bf916052e +index 0000000000000000000000000000000000000000..e24079e44924584562cc092dc28ee559b8f06002 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/ItemContainerContents.java -@@ -0,0 +1,42 @@ +@@ -0,0 +1,43 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; +import java.util.Arrays; ++import java.util.Collection; +import java.util.List; +import org.bukkit.inventory.ItemStack; +import org.checkerframework.checker.nullness.qual.NonNull; @@ -1233,11 +1242,11 @@ index 0000000000000000000000000000000000000000..1f44eac662f975ee123305eb935e068b + + @Contract(value = "_ -> new", pure = true) + static @NonNull ItemContainerContents containerContents(final @NonNull ItemStack @NonNull...contents) { -+ return containerContents().addAll(Arrays.asList(contents)).build(); ++ return containerContents(Arrays.asList(contents)); + } + + @Contract(value = "_ -> new", pure = true) -+ static @NonNull ItemContainerContents containerContents(final @NonNull List<@NonNull ItemStack> contents) { ++ static @NonNull ItemContainerContents containerContents(final @NonNull Collection<@NonNull ItemStack> contents) { + return containerContents().addAll(contents).build(); + } + @@ -1256,12 +1265,12 @@ index 0000000000000000000000000000000000000000..1f44eac662f975ee123305eb935e068b + @NonNull Builder add(@NonNull ItemStack stack); + + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAll(@NonNull List<@NonNull ItemStack> stacks); ++ @NonNull Builder addAll(@NonNull Collection<@NonNull ItemStack> stacks); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/ItemEnchantments.java b/src/main/java/io/papermc/paper/datacomponent/item/ItemEnchantments.java new file mode 100644 -index 0000000000000000000000000000000000000000..3b519007fd7b7e62bcc15a1ad93fd61b954ee4c5 +index 0000000000000000000000000000000000000000..68ebd664bb9d78bb865b1ff9e6c2b5a1c03bbcf7 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/ItemEnchantments.java @@ -0,0 +1,58 @@ @@ -1298,7 +1307,7 @@ index 0000000000000000000000000000000000000000..3b519007fd7b7e62bcc15a1ad93fd61b + * @return enchantments + */ + @Contract(pure = true) -+ @NonNull @Unmodifiable Map<@NonNull Enchantment, @NonNull @IntRange(from = 1, to = 255) Integer> enchantments(); ++ @NonNull @Unmodifiable Map<@NonNull Enchantment, @NonNull @IntRange(from = 0, to = 255) Integer> enchantments(); + + @ApiStatus.NonExtendable + interface Builder extends ShownInTooltip.Builder<Builder>, ComponentBuilder<ItemEnchantments> { @@ -1325,7 +1334,7 @@ index 0000000000000000000000000000000000000000..3b519007fd7b7e62bcc15a1ad93fd61b +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/ItemLore.java b/src/main/java/io/papermc/paper/datacomponent/item/ItemLore.java new file mode 100644 -index 0000000000000000000000000000000000000000..6ee7cdd943833fc72ef7260478a3fadf3496adf4 +index 0000000000000000000000000000000000000000..e1689b544c031a94db9d10e1bba7a7052dae5a40 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/ItemLore.java @@ -0,0 +1,74 @@ @@ -1400,7 +1409,7 @@ index 0000000000000000000000000000000000000000..6ee7cdd943833fc72ef7260478a3fadf + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAllLines(@NonNull List<@NonNull ? extends ComponentLike> lines); ++ @NonNull Builder addLines(@NonNull List<@NonNull ? extends ComponentLike> lines); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/JukeboxPlayable.java b/src/main/java/io/papermc/paper/datacomponent/item/JukeboxPlayable.java @@ -1437,7 +1446,7 @@ index 0000000000000000000000000000000000000000..1d2276a6522044f06713db5ab8495d8a +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/LockCode.java b/src/main/java/io/papermc/paper/datacomponent/item/LockCode.java new file mode 100644 -index 0000000000000000000000000000000000000000..cf6a2e8e6640deeae05283b3cb5755a417d01484 +index 0000000000000000000000000000000000000000..999209e91587c429c830b859f47546cd67642530 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/LockCode.java @@ -0,0 +1,27 @@ @@ -1462,7 +1471,7 @@ index 0000000000000000000000000000000000000000..cf6a2e8e6640deeae05283b3cb5755a4 + interface Builder { + + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder lock(@NonNull String code); ++ @NonNull Builder lock(@NonNull String key); + + @Contract(value = "-> new", pure = true) + @NonNull LockCode build(); @@ -1648,12 +1657,12 @@ index 0000000000000000000000000000000000000000..3cf5e994ce00dcd1823b9fff5f035931 + MapDecorations.@NonNull Builder putAll(@NonNull Map<@NonNull String, @NonNull DecorationEntry> entries); + } +} -diff --git a/src/main/java/io/papermc/paper/datacomponent/item/MapID.java b/src/main/java/io/papermc/paper/datacomponent/item/MapID.java +diff --git a/src/main/java/io/papermc/paper/datacomponent/item/MapId.java b/src/main/java/io/papermc/paper/datacomponent/item/MapId.java new file mode 100644 -index 0000000000000000000000000000000000000000..89e3f32ef74e7a2018cf76ebe51f31a1037bb701 +index 0000000000000000000000000000000000000000..e5e28d0af32cc76bb5ff615c886a1bca2bfb0bf5 --- /dev/null -+++ b/src/main/java/io/papermc/paper/datacomponent/item/MapID.java -@@ -0,0 +1,41 @@ ++++ b/src/main/java/io/papermc/paper/datacomponent/item/MapId.java +@@ -0,0 +1,42 @@ +package io.papermc.paper.datacomponent.item; + +import org.checkerframework.checker.nullness.qual.NonNull; @@ -1664,10 +1673,10 @@ index 0000000000000000000000000000000000000000..89e3f32ef74e7a2018cf76ebe51f31a1 + * References the shared map state holding map contents and markers for a Filled Map. + */ -+public interface MapID { ++public interface MapId { + + @Contract(value = "-> new", pure = true) -+ static MapID.@NonNull Builder mapId() { ++ static MapId.@NonNull Builder mapId() { + return ComponentTypesBridge.bridge().mapId(); + } + @@ -1689,10 +1698,11 @@ index 0000000000000000000000000000000000000000..89e3f32ef74e7a2018cf76ebe51f31a1 + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder mapId(int id); ++ @NonNull Builder id(int id); + + @Contract(value = "-> new", pure = true) -+ @NonNull MapID build(); ++ @NonNull ++ MapId build(); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/MapItemColor.java b/src/main/java/io/papermc/paper/datacomponent/item/MapItemColor.java @@ -1800,13 +1810,14 @@ index 0000000000000000000000000000000000000000..abd94c0c900f7c2bf936e0c5c28ec928 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PotionContents.java b/src/main/java/io/papermc/paper/datacomponent/item/PotionContents.java new file mode 100644 -index 0000000000000000000000000000000000000000..586f32d0198ec0f17006066c72fad8c5e7af6120 +index 0000000000000000000000000000000000000000..fb2ad16d4506bdcc660e0e89075dca599505604d --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PotionContents.java -@@ -0,0 +1,92 @@ +@@ -0,0 +1,97 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; ++import java.util.Collection; +import java.util.List; +import org.bukkit.Color; +import org.bukkit.potion.PotionEffect; @@ -1840,6 +1851,8 @@ index 0000000000000000000000000000000000000000..586f32d0198ec0f17006066c72fad8c5 + * Overrides the visual color of the potion. + * + * @return color override, or {@code null} if not present ++ * @apiNote alpha channel of the color is only relevant ++ * for Tipped Arrow + */ + @Contract(pure = true) + @Nullable Color customColor(); @@ -1858,12 +1871,12 @@ index 0000000000000000000000000000000000000000..586f32d0198ec0f17006066c72fad8c5 + /** + * Sets the potion type for this builder. + * -+ * @param potionType builder ++ * @param type builder + * @see #potion() + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder potion(@Nullable PotionType potionType); ++ @NonNull Builder potion(@Nullable PotionType type); + + /** + * Sets the color override for this builder. @@ -1871,6 +1884,8 @@ index 0000000000000000000000000000000000000000..586f32d0198ec0f17006066c72fad8c5 + * @param color color + * @see #customColor() + * @return the builder for chaining ++ * @apiNote alpha channel of the color is supported only for ++ * Tipped Arrow + */ + @Contract(value = "_ -> this", mutates = "this") + @NonNull Builder customColor(@Nullable Color color); @@ -1878,37 +1893,36 @@ index 0000000000000000000000000000000000000000..586f32d0198ec0f17006066c72fad8c5 + /** + * Adds a custom effect instance to this builder. + * -+ * @param potionEffect effect ++ * @param effect effect + * @see #customEffects() + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder add(@NonNull PotionEffect potionEffect); ++ @NonNull Builder addCustomEffect(@NonNull PotionEffect effect); + + /** + * Adds custom effect instances to this builder. + * -+ * @param potionEffects effects ++ * @param effects effects + * @see #customEffects() + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAll(@NonNull List<@NonNull PotionEffect> potionEffects); ++ @NonNull Builder addCustomEffects(@NonNull Collection<@NonNull PotionEffect> effects); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/ResolvableProfile.java b/src/main/java/io/papermc/paper/datacomponent/item/ResolvableProfile.java new file mode 100644 -index 0000000000000000000000000000000000000000..10cb1af6c976659f80839ce46cdddcc89ed20681 +index 0000000000000000000000000000000000000000..2cae652ae18fd52a4b932ca350e35c711c4612e4 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/ResolvableProfile.java -@@ -0,0 +1,51 @@ +@@ -0,0 +1,55 @@ +package io.papermc.paper.datacomponent.item; + +import com.destroystokyo.paper.profile.PlayerProfile; +import com.destroystokyo.paper.profile.ProfileProperty; +import io.papermc.paper.datacomponent.ComponentBuilder; +import java.util.Collection; -+import java.util.List; +import java.util.UUID; +import java.util.concurrent.CompletableFuture; +import org.checkerframework.checker.nullness.qual.NonNull; @@ -1920,6 +1934,11 @@ index 0000000000000000000000000000000000000000..10cb1af6c976659f80839ce46cdddcc8 +public interface ResolvableProfile { + ++ @Contract(value = "_ -> new", pure = true) ++ static @NonNull ResolvableProfile resolvableProfile(@NonNull PlayerProfile profile) { ++ return ComponentTypesBridge.bridge().resolvableProfile(profile); ++ } ++ + @Contract(value = "-> new", pure = true) + static ResolvableProfile.@NonNull Builder resolvableProfile() { + return ComponentTypesBridge.bridge().resolvableProfile(); @@ -1950,7 +1969,7 @@ index 0000000000000000000000000000000000000000..10cb1af6c976659f80839ce46cdddcc8 + @NonNull Builder addProperty(@NonNull ProfileProperty property); + + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAllProperties(@NonNull List<@NonNull ProfileProperty> properties); ++ @NonNull Builder addProperties(@NonNull Collection<@NonNull ProfileProperty> properties); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/SeededContainerLoot.java b/src/main/java/io/papermc/paper/datacomponent/item/SeededContainerLoot.java @@ -2025,15 +2044,16 @@ index 0000000000000000000000000000000000000000..1e39fc6779e324030fb2890a4568376f +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/SuspiciousStewEffects.java b/src/main/java/io/papermc/paper/datacomponent/item/SuspiciousStewEffects.java new file mode 100644 -index 0000000000000000000000000000000000000000..64d99c69d17ca1bc5be5c2e21b6ae423048f1d87 +index 0000000000000000000000000000000000000000..2c8c9aaac9326fc47f963651def7642a12341189 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/SuspiciousStewEffects.java -@@ -0,0 +1,62 @@ +@@ -0,0 +1,63 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; +import io.papermc.paper.potion.SuspiciousEffectEntry; +import java.util.Arrays; ++import java.util.Collection; +import java.util.List; +import org.checkerframework.checker.nullness.qual.NonNull; +import org.jetbrains.annotations.ApiStatus; @@ -2048,11 +2068,11 @@ index 0000000000000000000000000000000000000000..64d99c69d17ca1bc5be5c2e21b6ae423 + + @Contract(value = "_ -> new", pure = true) + static @NonNull SuspiciousStewEffects suspiciousStewEffects(final @NonNull SuspiciousEffectEntry @NonNull...effects) { -+ return suspiciousStewEffects().addAll(Arrays.asList(effects)).build(); ++ return suspiciousStewEffects(Arrays.asList(effects)); + } + + @Contract(value = "_ -> new", pure = true) -+ static @NonNull SuspiciousStewEffects suspiciousStewEffects(final @NonNull List<@NonNull SuspiciousEffectEntry> effects) { ++ static @NonNull SuspiciousStewEffects suspiciousStewEffects(final @NonNull Collection<@NonNull SuspiciousEffectEntry> effects) { + return suspiciousStewEffects().addAll(effects).build(); + } + @@ -2088,18 +2108,19 @@ index 0000000000000000000000000000000000000000..64d99c69d17ca1bc5be5c2e21b6ae423 + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addAll(@NonNull List<@NonNull SuspiciousEffectEntry> entries); ++ @NonNull Builder addAll(@NonNull Collection<@NonNull SuspiciousEffectEntry> entries); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/Tool.java b/src/main/java/io/papermc/paper/datacomponent/item/Tool.java new file mode 100644 -index 0000000000000000000000000000000000000000..914fd3144dd81dd2209489671d1a1df5231b9167 +index 0000000000000000000000000000000000000000..aeee3c4338dbf17e3c7623ab4276fe43ad79e0d0 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/Tool.java -@@ -0,0 +1,132 @@ +@@ -0,0 +1,133 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; ++import java.util.Collection; +import java.util.List; +import io.papermc.paper.registry.set.RegistryKeySet; +import net.kyori.adventure.util.TriState; @@ -2149,20 +2170,20 @@ index 0000000000000000000000000000000000000000..914fd3144dd81dd2209489671d1a1df5 + @ApiStatus.NonExtendable + interface Rule { + -+ static @NonNull Rule of(final @NonNull RegistryKeySet<BlockType> blockTypes, final @Nullable Float speed, final @NonNull TriState correctForDrops) { -+ return ComponentTypesBridge.bridge().rule(blockTypes, speed, correctForDrops); ++ static @NonNull Rule of(final @NonNull RegistryKeySet<BlockType> blocks, final @Nullable Float speed, final @NonNull TriState correctForDrops) { ++ return ComponentTypesBridge.bridge().rule(blocks, speed, correctForDrops); + } + + static @NonNull Rule minesAndDrops(final @NonNull RegistryKeySet<BlockType> blocks, final float speed) { + return of(blocks, speed, TriState.TRUE); + } + -+ static @NonNull Rule deniesDrops(final @NonNull RegistryKeySet<BlockType> tag) { -+ return of(tag, null, TriState.FALSE); ++ static @NonNull Rule deniesDrops(final @NonNull RegistryKeySet<BlockType> blocks) { ++ return of(blocks, null, TriState.FALSE); + } + -+ static @NonNull Rule overrideSpeed(final @NonNull RegistryKeySet<BlockType> tag, final float speed) { -+ return of(tag, speed, TriState.NOT_SET); ++ static @NonNull Rule overrideSpeed(final @NonNull RegistryKeySet<BlockType> blocks, final float speed) { ++ return of(blocks, speed, TriState.NOT_SET); + } + + /** @@ -2170,7 +2191,7 @@ index 0000000000000000000000000000000000000000..914fd3144dd81dd2209489671d1a1df5 + * + * @return blocks + */ -+ @NonNull RegistryKeySet<BlockType> blockTypes(); ++ @NonNull RegistryKeySet<BlockType> blocks(); + + /** + * Overrides the mining speed if present and matched. @@ -2199,16 +2220,16 @@ index 0000000000000000000000000000000000000000..914fd3144dd81dd2209489671d1a1df5 + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder damagePerBlock(int damage); ++ @NonNull Builder damagePerBlock(@NonNegative int damage); + + /** + * Controls mining speed to use if no rules match and don't override mining speed. + * -+ * @param speed mining speed ++ * @param miningSpeed mining speed + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder defaultMiningSpeed(float speed); ++ @NonNull Builder defaultMiningSpeed(float miningSpeed); + + /** + * Adds a rule to the tool that controls the breaking speed / damage per block if matched. @@ -2226,7 +2247,7 @@ index 0000000000000000000000000000000000000000..914fd3144dd81dd2209489671d1a1df5 + * @return the builder for chaining + */ + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder addRules(@NonNull List<@NonNull Rule> rules); ++ @NonNull Builder addRules(@NonNull Collection<@NonNull Rule> rules); + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/Unbreakable.java b/src/main/java/io/papermc/paper/datacomponent/item/Unbreakable.java @@ -2337,10 +2358,10 @@ index 0000000000000000000000000000000000000000..9e448331e8855143ebdad2ea6419bcf2 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/WrittenBookContent.java b/src/main/java/io/papermc/paper/datacomponent/item/WrittenBookContent.java new file mode 100644 -index 0000000000000000000000000000000000000000..95e2323c875a36fb383b41fd3d58722ad304b829 +index 0000000000000000000000000000000000000000..2b543a336ed2f53861d67470005373de0972ea5e --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/WrittenBookContent.java -@@ -0,0 +1,96 @@ +@@ -0,0 +1,97 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.datacomponent.ComponentBuilder; @@ -2350,6 +2371,7 @@ index 0000000000000000000000000000000000000000..95e2323c875a36fb383b41fd3d58722a +import net.kyori.adventure.text.Component; +import net.kyori.adventure.text.ComponentLike; +import org.checkerframework.checker.nullness.qual.NonNull; ++import org.checkerframework.common.value.qual.IntRange; +import org.jetbrains.annotations.ApiStatus; +import org.jetbrains.annotations.Contract; +import org.jetbrains.annotations.Unmodifiable; @@ -2387,12 +2409,12 @@ index 0000000000000000000000000000000000000000..95e2323c875a36fb383b41fd3d58722a + @NonNull String author(); + + /** -+ * The number of times this book has been copied (0 = original) ++ * The number of times this book has been copied (0 = original). + * + * @return generation + */ + @Contract(pure = true) -+ int generation(); ++ @IntRange(from = 0, to = 3) int generation(); + + @Contract(pure = true) + @NonNull @Unmodifiable List<@NonNull Filtered<@NonNull Component>> pages(); @@ -2419,7 +2441,7 @@ index 0000000000000000000000000000000000000000..95e2323c875a36fb383b41fd3d58722a + @NonNull Builder author(@NonNull String author); + + @Contract(value = "_ -> this", mutates = "this") -+ @NonNull Builder generation(int generation); ++ @NonNull Builder generation(@IntRange(from = 0, to = 3) int generation); + + @Contract(value = "_ -> this", mutates = "this") + @NonNull Builder resolved(boolean resolved); @@ -2461,7 +2483,7 @@ index 0000000000000000000000000000000000000000..5843768d0be2ae4a0219636ed7640727 + SCALE +} diff --git a/src/main/java/io/papermc/paper/registry/RegistryKey.java b/src/main/java/io/papermc/paper/registry/RegistryKey.java -index 2945dde566682f977e84fde5d473a6c69be24df1..6ab6e9d3a1fcb5fcb370e507164da70012e61e88 100644 +index 2945dde566682f977e84fde5d473a6c69be24df1..530cbadc8b4871113dc9ebb24bc565a95a61fdae 100644 --- a/src/main/java/io/papermc/paper/registry/RegistryKey.java +++ b/src/main/java/io/papermc/paper/registry/RegistryKey.java @@ -1,5 +1,6 @@ @@ -2471,12 +2493,17 @@ index 2945dde566682f977e84fde5d473a6c69be24df1..6ab6e9d3a1fcb5fcb370e507164da700 import net.kyori.adventure.key.Keyed; import org.bukkit.Art; import org.bukkit.Fluid; -@@ -145,4 +146,5 @@ public sealed interface RegistryKey<T> extends Keyed permits RegistryKeyImpl { - RegistryKey<Fluid> FLUID = create("fluid"); - RegistryKey<Frog.Variant> FROG_VARIANT = create("frog_variant"); - RegistryKey<MapCursor.Type> MAP_DECORATION_TYPE = create("map_decoration_type"); +@@ -81,6 +82,10 @@ public sealed interface RegistryKey<T> extends Keyed permits RegistryKeyImpl { + */ + @ApiStatus.Experimental // Paper - already required for registry builders + RegistryKey<ItemType> ITEM = create("item"); ++ /** ++ * Built-in registry for data component types. ++ */ + RegistryKey<DataComponentType> DATA_COMPONENT_TYPE = create("data_component_type"); - } + + + /* ********************** * diff --git a/src/main/java/io/papermc/paper/util/Filtered.java b/src/main/java/io/papermc/paper/util/Filtered.java new file mode 100644 index 0000000000000000000000000000000000000000..5c8cdf46bc12501e1f284b4760c48e79233d05ff @@ -2514,7 +2541,7 @@ index 0000000000000000000000000000000000000000..5c8cdf46bc12501e1f284b4760c48e79 + @Nullable T filtered(); +} diff --git a/src/main/java/org/bukkit/Material.java b/src/main/java/org/bukkit/Material.java -index 54704da43cf9c429f3914f0580246dde99aa93c0..7f566e1b6de89923cc1eca079b00c10afc2ae981 100644 +index 54704da43cf9c429f3914f0580246dde99aa93c0..2c295ad8e3155d19fdac09d3a02d9274aba3bc62 100644 --- a/src/main/java/org/bukkit/Material.java +++ b/src/main/java/org/bukkit/Material.java @@ -130,7 +130,7 @@ import org.jetbrains.annotations.Nullable; @@ -2551,34 +2578,34 @@ index 54704da43cf9c429f3914f0580246dde99aa93c0..7f566e1b6de89923cc1eca079b00c10a + /** + * Gets the default data component value for the data type for this ItemType. + * -+ * @param dataComponentType the data component type -+ * @return the default value or null if there is none ++ * @param type the data component type + * @param <T> the value type ++ * @return the default value or {@code null} if there is none + * @see #hasDefaultData(io.papermc.paper.datacomponent.DataComponentType) for DataComponentType.NonValued -+ * @throws IllegalArgumentException if {@link #isItem()} is false ++ * @throws IllegalArgumentException if {@link #isItem()} is {@code false} + */ -+ public @Nullable <T> T getDefaultData(final io.papermc.paper.datacomponent.DataComponentType.@NotNull Valued<T> dataComponentType) { ++ public @Nullable <T> T getDefaultData(final io.papermc.paper.datacomponent.DataComponentType.@NotNull Valued<T> type) { + Preconditions.checkArgument(this.asItemType() != null); -+ return this.asItemType().getDefaultData(dataComponentType); ++ return this.asItemType().getDefaultData(type); + } + + /** + * Checks if the data component type has a default value for this ItemType. + * -+ * @param dataComponentType the data component type -+ * @return true if there is a default value -+ * @throws IllegalArgumentException if {@link #isItem()} is false ++ * @param type the data component type ++ * @return {@code true} if there is a default value ++ * @throws IllegalArgumentException if {@link #isItem()} is {@code false} + */ -+ public boolean hasDefaultData(final io.papermc.paper.datacomponent.@NotNull DataComponentType dataComponentType) { ++ public boolean hasDefaultData(final io.papermc.paper.datacomponent.@NotNull DataComponentType type) { + Preconditions.checkArgument(this.asItemType() != null); -+ return this.asItemType().hasDefaultData(dataComponentType); ++ return this.asItemType().hasDefaultData(type); + } + + /** + * Gets the default data component types for this ItemType. + * + * @return an immutable set of data component types -+ * @throws IllegalArgumentException if {@link #isItem()} is false ++ * @throws IllegalArgumentException if {@link #isItem()} is {@code false} + */ + public [email protected] @NotNull Set<io.papermc.paper.datacomponent.DataComponentType> getDefaultDataTypes() { + Preconditions.checkArgument(this.asItemType() != null); @@ -2600,7 +2627,7 @@ index 9725580b6458e5d37fbc6059869604f9883bd6d1..966bbc686280a1b7f479a2ff755e4776 /** * Get the object by its key. diff --git a/src/main/java/org/bukkit/inventory/ItemStack.java b/src/main/java/org/bukkit/inventory/ItemStack.java -index f603b5b6ba80af919f415322583a8345a5b1358a..22035e8cc586ca454fab6b494928d6d610574615 100644 +index f603b5b6ba80af919f415322583a8345a5b1358a..4ffa69f89b4ca15d9f4a53642eced10a760a9600 100644 --- a/src/main/java/org/bukkit/inventory/ItemStack.java +++ b/src/main/java/org/bukkit/inventory/ItemStack.java @@ -1031,4 +1031,124 @@ public class ItemStack implements Cloneable, ConfigurationSerializable, Translat @@ -2613,8 +2640,8 @@ index f603b5b6ba80af919f415322583a8345a5b1358a..22035e8cc586ca454fab6b494928d6d6 + * Gets the value for the data component type on this stack. + * + * @param type the data component type -+ * @return the value for the data component type, or null if not set or marked as removed + * @param <T> the value type ++ * @return the value for the data component type, or {@code null} if not set or marked as removed + * @see #hasData(io.papermc.paper.datacomponent.DataComponentType) for DataComponentType.NonValued + */ + @org.jetbrains.annotations.Contract(pure = true) @@ -2628,8 +2655,8 @@ index f603b5b6ba80af919f415322583a8345a5b1358a..22035e8cc586ca454fab6b494928d6d6 + * + * @param type the data component type + * @param fallback the fallback value if the value isn't present -+ * @return the value for the data component type or the fallback value + * @param <T> the value type ++ * @return the value for the data component type or the fallback value + */ + @Utility + @org.jetbrains.annotations.Contract(value = "_, !null -> !null", pure = true) @@ -2729,7 +2756,7 @@ index f603b5b6ba80af919f415322583a8345a5b1358a..22035e8cc586ca454fab6b494928d6d6 + // Paper end - data component API } diff --git a/src/main/java/org/bukkit/inventory/ItemType.java b/src/main/java/org/bukkit/inventory/ItemType.java -index 6bc1853ada3ea38bc36cb31fbb5ce246347fe5d4..a5d2ba61678bb55ee6ff44026f58e15fa7f1e466 100644 +index 6bc1853ada3ea38bc36cb31fbb5ce246347fe5d4..955a09822f73a9343ef9bc20b6a27bc169fb5033 100644 --- a/src/main/java/org/bukkit/inventory/ItemType.java +++ b/src/main/java/org/bukkit/inventory/ItemType.java @@ -2326,4 +2326,31 @@ public interface ItemType extends Keyed, Translatable, net.kyori.adventure.trans @@ -2741,20 +2768,20 @@ index 6bc1853ada3ea38bc36cb31fbb5ce246347fe5d4..a5d2ba61678bb55ee6ff44026f58e15f + /** + * Gets the default data component value for the data type for this ItemType. + * -+ * @param dataComponentType the data component type -+ * @return the default value or null if there is none ++ * @param type the data component type + * @param <T> the value type ++ * @return the default value or {@code null} if there is none + * @see #hasDefaultData(io.papermc.paper.datacomponent.DataComponentType) for DataComponentType.NonValued + */ -+ @Nullable <T> T getDefaultData(io.papermc.paper.datacomponent.DataComponentType.@NotNull Valued<T> dataComponentType); ++ @Nullable <T> T getDefaultData(io.papermc.paper.datacomponent.DataComponentType.@NotNull Valued<T> type); + + /** + * Checks if the data component type has a default value for this ItemType. + * -+ * @param dataComponentType the data component type ++ * @param type the data component type + * @return true if there is a default value + */ -+ boolean hasDefaultData(io.papermc.paper.datacomponent.@NotNull DataComponentType dataComponentType); ++ boolean hasDefaultData(io.papermc.paper.datacomponent.@NotNull DataComponentType type); + + /** + * Gets the default data component types for this ItemType. diff --git a/patches/server/1026-WIP-DataComponent-API.patch b/patches/server/1026-WIP-DataComponent-API.patch index 13a5043d4a..cd4ddbe237 100644 --- a/patches/server/1026-WIP-DataComponent-API.patch +++ b/patches/server/1026-WIP-DataComponent-API.patch @@ -7,18 +7,33 @@ Subject: [PATCH] WIP DataComponent API public net/minecraft/world/item/component/ItemContainerContents MAX_SIZE public net/minecraft/world/item/component/ItemContainerContents items +diff --git a/src/main/java/io/papermc/paper/adventure/PaperAdventure.java b/src/main/java/io/papermc/paper/adventure/PaperAdventure.java +index 22fe529890f34f66534c01248f654dc911b44c3b..6a1908d0eca04af885171cde44f419478048064e 100644 +--- a/src/main/java/io/papermc/paper/adventure/PaperAdventure.java ++++ b/src/main/java/io/papermc/paper/adventure/PaperAdventure.java +@@ -149,6 +149,10 @@ public final class PaperAdventure { + + // Key + ++ public static Key asAdventure(final ResourceLocation key) { ++ return Key.key(key.getNamespace(), key.getPath()); // todo move in the right patch ++ } ++ + public static ResourceLocation asVanilla(final Key key) { + return ResourceLocation.fromNamespaceAndPath(key.namespace(), key.value()); + } diff --git a/src/main/java/io/papermc/paper/datacomponent/ComponentAdapter.java b/src/main/java/io/papermc/paper/datacomponent/ComponentAdapter.java new file mode 100644 -index 0000000000000000000000000000000000000000..2ce01dbcbd205625bae879af14e2c1a7d919b200 +index 0000000000000000000000000000000000000000..aa2fdf49b372ddf69467d013daea67fecebfe3c1 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/ComponentAdapter.java @@ -0,0 +1,36 @@ +package io.papermc.paper.datacomponent; + +import java.util.function.Function; -+import com.mojang.serialization.JavaOps; +import net.minecraft.core.component.DataComponentType; +import net.minecraft.core.registries.BuiltInRegistries; ++import net.minecraft.util.NullOps; +import net.minecraft.util.Unit; +import org.bukkit.craftbukkit.CraftRegistry; + @@ -37,7 +52,7 @@ index 0000000000000000000000000000000000000000..2ce01dbcbd205625bae879af14e2c1a7 + public NMS toVanilla(final API value) { + NMS nms = this.apiToVanilla.apply(value); + if (this.codecValidation) { -+ this.type().codec().encodeStart(CraftRegistry.getMinecraftRegistry().createSerializationContext(JavaOps.INSTANCE), nms).error().ifPresent(error -> { ++ this.type.codec().encodeStart(CraftRegistry.getMinecraftRegistry().createSerializationContext(NullOps.INSTANCE), nms).ifError(error -> { + throw new IllegalArgumentException("Failed to encode data component %s (%s)".formatted(BuiltInRegistries.DATA_COMPONENT_TYPE.getKey(this.type), error.message())); + }); + } @@ -51,14 +66,13 @@ index 0000000000000000000000000000000000000000..2ce01dbcbd205625bae879af14e2c1a7 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/ComponentAdapters.java b/src/main/java/io/papermc/paper/datacomponent/ComponentAdapters.java new file mode 100644 -index 0000000000000000000000000000000000000000..852f456048940e07189810b4591b2a566b63a5f2 +index 0000000000000000000000000000000000000000..cfec3010fa978aef047ce619315d430461205c9b --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/ComponentAdapters.java -@@ -0,0 +1,186 @@ +@@ -0,0 +1,167 @@ +package io.papermc.paper.datacomponent; + +import com.mojang.brigadier.exceptions.CommandSyntaxException; -+import com.mojang.serialization.JavaOps; +import io.papermc.paper.adventure.PaperAdventure; +import io.papermc.paper.datacomponent.item.PaperBannerPatternLayers; +import io.papermc.paper.datacomponent.item.PaperBlockItemDataProperties; @@ -79,7 +93,7 @@ index 0000000000000000000000000000000000000000..852f456048940e07189810b4591b2a56 +import io.papermc.paper.datacomponent.item.PaperLockCode; +import io.papermc.paper.datacomponent.item.PaperLodestoneTracker; +import io.papermc.paper.datacomponent.item.PaperMapDecorations; -+import io.papermc.paper.datacomponent.item.PaperMapID; ++import io.papermc.paper.datacomponent.item.PaperMapId; +import io.papermc.paper.datacomponent.item.PaperMapItemColor; +import io.papermc.paper.datacomponent.item.PaperPotDecorations; +import io.papermc.paper.datacomponent.item.PaperPotionContents; @@ -89,20 +103,15 @@ index 0000000000000000000000000000000000000000..852f456048940e07189810b4591b2a56 +import io.papermc.paper.datacomponent.item.PaperUnbreakable; +import io.papermc.paper.datacomponent.item.PaperWritableBookContent; +import io.papermc.paper.datacomponent.item.PaperWrittenBookContent; -+import java.util.ArrayList; -+import java.util.Collections; +import java.util.HashMap; -+import java.util.List; +import java.util.Map; +import java.util.function.Function; -+import net.kyori.adventure.key.Key; +import net.minecraft.core.component.DataComponentType; +import net.minecraft.core.component.DataComponents; +import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.nbt.CompoundTag; +import net.minecraft.nbt.Tag; +import net.minecraft.resources.ResourceKey; -+import net.minecraft.resources.ResourceLocation; +import net.minecraft.util.Unit; +import net.minecraft.world.item.Rarity; +import net.minecraft.world.item.component.CustomData; @@ -110,12 +119,13 @@ index 0000000000000000000000000000000000000000..852f456048940e07189810b4591b2a56 +import org.bukkit.DyeColor; +import org.bukkit.craftbukkit.CraftMusicInstrument; +import org.bukkit.craftbukkit.inventory.CraftMetaFirework; -+import org.bukkit.craftbukkit.util.CraftNamespacedKey; +import org.bukkit.craftbukkit.util.Handleable; +import org.bukkit.inventory.ItemRarity; +import org.checkerframework.checker.nullness.qual.NonNull; +import org.checkerframework.framework.qual.DefaultQualifier; + ++import static io.papermc.paper.datacomponent.ComponentUtils.transform; ++ +@DefaultQualifier(NonNull.class) +public final class ComponentAdapters { + @@ -163,7 +173,7 @@ index 0000000000000000000000000000000000000000..852f456048940e07189810b4591b2a56 + register(DataComponents.STORED_ENCHANTMENTS, PaperItemEnchantments::new); + register(DataComponents.DYED_COLOR, PaperDyedItemColor::new); + register(DataComponents.MAP_COLOR, PaperMapItemColor::new); -+ register(DataComponents.MAP_ID, PaperMapID::new); ++ register(DataComponents.MAP_ID, PaperMapId::new); + register(DataComponents.MAP_DECORATIONS, PaperMapDecorations::new); + register(DataComponents.MAP_POST_PROCESSING, nms -> io.papermc.paper.item.MapPostProcessing.valueOf(nms.name()), api -> MapPostProcessing.valueOf(api.name())); + register(DataComponents.CHARGED_PROJECTILES, PaperChargedProjectiles::new); @@ -180,26 +190,12 @@ index 0000000000000000000000000000000000000000..852f456048940e07189810b4591b2a56 + register(DataComponents.INSTRUMENT, CraftMusicInstrument::minecraftHolderToBukkit, CraftMusicInstrument::bukkitToMinecraftHolder); + registerIdentity(DataComponents.OMINOUS_BOTTLE_AMPLIFIER); + register(DataComponents.JUKEBOX_PLAYABLE, PaperJukeboxPlayable::new); -+ register(DataComponents.RECIPES, nms -> { -+ final List<Key> api = new ArrayList<>(nms.size()); -+ for (final ResourceLocation location : nms) { -+ api.add(CraftNamespacedKey.fromMinecraft(location)); -+ } -+ -+ return Collections.unmodifiableList(api); -+ }, api -> { -+ final List<ResourceLocation> nms = new ArrayList<>(api.size()); -+ for (final Key key : api) { -+ nms.add(PaperAdventure.asVanilla(key)); -+ } -+ -+ return Collections.unmodifiableList(nms); -+ }); ++ register(DataComponents.RECIPES, nms -> transform(nms, PaperAdventure::asAdventure), api -> transform(api, PaperAdventure::asVanilla)); + register(DataComponents.LODESTONE_TRACKER, PaperLodestoneTracker::new); + register(DataComponents.FIREWORK_EXPLOSION, CraftMetaFirework::getEffect, CraftMetaFirework::getExplosion); + register(DataComponents.FIREWORKS, PaperFireworks::new); + register(DataComponents.PROFILE, PaperResolvableProfile::new); -+ register(DataComponents.NOTE_BLOCK_SOUND, CraftNamespacedKey::fromMinecraft, CraftNamespacedKey::toMinecraft); ++ register(DataComponents.NOTE_BLOCK_SOUND, PaperAdventure::asAdventure, PaperAdventure::asVanilla); + register(DataComponents.BANNER_PATTERNS, PaperBannerPatternLayers::new); + register(DataComponents.BASE_COLOR, nms -> DyeColor.getByWoolData((byte) nms.getId()), api -> net.minecraft.world.item.DyeColor.byId(api.getWoolData())); + register(DataComponents.POT_DECORATIONS, PaperPotDecorations::new); @@ -280,23 +276,21 @@ index 0000000000000000000000000000000000000000..07e268941d95c315592e3464c3ea0802 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/PaperComponentType.java b/src/main/java/io/papermc/paper/datacomponent/PaperComponentType.java new file mode 100644 -index 0000000000000000000000000000000000000000..60bb87cc071d21e58615210e6b0b4dfe0dc9ea71 +index 0000000000000000000000000000000000000000..74e883d50477b3b4dabdcb674d95e92ea7b5e4c1 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/PaperComponentType.java -@@ -0,0 +1,119 @@ +@@ -0,0 +1,112 @@ +package io.papermc.paper.datacomponent; + +import java.util.Collections; +import java.util.HashSet; +import java.util.Set; -+import net.kyori.adventure.key.Key; +import net.minecraft.core.component.DataComponentMap; ++import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.core.registries.Registries; -+import net.minecraft.resources.ResourceKey; +import org.bukkit.NamespacedKey; +import org.bukkit.Registry; +import org.bukkit.craftbukkit.CraftRegistry; -+import org.bukkit.craftbukkit.util.CraftNamespacedKey; +import org.bukkit.craftbukkit.util.Handleable; +import org.checkerframework.checker.nullness.qual.NonNull; +import org.checkerframework.checker.nullness.qual.Nullable; @@ -350,13 +344,8 @@ index 0000000000000000000000000000000000000000..60bb87cc071d21e58615210e6b0b4dfe + } + + @Override -+ public Key key() { -+ return this.key; -+ } -+ -+ @Override + public boolean isPersistent() { -+ return !this.getHandle().isTransient(); ++ return !this.type.isTransient(); + } + + public ComponentAdapter<NMS, T> getAdapter() { @@ -370,7 +359,7 @@ index 0000000000000000000000000000000000000000..60bb87cc071d21e58615210e6b0b4dfe + + @SuppressWarnings("unchecked") + public static <NMS> DataComponentType of(final NamespacedKey key, final net.minecraft.core.component.DataComponentType<NMS> type) { -+ final ComponentAdapter<NMS, ?> adapter = (ComponentAdapter<NMS, ?>) ComponentAdapters.ADAPTERS.get(ResourceKey.create(Registries.DATA_COMPONENT_TYPE, CraftNamespacedKey.toMinecraft(key))); ++ final ComponentAdapter<NMS, ?> adapter = (ComponentAdapter<NMS, ?>) ComponentAdapters.ADAPTERS.get(BuiltInRegistries.DATA_COMPONENT_TYPE.getResourceKey(type).orElseThrow()); + if (adapter == null) { + throw new IllegalArgumentException("No adapter found for " + key); + } @@ -405,12 +394,13 @@ index 0000000000000000000000000000000000000000..60bb87cc071d21e58615210e6b0b4dfe +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/ComponentTypesBridgesImpl.java b/src/main/java/io/papermc/paper/datacomponent/item/ComponentTypesBridgesImpl.java new file mode 100644 -index 0000000000000000000000000000000000000000..c21519941b82788733d541bd114e8b0ea12024bc +index 0000000000000000000000000000000000000000..9025c842daaf93f436b70c44494ff3875e56fd73 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/ComponentTypesBridgesImpl.java -@@ -0,0 +1,178 @@ +@@ -0,0 +1,184 @@ +package io.papermc.paper.datacomponent.item; + ++import com.destroystokyo.paper.profile.PlayerProfile; +import io.papermc.paper.registry.set.RegistryKeySet; +import io.papermc.paper.util.Filtered; +import net.kyori.adventure.key.Key; @@ -498,8 +488,8 @@ index 0000000000000000000000000000000000000000..c21519941b82788733d541bd114e8b0e + } + + @Override -+ public MapID.Builder mapId() { -+ return new PaperMapID.BuilderImpl(); ++ public MapId.Builder mapId() { ++ return new PaperMapId.BuilderImpl(); + } + + @Override @@ -533,8 +523,8 @@ index 0000000000000000000000000000000000000000..c21519941b82788733d541bd114e8b0e + } + + @Override -+ public Tool.Rule rule(final RegistryKeySet<BlockType> blockTypes, final @Nullable Float speed, final TriState correctForDrops) { -+ return PaperItemTool.PaperRule.fromUnsafe(blockTypes, speed, correctForDrops); ++ public Tool.Rule rule(final RegistryKeySet<BlockType> blocks, final @Nullable Float speed, final TriState correctForDrops) { ++ return PaperItemTool.PaperRule.fromUnsafe(blocks, speed, correctForDrops); + } + + @Override @@ -573,6 +563,11 @@ index 0000000000000000000000000000000000000000..c21519941b82788733d541bd114e8b0e + } + + @Override ++ public ResolvableProfile resolvableProfile(final PlayerProfile profile) { ++ return PaperResolvableProfile.toApi(profile); ++ } ++ ++ @Override + public BannerPatternLayers.Builder bannerPatternLayers() { + return new PaperBannerPatternLayers.BuilderImpl(); + } @@ -589,12 +584,13 @@ index 0000000000000000000000000000000000000000..c21519941b82788733d541bd114e8b0e +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperBannerPatternLayers.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperBannerPatternLayers.java new file mode 100644 -index 0000000000000000000000000000000000000000..e8e602f99c718c8939ce71aa2aad57a06f373c94 +index 0000000000000000000000000000000000000000..dbc03f95a46bd4c10c6f4177ffc5b6f3d3113aa3 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperBannerPatternLayers.java -@@ -0,0 +1,62 @@ +@@ -0,0 +1,63 @@ +package io.papermc.paper.datacomponent.item; + ++import java.util.Collection; +import java.util.List; +import java.util.Optional; +import org.bukkit.DyeColor; @@ -621,7 +617,7 @@ index 0000000000000000000000000000000000000000..e8e602f99c718c8939ce71aa2aad57a0 + private static List<Pattern> convert(final net.minecraft.world.level.block.entity.BannerPatternLayers nmsPatterns) { + return transform(nmsPatterns.layers(), input -> { + final Optional<PatternType> type = CraftRegistry.unwrapAndConvertHolder(org.bukkit.Registry.BANNER_PATTERN, input.pattern()); -+ return new Pattern(DyeColor.getByWoolData((byte) input.color().getId()), type.orElseThrow(() -> new IllegalStateException("Custom banner are not supported yet in the API!"))); ++ return new Pattern(DyeColor.getByWoolData((byte) input.color().getId()), type.orElseThrow(() -> new IllegalStateException("Custom banner patterns are not supported yet in the API!"))); + }); + } + @@ -644,7 +640,7 @@ index 0000000000000000000000000000000000000000..e8e602f99c718c8939ce71aa2aad57a0 + } + + @Override -+ public BannerPatternLayers.Builder addAll(final List<Pattern> patterns) { ++ public BannerPatternLayers.Builder addAll(final Collection<Pattern> patterns) { + patterns.forEach(this::add); + return this; + } @@ -718,13 +714,14 @@ index 0000000000000000000000000000000000000000..09335d46724831478fe396905a0f8d21 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperBundleContents.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperBundleContents.java new file mode 100644 -index 0000000000000000000000000000000000000000..7eb80089785a8c28db046402d52326ffab695e4d +index 0000000000000000000000000000000000000000..6c8b0d5cd0f043f6f8d694d0a2577457ab0273c5 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperBundleContents.java -@@ -0,0 +1,51 @@ +@@ -0,0 +1,52 @@ +package io.papermc.paper.datacomponent.item; + +import java.util.ArrayList; ++import java.util.Collection; +import java.util.List; +import com.google.common.base.Preconditions; +import org.bukkit.craftbukkit.inventory.CraftItemStack; @@ -756,13 +753,13 @@ index 0000000000000000000000000000000000000000..7eb80089785a8c28db046402d52326ff + + @Override + public BundleContents.Builder add(final ItemStack stack) { -+ Preconditions.checkArgument(!stack.isEmpty(), "Item stack cannot be empty!"); ++ Preconditions.checkArgument(!stack.isEmpty(), "stack cannot be empty"); + this.items.add(CraftItemStack.asNMSCopy(stack)); + return this; + } + + @Override -+ public BundleContents.Builder addAll(final List<ItemStack> stacks) { ++ public BundleContents.Builder addAll(final Collection<ItemStack> stacks) { + stacks.forEach(this::add); + return this; + } @@ -775,13 +772,14 @@ index 0000000000000000000000000000000000000000..7eb80089785a8c28db046402d52326ff +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperChargedProjectiles.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperChargedProjectiles.java new file mode 100644 -index 0000000000000000000000000000000000000000..080281b2feb577b0d9c9b342dda81352dd0fb922 +index 0000000000000000000000000000000000000000..176420df726deddfe635d9aa2a10b3152e759e8e --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperChargedProjectiles.java -@@ -0,0 +1,51 @@ +@@ -0,0 +1,52 @@ +package io.papermc.paper.datacomponent.item; + +import java.util.ArrayList; ++import java.util.Collection; +import java.util.List; +import com.google.common.base.Preconditions; +import org.bukkit.craftbukkit.inventory.CraftItemStack; @@ -813,13 +811,13 @@ index 0000000000000000000000000000000000000000..080281b2feb577b0d9c9b342dda81352 + + @Override + public ChargedProjectiles.Builder add(final ItemStack stack) { -+ Preconditions.checkArgument(!stack.isEmpty(), "Item stack cannot be empty!"); ++ Preconditions.checkArgument(!stack.isEmpty(), "stack cannot be empty"); + this.items.add(CraftItemStack.asNMSCopy(stack)); + return this; + } + + @Override -+ public ChargedProjectiles.Builder addAll(final List<ItemStack> stacks) { ++ public ChargedProjectiles.Builder addAll(final Collection<ItemStack> stacks) { + stacks.forEach(this::add); + return this; + } @@ -832,7 +830,7 @@ index 0000000000000000000000000000000000000000..080281b2feb577b0d9c9b342dda81352 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperCustomModelData.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperCustomModelData.java new file mode 100644 -index 0000000000000000000000000000000000000000..88f9697d3beda288c3e02b571753c1244f7c5e58 +index 0000000000000000000000000000000000000000..d406a222776293944486197239a57b4fdbac8484 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperCustomModelData.java @@ -0,0 +1,37 @@ @@ -862,7 +860,7 @@ index 0000000000000000000000000000000000000000..88f9697d3beda288c3e02b571753c124 + private int data; + + @Override -+ public CustomModelData.Builder customModelData(final int data) { ++ public CustomModelData.Builder data(final int data) { + this.data = data; + return this; + } @@ -936,14 +934,15 @@ index 0000000000000000000000000000000000000000..ff2a81366fcd554451e9b2aa438e9277 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperFireworks.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperFireworks.java new file mode 100644 -index 0000000000000000000000000000000000000000..605728447636c2a721d6e7c340900c8a8f4eaeb0 +index 0000000000000000000000000000000000000000..32bc904d2140ce5da2c5005722aba38ba5c85486 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperFireworks.java -@@ -0,0 +1,80 @@ +@@ -0,0 +1,81 @@ +package io.papermc.paper.datacomponent.item; + +import com.google.common.base.Preconditions; +import java.util.ArrayList; ++import java.util.Collection; +import java.util.List; +import net.minecraft.world.item.component.FireworkExplosion; +import org.bukkit.FireworkEffect; @@ -985,13 +984,13 @@ index 0000000000000000000000000000000000000000..605728447636c2a721d6e7c340900c8a + + @Override + public Fireworks.Builder flightDuration(final int duration) { -+ Preconditions.checkArgument(duration >= 0 && duration <= 0xFF, "duration must be an unsigned byte ([%s, %s]) but was %s", 0, 0xFF, duration); ++ Preconditions.checkArgument(duration >= 0 && duration <= 0xFF, "duration must be an unsigned byte ([%s, %s]), was %s", 0, 0xFF, duration); + this.duration = duration; + return this; + } + + @Override -+ public Fireworks.Builder add(final FireworkEffect effect) { ++ public Fireworks.Builder addEffect(final FireworkEffect effect) { + Preconditions.checkArgument( + this.effects.size() + 1 <= net.minecraft.world.item.component.Fireworks.MAX_EXPLOSIONS, + "Cannot have more than %s effects, had %s", @@ -1003,7 +1002,7 @@ index 0000000000000000000000000000000000000000..605728447636c2a721d6e7c340900c8a + } + + @Override -+ public Fireworks.Builder addAll(final List<FireworkEffect> effects) { ++ public Fireworks.Builder addEffects(final Collection<FireworkEffect> effects) { + Preconditions.checkArgument( + this.effects.size() + effects.size() <= net.minecraft.world.item.component.Fireworks.MAX_EXPLOSIONS, + "Cannot have more than %s effects, had %s", @@ -1022,14 +1021,15 @@ index 0000000000000000000000000000000000000000..605728447636c2a721d6e7c340900c8a +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperFoodProperties.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperFoodProperties.java new file mode 100644 -index 0000000000000000000000000000000000000000..7b210b4172fbc78adaae52602045eef40701a98d +index 0000000000000000000000000000000000000000..c3057183a3ab5ed6a26c73dca63c20a66ee91ca4 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperFoodProperties.java -@@ -0,0 +1,153 @@ +@@ -0,0 +1,154 @@ +package io.papermc.paper.datacomponent.item; + +import com.google.common.base.Preconditions; +import java.util.ArrayList; ++import java.util.Collection; +import java.util.List; +import java.util.Optional; +import org.bukkit.craftbukkit.inventory.CraftItemStack; @@ -1149,7 +1149,7 @@ index 0000000000000000000000000000000000000000..7b210b4172fbc78adaae52602045eef4 + + @Override + public FoodProperties.Builder usingConvertsTo(final @Nullable ItemStack stack) { -+ Preconditions.checkArgument(stack == null || !stack.isEmpty(), "Item stack cannot be empty!"); ++ Preconditions.checkArgument(stack == null || !stack.isEmpty(), "stack cannot be empty"); + this.convertedStack = stack; + return this; + } @@ -1161,7 +1161,7 @@ index 0000000000000000000000000000000000000000..7b210b4172fbc78adaae52602045eef4 + } + + @Override -+ public FoodProperties.Builder addAllEffects(final List<PossibleEffect> effects) { ++ public FoodProperties.Builder addEffects(final Collection<PossibleEffect> effects) { + addAndConvert(this.possibleEffects, effects, effect -> ((PossibleEffectImpl) effect).possibleEffect()); + return this; + } @@ -1181,7 +1181,7 @@ index 0000000000000000000000000000000000000000..7b210b4172fbc78adaae52602045eef4 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperItemAdventurePredicate.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemAdventurePredicate.java new file mode 100644 -index 0000000000000000000000000000000000000000..2bf2540e1ef88d8e20c0182bd794a09f5819aa53 +index 0000000000000000000000000000000000000000..2984b9026b3c4b5a254fe9db0e829bfb0b69d13c --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemAdventurePredicate.java @@ -0,0 +1,77 @@ @@ -1214,7 +1214,7 @@ index 0000000000000000000000000000000000000000..2bf2540e1ef88d8e20c0182bd794a09f + + private static List<BlockPredicate> convert(final net.minecraft.world.item.AdventureModePredicate nmsModifiers) { + return transform(nmsModifiers.predicates, nms -> BlockPredicate.predicate() -+ .blocks(nms.blocks().map(holders -> PaperRegistrySets.convertToApi(RegistryKey.BLOCK, holders)).orElse(null)).build()); ++ .blocks(nms.blocks().map(blocks -> PaperRegistrySets.convertToApi(RegistryKey.BLOCK, blocks)).orElse(null)).build()); + } + + @Override @@ -1264,10 +1264,10 @@ index 0000000000000000000000000000000000000000..2bf2540e1ef88d8e20c0182bd794a09f +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperItemArmorTrim.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemArmorTrim.java new file mode 100644 -index 0000000000000000000000000000000000000000..861de65b528844756d2c1cea085768858bc50328 +index 0000000000000000000000000000000000000000..8a288e339d50853852062f63290f696d3f55db0a --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemArmorTrim.java -@@ -0,0 +1,65 @@ +@@ -0,0 +1,64 @@ +package io.papermc.paper.datacomponent.item; + +import org.bukkit.craftbukkit.inventory.trim.CraftTrimMaterial; @@ -1325,8 +1325,7 @@ index 0000000000000000000000000000000000000000..861de65b528844756d2c1cea08576885 + + @Override + public ItemArmorTrim build() { -+ return new PaperItemArmorTrim( -+ new net.minecraft.world.item.armortrim.ArmorTrim( ++ return new PaperItemArmorTrim(new net.minecraft.world.item.armortrim.ArmorTrim( + CraftTrimMaterial.bukkitToMinecraftHolder(this.armorTrim.getMaterial()), + CraftTrimPattern.bukkitToMinecraftHolder(this.armorTrim.getPattern()) + ).withTooltip(this.showInTooltip)); @@ -1335,10 +1334,10 @@ index 0000000000000000000000000000000000000000..861de65b528844756d2c1cea08576885 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperItemAttributeModifiers.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemAttributeModifiers.java new file mode 100644 -index 0000000000000000000000000000000000000000..78867991f5075005725307d16ed2c8487e0e7b7e +index 0000000000000000000000000000000000000000..73ba3225fd5d13bc2d1849ff083e603a678f8c12 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemAttributeModifiers.java -@@ -0,0 +1,96 @@ +@@ -0,0 +1,97 @@ +package io.papermc.paper.datacomponent.item; + +import com.google.common.base.Preconditions; @@ -1398,18 +1397,19 @@ index 0000000000000000000000000000000000000000..78867991f5075005725307d16ed2c848 + private boolean showInTooltip = net.minecraft.world.item.component.ItemAttributeModifiers.EMPTY.showInTooltip(); + + @Override -+ public ItemAttributeModifiers.Builder addModifier(final Attribute attribute, final AttributeModifier attributeModifier) { ++ public ItemAttributeModifiers.Builder addModifier(final Attribute attribute, final AttributeModifier modifier) { + Preconditions.checkArgument( + this.entries.stream().noneMatch(e -> -+ e.modifier().id().equals(CraftNamespacedKey.toMinecraft(attributeModifier.getKey())) && e.attribute().is(CraftNamespacedKey.toMinecraft(attribute.getKey()))), ++ e.modifier().id().equals(CraftNamespacedKey.toMinecraft(modifier.getKey())) && e.attribute().is(CraftNamespacedKey.toMinecraft(attribute.getKey())) ++ ), + "Cannot add 2 modifiers with identical keys on the same attribute (modifier %s for attribute %s)", -+ attributeModifier.getKey(), attribute.getKey() ++ modifier.getKey(), attribute.getKey() + ); + + this.entries.add(new net.minecraft.world.item.component.ItemAttributeModifiers.Entry( + CraftAttribute.bukkitToMinecraftHolder(attribute), -+ CraftAttributeInstance.convert(attributeModifier), -+ CraftEquipmentSlot.getNMSGroup(attributeModifier.getSlotGroup()) ++ CraftAttributeInstance.convert(modifier), ++ CraftEquipmentSlot.getNMSGroup(modifier.getSlotGroup()) + )); + return this; + } @@ -1437,14 +1437,15 @@ index 0000000000000000000000000000000000000000..78867991f5075005725307d16ed2c848 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperItemContainerContents.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemContainerContents.java new file mode 100644 -index 0000000000000000000000000000000000000000..967da68950438b489a6e816eab94e58ffd316da7 +index 0000000000000000000000000000000000000000..acc28103e0951e1b537a487737083bdf834065e1 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemContainerContents.java -@@ -0,0 +1,63 @@ +@@ -0,0 +1,64 @@ +package io.papermc.paper.datacomponent.item; + +import com.google.common.base.Preconditions; +import java.util.ArrayList; ++import java.util.Collection; +import java.util.List; +import org.bukkit.craftbukkit.inventory.CraftItemStack; +import org.bukkit.craftbukkit.util.Handleable; @@ -1487,7 +1488,7 @@ index 0000000000000000000000000000000000000000..967da68950438b489a6e816eab94e58f + } + + @Override -+ public ItemContainerContents.Builder addAll(final List<ItemStack> stacks) { ++ public ItemContainerContents.Builder addAll(final Collection<ItemStack> stacks) { + Preconditions.checkArgument( + this.items.size() + stacks.size() <= net.minecraft.world.item.component.ItemContainerContents.MAX_SIZE, + "Cannot have more than %s items, had %s", @@ -1506,10 +1507,10 @@ index 0000000000000000000000000000000000000000..967da68950438b489a6e816eab94e58f +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperItemEnchantments.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemEnchantments.java new file mode 100644 -index 0000000000000000000000000000000000000000..47793f7b41850b982646e16485568dc7bdad0d9c +index 0000000000000000000000000000000000000000..9b3f83ca21a056aade6bbc44f6d46f49952a7c7d --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemEnchantments.java -@@ -0,0 +1,93 @@ +@@ -0,0 +1,94 @@ +package io.papermc.paper.datacomponent.item; + +import com.google.common.base.Preconditions; @@ -1563,13 +1564,13 @@ index 0000000000000000000000000000000000000000..47793f7b41850b982646e16485568dc7 + static final class BuilderImpl implements ItemEnchantments.Builder { + + private final Map<Enchantment, Integer> enchantments = new HashMap<>(); -+ private boolean showInTooltip = true; // use default from codec ++ private boolean showInTooltip = true; + + @Override + public ItemEnchantments.Builder add(final Enchantment enchantment, final int level) { + Preconditions.checkArgument( + level >= 1 && level <= net.minecraft.world.item.enchantment.Enchantment.MAX_LEVEL, -+ "level must be included in [%s, %s], but was %s", ++ "level must be between %s and %s, was %s", + 1, net.minecraft.world.item.enchantment.Enchantment.MAX_LEVEL, + level + ); @@ -1591,11 +1592,12 @@ index 0000000000000000000000000000000000000000..47793f7b41850b982646e16485568dc7 + + @Override + public ItemEnchantments build() { ++ net.minecraft.world.item.enchantment.ItemEnchantments initialEnchantments = net.minecraft.world.item.enchantment.ItemEnchantments.EMPTY.withTooltip(this.showInTooltip); + if (this.enchantments.isEmpty()) { -+ return new PaperItemEnchantments(net.minecraft.world.item.enchantment.ItemEnchantments.EMPTY.withTooltip(this.showInTooltip)); ++ return new PaperItemEnchantments(initialEnchantments); + } -+ final net.minecraft.world.item.enchantment.ItemEnchantments.Mutable mutable = new net.minecraft.world.item.enchantment.ItemEnchantments.Mutable(net.minecraft.world.item.enchantment.ItemEnchantments.EMPTY); -+ mutable.showInTooltip = this.showInTooltip; ++ ++ final net.minecraft.world.item.enchantment.ItemEnchantments.Mutable mutable = new net.minecraft.world.item.enchantment.ItemEnchantments.Mutable(initialEnchantments); + this.enchantments.forEach((enchantment, level) -> { + mutable.set(CraftEnchantment.bukkitToMinecraftHolder(enchantment), level); + }); @@ -1605,10 +1607,10 @@ index 0000000000000000000000000000000000000000..47793f7b41850b982646e16485568dc7 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperItemLore.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemLore.java new file mode 100644 -index 0000000000000000000000000000000000000000..041eb21f9d5a3549ce6f27cbfe7cdf2e32c4671e +index 0000000000000000000000000000000000000000..b508a8b441055bba0704619444cd9ffc37a30807 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemLore.java -@@ -0,0 +1,85 @@ +@@ -0,0 +1,80 @@ +package io.papermc.paper.datacomponent.item; + +import com.google.common.base.Preconditions; @@ -1648,38 +1650,33 @@ index 0000000000000000000000000000000000000000..041eb21f9d5a3549ce6f27cbfe7cdf2e + + private List<Component> lines = new ArrayList<>(); + -+ @Override -+ public ItemLore.Builder lines(final List<? extends ComponentLike> lines) { ++ private static void validateLineCount(final int current, final int add) { ++ final int newSize = current + add; + Preconditions.checkArgument( -+ lines.size() <= net.minecraft.world.item.component.ItemLore.MAX_LINES, ++ newSize <= net.minecraft.world.item.component.ItemLore.MAX_LINES, + "Cannot have more than %s lines, had %s", + net.minecraft.world.item.component.ItemLore.MAX_LINES, -+ lines.size() ++ newSize + ); ++ } ++ ++ @Override ++ public ItemLore.Builder lines(final List<? extends ComponentLike> lines) { ++ validateLineCount(0, lines.size()); + this.lines = new ArrayList<>(ComponentLike.asComponents(lines)); + return this; + } + + @Override + public ItemLore.Builder addLine(final ComponentLike line) { -+ Preconditions.checkArgument( -+ this.lines.size() + 1 <= net.minecraft.world.item.component.ItemLore.MAX_LINES, -+ "Cannot have more than %s lines, had %s", -+ net.minecraft.world.item.component.ItemLore.MAX_LINES, -+ this.lines.size() + 1 -+ ); ++ validateLineCount(this.lines.size(), 1); + this.lines.add(line.asComponent()); + return this; + } + + @Override -+ public ItemLore.Builder addAllLines(final @NonNull List<? extends ComponentLike> lines) { -+ Preconditions.checkArgument( -+ this.lines.size() + lines.size() <= net.minecraft.world.item.component.ItemLore.MAX_LINES, -+ "Cannot have more than %s lines, had %s", -+ net.minecraft.world.item.component.ItemLore.MAX_LINES, -+ this.lines.size() + lines.size() -+ ); ++ public ItemLore.Builder addLines(final @NonNull List<? extends ComponentLike> lines) { ++ validateLineCount(this.lines.size(), lines.size()); + this.lines.addAll(ComponentLike.asComponents(lines)); + return this; + } @@ -1696,13 +1693,14 @@ index 0000000000000000000000000000000000000000..041eb21f9d5a3549ce6f27cbfe7cdf2e +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperItemTool.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemTool.java new file mode 100644 -index 0000000000000000000000000000000000000000..35f12ebb9cb7dc222405de917b232a46a1afcade +index 0000000000000000000000000000000000000000..4d6b198aee85c9ae7747f270fe1c04282b61c6a5 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperItemTool.java -@@ -0,0 +1,103 @@ +@@ -0,0 +1,104 @@ +package io.papermc.paper.datacomponent.item; + +import java.util.ArrayList; ++import java.util.Collection; +import java.util.List; +import java.util.Optional; +import com.google.common.base.Preconditions; @@ -1726,12 +1724,12 @@ index 0000000000000000000000000000000000000000..35f12ebb9cb7dc222405de917b232a46 + List<Tool.Rule> rules +) implements Tool, Handleable<net.minecraft.world.item.component.Tool> { + -+ public PaperItemTool(final net.minecraft.world.item.component.Tool itemModifiers) { -+ this(itemModifiers, convert(itemModifiers)); ++ public PaperItemTool(final net.minecraft.world.item.component.Tool tool) { ++ this(tool, convert(tool)); + } + -+ private static List<Tool.Rule> convert(final net.minecraft.world.item.component.Tool nmsModifiers) { -+ return transform(nmsModifiers.rules(), nms -> new PaperRule( ++ private static List<Tool.Rule> convert(final net.minecraft.world.item.component.Tool tool) { ++ return transform(tool.rules(), nms -> new PaperRule( + PaperRegistrySets.convertToApi(RegistryKey.BLOCK, nms.blocks()), + nms.speed().orElse(null), + TriState.byBoolean(nms.correctForDrops().orElse(null)) @@ -1753,13 +1751,12 @@ index 0000000000000000000000000000000000000000..35f12ebb9cb7dc222405de917b232a46 + return this.impl.damagePerBlock(); + } + -+ + // TODO maybe move to API as package-private so they can create Entry objects? not sure if needed -+ record PaperRule(RegistryKeySet<BlockType> blockTypes, @Nullable Float speed, TriState correctForDrops) implements Rule { ++ record PaperRule(RegistryKeySet<BlockType> blocks, @Nullable Float speed, TriState correctForDrops) implements Rule { + -+ public static PaperRule fromUnsafe(RegistryKeySet<BlockType> blockTypes, @Nullable Float speed, TriState correctForDrops) { -+ Preconditions.checkArgument(speed == null || speed > 0, "Speed must be positive"); -+ return new PaperRule(blockTypes, speed, correctForDrops); ++ public static PaperRule fromUnsafe(final RegistryKeySet<BlockType> blocks, final @Nullable Float speed, final TriState correctForDrops) { ++ Preconditions.checkArgument(speed == null || speed > 0, "speed must be positive"); ++ return new PaperRule(blocks, speed, correctForDrops); + } + } + @@ -1771,20 +1768,21 @@ index 0000000000000000000000000000000000000000..35f12ebb9cb7dc222405de917b232a46 + + @Override + public Builder damagePerBlock(final int damage) { ++ Preconditions.checkArgument(damage >= 0, "damage must be non-negative, was %s", damage); + this.damage = damage; + return this; + } + + @Override -+ public Builder defaultMiningSpeed(final float speed) { -+ this.miningSpeed = speed; ++ public Builder defaultMiningSpeed(final float miningSpeed) { ++ this.miningSpeed = miningSpeed; + return this; + } + + @Override + public Builder addRule(final Rule rule) { + this.rules.add(new net.minecraft.world.item.component.Tool.Rule( -+ PaperRegistrySets.convertToNms(Registries.BLOCK, BuiltInRegistries.BUILT_IN_CONVERSIONS.lookup(), rule.blockTypes()), ++ PaperRegistrySets.convertToNms(Registries.BLOCK, BuiltInRegistries.BUILT_IN_CONVERSIONS.lookup(), rule.blocks()), + Optional.ofNullable(rule.speed()), + Optional.ofNullable(rule.correctForDrops().toBoolean()) + )); @@ -1792,7 +1790,7 @@ index 0000000000000000000000000000000000000000..35f12ebb9cb7dc222405de917b232a46 + } + + @Override -+ public Builder addRules(final List<Rule> rules) { ++ public Builder addRules(final Collection<Rule> rules) { + rules.forEach(this::addRule); + return this; + } @@ -1805,7 +1803,7 @@ index 0000000000000000000000000000000000000000..35f12ebb9cb7dc222405de917b232a46 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperJukeboxPlayable.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperJukeboxPlayable.java new file mode 100644 -index 0000000000000000000000000000000000000000..2abd5f1a78fb0335bc4ed2651c53eb1290f213f2 +index 0000000000000000000000000000000000000000..1afafbc43cbf1a0ce07b43ceeefdeaf9158da355 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperJukeboxPlayable.java @@ -0,0 +1,61 @@ @@ -1848,7 +1846,7 @@ index 0000000000000000000000000000000000000000..2abd5f1a78fb0335bc4ed2651c53eb12 + private JukeboxSong song; + private boolean showInTooltip = true; + -+ public BuilderImpl(JukeboxSong song) { ++ BuilderImpl(JukeboxSong song) { + this.song = song; + } + @@ -1872,7 +1870,7 @@ index 0000000000000000000000000000000000000000..2abd5f1a78fb0335bc4ed2651c53eb12 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperLockCode.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperLockCode.java new file mode 100644 -index 0000000000000000000000000000000000000000..0737a3d3ed9a325f0cf232278de0098d711032ab +index 0000000000000000000000000000000000000000..970d439bdfdb2e08f5ed0b004ba797729ef72beb --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperLockCode.java @@ -0,0 +1,40 @@ @@ -1899,20 +1897,20 @@ index 0000000000000000000000000000000000000000..0737a3d3ed9a325f0cf232278de0098d + + static final class BuilderImpl implements LockCode.Builder { + -+ private String lock = net.minecraft.world.LockCode.NO_LOCK.key(); ++ private String key = net.minecraft.world.LockCode.NO_LOCK.key(); + + @Override -+ public LockCode.Builder lock(final String code) { -+ this.lock = code; ++ public LockCode.Builder lock(final String key) { ++ this.key = key; + return this; + } + + @Override + public LockCode build() { -+ if (this.lock.isEmpty()) { ++ if (this.key.isEmpty()) { + return new PaperLockCode(net.minecraft.world.LockCode.NO_LOCK); + } -+ return new PaperLockCode(new net.minecraft.world.LockCode(this.lock)); ++ return new PaperLockCode(new net.minecraft.world.LockCode(this.key)); + } + } +} @@ -1982,14 +1980,15 @@ index 0000000000000000000000000000000000000000..7f3a2929203a1c681f89d7f8aab8e574 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperMapDecorations.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperMapDecorations.java new file mode 100644 -index 0000000000000000000000000000000000000000..90610ea3860e764f9e634bb81f952c1621269d1d +index 0000000000000000000000000000000000000000..9d0b5c44e290acc8692487021e924bb8c76e2341 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperMapDecorations.java -@@ -0,0 +1,90 @@ +@@ -0,0 +1,95 @@ +package io.papermc.paper.datacomponent.item; + +import java.util.HashMap; +import java.util.Map; ++import java.util.Set; +import org.bukkit.craftbukkit.map.CraftMapCursor; +import org.bukkit.craftbukkit.util.Handleable; +import org.bukkit.map.MapCursor; @@ -2019,8 +2018,9 @@ index 0000000000000000000000000000000000000000..90610ea3860e764f9e634bb81f952c16 + + @Override + public Map<String, DecorationEntry> getDecorations() { -+ Map<String, DecorationEntry> decorations = new HashMap<>(); -+ for (Map.Entry<String, net.minecraft.world.item.component.MapDecorations.Entry> entry : this.impl.decorations().entrySet()) { ++ Set<Map.Entry<String, net.minecraft.world.item.component.MapDecorations.Entry>> entries = this.impl.decorations().entrySet(); ++ Map<String, DecorationEntry> decorations = new HashMap<>(entries.size()); ++ for (Map.Entry<String, net.minecraft.world.item.component.MapDecorations.Entry> entry : entries) { + decorations.put(entry.getKey(), new PaperDecorationEntry(entry.getValue())); + } + @@ -2072,30 +2072,32 @@ index 0000000000000000000000000000000000000000..90610ea3860e764f9e634bb81f952c16 + + @Override + public MapDecorations build() { ++ if (this.effects.isEmpty()) { ++ return new PaperMapDecorations(net.minecraft.world.item.component.MapDecorations.EMPTY); ++ } + return new PaperMapDecorations(new net.minecraft.world.item.component.MapDecorations(this.effects)); + } + } +} -diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperMapID.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperMapID.java +diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperMapId.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperMapId.java new file mode 100644 -index 0000000000000000000000000000000000000000..e74819d2e8c3819419d5ddbe686fddf3cb030dd4 +index 0000000000000000000000000000000000000000..53db58f214fa60a1e3741d5b77f43602984a0c37 --- /dev/null -+++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperMapID.java -@@ -0,0 +1,38 @@ ++++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperMapId.java +@@ -0,0 +1,37 @@ +package io.papermc.paper.datacomponent.item; + -+import net.minecraft.world.level.saveddata.maps.MapId; +import org.bukkit.craftbukkit.util.Handleable; +import org.checkerframework.checker.nullness.qual.NonNull; +import org.checkerframework.framework.qual.DefaultQualifier; + +@DefaultQualifier(NonNull.class) -+public record PaperMapID( -+ MapId impl -+) implements MapID, Handleable<MapId> { ++public record PaperMapId( ++ net.minecraft.world.level.saveddata.maps.MapId impl ++) implements MapId, Handleable<net.minecraft.world.level.saveddata.maps.MapId> { + + @Override -+ public MapId getHandle() { ++ public net.minecraft.world.level.saveddata.maps.MapId getHandle() { + return this.impl; + } + @@ -2104,19 +2106,19 @@ index 0000000000000000000000000000000000000000..e74819d2e8c3819419d5ddbe686fddf3 + return this.impl.id(); + } + -+ static final class BuilderImpl implements MapID.Builder { ++ static final class BuilderImpl implements MapId.Builder { + + private int id = 0; + + @Override -+ public MapID.Builder mapId(final int id) { ++ public MapId.Builder id(final int id) { + this.id = id; + return this; + } + + @Override -+ public MapID build() { -+ return new PaperMapID(new MapId(this.id)); ++ public MapId build() { ++ return new PaperMapId(new net.minecraft.world.level.saveddata.maps.MapId(this.id)); + } + } +} @@ -2166,10 +2168,10 @@ index 0000000000000000000000000000000000000000..86c9366220bf0b31551d66751ade98bf +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperPotDecorations.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperPotDecorations.java new file mode 100644 -index 0000000000000000000000000000000000000000..3bf2538dff070f48b735bafe88a23e6ee22fbc6d +index 0000000000000000000000000000000000000000..be35ef33c9391ab766940bb7a98e191b73540360 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperPotDecorations.java -@@ -0,0 +1,87 @@ +@@ -0,0 +1,91 @@ +package io.papermc.paper.datacomponent.item; + +import com.google.common.base.Preconditions; @@ -2248,6 +2250,10 @@ index 0000000000000000000000000000000000000000..3bf2538dff070f48b735bafe88a23e6e + + @Override + public PotDecorations build() { ++ if (this.back == null && this.left == null && this.right == null && this.front == null) { ++ return new PaperPotDecorations(net.minecraft.world.level.block.entity.PotDecorations.EMPTY); ++ } ++ + return new PaperPotDecorations(new net.minecraft.world.level.block.entity.PotDecorations( + Optional.ofNullable(this.back).map(CraftItemType::bukkitToMinecraft), + Optional.ofNullable(this.left).map(CraftItemType::bukkitToMinecraft), @@ -2259,13 +2265,14 @@ index 0000000000000000000000000000000000000000..3bf2538dff070f48b735bafe88a23e6e +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperPotionContents.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperPotionContents.java new file mode 100644 -index 0000000000000000000000000000000000000000..ac8973d7f558bb1391e7f7eb665bfdfe0e6d1ca1 +index 0000000000000000000000000000000000000000..37b896d55a3aef7d1dfc01d85c7bb4df9ee1913e --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperPotionContents.java -@@ -0,0 +1,90 @@ +@@ -0,0 +1,91 @@ +package io.papermc.paper.datacomponent.item; + +import java.util.ArrayList; ++import java.util.Collection; +import java.util.List; +import java.util.Optional; +import net.minecraft.world.effect.MobEffectInstance; @@ -2315,13 +2322,13 @@ index 0000000000000000000000000000000000000000..ac8973d7f558bb1391e7f7eb665bfdfe + + static final class BuilderImpl implements PotionContents.Builder { + -+ private final List<MobEffectInstance> potionEffects = new ArrayList<>(); ++ private final List<MobEffectInstance> customEffects = new ArrayList<>(); + private @Nullable PotionType type; + private @Nullable Color color; + + @Override -+ public PotionContents.Builder potion(final @Nullable PotionType potionType) { -+ this.type = potionType; ++ public PotionContents.Builder potion(final @Nullable PotionType type) { ++ this.type = type; + return this; + } + @@ -2332,14 +2339,14 @@ index 0000000000000000000000000000000000000000..ac8973d7f558bb1391e7f7eb665bfdfe + } + + @Override -+ public PotionContents.Builder add(final PotionEffect potionEffect) { -+ this.potionEffects.add(CraftPotionUtil.fromBukkit(potionEffect)); ++ public PotionContents.Builder addCustomEffect(final PotionEffect effect) { ++ this.customEffects.add(CraftPotionUtil.fromBukkit(effect)); + return this; + } + + @Override -+ public PotionContents.Builder addAll(final List<PotionEffect> potionEffects) { -+ potionEffects.forEach(this::add); ++ public PotionContents.Builder addCustomEffects(final Collection<PotionEffect> effects) { ++ effects.forEach(this::addCustomEffect); + return this; + } + @@ -2348,17 +2355,17 @@ index 0000000000000000000000000000000000000000..ac8973d7f558bb1391e7f7eb665bfdfe + return new PaperPotionContents(new net.minecraft.world.item.alchemy.PotionContents( + Optional.ofNullable(this.type).map(CraftPotionType::bukkitToMinecraftHolder), + Optional.ofNullable(this.color).map(Color::asARGB), -+ this.potionEffects ++ this.customEffects + )); + } + } +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperResolvableProfile.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperResolvableProfile.java new file mode 100644 -index 0000000000000000000000000000000000000000..96f91e0b7718eda002eaf8714c21516aa6ffe5bf +index 0000000000000000000000000000000000000000..c5e2f645d05c73f2a6a7902c8c3aaa92816bcca3 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperResolvableProfile.java -@@ -0,0 +1,106 @@ +@@ -0,0 +1,109 @@ +package io.papermc.paper.datacomponent.item; + +import com.destroystokyo.paper.profile.CraftPlayerProfile; @@ -2368,7 +2375,6 @@ index 0000000000000000000000000000000000000000..96f91e0b7718eda002eaf8714c21516a +import com.mojang.authlib.properties.Property; +import com.mojang.authlib.properties.PropertyMap; +import java.util.Collection; -+import java.util.List; +import java.util.Optional; +import java.util.UUID; +import java.util.concurrent.CompletableFuture; @@ -2393,6 +2399,10 @@ index 0000000000000000000000000000000000000000..96f91e0b7718eda002eaf8714c21516a + ); + } + ++ static PaperResolvableProfile toApi(final PlayerProfile profile) { ++ return new PaperResolvableProfile(new net.minecraft.world.item.component.ResolvableProfile(CraftPlayerProfile.asAuthlibCopy(profile))); ++ } ++ + @Override + public net.minecraft.world.item.component.ResolvableProfile getHandle() { + return this.impl; @@ -2438,19 +2448,19 @@ index 0000000000000000000000000000000000000000..96f91e0b7718eda002eaf8714c21516a + @Override + public ResolvableProfile.Builder addProperty(final ProfileProperty property) { + // ProfileProperty constructor already has specific validations -+ final int newSize = this.propertyMap.size() + 1; // todo see below notice -+ Preconditions.checkArgument(newSize <= 16, "Cannot have more than 16 properties, was %s", newSize); -+ this.propertyMap.put(property.getName(), new Property(property.getName(), property.getValue(), property.getSignature())); ++ Property newProperty = new Property(property.getName(), property.getValue(), property.getSignature()); ++ if (!this.propertyMap.containsEntry(property.getName(), newProperty)) { // underlying map is a multimap that doesn't allow duplicate key-value pair ++ int newSize = this.propertyMap.size() + 1; ++ Preconditions.checkArgument(newSize <= 16, "Cannot have more than 16 properties, was %s", newSize); ++ } ++ ++ this.propertyMap.put(property.getName(), newProperty); + return this; + } + + @Override -+ public ResolvableProfile.Builder addAllProperties(final List<ProfileProperty> properties) { -+ final int newSize = this.propertyMap.size() + properties.size(); // todo this check is wrong for duplicate property key since this is a map not a list -+ Preconditions.checkArgument(newSize <= 16, "Cannot have more than 16 properties, was %s", newSize); -+ for (final ProfileProperty property : properties) { -+ this.propertyMap.put(property.getName(), new Property(property.getName(), property.getValue(), property.getSignature())); -+ } ++ public ResolvableProfile.Builder addProperties(final Collection<ProfileProperty> properties) { ++ properties.forEach(this::addProperty); + return this; + } + @@ -2534,14 +2544,15 @@ index 0000000000000000000000000000000000000000..c6a11cbe924926ec6d7ac1d69b5dacfb +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperSuspiciousStewEffects.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperSuspiciousStewEffects.java new file mode 100644 -index 0000000000000000000000000000000000000000..5113d65c36c64710b0d1668baa986a755a215d5a +index 0000000000000000000000000000000000000000..baf2d9ff2470ce71618f711c517ead5fc57da98f --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperSuspiciousStewEffects.java -@@ -0,0 +1,59 @@ +@@ -0,0 +1,60 @@ +package io.papermc.paper.datacomponent.item; + +import io.papermc.paper.potion.SuspiciousEffectEntry; +import java.util.ArrayList; ++import java.util.Collection; +import java.util.List; +import org.bukkit.craftbukkit.potion.CraftPotionEffectType; +import org.bukkit.craftbukkit.util.Handleable; @@ -2583,7 +2594,7 @@ index 0000000000000000000000000000000000000000..5113d65c36c64710b0d1668baa986a75 + } + + @Override -+ public Builder addAll(final List<SuspiciousEffectEntry> entries) { ++ public Builder addAll(final Collection<SuspiciousEffectEntry> entries) { + entries.forEach(this::add); + return this; + } @@ -2599,7 +2610,7 @@ index 0000000000000000000000000000000000000000..5113d65c36c64710b0d1668baa986a75 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperUnbreakable.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperUnbreakable.java new file mode 100644 -index 0000000000000000000000000000000000000000..f95ceec3e154772f0af9e51eac99dcd77a1beab8 +index 0000000000000000000000000000000000000000..2ff5004427766b0034595ddad04aac6bdfdcc279 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperUnbreakable.java @@ -0,0 +1,42 @@ @@ -2631,7 +2642,7 @@ index 0000000000000000000000000000000000000000..f95ceec3e154772f0af9e51eac99dcd7 + + static final class BuilderImpl implements Unbreakable.Builder { + -+ private boolean showInTooltip = true; // should match the default value in the Unbreakable codec ++ private boolean showInTooltip = true; + + @Override + public Unbreakable.Builder showInTooltip(final boolean showInTooltip) { @@ -2647,10 +2658,10 @@ index 0000000000000000000000000000000000000000..f95ceec3e154772f0af9e51eac99dcd7 +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperWritableBookContent.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperWritableBookContent.java new file mode 100644 -index 0000000000000000000000000000000000000000..e6336a7fd93c8bd6f9c3d63d48ce3c7d154a0d4b +index 0000000000000000000000000000000000000000..5a93339d747a1dc18688abddeffda69c5a63b4b3 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperWritableBookContent.java -@@ -0,0 +1,107 @@ +@@ -0,0 +1,111 @@ +package io.papermc.paper.datacomponent.item; + +import com.google.common.base.Preconditions; @@ -2752,6 +2763,10 @@ index 0000000000000000000000000000000000000000..e6336a7fd93c8bd6f9c3d63d48ce3c7d + + @Override + public WritableBookContent build() { ++ if (this.pages.isEmpty()) { ++ return new PaperWritableBookContent(net.minecraft.world.item.component.WritableBookContent.EMPTY); ++ } ++ + return new PaperWritableBookContent( + new net.minecraft.world.item.component.WritableBookContent(this.pages) + ); @@ -2760,7 +2775,7 @@ index 0000000000000000000000000000000000000000..e6336a7fd93c8bd6f9c3d63d48ce3c7d +} diff --git a/src/main/java/io/papermc/paper/datacomponent/item/PaperWrittenBookContent.java b/src/main/java/io/papermc/paper/datacomponent/item/PaperWrittenBookContent.java new file mode 100644 -index 0000000000000000000000000000000000000000..c4de9165c341d9aa860ddb13c3c2d743a2680e81 +index 0000000000000000000000000000000000000000..c9f5bffbe211c4cbedce0da3f1b7a873876c4d98 --- /dev/null +++ b/src/main/java/io/papermc/paper/datacomponent/item/PaperWrittenBookContent.java @@ -0,0 +1,190 @@ @@ -2890,9 +2905,9 @@ index 0000000000000000000000000000000000000000..c4de9165c341d9aa860ddb13c3c2d743 + @Override + public WrittenBookContent.Builder generation(final int generation) { + Preconditions.checkArgument( -+ generation <= net.minecraft.world.item.component.WrittenBookContent.MAX_GENERATION, -+ "Maximum generation is %s, was %s", -+ net.minecraft.world.item.component.WrittenBookContent.MAX_GENERATION, ++ generation >= 0 && generation <= net.minecraft.world.item.component.WrittenBookContent.MAX_GENERATION, ++ "generation must be between %s and %s, was %s", ++ 0, net.minecraft.world.item.component.WrittenBookContent.MAX_GENERATION, + generation + ); + this.generation = generation; @@ -2976,7 +2991,7 @@ index 9c0972023bc9be20ba81bbc2e1d6688b615760c0..7eb43862789ec1b37b658727e0fc7a99 // data-drivens entry(Registries.STRUCTURE, RegistryKey.STRUCTURE, Structure.class, CraftStructure::new).delayed(), diff --git a/src/main/java/net/minecraft/world/item/enchantment/ItemEnchantments.java b/src/main/java/net/minecraft/world/item/enchantment/ItemEnchantments.java -index 8ac485d82c2d2b32f4d54e02c18c2cb2c3df4fa4..4f15ec26c7512a6f2b9c14e108d582d33e41689b 100644 +index 8ac485d82c2d2b32f4d54e02c18c2cb2c3df4fa4..5b648e2df4624dadec8f9185901de579211813fe 100644 --- a/src/main/java/net/minecraft/world/item/enchantment/ItemEnchantments.java +++ b/src/main/java/net/minecraft/world/item/enchantment/ItemEnchantments.java @@ -60,7 +60,7 @@ public class ItemEnchantments implements TooltipProvider { @@ -2984,12 +2999,12 @@ index 8ac485d82c2d2b32f4d54e02c18c2cb2c3df4fa4..4f15ec26c7512a6f2b9c14e108d582d3 ItemEnchantments::new ); - final Object2IntAVLTreeMap<Holder<Enchantment>> enchantments; // Paper -+ public final Object2IntAVLTreeMap<Holder<Enchantment>> enchantments; // Paper - make public ++ final Object2IntAVLTreeMap<Holder<Enchantment>> enchantments; public final boolean showInTooltip; ItemEnchantments(Object2IntAVLTreeMap<Holder<Enchantment>> enchantments, boolean showInTooltip) { // Paper diff --git a/src/main/java/org/bukkit/craftbukkit/inventory/CraftItemStack.java b/src/main/java/org/bukkit/craftbukkit/inventory/CraftItemStack.java -index 32a41c8b324aad67b9dcf74387aef299e6478a64..8bc572919dfd04f477a5b6aa62ee6bd7710c8039 100644 +index 32a41c8b324aad67b9dcf74387aef299e6478a64..4bb3d717ca50feaa23394c3f21257fdc14852c49 100644 --- a/src/main/java/org/bukkit/craftbukkit/inventory/CraftItemStack.java +++ b/src/main/java/org/bukkit/craftbukkit/inventory/CraftItemStack.java @@ -192,7 +192,7 @@ public final class CraftItemStack extends ItemStack { @@ -3010,25 +3025,86 @@ index 32a41c8b324aad67b9dcf74387aef299e6478a64..8bc572919dfd04f477a5b6aa62ee6bd7 } // Paper start -@@ -364,7 +364,7 @@ public final class CraftItemStack extends ItemStack { - // Paper start - support updating profile after resolving it - final CraftMetaItem.Applicator tag = new CraftMetaItem.Applicator() { - @Override -- void skullCallback(final com.mojang.authlib.GameProfile gameProfile) { -+ public void skullCallback(final com.mojang.authlib.GameProfile gameProfile) { // Paper - itemStack.set(DataComponents.PROFILE, new net.minecraft.world.item.component.ResolvableProfile(gameProfile)); - } - }; -@@ -419,7 +419,7 @@ public final class CraftItemStack extends ItemStack { - // Paper start - support updating profile after resolving it - CraftMetaItem.Applicator tag = new CraftMetaItem.Applicator() { - @Override -- void skullCallback(final com.mojang.authlib.GameProfile gameProfile) { -+ public void skullCallback(final com.mojang.authlib.GameProfile gameProfile) { // Paper - item.set(DataComponents.PROFILE, new net.minecraft.world.item.component.ResolvableProfile(gameProfile)); - } - }; -@@ -539,4 +539,84 @@ public final class CraftItemStack extends ItemStack { +@@ -253,12 +253,14 @@ public final class CraftItemStack extends ItemStack { + public void addUnsafeEnchantment(Enchantment ench, int level) { + Preconditions.checkArgument(ench != null, "Enchantment cannot be null"); + +- // Paper start - Replace whole method +- final ItemMeta itemMeta = this.getItemMeta(); +- if (itemMeta != null) { +- itemMeta.addEnchant(ench, level, true); +- this.setItemMeta(itemMeta); ++ // Paper start ++ if (this.handle == null) { ++ return; + } ++ ++ EnchantmentHelper.updateEnchantments(this.handle, mutable -> { // data component api doesn't really support mutable things once already set yet ++ mutable.set(CraftEnchantment.bukkitToMinecraftHolder(ench), level); ++ }); + // Paper end + } + +@@ -288,27 +290,49 @@ public final class CraftItemStack extends ItemStack { + public int removeEnchantment(Enchantment ench) { + Preconditions.checkArgument(ench != null, "Enchantment cannot be null"); + +- // Paper start - replace entire method +- int level = getEnchantmentLevel(ench); +- if (level > 0) { +- final ItemMeta itemMeta = this.getItemMeta(); +- if (itemMeta == null) return 0; +- itemMeta.removeEnchant(ench); +- this.setItemMeta(itemMeta); ++ // Paper start ++ if (this.handle == null) { ++ return 0; ++ } ++ ++ ItemEnchantments itemEnchantments = this.handle.getOrDefault(DataComponents.ENCHANTMENTS, ItemEnchantments.EMPTY); ++ if (itemEnchantments.isEmpty()) { ++ return 0; ++ } ++ ++ Holder<net.minecraft.world.item.enchantment.Enchantment> removedEnchantment = CraftEnchantment.bukkitToMinecraftHolder(ench); ++ if (itemEnchantments.keySet().contains(removedEnchantment)) { ++ int previousLevel = itemEnchantments.getLevel(removedEnchantment); ++ ++ ItemEnchantments.Mutable mutable = new ItemEnchantments.Mutable(itemEnchantments); // data component api doesn't really support mutable things once already set yet ++ mutable.removeIf(enchantment -> enchantment.equals(removedEnchantment)); ++ this.handle.set(DataComponents.ENCHANTMENTS, mutable.toImmutable()); ++ return previousLevel; + } + // Paper end + +- return level; ++ return 0; + } + + @Override + public void removeEnchantments() { ++ // Paper start - fix NPE ++ if (this.handle == null) { ++ return; ++ } ++ // Paper end + this.handle.remove(DataComponents.ENCHANTMENTS); + } + + @Override + public Map<Enchantment, Integer> getEnchantments() { +- return this.hasItemMeta() ? this.getItemMeta().getEnchants() : ImmutableMap.<Enchantment, Integer>of(); // Paper - use Item Meta ++ // Paper start ++ io.papermc.paper.datacomponent.item.ItemEnchantments itemEnchantments = this.getData(io.papermc.paper.datacomponent.DataComponentTypes.ENCHANTMENTS); // empty constant might be useful here ++ if (itemEnchantments == null) { ++ return java.util.Collections.emptyMap(); ++ } ++ return itemEnchantments.enchantments(); ++ // Paper end + } + + static Map<Enchantment, Integer> getEnchantments(net.minecraft.world.item.ItemStack item) { +@@ -539,4 +563,84 @@ public final class CraftItemStack extends ItemStack { return this.pdcView; } // Paper end - pdc @@ -3114,7 +3190,7 @@ index 32a41c8b324aad67b9dcf74387aef299e6478a64..8bc572919dfd04f477a5b6aa62ee6bd7 + // Paper end - data component API } diff --git a/src/main/java/org/bukkit/craftbukkit/inventory/CraftItemType.java b/src/main/java/org/bukkit/craftbukkit/inventory/CraftItemType.java -index 07539ebfefa3352de5ee7a17f2724cf2c979f399..29feba5baa188885d1e586681635fcace788b4c4 100644 +index 07539ebfefa3352de5ee7a17f2724cf2c979f399..1ad733bd5fe0be1186a4e185424c4d1615f99eda 100644 --- a/src/main/java/org/bukkit/craftbukkit/inventory/CraftItemType.java +++ b/src/main/java/org/bukkit/craftbukkit/inventory/CraftItemType.java @@ -263,4 +263,21 @@ public class CraftItemType<M extends ItemMeta> implements ItemType.Typed<M>, Han @@ -3124,13 +3200,13 @@ index 07539ebfefa3352de5ee7a17f2724cf2c979f399..29feba5baa188885d1e586681635fcac + + // Paper start - data component API + @Override -+ public <T> T getDefaultData(final io.papermc.paper.datacomponent.DataComponentType.Valued<T> dataComponentType) { -+ return io.papermc.paper.datacomponent.PaperComponentType.convertDataComponentValue(this.item.components(), ((io.papermc.paper.datacomponent.PaperComponentType.ValuedImpl<T, ?>) dataComponentType)); ++ public <T> T getDefaultData(final io.papermc.paper.datacomponent.DataComponentType.Valued<T> type) { ++ return io.papermc.paper.datacomponent.PaperComponentType.convertDataComponentValue(this.item.components(), ((io.papermc.paper.datacomponent.PaperComponentType.ValuedImpl<T, ?>) type)); + } + + @Override -+ public boolean hasDefaultData(final io.papermc.paper.datacomponent.DataComponentType dataComponentType) { -+ return this.item.components().has(io.papermc.paper.datacomponent.PaperComponentType.bukkitToMinecraft(dataComponentType)); ++ public boolean hasDefaultData(final io.papermc.paper.datacomponent.DataComponentType type) { ++ return this.item.components().has(io.papermc.paper.datacomponent.PaperComponentType.bukkitToMinecraft(type)); + } + + @Override @@ -3161,28 +3237,15 @@ index 7277e7ee566aabf6e01937072d949ed67c3e8e38..24ff8b4ed2a70d02b850c3701d3295fd IntList colors = CraftMetaFirework.addColors(effect.getColors()); IntList fadeColors = CraftMetaFirework.addColors(effect.getFadeColors()); -diff --git a/src/main/java/org/bukkit/craftbukkit/inventory/CraftMetaItem.java b/src/main/java/org/bukkit/craftbukkit/inventory/CraftMetaItem.java -index 4d97024bb05ab815409fc25c5924903868cc3945..c3e2cf55768a28824764fee387e8c1b2c0863744 100644 ---- a/src/main/java/org/bukkit/craftbukkit/inventory/CraftMetaItem.java -+++ b/src/main/java/org/bukkit/craftbukkit/inventory/CraftMetaItem.java -@@ -136,7 +136,7 @@ import org.bukkit.persistence.PersistentDataContainer; - */ - @DelegateDeserialization(SerializableMeta.class) - // Important: ItemMeta needs to be the first interface see #applicableTo(Material) --class CraftMetaItem implements ItemMeta, Damageable, Repairable, BlockDataMeta { -+public class CraftMetaItem implements ItemMeta, Damageable, Repairable, BlockDataMeta { // Paper - - static class ItemMetaKey { - diff --git a/src/main/java/org/bukkit/craftbukkit/util/CraftLocation.java b/src/main/java/org/bukkit/craftbukkit/util/CraftLocation.java -index 097996d3955ab5126b71f7bff1dd2c62becb5ffd..0797ef29b76564491351042ce47e3d4500490bef 100644 +index 097996d3955ab5126b71f7bff1dd2c62becb5ffd..2e75620e803868ad3c254d11e6265062b2542249 100644 --- a/src/main/java/org/bukkit/craftbukkit/util/CraftLocation.java +++ b/src/main/java/org/bukkit/craftbukkit/util/CraftLocation.java @@ -40,6 +40,16 @@ public final class CraftLocation { return new BlockPos(location.getBlockX(), location.getBlockY(), location.getBlockZ()); } -+ // Paper start ++ // Paper start - todo move in the right patch + public static net.minecraft.core.GlobalPos toGlobalPos(Location location) { + return net.minecraft.core.GlobalPos.of(((org.bukkit.craftbukkit.CraftWorld) location.getWorld()).getHandle().dimension(), toBlockPosition(location)); + } @@ -3204,10 +3267,10 @@ index 0000000000000000000000000000000000000000..1c1fcbbacc3881e088d64a7a840b3f3e +io.papermc.paper.datacomponent.item.ComponentTypesBridgesImpl diff --git a/src/test/java/io/papermc/paper/item/ItemStackDataComponentTest.java b/src/test/java/io/papermc/paper/item/ItemStackDataComponentTest.java new file mode 100644 -index 0000000000000000000000000000000000000000..49e18cffd75bbd9c28e75807d303759f552819dd +index 0000000000000000000000000000000000000000..0ce6b68576f33d6f9a9f9f9e2f587dd0d7de2d67 --- /dev/null +++ b/src/test/java/io/papermc/paper/item/ItemStackDataComponentTest.java -@@ -0,0 +1,389 @@ +@@ -0,0 +1,386 @@ +package io.papermc.paper.item; + +import io.papermc.paper.datacomponent.DataComponentType; @@ -3222,7 +3285,7 @@ index 0000000000000000000000000000000000000000..49e18cffd75bbd9c28e75807d303759f +import io.papermc.paper.datacomponent.item.ItemEnchantments; +import io.papermc.paper.datacomponent.item.ItemLore; +import io.papermc.paper.datacomponent.item.JukeboxPlayable; -+import io.papermc.paper.datacomponent.item.MapID; ++import io.papermc.paper.datacomponent.item.MapId; +import io.papermc.paper.datacomponent.item.MapItemColor; +import io.papermc.paper.datacomponent.item.PotDecorations; +import io.papermc.paper.datacomponent.item.Tool; @@ -3368,7 +3431,6 @@ index 0000000000000000000000000000000000000000..49e18cffd75bbd9c28e75807d303759f + Assertions.assertTrue(stack.getItemMeta().getEnchants().isEmpty()); + } + -+ + @Test + void testItemAttributes() { + final ItemStack stack = new ItemStack(Material.STONE); @@ -3383,7 +3445,7 @@ index 0000000000000000000000000000000000000000..49e18cffd75bbd9c28e75807d303759f + + @Test + void testCustomModelData() { -+ testWithMeta(new ItemStack(Material.STONE), DataComponentTypes.CUSTOM_MODEL_DATA, CustomModelData.customModelData().customModelData(1).build(), CustomModelData::data, ItemMeta.class, ItemMeta::getCustomModelData, ItemMeta::setCustomModelData); ++ testWithMeta(new ItemStack(Material.STONE), DataComponentTypes.CUSTOM_MODEL_DATA, CustomModelData.customModelData().data(1).build(), CustomModelData::data, ItemMeta.class, ItemMeta::getCustomModelData, ItemMeta::setCustomModelData); + } + + @Test @@ -3397,7 +3459,7 @@ index 0000000000000000000000000000000000000000..49e18cffd75bbd9c28e75807d303759f + .canAlwaysEat(true) + .eatSeconds(1.3F) + .nutrition(1) -+ .addAllEffects(List.of(FoodProperties.PossibleEffect.of(new PotionEffect(PotionEffectType.SLOWNESS, 5, 255), 1F))) ++ .addEffects(List.of(FoodProperties.PossibleEffect.of(new PotionEffect(PotionEffectType.SLOWNESS, 5, 10), 1F))) + .usingConvertsTo(new ItemStack(Material.STONE)) + .build(); + @@ -3418,7 +3480,6 @@ index 0000000000000000000000000000000000000000..49e18cffd75bbd9c28e75807d303759f + } + Assertions.assertEquals(properties.usingConvertsTo(), component.getUsingConvertsTo()); + -+ + stack.unsetData(DataComponentTypes.FOOD); + meta = stack.getItemMeta(); + Assertions.assertFalse(meta.hasFood()); @@ -3455,7 +3516,7 @@ index 0000000000000000000000000000000000000000..49e18cffd75bbd9c28e75807d303759f + for (ToolComponent.ToolRule effect : component.getRules()) { + Assertions.assertEquals(properties.rules().get(idx).speed(), effect.getSpeed()); + Assertions.assertEquals(properties.rules().get(idx).correctForDrops().toBoolean(), effect.isCorrectForDrops()); -+ Assertions.assertEquals(properties.rules().get(idx).blockTypes().resolve(Registry.BLOCK), effect.getBlocks().stream().map(Material::asBlockType).toList()); ++ Assertions.assertEquals(properties.rules().get(idx).blocks().resolve(Registry.BLOCK), effect.getBlocks().stream().map(Material::asBlockType).toList()); + idx++; + } + @@ -3504,7 +3565,7 @@ index 0000000000000000000000000000000000000000..49e18cffd75bbd9c28e75807d303759f + + @Test + void testMapId() { -+ testWithMeta(new ItemStack(Material.FILLED_MAP), DataComponentTypes.MAP_ID, MapID.mapId().mapId(1).build(), MapID::id, MapMeta.class, MapMeta::getMapId, MapMeta::setMapId); ++ testWithMeta(new ItemStack(Material.FILLED_MAP), DataComponentTypes.MAP_ID, MapId.mapId().id(1).build(), MapId::id, MapMeta.class, MapMeta::getMapId, MapMeta::setMapId); + } + + @Test @@ -3530,7 +3591,6 @@ index 0000000000000000000000000000000000000000..49e18cffd75bbd9c28e75807d303759f + Assertions.assertFalse(((ArmorMeta) stack.getItemMeta()).hasTrim()); + } + -+ + @Test + void testChargedProjectiles() { + final ItemStack stack = new ItemStack(Material.CROSSBOW); @@ -3940,15 +4000,14 @@ index aabe3730fa582f442ee0544dd1a9f3123f719c68..a75fb4f856728610bec5ebd24eb9c283 this.downCastTest(name, provider.stack(), craftBlank); craftBlank.setItemMeta(craftBlank.getItemMeta()); diff --git a/src/test/java/org/bukkit/support/provider/RegistriesArgumentProvider.java b/src/test/java/org/bukkit/support/provider/RegistriesArgumentProvider.java -index a480944e1fc1b79b91be7e8d3e3799b9168cf5a0..7ae45920e02c1ada0a5d4d1f3512a0b8006ff18e 100644 +index a480944e1fc1b79b91be7e8d3e3799b9168cf5a0..2649f6cc4d51de64841318362b69aaef6f14b589 100644 --- a/src/test/java/org/bukkit/support/provider/RegistriesArgumentProvider.java +++ b/src/test/java/org/bukkit/support/provider/RegistriesArgumentProvider.java -@@ -58,7 +58,7 @@ public class RegistriesArgumentProvider implements ArgumentsProvider { +@@ -58,6 +58,7 @@ public class RegistriesArgumentProvider implements ArgumentsProvider { register(RegistryKey.WOLF_VARIANT, Wolf.Variant.class, Registries.WOLF_VARIANT, CraftWolf.CraftVariant.class, WolfVariant.class); register(RegistryKey.ITEM, ItemType.class, Registries.ITEM, CraftItemType.class, net.minecraft.world.item.Item.class, true); register(RegistryKey.BLOCK, BlockType.class, Registries.BLOCK, CraftBlockType.class, net.minecraft.world.level.block.Block.class, true); -- -+ register(RegistryKey.DATA_COMPONENT_TYPE, io.papermc.paper.datacomponent.DataComponentType.class, Registries.DATA_COMPONENT_TYPE, io.papermc.paper.datacomponent.PaperComponentType.class, net.minecraft.core.component.DataComponentType.class, false); ++ register(RegistryKey.DATA_COMPONENT_TYPE, io.papermc.paper.datacomponent.DataComponentType.class, Registries.DATA_COMPONENT_TYPE, io.papermc.paper.datacomponent.PaperComponentType.class, net.minecraft.core.component.DataComponentType.class); + } - private static void register(RegistryKey registryKey, Class bukkit, ResourceKey registry, Class craft, Class minecraft) { // Paper |