diff --git a/patches/server/Adventure.patch b/patches/server/Adventure.patch index aa85206011..ab998b46d1 100644 --- a/patches/server/Adventure.patch +++ b/patches/server/Adventure.patch @@ -1219,6 +1219,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 +import org.bukkit.craftbukkit.command.VanillaCommandWrapper; +import org.bukkit.craftbukkit.entity.CraftEntity; +import org.intellij.lang.annotations.Subst; ++import org.jetbrains.annotations.Contract; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + @@ -1337,7 +1338,13 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + return jsons; + } + -+ public static net.minecraft.network.chat.Component asVanilla(@Nullable final Component component) { ++ public static net.minecraft.network.chat.@NotNull Component asVanillaNullToEmpty(final @Nullable Component component) { ++ if (component == null) return net.minecraft.network.chat.CommonComponents.EMPTY; ++ return asVanilla(component); ++ } ++ ++ @Contract("null -> null; !null -> !null") ++ public static net.minecraft.network.chat.Component asVanilla(final @Nullable Component component) { + if (component == null) return null; + if (true) return new AdventureComponent(component); + return WRAPPER_AWARE_SERIALIZER.serialize(component); @@ -4159,7 +4166,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (this.getHandle().connection == null) return; - ClientboundTabListPacket packet = new ClientboundTabListPacket((this.playerListHeader == null) ? Component.empty() : this.playerListHeader, (this.playerListFooter == null) ? Component.empty() : this.playerListFooter); -+ ClientboundTabListPacket packet = new ClientboundTabListPacket((this.playerListHeader == null) ? Component.empty() : io.papermc.paper.adventure.PaperAdventure.asVanilla(this.playerListHeader), (this.playerListFooter == null) ? Component.empty() : io.papermc.paper.adventure.PaperAdventure.asVanilla(this.playerListFooter)); // Paper - adventure ++ ClientboundTabListPacket packet = new ClientboundTabListPacket(io.papermc.paper.adventure.PaperAdventure.asVanillaNullToEmpty(this.playerListHeader), io.papermc.paper.adventure.PaperAdventure.asVanillaNullToEmpty(this.playerListFooter)); // Paper - adventure this.getHandle().connection.send(packet); } @@ -4421,8 +4428,8 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + final ServerGamePacketListenerImpl connection = this.getHandle().connection; + if (connection == null) return; + final ClientboundTabListPacket packet = new ClientboundTabListPacket( -+ io.papermc.paper.adventure.PaperAdventure.asVanilla((this.playerListHeader == null) ? net.kyori.adventure.text.Component.empty() : this.playerListHeader), -+ io.papermc.paper.adventure.PaperAdventure.asVanilla((this.playerListFooter == null) ? net.kyori.adventure.text.Component.empty() : this.playerListFooter) ++ io.papermc.paper.adventure.PaperAdventure.asVanillaNullToEmpty(this.playerListHeader), ++ io.papermc.paper.adventure.PaperAdventure.asVanillaNullToEmpty(this.playerListFooter) + ); + connection.send(packet); + } @@ -4744,7 +4751,12 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + // Paper start - Adventure + @Override + public net.kyori.adventure.text.event.HoverEvent asHoverEvent(final ItemStack item, final java.util.function.UnaryOperator op) { -+ return net.kyori.adventure.text.event.HoverEvent.showItem(op.apply(net.kyori.adventure.text.event.HoverEvent.ShowItem.showItem(item.getType().getKey(), item.getAmount(), io.papermc.paper.adventure.PaperAdventure.asAdventure(CraftItemStack.asNMSCopy(item).getComponentsPatch())))); ++ return net.kyori.adventure.text.event.HoverEvent.showItem(op.apply( ++ net.kyori.adventure.text.event.HoverEvent.ShowItem.showItem( ++ item.getType().getKey(), ++ item.getAmount(), ++ io.papermc.paper.adventure.PaperAdventure.asAdventure(CraftItemStack.unwrap(item).getComponentsPatch())) // unwrap is fine here because the components patch will be safely copied ++ )); + } + + @Override diff --git a/patches/server/Implement-enchantWithLevels-API.patch b/patches/server/Implement-enchantWithLevels-API.patch index c2207edfba..188b11267f 100644 --- a/patches/server/Implement-enchantWithLevels-API.patch +++ b/patches/server/Implement-enchantWithLevels-API.patch @@ -22,7 +22,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + Preconditions.checkArgument(random != null, "Argument 'random' must not be null"); + final net.minecraft.world.item.ItemStack internalStack = CraftItemStack.asNMSCopy(itemStack); + if (internalStack.isEnchanted()) { -+ internalStack.applyComponents(net.minecraft.core.component.DataComponentPatch.builder().remove(net.minecraft.core.component.DataComponents.ENCHANTMENTS).build()); ++ internalStack.set(net.minecraft.core.component.DataComponents.ENCHANTMENTS, null); + } + final net.minecraft.world.item.ItemStack enchanted = net.minecraft.world.item.enchantment.EnchantmentHelper.enchantItem( + MinecraftServer.getServer().getWorldData().enabledFeatures(), diff --git a/patches/server/LootTable-API-and-replenishable-lootables.patch b/patches/server/LootTable-API-and-replenishable-lootables.patch index 50780be420..7fae07f171 100644 --- a/patches/server/LootTable-API-and-replenishable-lootables.patch +++ b/patches/server/LootTable-API-and-replenishable-lootables.patch @@ -673,9 +673,8 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + // Copied from super with changes, always check the original method + this.lootableData.loadNbt(nbt); // Paper + if (nbt.contains("LootTable", 8)) { -+ final var loc = new net.minecraft.resources.ResourceLocation(nbt.getString("LootTable")); -+ this.setLootTable(ResourceKey.create(net.minecraft.core.registries.Registries.LOOT_TABLE, loc)); -+ try { org.bukkit.craftbukkit.util.CraftNamespacedKey.fromMinecraft(this.lootTable.location()); } catch (IllegalArgumentException ex) { this.lootTable = null; } // Paper - validate ++ this.setLootTable(net.minecraft.Optionull.map(net.minecraft.resources.ResourceLocation.tryParse(nbt.getString("LootTable")), rl -> ResourceKey.create(net.minecraft.core.registries.Registries.LOOT_TABLE, rl))); ++ try { if (this.lootTable != null) org.bukkit.craftbukkit.util.CraftNamespacedKey.fromMinecraft(this.lootTable.location()); } catch (IllegalArgumentException ex) { this.lootTable = null; } // Paper - validate + if (nbt.contains("LootTableSeed", 4)) { + this.setLootTableSeed(nbt.getLong("LootTableSeed")); + } else { diff --git a/patches/server/Properly-track-the-changed-item-from-dispense-events.patch b/patches/server/Properly-track-the-changed-item-from-dispense-events.patch index 0b58597ca9..23580b9633 100644 --- a/patches/server/Properly-track-the-changed-item-from-dispense-events.patch +++ b/patches/server/Properly-track-the-changed-item-from-dispense-events.patch @@ -79,7 +79,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 } } -+ Projectile iprojectile = this.projectileItem.asProjectile(worldserver, iposition, CraftItemStack.asNMSCopy(event.getItem()), enumdirection); // Paper - move from above and track changed items in the dispense event ++ Projectile iprojectile = this.projectileItem.asProjectile(worldserver, iposition, CraftItemStack.unwrap(event.getItem()), enumdirection); // Paper - move from above and track changed items in the dispense event; unwrap is safe here because all uses of the stack make their own copies this.projectileItem.shoot(iprojectile, event.getVelocity().getX(), event.getVelocity().getY(), event.getVelocity().getZ(), this.dispenseConfig.power(), this.dispenseConfig.uncertainty()); ((Entity) iprojectile).projectileSource = new org.bukkit.craftbukkit.projectiles.CraftBlockProjectileSource(pointer.blockEntity()); // CraftBukkit end