diff --git a/patches/server/Add-hand-to-fish-event-for-all-player-interactions.patch b/patches/server/Add-hand-to-fish-event-for-all-player-interactions.patch index 7f37957711..f25f1a4006 100644 --- a/patches/server/Add-hand-to-fish-event-for-all-player-interactions.patch +++ b/patches/server/Add-hand-to-fish-event-for-all-player-interactions.patch @@ -12,7 +12,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 @Override public void readAdditionalSaveData(CompoundTag nbt) {} -+ // Paper start - add hand parameter ++ // Paper start - Add hand parameter to PlayerFishEvent + @Deprecated + @io.papermc.paper.annotation.DoNotUse public int retrieve(ItemStack usedItem) { @@ -20,7 +20,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + } + + public int retrieve(net.minecraft.world.InteractionHand hand, ItemStack usedItem) { -+ // Paper end ++ // Paper end - Add hand parameter to PlayerFishEvent net.minecraft.world.entity.player.Player entityhuman = this.getPlayerOwner(); if (!this.level().isClientSide && entityhuman != null && !this.shouldStopFishing(entityhuman)) { @@ -29,7 +29,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (this.hookedIn != null) { // CraftBukkit start - PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), this.hookedIn.getBukkitEntity(), (FishHook) this.getBukkitEntity(), PlayerFishEvent.State.CAUGHT_ENTITY); -+ PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), this.hookedIn.getBukkitEntity(), (FishHook) this.getBukkitEntity(), org.bukkit.craftbukkit.CraftEquipmentSlot.getHand(hand), PlayerFishEvent.State.CAUGHT_ENTITY); // Paper - add hand ++ PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), this.hookedIn.getBukkitEntity(), (FishHook) this.getBukkitEntity(), org.bukkit.craftbukkit.CraftEquipmentSlot.getHand(hand), PlayerFishEvent.State.CAUGHT_ENTITY); // Paper - Add hand parameter to PlayerFishEvent this.level().getCraftServer().getPluginManager().callEvent(playerFishEvent); if (playerFishEvent.isCancelled()) { @@ -38,7 +38,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // Paper end // CraftBukkit start - PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), entityitem != null ? entityitem.getBukkitEntity() : null, (FishHook) this.getBukkitEntity(), PlayerFishEvent.State.CAUGHT_FISH); // Paper - entityitem may be null -+ PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), entityitem != null ? entityitem.getBukkitEntity() : null, (FishHook) this.getBukkitEntity(), org.bukkit.craftbukkit.CraftEquipmentSlot.getHand(hand), PlayerFishEvent.State.CAUGHT_FISH); // Paper - entityitem may be null // Paper - add hand ++ PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), entityitem != null ? entityitem.getBukkitEntity() : null, (FishHook) this.getBukkitEntity(), org.bukkit.craftbukkit.CraftEquipmentSlot.getHand(hand), PlayerFishEvent.State.CAUGHT_FISH); // Paper - entityitem may be null // Paper - Add hand parameter to PlayerFishEvent playerFishEvent.setExpToDrop(this.random.nextInt(6) + 1); this.level().getCraftServer().getPluginManager().callEvent(playerFishEvent); @@ -47,7 +47,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (this.onGround()) { // CraftBukkit start - PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), null, (FishHook) this.getBukkitEntity(), PlayerFishEvent.State.IN_GROUND); -+ PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), null, (FishHook) this.getBukkitEntity(), org.bukkit.craftbukkit.CraftEquipmentSlot.getHand(hand), PlayerFishEvent.State.IN_GROUND); // Paper - add hand ++ PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), null, (FishHook) this.getBukkitEntity(), org.bukkit.craftbukkit.CraftEquipmentSlot.getHand(hand), PlayerFishEvent.State.IN_GROUND); // Paper - Add hand parameter to PlayerFishEvent this.level().getCraftServer().getPluginManager().callEvent(playerFishEvent); if (playerFishEvent.isCancelled()) { @@ -56,7 +56,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // CraftBukkit start if (i == 0) { - PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), null, (FishHook) this.getBukkitEntity(), PlayerFishEvent.State.REEL_IN); -+ PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), null, (FishHook) this.getBukkitEntity(), org.bukkit.craftbukkit.CraftEquipmentSlot.getHand(hand), PlayerFishEvent.State.REEL_IN); // Paper - add hand ++ PlayerFishEvent playerFishEvent = new PlayerFishEvent((Player) entityhuman.getBukkitEntity(), null, (FishHook) this.getBukkitEntity(), org.bukkit.craftbukkit.CraftEquipmentSlot.getHand(hand), PlayerFishEvent.State.REEL_IN); // Paper - Add hand parameter to PlayerFishEvent this.level().getCraftServer().getPluginManager().callEvent(playerFishEvent); if (playerFishEvent.isCancelled()) { return 0; @@ -69,7 +69,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (user.fishing != null) { if (!world.isClientSide) { - i = user.fishing.retrieve(itemstack); -+ i = user.fishing.retrieve(hand, itemstack); // Paper - add hand parameter ++ i = user.fishing.retrieve(hand, itemstack); // Paper - Add hand parameter to PlayerFishEvent itemstack.hurtAndBreak(i, user, (entityhuman1) -> { entityhuman1.broadcastBreakEvent(hand); }); diff --git a/patches/server/Add-missing-InventoryHolders-to-inventories.patch b/patches/server/Add-missing-InventoryHolders-to-inventories.patch index 60c9b5497d..0c182bf84b 100644 --- a/patches/server/Add-missing-InventoryHolders-to-inventories.patch +++ b/patches/server/Add-missing-InventoryHolders-to-inventories.patch @@ -34,11 +34,11 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 } public org.bukkit.inventory.InventoryHolder getOwner() { -+ // Paper start ++ // Paper start - Add missing InventoryHolders + if (this.bukkitOwner == null && this.bukkitOwnerCreator != null) { + this.bukkitOwner = this.bukkitOwnerCreator.get(); + } -+ // Paper end ++ // Paper end - Add missing InventoryHolders return this.bukkitOwner; } @@ -46,13 +46,13 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 public SimpleContainer(int size) { this(size, null); } -+ // Paper start ++ // Paper start - Add missing InventoryHolders + private @Nullable java.util.function.Supplier bukkitOwnerCreator; + public SimpleContainer(java.util.function.Supplier bukkitOwnerCreator, int size) { + this(size); + this.bukkitOwnerCreator = bukkitOwnerCreator; + } -+ // Paper end ++ // Paper end - Add missing InventoryHolders public SimpleContainer(int i, org.bukkit.inventory.InventoryHolder owner) { this.bukkitOwner = owner; @@ -65,7 +65,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 return this.stateId; } + -+ // Paper start - add missing BlockInventoryHolder to inventories ++ // Paper start - Add missing InventoryHolders + // The reason this is a supplier, is that the createHolder method uses the bukkit InventoryView#getTopInventory to get the inventory in question + // and that can't be obtained safely until the AbstractContainerMenu has been fully constructed. Using a supplier lazily + // initializes the InventoryHolder safely. @@ -74,7 +74,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + Preconditions.checkArgument(context != null, "context was null"); + return () -> context.createBlockHolder(this); + } -+ // Paper end ++ // Paper end - Add missing InventoryHolders } diff --git a/src/main/java/net/minecraft/world/inventory/BeaconMenu.java b/src/main/java/net/minecraft/world/inventory/BeaconMenu.java index 0000000000000000000000000000000000000000..0000000000000000000000000000000000000000 100644 @@ -85,7 +85,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 super(MenuType.BEACON, syncId); this.player = (Inventory) inventory; // CraftBukkit - TODO: check this - this.beacon = new SimpleContainer(1) { -+ this.beacon = new SimpleContainer(this.createBlockHolder(context), 1) { // Paper ++ this.beacon = new SimpleContainer(this.createBlockHolder(context), 1) { // Paper - Add missing InventoryHolders @Override public boolean canPlaceItem(int slot, ItemStack stack) { return stack.is(ItemTags.BEACON_PAYMENT_ITEMS); @@ -98,7 +98,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 public CartographyTableMenu(int syncId, Inventory inventory, final ContainerLevelAccess context) { super(MenuType.CARTOGRAPHY_TABLE, syncId); - this.container = new SimpleContainer(2) { -+ this.container = new SimpleContainer(this.createBlockHolder(context), 2) { // Paper ++ this.container = new SimpleContainer(this.createBlockHolder(context), 2) { // Paper - Add missing InventoryHolders @Override public void setChanged() { CartographyTableMenu.this.slotsChanged(this); @@ -107,7 +107,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // CraftBukkit end }; - this.resultContainer = new ResultContainer() { -+ this.resultContainer = new ResultContainer(this.createBlockHolder(context)) { // Paper ++ this.resultContainer = new ResultContainer(this.createBlockHolder(context)) { // Paper - Add missing InventoryHolders @Override public void setChanged() { CartographyTableMenu.this.slotsChanged(this); @@ -119,7 +119,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 return new org.bukkit.Location(this.getWorld().getWorld(), this.getPosition().getX(), this.getPosition().getY(), this.getPosition().getZ()); } // CraftBukkit end -+ // Paper start ++ // Paper start - Add missing InventoryHolders + default boolean isBlock() { + return false; + } @@ -130,7 +130,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + } + return new org.bukkit.craftbukkit.inventory.CraftBlockInventoryHolder(this, menu.getBukkitView().getTopInventory()); + } -+ // Paper end ++ // Paper end - Add missing InventoryHolders ContainerLevelAccess NULL = new ContainerLevelAccess() { @Override @@ -138,12 +138,12 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 return pos; } // CraftBukkit end -+ // Paper start ++ // Paper start - Add missing InventoryHolders + @Override + public boolean isBlock() { + return true; + } -+ // Paper end ++ // Paper end - Add missing InventoryHolders @Override public Optional evaluate(BiFunction getter) { @@ -156,7 +156,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 public EnchantmentMenu(int syncId, Inventory playerInventory, ContainerLevelAccess context) { super(MenuType.ENCHANTMENT, syncId); - this.enchantSlots = new SimpleContainer(2) { -+ this.enchantSlots = new SimpleContainer(this.createBlockHolder(context), 2) { // Paper ++ this.enchantSlots = new SimpleContainer(this.createBlockHolder(context), 2) { // Paper - Add missing InventoryHolders @Override public void setChanged() { super.setChanged(); @@ -170,8 +170,8 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 super(MenuType.GRINDSTONE, syncId); - this.resultSlots = new ResultContainer(); - this.repairSlots = new SimpleContainer(2) { -+ this.resultSlots = new ResultContainer(this.createBlockHolder(context)); // Paper -+ this.repairSlots = new SimpleContainer(this.createBlockHolder(context), 2) { // Paper ++ this.resultSlots = new ResultContainer(this.createBlockHolder(context)); // Paper - Add missing InventoryHolders ++ this.repairSlots = new SimpleContainer(this.createBlockHolder(context), 2) { // Paper - Add missing InventoryHolders @Override public void setChanged() { super.setChanged(); @@ -184,7 +184,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 protected final Container inputSlots; private final List inputSlotIndexes; - protected final ResultContainer resultSlots = new ResultContainer(); -+ protected final ResultContainer resultSlots; // Paper - delay field init ++ protected final ResultContainer resultSlots; // Paper - Add missing InventoryHolders; delay field init private final int resultSlotIndex; protected abstract boolean mayPickup(Player player, boolean present); @@ -192,7 +192,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 public ItemCombinerMenu(@Nullable MenuType type, int syncId, Inventory playerInventory, ContainerLevelAccess context) { super(type, syncId); this.access = context; -+ this.resultSlots = new ResultContainer(this.createBlockHolder(this.access)); // Paper - delay field init ++ this.resultSlots = new ResultContainer(this.createBlockHolder(this.access)); // Paper - Add missing InventoryHolders; delay field init this.player = playerInventory.player; ItemCombinerMenuSlotDefinition itemcombinermenuslotdefinition = this.createInputSlotDefinitions(); @@ -201,7 +201,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 private SimpleContainer createContainer(int size) { - return new SimpleContainer(size) { -+ return new SimpleContainer(this.createBlockHolder(this.access), size) { // Paper ++ return new SimpleContainer(this.createBlockHolder(this.access), size) { // Paper - Add missing InventoryHolders @Override public void setChanged() { super.setChanged(); @@ -214,7 +214,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 this.slotUpdateListener = () -> { }; - this.inputContainer = new SimpleContainer(3) { -+ this.inputContainer = new SimpleContainer(this.createBlockHolder(context), 3) { // Paper ++ this.inputContainer = new SimpleContainer(this.createBlockHolder(context), 3) { // Paper - Add missing InventoryHolders @Override public void setChanged() { super.setChanged(); @@ -223,7 +223,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // CraftBukkit end }; - this.outputContainer = new SimpleContainer(1) { -+ this.outputContainer = new SimpleContainer(this.createBlockHolder(context), 1) { // Paper ++ this.outputContainer = new SimpleContainer(this.createBlockHolder(context), 1) { // Paper - Add missing InventoryHolders @Override public void setChanged() { super.setChanged(); @@ -236,12 +236,12 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 public org.bukkit.inventory.InventoryHolder getOwner() { - return null; // Result slots don't get an owner -+ // Paper start ++ // Paper start - Add missing InventoryHolders + if (this.holder == null && this.holderCreator != null) { + this.holder = this.holderCreator.get(); + } + return this.holder; // Result slots don't get an owner -+ // Paper end - yes they do ++ // Paper end - Add missing InventoryHolders } // Don't need a transaction; the InventoryCrafting keeps track of it for us @@ -249,14 +249,14 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 return null; } // CraftBukkit end -+ // Paper start ++ // Paper start - Add missing InventoryHolders + private @Nullable java.util.function.Supplier holderCreator; + private @Nullable org.bukkit.inventory.InventoryHolder holder; + public ResultContainer(java.util.function.Supplier holderCreator) { + this(); + this.holderCreator = holderCreator; + } -+ // Paper end ++ // Paper end - Add missing InventoryHolders public ResultContainer() { this.itemStacks = NonNullList.withSize(1, ItemStack.EMPTY); @@ -269,7 +269,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 this.slotUpdateListener = () -> { }; - this.container = new SimpleContainer(1) { -+ this.container = new SimpleContainer(this.createBlockHolder(context), 1) { // Paper ++ this.container = new SimpleContainer(this.createBlockHolder(context), 1) { // Paper - Add missing InventoryHolders @Override public void setChanged() { super.setChanged(); @@ -278,7 +278,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // CraftBukkit end }; - this.resultContainer = new ResultContainer(); -+ this.resultContainer = new ResultContainer(this.createBlockHolder(context)); // Paper ++ this.resultContainer = new ResultContainer(this.createBlockHolder(context)); // Paper - Add missing InventoryHolders this.access = context; this.level = playerInventory.player.level(); this.inputSlot = this.addSlot(new Slot(this.container, 0, 20, 33)); @@ -290,13 +290,13 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 this.block = CraftBlock.at(world, pos); this.inventory = new CraftInventory(inv); } -+ // Paper start ++ // Paper start - Add missing InventoryHolders + public CraftBlockInventoryHolder(net.minecraft.world.inventory.ContainerLevelAccess levelAccess, Inventory inventory) { + com.google.common.base.Preconditions.checkArgument(levelAccess.isBlock()); + this.block = CraftBlock.at(levelAccess.getWorld(), levelAccess.getPosition()); + this.inventory = inventory; + } -+ // Paper end ++ // Paper end - Add missing InventoryHolders @Override public Block getBlock() { diff --git a/patches/server/Add-missing-logs-for-log-ips-config-option.patch b/patches/server/Add-missing-logs-for-log-ips-config-option.patch index 3fb50664e9..ec1d1047ed 100644 --- a/patches/server/Add-missing-logs-for-log-ips-config-option.patch +++ b/patches/server/Add-missing-logs-for-log-ips-config-option.patch @@ -13,7 +13,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (i == 0) { - LegacyQueryHandler.LOGGER.debug("Ping: (<1.3.x) from {}", socketaddress); -+ LegacyQueryHandler.LOGGER.debug("Ping: (<1.3.x) from {}", net.minecraft.server.MinecraftServer.getServer().logIPs() ? socketaddress: ""); // Paper ++ LegacyQueryHandler.LOGGER.debug("Ping: (<1.3.x) from {}", net.minecraft.server.MinecraftServer.getServer().logIPs() ? socketaddress: ""); // Paper - Respect logIPs option // Paper start - Call PaperServerListPingEvent and use results event = com.destroystokyo.paper.network.PaperLegacyStatusClient.processRequest(net.minecraft.server.MinecraftServer.getServer(), (java.net.InetSocketAddress) socketaddress, 39, null); @@ -22,7 +22,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // Paper end } else { - LegacyQueryHandler.LOGGER.debug("Ping: (1.4-1.5.x) from {}", socketaddress); -+ LegacyQueryHandler.LOGGER.debug("Ping: (1.4-1.5.x) from {}", net.minecraft.server.MinecraftServer.getServer().logIPs() ? socketaddress: ""); // Paper ++ LegacyQueryHandler.LOGGER.debug("Ping: (1.4-1.5.x) from {}", net.minecraft.server.MinecraftServer.getServer().logIPs() ? socketaddress: ""); // Paper - Respect logIPs option } if (s == null) { @@ -31,7 +31,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 this.buf = null; - LOGGER.debug("Ping: (1.6) from {}", ctx.channel().remoteAddress()); -+ LOGGER.debug("Ping: (1.6) from {}", net.minecraft.server.MinecraftServer.getServer().logIPs() ? ctx.channel().remoteAddress(): ""); // Paper ++ LOGGER.debug("Ping: (1.6) from {}", net.minecraft.server.MinecraftServer.getServer().logIPs() ? ctx.channel().remoteAddress(): ""); // Paper - Respect logIPs option java.net.InetSocketAddress virtualHost = com.destroystokyo.paper.network.PaperNetworkClient.prepareVirtualHost(host, port); com.destroystokyo.paper.event.server.PaperServerListPingEvent event = com.destroystokyo.paper.network.PaperLegacyStatusClient.processRequest( diff --git a/patches/server/Add-predicate-for-blocks-when-raytracing.patch b/patches/server/Add-predicate-for-blocks-when-raytracing.patch index 8c181b41e9..6dd4a09fd4 100644 --- a/patches/server/Add-predicate-for-blocks-when-raytracing.patch +++ b/patches/server/Add-predicate-for-blocks-when-raytracing.patch @@ -12,12 +12,12 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // CraftBukkit start - moved block handling into separate method for use by Block#rayTrace default BlockHitResult clip(ClipContext raytrace1, BlockPos blockposition) { -+ // Paper start ++ // Paper start - Add predicate for blocks when raytracing + return clip(raytrace1, blockposition, null); + } + + default BlockHitResult clip(ClipContext raytrace1, BlockPos blockposition, java.util.function.Predicate canCollide) { -+ // Paper end ++ // Paper end - Add predicate for blocks when raytracing // Paper start - Prevent raytrace from loading chunks BlockState iblockdata = this.getBlockStateIfLoaded(blockposition); if (iblockdata == null) { @@ -34,15 +34,15 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // CraftBukkit end default BlockHitResult clip(ClipContext context) { -+ // Paper start ++ // Paper start - Add predicate for blocks when raytracing + return clip(context, (java.util.function.Predicate) null); + } + + default BlockHitResult clip(ClipContext context, java.util.function.Predicate canCollide) { -+ // Paper end ++ // Paper end - Add predicate for blocks when raytracing return (BlockHitResult) BlockGetter.traverseBlocks(context.getFrom(), context.getTo(), context, (raytrace1, blockposition) -> { - return this.clip(raytrace1, blockposition); // CraftBukkit - moved into separate method -+ return this.clip(raytrace1, blockposition, canCollide); // CraftBukkit - moved into separate method // Paper - use method with canCollide predicate ++ return this.clip(raytrace1, blockposition, canCollide); // CraftBukkit - moved into separate method // Paper - Add predicate for blocks when raytracing }, (raytrace1) -> { Vec3 vec3d = raytrace1.getFrom().subtract(raytrace1.getTo()); @@ -54,7 +54,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 @Override public RayTraceResult rayTraceEntities(Location start, Vector direction, double maxDistance, double raySize, Predicate filter) { -+ // Paper start ++ // Paper start - Add predicate for blocks when raytracing + return rayTraceEntities((io.papermc.paper.math.Position) start, direction, maxDistance, raySize, filter); + } + @@ -64,7 +64,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - start.checkFinite(); + Preconditions.checkArgument(!(start instanceof Location location) || this.equals(location.getWorld()), "Location start cannot be in a different world"); + Preconditions.checkArgument(start.isFinite(), "Location start is not finite"); -+ // Paper end ++ // Paper end - Add predicate for blocks when raytracing Preconditions.checkArgument(direction != null, "Vector direction cannot be null"); direction.checkFinite(); @@ -72,7 +72,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 @Override public RayTraceResult rayTraceBlocks(Location start, Vector direction, double maxDistance, FluidCollisionMode fluidCollisionMode, boolean ignorePassableBlocks) { -+ // Paper start ++ // Paper start - Add predicate for blocks when raytracing + return this.rayTraceBlocks(start, direction, maxDistance, fluidCollisionMode, ignorePassableBlocks, null); + } + @@ -83,7 +83,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - start.checkFinite(); + Preconditions.checkArgument(!(start instanceof Location location) || this.equals(location.getWorld()), "Location start cannot be in a different world"); + Preconditions.checkArgument(start.isFinite(), "Location start is not finite"); -+ // Paper end ++ // Paper end - Add predicate for blocks when raytracing Preconditions.checkArgument(direction != null, "Vector direction cannot be null"); direction.checkFinite(); @@ -92,10 +92,10 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 Vector dir = direction.clone().normalize().multiply(maxDistance); - Vec3 startPos = CraftLocation.toVec3D(start); -+ Vec3 startPos = io.papermc.paper.util.MCUtil.toVec3(start); // Paper ++ Vec3 startPos = io.papermc.paper.util.MCUtil.toVec3(start); // Paper - Add predicate for blocks when raytracing Vec3 endPos = startPos.add(dir.getX(), dir.getY(), dir.getZ()); - HitResult nmsHitResult = this.getHandle().clip(new ClipContext(startPos, endPos, ignorePassableBlocks ? ClipContext.Block.COLLIDER : ClipContext.Block.OUTLINE, CraftFluidCollisionMode.toNMS(fluidCollisionMode), CollisionContext.empty())); -+ HitResult nmsHitResult = this.getHandle().clip(new ClipContext(startPos, endPos, ignorePassableBlocks ? ClipContext.Block.COLLIDER : ClipContext.Block.OUTLINE, CraftFluidCollisionMode.toNMS(fluidCollisionMode), CollisionContext.empty()), canCollide); // Paper - use method with canCollide predicate ++ HitResult nmsHitResult = this.getHandle().clip(new ClipContext(startPos, endPos, ignorePassableBlocks ? ClipContext.Block.COLLIDER : ClipContext.Block.OUTLINE, CraftFluidCollisionMode.toNMS(fluidCollisionMode), CollisionContext.empty()), canCollide); // Paper - Add predicate for blocks when raytracing return CraftRayTraceResult.fromNMS(this, nmsHitResult); } @@ -103,14 +103,14 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 @Override public RayTraceResult rayTrace(Location start, Vector direction, double maxDistance, FluidCollisionMode fluidCollisionMode, boolean ignorePassableBlocks, double raySize, Predicate filter) { - RayTraceResult blockHit = this.rayTraceBlocks(start, direction, maxDistance, fluidCollisionMode, ignorePassableBlocks); -+ // Paper start ++ // Paper start - Add predicate for blocks when raytracing + return this.rayTrace(start, direction, maxDistance, fluidCollisionMode, ignorePassableBlocks, raySize, filter, null); + } + + @Override + public RayTraceResult rayTrace(io.papermc.paper.math.Position start, Vector direction, double maxDistance, FluidCollisionMode fluidCollisionMode, boolean ignorePassableBlocks, double raySize, Predicate filter, Predicate canCollide) { + RayTraceResult blockHit = this.rayTraceBlocks(start, direction, maxDistance, fluidCollisionMode, ignorePassableBlocks, canCollide); -+ // Paper end ++ // Paper end - Add predicate for blocks when raytracing Vector startVec = null; double blockHitDistance = maxDistance; diff --git a/patches/server/Allow-proper-checking-of-empty-item-stacks.patch b/patches/server/Allow-proper-checking-of-empty-item-stacks.patch index a785e97a10..62ad70af25 100644 --- a/patches/server/Allow-proper-checking-of-empty-item-stacks.patch +++ b/patches/server/Allow-proper-checking-of-empty-item-stacks.patch @@ -17,7 +17,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + public boolean isEmpty() { + return handle == null || handle.isEmpty(); + } -+ // Paper end ++ // Paper end - override isEmpty to use vanilla's impl + public static net.minecraft.world.item.ItemStack asNMSCopy(ItemStack original) { if (original instanceof CraftItemStack) { @@ -25,7 +25,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 return stack.handle == null ? net.minecraft.world.item.ItemStack.EMPTY : stack.handle.copy(); } - if (original == null || original.getType() == Material.AIR) { -+ if (original == null || original.isEmpty()) { // Paper - use isEmpty ++ if (original == null || original.isEmpty()) { // Paper - override isEmpty to use vanilla's impl; use isEmpty return net.minecraft.world.item.ItemStack.EMPTY; } diff --git a/patches/server/Don-t-fire-sync-events-during-worldgen.patch b/patches/server/Don-t-fire-sync-events-during-worldgen.patch index 725ec3420d..4120117fab 100644 --- a/patches/server/Don-t-fire-sync-events-during-worldgen.patch +++ b/patches/server/Don-t-fire-sync-events-during-worldgen.patch @@ -26,7 +26,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // CraftBukkit start private boolean addEntity(Entity entity, CreatureSpawnEvent.SpawnReason spawnReason) { org.spigotmc.AsyncCatcher.catchOp("entity add"); // Spigot -+ entity.generation = false; // Reset flag if it was added during a ServerLevel generation process ++ entity.generation = false; // Paper - Don't fire sync event during generation; Reset flag if it was added during a ServerLevel generation process // Paper start if (entity.valid) { MinecraftServer.LOGGER.error("Attempted Double World add on " + entity, new Throwable()); @@ -39,11 +39,11 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 return; } - this.level.getCraftServer().getPluginManager().callEvent(new EntityPoseChangeEvent(this.getBukkitEntity(), Pose.values()[pose.ordinal()])); -+ // Paper start - don't fire event during generation ++ // Paper start - Don't fire sync event during generation + if (!this.generation) { + this.level.getCraftServer().getPluginManager().callEvent(new EntityPoseChangeEvent(this.getBukkitEntity(), Pose.values()[pose.ordinal()])); + } -+ // Paper end - don't fire event during generation ++ // Paper end - Don't fire sync event during generation // CraftBukkit end this.entityData.set(Entity.DATA_POSE, pose); } @@ -55,15 +55,15 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 } public static Optional create(CompoundTag nbt, Level world) { -+ // Paper start - add generation bool param ++ // Paper start - Don't fire sync event during generation + return create(nbt, world, false); + } + public static Optional create(CompoundTag nbt, Level world, boolean generation) { -+ // Paper end - add generation bool param ++ // Paper end - Don't fire sync event during generation return Util.ifElse(EntityType.by(nbt).map((entitytypes) -> { return entitytypes.create(world); }), (entity) -> { -+ if (generation) entity.generation = true; // Paper - add generation bool param ++ if (generation) entity.generation = true; // Paper - Don't fire sync event during generation entity.load(nbt); }, () -> { EntityType.LOGGER.warn("Skipping Entity with id {}", nbt.getString("id")); @@ -75,11 +75,11 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 } public boolean addEffect(MobEffectInstance mobeffect, @Nullable Entity entity, EntityPotionEffectEvent.Cause cause) { -+ // Paper start - add boolean param to optionally fire the event ++ // Paper start - Don't fire sync event during generation + return this.addEffect(mobeffect, entity, cause, true); + } + public boolean addEffect(MobEffectInstance mobeffect, @Nullable Entity entity, EntityPotionEffectEvent.Cause cause, boolean fireEvent) { -+ // Paper end ++ // Paper end - Don't fire sync event during generation // org.spigotmc.AsyncCatcher.catchOp("effect add"); // Spigot // Paper - move to API if (this.isTickingEffects) { this.effectsToProcess.add(new ProcessableEffect(mobeffect, cause)); @@ -87,13 +87,13 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 override = new MobEffectInstance(mobeffect1).update(mobeffect); } -+ if (fireEvent) { // Paper ++ if (fireEvent) { // Paper - Don't fire sync event during generation EntityPotionEffectEvent event = CraftEventFactory.callEntityPotionEffectChangeEvent(this, mobeffect1, mobeffect, cause, override); -+ override = event.isOverride(); // Paper ++ override = event.isOverride(); // Paper - Don't fire sync event during generation if (event.isCancelled()) { return false; } -+ } // Paper ++ } // Paper - Don't fire sync event during generation // CraftBukkit end if (mobeffect1 == null) { @@ -102,7 +102,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 flag = true; // CraftBukkit start - } else if (event.isOverride()) { -+ } else if (override) { // Paper ++ } else if (override) { // Paper - Don't fire sync event during generation mobeffect1.update(mobeffect); this.onEffectUpdated(mobeffect1, true, entity); // CraftBukkit end @@ -115,7 +115,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (mobeffectlist != null) { - this.addEffect(new MobEffectInstance(mobeffectlist, -1), org.bukkit.event.entity.EntityPotionEffectEvent.Cause.SPIDER_SPAWN); // CraftBukkit -+ this.addEffect(new MobEffectInstance(mobeffectlist, -1), null, org.bukkit.event.entity.EntityPotionEffectEvent.Cause.SPIDER_SPAWN, world instanceof net.minecraft.server.level.ServerLevel); // CraftBukkit // Paper - only fire the effect event if this is happening in a ServerLevel ++ this.addEffect(new MobEffectInstance(mobeffectlist, -1), null, org.bukkit.event.entity.EntityPotionEffectEvent.Cause.SPIDER_SPAWN, world instanceof net.minecraft.server.level.ServerLevel); // CraftBukkit // Paper - Don't fire sync event during generation; only if this is happening in a ServerLevel } } @@ -128,7 +128,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // CraftBukkit start // try { - return EntityType.create(nbt, world.getLevel()); -+ return EntityType.create(nbt, world.getLevel(), true); // Paper - set generation bool ++ return EntityType.create(nbt, world.getLevel(), true); // Paper - Don't fire sync event during generation // } catch (Exception exception) { // return Optional.empty(); // } @@ -149,7 +149,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - public void addFreshEntityWithPassengers(Entity entity) { - this.handle.addFreshEntityWithPassengers(entity); - } -+ // Paper start - don't override these methods so all entities are run through addFreshEntity ++ // Paper start - Don't fire sync event during generation; don't override these methods so all entities are run through addFreshEntity + // @Override + // public void addFreshEntityWithPassengers(Entity arg0, CreatureSpawnEvent.SpawnReason arg1) { + // this.handle.addFreshEntityWithPassengers(arg0, arg1); @@ -159,7 +159,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + // public void addFreshEntityWithPassengers(Entity entity) { + // this.handle.addFreshEntityWithPassengers(entity); + // } -+ // Paper end - don't override these methods ++ // Paper end - Don't fire sync event during generation; don't override these methods @Override public ServerLevel getMinecraftWorld() { @@ -186,7 +186,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - } - super.addFreshEntityWithPassengers(arg0, arg1); - } -+ // Paper start - don't override these methods so all entities are run through addFreshEntity ++ // Paper start - Don't fire sync event during generation; don't override these methods so all entities are run through addFreshEntity + // @Override + // public void addFreshEntityWithPassengers(Entity entity) { + // if (this.structureTransformer != null && !this.structureTransformer.transformEntity(entity)) { @@ -202,7 +202,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + // } + // super.addFreshEntityWithPassengers(arg0, arg1); + // } -+ // Paper end - don't override these methods ++ // Paper end - Don't fire sync event during generation; don't override these methods public boolean setCraftBlock(BlockPos position, CraftBlockState craftBlockState, int i, int j) { if (this.structureTransformer != null) { diff --git a/patches/server/Fix-NPE-in-SculkBloomEvent-world-access.patch b/patches/server/Fix-NPE-in-SculkBloomEvent-world-access.patch index 1a3c35ddcc..d34e702ea7 100644 --- a/patches/server/Fix-NPE-in-SculkBloomEvent-world-access.patch +++ b/patches/server/Fix-NPE-in-SculkBloomEvent-world-access.patch @@ -15,13 +15,13 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - this.catalystListener.level = this.level; // CraftBukkit } -+ // Paper start ++ // Paper start - Fix NPE in SculkBloomEvent world access + @Override + public void setLevel(Level level) { + super.setLevel(level); + this.catalystListener.sculkSpreader.level = level; + } -+ // Paper end ++ // Paper end - Fix NPE in SculkBloomEvent world access + public static void serverTick(Level world, BlockPos pos, BlockState state, SculkCatalystBlockEntity blockEntity) { org.bukkit.craftbukkit.event.CraftEventFactory.sourceBlockOverride = blockEntity.getBlockPos(); // CraftBukkit - SPIGOT-7068: Add source block override, not the most elegant way but better than passing down a BlockPosition up to five methods deep. @@ -37,7 +37,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 this.positionSource = positionSource; this.sculkSpreader = SculkSpreader.createLevelSpreader(); - this.sculkSpreader.level = this.level; // CraftBukkit -+ // this.sculkSpreader.level = this.level; // CraftBukkit // Paper - bad fix ++ // this.sculkSpreader.level = this.level; // CraftBukkit // Paper - Fix NPE in SculkBloomEvent world access } @Override diff --git a/patches/server/Fix-missing-map-initialize-event-call.patch b/patches/server/Fix-missing-map-initialize-event-call.patch index d7b54db21d..ea439a41b0 100644 --- a/patches/server/Fix-missing-map-initialize-event-call.patch +++ b/patches/server/Fix-missing-map-initialize-event-call.patch @@ -18,7 +18,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - MapItemSavedData worldmap = (MapItemSavedData) this.getServer().overworld().getDataStorage().get(MapItemSavedData.factory(), id); - if (worldmap != null) { - worldmap.id = id; -+ // Paper start - Call missing map initialize event & set id ++ // Paper start - Call missing map initialize event and set id + final DimensionDataStorage storage = this.getServer().overworld().getDataStorage(); + + final net.minecraft.world.level.saveddata.SavedData existing = storage.cache.get(id); @@ -38,7 +38,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - // CraftBukkit end + + return existing instanceof MapItemSavedData data ? data : null; -+ // Paper end ++ // Paper end - Call missing map initialize event and set id } @Override diff --git a/patches/server/Fix-several-issues-with-EntityBreedEvent.patch b/patches/server/Fix-several-issues-with-EntityBreedEvent.patch index 51966f9eeb..7e66945dd5 100644 --- a/patches/server/Fix-several-issues-with-EntityBreedEvent.patch +++ b/patches/server/Fix-several-issues-with-EntityBreedEvent.patch @@ -18,10 +18,10 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 int i = this.getAge(); if (!this.level().isClientSide && i == 0 && this.canFallInLove()) { -+ final ItemStack breedCopy = itemstack.copy(); // Paper ++ final ItemStack breedCopy = itemstack.copy(); // Paper - Fix EntityBreedEvent copying this.usePlayerItem(player, hand, itemstack); - this.setInLove(player); -+ this.setInLove(player, breedCopy); // Paper ++ this.setInLove(player, breedCopy); // Paper - Fix EntityBreedEvent copying return InteractionResult.SUCCESS; } @@ -29,18 +29,18 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 return this.inLove <= 0; } -+ @Deprecated @io.papermc.paper.annotation.DoNotUse // Paper ++ @Deprecated @io.papermc.paper.annotation.DoNotUse // Paper - Fix EntityBreedEvent copying public void setInLove(@Nullable Player player) { -+ // Paper start - pass breed stack ++ // Paper start - Fix EntityBreedEvent copying + this.setInLove(player, null); + } + public void setInLove(@Nullable Player player, @Nullable ItemStack breedItemCopy) { + if (breedItemCopy != null) this.breedItem = breedItemCopy; -+ // Paper end ++ // Paper end - Fix EntityBreedEvent copying // CraftBukkit start EntityEnterLoveModeEvent entityEnterLoveModeEvent = CraftEventFactory.callEntityEnterLoveModeEvent(player, this, 600); if (entityEnterLoveModeEvent.isCancelled()) { -+ this.breedItem = null; // Paper - clear if cancelled ++ this.breedItem = null; // Paper - Fix EntityBreedEvent copying; clear if cancelled return; } this.inLove = entityEnterLoveModeEvent.getTicksInLove(); @@ -49,7 +49,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 this.loveCause = player.getUUID(); } - this.breedItem = player.getInventory().getSelected(); // CraftBukkit -+ // Paper - set breed item in better place ++ // Paper - Fix EntityBreedEvent copying; set breed item in better place this.level().broadcastEntityEvent(this, (byte) 18); } @@ -61,10 +61,10 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 this.usePlayerItem(player, hand, itemstack); this.ageUp((int) ((float) (-this.getAge() / 20) * 0.1F), true); } else if (!this.level().isClientSide && this.getAge() == 0 && this.canFallInLove()) { -+ final ItemStack breedCopy = itemstack.copy(); // Paper ++ final ItemStack breedCopy = itemstack.copy(); // Paper - Fix EntityBreedEvent copying this.usePlayerItem(player, hand, itemstack); - this.setInLove(player); -+ this.setInLove(player, breedCopy); // Paper ++ this.setInLove(player, breedCopy); // Paper - Fix EntityBreedEvent copying } else { if (this.level().isClientSide || this.isSitting() || this.isInWater()) { return InteractionResult.PASS; @@ -77,7 +77,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 boolean bl2 = this.isTamed() && this.getAge() == 0 && this.canFallInLove(); if (bl2) { - this.setInLove(player); -+ this.setInLove(player, item.copy()); // Paper ++ this.setInLove(player, item.copy()); // Paper - Fix EntityBreedEvent copying } boolean bl3 = this.isBaby(); @@ -90,7 +90,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (!this.level().isClientSide && this.isTamed() && this.getAge() == 0 && !this.isInLove()) { flag = true; - this.setInLove(player); -+ this.setInLove(player, item.copy()); // Paper ++ this.setInLove(player, item.copy()); // Paper - Fix EntityBreedEvent copying } } else if (item.is(Items.GOLDEN_APPLE) || item.is(Items.ENCHANTED_GOLDEN_APPLE)) { f = 10.0F; @@ -99,7 +99,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (!this.level().isClientSide && this.isTamed() && this.getAge() == 0 && !this.isInLove()) { flag = true; - this.setInLove(player); -+ this.setInLove(player, item.copy()); // Paper ++ this.setInLove(player, item.copy()); // Paper - Fix EntityBreedEvent copying } } @@ -112,7 +112,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (this.isTamed() && this.getAge() == 0 && this.canFallInLove()) { flag = true; - this.setInLove(player); -+ this.setInLove(player, item.copy()); // Paper ++ this.setInLove(player, item.copy()); // Paper - Fix EntityBreedEvent copying } } diff --git a/patches/server/Fix-silent-equipment-change-for-mobs.patch b/patches/server/Fix-silent-equipment-change-for-mobs.patch index 87c0c6f145..13d2c5f6ac 100644 --- a/patches/server/Fix-silent-equipment-change-for-mobs.patch +++ b/patches/server/Fix-silent-equipment-change-for-mobs.patch @@ -12,22 +12,22 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 @Override public void setItemSlot(EquipmentSlot slot, ItemStack stack) { -+ // Paper start ++ // Paper start - Fix silent equipment change + setItemSlot(slot, stack, false); + } + + @Override + public void setItemSlot(EquipmentSlot slot, ItemStack stack, boolean silent) { -+ // Paper end ++ // Paper end - Fix silent equipment change this.verifyEquippedItem(stack); switch (slot.getType()) { case HAND: - this.onEquipItem(slot, (ItemStack) this.handItems.set(slot.getIndex(), stack), stack); -+ this.onEquipItem(slot, (ItemStack) this.handItems.set(slot.getIndex(), stack), stack, silent); // Paper ++ this.onEquipItem(slot, (ItemStack) this.handItems.set(slot.getIndex(), stack), stack, silent); // Paper - Fix silent equipment change break; case ARMOR: - this.onEquipItem(slot, (ItemStack) this.armorItems.set(slot.getIndex(), stack), stack); -+ this.onEquipItem(slot, (ItemStack) this.armorItems.set(slot.getIndex(), stack), stack, silent); // Paper ++ this.onEquipItem(slot, (ItemStack) this.armorItems.set(slot.getIndex(), stack), stack, silent); // Paper - Fix silent equipment change } } @@ -41,8 +41,8 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 @Override - public void setItemSlot(EquipmentSlot slot, ItemStack stack) { - super.setItemSlot(slot, stack); -+ public void setItemSlot(EquipmentSlot slot, ItemStack stack, boolean silent) { // Paper -+ super.setItemSlot(slot, stack, silent); // Paper ++ public void setItemSlot(EquipmentSlot slot, ItemStack stack, boolean silent) { // Paper - Fix silent equipment change ++ super.setItemSlot(slot, stack, silent); // Paper - Fix silent equipment change if (!this.level().isClientSide) { this.reassessWeaponGoal(); } @@ -58,7 +58,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + // notify observers if the block state is the same and the Y level equals the original y level (for mega trees) + // blocks at the same Y level with the same state can be assumed to be saplings which trigger observers regardless of if the + // tree grew or not -+ if (craftBlockState.getPosition().getY() == pos.getY() && this.getBlockState(craftBlockState.getPosition()) == craftBlockState.getHandle()) { ++ if (craftBlockState.getPosition().getY() == pos.getY() && this.getBlockState(craftBlockState.getPosition()) == craftBlockState.getHandle()) { // Paper - Fix silent equipment change this.notifyAndUpdatePhysics(craftBlockState.getPosition(), null, craftBlockState.getHandle(), craftBlockState.getHandle(), craftBlockState.getHandle(), craftBlockState.getFlag(), 512); } } diff --git a/patches/server/Fix-spigot-s-Forced-Stats.patch b/patches/server/Fix-spigot-s-Forced-Stats.patch index 5bf34f6de2..bf67dfe2ba 100644 --- a/patches/server/Fix-spigot-s-Forced-Stats.patch +++ b/patches/server/Fix-spigot-s-Forced-Stats.patch @@ -29,13 +29,18 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 } } -+ // Spigot start // Paper start - moved after stat fetching for player state file. ++ // Paper start - Moved after stat fetching for player state file ++ // Moves the loading after vanilla loading, so it overrides the values. ++ // Disables saving any forced stats, so it stays at the same value (without enabling disableStatSaving) ++ // Fixes stat initialization to not cause a NullPointerException ++ // Spigot start + for ( Map.Entry entry : org.spigotmc.SpigotConfig.forcedStats.entrySet() ) + { + Stat wrapper = Stats.CUSTOM.get(java.util.Objects.requireNonNull(BuiltInRegistries.CUSTOM_STAT.get(entry.getKey()))); // Paper - ensured by SpigotConfig#stats + this.stats.put( wrapper, entry.getValue().intValue() ); + } -+ // Spigot end // Paper end - moved after stat fetching for player state file. ++ // Spigot end ++ // Paper end - Moved after stat fetching for player state file } public void save() { diff --git a/patches/server/Fix-strikeLightningEffect-powers-lightning-rods-and-.patch b/patches/server/Fix-strikeLightningEffect-powers-lightning-rods-and-.patch index 8ecfd7c7a2..fbf582675c 100644 --- a/patches/server/Fix-strikeLightningEffect-powers-lightning-rods-and-.patch +++ b/patches/server/Fix-strikeLightningEffect-powers-lightning-rods-and-.patch @@ -14,7 +14,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 private final Set hitEntities = Sets.newHashSet(); private int blocksSetOnFire; - public boolean isSilent = false; // Spigot -+ public boolean isEffect; // Paper ++ public boolean isEffect; // Paper - Properly handle lightning effects api public LightningBolt(EntityType type, Level world) { super(type, world); @@ -23,7 +23,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 public void tick() { super.tick(); - if (!this.isSilent && this.life == 2) { // Spigot -+ if (!this.isEffect && this.life == 2) { // Spigot // Paper ++ if (!this.isEffect && this.life == 2) { // Spigot // Paper - Properly handle lightning effects api if (this.level().isClientSide()) { this.level().playLocalSound(this.getX(), this.getY(), this.getZ(), SoundEvents.LIGHTNING_BOLT_THUNDER, SoundSource.WEATHER, 10000.0F, 0.8F + this.random.nextFloat() * 0.2F, false); this.level().playLocalSound(this.getX(), this.getY(), this.getZ(), SoundEvents.LIGHTNING_BOLT_IMPACT, SoundSource.WEATHER, 2.0F, 0.5F + this.random.nextFloat() * 0.2F, false); @@ -32,7 +32,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 } - if (this.life >= 0 && !this.visualOnly) { // CraftBukkit - add !this.visualOnly -+ if (this.life >= 0 && !this.isEffect) { // CraftBukkit - add !this.visualOnly // Paper - undo ++ if (this.life >= 0 && !this.isEffect) { // CraftBukkit - add !this.visualOnly // Paper - Properly handle lightning effects api if (!(this.level() instanceof ServerLevel)) { this.level().setSkyFlashTime(2); } else if (!this.visualOnly) { @@ -41,7 +41,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 private void spawnFire(int spreadAttempts) { - if (!this.visualOnly && !this.level().isClientSide && this.level().getGameRules().getBoolean(GameRules.RULE_DOFIRETICK)) { -+ if (!this.visualOnly && !this.isEffect && !this.level().isClientSide && this.level().getGameRules().getBoolean(GameRules.RULE_DOFIRETICK)) { // Paper ++ if (!this.visualOnly && !this.isEffect && !this.level().isClientSide && this.level().getGameRules().getBoolean(GameRules.RULE_DOFIRETICK)) { // Paper - Properly handle lightning effects api BlockPos blockposition = this.blockPosition(); BlockState iblockdata = BaseFireBlock.getState(this.level(), blockposition); @@ -54,7 +54,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 LightningBolt lightning = EntityType.LIGHTNING_BOLT.create(this.world); lightning.moveTo(loc.getX(), loc.getY(), loc.getZ()); - lightning.setVisualOnly(isVisual); -+ lightning.isEffect = isVisual; // Paper ++ lightning.isEffect = isVisual; // Paper - Properly handle lightning effects api this.world.strikeLightning(lightning, LightningStrikeEvent.Cause.CUSTOM); return (LightningStrike) lightning.getBukkitEntity(); } @@ -72,7 +72,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 lightning.moveTo( loc.getX(), loc.getY(), loc.getZ() ); - lightning.visualOnly = true; - lightning.isSilent = isSilent; -+ lightning.isEffect = true; // Paper ++ lightning.isEffect = true; // Paper - Properly handle lightning effects api CraftWorld.this.world.strikeLightning( lightning, LightningStrikeEvent.Cause.CUSTOM ); return (LightningStrike) lightning.getBukkitEntity(); } @@ -85,7 +85,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 @Override public boolean isEffect() { - return this.getHandle().visualOnly; -+ return this.getHandle().isEffect; // Paper ++ return this.getHandle().isEffect; // Paper - Properly handle lightning effects api } public int getFlashes() { @@ -94,7 +94,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 public boolean isSilent() { - return CraftLightningStrike.this.getHandle().isSilent; -+ return false; // Paper - the concept of isSilent doesn't exist as sound is controlled by the client ++ return false; // Paper - Properly handle lightning effects api; the concept of isSilent doesn't exist as sound is controlled by the client } }; diff --git a/patches/server/Lag-compensation-ticks.patch b/patches/server/Lag-compensation-ticks.patch index 997b3cf929..89d9c2f46a 100644 --- a/patches/server/Lag-compensation-ticks.patch +++ b/patches/server/Lag-compensation-ticks.patch @@ -89,7 +89,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + boolean shouldLagCompensate = this.useItem.getItem().isEdible() && this.eatStartTime != -1 && (System.nanoTime() - this.eatStartTime) > ((1 + this.totalEatTimeTicks) * 50 * (1000 * 1000)); + if ((--this.useItemRemaining == 0 || shouldLagCompensate) && !this.level().isClientSide && !stack.useOnRelease()) { + this.useItemRemaining = 0; -+ // Paper end ++ // Paper end - lag compensate eating this.completeUsingItem(); } @@ -101,7 +101,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + // Paper start - lag compensate eating + this.useItemRemaining = this.totalEatTimeTicks = itemstack.getUseDuration(); + this.eatStartTime = System.nanoTime(); -+ // Paper end ++ // Paper end - lag compensate eating if (!this.level().isClientSide) { this.setLivingEntityFlag(1, true); this.setLivingEntityFlag(2, hand == InteractionHand.OFF_HAND); @@ -113,7 +113,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + // Paper start - lag compensate eating + this.useItemRemaining = this.totalEatTimeTicks = 0; + this.eatStartTime = -1L; -+ // Paper end ++ // Paper end - lag compensate eating } } @@ -125,7 +125,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + // Paper start - lag compensate eating + this.useItemRemaining = this.totalEatTimeTicks = 0; + this.eatStartTime = -1L; -+ // Paper end ++ // Paper end - lag compensate eating } public boolean isBlocking() { diff --git a/patches/server/Make-setVelocity-method-of-Fireballs-change-the-trav.patch b/patches/server/Make-setVelocity-method-of-Fireballs-change-the-trav.patch index 1ea3f7595f..2d6a270440 100644 --- a/patches/server/Make-setVelocity-method-of-Fireballs-change-the-trav.patch +++ b/patches/server/Make-setVelocity-method-of-Fireballs-change-the-trav.patch @@ -23,7 +23,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + this.getHandle().zPower = velocity.getZ(); + update(); + } -+ // Paper end ++ // Paper end - set direction without normalizing + @Override public AbstractHurtingProjectile getHandle() { diff --git a/patches/server/Optimise-chunk-tick-iteration.patch b/patches/server/Optimise-chunk-tick-iteration.patch index dd52ff7654..e5a5615f81 100644 --- a/patches/server/Optimise-chunk-tick-iteration.patch +++ b/patches/server/Optimise-chunk-tick-iteration.patch @@ -39,7 +39,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 players[NearbyMapType.GENERAL_REALLY_SMALL.ordinal()].update(chunk.x, chunk.z, GENERAL_REALLY_SMALL_VIEW_DISTANCE); players[NearbyMapType.TICK_VIEW_DISTANCE.ordinal()].update(chunk.x, chunk.z, ChunkSystem.getTickViewDistance(player)); players[NearbyMapType.VIEW_DISTANCE.ordinal()].update(chunk.x, chunk.z, ChunkSystem.getLoadViewDistance(player)); -+ players[NearbyMapType.SPAWN_RANGE.ordinal()].update(chunk.x, chunk.z, SPAWN_RANGE_VIEW_DISTANCE); ++ players[NearbyMapType.SPAWN_RANGE.ordinal()].update(chunk.x, chunk.z, SPAWN_RANGE_VIEW_DISTANCE); // Paper - optimise chunk iteration } public TrackedChunk getChunk(final ChunkPos pos) { @@ -103,7 +103,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + public void broadcastChanges(LevelChunk chunk) { - if (this.hasChangedSections || !this.skyChangedLightSectionFilter.isEmpty() || !this.blockChangedLightSectionFilter.isEmpty()) { -+ if (this.needsBroadcastChanges()) { // Paper - moved into above, other logic needs to call ++ if (this.needsBroadcastChanges()) { // Paper - optimise chunk tick iteration; moved into above, other logic needs to call Level world = chunk.getLevel(); List list; @@ -135,7 +135,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // Paper end - private static double euclideanDistanceSquared(ChunkPos pos, Entity entity) { -+ public static double euclideanDistanceSquared(ChunkPos pos, Entity entity) { // Paper - optimise chunk iteration - public ++ public static double euclideanDistanceSquared(ChunkPos pos, Entity entity) { // Paper - optimise chunk iteration; public double d0 = (double) SectionPos.sectionToBlockCoord(pos.x, 8); double d1 = (double) SectionPos.sectionToBlockCoord(pos.z, 8); double d2 = d0 - entity.getX(); diff --git a/patches/server/Optimise-nearby-player-retrieval.patch b/patches/server/Optimise-nearby-player-retrieval.patch index a3e9b5de8e..f50e37ded7 100644 --- a/patches/server/Optimise-nearby-player-retrieval.patch +++ b/patches/server/Optimise-nearby-player-retrieval.patch @@ -148,7 +148,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 T livingEntity = null; for(T livingEntity2 : entityList) { -+ // Paper start - move up ++ // Paper start - optimise nearby player retrieval; move up + // don't check entities outside closest range + double e = livingEntity2.distanceToSqr(x, y, z); + if (d == -1.0D || e < d) { @@ -156,7 +156,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (targetPredicate.test(entity, livingEntity2)) { - double e = livingEntity2.distanceToSqr(x, y, z); - if (d == -1.0D || e < d) { -+ // Paper - move up ++ // Paper - optimise nearby player retrieval; move up d = e; livingEntity = livingEntity2; } diff --git a/patches/server/Remove-streams-for-villager-AI.patch b/patches/server/Remove-streams-for-villager-AI.patch index ca687e272e..a77b074426 100644 --- a/patches/server/Remove-streams-for-villager-AI.patch +++ b/patches/server/Remove-streams-for-villager-AI.patch @@ -13,7 +13,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 this.status = Behavior.Status.RUNNING; this.orderPolicy.apply(this.behaviors); - this.runningPolicy.apply(this.behaviors.stream(), world, entity, time); -+ this.runningPolicy.apply(this.behaviors.entries, world, entity, time); ++ this.runningPolicy.apply(this.behaviors.entries, world, entity, time); // Paper - Remove streams return true; } else { return false; @@ -26,13 +26,13 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - }).forEach((task) -> { - task.tickOrStop(world, entity, time); - }); -+ // Paper start ++ // Paper start - Remove streams + for (BehaviorControl task : this.behaviors) { + if (task.getStatus() == Behavior.Status.RUNNING) { + task.tickOrStop(world, entity, time); + } + } -+ // Paper end ++ // Paper end - Remove streams if (this.behaviors.stream().noneMatch((task) -> { return task.getStatus() == Behavior.Status.RUNNING; })) { @@ -45,13 +45,13 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - }).forEach((task) -> { - task.doStop(world, entity, time); - }); -+ // Paper start ++ // Paper start - Remove streams + for (BehaviorControl behavior : this.behaviors) { + if (behavior.getStatus() == Behavior.Status.RUNNING) { + behavior.doStop(world, entity, time); + } + } -+ // Paper end ++ // Paper end - Remove streams this.exitErasedMemories.forEach(entity.getBrain()::eraseMemory); } @@ -65,7 +65,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - }).filter((task) -> { - return task.tryStart(world, entity, time); - }).findFirst(); -+ // Paper start - remove streams ++ // Paper start - Remove streams + public void apply(List>> tasks, ServerLevel world, E entity, long time) { + for (ShufflingList.WeightedEntry> task : tasks) { + final BehaviorControl behavior = task.getData(); @@ -73,7 +73,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + break; + } + } -+ // Paper end - remove streams ++ // Paper end - Remove streams } }, TRY_ALL { @@ -84,7 +84,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 - }).forEach((task) -> { - task.tryStart(world, entity, time); - }); -+ // Paper start - remove streams ++ // Paper start - Remove streams + public void apply(List>> tasks, ServerLevel world, E entity, long time) { + for (ShufflingList.WeightedEntry> task : tasks) { + final BehaviorControl behavior = task.getData(); @@ -92,12 +92,12 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + behavior.tryStart(world, entity, time); + } + } -+ // Paper end - remove streams ++ // Paper end - Remove streams } }; - public abstract void apply(Stream> tasks, ServerLevel world, E entity, long time); -+ public abstract void apply(List>> tasks, ServerLevel world, E entity, long time); // Paper - remove streams ++ public abstract void apply(List>> tasks, ServerLevel world, E entity, long time); // Paper - Remove streams } } diff --git a/src/main/java/net/minecraft/world/entity/ai/behavior/ShufflingList.java b/src/main/java/net/minecraft/world/entity/ai/behavior/ShufflingList.java @@ -126,7 +126,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 }); - list.sort(Comparator.comparingDouble(entity::distanceToSqr)); + list.sort((e1, e2) -> Double.compare(entity.distanceToSqr(e1), entity.distanceToSqr(e2))); // better to take the sort perf hit than using line of sight more than we need to. -+ // Paper start - remove streams ++ // Paper start - Remove streams // Paper start - remove streams in favour of lists ItemEntity nearest = null; - for (ItemEntity entityItem : list) { @@ -134,7 +134,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + for (int i = 0; i < list.size(); i++) { + ItemEntity entityItem = list.get(i); + if (entity.hasLineOfSight(entityItem)) { -+ // Paper end - remove streams ++ // Paper end - Remove streams nearest = entityItem; break; } diff --git a/patches/server/Update-entity-data-when-attaching-firework-to-entity.patch b/patches/server/Update-entity-data-when-attaching-firework-to-entity.patch index 44a0fd245b..e3b90987ad 100644 --- a/patches/server/Update-entity-data-when-attaching-firework-to-entity.patch +++ b/patches/server/Update-entity-data-when-attaching-firework-to-entity.patch @@ -17,7 +17,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + // Paper start - update entity data + this.getHandle().getEntityData().set(FireworkRocketEntity.DATA_ATTACHED_TO_TARGET, + entity != null ? java.util.OptionalInt.of(entity.getEntityId()) : java.util.OptionalInt.empty()); -+ // Paper end ++ // Paper end - update entity data return true; } diff --git a/patches/server/Use-correct-variable-for-initializing-CraftLootTable.patch b/patches/server/Use-correct-variable-for-initializing-CraftLootTable.patch index 3faa78a066..7c396cd8a5 100644 --- a/patches/server/Use-correct-variable-for-initializing-CraftLootTable.patch +++ b/patches/server/Use-correct-variable-for-initializing-CraftLootTable.patch @@ -13,7 +13,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 // CraftBukkit start map1.forEach((key, lootTable) -> { - if (object instanceof LootTable table) { -+ if (lootTable instanceof LootTable table) { // Paper - use correct variable ++ if (lootTable instanceof LootTable table) { // Paper - Use correct variable for initializing CraftLootTable table.craftLootTable = new CraftLootTable(CraftNamespacedKey.fromMinecraft(key.location()), table); } }); diff --git a/patches/server/fix-secure-profile-with-proxy-online-mode.patch b/patches/server/fix-secure-profile-with-proxy-online-mode.patch index 81836f4098..b5d87c41f0 100644 --- a/patches/server/fix-secure-profile-with-proxy-online-mode.patch +++ b/patches/server/fix-secure-profile-with-proxy-online-mode.patch @@ -17,7 +17,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + return dedicatedserverproperties.enforceSecureProfile + && io.papermc.paper.configuration.GlobalConfiguration.get().proxies.isProxyOnlineMode() + && this.services.canValidateProfileKeys(); -+ // Paper end ++ // Paper end - fix secure profile with proxy online mode } @Override