fix: fixes #55

This commit is contained in:
Helvetica Volubi
2025-09-01 22:11:48 +08:00
parent 192ef93833
commit d985a9ca33
20 changed files with 152 additions and 186 deletions
@@ -5,7 +5,7 @@ Subject: [PATCH] Add config to enable cross region damage trace
diff --git a/net/minecraft/server/level/ServerPlayer.java b/net/minecraft/server/level/ServerPlayer.java diff --git a/net/minecraft/server/level/ServerPlayer.java b/net/minecraft/server/level/ServerPlayer.java
index 11e6197dec541b28733715f0d7eaa4c7b834d632..6b7c92fdf562dfa46eee8e8acbc82b02fc3226c5 100644 index 11e6197dec541b28733715f0d7eaa4c7b834d632..de1263404395c28209234a556347284fa557f81c 100644
--- a/net/minecraft/server/level/ServerPlayer.java --- a/net/minecraft/server/level/ServerPlayer.java
+++ b/net/minecraft/server/level/ServerPlayer.java +++ b/net/minecraft/server/level/ServerPlayer.java
@@ -1345,6 +1345,13 @@ public class ServerPlayer extends Player implements ca.spottedleaf.moonrise.patc @@ -1345,6 +1345,13 @@ public class ServerPlayer extends Player implements ca.spottedleaf.moonrise.patc
@@ -40,7 +40,7 @@ index 11e6197dec541b28733715f0d7eaa4c7b834d632..6b7c92fdf562dfa46eee8e8acbc82b02
+ } catch (Throwable ex) { + } catch (Throwable ex) {
+ LOGGER.error(ex.getMessage(), ex); + LOGGER.error(ex.getMessage(), ex);
+ } + }
+ }, null, 1L ); + }, null, 1L);
+ } + }
+ // Luminol End - Cross Region Damage trace + // Luminol End - Cross Region Damage trace
+ +
@@ -10,15 +10,15 @@ import java.util.List;
@ConfigClassInfo(configAttribution = EnumConfigCategory.FUNCTION, mainName = "survux-protocol") @ConfigClassInfo(configAttribution = EnumConfigCategory.FUNCTION, mainName = "survux-protocol")
public class SurvuxProtocolConfig implements IConfigModule { public class SurvuxProtocolConfig implements IConfigModule {
@TransformedConfig(name = "entity-protocol", category = {"misc", "survux-protocol"}) @TransformedConfig(name = "entity-protocol", category = {"misc", "survux-protocol"})
@ConfigInfo(baseName = "entity-protocol") @ConfigInfo(baseName = "entity-protocol")
public static boolean entityProtocol = false; public static boolean entityProtocol = false;
@TransformedConfig(name = "hud-logger-protocol", category = {"misc", "survux-protocol"}) @TransformedConfig(name = "hud-logger-protocol", category = {"misc", "survux-protocol"})
@ConfigInfo(baseName = "hud-logger-protocol") @ConfigInfo(baseName = "hud-logger-protocol")
public static boolean hudLoggerProtocol = false; public static boolean hudLoggerProtocol = false;
@TransformedConfig(name = "hud-metadata-protocol", category = {"misc", "survux-protocol"}) @TransformedConfig(name = "hud-metadata-protocol", category = {"misc", "survux-protocol"})
@ConfigInfo(baseName = "hud-metadata-protocol") @ConfigInfo(baseName = "hud-metadata-protocol")
public static boolean hudMetadataProtocol = false; public static boolean hudMetadataProtocol = false;
@@ -26,7 +26,7 @@ public class SurvuxProtocolConfig implements IConfigModule {
@ConfigInfo(baseName = "hud-metadata-share-seed") @ConfigInfo(baseName = "hud-metadata-share-seed")
public static boolean hudMetadataShareSeed = false; public static boolean hudMetadataShareSeed = false;
@TransformedConfig(name ="structure-protocol", category = {"misc", "survux-protocol"}) @TransformedConfig(name = "structure-protocol", category = {"misc", "survux-protocol"})
@ConfigInfo(baseName = "structure-protocol") @ConfigInfo(baseName = "structure-protocol")
public static boolean structureProtocol = false; public static boolean structureProtocol = false;
@@ -50,6 +50,7 @@ import static net.kyori.adventure.text.Component.text;
public class BotCommand extends Command { public class BotCommand extends Command {
private static final Logger LOGGER = LogUtils.getLogger(); private static final Logger LOGGER = LogUtils.getLogger();
public BotCommand() { public BotCommand() {
super("bot"); super("bot");
this.setPermission("lophine.bot"); this.setPermission("lophine.bot");
@@ -115,8 +116,8 @@ public class BotCommand extends Command {
String fullName = BotUtil.getFullName(botName); String fullName = BotUtil.getFullName(botName);
if (this.canCreate(sender, fullName)) { if (this.canCreate(sender, fullName)) {
BotCreateState.Builder builder = BotCreateState.builder(botName, Bukkit.getWorlds().getFirst().getSpawnLocation()) BotCreateState.Builder builder = BotCreateState.builder(botName, Bukkit.getWorlds().getFirst().getSpawnLocation())
.createReason(BotCreateEvent.CreateReason.COMMAND) .createReason(BotCreateEvent.CreateReason.COMMAND)
.creator(sender); .creator(sender);
if (args.length >= 3) { if (args.length >= 3) {
builder.skinName(args[2]); builder.skinName(args[2]);
@@ -154,7 +155,7 @@ public class BotCommand extends Command {
String botName = args[1]; String botName = args[1];
BotList botList = BotList.INSTANCE; BotList botList = BotList.INSTANCE;
ServerBot bot = botList.getBotByName(BotUtil.getFullName(botName)); ServerBot bot = botList.getBotByName(BotUtil.getFullName(botName));
if (bot == null) { if (bot == null) {
sender.sendMessage(text("This fakeplayer is not in server", NamedTextColor.RED)); sender.sendMessage(text("This fakeplayer is not in server", NamedTextColor.RED));
return true; return true;
@@ -223,7 +224,7 @@ public class BotCommand extends Command {
private boolean handleList(CommandSender sender, String[] args) { private boolean handleList(CommandSender sender, String[] args) {
BotList botList = BotList.INSTANCE; BotList botList = BotList.INSTANCE;
if (args.length < 2) { if (args.length < 2) {
Map<World, List<String>> botMap = new HashMap<>(); Map<World, List<String>> botMap = new HashMap<>();
for (World world : Bukkit.getWorlds()) { for (World world : Bukkit.getWorlds()) {
@@ -265,7 +266,7 @@ public class BotCommand extends Command {
sender.sendMessage(text("Bot action feature is disabled!", NamedTextColor.RED)); sender.sendMessage(text("Bot action feature is disabled!", NamedTextColor.RED));
return true; return true;
} }
if (args.length < 3) { if (args.length < 3) {
sender.sendMessage(text("Use /bot action <name> <action> to make fakeplayer do action", NamedTextColor.RED)); sender.sendMessage(text("Use /bot action <name> <action> to make fakeplayer do action", NamedTextColor.RED));
return true; return true;
@@ -336,7 +337,7 @@ public class BotCommand extends Command {
for (int i = 0; i < bot.getBotActions().size(); i++) { for (int i = 0; i < bot.getBotActions().size(); i++) {
ServerBotAction<?> action = bot.getBotActions().get(i); ServerBotAction<?> action = bot.getBotActions().get(i);
BotActionStopEvent event = new BotActionStopEvent( BotActionStopEvent event = new BotActionStopEvent(
bot.getBukkitEntity(), action.getName(), action.getUUID(), BotActionStopEvent.Reason.COMMAND, sender bot.getBukkitEntity(), action.getName(), action.getUUID(), BotActionStopEvent.Reason.COMMAND, sender
); );
event.callEvent(); event.callEvent();
if (!event.isCancelled()) { if (!event.isCancelled()) {
@@ -357,7 +358,7 @@ public class BotCommand extends Command {
ServerBotAction<?> action = bot.getBotActions().get(i); ServerBotAction<?> action = bot.getBotActions().get(i);
BotActionStopEvent event = new BotActionStopEvent( BotActionStopEvent event = new BotActionStopEvent(
bot.getBukkitEntity(), action.getName(), action.getUUID(), BotActionStopEvent.Reason.COMMAND, sender bot.getBukkitEntity(), action.getName(), action.getUUID(), BotActionStopEvent.Reason.COMMAND, sender
); );
event.callEvent(); event.callEvent();
if (!event.isCancelled()) { if (!event.isCancelled()) {
@@ -375,7 +376,7 @@ public class BotCommand extends Command {
sender.sendMessage(text("Bot config feature is disabled!", NamedTextColor.RED)); sender.sendMessage(text("Bot config feature is disabled!", NamedTextColor.RED));
return true; return true;
} }
if (args.length < 3) { if (args.length < 3) {
sender.sendMessage(text("Use /bot config <name> <config> to modify fakeplayer's config", NamedTextColor.RED)); sender.sendMessage(text("Use /bot config <name> <config> to modify fakeplayer's config", NamedTextColor.RED));
return true; return true;
@@ -421,7 +422,7 @@ public class BotCommand extends Command {
sender.sendMessage(text("Bot save/load feature is disabled!", NamedTextColor.RED)); sender.sendMessage(text("Bot save/load feature is disabled!", NamedTextColor.RED));
return true; return true;
} }
if (args.length < 2) { if (args.length < 2) {
sender.sendMessage(text("Use /bot save <name> to save a fakeplayer", NamedTextColor.RED)); sender.sendMessage(text("Use /bot save <name> to save a fakeplayer", NamedTextColor.RED));
return true; return true;
@@ -446,7 +447,7 @@ public class BotCommand extends Command {
sender.sendMessage(text("Bot save/load feature is disabled!", NamedTextColor.RED)); sender.sendMessage(text("Bot save/load feature is disabled!", NamedTextColor.RED));
return true; return true;
} }
if (args.length < 2) { if (args.length < 2) {
sender.sendMessage(text("Use /bot load <name> to load a fakeplayer", NamedTextColor.RED)); sender.sendMessage(text("Use /bot load <name> to load a fakeplayer", NamedTextColor.RED));
return true; return true;
@@ -33,7 +33,8 @@ import org.leavesmc.leaves.plugin.MinecraftInternalPlugin;
import java.util.Objects; import java.util.Objects;
import java.util.function.Consumer; import java.util.function.Consumer;
public record BotCreateState(String realName, String name, String skinName, String[] skin, Location location, BotCreateEvent.CreateReason createReason, CommandSender creator) { public record BotCreateState(String realName, String name, String skinName, String[] skin, Location location,
BotCreateEvent.CreateReason createReason, CommandSender creator) {
private static final MinecraftServer server = MinecraftServer.getServer(); private static final MinecraftServer server = MinecraftServer.getServer();
@@ -117,25 +118,25 @@ public record BotCreateState(String realName, String name, String skinName, Stri
public void spawnWithSkin(Consumer<Bot> consumer) { public void spawnWithSkin(Consumer<Bot> consumer) {
Bukkit.getRegionScheduler().execute( Bukkit.getRegionScheduler().execute(
MinecraftInternalPlugin.INSTANCE, MinecraftInternalPlugin.INSTANCE,
location.getWorld(), location.getWorld(),
location.getBlockX() >> 4, location.getBlockX() >> 4,
location.getBlockZ() >> 4, location.getBlockZ() >> 4,
() -> { () -> {
this.mojangAPISkin(); this.mojangAPISkin();
Bukkit.getRegionScheduler().execute( Bukkit.getRegionScheduler().execute(
MinecraftInternalPlugin.INSTANCE, MinecraftInternalPlugin.INSTANCE,
location.getWorld(), location.getWorld(),
location.getBlockX() >> 4, location.getBlockX() >> 4,
location.getBlockZ() >> 4, location.getBlockZ() >> 4,
() -> { () -> {
CraftBot bot = this.spawn(); CraftBot bot = this.spawn();
if (bot != null && consumer != null) { if (bot != null && consumer != null) {
consumer.accept(bot); consumer.accept(bot);
} }
} }
); );
} }
); );
} }
@@ -38,9 +38,9 @@ public class BotInventoryContainer extends Inventory {
customData.putBoolean("Leaves.Gui.Placeholder", true); customData.putBoolean("Leaves.Gui.Placeholder", true);
DataComponentPatch patch = DataComponentPatch.builder() DataComponentPatch patch = DataComponentPatch.builder()
.set(DataComponents.CUSTOM_NAME, Component.empty()) .set(DataComponents.CUSTOM_NAME, Component.empty())
.set(DataComponents.CUSTOM_DATA, CustomData.of(customData)) .set(DataComponents.CUSTOM_DATA, CustomData.of(customData))
.build(); .build();
button = new ItemStack(Items.STRUCTURE_VOID); button = new ItemStack(Items.STRUCTURE_VOID);
button.applyComponents(patch); button.applyComponents(patch);
@@ -49,13 +49,7 @@ import org.jetbrains.annotations.Nullable;
import org.leavesmc.leaves.event.bot.*; import org.leavesmc.leaves.event.bot.*;
import org.slf4j.Logger; import org.slf4j.Logger;
import java.util.HashSet; import java.util.*;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Optional;
import java.util.Set;
import java.util.UUID;
import java.util.concurrent.CopyOnWriteArrayList; import java.util.concurrent.CopyOnWriteArrayList;
public class BotList { public class BotList {
@@ -189,8 +183,8 @@ public class BotList {
bot.renderData(); bot.renderData();
bot.initInventoryMenu(); bot.initInventoryMenu();
botsNameByWorldUuid botsNameByWorldUuid
.computeIfAbsent(bot.level().uuid.toString(), (k) -> new HashSet<>()) .computeIfAbsent(bot.level().uuid.toString(), (k) -> new HashSet<>())
.add(bot.getBukkitEntity().getRealName()); .add(bot.getBukkitEntity().getRealName());
BotList.LOGGER.info("{}[{}] logged in with entity id {} at ([{}]{}, {}, {})", bot.getName().getString(), "Local", bot.getId(), bot.level().serverLevelData.getLevelName(), bot.getX(), bot.getY(), bot.getZ()); BotList.LOGGER.info("{}[{}] logged in with entity id {} at ([{}]{}, {}, {})", bot.getName().getString(), "Local", bot.getId(), bot.level().serverLevelData.getLevelName(), bot.getX(), bot.getY(), bot.getZ());
return bot; return bot;
} }
@@ -253,11 +247,11 @@ public class BotList {
level.removePlayerImmediately(bot, Entity.RemovalReason.UNLOADED_WITH_PLAYER); level.removePlayerImmediately(bot, Entity.RemovalReason.UNLOADED_WITH_PLAYER);
} else { } else {
io.papermc.paper.threadedregions.RegionizedServer.getInstance().taskQueue.queueTickTaskQueue( io.papermc.paper.threadedregions.RegionizedServer.getInstance().taskQueue.queueTickTaskQueue(
level, chunkX, chunkZ, () -> { level, chunkX, chunkZ, () -> {
level.removePlayerImmediately(bot, Entity.RemovalReason.UNLOADED_WITH_PLAYER); level.removePlayerImmediately(bot, Entity.RemovalReason.UNLOADED_WITH_PLAYER);
}); });
} }
this.bots.remove(bot); this.bots.remove(bot);
this.botsByName.remove(bot.getScoreboardName().toLowerCase(Locale.ROOT)); this.botsByName.remove(bot.getScoreboardName().toLowerCase(Locale.ROOT));
@@ -314,8 +308,8 @@ public class BotList {
continue; continue;
} }
this.botsNameByWorldUuid this.botsNameByWorldUuid
.computeIfAbsent(levelUuid.toString(), (k) -> new HashSet<>()) .computeIfAbsent(levelUuid.toString(), (k) -> new HashSet<>())
.add(realName); .add(realName);
} }
} }
@@ -335,11 +329,11 @@ public class BotList {
String prevUuid = bot.level().uuid.toString(); String prevUuid = bot.level().uuid.toString();
String newUuid = level.uuid.toString(); String newUuid = level.uuid.toString();
this.botsNameByWorldUuid this.botsNameByWorldUuid
.computeIfAbsent(newUuid, (k) -> new HashSet<>()) .computeIfAbsent(newUuid, (k) -> new HashSet<>())
.add(bot.getBukkitEntity().getRealName()); .add(bot.getBukkitEntity().getRealName());
this.botsNameByWorldUuid this.botsNameByWorldUuid
.computeIfAbsent(prevUuid, (k) -> new HashSet<>()) .computeIfAbsent(prevUuid, (k) -> new HashSet<>())
.remove(bot.getBukkitEntity().getRealName()); .remove(bot.getBukkitEntity().getRealName());
} }
public void networkTick() { public void networkTick() {
@@ -45,9 +45,9 @@ public class MojangAPI {
public static String[] pullFromAPI(String name) { public static String[] pullFromAPI(String name) {
try { try {
String uuid = JsonParser.parseReader(new InputStreamReader(URI.create("https://api.mojang.com/users/profiles/minecraft/" + name).toURL().openStream())) String uuid = JsonParser.parseReader(new InputStreamReader(URI.create("https://api.mojang.com/users/profiles/minecraft/" + name).toURL().openStream()))
.getAsJsonObject().get("id").getAsString(); .getAsJsonObject().get("id").getAsString();
JsonObject property = JsonParser.parseReader(new InputStreamReader(URI.create("https://sessionserver.mojang.com/session/minecraft/profile/" + uuid + "?unsigned=false").toURL().openStream())) JsonObject property = JsonParser.parseReader(new InputStreamReader(URI.create("https://sessionserver.mojang.com/session/minecraft/profile/" + uuid + "?unsigned=false").toURL().openStream()))
.getAsJsonObject().get("properties").getAsJsonArray().get(0).getAsJsonObject(); .getAsJsonObject().get("properties").getAsJsonArray().get(0).getAsJsonObject();
return new String[]{property.get("value").getAsString(), property.get("signature").getAsString()}; return new String[]{property.get("value").getAsString(), property.get("signature").getAsString()};
} catch (IOException | IllegalStateException | IllegalArgumentException e) { } catch (IOException | IllegalStateException | IllegalArgumentException e) {
return null; return null;
@@ -62,11 +62,7 @@ import net.minecraft.world.level.gameevent.GameEvent;
import net.minecraft.world.level.portal.TeleportTransition; import net.minecraft.world.level.portal.TeleportTransition;
import net.minecraft.world.level.storage.ValueInput; import net.minecraft.world.level.storage.ValueInput;
import net.minecraft.world.level.storage.ValueOutput; import net.minecraft.world.level.storage.ValueOutput;
import net.minecraft.world.phys.AABB; import net.minecraft.world.phys.*;
import net.minecraft.world.phys.BlockHitResult;
import net.minecraft.world.phys.EntityHitResult;
import net.minecraft.world.phys.HitResult;
import net.minecraft.world.phys.Vec3;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.Location; import org.bukkit.Location;
import org.bukkit.command.CommandSender; import org.bukkit.command.CommandSender;
@@ -83,13 +79,7 @@ import org.leavesmc.leaves.plugin.MinecraftInternalPlugin;
import org.leavesmc.leaves.util.MathUtils; import org.leavesmc.leaves.util.MathUtils;
import org.slf4j.Logger; import org.slf4j.Logger;
import java.util.ArrayList; import java.util.*;
import java.util.Collection;
import java.util.EnumSet;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.UUID;
import java.util.function.Predicate; import java.util.function.Predicate;
public class ServerBot extends ServerPlayer { public class ServerBot extends ServerPlayer {
@@ -175,15 +165,15 @@ public class ServerBot extends ServerPlayer {
Input input = this.getLastClientInput(); Input input = this.getLastClientInput();
this.setLastClientInput( this.setLastClientInput(
new Input( new Input(
this.zza > 0, this.zza > 0,
this.zza < 0, this.zza < 0,
this.xxa > 0, this.xxa > 0,
this.xxa < 0, this.xxa < 0,
input.jump(), input.jump(),
input.shift(), input.shift(),
input.sprint() input.sprint()
) )
); );
} }
@@ -226,11 +216,11 @@ public class ServerBot extends ServerPlayer {
if (this.getConfigValue(Configs.TICK_TYPE) == TickType.NETWORK) { if (this.getConfigValue(Configs.TICK_TYPE) == TickType.NETWORK) {
try { try {
Bukkit.getRegionScheduler().execute( Bukkit.getRegionScheduler().execute(
MinecraftInternalPlugin.INSTANCE, MinecraftInternalPlugin.INSTANCE,
this.level().getWorld(), this.level().getWorld(),
this.getBlockX() >> 4, this.getBlockX() >> 4,
this.getBlockZ() >> 4, this.getBlockZ() >> 4,
this::runAction this::runAction
); );
} catch (Exception e) { } catch (Exception e) {
this.runAction(); this.runAction();
@@ -495,7 +485,7 @@ public class ServerBot extends ServerPlayer {
public void renderData() { public void renderData() {
this.getServer().getPlayerList().getPlayers().forEach( this.getServer().getPlayerList().getPlayers().forEach(
player -> this.sendFakeDataIfNeed(player, false) player -> this.sendFakeDataIfNeed(player, false)
); );
} }
@@ -21,12 +21,7 @@ import org.jetbrains.annotations.Contract;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
import org.leavesmc.leaves.bot.ServerBot; import org.leavesmc.leaves.bot.ServerBot;
import org.leavesmc.leaves.bot.agent.configs.AlwaysSendDataConfig; import org.leavesmc.leaves.bot.agent.configs.*;
import org.leavesmc.leaves.bot.agent.configs.LocatorBarConfig;
import org.leavesmc.leaves.bot.agent.configs.SimulationDistanceConfig;
import org.leavesmc.leaves.bot.agent.configs.SkipSleepConfig;
import org.leavesmc.leaves.bot.agent.configs.SpawnPhantomConfig;
import org.leavesmc.leaves.bot.agent.configs.TickTypeConfig;
import java.util.Collection; import java.util.Collection;
import java.util.HashMap; import java.util.HashMap;
@@ -60,8 +60,8 @@ public class ServerBreakBlockAction extends ServerTimerBotAction<ServerBreakBloc
if (!iblockdata.isAir()) { if (!iblockdata.isAir()) {
bot.swing(InteractionHand.MAIN_HAND); bot.swing(InteractionHand.MAIN_HAND);
EnchantmentHelper.onHitBlock( EnchantmentHelper.onHitBlock(
bot.level(), bot.getMainHandItem(), bot, bot, EquipmentSlot.MAINHAND, Vec3.atCenterOf(pos), iblockdata, bot.level(), bot.getMainHandItem(), bot, bot, EquipmentSlot.MAINHAND, Vec3.atCenterOf(pos), iblockdata,
item -> bot.onEquippedItemBroken(item, EquipmentSlot.MAINHAND) item -> bot.onEquippedItemBroken(item, EquipmentSlot.MAINHAND)
); );
iblockdata.attack(bot.level(), pos, bot); iblockdata.attack(bot.level(), pos, bot);
float f = iblockdata.getDestroyProgress(bot, bot.level(), pos); float f = iblockdata.getDestroyProgress(bot, bot.level(), pos);
@@ -46,8 +46,8 @@ public class ServerLookAction extends ServerBotAction<ServerLookAction> {
public ServerLookAction() { public ServerLookAction() {
super("look", CommandArgument.of(CommandArgumentType.STRING, CommandArgumentType.DOUBLE, CommandArgumentType.DOUBLE), ServerLookAction::new); super("look", CommandArgument.of(CommandArgumentType.STRING, CommandArgumentType.DOUBLE, CommandArgumentType.DOUBLE), ServerLookAction::new);
this.setSuggestion(0, (sender, arg) -> sender instanceof Player player ? this.setSuggestion(0, (sender, arg) -> sender instanceof Player player ?
Pair.of(Stream.concat(Arrays.stream(MinecraftServer.getServer().getPlayerNames()), Stream.of(DF.format(player.getX()))).toList(), "<Player>|<X>") : Pair.of(Stream.concat(Arrays.stream(MinecraftServer.getServer().getPlayerNames()), Stream.of(DF.format(player.getX()))).toList(), "<Player>|<X>") :
Pair.of(Stream.concat(Arrays.stream(MinecraftServer.getServer().getPlayerNames()), Stream.of("0")).toList(), "<Player>|<X>") Pair.of(Stream.concat(Arrays.stream(MinecraftServer.getServer().getPlayerNames()), Stream.of("0")).toList(), "<Player>|<X>")
); );
this.setSuggestion(1, (sender, arg) -> sender instanceof Player player ? Pair.of(List.of(DF.format(player.getY())), "<Y>") : Pair.of(List.of("0"), "<Y>")); this.setSuggestion(1, (sender, arg) -> sender instanceof Player player ? Pair.of(List.of(DF.format(player.getY())), "<Y>") : Pair.of(List.of("0"), "<Y>"));
this.setSuggestion(2, (sender, arg) -> sender instanceof Player player ? Pair.of(List.of(DF.format(player.getZ())), "<Z>") : Pair.of(List.of("0"), "<Z>")); this.setSuggestion(2, (sender, arg) -> sender instanceof Player player ? Pair.of(List.of(DF.format(player.getZ())), "<Z>") : Pair.of(List.of("0"), "<Z>"));
@@ -72,9 +72,9 @@ public class ServerLookAction extends ServerBotAction<ServerLookAction> {
public void load(@NotNull CompoundTag nbt) { public void load(@NotNull CompoundTag nbt) {
super.load(nbt); super.load(nbt);
this.setPos(new Vector( this.setPos(new Vector(
nbt.getDouble("x").orElse(0.0), nbt.getDouble("x").orElse(0.0),
nbt.getDouble("y").orElse(0.0), nbt.getDouble("y").orElse(0.0),
nbt.getDouble("z").orElse(0.0) nbt.getDouble("z").orElse(0.0)
)); ));
} }
@@ -39,11 +39,11 @@ public class ServerMountAction extends ServerBotAction<ServerMountAction> {
public boolean doTick(@NotNull ServerBot bot) { public boolean doTick(@NotNull ServerBot bot) {
Location center = bot.getBukkitEntity().getLocation(); Location center = bot.getBukkitEntity().getLocation();
List<Vehicle> vehicles = center.getNearbyEntitiesByType( List<Vehicle> vehicles = center.getNearbyEntitiesByType(
Vehicle.class, Vehicle.class,
3, 3,
vehicle -> manhattanDistance(bot, ((CraftEntity) vehicle).getHandle()) <= 2 vehicle -> manhattanDistance(bot, ((CraftEntity) vehicle).getHandle()) <= 2
).stream().sorted(Comparator.comparingDouble( ).stream().sorted(Comparator.comparingDouble(
(vehicle) -> center.distanceSquared(vehicle.getLocation()) (vehicle) -> center.distanceSquared(vehicle.getLocation())
)).toList(); )).toList();
for (Vehicle vehicle : vehicles) { for (Vehicle vehicle : vehicles) {
@@ -62,7 +62,7 @@ public class ServerMountAction extends ServerBotAction<ServerMountAction> {
private double manhattanDistance(@NotNull Entity entity1, @NotNull Entity entity2) { private double manhattanDistance(@NotNull Entity entity1, @NotNull Entity entity2) {
return Math.abs(entity1.getX() - entity2.getX()) + return Math.abs(entity1.getX() - entity2.getX()) +
Math.abs(entity1.getY() - entity2.getY()) + Math.abs(entity1.getY() - entity2.getY()) +
Math.abs(entity1.getZ() - entity2.getZ()); Math.abs(entity1.getZ() - entity2.getZ());
} }
} }
@@ -34,8 +34,8 @@ import java.util.List;
public class ServerMoveAction extends ServerStateBotAction<ServerMoveAction> { public class ServerMoveAction extends ServerStateBotAction<ServerMoveAction> {
private static final Pair<List<String>, String> suggestions = Pair.of( private static final Pair<List<String>, String> suggestions = Pair.of(
Arrays.stream(MoveDirection.values()).map((it) -> it.name).toList(), Arrays.stream(MoveDirection.values()).map((it) -> it.name).toList(),
"<Direction>" "<Direction>"
); );
private MoveDirection direction = MoveDirection.FORWARD; private MoveDirection direction = MoveDirection.FORWARD;
@@ -124,7 +124,7 @@ public abstract class ServerUseBotAction<T extends ServerUseBotAction<T>> extend
super.load(nbt); super.load(nbt);
this.useTickTimeout = nbt.getInt("useTick").orElseThrow(); this.useTickTimeout = nbt.getInt("useTick").orElseThrow();
this.alreadyUsedTick = nbt.getInt("alreadyUsedTick").orElseGet( this.alreadyUsedTick = nbt.getInt("alreadyUsedTick").orElseGet(
() -> this.useTickTimeout - nbt.getInt("tickToRelease").orElseThrow() () -> this.useTickTimeout - nbt.getInt("tickToRelease").orElseThrow()
); );
} }
@@ -17,10 +17,11 @@
package org.leavesmc.leaves.bot.agent.configs; package org.leavesmc.leaves.bot.agent.configs;
import fun.bm.lophine.config.modules.experiment.WaypointConfig;
import fun.bm.lophine.config.modules.function.FakeplayerConfig;
import net.minecraft.nbt.CompoundTag; import net.minecraft.nbt.CompoundTag;
import net.minecraft.server.waypoints.ServerWaypointManager; import net.minecraft.server.waypoints.ServerWaypointManager;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import fun.bm.lophine.config.modules.function.FakeplayerConfig;
import org.leavesmc.leaves.bot.agent.AbstractBotConfig; import org.leavesmc.leaves.bot.agent.AbstractBotConfig;
import org.leavesmc.leaves.command.CommandArgument; import org.leavesmc.leaves.command.CommandArgument;
import org.leavesmc.leaves.command.CommandArgumentType; import org.leavesmc.leaves.command.CommandArgumentType;
@@ -35,7 +36,7 @@ public class LocatorBarConfig extends AbstractBotConfig<Boolean> {
public LocatorBarConfig() { public LocatorBarConfig() {
super(NAME, CommandArgument.of(CommandArgumentType.BOOLEAN).setSuggestion(0, List.of("true", "false"))); super(NAME, CommandArgument.of(CommandArgumentType.BOOLEAN).setSuggestion(0, List.of("true", "false")));
this.value = FakeplayerConfig.enableLocatorBar; this.value = FakeplayerConfig.enableLocatorBar && WaypointConfig.forceEnableWaypointUnsafe;
} }
@Override @Override
@@ -50,8 +50,8 @@ public class SpawnPhantomConfig extends AbstractBotConfig<Boolean> {
@Override @Override
public List<String> getMessage() { public List<String> getMessage() {
return List.of( return List.of(
bot.getScoreboardName() + "'s spawn_phantom: " + this.getValue(), bot.getScoreboardName() + "'s spawn_phantom: " + this.getValue(),
bot.getScoreboardName() + "'s not_sleeping_ticks: " + bot.notSleepTicks bot.getScoreboardName() + "'s not_sleeping_ticks: " + bot.notSleepTicks
); );
} }
@@ -59,7 +59,8 @@ public class CraftBot extends CraftPlayer implements Bot {
public <T extends BotAction<T>> void addAction(@NotNull T action) { public <T extends BotAction<T>> void addAction(@NotNull T action) {
switch (action) { switch (action) {
case CraftBotAction act -> this.getHandle().addBotAction(act.getHandle(), null); case CraftBotAction act -> this.getHandle().addBotAction(act.getHandle(), null);
default -> throw new IllegalArgumentException("Action " + action.getClass().getName() + " is not a valid BotAction type!"); default ->
throw new IllegalArgumentException("Action " + action.getClass().getName() + " is not a valid BotAction type!");
} }
} }
@@ -1,7 +1,3 @@
package org.leavesmc.leaves.entity.bot;
import com.google.common.collect.Lists;
import net.minecraft.server.MinecraftServer;
/* /*
* This file is part of Leaves (https://github.com/LeavesMC/Leaves) * This file is part of Leaves (https://github.com/LeavesMC/Leaves)
* *
@@ -19,6 +15,10 @@ import net.minecraft.server.MinecraftServer;
* along with Leaves. If not, see <https://www.gnu.org/licenses/>. * along with Leaves. If not, see <https://www.gnu.org/licenses/>.
*/ */
package org.leavesmc.leaves.entity.bot;
import com.google.common.collect.Lists;
import net.minecraft.server.MinecraftServer;
import org.bukkit.Location; import org.bukkit.Location;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
@@ -29,6 +29,7 @@ import net.minecraft.resources.ResourceLocation;
import net.minecraft.server.level.ServerPlayer; import net.minecraft.server.level.ServerPlayer;
import net.minecraft.util.RandomSource; import net.minecraft.util.RandomSource;
import net.minecraft.world.entity.Entity; import net.minecraft.world.entity.Entity;
import net.minecraft.world.entity.LivingEntity;
import net.minecraft.world.level.block.entity.BlockEntity; import net.minecraft.world.level.block.entity.BlockEntity;
import org.leavesmc.leaves.protocol.core.LeavesCustomPayload; import org.leavesmc.leaves.protocol.core.LeavesCustomPayload;
import org.leavesmc.leaves.protocol.core.LeavesProtocol; import org.leavesmc.leaves.protocol.core.LeavesProtocol;
@@ -101,37 +102,27 @@ public class ServuxEntityDataProtocol implements LeavesProtocol {
} }
public static void onBlockEntityRequest(ServerPlayer player, BlockPos pos) { public static void onBlockEntityRequest(ServerPlayer player, BlockPos pos) {
io.papermc.paper.threadedregions.RegionizedServer.getInstance().taskQueue.queueTickTaskQueue( player.getBukkitEntity().taskScheduler.schedule((LivingEntity nmsEntity) -> {
player.level(), BlockEntity be = nmsEntity.level().getBlockEntity(pos);
ca.spottedleaf.moonrise.common.util.CoordinateUtils.getChunkX(player.position()), CompoundTag nbt = be != null ? be.saveWithFullMetadata(nmsEntity.registryAccess()) : new CompoundTag();
ca.spottedleaf.moonrise.common.util.CoordinateUtils.getChunkZ(player.position()),
() -> {
BlockEntity be = player.level().getBlockEntity(pos);
CompoundTag nbt = be != null ? be.saveWithFullMetadata(player.registryAccess()) : new CompoundTag();
EntityDataPayload payload = new EntityDataPayload(EntityDataPayloadType.PACKET_S2C_BLOCK_NBT_RESPONSE_SIMPLE); EntityDataPayload payload = new EntityDataPayload(EntityDataPayloadType.PACKET_S2C_BLOCK_NBT_RESPONSE_SIMPLE);
payload.pos = pos.immutable(); payload.pos = pos.immutable();
payload.nbt.merge(nbt); payload.nbt.merge(nbt);
sendPacket(player, payload); sendPacket((ServerPlayer) nmsEntity, payload);
} }, null, 1L);
);
} }
public static void onEntityRequest(ServerPlayer player, int entityId) { public static void onEntityRequest(ServerPlayer player, int entityId) {
io.papermc.paper.threadedregions.RegionizedServer.getInstance().taskQueue.queueTickTaskQueue( player.getBukkitEntity().taskScheduler.schedule((LivingEntity nmsEntity) -> {
player.level(), Entity entity = nmsEntity.level().getEntity(entityId);
ca.spottedleaf.moonrise.common.util.CoordinateUtils.getChunkX(player.position()), CompoundTag nbt = TagUtil.saveEntityWithoutId(entity);
ca.spottedleaf.moonrise.common.util.CoordinateUtils.getChunkZ(player.position()),
() -> {
Entity entity = player.level().getEntity(entityId);
CompoundTag nbt = TagUtil.saveEntityWithoutId(entity);
EntityDataPayload payload = new EntityDataPayload(EntityDataPayloadType.PACKET_S2C_ENTITY_NBT_RESPONSE_SIMPLE); EntityDataPayload payload = new EntityDataPayload(EntityDataPayloadType.PACKET_S2C_ENTITY_NBT_RESPONSE_SIMPLE);
payload.entityId = entityId; payload.entityId = entityId;
payload.nbt.merge(nbt); payload.nbt.merge(nbt);
sendPacket(player, payload); sendPacket((ServerPlayer) nmsEntity, payload);
} }, null, 1L);
);
} }
public static void sendPacket(ServerPlayer player, EntityDataPayload payload) { public static void sendPacket(ServerPlayer player, EntityDataPayload payload) {
@@ -29,6 +29,7 @@ import net.minecraft.server.MinecraftServer;
import net.minecraft.server.ServerTickRateManager; import net.minecraft.server.ServerTickRateManager;
import net.minecraft.server.level.ServerPlayer; import net.minecraft.server.level.ServerPlayer;
import net.minecraft.util.StringRepresentable; import net.minecraft.util.StringRepresentable;
import net.minecraft.world.entity.LivingEntity;
import net.minecraft.world.entity.MobCategory; import net.minecraft.world.entity.MobCategory;
import net.minecraft.world.level.NaturalSpawner; import net.minecraft.world.level.NaturalSpawner;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
@@ -114,28 +115,23 @@ public abstract class DataLogger<T extends Tag> {
} }
private TickData build(MinecraftServer server, ServuxHudDataProtocol protocol, ServerPlayer player) { private TickData build(MinecraftServer server, ServuxHudDataProtocol protocol, ServerPlayer player) {
io.papermc.paper.threadedregions.RegionizedServer.getInstance().taskQueue.queueTickTaskQueue( player.getBukkitEntity().taskScheduler.schedule((LivingEntity nmsEntity) -> {
player.level(), ServerTickRateManager tickManager = server.tickRateManager();
ca.spottedleaf.moonrise.common.util.CoordinateUtils.getChunkX(player.position()), boolean frozen = tickManager.isFrozen();
ca.spottedleaf.moonrise.common.util.CoordinateUtils.getChunkZ(player.position()), boolean sprinting = tickManager.isSprinting();
() -> { io.papermc.paper.threadedregions.TickData.TickReportData tickData = TickRegionScheduler.getCurrentRegion().getData().getRegionSchedulingHandle().getTickReport5s(System.nanoTime());
ServerTickRateManager tickManager = server.tickRateManager(); final double tps = tickData.tpsData().segmentAll().average();
boolean frozen = tickManager.isFrozen(); final double mspt = tickData.timePerTickData().segmentAll().average() / 1.0E6;
boolean sprinting = tickManager.isSprinting();
io.papermc.paper.threadedregions.TickData.TickReportData tickData = TickRegionScheduler.getCurrentRegion().getData().getRegionSchedulingHandle().getTickReport5s(System.nanoTime());
final double tps = tickData.tpsData().segmentAll().average();
final double mspt = tickData.timePerTickData().segmentAll().average() / 1.0E6;
TickData tk = new TickData( TickData tk = new TickData(
mspt, tps, mspt, tps,
tickManager.getRemainingSprintTicks(), tickManager.getRemainingSprintTicks(),
frozen, sprinting, frozen, sprinting,
tickManager.isSteppingForward() tickManager.isSteppingForward()
); );
Tag ret = TickData.CODEC.encodeStart(server.registryAccess().createSerializationContext(NbtOps.INSTANCE), tk).getOrThrow(); Tag ret = TickData.CODEC.encodeStart(server.registryAccess().createSerializationContext(NbtOps.INSTANCE), tk).getOrThrow();
protocol.applyData(Type.TPS, player, ret); protocol.applyData(Type.TPS, (ServerPlayer) nmsEntity, ret);
} }, null, 1L);
);
return null; return null;
} }
@@ -152,30 +148,26 @@ public abstract class DataLogger<T extends Tag> {
@Override @Override
public CompoundTag getResult(MinecraftServer server, ServuxHudDataProtocol protocol, ServerPlayer player) { public CompoundTag getResult(MinecraftServer server, ServuxHudDataProtocol protocol, ServerPlayer player) {
CompoundTag nbt = new CompoundTag(); CompoundTag nbt = new CompoundTag();
io.papermc.paper.threadedregions.RegionizedServer.getInstance().taskQueue.queueTickTaskQueue( player.getBukkitEntity().taskScheduler.schedule((LivingEntity nmsEntity) -> {
player.level(), final RegionizedWorldData data = nmsEntity.level().getCurrentWorldData();
ca.spottedleaf.moonrise.common.util.CoordinateUtils.getChunkX(player.position()), if (data == null) return;
ca.spottedleaf.moonrise.common.util.CoordinateUtils.getChunkZ(player.position()),
() -> {
final RegionizedWorldData data = player.level().getCurrentWorldData();
if (data == null) return;
final NaturalSpawner.SpawnState info = data.lastSpawnState; final NaturalSpawner.SpawnState info = data.lastSpawnState;
if (info == null) return; if (info == null) return;
int chunks = info.getSpawnableChunkCount(); int chunks = info.getSpawnableChunkCount();
Object2IntMap<MobCategory> counts = info.getMobCategoryCounts(); Object2IntMap<MobCategory> counts = info.getMobCategoryCounts();
MobCapData mobCapData = new MobCapData(new ArrayList<>(), player.level().getGameTime()); MobCapData mobCapData = new MobCapData(new ArrayList<>(), nmsEntity.level().getGameTime());
for (MobCategory category : MobCategory.values()) { for (MobCategory category : MobCategory.values()) {
mobCapData.data().add(new MobCapData.Cap(counts.getOrDefault(category, 0), NaturalSpawner.globalLimitForCategory(player.level(), category, chunks))); mobCapData.data().add(new MobCapData.Cap(counts.getOrDefault(category, 0), NaturalSpawner.globalLimitForCategory(player.level(), category, chunks)));
} }
try { try {
nbt.put(player.level().dimension().location().toString(), MobCapData.CODEC.encodeStart(player.level().registryAccess().createSerializationContext(NbtOps.INSTANCE), mobCapData).getPartialOrThrow()); nbt.put(nmsEntity.level().dimension().location().toString(), MobCapData.CODEC.encodeStart(player.level().registryAccess().createSerializationContext(NbtOps.INSTANCE), mobCapData).getPartialOrThrow());
protocol.applyData(Type.MOB_CAPS, player, nbt); protocol.applyData(Type.MOB_CAPS, (ServerPlayer) nmsEntity, nbt);
} catch (Exception ignored) { } catch (Exception ignored) {
} }
}); }, null, 1L);
return null; return null;
} }
} }