mirror of
https://github.com/PurpurMC/Purpur.git
synced 2026-02-17 16:37:43 +01:00
Upstream has released updates that appear to apply and compile correctly Paper Changes: 05af2837c [CI-SKIP] Improved the annotation test output 586966949 abstract custom set tags, add entity tags c7667378e Added PlayerLoomPatternSelectEvent 00972e80d Reimplement GS4QueryEvent 544c5c278 Re-add coral block tags (#4987) 7d56c8deb Added PlayerLecternPageChangeEvent c7cdf255b Add BlockFailedDispenseEvent c8a8d6fbe Added world settings for mobs picking up loot 91eda5bd3 Added ServerResourcesReloadedEvent be81b4f5c Add a Enchantable MaterialTag 975d18703 Add doors to material tags d075e748e colorful itemdump f3ba3dee0 Added WorldGameRuleChangeEvent 086d20118 Guardian beam workaround b63c890ec Support spawning item stacks d7d74c552 added height config for bamboo 7878e3bc2 Use setAmount for Recipe Amount 50e70697b Add EntityLoadCrossbowEvent f344e092c Add Anti-Xray bypass permission 9fd31e675 fix for nerfed slime mobs splitting 4a7962cd1 Zombie API - breaking doors 5650a41f5 Fix interact event not being called in adventure 2c9ed4335 Add PlayerFlowerPotManipulateEvent 1f32290b6 [Auto] Updated Upstream (CraftBukkit) d87694a20 Redact Velocity forwarding secret properly (#4980) 24a0b0206 [Auto] Updated Upstream (CraftBukkit) 7681042ef [Auto] Updated Upstream (Bukkit/CraftBukkit) 7dea3dba6 [Auto] Updated Upstream (CraftBukkit) 4b3792920 JavaDoc fixes f13b4727e Allow disabling mob spawner spawn egg transformation 525b50737 Cache burn durations 2c37d1077 Optimized tick ready check b4000b01a Add API to get the Material of Boats and Minecarts f1317386d Fix sign lazy initialisation 9f61759d9 Updated Upstream (CraftBukkit/Spigot) (#4972) aaff430b6 [CI-SKIP] Use GitHub Actions for build status 9f4055d99 Fix harming potion dupe 7bfb781ff Additional Block Material API's 0eaffd008 Micro Optimize DataBits Tuinity Changes: 9e5cabb6e Port starlight changes
303 lines
15 KiB
Diff
303 lines
15 KiB
Diff
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
|
From: William Blake Galbreath <blake.galbreath@gmail.com>
|
|
Date: Thu, 8 Aug 2019 15:29:15 -0500
|
|
Subject: [PATCH] AFK API
|
|
|
|
|
|
diff --git a/src/main/java/net/minecraft/server/EntityHuman.java b/src/main/java/net/minecraft/server/EntityHuman.java
|
|
index 3ef463e1313b9729c86437f499930ab4cd332a6d..7880c329942ff96acd1d9c713c5484107c0d660f 100644
|
|
--- a/src/main/java/net/minecraft/server/EntityHuman.java
|
|
+++ b/src/main/java/net/minecraft/server/EntityHuman.java
|
|
@@ -84,6 +84,15 @@ public abstract class EntityHuman extends EntityLiving {
|
|
}
|
|
// CraftBukkit end
|
|
|
|
+ // Purpur start
|
|
+ public void setAfk(boolean setAfk){
|
|
+ }
|
|
+
|
|
+ public boolean isAfk() {
|
|
+ return false;
|
|
+ }
|
|
+ // Purpur end
|
|
+
|
|
public EntityHuman(World world, BlockPosition blockposition, float f, GameProfile gameprofile) {
|
|
super(EntityTypes.PLAYER, world);
|
|
this.bL = ItemStack.b;
|
|
diff --git a/src/main/java/net/minecraft/server/EntityPlayer.java b/src/main/java/net/minecraft/server/EntityPlayer.java
|
|
index 40f56858143651bb0addd0b74db7388ecbe56521..82b975dd483b55461df0e110add5546a7815c650 100644
|
|
--- a/src/main/java/net/minecraft/server/EntityPlayer.java
|
|
+++ b/src/main/java/net/minecraft/server/EntityPlayer.java
|
|
@@ -1904,8 +1904,54 @@ public class EntityPlayer extends EntityHuman implements ICrafting {
|
|
|
|
public void resetIdleTimer() {
|
|
this.ca = SystemUtils.getMonotonicMillis();
|
|
+ setAfk(false); // Purpur
|
|
}
|
|
|
|
+ // Purpur start
|
|
+ private boolean isAfk = false;
|
|
+
|
|
+ @Override
|
|
+ public void setAfk(boolean setAfk) {
|
|
+ if (this.isAfk == setAfk) {
|
|
+ return;
|
|
+ }
|
|
+
|
|
+ String msg = setAfk ? net.pl3x.purpur.PurpurConfig.afkBroadcastAway : net.pl3x.purpur.PurpurConfig.afkBroadcastBack;
|
|
+
|
|
+ net.pl3x.purpur.event.PlayerAFKEvent event = new net.pl3x.purpur.event.PlayerAFKEvent(getBukkitEntity(), setAfk, world.purpurConfig.idleTimeoutKick, msg, !Bukkit.isPrimaryThread());
|
|
+ if (!event.callEvent() || event.shouldKick()) {
|
|
+ return;
|
|
+ }
|
|
+
|
|
+ this.isAfk = setAfk;
|
|
+
|
|
+ if (!setAfk) {
|
|
+ resetIdleTimer();
|
|
+ }
|
|
+
|
|
+ msg = event.getBroadcastMsg();
|
|
+ if (msg != null && !msg.isEmpty()) {
|
|
+ server.getPlayerList().sendMessage(org.bukkit.craftbukkit.util.CraftChatMessage.fromStringOrNull(String.format(msg, getProfile().getName())));
|
|
+ }
|
|
+
|
|
+ if (world.purpurConfig.idleTimeoutUpdateTabList) {
|
|
+ getBukkitEntity().setPlayerListName((setAfk ? net.pl3x.purpur.PurpurConfig.afkTabListPrefix : "") + getName());
|
|
+ }
|
|
+
|
|
+ ((WorldServer) world).everyoneSleeping();
|
|
+ }
|
|
+
|
|
+ @Override
|
|
+ public boolean isAfk() {
|
|
+ return isAfk;
|
|
+ }
|
|
+
|
|
+ @Override
|
|
+ public boolean isCollidable() {
|
|
+ return !isAfk() && super.isCollidable();
|
|
+ }
|
|
+ // Purpur end
|
|
+
|
|
public ServerStatisticManager getStatisticManager() {
|
|
return this.serverStatisticManager;
|
|
}
|
|
diff --git a/src/main/java/net/minecraft/server/IEntityAccess.java b/src/main/java/net/minecraft/server/IEntityAccess.java
|
|
index cbaf18af1066e8bde10293bba5eb3060bae1e66f..0c98a436021cbdedba5352073b1f8bf9852298eb 100644
|
|
--- a/src/main/java/net/minecraft/server/IEntityAccess.java
|
|
+++ b/src/main/java/net/minecraft/server/IEntityAccess.java
|
|
@@ -174,28 +174,18 @@ public interface IEntityAccess {
|
|
}
|
|
// Paper end
|
|
|
|
- default boolean isPlayerNearby(double d0, double d1, double d2, double d3) {
|
|
- Iterator iterator = this.getPlayers().iterator();
|
|
-
|
|
- double d4;
|
|
-
|
|
- do {
|
|
- EntityHuman entityhuman;
|
|
-
|
|
- do {
|
|
- do {
|
|
- if (!iterator.hasNext()) {
|
|
- return false;
|
|
- }
|
|
-
|
|
- entityhuman = (EntityHuman) iterator.next();
|
|
- } while (!IEntitySelector.g.test(entityhuman));
|
|
- } while (!IEntitySelector.b.test(entityhuman));
|
|
-
|
|
- d4 = entityhuman.h(d0, d1, d2);
|
|
- } while (d3 >= 0.0D && d4 >= d3 * d3);
|
|
-
|
|
- return true;
|
|
+ // Purpur start
|
|
+ default boolean isPlayerNearby(double x, double y, double z, double distance) {
|
|
+ double distanceSq = distance * distance;
|
|
+ for (EntityHuman player : getPlayers()) {
|
|
+ if (IEntitySelector.notSpectator().test(player) && IEntitySelector.isLivingAlive().test(player) && IEntitySelector.notAfk.test(player)) {
|
|
+ if (distance < 0.0D || player.getDistanceSquared(x, y, z) < distanceSq) {
|
|
+ return true;
|
|
+ }
|
|
+ }
|
|
+ }
|
|
+ return false;
|
|
+ // Purpur end
|
|
}
|
|
|
|
@Nullable
|
|
diff --git a/src/main/java/net/minecraft/server/IEntitySelector.java b/src/main/java/net/minecraft/server/IEntitySelector.java
|
|
index b5e1a860a2569d7668330827614d221b60f3fc78..5f85a1d513f4fdc21b64e1a2b6882e3325b98ddd 100644
|
|
--- a/src/main/java/net/minecraft/server/IEntitySelector.java
|
|
+++ b/src/main/java/net/minecraft/server/IEntitySelector.java
|
|
@@ -7,6 +7,7 @@ import javax.annotation.Nullable;
|
|
public final class IEntitySelector {
|
|
|
|
public static final Predicate<Entity> a = Entity::isAlive;
|
|
+ public static Predicate<EntityLiving> isLivingAlive() { return b; } // Purpur - OBFHELPER
|
|
public static final Predicate<EntityLiving> b = EntityLiving::isAlive;
|
|
public static final Predicate<Entity> c = (entity) -> {
|
|
return entity.isAlive() && !entity.isVehicle() && !entity.isPassenger();
|
|
@@ -27,6 +28,7 @@ public final class IEntitySelector {
|
|
return !entity.isSpectator();
|
|
};
|
|
public static Predicate<EntityHuman> isInsomniac = (player) -> MathHelper.clamp(((EntityPlayer) player).getStatisticManager().getStatisticValue(StatisticList.CUSTOM.get(StatisticList.TIME_SINCE_REST)), 1, Integer.MAX_VALUE) >= 72000; // Paper
|
|
+ public static Predicate<EntityHuman> notAfk = (player) -> !player.isAfk(); // Purpur
|
|
|
|
// Paper start
|
|
public static final Predicate<Entity> affectsSpawning = (entity) -> {
|
|
diff --git a/src/main/java/net/minecraft/server/PlayerConnection.java b/src/main/java/net/minecraft/server/PlayerConnection.java
|
|
index 5c708ed2cd3b10744b0d6d2eb2ef51d0411ce0dc..d1d4f4baf33e6b2224116f22a63b6d218e26635b 100644
|
|
--- a/src/main/java/net/minecraft/server/PlayerConnection.java
|
|
+++ b/src/main/java/net/minecraft/server/PlayerConnection.java
|
|
@@ -250,6 +250,12 @@ public class PlayerConnection implements PacketListenerPlayIn {
|
|
}
|
|
|
|
if (this.player.F() > 0L && this.minecraftServer.getIdleTimeout() > 0 && SystemUtils.getMonotonicMillis() - this.player.F() > (long) (this.minecraftServer.getIdleTimeout() * 1000 * 60)) {
|
|
+ // Purpur start
|
|
+ this.player.setAfk(true);
|
|
+ if (!this.player.world.purpurConfig.idleTimeoutKick) {
|
|
+ return;
|
|
+ }
|
|
+ // Purpur end
|
|
this.player.resetIdleTimer(); // CraftBukkit - SPIGOT-854
|
|
this.disconnect(new ChatMessage("multiplayer.disconnect.idling"));
|
|
}
|
|
@@ -506,6 +512,8 @@ public class PlayerConnection implements PacketListenerPlayIn {
|
|
this.lastYaw = to.getYaw();
|
|
this.lastPitch = to.getPitch();
|
|
|
|
+ if (!to.getWorld().getUID().equals(from.getWorld().getUID()) || to.getBlockX() != from.getBlockX() || to.getBlockY() != from.getBlockY() || to.getBlockZ() != from.getBlockZ() || to.getYaw() != from.getYaw() || to.getPitch() != from.getPitch()) this.player.resetIdleTimer(); // Purpur
|
|
+
|
|
// Skip the first time we do this
|
|
if (true) { // Spigot - don't skip any move events
|
|
Location oldTo = to.clone();
|
|
@@ -1217,7 +1225,7 @@ public class PlayerConnection implements PacketListenerPlayIn {
|
|
|
|
if (!this.player.H() && d11 > org.spigotmc.SpigotConfig.movedWronglyThreshold && !this.player.isSleeping() && !this.player.playerInteractManager.isCreative() && this.player.playerInteractManager.getGameMode() != EnumGamemode.SPECTATOR) { // Spigot
|
|
flag1 = true;
|
|
- PlayerConnection.LOGGER.warn("{} moved wrongly!", this.player.getDisplayName().getString());
|
|
+ PlayerConnection.LOGGER.warn("{} moved wrongly! ({})", this.player.getDisplayName().getString(), d11); // Purpur
|
|
}
|
|
|
|
this.player.setLocation(d4, d5, d6, f, f1);
|
|
@@ -1256,6 +1264,8 @@ public class PlayerConnection implements PacketListenerPlayIn {
|
|
this.lastYaw = to.getYaw();
|
|
this.lastPitch = to.getPitch();
|
|
|
|
+ if (!to.getWorld().getUID().equals(from.getWorld().getUID()) || to.getBlockX() != from.getBlockX() || to.getBlockY() != from.getBlockY() || to.getBlockZ() != from.getBlockZ() || to.getYaw() != from.getYaw() || to.getPitch() != from.getPitch()) this.player.resetIdleTimer(); // Purpur
|
|
+
|
|
// Skip the first time we do this
|
|
if (from.getX() != Double.MAX_VALUE) {
|
|
Location oldTo = to.clone();
|
|
diff --git a/src/main/java/net/minecraft/server/WorldServer.java b/src/main/java/net/minecraft/server/WorldServer.java
|
|
index ff1d80c7c3271a18fa355430417dd1992b8494a8..9d4181179760140c88cda25f8082d9b682814772 100644
|
|
--- a/src/main/java/net/minecraft/server/WorldServer.java
|
|
+++ b/src/main/java/net/minecraft/server/WorldServer.java
|
|
@@ -781,7 +781,7 @@ public class WorldServer extends World implements GeneratorAccessSeed {
|
|
// CraftBukkit end
|
|
|
|
if (this.everyoneSleeping && this.players.stream().noneMatch((entityplayer) -> {
|
|
- return !entityplayer.isSpectator() && !entityplayer.isDeeplySleeping() && !entityplayer.fauxSleeping; // CraftBukkit
|
|
+ return !entityplayer.isSpectator() && !entityplayer.isDeeplySleeping() && !entityplayer.fauxSleeping && !(purpurConfig.idleTimeoutCountAsSleeping && entityplayer.isAfk()); // CraftBukkit // Purpur
|
|
})) {
|
|
// CraftBukkit start
|
|
long l = this.worldData.getDayTime() + 24000L;
|
|
@@ -1118,7 +1118,7 @@ public class WorldServer extends World implements GeneratorAccessSeed {
|
|
while (iterator.hasNext()) {
|
|
EntityPlayer entityplayer = (EntityPlayer) iterator.next();
|
|
|
|
- if (entityplayer.isSpectator() || (entityplayer.fauxSleeping && !entityplayer.isSleeping())) { // CraftBukkit
|
|
+ if (entityplayer.isSpectator() || (entityplayer.fauxSleeping && !entityplayer.isSleeping()) || (purpurConfig.idleTimeoutCountAsSleeping && entityplayer.isAfk())) { // CraftBukkit // Purpur
|
|
++i;
|
|
} else if (entityplayer.isSleeping()) {
|
|
++j;
|
|
diff --git a/src/main/java/net/pl3x/purpur/PurpurConfig.java b/src/main/java/net/pl3x/purpur/PurpurConfig.java
|
|
index 1705aefab4c16b3b766152fd81c5fc60bbd8d2e7..5d22e643f254e9ea52de8725497ff7c54ceb4afd 100644
|
|
--- a/src/main/java/net/pl3x/purpur/PurpurConfig.java
|
|
+++ b/src/main/java/net/pl3x/purpur/PurpurConfig.java
|
|
@@ -1,6 +1,7 @@
|
|
package net.pl3x.purpur;
|
|
|
|
import com.google.common.base.Throwables;
|
|
+import net.minecraft.server.LocaleLanguage;
|
|
import net.minecraft.server.MinecraftServer;
|
|
import net.pl3x.purpur.command.PurpurCommand;
|
|
import org.bukkit.Bukkit;
|
|
@@ -129,6 +130,15 @@ public class PurpurConfig {
|
|
return config.getString(path, config.getString(path));
|
|
}
|
|
|
|
+ public static String afkBroadcastAway = "§e§o%s is now AFK";
|
|
+ public static String afkBroadcastBack = "§e§o%s is no longer AFK";
|
|
+ public static String afkTabListPrefix = "[AFK] ";
|
|
+ private static void messages() {
|
|
+ afkBroadcastAway = getString("settings.messages.afk-broadcast-away", afkBroadcastAway);
|
|
+ afkBroadcastBack = getString("settings.messages.afk-broadcast-back", afkBroadcastBack);
|
|
+ afkTabListPrefix = getString("settings.messages.afk-tab-list-prefix", afkTabListPrefix);
|
|
+ }
|
|
+
|
|
public static String timingsUrl = "https://timings.pl3x.net";
|
|
private static void timingsSettings() {
|
|
timingsUrl = getString("settings.timings.url", timingsUrl);
|
|
diff --git a/src/main/java/net/pl3x/purpur/PurpurWorldConfig.java b/src/main/java/net/pl3x/purpur/PurpurWorldConfig.java
|
|
index 361f7857e461578e90cb71e15027dadaf794cb69..2578a4677d1ee060f687be531e696b7c7be89e84 100644
|
|
--- a/src/main/java/net/pl3x/purpur/PurpurWorldConfig.java
|
|
+++ b/src/main/java/net/pl3x/purpur/PurpurWorldConfig.java
|
|
@@ -56,4 +56,15 @@ public class PurpurWorldConfig {
|
|
PurpurConfig.config.addDefault("world-settings.default." + path, def);
|
|
return PurpurConfig.config.getString("world-settings." + worldName + "." + path, PurpurConfig.config.getString("world-settings.default." + path));
|
|
}
|
|
+
|
|
+ public boolean idleTimeoutKick = true;
|
|
+ public boolean idleTimeoutTickNearbyEntities = true;
|
|
+ public boolean idleTimeoutCountAsSleeping = false;
|
|
+ public boolean idleTimeoutUpdateTabList = false;
|
|
+ private void playerIdleTimeoutSettings() {
|
|
+ idleTimeoutKick = getBoolean("gameplay-mechanics.player.idle-timeout.kick-if-idle", idleTimeoutKick);
|
|
+ idleTimeoutTickNearbyEntities = getBoolean("gameplay-mechanics.player.idle-timeout.tick-nearby-entities", idleTimeoutTickNearbyEntities);
|
|
+ idleTimeoutCountAsSleeping = getBoolean("gameplay-mechanics.player.idle-timeout.count-as-sleeping", idleTimeoutCountAsSleeping);
|
|
+ idleTimeoutUpdateTabList = getBoolean("gameplay-mechanics.player.idle-timeout.update-tab-list", idleTimeoutUpdateTabList);
|
|
+ }
|
|
}
|
|
diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java
|
|
index 58caa3240b90cdc661e1e32e3f5c312ed62c3c21..6d97bcffb6a3a64de97f159dfbc3e21935bda3f2 100644
|
|
--- a/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java
|
|
+++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java
|
|
@@ -2216,4 +2216,21 @@ public class CraftPlayer extends CraftHumanEntity implements Player {
|
|
return spigot;
|
|
}
|
|
// Spigot end
|
|
+
|
|
+ // Purpur start
|
|
+ @Override
|
|
+ public boolean isAfk() {
|
|
+ return getHandle().isAfk();
|
|
+ }
|
|
+
|
|
+ @Override
|
|
+ public void setAfk(boolean setAfk) {
|
|
+ getHandle().setAfk(setAfk);
|
|
+ }
|
|
+
|
|
+ @Override
|
|
+ public void resetIdleTimer() {
|
|
+ getHandle().resetIdleTimer();
|
|
+ }
|
|
+ // Purpur end
|
|
}
|
|
diff --git a/src/main/java/org/spigotmc/ActivationRange.java b/src/main/java/org/spigotmc/ActivationRange.java
|
|
index 0b93635ba59df4eb4456a97c5e9b51ab5aeda53f..b47d6fa2de3368d1afe329573bc18c3541bb7377 100644
|
|
--- a/src/main/java/org/spigotmc/ActivationRange.java
|
|
+++ b/src/main/java/org/spigotmc/ActivationRange.java
|
|
@@ -207,6 +207,7 @@ public class ActivationRange
|
|
{
|
|
|
|
player.activatedTick = MinecraftServer.currentTick;
|
|
+ if (!player.world.purpurConfig.idleTimeoutTickNearbyEntities && player.isAfk()) continue; // Purpur
|
|
maxBB = player.getBoundingBox().grow( maxRange, 256, maxRange );
|
|
ActivationType.MISC.boundingBox = player.getBoundingBox().grow( miscActivationRange, 256, miscActivationRange );
|
|
ActivationType.RAIDER.boundingBox = player.getBoundingBox().grow( raiderActivationRange, 256, raiderActivationRange );
|