diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp index c32f0402a..674918aef 100644 --- a/src/server/game/Entities/Player/Player.cpp +++ b/src/server/game/Entities/Player/Player.cpp @@ -10389,24 +10389,39 @@ void Player::ContinueTaxiFlight() TaxiPathNodeList const& nodeList = sTaxiPathNodesByPath[path]; - float bestDist = SIZE_OF_GRIDS * SIZE_OF_GRIDS; // xinef: large value - float currDist = 0.0f; + // Use triangle inequality to find the segment the player is on. + // When distPrev + distNext < distNodes, the player projects between + // the two nodes of the segment. Resume from the end node (i). + float distPrev; + float distNext = + (nodeList[0]->x - GetPositionX()) * (nodeList[0]->x - GetPositionX()) + + (nodeList[0]->y - GetPositionY()) * (nodeList[0]->y - GetPositionY()) + + (nodeList[0]->z - GetPositionZ()) * (nodeList[0]->z - GetPositionZ()); - // xinef: changed to -1, we dont want to catch last node - for (uint32 i = 0; i < nodeList.size() - 1; ++i) + for (uint32 i = 1; i < nodeList.size(); ++i) { TaxiPathNodeEntry const* node = nodeList[i]; - TaxiPathNodeEntry const* nextNode = nodeList[i + 1]; + TaxiPathNodeEntry const* prevNode = nodeList[i - 1]; - // xinef: skip nodes at another map, get last valid node on current map - if (nextNode->mapid != GetMapId() || node->mapid != GetMapId()) + // skip nodes at another map + if (node->mapid != GetMapId()) continue; - currDist = (node->x - GetPositionX()) * (node->x - GetPositionX()) + (node->y - GetPositionY()) * (node->y - GetPositionY()) + (node->z - GetPositionZ()) * (node->z - GetPositionZ()); - if (currDist < bestDist) + distPrev = distNext; + distNext = + (node->x - GetPositionX()) * (node->x - GetPositionX()) + + (node->y - GetPositionY()) * (node->y - GetPositionY()) + + (node->z - GetPositionZ()) * (node->z - GetPositionZ()); + + float distNodes = + (node->x - prevNode->x) * (node->x - prevNode->x) + + (node->y - prevNode->y) * (node->y - prevNode->y) + + (node->z - prevNode->z) * (node->z - prevNode->z); + + if (distPrev + distNext < distNodes) { startNode = i; - bestDist = currDist; + break; } } diff --git a/src/server/game/Entities/Player/PlayerUpdates.cpp b/src/server/game/Entities/Player/PlayerUpdates.cpp index ce2fde051..fec393e3e 100644 --- a/src/server/game/Entities/Player/PlayerUpdates.cpp +++ b/src/server/game/Entities/Player/PlayerUpdates.cpp @@ -1435,7 +1435,7 @@ void Player::UpdatePvPState() if (pvpInfo.IsHostile) // in hostile area { - if (IsInFlight()) // on taxi + if (IsInFlight() || !m_taxi.empty()) // on taxi or taxi pending resume after login return; if (!IsPvP() || pvpInfo.EndTimer != 0)