diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/common/Common.h | 1 | ||||
-rw-r--r-- | src/server/game/DataStores/DB2Stores.cpp | 2 | ||||
-rw-r--r-- | src/server/game/DataStores/DB2Structure.h | 11 | ||||
-rw-r--r-- | src/server/game/DataStores/DBCStructure.h | 5 | ||||
-rw-r--r-- | src/server/game/Entities/Player/Player.cpp | 33 | ||||
-rw-r--r-- | src/server/game/Entities/Player/Player.h | 2 | ||||
-rw-r--r-- | src/server/game/Entities/Transport/Transport.cpp | 1 | ||||
-rw-r--r-- | src/server/game/Globals/ObjectMgr.cpp | 10 | ||||
-rw-r--r-- | src/server/game/Handlers/TaxiHandler.cpp | 64 | ||||
-rw-r--r-- | src/server/game/Maps/TransportMgr.cpp | 8 | ||||
-rw-r--r-- | src/server/game/Maps/TransportMgr.h | 2 | ||||
-rw-r--r-- | src/server/game/Movement/MotionMaster.cpp | 3 | ||||
-rwxr-xr-x | src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp | 109 | ||||
-rwxr-xr-x | src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.h | 38 | ||||
-rw-r--r-- | src/server/game/Movement/Waypoints/Path.h | 98 |
15 files changed, 158 insertions, 229 deletions
diff --git a/src/common/Common.h b/src/common/Common.h index e83340bdd84..58bb006166a 100644 --- a/src/common/Common.h +++ b/src/common/Common.h @@ -39,6 +39,7 @@ #include <sstream> #include <algorithm> #include <memory> +#include <vector> #include <boost/optional.hpp> #include <boost/utility/in_place_factory.hpp> diff --git a/src/server/game/DataStores/DB2Stores.cpp b/src/server/game/DataStores/DB2Stores.cpp index ae26119986c..68658586239 100644 --- a/src/server/game/DataStores/DB2Stores.cpp +++ b/src/server/game/DataStores/DB2Stores.cpp @@ -443,7 +443,7 @@ void DB2Manager::LoadStores(std::string const& dataPath, uint32 defaultLocale) // fill data for (TaxiPathNodeEntry const* entry : sTaxiPathNodeStore) - sTaxiPathNodesByPath[entry->PathID].set(entry->NodeIndex, entry); + sTaxiPathNodesByPath[entry->PathID][entry->NodeIndex] = entry; // Initialize global taxinodes mask // include existed nodes that have at least single not spell base (scripted) path diff --git a/src/server/game/DataStores/DB2Structure.h b/src/server/game/DataStores/DB2Structure.h index f2f8bec2b68..9c898ea0101 100644 --- a/src/server/game/DataStores/DB2Structure.h +++ b/src/server/game/DataStores/DB2Structure.h @@ -20,7 +20,6 @@ #include "Common.h" #include "DBCEnums.h" -#include "Path.h" #include "Util.h" #pragma pack(push, 1) @@ -1358,15 +1357,7 @@ struct TaxiPathBySourceAndDestination typedef std::map<uint32, TaxiPathBySourceAndDestination> TaxiPathSetForSource; typedef std::map<uint32, TaxiPathSetForSource> TaxiPathSetBySource; -struct TaxiPathNodePtr -{ - TaxiPathNodePtr() : i_ptr(NULL) { } - TaxiPathNodePtr(TaxiPathNodeEntry const* ptr) : i_ptr(ptr) { } - TaxiPathNodeEntry const* i_ptr; - operator TaxiPathNodeEntry const& () const { return *i_ptr; } -}; - -typedef Path<TaxiPathNodePtr, TaxiPathNodeEntry const> TaxiPathNodeList; +typedef std::vector<TaxiPathNodeEntry const*> TaxiPathNodeList; typedef std::vector<TaxiPathNodeList> TaxiPathNodesByPath; #define TaxiMaskSize 217 diff --git a/src/server/game/DataStores/DBCStructure.h b/src/server/game/DataStores/DBCStructure.h index dc53a316ee7..b2a2704307e 100644 --- a/src/server/game/DataStores/DBCStructure.h +++ b/src/server/game/DataStores/DBCStructure.h @@ -21,13 +21,8 @@ #include "Common.h" #include "DBCEnums.h" -#include "Path.h" #include "Util.h" -#include <map> -#include <set> -#include <vector> - // Structures using to access raw DBC data and required packing to portability #pragma pack(push, 1) diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp index b00b18f2f4f..9689144ebc9 100644 --- a/src/server/game/Entities/Player/Player.cpp +++ b/src/server/game/Entities/Player/Player.cpp @@ -21038,6 +21038,7 @@ bool Player::ActivateTaxiPathTo(std::vector<uint32> const& nodes, Creature* npc // fill destinations path tail uint32 sourcepath = 0; uint32 totalcost = 0; + uint32 firstcost = 0; uint32 prevnode = sourcenode; uint32 lastnode = 0; @@ -21056,6 +21057,8 @@ bool Player::ActivateTaxiPathTo(std::vector<uint32> const& nodes, Creature* npc } totalcost += cost; + if (i == 1) + firstcost = cost; if (prevnode == sourcenode) sourcepath = path; @@ -21094,8 +21097,6 @@ bool Player::ActivateTaxiPathTo(std::vector<uint32> const& nodes, Creature* npc } //Checks and preparations done, DO FLIGHT - ModifyMoney(-int64(totalcost)); - UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_TRAVELLING, totalcost); UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_FLIGHT_PATHS_TAKEN, 1); // prevent stealth flight @@ -21106,11 +21107,15 @@ bool Player::ActivateTaxiPathTo(std::vector<uint32> const& nodes, Creature* npc TaxiNodesEntry const* lastPathNode = sTaxiNodesStore.LookupEntry(nodes[nodes.size()-1]); ASSERT(lastPathNode); m_taxi.ClearTaxiDestinations(); + ModifyMoney(-int64(totalcost)); + UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_TRAVELLING, totalcost); TeleportTo(lastPathNode->MapID, lastPathNode->Pos.X, lastPathNode->Pos.Y, lastPathNode->Pos.Z, GetOrientation()); return false; } else { + ModifyMoney(-int64(firstcost)); + UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_TRAVELLING, firstcost); GetSession()->SendActivateTaxiReply(ERR_TAXIOK); GetSession()->SendDoFlight(mount_display_id, sourcepath); } @@ -21161,30 +21166,30 @@ void Player::ContinueTaxiFlight() float distPrev = MAP_SIZE*MAP_SIZE; float distNext = - (nodeList[0].Loc.X-GetPositionX())*(nodeList[0].Loc.X-GetPositionX())+ - (nodeList[0].Loc.Y-GetPositionY())*(nodeList[0].Loc.Y-GetPositionY())+ - (nodeList[0].Loc.Z-GetPositionZ())*(nodeList[0].Loc.Z-GetPositionZ()); + (nodeList[0]->Loc.X - GetPositionX())*(nodeList[0]->Loc.X - GetPositionX()) + + (nodeList[0]->Loc.Y - GetPositionY())*(nodeList[0]->Loc.Y - GetPositionY()) + + (nodeList[0]->Loc.Z - GetPositionZ())*(nodeList[0]->Loc.Z - GetPositionZ()); for (uint32 i = 1; i < nodeList.size(); ++i) { - TaxiPathNodeEntry const& node = nodeList[i]; - TaxiPathNodeEntry const& prevNode = nodeList[i-1]; + TaxiPathNodeEntry const* node = nodeList[i]; + TaxiPathNodeEntry const* prevNode = nodeList[i-1]; // skip nodes at another map - if (node.MapID != GetMapId()) + if (node->MapID != GetMapId()) continue; distPrev = distNext; distNext = - (node.Loc.X-GetPositionX())*(node.Loc.X-GetPositionX())+ - (node.Loc.Y-GetPositionY())*(node.Loc.Y-GetPositionY())+ - (node.Loc.Z-GetPositionZ())*(node.Loc.Z-GetPositionZ()); + (node->Loc.X - GetPositionX()) * (node->Loc.X - GetPositionX()) + + (node->Loc.Y - GetPositionY()) * (node->Loc.Y - GetPositionY()) + + (node->Loc.Z - GetPositionZ()) * (node->Loc.Z - GetPositionZ()); float distNodes = - (node.Loc.X-prevNode.Loc.X)*(node.Loc.X-prevNode.Loc.X)+ - (node.Loc.Y-prevNode.Loc.Y)*(node.Loc.Y-prevNode.Loc.Y)+ - (node.Loc.Z-prevNode.Loc.Z)*(node.Loc.Z-prevNode.Loc.Z); + (node->Loc.X - prevNode->Loc.X) * (node->Loc.X - prevNode->Loc.X) + + (node->Loc.Y - prevNode->Loc.Y) * (node->Loc.Y - prevNode->Loc.Y) + + (node->Loc.Z - prevNode->Loc.Z) * (node->Loc.Z - prevNode->Loc.Z); if (distNext + distPrev < distNodes) { diff --git a/src/server/game/Entities/Player/Player.h b/src/server/game/Entities/Player/Player.h index d4973e0f332..559f1f28570 100644 --- a/src/server/game/Entities/Player/Player.h +++ b/src/server/game/Entities/Player/Player.h @@ -1129,6 +1129,8 @@ class PlayerTaxi m_TaxiDestinations.pop_front(); return GetTaxiDestination(); } + + std::deque<uint32> const& GetPath() const { return m_TaxiDestinations; } bool empty() const { return m_TaxiDestinations.empty(); } friend std::ostringstream& operator<< (std::ostringstream& ss, PlayerTaxi const& taxi); diff --git a/src/server/game/Entities/Transport/Transport.cpp b/src/server/game/Entities/Transport/Transport.cpp index 0be9a205e5b..e6b3067cc2a 100644 --- a/src/server/game/Entities/Transport/Transport.cpp +++ b/src/server/game/Entities/Transport/Transport.cpp @@ -20,7 +20,6 @@ #include "Transport.h" #include "MapManager.h" #include "ObjectMgr.h" -#include "Path.h" #include "ScriptMgr.h" #include "DBCStores.h" #include "GameObjectAI.h" diff --git a/src/server/game/Globals/ObjectMgr.cpp b/src/server/game/Globals/ObjectMgr.cpp index 7f014e22efb..5352112caca 100644 --- a/src/server/game/Globals/ObjectMgr.cpp +++ b/src/server/game/Globals/ObjectMgr.cpp @@ -4875,13 +4875,13 @@ void ObjectMgr::LoadEventScripts() { for (size_t node_idx = 0; node_idx < sTaxiPathNodesByPath[path_idx].size(); ++node_idx) { - TaxiPathNodeEntry const& node = sTaxiPathNodesByPath[path_idx][node_idx]; + TaxiPathNodeEntry const* node = sTaxiPathNodesByPath[path_idx][node_idx]; - if (node.ArrivalEventID) - evt_scripts.insert(node.ArrivalEventID); + if (node->ArrivalEventID) + evt_scripts.insert(node->ArrivalEventID); - if (node.DepartureEventID) - evt_scripts.insert(node.DepartureEventID); + if (node->DepartureEventID) + evt_scripts.insert(node->DepartureEventID); } } diff --git a/src/server/game/Handlers/TaxiHandler.cpp b/src/server/game/Handlers/TaxiHandler.cpp index 20a8ba70f76..1669bc306d6 100644 --- a/src/server/game/Handlers/TaxiHandler.cpp +++ b/src/server/game/Handlers/TaxiHandler.cpp @@ -24,7 +24,6 @@ #include "Log.h" #include "ObjectMgr.h" #include "Player.h" -#include "Path.h" #include "WaypointMovementGenerator.h" void WorldSession::HandleTaxiNodeStatusQueryOpcode(WorldPacket& recvData) @@ -198,7 +197,7 @@ void WorldSession::HandleActivateTaxiExpressOpcode (WorldPacket& recvData) void WorldSession::HandleMoveSplineDoneOpcode(WorldPacket& recvData) { - recvData.read_skip<uint32>(); // unk + recvData.read_skip<uint32>(); // spline id MovementInfo movementInfo; // used only for proper packet read _player->ValidateMovementInfo(&movementInfo); @@ -209,59 +208,32 @@ void WorldSession::HandleMoveSplineDoneOpcode(WorldPacket& recvData) // we need process only (1) uint32 curDest = GetPlayer()->m_taxi.GetTaxiDestination(); - if (!curDest) - return; - - TaxiNodesEntry const* curDestNode = sTaxiNodesStore.LookupEntry(curDest); - - // far teleport case - if (curDestNode && curDestNode->MapID != GetPlayer()->GetMapId()) + if (curDest) { - if (GetPlayer()->GetMotionMaster()->GetCurrentMovementGeneratorType() == FLIGHT_MOTION_TYPE) - { - // short preparations to continue flight - FlightPathMovementGenerator* flight = (FlightPathMovementGenerator*)(GetPlayer()->GetMotionMaster()->top()); - - flight->SetCurrentNodeAfterTeleport(); - TaxiPathNodeEntry const& node = flight->GetPath()[flight->GetCurrentNode()]; - flight->SkipCurrentNode(); + TaxiNodesEntry const* curDestNode = sTaxiNodesStore.LookupEntry(curDest); - GetPlayer()->TeleportTo(curDestNode->MapID, node.Loc.X, node.Loc.Y, node.Loc.Z, GetPlayer()->GetOrientation()); - } - return; - } - - uint32 destinationnode = GetPlayer()->m_taxi.NextTaxiDestination(); - if (destinationnode > 0) // if more destinations to go - { - // current source node for next destination - uint32 sourcenode = GetPlayer()->m_taxi.GetTaxiSource(); - - // Add to taximask middle hubs in taxicheat mode (to prevent having player with disabled taxicheat and not having back flight path) - if (GetPlayer()->isTaxiCheater()) + // far teleport case + if (curDestNode && curDestNode->MapID != GetPlayer()->GetMapId()) { - if (GetPlayer()->m_taxi.SetTaximaskNode(sourcenode)) + if (GetPlayer()->GetMotionMaster()->GetCurrentMovementGeneratorType() == FLIGHT_MOTION_TYPE) { - WorldPacket data(SMSG_NEW_TAXI_PATH, 0); - _player->GetSession()->SendPacket(&data); - } - } + // short preparations to continue flight + FlightPathMovementGenerator* flight = (FlightPathMovementGenerator*)(GetPlayer()->GetMotionMaster()->top()); - TC_LOG_DEBUG("network", "WORLD: Taxi has to go from %u to %u", sourcenode, destinationnode); + flight->SetCurrentNodeAfterTeleport(); + TaxiPathNodeEntry const* node = flight->GetPath()[flight->GetCurrentNode()]; + flight->SkipCurrentNode(); - uint32 mountDisplayId = sObjectMgr->GetTaxiMountDisplayId(sourcenode, GetPlayer()->GetTeam()); - - uint32 path, cost; - sObjectMgr->GetTaxiPath(sourcenode, destinationnode, path, cost); + GetPlayer()->TeleportTo(curDestNode->MapID, node->Loc.X, node->Loc.Y, node->Loc.Z, GetPlayer()->GetOrientation()); + } + } - if (path && mountDisplayId) - SendDoFlight(mountDisplayId, path, 1); // skip start fly node - else - GetPlayer()->m_taxi.ClearTaxiDestinations(); // clear problematic path and next return; } - else - GetPlayer()->m_taxi.ClearTaxiDestinations(); // not destinations, clear source node + + // at this point only 1 node is expected (final destination) + if (GetPlayer()->m_taxi.GetPath().size() != 1) + return; GetPlayer()->CleanupAfterTaxiFlight(); GetPlayer()->SetFallInformation(0, GetPlayer()->GetPositionZ()); diff --git a/src/server/game/Maps/TransportMgr.cpp b/src/server/game/Maps/TransportMgr.cpp index 8c7442a8ae5..86c4fb73108 100644 --- a/src/server/game/Maps/TransportMgr.cpp +++ b/src/server/game/Maps/TransportMgr.cpp @@ -114,7 +114,7 @@ void TransportMgr::GeneratePath(GameObjectTemplate const* goInfo, TransportTempl Movement::PointsArray splinePath, allPoints; bool mapChange = false; for (size_t i = 0; i < path.size(); ++i) - allPoints.push_back(G3D::Vector3(path[i].Loc.X, path[i].Loc.Y, path[i].Loc.Z)); + allPoints.push_back(G3D::Vector3(path[i]->Loc.X, path[i]->Loc.Y, path[i]->Loc.Z)); // Add extra points to allow derivative calculations for all path nodes allPoints.insert(allPoints.begin(), allPoints.front().lerp(allPoints[1], -0.2f)); @@ -130,8 +130,8 @@ void TransportMgr::GeneratePath(GameObjectTemplate const* goInfo, TransportTempl { if (!mapChange) { - TaxiPathNodeEntry const& node_i = path[i]; - if (i != path.size() - 1 && (node_i.Flags & 1 || node_i.MapID != path[i + 1].MapID)) + TaxiPathNodeEntry const* node_i = path[i]; + if (i != path.size() - 1 && (node_i->Flags & 1 || node_i->MapID != path[i + 1]->MapID)) { keyFrames.back().Teleport = true; mapChange = true; @@ -144,7 +144,7 @@ void TransportMgr::GeneratePath(GameObjectTemplate const* goInfo, TransportTempl k.InitialOrientation = Position::NormalizeOrientation(std::atan2(h.y, h.x) + float(M_PI)); keyFrames.push_back(k); - splinePath.push_back(G3D::Vector3(node_i.Loc.X, node_i.Loc.Y, node_i.Loc.Z)); + splinePath.push_back(G3D::Vector3(node_i->Loc.X, node_i->Loc.Y, node_i->Loc.Z)); transport->mapsUsed.insert(k.Node->MapID); } } diff --git a/src/server/game/Maps/TransportMgr.h b/src/server/game/Maps/TransportMgr.h index 61d08908b78..5e032dbd71f 100644 --- a/src/server/game/Maps/TransportMgr.h +++ b/src/server/game/Maps/TransportMgr.h @@ -39,7 +39,7 @@ typedef std::unordered_map<uint32, std::set<uint32> > TransportInstanceMap; struct KeyFrame { - explicit KeyFrame(TaxiPathNodeEntry const& _node) : Index(0), Node(&_node), InitialOrientation(0.0f), + explicit KeyFrame(TaxiPathNodeEntry const* node) : Index(0), Node(node), InitialOrientation(0.0f), DistSinceStop(-1.0f), DistUntilStop(-1.0f), DistFromPrev(-1.0f), TimeFrom(0.0f), TimeTo(0.0f), Teleport(false), ArriveTime(0), DepartureTime(0), Spline(NULL), NextDistFromPrev(0.0f), NextArriveTime(0) { diff --git a/src/server/game/Movement/MotionMaster.cpp b/src/server/game/Movement/MotionMaster.cpp index 0a4deebbbfc..50ff839e23c 100644 --- a/src/server/game/Movement/MotionMaster.cpp +++ b/src/server/game/Movement/MotionMaster.cpp @@ -534,7 +534,8 @@ void MotionMaster::MoveTaxiFlight(uint32 path, uint32 pathnode) if (path < sTaxiPathNodesByPath.size()) { TC_LOG_DEBUG("misc", "%s taxi to (Path %u node %u)", _owner->GetName().c_str(), path, pathnode); - FlightPathMovementGenerator* mgen = new FlightPathMovementGenerator(sTaxiPathNodesByPath[path], pathnode); + FlightPathMovementGenerator* mgen = new FlightPathMovementGenerator(pathnode); + mgen->LoadPath(_owner->ToPlayer()); Mutate(mgen, MOTION_SLOT_CONTROLLED); } else diff --git a/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp b/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp index 46ccd8638da..a0858b35c17 100755 --- a/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp +++ b/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp @@ -245,17 +245,62 @@ bool WaypointMovementGenerator<Creature>::GetResetPos(Creature*, float& x, float uint32 FlightPathMovementGenerator::GetPathAtMapEnd() const { - if (i_currentNode >= i_path->size()) - return i_path->size(); + if (i_currentNode >= i_path.size()) + return i_path.size(); - uint32 curMapId = (*i_path)[i_currentNode].MapID; - for (uint32 i = i_currentNode; i < i_path->size(); ++i) - { - if ((*i_path)[i].MapID != curMapId) + uint32 curMapId = i_path[i_currentNode]->MapID; + for (uint32 i = i_currentNode; i < i_path.size(); ++i) + if (i_path[i]->MapID != curMapId) return i; - } - return i_path->size(); + return i_path.size(); +} + +#define SKIP_SPLINE_POINT_DISTANCE_SQ (40.0f * 40.0f) + +bool IsNodeIncludedInShortenedPath(TaxiPathNodeEntry const* p1, TaxiPathNodeEntry const* p2) +{ + return p1->MapID != p2->MapID || std::pow(p1->Loc.X - p2->Loc.X, 2) + std::pow(p1->Loc.Y - p2->Loc.Y, 2) > SKIP_SPLINE_POINT_DISTANCE_SQ; +} + +void FlightPathMovementGenerator::LoadPath(Player* player) +{ + _pointsForPathSwitch.clear(); + std::deque<uint32> const& taxi = player->m_taxi.GetPath(); + for (uint32 src = 0, dst = 1; dst < taxi.size(); src = dst++) + { + uint32 path, cost; + sObjectMgr->GetTaxiPath(taxi[src], taxi[dst], path, cost); + if (path > sTaxiPathNodesByPath.size()) + return; + + TaxiPathNodeList const& nodes = sTaxiPathNodesByPath[path]; + if (!nodes.empty()) + { + TaxiPathNodeEntry const* start = nodes[0]; + TaxiPathNodeEntry const* end = nodes[nodes.size() - 1]; + bool passedPreviousSegmentProximityCheck = false; + for (uint32 i = 0; i < nodes.size(); ++i) + { + if (passedPreviousSegmentProximityCheck || !src || i_path.empty() || IsNodeIncludedInShortenedPath(i_path[i_path.size() - 1], nodes[i])) + { + if ((!src || (IsNodeIncludedInShortenedPath(start, nodes[i]) && i >= 2)) && + (dst == taxi.size() - 1 || (IsNodeIncludedInShortenedPath(end, nodes[i]) && i < nodes.size() - 1))) + { + passedPreviousSegmentProximityCheck = true; + i_path.push_back(nodes[i]); + } + } + else + { + i_path.pop_back(); + --_pointsForPathSwitch.back().PathIndex; + } + } + } + + _pointsForPathSwitch.push_back({ uint32(i_path.size() - 1), int32(cost) }); + } } void FlightPathMovementGenerator::DoInitialize(Player* player) @@ -296,7 +341,7 @@ void FlightPathMovementGenerator::DoReset(Player* player) uint32 end = GetPathAtMapEnd(); for (uint32 i = GetCurrentNode(); i != end; ++i) { - G3D::Vector3 vertice((*i_path)[i].Loc.X, (*i_path)[i].Loc.Y, (*i_path)[i].Loc.Z); + G3D::Vector3 vertice(i_path[i]->Loc.X, i_path[i]->Loc.Y, i_path[i]->Loc.Z); init.Path().push_back(vertice); } init.SetFirstPointId(GetCurrentNode()); @@ -316,9 +361,21 @@ bool FlightPathMovementGenerator::DoUpdate(Player* player, uint32 /*diff*/) bool departureEvent = true; do { - DoEventIfAny(player, (*i_path)[i_currentNode], departureEvent); + DoEventIfAny(player, i_path[i_currentNode], departureEvent); + while (!_pointsForPathSwitch.empty() && _pointsForPathSwitch.front().PathIndex <= i_currentNode) + { + _pointsForPathSwitch.pop_front(); + player->m_taxi.NextTaxiDestination(); + if (!_pointsForPathSwitch.empty()) + { + player->UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_TRAVELLING, _pointsForPathSwitch.front().Cost); + player->ModifyMoney(-_pointsForPathSwitch.front().Cost); + } + } + if (pointId == i_currentNode) break; + if (i_currentNode == _preloadTargetNode) PreloadEndGrid(); i_currentNode += (uint32)departureEvent; @@ -327,18 +384,18 @@ bool FlightPathMovementGenerator::DoUpdate(Player* player, uint32 /*diff*/) while (true); } - return i_currentNode < (i_path->size()-1); + return i_currentNode < (i_path.size() - 1); } void FlightPathMovementGenerator::SetCurrentNodeAfterTeleport() { - if (i_path->empty()) + if (i_path.empty() || i_currentNode >= i_path.size()) return; - uint32 map0 = (*i_path)[0].MapID; - for (size_t i = 1; i < i_path->size(); ++i) + uint32 map0 = i_path[i_currentNode]->MapID; + for (size_t i = i_currentNode + 1; i < i_path.size(); ++i) { - if ((*i_path)[i].MapID != map0) + if (i_path[i]->MapID != map0) { i_currentNode = i; return; @@ -346,19 +403,21 @@ void FlightPathMovementGenerator::SetCurrentNodeAfterTeleport() } } -void FlightPathMovementGenerator::DoEventIfAny(Player* player, TaxiPathNodeEntry const& node, bool departure) +void FlightPathMovementGenerator::DoEventIfAny(Player* player, TaxiPathNodeEntry const* node, bool departure) { - if (uint32 eventid = departure ? node.DepartureEventID : node.ArrivalEventID) + if (uint32 eventid = departure ? node->DepartureEventID : node->ArrivalEventID) { - TC_LOG_DEBUG("maps.script", "Taxi %s event %u of node %u of path %u for player %s", departure ? "departure" : "arrival", eventid, node.NodeIndex, node.PathID, player->GetName().c_str()); + TC_LOG_DEBUG("maps.script", "Taxi %s event %u of node %u of path %u for player %s", departure ? "departure" : "arrival", eventid, node->NodeIndex, node->PathID, player->GetName().c_str()); player->GetMap()->ScriptsStart(sEventScripts, eventid, player, player); } } bool FlightPathMovementGenerator::GetResetPos(Player*, float& x, float& y, float& z) { - const TaxiPathNodeEntry& node = (*i_path)[i_currentNode]; - x = node.Loc.X; y = node.Loc.Y; z = node.Loc.Z; + TaxiPathNodeEntry const* node = i_path[i_currentNode]; + x = node->Loc.X; + y = node->Loc.Y; + z = node->Loc.Z; return true; } @@ -366,11 +425,11 @@ void FlightPathMovementGenerator::InitEndGridInfo() { /*! Storage to preload flightmaster grid at end of flight. For multi-stop flights, this will be reinitialized for each flightmaster at the end of each spline (or stop) in the flight. */ - uint32 nodeCount = (*i_path).size(); //! Number of nodes in path. - _endMapId = (*i_path)[nodeCount - 1].MapID; //! MapId of last node + uint32 nodeCount = i_path.size(); //! Number of nodes in path. + _endMapId = i_path[nodeCount - 1]->MapID; //! MapId of last node _preloadTargetNode = nodeCount - 3; - _endGridX = (*i_path)[nodeCount - 1].Loc.X; - _endGridY = (*i_path)[nodeCount - 1].Loc.Y; + _endGridX = i_path[nodeCount - 1]->Loc.X; + _endGridY = i_path[nodeCount - 1]->Loc.Y; } void FlightPathMovementGenerator::PreloadEndGrid() @@ -381,7 +440,7 @@ void FlightPathMovementGenerator::PreloadEndGrid() // Load the grid if (endMap) { - TC_LOG_DEBUG("misc", "Preloading rid (%f, %f) for map %u at node index %u/%u", _endGridX, _endGridY, _endMapId, _preloadTargetNode, (uint32)(i_path->size()-1)); + TC_LOG_DEBUG("misc", "Preloading rid (%f, %f) for map %u at node index %u/%u", _endGridX, _endGridY, _endMapId, _preloadTargetNode, (uint32)(i_path.size() - 1)); endMap->LoadGrid(_endGridX, _endGridY); } else diff --git a/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.h b/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.h index eb8533159a9..caf76b5ea19 100755 --- a/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.h +++ b/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.h @@ -27,13 +27,8 @@ #include "MovementGenerator.h" #include "WaypointManager.h" -#include "Path.h" - #include "Player.h" -#include <vector> -#include <set> - #define FLIGHT_TRAVEL_UPDATE 100 #define STOP_TIME_FOR_PLAYER 3 * MINUTE * IN_MILLISECONDS // 3 Minutes #define TIMEDIFF_NEXT_WP 250 @@ -42,11 +37,9 @@ template<class T, class P> class PathMovementBase { public: - PathMovementBase() : i_path(NULL), i_currentNode(0) { } + PathMovementBase() : i_path(), i_currentNode(0) { } virtual ~PathMovementBase() { }; - // template pattern, not defined .. override required - void LoadPath(T &); uint32 GetCurrentNode() const { return i_currentNode; } protected: @@ -110,30 +103,30 @@ class WaypointMovementGenerator<Creature> : public MovementGeneratorMedium< Crea * and hence generates ground and activities for the player. */ class FlightPathMovementGenerator : public MovementGeneratorMedium< Player, FlightPathMovementGenerator >, - public PathMovementBase<Player, TaxiPathNodeList const*> + public PathMovementBase<Player, TaxiPathNodeList> { public: - explicit FlightPathMovementGenerator(TaxiPathNodeList const& pathnodes, uint32 startNode = 0) + explicit FlightPathMovementGenerator(uint32 startNode = 0) { - i_path = &pathnodes; i_currentNode = startNode; _endGridX = 0.0f; _endGridY = 0.0f; _endMapId = 0; _preloadTargetNode = 0; } + void LoadPath(Player* player); void DoInitialize(Player*); void DoReset(Player*); void DoFinalize(Player*); bool DoUpdate(Player*, uint32); MovementGeneratorType GetMovementGeneratorType() const override { return FLIGHT_MOTION_TYPE; } - TaxiPathNodeList const& GetPath() { return *i_path; } + TaxiPathNodeList const& GetPath() { return i_path; } uint32 GetPathAtMapEnd() const; - bool HasArrived() const { return (i_currentNode >= i_path->size()); } + bool HasArrived() const { return (i_currentNode >= i_path.size()); } void SetCurrentNodeAfterTeleport(); void SkipCurrentNode() { ++i_currentNode; } - void DoEventIfAny(Player* player, TaxiPathNodeEntry const& node, bool departure); + void DoEventIfAny(Player* player, TaxiPathNodeEntry const* node, bool departure); bool GetResetPos(Player*, float& x, float& y, float& z); @@ -141,9 +134,18 @@ class FlightPathMovementGenerator : public MovementGeneratorMedium< Player, Flig void PreloadEndGrid(); private: - float _endGridX; //! X coord of last node location - float _endGridY; //! Y coord of last node location - uint32 _endMapId; //! map Id of last node location - uint32 _preloadTargetNode; //! node index where preloading starts + + float _endGridX; //! X coord of last node location + float _endGridY; //! Y coord of last node location + uint32 _endMapId; //! map Id of last node location + uint32 _preloadTargetNode; //! node index where preloading starts + + struct TaxiNodeChangeInfo + { + uint32 PathIndex; + int32 Cost; + }; + + std::deque<TaxiNodeChangeInfo> _pointsForPathSwitch; //! node indexes and costs where TaxiPath changes }; #endif diff --git a/src/server/game/Movement/Waypoints/Path.h b/src/server/game/Movement/Waypoints/Path.h deleted file mode 100644 index 844089cf393..00000000000 --- a/src/server/game/Movement/Waypoints/Path.h +++ /dev/null @@ -1,98 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef TRINITYCORE_PATH_H -#define TRINITYCORE_PATH_H - -#include "Common.h" -#include <deque> - -struct PathNode -{ - PathNode(): x(0.0f), y(0.0f), z(0.0f) { } - PathNode(float _x, float _y, float _z): x(_x), y(_y), z(_z) { } - float x, y, z; -}; - -template<typename PathElem, typename PathNode = PathElem> -class Path -{ - public: - size_t size() const { return i_nodes.size(); } - bool empty() const { return i_nodes.empty(); } - void resize(unsigned int sz) { i_nodes.resize(sz); } - void clear() { i_nodes.clear(); } - void erase(uint32 idx) { i_nodes.erase(i_nodes.begin() + idx); } - void crop(unsigned int start, unsigned int end) - { - while (start && !i_nodes.empty()) - { - i_nodes.pop_front(); - --start; - } - - while (end && !i_nodes.empty()) - { - i_nodes.pop_back(); - --end; - } - } - - float GetTotalLength(uint32 start, uint32 end) const - { - float len = 0.0f; - for (uint32 idx = start + 1; idx < end; ++idx) - { - PathNode const& node = i_nodes[idx]; - PathNode const& prev = i_nodes[idx - 1]; - float xd = node.x - prev.x; - float yd = node.y - prev.y; - float zd = node.z - prev.z; - len += std::sqrt(xd*xd + yd*yd + zd*zd); - } - return len; - } - - float GetTotalLength() const { return GetTotalLength(0, size()); } - - float GetPassedLength(uint32 curnode, float x, float y, float z) const - { - float len = GetTotalLength(0, curnode); - - if (curnode > 0) - { - PathNode const& node = i_nodes[curnode - 1]; - float xd = x - node.x; - float yd = y - node.y; - float zd = z - node.z; - len += std::sqrt(xd*xd + yd*yd + zd*zd); - } - - return len; - } - - PathNode& operator[](size_t idx) { return i_nodes[idx]; } - PathNode const& operator[](size_t idx) const { return i_nodes[idx]; } - - void set(size_t idx, PathElem elem) { i_nodes[idx] = elem; } - - protected: - std::deque<PathElem> i_nodes; -}; - -#endif |