diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/server/game/Entities/Player/Player.cpp | 29 | ||||
-rw-r--r-- | src/server/game/Handlers/MovementHandler.cpp | 30 | ||||
-rw-r--r-- | src/server/game/Server/Packets/MovementPackets.cpp | 23 | ||||
-rw-r--r-- | src/server/game/Server/Packets/MovementPackets.h | 32 | ||||
-rw-r--r-- | src/server/game/Server/Protocol/Opcodes.cpp | 6 | ||||
-rw-r--r-- | src/server/game/Server/WorldSession.cpp | 4 | ||||
-rw-r--r-- | src/server/game/Server/WorldSession.h | 2 |
7 files changed, 103 insertions, 23 deletions
diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp index 4499d5473fb..1dd3f63097a 100644 --- a/src/server/game/Entities/Player/Player.cpp +++ b/src/server/game/Entities/Player/Player.cpp @@ -1220,7 +1220,7 @@ void Player::Update(uint32 p_time) m_zoneUpdateTimer -= p_time; } - if (m_timeSyncTimer > 0) + if (m_timeSyncTimer > 0 && !IsBeingTeleportedFar()) { if (p_time >= m_timeSyncTimer) SendTimeSync(); @@ -1635,18 +1635,10 @@ bool Player::TeleportTo(uint32 mapid, float x, float y, float z, float orientati if (!GetSession()->PlayerLogout()) { - if (mEntry->IsDungeon()) - { - WorldPackets::Instance::UpdateLastInstance updateLastInstance; - updateLastInstance.MapID = mapid; - SendDirectMessage(updateLastInstance.Write()); - } - - WorldPackets::Movement::NewWorld packet; - packet.MapID = mapid; - packet.Pos = static_cast<Position>(m_teleport_dest); - packet.Reason = !(options & TELE_TO_SEAMLESS) ? NEW_WORLD_NORMAL : NEW_WORLD_SEAMLESS; - SendDirectMessage(packet.Write()); + WorldPackets::Movement::SuspendToken suspendToken; + suspendToken.SequenceIndex = m_movementCounter; // not incrementing + suspendToken.Reason = options & TELE_TO_SEAMLESS ? 2 : 1; + SendDirectMessage(suspendToken.Write()); } // move packet sent by client always after far teleport @@ -22222,6 +22214,14 @@ void Player::SetGroup(Group* group, int8 subgroup) void Player::SendInitialPacketsBeforeAddToMap() { + if (!(m_teleport_options & TELE_TO_SEAMLESS)) + { + m_movementCounter = 0; + ResetTimeSync(); + } + + SendTimeSync(); + /// Pass 'this' as argument because we're not stored in ObjectAccessor yet GetSocial()->SendSocialList(this, SOCIAL_FLAG_ALL); @@ -22313,9 +22313,6 @@ void Player::SendInitialPacketsAfterAddToMap() GetZoneAndAreaId(newzone, newarea); UpdateZone(newzone, newarea); // also call SendInitWorldStates(); - ResetTimeSync(); - SendTimeSync(); - GetSession()->SendLoadCUFProfiles(); CastSpell(this, 836, true); // LOGINEFFECT diff --git a/src/server/game/Handlers/MovementHandler.cpp b/src/server/game/Handlers/MovementHandler.cpp index 6464dd1838a..d8943099a93 100644 --- a/src/server/game/Handlers/MovementHandler.cpp +++ b/src/server/game/Handlers/MovementHandler.cpp @@ -31,6 +31,7 @@ #include "InstanceSaveMgr.h" #include "ObjectMgr.h" #include "Vehicle.h" +#include "InstancePackets.h" #include "MovementPackets.h" #define MOVEMENT_PACKET_TIME_DELAY 0 @@ -95,6 +96,11 @@ void WorldSession::HandleMoveWorldportAckOpcode() GetPlayer()->ResetMap(); GetPlayer()->SetMap(newMap); + WorldPackets::Movement::ResumeToken resumeToken; + resumeToken.SequenceIndex = _player->m_movementCounter; + resumeToken.Reason = seamlessTeleport ? 2 : 1; + SendPacket(resumeToken.Write()); + if (!seamlessTeleport) GetPlayer()->SendInitialPacketsBeforeAddToMap(); @@ -214,6 +220,30 @@ void WorldSession::HandleMoveWorldportAckOpcode() GetPlayer()->ProcessDelayedOperations(); } +void WorldSession::HandleSuspendTokenResponse(WorldPackets::Movement::SuspendTokenResponse& /*suspendTokenResponse*/) +{ + if (!_player->IsBeingTeleportedFar()) + return; + + WorldLocation const& loc = GetPlayer()->GetTeleportDest(); + + if (sMapStore.AssertEntry(loc.GetMapId())->IsDungeon()) + { + WorldPackets::Instance::UpdateLastInstance updateLastInstance; + updateLastInstance.MapID = loc.GetMapId(); + SendPacket(updateLastInstance.Write()); + } + + WorldPackets::Movement::NewWorld packet; + packet.MapID = loc.GetMapId(); + packet.Pos.Relocate(loc); + packet.Reason = !_player->IsBeingTeleportedSeamlessly() ? NEW_WORLD_NORMAL : NEW_WORLD_SEAMLESS; + SendPacket(packet.Write()); + + if (_player->IsBeingTeleportedSeamlessly()) + HandleMoveWorldportAckOpcode(); +} + void WorldSession::HandleMoveTeleportAck(WorldPackets::Movement::MoveTeleportAck& packet) { TC_LOG_DEBUG("network", "CMSG_MOVE_TELEPORT_ACK: Guid: %s, Sequence: %u, Time: %u", packet.MoverGUID.ToString().c_str(), packet.AckIndex, packet.MoveTime); diff --git a/src/server/game/Server/Packets/MovementPackets.cpp b/src/server/game/Server/Packets/MovementPackets.cpp index 582a057e09f..6fdad7553a3 100644 --- a/src/server/game/Server/Packets/MovementPackets.cpp +++ b/src/server/game/Server/Packets/MovementPackets.cpp @@ -715,3 +715,26 @@ WorldPacket const* WorldPackets::Movement::SummonRequest::Write() return &_worldPacket; } + +WorldPacket const* WorldPackets::Movement::SuspendToken::Write() +{ + _worldPacket << uint32(SequenceIndex); + _worldPacket.WriteBits(Reason, 2); + _worldPacket.FlushBits(); + + return &_worldPacket; +} + +void WorldPackets::Movement::SuspendTokenResponse::Read() +{ + _worldPacket >> SequenceIndex; +} + +WorldPacket const* WorldPackets::Movement::ResumeToken::Write() +{ + _worldPacket << uint32(SequenceIndex); + _worldPacket.WriteBits(Reason, 2); + _worldPacket.FlushBits(); + + return &_worldPacket; +} diff --git a/src/server/game/Server/Packets/MovementPackets.h b/src/server/game/Server/Packets/MovementPackets.h index 6d97161d9c9..3bce8ed665c 100644 --- a/src/server/game/Server/Packets/MovementPackets.h +++ b/src/server/game/Server/Packets/MovementPackets.h @@ -461,6 +461,38 @@ namespace WorldPackets int32 AreaID = 0; bool SkipStartingArea = false; }; + + class SuspendToken final : public ServerPacket + { + public: + SuspendToken() : ServerPacket(SMSG_SUSPEND_TOKEN, 4 + 1) { } + + WorldPacket const* Write() override; + + uint32 SequenceIndex = 1; + uint32 Reason = 1; + }; + + class SuspendTokenResponse final : public ClientPacket + { + public: + SuspendTokenResponse(WorldPacket&& packet) : ClientPacket(CMSG_SUSPEND_TOKEN_RESPONSE, std::move(packet)) { } + + void Read() override; + + uint32 SequenceIndex = 0; + }; + + class ResumeToken final : public ServerPacket + { + public: + ResumeToken() : ServerPacket(SMSG_RESUME_TOKEN, 4 + 1) { } + + WorldPacket const* Write() override; + + uint32 SequenceIndex = 1; + uint32 Reason = 1; + }; } ByteBuffer& operator<<(ByteBuffer& data, Movement::MonsterSplineFilterKey const& monsterSplineFilterKey); diff --git a/src/server/game/Server/Protocol/Opcodes.cpp b/src/server/game/Server/Protocol/Opcodes.cpp index 7dd7b2dc3e9..a2e4bfe6321 100644 --- a/src/server/game/Server/Protocol/Opcodes.cpp +++ b/src/server/game/Server/Protocol/Opcodes.cpp @@ -732,7 +732,7 @@ void OpcodeTable::Initialize() DEFINE_HANDLER(CMSG_SUPPORT_TICKET_SUBMIT_COMPLAINT, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Ticket::SupportTicketSubmitComplaint, &WorldSession::HandleSupportTicketSubmitComplaint); DEFINE_HANDLER(CMSG_SUPPORT_TICKET_SUBMIT_SUGGESTION, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Ticket::SupportTicketSubmitSuggestion, &WorldSession::HandleSupportTicketSubmitSuggestion); DEFINE_HANDLER(CMSG_SUSPEND_COMMS_ACK, STATUS_UNHANDLED, PROCESS_INPLACE, WorldPackets::Null, &WorldSession::Handle_NULL); - DEFINE_HANDLER(CMSG_SUSPEND_TOKEN_RESPONSE, STATUS_UNHANDLED, PROCESS_INPLACE, WorldPackets::Null, &WorldSession::Handle_NULL); + DEFINE_HANDLER(CMSG_SUSPEND_TOKEN_RESPONSE, STATUS_TRANSFER, PROCESS_THREADUNSAFE, WorldPackets::Movement::SuspendTokenResponse, &WorldSession::HandleSuspendTokenResponse); DEFINE_HANDLER(CMSG_SWAP_INV_ITEM, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Item::SwapInvItem, &WorldSession::HandleSwapInvItemOpcode); DEFINE_HANDLER(CMSG_SWAP_ITEM, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Item::SwapItem, &WorldSession::HandleSwapItem); DEFINE_HANDLER(CMSG_SWAP_SUB_GROUPS, STATUS_LOGGEDIN, PROCESS_INPLACE, WorldPackets::Party::SwapSubGroups, &WorldSession::HandleSwapSubGroupsOpcode); @@ -1534,7 +1534,7 @@ void OpcodeTable::Initialize() DEFINE_SERVER_OPCODE_HANDLER(SMSG_RESPOND_INSPECT_ACHIEVEMENTS, STATUS_NEVER, CONNECTION_TYPE_INSTANCE); DEFINE_SERVER_OPCODE_HANDLER(SMSG_RESUME_CAST_BAR, STATUS_UNHANDLED, CONNECTION_TYPE_REALM); DEFINE_SERVER_OPCODE_HANDLER(SMSG_RESUME_COMMS, STATUS_NEVER, CONNECTION_TYPE_REALM); - DEFINE_SERVER_OPCODE_HANDLER(SMSG_RESUME_TOKEN, STATUS_UNHANDLED, CONNECTION_TYPE_REALM); + DEFINE_SERVER_OPCODE_HANDLER(SMSG_RESUME_TOKEN, STATUS_NEVER, CONNECTION_TYPE_INSTANCE); DEFINE_SERVER_OPCODE_HANDLER(SMSG_RESURRECT_REQUEST, STATUS_NEVER, CONNECTION_TYPE_REALM); DEFINE_SERVER_OPCODE_HANDLER(SMSG_RESYNC_RUNES, STATUS_NEVER, CONNECTION_TYPE_REALM); DEFINE_SERVER_OPCODE_HANDLER(SMSG_ROLE_CHANGED_INFORM, STATUS_NEVER, CONNECTION_TYPE_REALM); @@ -1641,7 +1641,7 @@ void OpcodeTable::Initialize() DEFINE_SERVER_OPCODE_HANDLER(SMSG_SUPERCEDED_SPELLS, STATUS_UNHANDLED, CONNECTION_TYPE_REALM); DEFINE_SERVER_OPCODE_HANDLER(SMSG_SUPPRESS_NPC_GREETINGS, STATUS_UNHANDLED, CONNECTION_TYPE_REALM); DEFINE_SERVER_OPCODE_HANDLER(SMSG_SUSPEND_COMMS, STATUS_UNHANDLED, CONNECTION_TYPE_REALM); - DEFINE_SERVER_OPCODE_HANDLER(SMSG_SUSPEND_TOKEN, STATUS_UNHANDLED, CONNECTION_TYPE_REALM); + DEFINE_SERVER_OPCODE_HANDLER(SMSG_SUSPEND_TOKEN, STATUS_NEVER, CONNECTION_TYPE_INSTANCE); DEFINE_SERVER_OPCODE_HANDLER(SMSG_TALENTS_INVOLUNTARILY_RESET, STATUS_UNHANDLED, CONNECTION_TYPE_REALM); DEFINE_SERVER_OPCODE_HANDLER(SMSG_TAXI_NODE_STATUS, STATUS_NEVER, CONNECTION_TYPE_REALM); DEFINE_SERVER_OPCODE_HANDLER(SMSG_TEXT_EMOTE, STATUS_NEVER, CONNECTION_TYPE_INSTANCE); diff --git a/src/server/game/Server/WorldSession.cpp b/src/server/game/Server/WorldSession.cpp index 59f18bc79b0..8e1a912623e 100644 --- a/src/server/game/Server/WorldSession.cpp +++ b/src/server/game/Server/WorldSession.cpp @@ -336,10 +336,6 @@ bool WorldSession::Update(uint32 diff, PacketFilter& updater) if (IsConnectionIdle()) m_Socket[CONNECTION_TYPE_REALM]->CloseSocket(); - if (updater.ProcessUnsafe()) - while (_player && _player->IsBeingTeleportedSeamlessly()) - HandleMoveWorldportAckOpcode(); - ///- Retrieve packets from the receive queue and call the appropriate handlers /// not process packets if socket already closed WorldPacket* packet = NULL; diff --git a/src/server/game/Server/WorldSession.h b/src/server/game/Server/WorldSession.h index b65a8b30d56..26e8329ee9c 100644 --- a/src/server/game/Server/WorldSession.h +++ b/src/server/game/Server/WorldSession.h @@ -442,6 +442,7 @@ namespace WorldPackets class MoveTimeSkipped; class SummonResponse; class MoveSplineDone; + class SuspendTokenResponse; } namespace NPC @@ -1243,6 +1244,7 @@ class TC_GAME_API WorldSession void HandleMoveWorldportAckOpcode(WorldPackets::Movement::WorldPortResponse& packet); void HandleMoveWorldportAckOpcode(); // for server-side calls + void HandleSuspendTokenResponse(WorldPackets::Movement::SuspendTokenResponse& suspendTokenResponse); void HandleMovementOpcodes(WorldPackets::Movement::ClientPlayerMovement& packet); void HandleSetActiveMoverOpcode(WorldPackets::Movement::SetActiveMover& packet); |