From 4abf6489bbfc9d33e15325143f7c1ef7ca63741f Mon Sep 17 00:00:00 2001
From: someaddons <38401808+someaddons@users.noreply.github.com>
Date: Sat, 2 Nov 2024 13:20:58 +0100
Subject: [PATCH] Pathing debug additions (#10357)
* Reworked debug tracking, now also allows tracking path jobs by type and can add players to a specific pathresult for direct tracking
---
.../formatter/intellij/Minecolonies.xml | 6 +-
.../api/entity/pathfinding/IPathJob.java | 11 +-
.../core/commands/EntryPoint.java | 133 +++++++++---------
.../citizencommands/CommandTrackType.java | 61 ++++++++
.../commands/colonycommands/CommandRaid.java | 49 ++++---
.../agriculture/EntityAIWorkFisherman.java | 16 +--
.../entity/pathfinding/PathfindingUtils.java | 33 ++---
.../MinecoloniesAdvancedPathNavigate.java | 5 +-
.../pathfinding/pathjobs/AbstractPathJob.java | 92 +++++++-----
.../pathjobs/PathJobFindWater.java | 5 +-
.../pathjobs/PathJobRaiderPathing.java | 2 +-
.../pathfinding/pathresults/PathResult.java | 111 ++++++++++++++-
12 files changed, 363 insertions(+), 161 deletions(-)
create mode 100644 src/main/java/com/minecolonies/core/commands/citizencommands/CommandTrackType.java
diff --git a/documentation/formatter/intellij/Minecolonies.xml b/documentation/formatter/intellij/Minecolonies.xml
index 7a4d1b49b2a..4ad74daf113 100644
--- a/documentation/formatter/intellij/Minecolonies.xml
+++ b/documentation/formatter/intellij/Minecolonies.xml
@@ -15,6 +15,8 @@
+
+
@@ -66,8 +68,8 @@
-
-
+
+
diff --git a/src/main/java/com/minecolonies/api/entity/pathfinding/IPathJob.java b/src/main/java/com/minecolonies/api/entity/pathfinding/IPathJob.java
index 1561ea029d5..d4d79b7ae07 100644
--- a/src/main/java/com/minecolonies/api/entity/pathfinding/IPathJob.java
+++ b/src/main/java/com/minecolonies/api/entity/pathfinding/IPathJob.java
@@ -1,7 +1,10 @@
package com.minecolonies.api.entity.pathfinding;
-import com.minecolonies.core.entity.pathfinding.pathresults.PathResult;
import com.minecolonies.core.entity.pathfinding.PathingOptions;
+import com.minecolonies.core.entity.pathfinding.pathresults.PathResult;
+import net.minecraft.core.BlockPos;
+import net.minecraft.world.entity.Mob;
+import net.minecraft.world.level.Level;
import net.minecraft.world.level.pathfinder.Path;
import java.util.concurrent.Callable;
@@ -22,4 +25,10 @@ public interface IPathJob extends Callable
* @return
*/
public PathingOptions getPathingOptions();
+
+ Mob getEntity();
+
+ Level getActualWorld();
+
+ BlockPos getStart();
}
diff --git a/src/main/java/com/minecolonies/core/commands/EntryPoint.java b/src/main/java/com/minecolonies/core/commands/EntryPoint.java
index 5f2f11028b9..e9ed9073d45 100755
--- a/src/main/java/com/minecolonies/core/commands/EntryPoint.java
+++ b/src/main/java/com/minecolonies/core/commands/EntryPoint.java
@@ -27,92 +27,93 @@ public static void register(final CommandDispatcher dispatch
* Kill commands subtree
*/
final CommandTree killCommands = new CommandTree("kill")
- .addNode(new CommandKillAnimal().build())
- .addNode(new CommandKillChicken().build())
- .addNode(new CommandKillCow().build())
- .addNode(new CommandKillMonster().build())
- .addNode(new CommandKillPig().build())
- .addNode(new CommandKillRaider().build())
- .addNode(new CommandKillSheep().build());
+ .addNode(new CommandKillAnimal().build())
+ .addNode(new CommandKillChicken().build())
+ .addNode(new CommandKillCow().build())
+ .addNode(new CommandKillMonster().build())
+ .addNode(new CommandKillPig().build())
+ .addNode(new CommandKillRaider().build())
+ .addNode(new CommandKillSheep().build());
/*
* Colony commands subtree
*/
final CommandTree colonyCommands = new CommandTree("colony")
- .addNode(new CommandAddOfficer().build())
- .addNode(new CommandSetRank().build())
- .addNode(new CommandChangeOwner().build())
- .addNode(new CommandClaimChunks().build())
- .addNode(new CommandShowClaim().build())
- .addNode(new CommandTeleport().build())
- .addNode(new CommandDeleteColony().build())
- .addNode(new CommandCanRaiderSpawn().build())
- .addNode(new CommandRaid().build())
- .addNode(new CommandHomeTeleport().build())
- .addNode(new CommandListColonies().build())
- .addNode(new CommandSetDeletable().build())
- .addNode(new CommandReclaimChunks().build())
- .addNode(new CommandLoadBackup().build())
- .addNode(new CommandLoadAllBackups().build())
- .addNode(new CommandColonyInfo().build())
- .addNode(new CommandColonyPrintStats().build())
- .addNode(new CommandColonyRaidsInfo().build())
- .addNode(new CommandColonyChunks().build())
- .addNode(new CommandRSReset().build())
- .addNode(new CommandRSResetAll().build())
- .addNode(new CommandSetAbandoned().build())
- .addNode(new CommandExportColony().build());
+ .addNode(new CommandAddOfficer().build())
+ .addNode(new CommandSetRank().build())
+ .addNode(new CommandChangeOwner().build())
+ .addNode(new CommandClaimChunks().build())
+ .addNode(new CommandShowClaim().build())
+ .addNode(new CommandTeleport().build())
+ .addNode(new CommandDeleteColony().build())
+ .addNode(new CommandCanRaiderSpawn().build())
+ .addNode(new CommandRaid().build())
+ .addNode(new CommandHomeTeleport().build())
+ .addNode(new CommandListColonies().build())
+ .addNode(new CommandSetDeletable().build())
+ .addNode(new CommandReclaimChunks().build())
+ .addNode(new CommandLoadBackup().build())
+ .addNode(new CommandLoadAllBackups().build())
+ .addNode(new CommandColonyInfo().build())
+ .addNode(new CommandColonyPrintStats().build())
+ .addNode(new CommandColonyRaidsInfo().build())
+ .addNode(new CommandColonyChunks().build())
+ .addNode(new CommandRSReset().build())
+ .addNode(new CommandRSResetAll().build())
+ .addNode(new CommandSetAbandoned().build())
+ .addNode(new CommandExportColony().build());
/*
* Citizen commands subtree
*/
final CommandTree citizenCommands = new CommandTree("citizens")
- .addNode(new CommandCitizenInfo().build())
- .addNode(new CommandCitizenKill().build())
- .addNode(new CommandCitizenList().build())
- .addNode(new CommandCitizenReload().build())
- .addNode(new CommandCitizenSpawnNew().build())
- .addNode(new CommandCitizenTeleport().build())
- .addNode(new CommandCitizenTriggerWalkTo().build())
- .addNode(new CommandCitizenTrack().build());
+ .addNode(new CommandCitizenInfo().build())
+ .addNode(new CommandCitizenKill().build())
+ .addNode(new CommandCitizenList().build())
+ .addNode(new CommandCitizenReload().build())
+ .addNode(new CommandCitizenSpawnNew().build())
+ .addNode(new CommandCitizenTeleport().build())
+ .addNode(new CommandCitizenTriggerWalkTo().build())
+ .addNode(new CommandCitizenTrack().build())
+ .addNode(new CommandTrackType().build());
/*
* Root minecolonies command tree, all subtrees are added here.
*/
final CommandTree minecoloniesRoot = new CommandTree(Constants.MOD_ID)
- .addNode(killCommands)
- .addNode(colonyCommands)
- .addNode(new CommandHomeTeleport().build())
- .addNode(citizenCommands)
- .addNode(new CommandWhereAmI().build())
- .addNode(new CommandWhoAmI().build())
- .addNode(new CommandRTP().build())
- .addNode(new CommandUnloadForcedChunks().build())
- .addNode(new CommandRaidAll().build())
- .addNode(new CommandBackup().build())
- .addNode(new CommandResetPlayerSupplies().build())
- .addNode(new CommandHelp().build())
- .addNode(new ScanCommand().build())
- .addNode(new CommandPruneWorld().build());
+ .addNode(killCommands)
+ .addNode(colonyCommands)
+ .addNode(new CommandHomeTeleport().build())
+ .addNode(citizenCommands)
+ .addNode(new CommandWhereAmI().build())
+ .addNode(new CommandWhoAmI().build())
+ .addNode(new CommandRTP().build())
+ .addNode(new CommandUnloadForcedChunks().build())
+ .addNode(new CommandRaidAll().build())
+ .addNode(new CommandBackup().build())
+ .addNode(new CommandResetPlayerSupplies().build())
+ .addNode(new CommandHelp().build())
+ .addNode(ScanCommand.build())
+ .addNode(new CommandPruneWorld().build());
/*
* Root minecolonies alias command tree, all subtrees are added here.
*/
final CommandTree minecoloniesRootAlias = new CommandTree("mc")
- .addNode(new CommandEntityTrack().build())
- .addNode(killCommands)
- .addNode(colonyCommands)
- .addNode(new CommandHomeTeleport().build())
- .addNode(citizenCommands)
- .addNode(new CommandWhereAmI().build())
- .addNode(new CommandWhoAmI().build())
- .addNode(new CommandRTP().build())
- .addNode(new CommandUnloadForcedChunks().build())
- .addNode(new CommandRaidAll().build())
- .addNode(new CommandBackup().build())
- .addNode(new CommandResetPlayerSupplies().build())
- .addNode(new CommandHelp().build())
- .addNode(new CommandPruneWorld().build());
+ .addNode(new CommandEntityTrack().build())
+ .addNode(killCommands)
+ .addNode(colonyCommands)
+ .addNode(new CommandHomeTeleport().build())
+ .addNode(citizenCommands)
+ .addNode(new CommandWhereAmI().build())
+ .addNode(new CommandWhoAmI().build())
+ .addNode(new CommandRTP().build())
+ .addNode(new CommandUnloadForcedChunks().build())
+ .addNode(new CommandRaidAll().build())
+ .addNode(new CommandBackup().build())
+ .addNode(new CommandResetPlayerSupplies().build())
+ .addNode(new CommandHelp().build())
+ .addNode(new CommandPruneWorld().build());
// Adds all command trees to the dispatcher to register the commands.
dispatcher.register(minecoloniesRoot.build());
diff --git a/src/main/java/com/minecolonies/core/commands/citizencommands/CommandTrackType.java b/src/main/java/com/minecolonies/core/commands/citizencommands/CommandTrackType.java
new file mode 100644
index 00000000000..d9df47de08b
--- /dev/null
+++ b/src/main/java/com/minecolonies/core/commands/citizencommands/CommandTrackType.java
@@ -0,0 +1,61 @@
+package com.minecolonies.core.commands.citizencommands;
+
+import com.minecolonies.core.commands.commandTypes.IMCCommand;
+import com.minecolonies.core.commands.commandTypes.IMCOPCommand;
+import com.minecolonies.core.entity.pathfinding.PathfindingUtils;
+import com.mojang.brigadier.arguments.StringArgumentType;
+import com.mojang.brigadier.builder.LiteralArgumentBuilder;
+import com.mojang.brigadier.context.CommandContext;
+import net.minecraft.commands.CommandSourceStack;
+import net.minecraft.network.chat.Component;
+
+/**
+ * Displays information about a chosen citizen in a chosen colony.
+ */
+public class CommandTrackType implements IMCOPCommand
+{
+ /**
+ * What happens when the command is executed after preConditions are successful.
+ *
+ * @param context the context of the command execution
+ */
+ @Override
+ public int onExecute(final CommandContext context)
+ {
+ if (!context.getSource().isPlayer())
+ {
+ return 1;
+ }
+
+ final String className = StringArgumentType.getString(context, "pathjobname");
+ if (className.equals("clear"))
+ {
+ PathfindingUtils.trackByType.entrySet().removeIf(entry -> entry.getValue().equals(context.getSource().getPlayer().getUUID()));
+ context.getSource().sendSystemMessage(Component.literal("Removed tracking for player"));
+ return 1;
+ }
+
+ PathfindingUtils.trackByType.put(className, context.getSource().getPlayer().getUUID());
+ context.getSource().sendSystemMessage(Component.literal("Tracking enabled for pathjobs containing: " + className));
+ return 1;
+ }
+
+ /**
+ * Name string of the command.
+ */
+ @Override
+ public String getName()
+ {
+ return "trackPathType";
+ }
+
+ @Override
+ public LiteralArgumentBuilder build()
+ {
+ return IMCCommand.newLiteral(getName())
+ .then(IMCCommand.newArgument("pathjobname", StringArgumentType.word()).suggests((context, builder) -> {
+ builder.suggest("clear");
+ return builder.buildFuture();
+ }).executes(this::checkPreConditionAndExecute));
+ }
+}
diff --git a/src/main/java/com/minecolonies/core/commands/colonycommands/CommandRaid.java b/src/main/java/com/minecolonies/core/commands/colonycommands/CommandRaid.java
index 112cd6c391a..622ed821c12 100644
--- a/src/main/java/com/minecolonies/core/commands/colonycommands/CommandRaid.java
+++ b/src/main/java/com/minecolonies/core/commands/colonycommands/CommandRaid.java
@@ -5,6 +5,7 @@
import com.minecolonies.api.colony.IColonyManager;
import com.minecolonies.api.colony.colonyEvents.registry.ColonyEventTypeRegistryEntry;
import com.minecolonies.api.colony.managers.interfaces.IRaiderManager;
+import com.minecolonies.api.util.Log;
import com.minecolonies.api.util.constant.translation.CommandTranslationConstants;
import com.minecolonies.core.colony.events.raid.norsemenevent.NorsemenShipRaidEvent;
import com.minecolonies.core.colony.events.raid.pirateEvent.PirateGroundRaidEvent;
@@ -39,18 +40,28 @@ public int onExecute(final CommandContext context)
public int onSpecificExecute(final CommandContext context)
{
- if(!checkPreCondition(context))
+ try
{
- return 0;
+ if (!checkPreCondition(context))
+ {
+ return 0;
+ }
+ return raidExecute(context, StringArgumentType.getString(context, RAID_TYPE_ARG));
}
- return raidExecute(context, StringArgumentType.getString(context, RAID_TYPE_ARG));
+ catch (Throwable e)
+ {
+ Log.getLogger().warn("Error during running command:", e);
+ }
+
+ return 0;
}
/**
* Actually find the colony and assign the raid event.
- * @param context command context from the user.
- * @param raidType type of raid, or "" if determining naturally.
- * @return zero if failed, one if successful.
+ *
+ * @param context command context from the user.
+ * @param raidType type of raid, or "" if determining naturally.
+ * @return zero if failed, one if successful.
*/
public int raidExecute(final CommandContext context, final String raidType)
{
@@ -64,7 +75,7 @@ public int raidExecute(final CommandContext context, final S
}
final boolean allowShips = BoolArgumentType.getBool(context, SHIP_ARG);
- if(StringArgumentType.getString(context, RAID_TIME_ARG).equals(RAID_NOW))
+ if (StringArgumentType.getString(context, RAID_TIME_ARG).equals(RAID_NOW))
{
final IRaiderManager.RaidSpawnResult result = colony.getRaiderManager().raiderEvent(raidType, true, allowShips);
if (result == IRaiderManager.RaidSpawnResult.SUCCESS)
@@ -74,11 +85,13 @@ public int raidExecute(final CommandContext context, final S
}
context.getSource().sendFailure(Component.translatable(CommandTranslationConstants.COMMAND_RAID_NOW_FAILURE, colony.getName(), result));
}
- else if(StringArgumentType.getString(context, RAID_TIME_ARG).equals(RAID_TONIGHT))
+ else if (StringArgumentType.getString(context, RAID_TIME_ARG).equals(RAID_TONIGHT))
{
if (!colony.getRaiderManager().canRaid())
{
- context.getSource().sendSuccess(() -> Component.translatable(CommandTranslationConstants.COMMAND_RAID_NOW_FAILURE, colony.getName(), IRaiderManager.RaidSpawnResult.CANNOT_RAID), true);
+ context.getSource()
+ .sendSuccess(() -> Component.translatable(CommandTranslationConstants.COMMAND_RAID_NOW_FAILURE, colony.getName(), IRaiderManager.RaidSpawnResult.CANNOT_RAID),
+ true);
return 1;
}
colony.getRaiderManager().setRaidNextNight(true, raidType, allowShips);
@@ -100,10 +113,10 @@ public String getName()
public LiteralArgumentBuilder build()
{
final List raidTypes = new ArrayList<>();
- for(final ColonyEventTypeRegistryEntry type : IMinecoloniesAPI.getInstance().getColonyEventRegistry().getValues())
+ for (final ColonyEventTypeRegistryEntry type : IMinecoloniesAPI.getInstance().getColonyEventRegistry().getValues())
{
- if(!type.getRegistryName().getPath().equals(PirateGroundRaidEvent.PIRATE_GROUND_RAID_EVENT_TYPE_ID.getPath())
- && !type.getRegistryName().getPath().equals(NorsemenShipRaidEvent.NORSEMEN_RAID_EVENT_TYPE_ID.getPath()))
+ if (!type.getRegistryName().getPath().equals(PirateGroundRaidEvent.PIRATE_GROUND_RAID_EVENT_TYPE_ID.getPath())
+ && !type.getRegistryName().getPath().equals(NorsemenShipRaidEvent.NORSEMEN_RAID_EVENT_TYPE_ID.getPath()))
{
raidTypes.add(type.getRegistryName().getPath());
}
@@ -116,11 +129,11 @@ public LiteralArgumentBuilder build()
return IMCCommand.newLiteral(getName())
.then(IMCCommand.newArgument(RAID_TIME_ARG, StringArgumentType.string())
.suggests((ctx, builder) -> SharedSuggestionProvider.suggest(opt, builder))
- .then(IMCCommand.newArgument(COLONYID_ARG, IntegerArgumentType.integer(1))
- .then(IMCCommand.newArgument(RAID_TYPE_ARG, StringArgumentType.string())
- .suggests((ctx, builder) -> SharedSuggestionProvider.suggest(raidTypes, builder))
- .then(IMCCommand.newArgument(SHIP_ARG, BoolArgumentType.bool())
- .executes(this::onSpecificExecute)))
- .executes(this::checkPreConditionAndExecute)));
+ .then(IMCCommand.newArgument(COLONYID_ARG, IntegerArgumentType.integer(1))
+ .then(IMCCommand.newArgument(RAID_TYPE_ARG, StringArgumentType.string())
+ .suggests((ctx, builder) -> SharedSuggestionProvider.suggest(raidTypes, builder))
+ .then(IMCCommand.newArgument(SHIP_ARG, BoolArgumentType.bool())
+ .executes(this::onSpecificExecute)))
+ .executes(this::checkPreConditionAndExecute)));
}
}
diff --git a/src/main/java/com/minecolonies/core/entity/ai/workers/production/agriculture/EntityAIWorkFisherman.java b/src/main/java/com/minecolonies/core/entity/ai/workers/production/agriculture/EntityAIWorkFisherman.java
index 99244c69ca4..bb699cd24a5 100755
--- a/src/main/java/com/minecolonies/core/entity/ai/workers/production/agriculture/EntityAIWorkFisherman.java
+++ b/src/main/java/com/minecolonies/core/entity/ai/workers/production/agriculture/EntityAIWorkFisherman.java
@@ -7,19 +7,19 @@
import com.minecolonies.api.entity.ai.statemachine.states.IAIState;
import com.minecolonies.api.entity.citizen.AbstractEntityCitizen;
import com.minecolonies.api.equipment.ModEquipmentTypes;
-import com.minecolonies.core.entity.pathfinding.Pathfinding;
-import com.minecolonies.core.entity.pathfinding.PathfindingUtils;
-import com.minecolonies.core.entity.pathfinding.pathjobs.PathJobFindWater;
-import com.minecolonies.core.entity.pathfinding.pathresults.WaterPathResult;
import com.minecolonies.api.loot.ModLootTables;
import com.minecolonies.api.sounds.EventType;
import com.minecolonies.api.util.*;
import com.minecolonies.core.colony.buildings.workerbuildings.BuildingFisherman;
import com.minecolonies.core.colony.interactionhandling.StandardInteraction;
import com.minecolonies.core.colony.jobs.JobFisherman;
-import com.minecolonies.core.entity.other.NewBobberEntity;
import com.minecolonies.core.entity.ai.workers.AbstractEntityAISkill;
import com.minecolonies.core.entity.citizen.EntityCitizen;
+import com.minecolonies.core.entity.other.NewBobberEntity;
+import com.minecolonies.core.entity.pathfinding.Pathfinding;
+import com.minecolonies.core.entity.pathfinding.PathfindingUtils;
+import com.minecolonies.core.entity.pathfinding.pathjobs.PathJobFindWater;
+import com.minecolonies.core.entity.pathfinding.pathresults.WaterPathResult;
import com.minecolonies.core.util.WorkerUtil;
import net.minecraft.core.BlockPos;
import net.minecraft.network.chat.Component;
@@ -46,8 +46,8 @@
import static com.minecolonies.api.entity.ai.statemachine.states.AIWorkerState.*;
import static com.minecolonies.api.util.constant.Constants.TICKS_SECOND;
-import static com.minecolonies.api.util.constant.StatisticsConstants.FISH_CAUGHT;
import static com.minecolonies.api.util.constant.EquipmentLevelConstants.TOOL_LEVEL_WOOD_OR_GOLD;
+import static com.minecolonies.api.util.constant.StatisticsConstants.FISH_CAUGHT;
import static com.minecolonies.api.util.constant.TranslationConstants.WATER_TOO_FAR;
import static com.minecolonies.core.colony.buildings.modules.BuildingModules.STATS_MODULE;
import static com.minecolonies.core.entity.other.NewBobberEntity.XP_PER_CATCH;
@@ -417,10 +417,6 @@ private IAIState findNewWater()
pathResult = searchWater(SEARCH_RANGE * 3, 1.0D, job.getPonds());
return getState();
}
- if (pathResult.isDone())
- {
- pathResult.getJob().syncDebug();
- }
if (pathResult.failedToReachDestination())
{
return setRandomWater();
diff --git a/src/main/java/com/minecolonies/core/entity/pathfinding/PathfindingUtils.java b/src/main/java/com/minecolonies/core/entity/pathfinding/PathfindingUtils.java
index 0c888efd473..6b5424d11ab 100644
--- a/src/main/java/com/minecolonies/core/entity/pathfinding/PathfindingUtils.java
+++ b/src/main/java/com/minecolonies/core/entity/pathfinding/PathfindingUtils.java
@@ -13,7 +13,6 @@
import net.minecraft.tags.BlockTags;
import net.minecraft.util.Mth;
import net.minecraft.world.entity.LivingEntity;
-import net.minecraft.world.entity.Mob;
import net.minecraft.world.level.BlockGetter;
import net.minecraft.world.level.Level;
import net.minecraft.world.level.LevelReader;
@@ -29,9 +28,7 @@
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
-import java.util.HashSet;
-import java.util.Map;
-import java.util.UUID;
+import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
public class PathfindingUtils
@@ -42,33 +39,33 @@ public class PathfindingUtils
private static Object empty = Fluids.EMPTY.defaultFluidState();
/**
- * Which citizens are being tracked by which players.
+ * Which citizens are being tracked by which players. Player to entity uuid
*/
public static final Map trackingMap = new ConcurrentHashMap<>();
+ /**
+ * Map for tracking specific path types, type to player uuid
+ */
+ public static final Map trackByType = new HashMap<>();
+
/**
* Set the set of reached blocks to the client.
*
* @param reached the reached blocks.
* @param mob the tracked mob.
*/
- public static void syncDebugReachedPositions(final HashSet reached, final Mob mob)
+ public static void syncDebugReachedPositions(final HashSet reached, final List players)
{
- if (reached.isEmpty())
+ if (reached.isEmpty() || players.isEmpty())
{
return;
}
- for (final Map.Entry entry : trackingMap.entrySet())
+ final SyncPathReachedMessage message = new SyncPathReachedMessage(reached);
+
+ for (final ServerPlayer player : players)
{
- if (entry.getValue().equals(mob.getUUID()))
- {
- final ServerPlayer player = mob.level.getServer().getPlayerList().getPlayer(entry.getKey());
- if (player != null)
- {
- Network.getNetwork().sendToPlayer(new SyncPathReachedMessage(reached), player);
- }
- }
+ Network.getNetwork().sendToPlayer(message, player);
}
}
@@ -328,8 +325,8 @@ public static boolean isLadder(final BlockState blockState, @Nullable final Path
return true;
}
return blockState.is(BlockTags.CLIMBABLE) && ((options != null && options.canClimbAdvanced()) ||
- blockState.getBlock() instanceof LadderBlock ||
- blockState.is(ModTags.freeClimbBlocks));
+ blockState.getBlock() instanceof LadderBlock ||
+ blockState.is(ModTags.freeClimbBlocks));
}
/**
diff --git a/src/main/java/com/minecolonies/core/entity/pathfinding/navigation/MinecoloniesAdvancedPathNavigate.java b/src/main/java/com/minecolonies/core/entity/pathfinding/navigation/MinecoloniesAdvancedPathNavigate.java
index 197823bfa18..d3da8c642c4 100644
--- a/src/main/java/com/minecolonies/core/entity/pathfinding/navigation/MinecoloniesAdvancedPathNavigate.java
+++ b/src/main/java/com/minecolonies/core/entity/pathfinding/navigation/MinecoloniesAdvancedPathNavigate.java
@@ -662,7 +662,6 @@ private void processCompletedCalculationResult()
return;
}
- pathResult.getJob().syncDebug();
moveTo(pathResult.getPath(), getSpeedFactor());
if (pathResult != null)
{
@@ -1019,7 +1018,7 @@ protected void followThePath()
if (isTracking)
{
- PathfindingUtils.syncDebugReachedPositions(reached, ourEntity);
+ PathfindingUtils.syncDebugReachedPositions(reached, pathResult.getDebugWatchers());
reached.clear();
}
@@ -1063,7 +1062,7 @@ else if (isTracking)
if (isTracking)
{
- PathfindingUtils.syncDebugReachedPositions(reached, ourEntity);
+ PathfindingUtils.syncDebugReachedPositions(reached, pathResult.getDebugWatchers());
reached.clear();
}
}
diff --git a/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/AbstractPathJob.java b/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/AbstractPathJob.java
index c0150cced10..5f131b9b2a0 100644
--- a/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/AbstractPathJob.java
+++ b/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/AbstractPathJob.java
@@ -67,6 +67,11 @@ public abstract class AbstractPathJob implements Callable, IPathJob
@NotNull
protected final LevelReader world;
+ /**
+ * The original world, do not use offthread
+ */
+ private final Level actualWorld;
+
/**
* The entity this job belongs to, can be none
*/
@@ -106,8 +111,8 @@ public abstract class AbstractPathJob implements Callable, IPathJob
/**
* Counts of nodes
*/
- private int totalNodesAdded = 0;
- private int totalNodesVisited = 0;
+ private int totalNodesAdded = 0;
+ protected int totalNodesVisited = 0;
/**
* Additional nodes that get explored when reaching the target, useful when the destination is an area or not in a great spot.
@@ -175,6 +180,7 @@ public AbstractPathJob(final Level world, @NotNull final BlockPos start, int ran
final int maxX = (int) (start.getX() + range * 1.3);
final int maxZ = (int) (start.getZ() + range * 1.3);
this.world = new ChunkCache(world, new BlockPos(minX, 0, minZ), new BlockPos(maxX, 0, maxZ));
+ this.actualWorld = world;
this.maxNodes = Math.min(MAX_NODES, range * range);
nodesToVisit = new PriorityQueue<>(range * 2);
@@ -186,11 +192,6 @@ public AbstractPathJob(final Level world, @NotNull final BlockPos start, int ran
result.setJob(this);
this.entity = entity;
-
- if (entity != null && PathfindingUtils.trackingMap.containsValue(entity.getUUID()))
- {
- initDebug();
- }
}
/**
@@ -202,7 +203,7 @@ public AbstractPathJob(final Level world, @NotNull final BlockPos start, int ran
* @param result
* @param entity
*/
- protected AbstractPathJob(final LevelReader chunkCache, @NotNull final BlockPos start, int range, final PathResult result, @Nullable final Mob entity)
+ protected AbstractPathJob(final Level actualWorld, final LevelReader chunkCache, @NotNull final BlockPos start, int range, final PathResult result, @Nullable final Mob entity)
{
range = Math.max(10, range);
this.maxNodes = Math.min(MAX_NODES, range * range);
@@ -211,6 +212,7 @@ protected AbstractPathJob(final LevelReader chunkCache, @NotNull final BlockPos
world = chunkCache;
cachedBlockLookup = new CachingBlockLookup(start, this.world);
+ this.actualWorld = actualWorld;
this.result = result;
result.setJob(this);
@@ -249,14 +251,10 @@ public AbstractPathJob(final Level world, @NotNull final BlockPos start, @NotNul
this.start = new BlockPos(start);
cachedBlockLookup = new CachingBlockLookup(start, this.world);
+ actualWorld = world;
this.result = result;
result.setJob(this);
-
- if (entity != null && PathfindingUtils.trackingMap.containsValue(entity.getUUID()))
- {
- initDebug();
- }
this.entity = entity;
}
@@ -1552,23 +1550,26 @@ private boolean calculateSwimming(final BlockState below, final BlockState state
return node.isSwimming();
}
- return PathfindingUtils.isWater(cachedBlockLookup, null, below,null)
- || PathfindingUtils.isWater(cachedBlockLookup, null, state,null)
- || PathfindingUtils.isWater(cachedBlockLookup, null, above,null);
+ return PathfindingUtils.isWater(cachedBlockLookup, null, below, null)
+ || PathfindingUtils.isWater(cachedBlockLookup, null, state, null)
+ || PathfindingUtils.isWater(cachedBlockLookup, null, above, null);
}
/**
* Initializes debug tracking
*/
- private void initDebug()
+ public void initDebug()
{
- debugDrawEnabled = true;
- debugNodesVisited = new HashSet<>();
- debugNodesVisitedLater = new HashSet<>();
- debugNodesNotVisited = new HashSet<>();
- debugNodesPath = new HashSet<>();
- debugNodesOrgPath = new HashSet<>();
- debugNodesExtra = new HashSet<>();
+ if (!debugDrawEnabled)
+ {
+ debugDrawEnabled = true;
+ debugNodesVisited = new HashSet<>();
+ debugNodesVisitedLater = new HashSet<>();
+ debugNodesNotVisited = new HashSet<>();
+ debugNodesPath = new HashSet<>();
+ debugNodesOrgPath = new HashSet<>();
+ debugNodesExtra = new HashSet<>();
+ }
}
/**
@@ -1680,23 +1681,20 @@ private void addPathNodeToDebug(final MNode node)
/**
* Sync the path to the client.
*/
- public void syncDebug()
+ public void syncDebug(final List debugWatchers)
{
- if (debugDrawEnabled && entity != null)
+ if (debugDrawEnabled)
{
- for (final Iterator> iter = PathfindingUtils.trackingMap.entrySet().iterator(); iter.hasNext(); )
+ final SyncPathMessage message = new SyncPathMessage(debugNodesVisited,
+ debugNodesNotVisited,
+ debugNodesPath,
+ debugNodesVisitedLater,
+ debugNodesOrgPath,
+ debugNodesExtra);
+
+ for (final ServerPlayer player : debugWatchers)
{
- final Map.Entry entry = iter.next();
- if (entry.getValue().equals(entity.getUUID()))
- {
- final ServerPlayer player = entity.level.getServer().getPlayerList().getPlayer(entry.getKey());
- if (player != null)
- {
- Network.getNetwork()
- .sendToPlayer(new SyncPathMessage(debugNodesVisited, debugNodesNotVisited, debugNodesPath, debugNodesVisitedLater, debugNodesOrgPath, debugNodesExtra),
- player);
- }
- }
+ Network.getNetwork().sendToPlayer(message, player);
}
}
}
@@ -1722,4 +1720,22 @@ public PathingOptions getPathingOptions()
{
return pathingOptions;
}
+
+ @Override
+ public Mob getEntity()
+ {
+ return entity;
+ }
+
+ @Override
+ public Level getActualWorld()
+ {
+ return actualWorld;
+ }
+
+ @Override
+ public BlockPos getStart()
+ {
+ return start;
+ }
}
diff --git a/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/PathJobFindWater.java b/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/PathJobFindWater.java
index 1118c48703e..b8966125a63 100644
--- a/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/PathJobFindWater.java
+++ b/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/PathJobFindWater.java
@@ -88,7 +88,7 @@ protected boolean isAtDestination(@NotNull final MNode n)
}
}
- final PathJobFindFishingPos job = new PathJobFindFishingPos(world, new BlockPos(n.x, n.y, n.z), hutLocation, 10);
+ final PathJobFindFishingPos job = new PathJobFindFishingPos(getActualWorld(), world, new BlockPos(n.x, n.y, n.z), hutLocation, 10);
job.setPathingOptions(getPathingOptions());
final Path path = job.search();
if (path != null && path.canReach())
@@ -125,12 +125,13 @@ private class PathJobFindFishingPos extends AbstractPathJob
private final int distance;
public PathJobFindFishingPos(
+ final Level actualWorld,
final LevelReader world,
final @NotNull BlockPos start,
final @NotNull BlockPos direction,
final int distance)
{
- super(world, start, distance + 100, new PathResult(), null);
+ super(actualWorld, world, start, distance + 100, new PathResult(), null);
this.direction = direction;
this.distance = distance;
}
diff --git a/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/PathJobRaiderPathing.java b/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/PathJobRaiderPathing.java
index f44d8e898a0..50732020423 100644
--- a/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/PathJobRaiderPathing.java
+++ b/src/main/java/com/minecolonies/core/entity/pathfinding/pathjobs/PathJobRaiderPathing.java
@@ -53,7 +53,7 @@ public PathJobRaiderPathing(
super(world, start, targetSpawnPoint, new PathResult(), null);
this.buildings = buildings;
direction = targetSpawnPoint;
- maxNodes = 5000;
+ maxNodes = 10000;
setPathingOptions(new PathingOptions().withJumpCost(1).withStartSwimCost(1).withSwimCost(1).withCanSwim(true).withCanEnterDoors(true));
}
diff --git a/src/main/java/com/minecolonies/core/entity/pathfinding/pathresults/PathResult.java b/src/main/java/com/minecolonies/core/entity/pathfinding/pathresults/PathResult.java
index 35d5c637352..ccb36dd9d7b 100644
--- a/src/main/java/com/minecolonies/core/entity/pathfinding/pathresults/PathResult.java
+++ b/src/main/java/com/minecolonies/core/entity/pathfinding/pathresults/PathResult.java
@@ -2,10 +2,14 @@
import com.minecolonies.api.util.Log;
import com.minecolonies.core.entity.pathfinding.PathFindingStatus;
+import com.minecolonies.core.entity.pathfinding.PathfindingUtils;
+import com.minecolonies.core.entity.pathfinding.pathjobs.AbstractPathJob;
+import net.minecraft.server.level.ServerPlayer;
+import net.minecraft.world.entity.player.Player;
import net.minecraft.world.level.pathfinder.Path;
import org.jetbrains.annotations.Nullable;
-import java.util.concurrent.Callable;
+import java.util.*;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Future;
@@ -13,7 +17,7 @@
/**
* Creates a pathResult of a certain path.
*/
-public class PathResult>
+public class PathResult
{
/**
* The pathfinding status
@@ -55,6 +59,11 @@ public class PathResult>
*/
public int searchedNodes = 0;
+ /**
+ * The players getting debug information
+ */
+ private List debugWatchers = null;
+
/**
* Get Status of the Path.
*
@@ -169,6 +178,31 @@ public void setJob(final T job)
this.job = job;
}
+ /**
+ * Adds another player to the debug tracking
+ *
+ * @param player ID
+ */
+ public void addTrackingPlayer(final UUID uuid)
+ {
+ if (uuid == null)
+ {
+ Log.getLogger().warn("Trying to add null uuid as tracking player");
+ }
+
+ if (debugWatchers == null)
+ {
+ debugWatchers = new ArrayList<>();
+ }
+
+ debugWatchers.add(uuid);
+
+ if (job != null)
+ {
+ job.initDebug();
+ }
+ }
+
/**
* Starts the job by queing it to an executor
*
@@ -178,10 +212,58 @@ public void startJob(final ExecutorService executorService)
{
if (job != null)
{
+ checkDebugging();
pathCalculation = executorService.submit(job);
}
}
+ /**
+ * Checks for debug tracking
+ */
+ private void checkDebugging()
+ {
+ if (!PathfindingUtils.trackByType.isEmpty())
+ {
+ for (Iterator> iterator = PathfindingUtils.trackByType.entrySet().iterator(); iterator.hasNext(); )
+ {
+ final Map.Entry entry = iterator.next();
+ final Player player = job.getActualWorld().getPlayerByUUID(entry.getValue());
+ if (player == null)
+ {
+ iterator.remove();
+ continue;
+ }
+
+ // Exclude stuff thats not visible
+ if (player.blockPosition().distManhattan(job.getStart()) > 400)
+ {
+ continue;
+ }
+
+ if (job.getClass().getSimpleName().toLowerCase().contains(entry.getKey().toLowerCase()))
+ {
+ addTrackingPlayer(entry.getValue());
+ }
+ }
+ }
+
+ if (job.getEntity() != null && PathfindingUtils.trackingMap.containsValue(job.getEntity().getUUID()))
+ {
+ for (final Map.Entry entry : PathfindingUtils.trackingMap.entrySet())
+ {
+ if (entry.getValue().equals(job.getEntity().getUUID()))
+ {
+ addTrackingPlayer(entry.getKey());
+ }
+ }
+ }
+
+ if (debugWatchers != null)
+ {
+ job.initDebug();
+ }
+ }
+
/**
* Processes the completed calculation results
*/
@@ -197,6 +279,7 @@ public void processCalculationResults()
path = pathCalculation.get();
pathCalculation = null;
setStatus(PathFindingStatus.CALCULATION_COMPLETE);
+ job.syncDebug(getDebugWatchers());
}
catch (InterruptedException | ExecutionException e)
{
@@ -246,4 +329,28 @@ public void cancel()
pathingDoneAndProcessed = true;
}
+
+ /**
+ * Gets the tracking players
+ *
+ * @return
+ */
+ public List getDebugWatchers()
+ {
+ final List newList = new ArrayList<>();
+
+ if (job != null && debugWatchers != null)
+ {
+ for (final UUID playerID : debugWatchers)
+ {
+ final Player player = job.getActualWorld().getPlayerByUUID(playerID);
+ if (player instanceof ServerPlayer serverPlayer)
+ {
+ newList.add(serverPlayer);
+ }
+ }
+ }
+
+ return newList;
+ }
}