2023-08-25 01:53:02 +02:00
|
|
|
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
|
|
|
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
|
|
|
Date: Wed, 23 Aug 2023 13:22:09 -0700
|
2024-08-31 20:29:50 +02:00
|
|
|
Subject: [PATCH] Fix slot desync
|
2023-08-25 01:53:02 +02:00
|
|
|
|
2024-08-31 20:29:50 +02:00
|
|
|
General patch fixing slot desyncs between the server and client that
|
|
|
|
result from cancelled events/paper introduced logic.
|
|
|
|
|
|
|
|
Co-authored-by: Minecrell <minecrell@minecrell.net>
|
|
|
|
Co-authored-by: Newwind <support@newwindserver.com>
|
2023-08-25 01:53:02 +02:00
|
|
|
|
2024-05-26 23:30:45 +02:00
|
|
|
diff --git a/src/main/java/net/minecraft/server/level/ServerPlayer.java b/src/main/java/net/minecraft/server/level/ServerPlayer.java
|
2024-11-29 02:39:40 +01:00
|
|
|
index df2c899988429cb68b0abbb829d378e6a2ed022b..0c5e67db809a9d741cb27d97d42dd9e71fda44eb 100644
|
2024-05-26 23:30:45 +02:00
|
|
|
--- a/src/main/java/net/minecraft/server/level/ServerPlayer.java
|
|
|
|
+++ b/src/main/java/net/minecraft/server/level/ServerPlayer.java
|
2024-10-24 12:11:32 +02:00
|
|
|
@@ -460,6 +460,7 @@ public class ServerPlayer extends net.minecraft.world.entity.player.Player {
|
2024-05-26 23:30:45 +02:00
|
|
|
|
|
|
|
// Use method to resend items in hands in case of client desync, because the item use got cancelled.
|
|
|
|
// For example, when cancelling the leash event
|
|
|
|
+ @Deprecated // Paper - this shouldn't be used, use the regular sendAllDataToRemote call to resync all
|
|
|
|
public void resendItemInHands() {
|
|
|
|
this.containerMenu.findSlot(this.getInventory(), this.getInventory().selected).ifPresent(s -> {
|
|
|
|
this.containerSynchronizer.sendSlotChange(this.containerMenu, s, this.getMainHandItem());
|
2024-08-31 20:29:50 +02:00
|
|
|
diff --git a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
|
2024-10-31 17:25:52 +01:00
|
|
|
index 38730e11118bf71d167a18b807e06c20ea0d63d0..5be7304c8417e2987837d1c6ce8b80231fd29c51 100644
|
2024-08-31 20:29:50 +02:00
|
|
|
--- a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
|
|
|
|
+++ b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
|
2024-10-31 17:25:52 +01:00
|
|
|
@@ -2747,10 +2747,11 @@ public class ServerGamePacketListenerImpl extends ServerCommonPacketListenerImpl
|
2024-08-31 20:29:50 +02:00
|
|
|
// Refresh the current entity metadata
|
|
|
|
entity.refreshEntityData(ServerGamePacketListenerImpl.this.player);
|
|
|
|
// SPIGOT-7136 - Allays
|
|
|
|
- if (entity instanceof Allay) {
|
|
|
|
+ if (entity instanceof Allay || entity instanceof net.minecraft.world.entity.animal.horse.AbstractHorse) { // Paper - Fix horse armor desync
|
|
|
|
ServerGamePacketListenerImpl.this.send(new ClientboundSetEquipmentPacket(entity.getId(), Arrays.stream(net.minecraft.world.entity.EquipmentSlot.values()).map((slot) -> Pair.of(slot, ((LivingEntity) entity).getItemBySlot(slot).copy())).collect(Collectors.toList())));
|
|
|
|
- ServerGamePacketListenerImpl.this.player.containerMenu.sendAllDataToRemote();
|
|
|
|
}
|
|
|
|
+
|
|
|
|
+ ServerGamePacketListenerImpl.this.player.containerMenu.sendAllDataToRemote(); // Paper - fix slot desync - always refresh player inventory
|
|
|
|
}
|
|
|
|
|
|
|
|
if (event.isCancelled()) {
|
2024-06-14 18:02:15 +02:00
|
|
|
diff --git a/src/main/java/net/minecraft/world/entity/Entity.java b/src/main/java/net/minecraft/world/entity/Entity.java
|
Rework async chunk api implementation
Firstly, the old methods all routed to the CompletableFuture method.
However, the CF method could not guarantee that if the caller
was off-main that the future would be "completed" on-main. Since
the callback methods used the CF one, this meant that the callback
methods did not guarantee that the callbacks were to be called on
the main thread.
Now, all methods route to getChunkAtAsync(x, z, gen, urgent, cb)
so that the methods with the callback are guaranteed to invoke
the callback on the main thread. The CF behavior remains unchanged;
it may still appear to complete on main if invoked off-main.
Secondly, remove the scheduleOnMain invocation in the async
chunk completion. This unnecessarily delays the callback
by 1 tick.
Thirdly, add getChunksAtAsync(minX, minZ, maxX, maxZ, ...) which
will load chunks within an area. This method is provided as a helper
as keeping all chunks loaded within an area can be complicated to
implement for plugins (due to the lacking ticket API), and is
already implemented internally anyways.
Fourthly, remove the ticket addition that occured with getChunkAt
and getChunkAtAsync. The ticket addition may delay the unloading
of the chunk unnecessarily. It also fixes a very rare timing bug
where the future/callback would be completed after the chunk
unloads.
2024-11-19 07:34:32 +01:00
|
|
|
index e2ca84fb27cff54eada6ca1c7a96a29d1dbbb4e5..2342892db8b2bb1994727e611abb820f8104e486 100644
|
2024-06-14 18:02:15 +02:00
|
|
|
--- a/src/main/java/net/minecraft/world/entity/Entity.java
|
|
|
|
+++ b/src/main/java/net/minecraft/world/entity/Entity.java
|
2024-11-04 18:42:38 +01:00
|
|
|
@@ -2753,8 +2753,9 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
|
2024-06-14 18:02:15 +02:00
|
|
|
if (!this.level().isClientSide()) {
|
|
|
|
// CraftBukkit start - fire PlayerLeashEntityEvent
|
|
|
|
if (CraftEventFactory.callPlayerLeashEntityEvent(this, player, player, hand).isCancelled()) {
|
|
|
|
- ((ServerPlayer) player).resendItemInHands(); // SPIGOT-7615: Resend to fix client desync with used item
|
|
|
|
+ // ((ServerPlayer) player).resendItemInHands(); // SPIGOT-7615: Resend to fix client desync with used item // Paper - Fix inventory desync
|
|
|
|
((ServerPlayer) player).connection.send(new ClientboundSetEntityLinkPacket(this, leashable.getLeashHolder()));
|
|
|
|
+ player.containerMenu.sendAllDataToRemote(); // Paper - Fix inventory desync
|
|
|
|
return InteractionResult.PASS;
|
|
|
|
}
|
|
|
|
// CraftBukkit end
|
2024-05-26 23:30:45 +02:00
|
|
|
diff --git a/src/main/java/net/minecraft/world/entity/animal/Cow.java b/src/main/java/net/minecraft/world/entity/animal/Cow.java
|
2024-10-24 12:11:32 +02:00
|
|
|
index d99760f943846a1cfe5d0ec97313f453004feb98..3e00bbff266fc71b07014e7e047d77b7f809239f 100644
|
2024-05-26 23:30:45 +02:00
|
|
|
--- a/src/main/java/net/minecraft/world/entity/animal/Cow.java
|
|
|
|
+++ b/src/main/java/net/minecraft/world/entity/animal/Cow.java
|
|
|
|
@@ -101,6 +101,7 @@ public class Cow extends Animal {
|
|
|
|
PlayerBucketFillEvent event = CraftEventFactory.callPlayerBucketFillEvent((ServerLevel) player.level(), player, this.blockPosition(), this.blockPosition(), null, itemstack, Items.MILK_BUCKET, hand);
|
|
|
|
|
|
|
|
if (event.isCancelled()) {
|
|
|
|
+ player.containerMenu.sendAllDataToRemote(); // Paper - Fix inventory desync
|
|
|
|
return InteractionResult.PASS;
|
|
|
|
}
|
|
|
|
// CraftBukkit end
|
|
|
|
diff --git a/src/main/java/net/minecraft/world/entity/animal/goat/Goat.java b/src/main/java/net/minecraft/world/entity/animal/goat/Goat.java
|
2024-10-25 13:52:04 +02:00
|
|
|
index 4c6dc427b90012b0945e073dd905dc7e8d1bec82..76aca47d8638d5c37c57d3a59fa7f8ceaa5a53b4 100644
|
2024-05-26 23:30:45 +02:00
|
|
|
--- a/src/main/java/net/minecraft/world/entity/animal/goat/Goat.java
|
|
|
|
+++ b/src/main/java/net/minecraft/world/entity/animal/goat/Goat.java
|
2024-10-24 12:11:32 +02:00
|
|
|
@@ -238,6 +238,7 @@ public class Goat extends Animal {
|
2024-05-26 23:30:45 +02:00
|
|
|
PlayerBucketFillEvent event = CraftEventFactory.callPlayerBucketFillEvent((ServerLevel) player.level(), player, this.blockPosition(), this.blockPosition(), null, itemstack, Items.MILK_BUCKET, hand);
|
|
|
|
|
|
|
|
if (event.isCancelled()) {
|
|
|
|
+ player.containerMenu.sendAllDataToRemote(); // Paper - Fix inventory desync
|
|
|
|
return InteractionResult.PASS;
|
|
|
|
}
|
|
|
|
// CraftBukkit end
|
|
|
|
diff --git a/src/main/java/net/minecraft/world/item/ArmorStandItem.java b/src/main/java/net/minecraft/world/item/ArmorStandItem.java
|
2024-10-24 12:11:32 +02:00
|
|
|
index 15c7c2417db1661c77c35455b59a77b1d1055858..cb4baebe22eeab17aed67a5ecc506b932fe2230b 100644
|
2024-05-26 23:30:45 +02:00
|
|
|
--- a/src/main/java/net/minecraft/world/item/ArmorStandItem.java
|
|
|
|
+++ b/src/main/java/net/minecraft/world/item/ArmorStandItem.java
|
|
|
|
@@ -55,6 +55,7 @@ public class ArmorStandItem extends Item {
|
|
|
|
entityarmorstand.moveTo(entityarmorstand.getX(), entityarmorstand.getY(), entityarmorstand.getZ(), f, 0.0F);
|
|
|
|
// CraftBukkit start
|
|
|
|
if (org.bukkit.craftbukkit.event.CraftEventFactory.callEntityPlaceEvent(context, entityarmorstand).isCancelled()) {
|
|
|
|
+ if (context.getPlayer() != null) context.getPlayer().containerMenu.sendAllDataToRemote(); // Paper - Fix inventory desync
|
|
|
|
return InteractionResult.FAIL;
|
|
|
|
}
|
|
|
|
// CraftBukkit end
|
2023-08-25 01:53:02 +02:00
|
|
|
diff --git a/src/main/java/net/minecraft/world/item/BlockItem.java b/src/main/java/net/minecraft/world/item/BlockItem.java
|
2024-10-24 12:11:32 +02:00
|
|
|
index 986b14a7b7c98641201ece649df09e4b8279a36c..c816c935ecc74a811ffdffbe6ded73c06e92324a 100644
|
2023-08-25 01:53:02 +02:00
|
|
|
--- a/src/main/java/net/minecraft/world/item/BlockItem.java
|
|
|
|
+++ b/src/main/java/net/minecraft/world/item/BlockItem.java
|
2024-10-24 12:11:32 +02:00
|
|
|
@@ -108,7 +108,7 @@ public class BlockItem extends Item {
|
2023-08-25 01:53:02 +02:00
|
|
|
if (placeEvent != null && (placeEvent.isCancelled() || !placeEvent.canBuild())) {
|
|
|
|
blockstate.update(true, false);
|
|
|
|
|
|
|
|
- if (this instanceof SolidBucketItem) {
|
|
|
|
+ if (true) { // Paper - if the event is called here, the inventory should be updated
|
|
|
|
((ServerPlayer) entityhuman).getBukkitEntity().updateInventory(); // SPIGOT-4541
|
|
|
|
}
|
2023-12-03 04:41:35 +01:00
|
|
|
return InteractionResult.FAIL;
|
2024-05-26 23:30:45 +02:00
|
|
|
diff --git a/src/main/java/net/minecraft/world/item/EndCrystalItem.java b/src/main/java/net/minecraft/world/item/EndCrystalItem.java
|
2024-10-24 12:11:32 +02:00
|
|
|
index 5311e653dceb085fcebb8ac5090d84e97e573e62..48317c7436445a7acff9103bac1de558c42f31cc 100644
|
2024-05-26 23:30:45 +02:00
|
|
|
--- a/src/main/java/net/minecraft/world/item/EndCrystalItem.java
|
|
|
|
+++ b/src/main/java/net/minecraft/world/item/EndCrystalItem.java
|
|
|
|
@@ -49,6 +49,7 @@ public class EndCrystalItem extends Item {
|
|
|
|
entityendercrystal.setShowBottom(false);
|
|
|
|
// CraftBukkit start
|
|
|
|
if (org.bukkit.craftbukkit.event.CraftEventFactory.callEntityPlaceEvent(context, entityendercrystal).isCancelled()) {
|
|
|
|
+ if (context.getPlayer() != null) context.getPlayer().containerMenu.sendAllDataToRemote(); // Paper - Fix inventory desync
|
|
|
|
return InteractionResult.FAIL;
|
|
|
|
}
|
|
|
|
// CraftBukkit end
|
|
|
|
diff --git a/src/main/java/net/minecraft/world/item/MinecartItem.java b/src/main/java/net/minecraft/world/item/MinecartItem.java
|
2024-10-24 12:11:32 +02:00
|
|
|
index 04eb25b05681a72968917b0b59c030d6629776fa..7153d9ed12276a0f2d8b8a17c79734aa25ed1fa5 100644
|
2024-05-26 23:30:45 +02:00
|
|
|
--- a/src/main/java/net/minecraft/world/item/MinecartItem.java
|
|
|
|
+++ b/src/main/java/net/minecraft/world/item/MinecartItem.java
|
2024-10-24 12:11:32 +02:00
|
|
|
@@ -69,6 +69,7 @@ public class MinecartItem extends Item {
|
2024-05-26 23:30:45 +02:00
|
|
|
|
2024-10-24 12:11:32 +02:00
|
|
|
// CraftBukkit start
|
|
|
|
if (org.bukkit.craftbukkit.event.CraftEventFactory.callEntityPlaceEvent(context, entityminecartabstract).isCancelled()) {
|
2024-05-26 23:30:45 +02:00
|
|
|
+ if (context.getPlayer() != null) context.getPlayer().containerMenu.sendAllDataToRemote(); // Paper - Fix inventory desync
|
2024-10-24 12:11:32 +02:00
|
|
|
return InteractionResult.FAIL;
|
|
|
|
}
|
|
|
|
// CraftBukkit end
|