fix in MMAP navigation when traveling to portal node
This commit is contained in:
1 parent
fe7b5e0f02
commit
6e17dedff2
2 files changed
+57
-3
No files matched your search
@@ -125,10 +125,22 @@ bool ClientlessTravelMgr::AnalyzePath(
|
|||||||
diagnostics.FinalDistance = diagnostics.DirectDistance;
|
diagnostics.FinalDistance = diagnostics.DirectDistance;
|
||||||
|
|
||||||
uint32 const pathType = diagnostics.PathType;
|
uint32 const pathType = diagnostics.PathType;
|
||||||
|
// VCORE_C814A_NAVIGATION_FIX: narrowly accept a short incomplete MMAP path
|
||||||
|
// only when its actual points reach the target without unsafe segments.
|
||||||
|
bool const shortEndReached =
|
||||||
|
diagnostics.Calculated &&
|
||||||
|
(pathType & uint32(PATHFIND_INCOMPLETE)) != 0 &&
|
||||||
|
(pathType & uint32(PATHFIND_NOPATH)) == 0 &&
|
||||||
|
diagnostics.PointCount >= 2 &&
|
||||||
|
diagnostics.DirectDistance <= 25.0f &&
|
||||||
|
diagnostics.PathLength <= 40.0f &&
|
||||||
|
diagnostics.FinalDistance <= 0.25f &&
|
||||||
|
diagnostics.MaxSegmentLength <= 6.0f &&
|
||||||
|
diagnostics.MaxZDelta <= 4.0f;
|
||||||
diagnostics.Complete =
|
diagnostics.Complete =
|
||||||
diagnostics.Calculated &&
|
diagnostics.Calculated &&
|
||||||
(pathType & uint32(PATHFIND_NOPATH)) == 0 &&
|
(pathType & uint32(PATHFIND_NOPATH)) == 0 &&
|
||||||
(pathType & uint32(PATHFIND_INCOMPLETE)) == 0;
|
((pathType & uint32(PATHFIND_INCOMPLETE)) == 0 || shortEndReached);
|
||||||
|
|
||||||
auto addReason = [&](char const* reason)
|
auto addReason = [&](char const* reason)
|
||||||
{
|
{
|
||||||
@@ -196,6 +208,19 @@ bool ClientlessTravelMgr::LaunchPath(Player* player, TravelRecord& record)
|
|||||||
|
|
||||||
Position const& target = record.Status.Target;
|
Position const& target = record.Status.Target;
|
||||||
|
|
||||||
|
// VCORE_C814A_NAVIGATION_FIX: an already reached node is not a failed spline.
|
||||||
|
if (Distance3D(player->GetPositionX(), player->GetPositionY(), player->GetPositionZ(),
|
||||||
|
target.GetPositionX(), target.GetPositionY(), target.GetPositionZ()) <= ARRIVAL_DISTANCE)
|
||||||
|
{
|
||||||
|
record.Status.State = ClientlessTravelState::Arrived;
|
||||||
|
record.Status.RemainingDistance = 0.0f;
|
||||||
|
record.Status.NoProgressMs = 0;
|
||||||
|
TC_LOG_INFO("server.adventurebot.navigation",
|
||||||
|
"NAV_ALREADY_ARRIVED guid=%u name='%s' map=%u",
|
||||||
|
player->GetGUID().GetCounter(), player->GetName().c_str(), player->GetMapId());
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
AnalyzePath(player, target, record.Status.Path);
|
AnalyzePath(player, target, record.Status.Path);
|
||||||
ClientlessPathDiagnostics const& nav = record.Status.Path;
|
ClientlessPathDiagnostics const& nav = record.Status.Path;
|
||||||
record.Status.NavSequence = _nextNavSequence++;
|
record.Status.NavSequence = _nextNavSequence++;
|
||||||
@@ -245,9 +270,38 @@ bool ClientlessTravelMgr::LaunchPath(Player* player, TravelRecord& record)
|
|||||||
|
|
||||||
auto const& points = path.GetPath();
|
auto const& points = path.GetPath();
|
||||||
uint32 const executionType = uint32(path.GetPathType());
|
uint32 const executionType = uint32(path.GetPathType());
|
||||||
|
// VCORE_C814A_NAVIGATION_FIX: confirm the execution path independently.
|
||||||
|
float executionLength = 0.0f;
|
||||||
|
float executionMaxSegment = 0.0f;
|
||||||
|
float executionMaxZ = 0.0f;
|
||||||
|
for (std::size_t i = 1; i < points.size(); ++i)
|
||||||
|
{
|
||||||
|
float const segment = Distance3D(points[i-1].x, points[i-1].y, points[i-1].z,
|
||||||
|
points[i].x, points[i].y, points[i].z);
|
||||||
|
executionLength += segment;
|
||||||
|
executionMaxSegment = std::max(executionMaxSegment, segment);
|
||||||
|
executionMaxZ = std::max(executionMaxZ, std::fabs(points[i].z - points[i-1].z));
|
||||||
|
}
|
||||||
|
float const executionFinalDistance = points.empty() ? nav.DirectDistance :
|
||||||
|
Distance3D(points.back().x, points.back().y, points.back().z,
|
||||||
|
target.GetPositionX(), target.GetPositionY(), target.GetPositionZ());
|
||||||
|
bool const executionShortEndReached =
|
||||||
|
(executionType & uint32(PATHFIND_INCOMPLETE)) != 0 &&
|
||||||
|
(executionType & uint32(PATHFIND_NOPATH)) == 0 &&
|
||||||
|
points.size() >= 2 &&
|
||||||
|
nav.DirectDistance <= 25.0f &&
|
||||||
|
executionLength <= 40.0f &&
|
||||||
|
executionFinalDistance <= 0.25f &&
|
||||||
|
executionMaxSegment <= 6.0f &&
|
||||||
|
executionMaxZ <= 4.0f;
|
||||||
|
if (executionShortEndReached)
|
||||||
|
TC_LOG_INFO("server.adventurebot.navigation",
|
||||||
|
"NAV_SHORT_INCOMPLETE_ACCEPT guid=%u name='%s' path=%.2f final=%.2f",
|
||||||
|
player->GetGUID().GetCounter(), player->GetName().c_str(),
|
||||||
|
executionLength, executionFinalDistance);
|
||||||
if (points.size() < 2 ||
|
if (points.size() < 2 ||
|
||||||
(executionType & uint32(PATHFIND_NOPATH)) != 0 ||
|
(executionType & uint32(PATHFIND_NOPATH)) != 0 ||
|
||||||
(executionType & uint32(PATHFIND_INCOMPLETE)) != 0)
|
((executionType & uint32(PATHFIND_INCOMPLETE)) != 0 && !executionShortEndReached))
|
||||||
{
|
{
|
||||||
record.Status.State = ClientlessTravelState::PathRejected;
|
record.Status.State = ClientlessTravelState::PathRejected;
|
||||||
TC_LOG_WARN("server.adventurebot.navigation",
|
TC_LOG_WARN("server.adventurebot.navigation",
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ log("Arthoran C8.13b bridge test loaded")
|
|||||||
--})
|
--})
|
||||||
|
|
||||||
queue_action("travel_to_node", {
|
queue_action("travel_to_node", {
|
||||||
node = "portal_at_2173_target",
|
node = "lakeshire",
|
||||||
bridge_radius = 400,
|
bridge_radius = 400,
|
||||||
bridge_path_max = 600
|
bridge_path_max = 600
|
||||||
})
|
})
|
||||||
Reference in new issue
Block a user