From 2d68716b24798fabd6af1a7430bf9ad2ac2633c6 Mon Sep 17 00:00:00 2001 From: bash Date: Sun, 31 May 2026 00:08:39 +0200 Subject: [PATCH] fix(Core/Movement): No-progress guard in MoveFarTo to break stuck oscillation near unreachable targets --- src/Ai/World/Rpg/Action/NewRpgBaseAction.cpp | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/src/Ai/World/Rpg/Action/NewRpgBaseAction.cpp b/src/Ai/World/Rpg/Action/NewRpgBaseAction.cpp index 51896c484..c3eb93a2f 100644 --- a/src/Ai/World/Rpg/Action/NewRpgBaseAction.cpp +++ b/src/Ai/World/Rpg/Action/NewRpgBaseAction.cpp @@ -131,6 +131,24 @@ bool NewRpgBaseAction::MoveFarTo(WorldPosition dest) if (path.empty()) return false; + // Progress guard: refuse to dispatch a path whose endpoint isn't + // meaningfully closer to dest than the bot already is. Prevents + // oscillation around terrain the mmap probe can route along but the + // bot can't actually traverse (cave entries with missing nav, narrow + // ledges, geometry that loops back). Reference doesn't have this + // guard but their RPG layer detects stuck via different signals; + // ours surfaces the issue here so the strategy can re-pick a POI. + { + float const distFromBot = botPos.distance(dest); + float const distFromPathEnd = path.getBack().distance(dest); + if (distFromPathEnd + 5.0f >= distFromBot) + { + EmitDebugMove("MoveFar", "no-progress", + dest.GetPositionX(), dest.GetPositionY(), dest.GetPositionZ()); + return false; + } + } + // Walk dispatch. std::vector const& pts = path.getPointPath(); Movement::PointsArray points;