From e7fe0db891aa3ea0c7abe3432fc50cde2bbdf692 Mon Sep 17 00:00:00 2001 From: violetc <58360096+s-yh-china@users.noreply.github.com> Date: Wed, 27 Jul 2022 16:19:38 +0800 Subject: [PATCH] Add fakeplayer api --- patches/api/0003-Add-fakeplayer-api.patch | 148 ++++++ .../server/0010-Add-fakeplayer-support.patch | 452 +++++++++++------- .../0011-Add-fakeplayer-action-support.patch | 328 ++++++------- .../0016-Spectator-dont-get-Advancement.patch | 4 +- 4 files changed, 590 insertions(+), 342 deletions(-) create mode 100644 patches/api/0003-Add-fakeplayer-api.patch diff --git a/patches/api/0003-Add-fakeplayer-api.patch b/patches/api/0003-Add-fakeplayer-api.patch new file mode 100644 index 00000000..ae6d74f4 --- /dev/null +++ b/patches/api/0003-Add-fakeplayer-api.patch @@ -0,0 +1,148 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: violetc <58360096+s-yh-china@users.noreply.github.com> +Date: Wed, 27 Jul 2022 15:30:34 +0800 +Subject: [PATCH] Add fakeplayer api + + +diff --git a/src/main/java/top/leavesmc/leaves/entity/Bot.java b/src/main/java/top/leavesmc/leaves/entity/Bot.java +new file mode 100644 +index 0000000000000000000000000000000000000000..d4afe549b5e1aba7d468450c5e1570d2e0c0a1f3 +--- /dev/null ++++ b/src/main/java/top/leavesmc/leaves/entity/Bot.java +@@ -0,0 +1,9 @@ ++package top.leavesmc.leaves.entity; ++ ++import org.bukkit.entity.Player; ++ ++/** ++ * Represents a fakeplayer ++ */ ++public interface Bot extends Player { ++} +diff --git a/src/main/java/top/leavesmc/leaves/event/bot/BotCreateEvent.java b/src/main/java/top/leavesmc/leaves/event/bot/BotCreateEvent.java +new file mode 100644 +index 0000000000000000000000000000000000000000..9424a0b82ebfedd571e759db4f41d51364ad0b88 +--- /dev/null ++++ b/src/main/java/top/leavesmc/leaves/event/bot/BotCreateEvent.java +@@ -0,0 +1,84 @@ ++package top.leavesmc.leaves.event.bot; ++ ++import org.bukkit.Location; ++import org.bukkit.event.Cancellable; ++import org.bukkit.event.HandlerList; ++import org.jetbrains.annotations.NotNull; ++import org.jetbrains.annotations.Nullable; ++import top.leavesmc.leaves.entity.Bot; ++ ++/** ++ * Call when a fakeplayer creates a server ++ */ ++public class BotCreateEvent extends BotEvent implements Cancellable { ++ private static final HandlerList handlers = new HandlerList(); ++ ++ private String joinMessage; ++ private Location createLocation; ++ private boolean cancel = false; ++ ++ public BotCreateEvent(@NotNull final Bot who, @NotNull final Location createLocation, @Nullable final String joinMessage) { ++ super(who); ++ this.joinMessage = joinMessage; ++ this.createLocation = createLocation; ++ } ++ ++ /** ++ * Gets the join message to send to all online players ++ * ++ * @return string join message. Can be null ++ */ ++ @Nullable ++ public String getJoinMessage() { ++ return joinMessage; ++ } ++ ++ /** ++ * Sets the join message to send to all online players ++ * ++ * @param joinMessage join message. If null, no message will be sent ++ */ ++ public void setJoinMessage(@Nullable String joinMessage) { ++ this.joinMessage = joinMessage; ++ } ++ ++ /** ++ * Gets the location to create the fakeplayer ++ * ++ * @return Location to create the fakeplayer ++ */ ++ @NotNull ++ public Location getCreateLocation() { ++ return createLocation; ++ } ++ ++ /** ++ * Sets the location to create the fakeplayer ++ * ++ * @param createLocation location to create the fakeplyer ++ */ ++ public void setCreateLocation(@NotNull Location createLocation) { ++ this.createLocation = createLocation; ++ } ++ ++ @Override ++ public boolean isCancelled() { ++ return cancel; ++ } ++ ++ @Override ++ public void setCancelled(boolean cancel) { ++ this.cancel = cancel; ++ } ++ ++ @Override ++ @NotNull ++ public HandlerList getHandlers() { ++ return handlers; ++ } ++ ++ @NotNull ++ public static HandlerList getHandlerList() { ++ return handlers; ++ } ++} +diff --git a/src/main/java/top/leavesmc/leaves/event/bot/BotEvent.java b/src/main/java/top/leavesmc/leaves/event/bot/BotEvent.java +new file mode 100644 +index 0000000000000000000000000000000000000000..4a4fe07ce965d4a97e0d8105a91310dac7d1343c +--- /dev/null ++++ b/src/main/java/top/leavesmc/leaves/event/bot/BotEvent.java +@@ -0,0 +1,31 @@ ++package top.leavesmc.leaves.event.bot; ++ ++import org.bukkit.event.Event; ++import org.jetbrains.annotations.NotNull; ++import top.leavesmc.leaves.entity.Bot; ++ ++/** ++ * Represents a fakeplayer related event ++ */ ++public abstract class BotEvent extends Event { ++ protected Bot bot; ++ ++ public BotEvent(@NotNull final Bot who) { ++ bot = who; ++ } ++ ++ public BotEvent(@NotNull final Bot who, boolean async) { // Paper - public ++ super(async); ++ bot = who; ++ } ++ ++ /** ++ * Returns the fakeplayer involved in this event ++ * ++ * @return Fakeplayer who is involved in this event ++ */ ++ @NotNull ++ public final Bot getBot() { ++ return bot; ++ } ++} diff --git a/patches/server/0010-Add-fakeplayer-support.patch b/patches/server/0010-Add-fakeplayer-support.patch index d97053f6..124ab850 100644 --- a/patches/server/0010-Add-fakeplayer-support.patch +++ b/patches/server/0010-Add-fakeplayer-support.patch @@ -5,14 +5,14 @@ Subject: [PATCH] Add fakeplayer support diff --git a/src/main/java/net/minecraft/server/PlayerAdvancements.java b/src/main/java/net/minecraft/server/PlayerAdvancements.java -index de0513b38e5fa0138f1cee6bb633561be12449fc..6de539d8819b9c25fbf96cd2ac8ef4a87c0fb231 100644 +index de0513b38e5fa0138f1cee6bb633561be12449fc..8548ef7f79e85aca593928b8e748d8b6d53e52bd 100644 --- a/src/main/java/net/minecraft/server/PlayerAdvancements.java +++ b/src/main/java/net/minecraft/server/PlayerAdvancements.java @@ -50,6 +50,7 @@ import net.minecraft.server.players.PlayerList; import net.minecraft.util.datafix.DataFixTypes; import net.minecraft.world.level.GameRules; import org.slf4j.Logger; -+import top.leavesmc.leaves.bot.Bot; ++import top.leavesmc.leaves.bot.ServerBot; public class PlayerAdvancements { @@ -21,7 +21,7 @@ index de0513b38e5fa0138f1cee6bb633561be12449fc..6de539d8819b9c25fbf96cd2ac8ef4a8 public boolean award(Advancement advancement, String criterionName) { + // Leaves start - bot can't get advancement -+ if (player instanceof Bot) { ++ if (player instanceof ServerBot) { + return false; + } + // Leaves end - bot can't get advancement @@ -29,35 +29,74 @@ index de0513b38e5fa0138f1cee6bb633561be12449fc..6de539d8819b9c25fbf96cd2ac8ef4a8 AdvancementProgress advancementprogress = this.getOrStartProgress(advancement); boolean flag1 = advancementprogress.isDone(); diff --git a/src/main/java/net/minecraft/server/players/PlayerList.java b/src/main/java/net/minecraft/server/players/PlayerList.java -index 20cdfdb3b9351f74e89bc45b3ab972384165659a..e7fc2bd7241430354509158e1dceafb723d6f692 100644 +index 20cdfdb3b9351f74e89bc45b3ab972384165659a..fe38a9cd9724d0547e0d1689153a8c155c377d0c 100644 --- a/src/main/java/net/minecraft/server/players/PlayerList.java +++ b/src/main/java/net/minecraft/server/players/PlayerList.java -@@ -100,6 +100,7 @@ import net.minecraft.world.scores.Objective; +@@ -100,10 +100,10 @@ import net.minecraft.world.scores.Objective; import net.minecraft.world.scores.PlayerTeam; import net.minecraft.world.scores.Scoreboard; // Paper import net.minecraft.world.scores.Team; -+import top.leavesmc.leaves.bot.Bot; ++import top.leavesmc.leaves.bot.ServerBot; import org.slf4j.Logger; // CraftBukkit start -@@ -368,6 +369,17 @@ public abstract class PlayerList { +-import io.papermc.paper.adventure.PaperAdventure; // Paper + import com.google.common.base.Predicate; + import java.util.stream.Collectors; + import net.minecraft.server.dedicated.DedicatedServer; +@@ -113,7 +113,6 @@ import org.bukkit.Location; + import org.bukkit.craftbukkit.CraftServer; + import org.bukkit.craftbukkit.CraftWorld; + import org.bukkit.craftbukkit.entity.CraftPlayer; +-import org.bukkit.craftbukkit.util.CraftChatMessage; + import org.bukkit.entity.Player; + import org.bukkit.event.player.PlayerChangedWorldEvent; + import org.bukkit.event.player.PlayerJoinEvent; +@@ -368,6 +367,17 @@ public abstract class PlayerList { return; } + // Leaves start - bot support + if (top.leavesmc.leaves.LeavesConfig.fakeplayerSupport) { -+ Bot bot = Bot.getBot(player.getName().getString()); ++ ServerBot bot = ServerBot.getBot(player.getName().getString()); + if (bot != null) { + bot.kill(); // Leaves - remove bot with the same name + } + -+ Bot.getBots().forEach(bot1 -> bot1.render(playerconnection, true)); // Leaves - render bot ++ ServerBot.getBots().forEach(bot1 -> bot1.render(playerconnection, true)); // Leaves - render bot + } + // Leaves end - bot support + final net.kyori.adventure.text.Component jm = playerJoinEvent.joinMessage(); if (jm != null && !jm.equals(net.kyori.adventure.text.Component.empty())) { // Paper - Adventure +diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftEntity.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftEntity.java +index 2a6c67634c31c332102d24bef293da1bacd0c000..877c9fa13c0ff1fbc90d957258bd0bc1f42c0fd4 100644 +--- a/src/main/java/org/bukkit/craftbukkit/entity/CraftEntity.java ++++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftEntity.java +@@ -187,6 +187,8 @@ import org.bukkit.plugin.Plugin; + import org.bukkit.util.BoundingBox; + import org.bukkit.util.NumberConversions; + import org.bukkit.util.Vector; ++import top.leavesmc.leaves.bot.ServerBot; ++import top.leavesmc.leaves.entity.CraftBot; + + public abstract class CraftEntity implements org.bukkit.entity.Entity { + private static PermissibleBase perm; +@@ -211,7 +213,12 @@ public abstract class CraftEntity implements org.bukkit.entity.Entity { + if (entity instanceof LivingEntity) { + // Players + if (entity instanceof Player) { +- if (entity instanceof ServerPlayer) { return new CraftPlayer(server, (ServerPlayer) entity); } ++ // Leaves start - add CraftBot ++ if (entity instanceof ServerPlayer) { ++ if (entity instanceof ServerBot) { return new CraftBot(server, (ServerBot) entity); } ++ else { return new CraftPlayer(server, (ServerPlayer) entity); } ++ } ++ // Leaves end - add CraftBot + else { return new CraftHumanEntity(server, (Player) entity); } + } + // Water Animals diff --git a/src/main/java/top/leavesmc/leaves/LeavesConfig.java b/src/main/java/top/leavesmc/leaves/LeavesConfig.java index a85a5de7d85cf6c5e19c0245c40e6106e6623007..898c61c25675232e203ee2c872ca25804c41358c 100644 --- a/src/main/java/top/leavesmc/leaves/LeavesConfig.java @@ -121,12 +160,166 @@ index a85a5de7d85cf6c5e19c0245c40e6106e6623007..898c61c25675232e203ee2c872ca2580 public static final class WorldConfig { public final String worldName; -diff --git a/src/main/java/top/leavesmc/leaves/bot/Bot.java b/src/main/java/top/leavesmc/leaves/bot/Bot.java +diff --git a/src/main/java/top/leavesmc/leaves/bot/BotCommand.java b/src/main/java/top/leavesmc/leaves/bot/BotCommand.java new file mode 100644 -index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f +index 0000000000000000000000000000000000000000..292fede3bb850892e57640814440bdcebfd43aec --- /dev/null -+++ b/src/main/java/top/leavesmc/leaves/bot/Bot.java -@@ -0,0 +1,489 @@ ++++ b/src/main/java/top/leavesmc/leaves/bot/BotCommand.java +@@ -0,0 +1,101 @@ ++package top.leavesmc.leaves.bot; ++ ++import org.bukkit.Bukkit; ++import org.bukkit.ChatColor; ++import org.bukkit.Location; ++import org.bukkit.command.Command; ++import org.bukkit.command.CommandSender; ++import org.bukkit.entity.Player; ++ ++import java.util.ArrayList; ++import java.util.List; ++ ++public class BotCommand extends Command { ++ ++ public BotCommand(String name) { ++ super(name); ++ this.description = "FakePlayer Command"; ++ this.usageMessage = "/bot [create | remove]"; ++ this.setPermission("bukkit.command.bot"); ++ } ++ ++ @Override ++ public List tabComplete(CommandSender sender, String alias, String[] args, Location location) throws IllegalArgumentException { ++ var list = new ArrayList(); ++ ++ if (args.length <= 1) { ++ list.add("create"); ++ list.add("remove"); ++ } else { ++ switch (args[0]) { ++ case "create" -> list.add("[BotName]"); ++ case "remove" -> list.addAll(ServerBot.getBots().stream().map(e -> e.getName().getString()).toList()); ++ } ++ } ++ ++ return list; ++ } ++ ++ @Override ++ public boolean execute(CommandSender sender, String commandLabel, String[] args) { ++ if (!testPermission(sender)) return true; ++ ++ if (args.length == 0) { ++ sender.sendMessage(ChatColor.RED + "Usage: " + usageMessage); ++ return false; ++ } ++ ++ switch (args[0]) { ++ case "create" -> this.onCreate(sender, args); ++ ++ case "remove" -> this.onRemove(sender, args); ++ ++ default -> { ++ sender.sendMessage(ChatColor.RED + "Usage: " + usageMessage); ++ return false; ++ } ++ } ++ ++ return true; ++ } ++ ++ private void onCreate(CommandSender sender, String[] args) { ++ if (args.length < 2) { ++ sender.sendMessage(ChatColor.RED + "Use /bot create [name] to create a fakeplayer"); ++ return; ++ } ++ ++ if (!(sender instanceof Player)) { ++ sender.sendMessage(ChatColor.RED + "This command only can use by player"); ++ return; ++ } ++ ++ if (Bukkit.getPlayer(args[1]) != null || ServerBot.getBot(args[1]) != null) { ++ sender.sendMessage(ChatColor.RED + "This player is in server"); ++ return; ++ } ++ ++ if (top.leavesmc.leaves.LeavesConfig.unableFakeplayerNames.contains(args[1])) { ++ sender.sendMessage(ChatColor.RED + "This name is unable"); ++ return; ++ } ++ ++ ServerBot.createBot(((Player) sender).getLocation(), args[1]); ++ } ++ ++ private void onRemove(CommandSender sender, String[] args) { ++ if (args.length < 2) { ++ sender.sendMessage(ChatColor.RED + "Use /bot remove [name] to remove a fakeplayer"); ++ return; ++ } ++ ++ ServerBot bot = ServerBot.getBot(args[1]); ++ ++ if (bot == null) { ++ sender.sendMessage(ChatColor.RED + "This fakeplayer is null"); ++ return; ++ } ++ ++ bot.kill(); ++ } ++} +diff --git a/src/main/java/top/leavesmc/leaves/bot/MojangAPI.java b/src/main/java/top/leavesmc/leaves/bot/MojangAPI.java +new file mode 100644 +index 0000000000000000000000000000000000000000..daaece30b2a3983f1cc9ee9a851e8f373974d5ec +--- /dev/null ++++ b/src/main/java/top/leavesmc/leaves/bot/MojangAPI.java +@@ -0,0 +1,41 @@ ++package top.leavesmc.leaves.bot; ++ ++import com.google.gson.JsonObject; ++import com.google.gson.JsonParser; ++ ++import java.io.IOException; ++import java.io.InputStreamReader; ++import java.net.URL; ++import java.util.HashMap; ++import java.util.Map; ++ ++public class MojangAPI { ++ ++ private static final boolean CACHE_ENABLED = false; ++ ++ private static final Map CACHE = new HashMap<>(); ++ ++ public static String[] getSkin(String name) { ++ if (CACHE_ENABLED && CACHE.containsKey(name)) { ++ return CACHE.get(name); ++ } ++ ++ String[] values = pullFromAPI(name); ++ CACHE.put(name, values); ++ return values; ++ } ++ ++ // Laggggggggggggggggggggggggggggggggggggggggg ++ public static String[] pullFromAPI(String name) { ++ try { ++ String uuid = new JsonParser().parse(new InputStreamReader(new URL("https://api.mojang.com/users/profiles/minecraft/" + name) ++ .openStream())).getAsJsonObject().get("id").getAsString(); ++ JsonObject property = new JsonParser() ++ .parse(new InputStreamReader(new URL("https://sessionserver.mojang.com/session/minecraft/profile/" + uuid + "?unsigned=false") ++ .openStream())).getAsJsonObject().get("properties").getAsJsonArray().get(0).getAsJsonObject(); ++ return new String[] {property.get("value").getAsString(), property.get("signature").getAsString()}; ++ } catch (IOException | IllegalStateException e) { ++ return null; ++ } ++ } ++} +diff --git a/src/main/java/top/leavesmc/leaves/bot/ServerBot.java b/src/main/java/top/leavesmc/leaves/bot/ServerBot.java +new file mode 100644 +index 0000000000000000000000000000000000000000..b833653b671df660686134754c794d3e6686b112 +--- /dev/null ++++ b/src/main/java/top/leavesmc/leaves/bot/ServerBot.java +@@ -0,0 +1,510 @@ +package top.leavesmc.leaves.bot; + +import com.mojang.authlib.GameProfile; @@ -155,7 +348,6 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 +import net.minecraft.world.entity.Entity; +import net.minecraft.world.entity.MoverType; +import net.minecraft.world.level.ChunkPos; -+import net.minecraft.world.level.Level; +import net.minecraft.world.level.chunk.LevelChunk; +import net.minecraft.world.phys.AABB; +import net.minecraft.world.phys.Vec3; @@ -167,15 +359,18 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 +import org.bukkit.block.Block; +import org.bukkit.craftbukkit.CraftWorld; +import org.bukkit.craftbukkit.entity.CraftPlayer; -+import org.bukkit.craftbukkit.inventory.CraftItemStack; +import org.bukkit.craftbukkit.scheduler.MinecraftInternalPlugin; +import org.bukkit.entity.Player; +import org.bukkit.event.entity.CreatureSpawnEvent; +import org.bukkit.event.player.PlayerJoinEvent; -+import org.bukkit.inventory.ItemStack; ++import org.bukkit.event.player.PlayerTeleportEvent; +import org.bukkit.plugin.Plugin; +import org.bukkit.util.BoundingBox; +import org.bukkit.util.Vector; ++import org.jetbrains.annotations.NotNull; ++import top.leavesmc.leaves.entity.Bot; ++import top.leavesmc.leaves.entity.CraftBot; ++import top.leavesmc.leaves.event.bot.BotCreateEvent; +import top.leavesmc.leaves.util.MathUtils; + +import javax.annotation.Nullable; @@ -184,7 +379,7 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 +import java.util.Set; +import java.util.UUID; + -+public class Bot extends ServerPlayer { ++public class ServerBot extends ServerPlayer { + + private Vector velocity; + private Vector oldVelocity; @@ -195,10 +390,10 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 + private byte jumpTicks; + private byte noFallTicks; + -+ private static final Set bots = new HashSet<>(); ++ private static final Set bots = new HashSet<>(); + private static final Plugin MINECRAFT_PLUGIN = new MinecraftInternalPlugin(); + -+ public Bot(MinecraftServer server, ServerLevel world, GameProfile profile) { ++ public ServerBot(MinecraftServer server, ServerLevel world, GameProfile profile) { + super(server, world, profile, null); + this.entityData.set(new EntityDataAccessor<>(16, EntityDataSerializers.INT), 0xFF); + @@ -216,14 +411,15 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 + }); + } + -+ public static Bot createBot(Location loc, String name, String[] skin) { ++ @Nullable ++ public static ServerBot createBot(@NotNull Location loc, @NotNull String name, String[] skin) { + MinecraftServer server = MinecraftServer.getServer(); + ServerLevel world = ((CraftWorld) Objects.requireNonNull(loc.getWorld())).getHandle(); + + UUID uuid = UUID.randomUUID(); + CustomGameProfile profile = new CustomGameProfile(uuid, name.length() > 16 ? name.substring(0, 16) : name, skin); + -+ Bot bot = new Bot(server, world, profile); ++ ServerBot bot = new ServerBot(server, world, profile); + + bot.connection = new ServerGamePacketListenerImpl(server, new Connection(PacketFlow.CLIENTBOUND) { + @Override @@ -232,20 +428,32 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 + }, bot); + bot.isRealPlayer = true; + -+ bot.teleportTo(loc.getX(), loc.getY(), loc.getZ()); -+ bot.setRot(loc.getYaw(), loc.getPitch()); -+ world.addFreshEntity(bot, CreatureSpawnEvent.SpawnReason.COMMAND); -+ -+ bot.renderAll(); -+ PlayerJoinEvent event = new PlayerJoinEvent(bot.getBukkitPlayer(), ChatColor.YELLOW + bot.getName().getString() + " joined the game"); ++ BotCreateEvent event = new BotCreateEvent(bot.getBukkitPlayer(), loc, ChatColor.YELLOW + bot.getName().getString() + " joined the game"); + server.server.getPluginManager().callEvent(event); -+ if (event.getJoinMessage() != null) { -+ Bukkit.broadcastMessage(event.getJoinMessage()); ++ if (!event.isCancelled()) { ++ if (event.getJoinMessage() != null) { ++ Bukkit.broadcastMessage(event.getJoinMessage()); ++ } ++ ++ loc = event.getCreateLocation(); ++ ServerLevel world1 = ((CraftWorld) Objects.requireNonNull(loc.getWorld())).getHandle(); ++ ++ if (world1 != world) { ++ world = world1; ++ bot.changeDimension(world, PlayerTeleportEvent.TeleportCause.COMMAND); ++ } ++ ++ bot.teleportTo(loc.getX(), loc.getY(), loc.getZ()); ++ bot.setRot(loc.getYaw(), loc.getPitch()); ++ world.addFreshEntity(bot, CreatureSpawnEvent.SpawnReason.COMMAND); ++ ++ bot.renderAll(); ++ ++ bots.add(bot); ++ return bot; + } + -+ bots.add(bot); -+ -+ return bot; ++ return null; + } + + private void renderAll() { @@ -383,11 +591,17 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 + return false; + } + -+ public Player getBukkitPlayer() { ++ public Bot getBukkitPlayer() { + return getBukkitEntity(); + } + + @Override ++ @NotNull ++ public CraftBot getBukkitEntity() { ++ return (CraftBot) super.getBukkitEntity(); ++ } ++ ++ @Override + public boolean isInWater() { + Location loc = getLocation(); + for (int i = 0; i <= 2; i++) { @@ -576,9 +790,9 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 + this.move(MoverType.SELF, new Vec3(velocity.getX(), y, velocity.getZ())); + } + -+ public static Bot getBot(ServerPlayer player) { -+ Bot bot = null; -+ for (Bot b : bots) { ++ public static ServerBot getBot(ServerPlayer player) { ++ ServerBot bot = null; ++ for (ServerBot b : bots) { + if (b.getId() == player.getId()) { + bot = b; + break; @@ -587,9 +801,9 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 + return bot; + } + -+ public static Bot getBot(String name) { -+ Bot bot = null; -+ for (Bot b : bots) { ++ public static ServerBot getBot(String name) { ++ ServerBot bot = null; ++ for (ServerBot b : bots) { + if (b.getName().getString().equals(name)) { + bot = b; + break; @@ -598,7 +812,7 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 + return bot; + } + -+ public static Set getBots() { // It needs unmodifiable ++ public static Set getBots() { // It needs unmodifiable + return bots; + } + @@ -616,158 +830,36 @@ index 0000000000000000000000000000000000000000..7a81e5b8aa7aaa5c8a6718d0ad603790 + } + } +} -diff --git a/src/main/java/top/leavesmc/leaves/bot/BotCommand.java b/src/main/java/top/leavesmc/leaves/bot/BotCommand.java +diff --git a/src/main/java/top/leavesmc/leaves/entity/CraftBot.java b/src/main/java/top/leavesmc/leaves/entity/CraftBot.java new file mode 100644 -index 0000000000000000000000000000000000000000..3b8d44fb61d504e521e73d3a34f6bd8ad9f13aee +index 0000000000000000000000000000000000000000..2d5044c4a09044364e818b7674908bf98932bf58 --- /dev/null -+++ b/src/main/java/top/leavesmc/leaves/bot/BotCommand.java -@@ -0,0 +1,101 @@ -+package top.leavesmc.leaves.bot; ++++ b/src/main/java/top/leavesmc/leaves/entity/CraftBot.java +@@ -0,0 +1,26 @@ ++package top.leavesmc.leaves.entity; + -+import org.bukkit.Bukkit; -+import org.bukkit.ChatColor; -+import org.bukkit.Location; -+import org.bukkit.command.Command; -+import org.bukkit.command.CommandSender; -+import org.bukkit.entity.Player; ++import org.bukkit.craftbukkit.CraftServer; ++import org.bukkit.craftbukkit.entity.CraftPlayer; ++import top.leavesmc.leaves.bot.ServerBot; + -+import java.util.ArrayList; -+import java.util.List; ++public class CraftBot extends CraftPlayer implements Bot { + -+public class BotCommand extends Command { -+ -+ public BotCommand(String name) { -+ super(name); -+ this.description = "FakePlayer Command"; -+ this.usageMessage = "/bot [create | remove]"; -+ this.setPermission("bukkit.command.bot"); ++ public CraftBot(CraftServer server, ServerBot entity) { ++ super(server, entity); + } + + @Override -+ public List tabComplete(CommandSender sender, String alias, String[] args, Location location) throws IllegalArgumentException { -+ var list = new ArrayList(); ++ public ServerBot getHandle() { ++ return (ServerBot) entity; ++ } + -+ if (args.length <= 1) { -+ list.add("create"); -+ list.add("remove"); -+ } else { -+ switch (args[0]) { -+ case "create" -> list.add("[BotName]"); -+ case "remove" -> list.addAll(Bot.getBots().stream().map(e -> e.getName().getString()).toList()); -+ } -+ } -+ -+ return list; ++ public void setHandle(final ServerBot entity) { ++ super.setHandle(entity); + } + + @Override -+ public boolean execute(CommandSender sender, String commandLabel, String[] args) { -+ if (!testPermission(sender)) return true; -+ -+ if (args.length == 0) { -+ sender.sendMessage(ChatColor.RED + "Usage: " + usageMessage); -+ return false; -+ } -+ -+ switch (args[0]) { -+ case "create" -> this.onCreate(sender, args); -+ -+ case "remove" -> this.onRemove(sender, args); -+ -+ default -> { -+ sender.sendMessage(ChatColor.RED + "Usage: " + usageMessage); -+ return false; -+ } -+ } -+ -+ return true; -+ } -+ -+ private void onCreate(CommandSender sender, String[] args) { -+ if (args.length < 2) { -+ sender.sendMessage(ChatColor.RED + "Use /bot create [name] to create a fakeplayer"); -+ return; -+ } -+ -+ if (!(sender instanceof Player)) { -+ sender.sendMessage(ChatColor.RED + "This command only can use by player"); -+ return; -+ } -+ -+ if (Bukkit.getPlayer(args[1]) != null || Bot.getBot(args[1]) != null) { -+ sender.sendMessage(ChatColor.RED + "This player is in server"); -+ return; -+ } -+ -+ if (top.leavesmc.leaves.LeavesConfig.unableFakeplayerNames.contains(args[1])) { -+ sender.sendMessage(ChatColor.RED + "This name is unable"); -+ return; -+ } -+ -+ Bot.createBot(((Player) sender).getLocation(), args[1]); -+ } -+ -+ private void onRemove(CommandSender sender, String[] args) { -+ if (args.length < 2) { -+ sender.sendMessage(ChatColor.RED + "Use /bot remove [name] to remove a fakeplayer"); -+ return; -+ } -+ -+ Bot bot = Bot.getBot(args[1]); -+ -+ if (bot == null) { -+ sender.sendMessage(ChatColor.RED + "This fakeplayer is null"); -+ return; -+ } -+ -+ bot.kill(); -+ } -+} -diff --git a/src/main/java/top/leavesmc/leaves/bot/MojangAPI.java b/src/main/java/top/leavesmc/leaves/bot/MojangAPI.java -new file mode 100644 -index 0000000000000000000000000000000000000000..daaece30b2a3983f1cc9ee9a851e8f373974d5ec ---- /dev/null -+++ b/src/main/java/top/leavesmc/leaves/bot/MojangAPI.java -@@ -0,0 +1,41 @@ -+package top.leavesmc.leaves.bot; -+ -+import com.google.gson.JsonObject; -+import com.google.gson.JsonParser; -+ -+import java.io.IOException; -+import java.io.InputStreamReader; -+import java.net.URL; -+import java.util.HashMap; -+import java.util.Map; -+ -+public class MojangAPI { -+ -+ private static final boolean CACHE_ENABLED = false; -+ -+ private static final Map CACHE = new HashMap<>(); -+ -+ public static String[] getSkin(String name) { -+ if (CACHE_ENABLED && CACHE.containsKey(name)) { -+ return CACHE.get(name); -+ } -+ -+ String[] values = pullFromAPI(name); -+ CACHE.put(name, values); -+ return values; -+ } -+ -+ // Laggggggggggggggggggggggggggggggggggggggggg -+ public static String[] pullFromAPI(String name) { -+ try { -+ String uuid = new JsonParser().parse(new InputStreamReader(new URL("https://api.mojang.com/users/profiles/minecraft/" + name) -+ .openStream())).getAsJsonObject().get("id").getAsString(); -+ JsonObject property = new JsonParser() -+ .parse(new InputStreamReader(new URL("https://sessionserver.mojang.com/session/minecraft/profile/" + uuid + "?unsigned=false") -+ .openStream())).getAsJsonObject().get("properties").getAsJsonArray().get(0).getAsJsonObject(); -+ return new String[] {property.get("value").getAsString(), property.get("signature").getAsString()}; -+ } catch (IOException | IllegalStateException e) { -+ return null; -+ } ++ public String toString() { ++ return "CraftBot{" + "name=" + getName() + '}'; + } +} diff --git a/src/main/java/top/leavesmc/leaves/util/MathUtils.java b/src/main/java/top/leavesmc/leaves/util/MathUtils.java diff --git a/patches/server/0011-Add-fakeplayer-action-support.patch b/patches/server/0011-Add-fakeplayer-action-support.patch index f202cf63..163d6bb7 100644 --- a/patches/server/0011-Add-fakeplayer-action-support.patch +++ b/patches/server/0011-Add-fakeplayer-action-support.patch @@ -29,10 +29,125 @@ index 898c61c25675232e203ee2c872ca25804c41358c..4d6d025c78086f186da710ae46f65eda } } -diff --git a/src/main/java/top/leavesmc/leaves/bot/Bot.java b/src/main/java/top/leavesmc/leaves/bot/Bot.java -index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab398d2b468 100644 ---- a/src/main/java/top/leavesmc/leaves/bot/Bot.java -+++ b/src/main/java/top/leavesmc/leaves/bot/Bot.java +diff --git a/src/main/java/top/leavesmc/leaves/bot/BotCommand.java b/src/main/java/top/leavesmc/leaves/bot/BotCommand.java +index 292fede3bb850892e57640814440bdcebfd43aec..7693118ee1bb06d9938b866dca8e6cc9d2f1dded 100644 +--- a/src/main/java/top/leavesmc/leaves/bot/BotCommand.java ++++ b/src/main/java/top/leavesmc/leaves/bot/BotCommand.java +@@ -6,6 +6,10 @@ import org.bukkit.Location; + import org.bukkit.command.Command; + import org.bukkit.command.CommandSender; + import org.bukkit.entity.Player; ++import top.leavesmc.leaves.bot.agent.Actions; ++import top.leavesmc.leaves.bot.agent.BotAction; ++import top.leavesmc.leaves.entity.CraftBot; ++import top.leavesmc.leaves.util.MathUtils; + + import java.util.ArrayList; + import java.util.List; +@@ -15,7 +19,7 @@ public class BotCommand extends Command { + public BotCommand(String name) { + super(name); + this.description = "FakePlayer Command"; +- this.usageMessage = "/bot [create | remove]"; ++ this.usageMessage = "/bot [create | remove | action]"; + this.setPermission("bukkit.command.bot"); + } + +@@ -26,13 +30,29 @@ public class BotCommand extends Command { + if (args.length <= 1) { + list.add("create"); + list.add("remove"); +- } else { ++ list.add("action"); ++ } ++ ++ if (args.length == 2) { ++ switch (args[0]) { ++ case "create" -> list.add(""); ++ case "remove", "action" -> list.addAll(ServerBot.getBots().stream().map(e -> e.getName().getString()).toList()); ++ } ++ } ++ ++ if (args.length == 3) { ++ switch (args[0]) { ++ case "action" -> list.addAll(Actions.getAll().stream().map(BotAction::getName).toList()); ++ } ++ } ++ ++ if (args.length == 4) { + switch (args[0]) { + case "create" -> list.add("[BotName]"); + case "remove" -> list.addAll(ServerBot.getBots().stream().map(e -> e.getName().getString()).toList()); ++ case "action" -> list.add("[tickDelay]"); + } + } +- + return list; + } + +@@ -50,6 +70,8 @@ public class BotCommand extends Command { + + case "remove" -> this.onRemove(sender, args); + ++ case "action" -> this.onAction(sender, args); ++ + default -> { + sender.sendMessage(ChatColor.RED + "Usage: " + usageMessage); + return false; +@@ -61,7 +83,7 @@ public class BotCommand extends Command { + + private void onCreate(CommandSender sender, String[] args) { + if (args.length < 2) { +- sender.sendMessage(ChatColor.RED + "Use /bot create [name] to create a fakeplayer"); ++ sender.sendMessage(ChatColor.RED + "Use /bot create to create a fakeplayer"); + return; + } + +@@ -85,7 +107,7 @@ public class BotCommand extends Command { + + private void onRemove(CommandSender sender, String[] args) { + if (args.length < 2) { +- sender.sendMessage(ChatColor.RED + "Use /bot remove [name] to remove a fakeplayer"); ++ sender.sendMessage(ChatColor.RED + "Use /bot remove to remove a fakeplayer"); + return; + } + +@@ -98,4 +120,31 @@ public class BotCommand extends Command { + + bot.kill(); + } ++ ++ private void onAction(CommandSender sender, String[] args) { ++ if (args.length < 3) { ++ sender.sendMessage(ChatColor.RED + "Use /bot action to make fakeplayer do action"); ++ return; ++ } ++ ++ int tickDelay = 20; ++ if (args.length > 3 && MathUtils.isNumeric(args[3])) { ++ tickDelay = Integer.parseInt(args[3]); ++ } ++ ++ ServerBot bot = ServerBot.getBot(args[1]); ++ BotAction action = Actions.getForName(args[2]); ++ ++ if (bot == null) { ++ sender.sendMessage(ChatColor.RED + "This fakeplayer is null"); ++ return; ++ } ++ if (action == null) { ++ sender.sendMessage(ChatColor.RED + "This action is null"); ++ return; ++ } ++ ++ bot.setBotAction(action.getNew(tickDelay, ((CraftBot) sender).getHandle())); ++ sender.sendMessage("Action set"); ++ } + } +diff --git a/src/main/java/top/leavesmc/leaves/bot/ServerBot.java b/src/main/java/top/leavesmc/leaves/bot/ServerBot.java +index b833653b671df660686134754c794d3e6686b112..d0b88733427d81aacb9699faf695c67988e83fe6 100644 +--- a/src/main/java/top/leavesmc/leaves/bot/ServerBot.java ++++ b/src/main/java/top/leavesmc/leaves/bot/ServerBot.java @@ -1,9 +1,12 @@ package top.leavesmc.leaves.bot; @@ -54,7 +169,7 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 import net.minecraft.network.syncher.EntityDataAccessor; import net.minecraft.network.syncher.EntityDataSerializers; import net.minecraft.server.MinecraftServer; -@@ -22,11 +26,14 @@ import net.minecraft.server.level.TicketType; +@@ -22,9 +26,13 @@ import net.minecraft.server.level.TicketType; import net.minecraft.server.network.ServerGamePacketListenerImpl; import net.minecraft.server.network.ServerPlayerConnection; import net.minecraft.util.Mth; @@ -66,14 +181,26 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 import net.minecraft.world.entity.MoverType; +import net.minecraft.world.entity.item.ItemEntity; import net.minecraft.world.level.ChunkPos; --import net.minecraft.world.level.Level; import net.minecraft.world.level.chunk.LevelChunk; import net.minecraft.world.phys.AABB; - import net.minecraft.world.phys.Vec3; -@@ -47,10 +54,14 @@ import org.bukkit.inventory.ItemStack; +@@ -37,11 +45,13 @@ import org.bukkit.World; + import org.bukkit.block.Block; + import org.bukkit.craftbukkit.CraftWorld; + import org.bukkit.craftbukkit.entity.CraftPlayer; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; + import org.bukkit.craftbukkit.scheduler.MinecraftInternalPlugin; + import org.bukkit.entity.Player; + import org.bukkit.event.entity.CreatureSpawnEvent; + import org.bukkit.event.player.PlayerJoinEvent; + import org.bukkit.event.player.PlayerTeleportEvent; ++import org.bukkit.inventory.ItemStack; import org.bukkit.plugin.Plugin; import org.bukkit.util.BoundingBox; import org.bukkit.util.Vector; +@@ -49,10 +59,14 @@ import org.jetbrains.annotations.NotNull; + import top.leavesmc.leaves.entity.Bot; + import top.leavesmc.leaves.entity.CraftBot; + import top.leavesmc.leaves.event.bot.BotCreateEvent; +import top.leavesmc.leaves.bot.agent.BotAction; import top.leavesmc.leaves.util.MathUtils; @@ -85,7 +212,7 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 import java.util.Objects; import java.util.Set; import java.util.UUID; -@@ -59,12 +70,17 @@ public class Bot extends ServerPlayer { +@@ -61,12 +75,17 @@ public class ServerBot extends ServerPlayer { private Vector velocity; private Vector oldVelocity; @@ -105,13 +232,9 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 + + private final ItemStack defaultItem; - private static final Set bots = new HashSet<>(); + private static final Set bots = new HashSet<>(); private static final Plugin MINECRAFT_PLUGIN = new MinecraftInternalPlugin(); -@@ -74,9 +90,12 @@ public class Bot extends ServerPlayer { - this.entityData.set(new EntityDataAccessor<>(16, EntityDataSerializers.INT), 0xFF); - - this.velocity = new Vector(0, 0, 0); -+ this.action = null; +@@ -79,6 +98,8 @@ public class ServerBot extends ServerPlayer { this.oldVelocity = velocity.clone(); this.noFallTicks = 60; this.fireTicks = 0; @@ -120,7 +243,7 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 this.removeOnDeath = true; } -@@ -170,12 +189,17 @@ public class Bot extends ServerPlayer { +@@ -185,12 +206,17 @@ public class ServerBot extends ServerPlayer { } } @@ -138,7 +261,7 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 // die check end @Override -@@ -183,10 +207,6 @@ public class Bot extends ServerPlayer { +@@ -198,10 +224,6 @@ public class ServerBot extends ServerPlayer { return groundTicks != 0; } @@ -149,7 +272,7 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 public static boolean solidAt(Location loc) { Block block = loc.getBlock(); BoundingBox box = block.getBoundingBox(); -@@ -275,12 +295,24 @@ public class Bot extends ServerPlayer { +@@ -296,12 +318,24 @@ public class ServerBot extends ServerPlayer { public void tick() { // loadChunks(); // Load chunks super.tick(); @@ -178,7 +301,7 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 if (checkGround()) { if (groundTicks < 5) groundTicks++; -@@ -308,7 +340,88 @@ public class Bot extends ServerPlayer { +@@ -329,7 +363,88 @@ public class ServerBot extends ServerPlayer { checkOutOfWorld(); @@ -267,7 +390,7 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 } @Override -@@ -341,21 +454,6 @@ public class Bot extends ServerPlayer { +@@ -362,21 +477,6 @@ public class ServerBot extends ServerPlayer { } } @@ -289,7 +412,7 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 public Location getLocation() { return getBukkitPlayer().getLocation(); } -@@ -447,6 +545,68 @@ public class Bot extends ServerPlayer { +@@ -468,6 +568,68 @@ public class ServerBot extends ServerPlayer { this.move(MoverType.SELF, new Vec3(velocity.getX(), y, velocity.getZ())); } @@ -355,124 +478,9 @@ index 7a81e5b8aa7aaa5c8a6718d0ad60379094e7b15f..2a0aff502b03d149c0c42da7e8ad3ab3 + this.newAction = botAction; + } + - public static Bot getBot(ServerPlayer player) { - Bot bot = null; - for (Bot b : bots) { -diff --git a/src/main/java/top/leavesmc/leaves/bot/BotCommand.java b/src/main/java/top/leavesmc/leaves/bot/BotCommand.java -index 3b8d44fb61d504e521e73d3a34f6bd8ad9f13aee..ec1c53e2f98717b648c80ddf7573edad7f29b135 100644 ---- a/src/main/java/top/leavesmc/leaves/bot/BotCommand.java -+++ b/src/main/java/top/leavesmc/leaves/bot/BotCommand.java -@@ -5,7 +5,11 @@ import org.bukkit.ChatColor; - import org.bukkit.Location; - import org.bukkit.command.Command; - import org.bukkit.command.CommandSender; -+import org.bukkit.craftbukkit.entity.CraftPlayer; - import org.bukkit.entity.Player; -+import top.leavesmc.leaves.bot.agent.Actions; -+import top.leavesmc.leaves.bot.agent.BotAction; -+import top.leavesmc.leaves.util.MathUtils; - - import java.util.ArrayList; - import java.util.List; -@@ -15,7 +19,7 @@ public class BotCommand extends Command { - public BotCommand(String name) { - super(name); - this.description = "FakePlayer Command"; -- this.usageMessage = "/bot [create | remove]"; -+ this.usageMessage = "/bot [create | remove | action]"; - this.setPermission("bukkit.command.bot"); - } - -@@ -26,13 +30,27 @@ public class BotCommand extends Command { - if (args.length <= 1) { - list.add("create"); - list.add("remove"); -- } else { -+ list.add("action"); -+ } -+ -+ if (args.length == 2) { - switch (args[0]) { -- case "create" -> list.add("[BotName]"); -- case "remove" -> list.addAll(Bot.getBots().stream().map(e -> e.getName().getString()).toList()); -+ case "create" -> list.add(""); -+ case "remove", "action" -> list.addAll(Bot.getBots().stream().map(e -> e.getName().getString()).toList()); - } - } - -+ if (args.length == 3) { -+ switch (args[0]) { -+ case "action" -> list.addAll(Actions.getAll().stream().map(BotAction::getName).toList()); -+ } -+ } -+ -+ if (args.length == 4) { -+ switch (args[0]) { -+ case "action" -> list.add("[tickDelay]"); -+ } -+ } - return list; - } - -@@ -50,6 +68,8 @@ public class BotCommand extends Command { - - case "remove" -> this.onRemove(sender, args); - -+ case "action" -> this.onAction(sender, args); -+ - default -> { - sender.sendMessage(ChatColor.RED + "Usage: " + usageMessage); - return false; -@@ -61,7 +81,7 @@ public class BotCommand extends Command { - - private void onCreate(CommandSender sender, String[] args) { - if (args.length < 2) { -- sender.sendMessage(ChatColor.RED + "Use /bot create [name] to create a fakeplayer"); -+ sender.sendMessage(ChatColor.RED + "Use /bot create to create a fakeplayer"); - return; - } - -@@ -85,7 +105,7 @@ public class BotCommand extends Command { - - private void onRemove(CommandSender sender, String[] args) { - if (args.length < 2) { -- sender.sendMessage(ChatColor.RED + "Use /bot remove [name] to remove a fakeplayer"); -+ sender.sendMessage(ChatColor.RED + "Use /bot remove to remove a fakeplayer"); - return; - } - -@@ -98,4 +118,31 @@ public class BotCommand extends Command { - - bot.kill(); - } -+ -+ private void onAction(CommandSender sender, String[] args) { -+ if (args.length < 3) { -+ sender.sendMessage(ChatColor.RED + "Use /bot action to make fakeplayer do action"); -+ return; -+ } -+ -+ int tickDelay = 20; -+ if (args.length > 3 && MathUtils.isNumeric(args[3])) { -+ tickDelay = Integer.parseInt(args[3]); -+ } -+ -+ Bot bot = Bot.getBot(args[1]); -+ BotAction action = Actions.getForName(args[2]); -+ -+ if (bot == null) { -+ sender.sendMessage(ChatColor.RED + "This fakeplayer is null"); -+ return; -+ } -+ if (action == null) { -+ sender.sendMessage(ChatColor.RED + "This action is null"); -+ return; -+ } -+ -+ bot.setBotAction(action.getNew(tickDelay, ((CraftPlayer) sender).getHandle())); -+ sender.sendMessage("Action set"); -+ } - } + public static ServerBot getBot(ServerPlayer player) { + ServerBot bot = null; + for (ServerBot b : bots) { diff --git a/src/main/java/top/leavesmc/leaves/bot/agent/Actions.java b/src/main/java/top/leavesmc/leaves/bot/agent/Actions.java new file mode 100644 index 0000000000000000000000000000000000000000..ccedc7b77bef852b66dfa8c4ee3d69b3c71717a0 @@ -528,14 +536,14 @@ index 0000000000000000000000000000000000000000..ccedc7b77bef852b66dfa8c4ee3d69b3 +} diff --git a/src/main/java/top/leavesmc/leaves/bot/agent/BotAction.java b/src/main/java/top/leavesmc/leaves/bot/agent/BotAction.java new file mode 100644 -index 0000000000000000000000000000000000000000..78f04e28afa856c900f84af42f22666bec3ec830 +index 0000000000000000000000000000000000000000..dd19f41fd5e1ad27637c0c3a8e96e7c17a96f891 --- /dev/null +++ b/src/main/java/top/leavesmc/leaves/bot/agent/BotAction.java @@ -0,0 +1,42 @@ +package top.leavesmc.leaves.bot.agent; + +import net.minecraft.server.level.ServerPlayer; -+import top.leavesmc.leaves.bot.Bot; ++import top.leavesmc.leaves.bot.ServerBot; + +public abstract class BotAction { + @@ -572,11 +580,11 @@ index 0000000000000000000000000000000000000000..78f04e28afa856c900f84af42f22666b + + public abstract BotAction getNew(int tickDelay, ServerPlayer player); + -+ public abstract void tick(Bot bot); ++ public abstract void tick(ServerBot bot); +} diff --git a/src/main/java/top/leavesmc/leaves/bot/agent/action/AttackAction.java b/src/main/java/top/leavesmc/leaves/bot/agent/action/AttackAction.java new file mode 100644 -index 0000000000000000000000000000000000000000..975b45b7ba3107b143577f53c6b54194e3a699b6 +index 0000000000000000000000000000000000000000..b69de7c67d39a84310f6105ae0619eb90b278cb8 --- /dev/null +++ b/src/main/java/top/leavesmc/leaves/bot/agent/action/AttackAction.java @@ -0,0 +1,26 @@ @@ -584,7 +592,7 @@ index 0000000000000000000000000000000000000000..975b45b7ba3107b143577f53c6b54194 + +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.world.phys.EntityHitResult; -+import top.leavesmc.leaves.bot.Bot; ++import top.leavesmc.leaves.bot.ServerBot; +import top.leavesmc.leaves.bot.agent.BotAction; + +public class AttackAction extends BotAction { @@ -599,7 +607,7 @@ index 0000000000000000000000000000000000000000..975b45b7ba3107b143577f53c6b54194 + } + + @Override -+ public void tick(Bot bot) { ++ public void tick(ServerBot bot) { + EntityHitResult result = bot.getTargetEntity(3); + if (result != null) { + bot.attack(result.getEntity()); @@ -608,14 +616,14 @@ index 0000000000000000000000000000000000000000..975b45b7ba3107b143577f53c6b54194 +} diff --git a/src/main/java/top/leavesmc/leaves/bot/agent/action/DropAction.java b/src/main/java/top/leavesmc/leaves/bot/agent/action/DropAction.java new file mode 100644 -index 0000000000000000000000000000000000000000..91da2f89b6937a78a39da2a6f2c346f0ad446001 +index 0000000000000000000000000000000000000000..4a072e9b2b6c33e5c3d5b2230b66484bb2dfc191 --- /dev/null +++ b/src/main/java/top/leavesmc/leaves/bot/agent/action/DropAction.java @@ -0,0 +1,22 @@ +package top.leavesmc.leaves.bot.agent.action; + +import net.minecraft.server.level.ServerPlayer; -+import top.leavesmc.leaves.bot.Bot; ++import top.leavesmc.leaves.bot.ServerBot; +import top.leavesmc.leaves.bot.agent.BotAction; + +public class DropAction extends BotAction { @@ -629,21 +637,21 @@ index 0000000000000000000000000000000000000000..91da2f89b6937a78a39da2a6f2c346f0 + } + + @Override -+ public void tick(Bot bot) { ++ public void tick(ServerBot bot) { + bot.dropAll(); + this.setCancel(true); + } +} diff --git a/src/main/java/top/leavesmc/leaves/bot/agent/action/RotateAction.java b/src/main/java/top/leavesmc/leaves/bot/agent/action/RotateAction.java new file mode 100644 -index 0000000000000000000000000000000000000000..8f7263a97f56144e98794eae3e137a3a73a6d909 +index 0000000000000000000000000000000000000000..450d74eddb7667b2c720cca76a397eaf7daa14d1 --- /dev/null +++ b/src/main/java/top/leavesmc/leaves/bot/agent/action/RotateAction.java @@ -0,0 +1,29 @@ +package top.leavesmc.leaves.bot.agent.action; + +import net.minecraft.server.level.ServerPlayer; -+import top.leavesmc.leaves.bot.Bot; ++import top.leavesmc.leaves.bot.ServerBot; +import top.leavesmc.leaves.bot.agent.BotAction; + +public class RotateAction extends BotAction { @@ -664,21 +672,21 @@ index 0000000000000000000000000000000000000000..8f7263a97f56144e98794eae3e137a3a + } + + @Override -+ public void tick(Bot bot) { ++ public void tick(ServerBot bot) { + bot.faceLocation(player.getBukkitEntity().getLocation()); + this.setCancel(true); + } +} diff --git a/src/main/java/top/leavesmc/leaves/bot/agent/action/StopAction.java b/src/main/java/top/leavesmc/leaves/bot/agent/action/StopAction.java new file mode 100644 -index 0000000000000000000000000000000000000000..09049b934d34aece15a201473f1cf4ed500a05a7 +index 0000000000000000000000000000000000000000..ec47646ca94b2eab55ac0f32de859f10867f87f3 --- /dev/null +++ b/src/main/java/top/leavesmc/leaves/bot/agent/action/StopAction.java @@ -0,0 +1,21 @@ +package top.leavesmc.leaves.bot.agent.action; + +import net.minecraft.server.level.ServerPlayer; -+import top.leavesmc.leaves.bot.Bot; ++import top.leavesmc.leaves.bot.ServerBot; +import top.leavesmc.leaves.bot.agent.BotAction; + +public class StopAction extends BotAction { @@ -692,13 +700,13 @@ index 0000000000000000000000000000000000000000..09049b934d34aece15a201473f1cf4ed + } + + @Override -+ public void tick(Bot bot) { ++ public void tick(ServerBot bot) { + this.setCancel(true); + } +} diff --git a/src/main/java/top/leavesmc/leaves/bot/agent/action/UseItemAction.java b/src/main/java/top/leavesmc/leaves/bot/agent/action/UseItemAction.java new file mode 100644 -index 0000000000000000000000000000000000000000..8f39161ff8f84392ef57a1ecda3b098a791841e5 +index 0000000000000000000000000000000000000000..7d12bc08b92cffbddf29b60fbaff2f2a43c4867e --- /dev/null +++ b/src/main/java/top/leavesmc/leaves/bot/agent/action/UseItemAction.java @@ -0,0 +1,24 @@ @@ -706,7 +714,7 @@ index 0000000000000000000000000000000000000000..8f39161ff8f84392ef57a1ecda3b098a + +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.world.InteractionHand; -+import top.leavesmc.leaves.bot.Bot; ++import top.leavesmc.leaves.bot.ServerBot; +import top.leavesmc.leaves.bot.agent.BotAction; + +public class UseItemAction extends BotAction { @@ -720,7 +728,7 @@ index 0000000000000000000000000000000000000000..8f39161ff8f84392ef57a1ecda3b098a + } + + @Override -+ public void tick(Bot bot) { ++ public void tick(ServerBot bot) { + bot.getInventory().getSelected().use(bot.getLevel(), bot, InteractionHand.MAIN_HAND); + bot.punch(); + bot.updateItemInMainHand(); @@ -728,7 +736,7 @@ index 0000000000000000000000000000000000000000..8f39161ff8f84392ef57a1ecda3b098a +} diff --git a/src/main/java/top/leavesmc/leaves/bot/agent/action/UseItemOnAction.java b/src/main/java/top/leavesmc/leaves/bot/agent/action/UseItemOnAction.java new file mode 100644 -index 0000000000000000000000000000000000000000..a58c57e572b5cd952b0b276a8157250170ce6285 +index 0000000000000000000000000000000000000000..d32cf3ddb83a8e9f18fc2a2bb19d4e5c76df9296 --- /dev/null +++ b/src/main/java/top/leavesmc/leaves/bot/agent/action/UseItemOnAction.java @@ -0,0 +1,29 @@ @@ -738,7 +746,7 @@ index 0000000000000000000000000000000000000000..a58c57e572b5cd952b0b276a81572501 +import net.minecraft.world.InteractionHand; +import net.minecraft.world.phys.BlockHitResult; +import net.minecraft.world.phys.HitResult; -+import top.leavesmc.leaves.bot.Bot; ++import top.leavesmc.leaves.bot.ServerBot; +import top.leavesmc.leaves.bot.agent.BotAction; + +public class UseItemOnAction extends BotAction { @@ -752,7 +760,7 @@ index 0000000000000000000000000000000000000000..a58c57e572b5cd952b0b276a81572501 + } + + @Override -+ public void tick(Bot bot) { ++ public void tick(ServerBot bot) { + HitResult result = bot.getRayTrace(4); + if (result != null && result.getType() == HitResult.Type.BLOCK) { + bot.gameMode.useItemOn(bot, bot.getLevel(), bot.getItemInHand(InteractionHand.MAIN_HAND), InteractionHand.MAIN_HAND, (BlockHitResult) result); diff --git a/patches/server/0016-Spectator-dont-get-Advancement.patch b/patches/server/0016-Spectator-dont-get-Advancement.patch index c2b523ab..b1ddcacd 100644 --- a/patches/server/0016-Spectator-dont-get-Advancement.patch +++ b/patches/server/0016-Spectator-dont-get-Advancement.patch @@ -5,7 +5,7 @@ Subject: [PATCH] Spectator dont get Advancement diff --git a/src/main/java/net/minecraft/server/PlayerAdvancements.java b/src/main/java/net/minecraft/server/PlayerAdvancements.java -index 6de539d8819b9c25fbf96cd2ac8ef4a87c0fb231..d8ae25c5c012b18f5b2ca7d5ec92b0965fb2087a 100644 +index 8548ef7f79e85aca593928b8e748d8b6d53e52bd..7f9786de88a03786c39fa3e85779ac1e751ef51a 100644 --- a/src/main/java/net/minecraft/server/PlayerAdvancements.java +++ b/src/main/java/net/minecraft/server/PlayerAdvancements.java @@ -49,6 +49,7 @@ import net.minecraft.server.level.ServerPlayer; @@ -14,7 +14,7 @@ index 6de539d8819b9c25fbf96cd2ac8ef4a87c0fb231..d8ae25c5c012b18f5b2ca7d5ec92b096 import net.minecraft.world.level.GameRules; +import net.minecraft.world.level.GameType; import org.slf4j.Logger; - import top.leavesmc.leaves.bot.Bot; + import top.leavesmc.leaves.bot.ServerBot; @@ -280,6 +281,11 @@ public class PlayerAdvancements { return false;