Paper/Spigot-Server-Patches/0568-Fix-Entity-Teleportation-and-cancel-velocity-if-tele.patch

72 lines
4.3 KiB
Diff
Raw Normal View History

From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Aikar <aikar@aikar.co>
Date: Tue, 25 Aug 2020 20:45:36 -0400
Subject: [PATCH] Fix Entity Teleportation and cancel velocity if teleported
Uses correct setPositionRotation for Entity teleporting instead of setLocation
as this is how Vanilla teleports entities.
Cancel any pending motion when teleported.
diff --git a/src/main/java/net/minecraft/server/Entity.java b/src/main/java/net/minecraft/server/Entity.java
index 5c52a2988b8830e4e5597f8a5b3718d242023cb7..a7b225249f7ffafa2c6e1fc60657067229e02960 100644
--- a/src/main/java/net/minecraft/server/Entity.java
+++ b/src/main/java/net/minecraft/server/Entity.java
@@ -54,6 +54,7 @@ public abstract class Entity implements INamableTileEntity, ICommandListener, Ke
// CraftBukkit start
private static final int CURRENT_LEVEL = 2;
+ boolean preserveMotion = true; // Paper - keep initial motion on first setPositionRotation
static boolean isLevelAtLeast(NBTTagCompound tag, int level) {
return tag.hasKey("Bukkit.updateLevel") && tag.getInt("Bukkit.updateLevel") >= level;
}
@@ -1317,6 +1318,13 @@ public abstract class Entity implements INamableTileEntity, ICommandListener, Ke
}
public void setPositionRotation(double d0, double d1, double d2, float f, float f1) {
+ // Paper - cancel entity velocity if teleported
+ if (!preserveMotion) {
+ this.mot = Vec3D.ORIGIN;
+ } else {
+ this.preserveMotion = false;
+ }
+ // Paper end
this.g(d0, d1, d2);
this.yaw = f;
this.pitch = f1;
diff --git a/src/main/java/net/minecraft/server/PlayerConnection.java b/src/main/java/net/minecraft/server/PlayerConnection.java
index f1e3c764fc8d5b6acb2ae94276e31fe37af817b6..5af38d36f64020d1df492ad57fafd2baf867536a 100644
--- a/src/main/java/net/minecraft/server/PlayerConnection.java
+++ b/src/main/java/net/minecraft/server/PlayerConnection.java
2020-12-08 08:51:55 +01:00
@@ -542,7 +542,7 @@ public class PlayerConnection implements PacketListenerPlayIn {
public void a(PacketPlayInTeleportAccept packetplayinteleportaccept) {
PlayerConnectionUtils.ensureMainThread(packetplayinteleportaccept, this, this.player.getWorldServer());
if (packetplayinteleportaccept.b() == this.teleportAwait && this.teleportPos != null) { // CraftBukkit
- this.player.setLocation(this.teleportPos.x, this.teleportPos.y, this.teleportPos.z, this.player.yaw, this.player.pitch);
+ this.player.setPositionRotation(this.teleportPos.x, this.teleportPos.y, this.teleportPos.z, this.player.yaw, this.player.pitch); // Paper - use proper setPositionRotation for teleportation
this.o = this.teleportPos.x;
this.p = this.teleportPos.y;
this.q = this.teleportPos.z;
@@ -1386,7 +1386,7 @@ public class PlayerConnection implements PacketListenerPlayIn {
// CraftBukkit end
this.A = this.e;
- this.player.setLocation(d0, d1, d2, f, f1);
+ this.player.setPositionRotation(d0, d1, d2, f, f1); // Paper - use proper setPositionRotation for teleportation
this.player.forceCheckHighPriority(); // Paper
this.player.playerConnection.sendPacket(new PacketPlayOutPosition(d0 - d3, d1 - d4, d2 - d5, f - f2, f1 - f3, set, this.teleportAwait));
}
diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftEntity.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftEntity.java
index c7636ffc952c436d7148e6e5926b0108cc628821..582ed13a9ba1748444ce4d624d83a4d7be7006f2 100644
--- a/src/main/java/org/bukkit/craftbukkit/entity/CraftEntity.java
+++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftEntity.java
@@ -554,7 +554,7 @@ public abstract class CraftEntity implements org.bukkit.entity.Entity {
}
// entity.setLocation() throws no event, and so cannot be cancelled
- entity.setLocation(location.getX(), location.getY(), location.getZ(), location.getYaw(), location.getPitch());
+ entity.setPositionRotation(location.getX(), location.getY(), location.getZ(), location.getYaw(), location.getPitch()); // Paper - use proper setPosition, as per vanilla teleporting
// SPIGOT-619: Force sync head rotation also
entity.setHeadRotation(location.getYaw());
((net.minecraft.server.WorldServer) entity.world).chunkCheck(entity); // Spigot - register to new chunk