fix(Core/Movement): rework root protocol with ack in mind (#23147)

This commit is contained in:
killerwife
2025-10-11 18:49:43 +02:00
committed by GitHub
parent bc89aa561c
commit 31b11d0d11
10 changed files with 86 additions and 143 deletions
@@ -1164,8 +1164,11 @@ void WorldSession::HandlePlayerLoginToCharInWorld(Player* pCurrChar)
SendPacket(&data);
// Xinef: fix possible problem with flag UNIT_FLAG_STUNNED added during logout
if (!pCurrChar->HasUnitState(UNIT_STATE_STUNNED))
if (pCurrChar->HasUnitState(UNIT_STATE_LOGOUT_TIMER))
{
pCurrChar->SetRooted(false, true, true);
pCurrChar->RemoveUnitFlag(UNIT_FLAG_STUNNED);
}
pCurrChar->SendInitialPacketsBeforeAddToMap();
+2 -2
View File
@@ -468,7 +468,7 @@ void WorldSession::HandleLogoutRequestOpcode(WorldPackets::Character::LogoutRequ
GetPlayer()->SetStandState(UNIT_STAND_STATE_SIT);
}
GetPlayer()->SetRooted(true);
GetPlayer()->SetRooted(true, true, true);
GetPlayer()->SetUnitFlag(UNIT_FLAG_STUNNED);
}
@@ -492,7 +492,7 @@ void WorldSession::HandleLogoutCancelOpcode(WorldPackets::Character::LogoutCance
// not remove flags if can't free move - its not set in Logout request code.
if (GetPlayer()->CanFreeMove())
{
GetPlayer()->SetRooted(false);
GetPlayer()->SetRooted(false, true, true);
GetPlayer()->SetStandState(UNIT_STAND_STATE_STAND);
GetPlayer()->RemoveUnitFlag(UNIT_FLAG_STUNNED);
+19 -62
View File
@@ -967,79 +967,36 @@ void WorldSession::ComputeNewClockDelta()
void WorldSession::HandleMoveRootAck(WorldPacket& recvData)
{
LOG_DEBUG("network", "WORLD: {}", GetOpcodeNameForLogging((Opcodes)recvData.GetOpcode()));
ObjectGuid guid;
recvData >> guid.ReadAsPacked();
Unit* mover = _player->m_mover;
if (!mover || guid != mover->GetGUID())
{
recvData.rfinish(); // prevent warnings spam
return;
}
uint32 movementCounter;
recvData >> movementCounter;
uint32 counter;
MovementInfo movementInfo;
movementInfo.guid = guid;
recvData >> guid.ReadAsPacked();
recvData >> counter;
ReadMovementInfo(recvData, &movementInfo);
/* process position-change */
int64 movementTime = (int64) movementInfo.time + _timeSyncClockDelta;
if (_timeSyncClockDelta == 0 || movementTime < 0 || movementTime > 0xFFFFFFFF)
{
LOG_INFO("misc", "The computed movement time using clockDelta is erronous. Using fallback instead");
movementInfo.time = getMSTime();
}
else
{
movementInfo.time = (uint32)movementTime;
}
movementInfo.guid = mover->GetGUID();
mover->m_movementInfo = movementInfo;
mover->UpdatePosition(movementInfo.pos);
}
void WorldSession::HandleMoveUnRootAck(WorldPacket& recvData)
{
ObjectGuid guid;
recvData >> guid.ReadAsPacked();
Unit* mover = _player->m_mover;
if (!mover || guid != mover->GetGUID())
{
recvData.rfinish(); // prevent warnings spam
if (mover->GetGUID() != guid)
return;
}
uint32 movementCounter;
recvData >> movementCounter;
MovementInfo movementInfo;
movementInfo.guid = guid;
ReadMovementInfo(recvData, &movementInfo);
/* process position-change */
int64 movementTime = (int64) movementInfo.time + _timeSyncClockDelta;
if (_timeSyncClockDelta == 0 || movementTime < 0 || movementTime > 0xFFFFFFFF)
if (recvData.GetOpcode() == CMSG_FORCE_MOVE_UNROOT_ACK) // unroot case
{
LOG_INFO("misc", "The computed movement time using clockDelta is erronous. Using fallback instead");
movementInfo.time = getMSTime();
if (!mover->m_movementInfo.HasMovementFlag(MOVEMENTFLAG_ROOT))
return;
}
else
else // root case
{
movementInfo.time = (uint32)movementTime;
if (mover->m_movementInfo.HasMovementFlag(MOVEMENTFLAG_ROOT))
return;
}
if (G3D::fuzzyEq(movementInfo.fallTime, 0.f))
{
movementInfo.RemoveMovementFlag(MOVEMENTFLAG_FALLING);
}
movementInfo.guid = mover->GetGUID();
mover->m_movementInfo = movementInfo;
mover->UpdatePosition(movementInfo.pos);
if (!ProcessMovementInfo(movementInfo, mover, _player, recvData))
return;
WorldPacket data(recvData.GetOpcode() == CMSG_FORCE_MOVE_UNROOT_ACK ? MSG_MOVE_UNROOT : MSG_MOVE_ROOT);
data << guid.WriteAsPacked();
WriteMovementInfo(&data, &movementInfo);
mover->SendMessageToSet(&data, _player);
}