fix(Core): creature movement bugs (#4544)
- fix UpdateEnvironmentIfNeeded was changing flying creature status all the time. closes: #4447 - fix hovering state was causing bugs at #4466 - add animation state priority: fly > hover > ground Co-authored-by: Wotex <fm@gmail.com> Co-authored-by: Francesco Borzì <borzifrancesco@gmail.com> Co-authored-by: Patrick Lewis <pat@lo5t.com>
This commit is contained in:
@@ -0,0 +1,3 @@
|
|||||||
|
INSERT INTO `version_db_world` (`sql_rev`) VALUES ('1613069340138846000');
|
||||||
|
|
||||||
|
UPDATE `creature_template` SET `InhabitType`=1 WHERE `entry`=36725;
|
||||||
@@ -2758,6 +2758,8 @@ bool Creature::SetDisableGravity(bool disable, bool packetOnly/*=false*/)
|
|||||||
if (!packetOnly && !Unit::SetDisableGravity(disable))
|
if (!packetOnly && !Unit::SetDisableGravity(disable))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
|
applyInhabitFlags();
|
||||||
|
|
||||||
if (!movespline->Initialized())
|
if (!movespline->Initialized())
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
@@ -2767,6 +2769,26 @@ bool Creature::SetDisableGravity(bool disable, bool packetOnly/*=false*/)
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Creature::applyInhabitFlags()
|
||||||
|
{
|
||||||
|
if (IsAlive() && !HasUnitState(UNIT_STATE_ROOT) && !HasUnitMovementFlag(MOVEMENTFLAG_ROOT))
|
||||||
|
{
|
||||||
|
if (IsLevitating())
|
||||||
|
{
|
||||||
|
SetByteValue(UNIT_FIELD_BYTES_1, UNIT_BYTES_1_OFFSET_ANIM_TIER, UNIT_BYTE1_FLAG_FLY);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (IsHovering())
|
||||||
|
{
|
||||||
|
SetByteValue(UNIT_FIELD_BYTES_1, UNIT_BYTES_1_OFFSET_ANIM_TIER, UNIT_BYTE1_FLAG_HOVER);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
SetByteValue(UNIT_FIELD_BYTES_1, UNIT_BYTES_1_OFFSET_ANIM_TIER, UNIT_BYTE1_FLAG_GROUND);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool Creature::SetSwim(bool enable)
|
bool Creature::SetSwim(bool enable)
|
||||||
{
|
{
|
||||||
if (!Unit::SetSwim(enable))
|
if (!Unit::SetSwim(enable))
|
||||||
@@ -2873,11 +2895,7 @@ bool Creature::SetHover(bool enable, bool packetOnly /*= false*/)
|
|||||||
if (!packetOnly && !Unit::SetHover(enable))
|
if (!packetOnly && !Unit::SetHover(enable))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
//! Unconfirmed for players:
|
applyInhabitFlags();
|
||||||
if (enable)
|
|
||||||
SetByteFlag(UNIT_FIELD_BYTES_1, UNIT_BYTES_1_OFFSET_ANIM_TIER, UNIT_BYTE1_FLAG_HOVER);
|
|
||||||
else
|
|
||||||
RemoveByteFlag(UNIT_FIELD_BYTES_1, UNIT_BYTES_1_OFFSET_ANIM_TIER, UNIT_BYTE1_FLAG_HOVER);
|
|
||||||
|
|
||||||
if (!movespline->Initialized())
|
if (!movespline->Initialized())
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
@@ -832,6 +832,8 @@ private:
|
|||||||
Spell const* _focusSpell; ///> Locks the target during spell cast for proper facing
|
Spell const* _focusSpell; ///> Locks the target during spell cast for proper facing
|
||||||
|
|
||||||
bool _isMissingSwimmingFlagOutOfCombat;
|
bool _isMissingSwimmingFlagOutOfCombat;
|
||||||
|
|
||||||
|
void applyInhabitFlags();
|
||||||
};
|
};
|
||||||
|
|
||||||
class AssistDelayEvent : public BasicEvent
|
class AssistDelayEvent : public BasicEvent
|
||||||
|
|||||||
@@ -3816,28 +3816,39 @@ void Unit::UpdateEnvironmentIfNeeded(const uint8 option)
|
|||||||
changed = true;
|
changed = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (c->CanFly() && isInAir)
|
else if (c->CanFly() && isInAir && !c->IsFalling())
|
||||||
{
|
{
|
||||||
if (!c->IsFalling() && (!HasUnitMovementFlag(MOVEMENTFLAG_CAN_FLY) || !HasUnitMovementFlag(MOVEMENTFLAG_DISABLE_GRAVITY) || !HasUnitMovementFlag(MOVEMENTFLAG_HOVER)))
|
|
||||||
|
if (!HasUnitMovementFlag(MOVEMENTFLAG_CAN_FLY) || !HasUnitMovementFlag(MOVEMENTFLAG_DISABLE_GRAVITY))
|
||||||
{
|
{
|
||||||
SetCanFly(true);
|
SetCanFly(true);
|
||||||
SetDisableGravity(true);
|
SetDisableGravity(true);
|
||||||
if (IsAlive() && (c->CanHover() || HasAuraType(SPELL_AURA_HOVER)))
|
|
||||||
SetHover(true);
|
|
||||||
changed = true;
|
changed = true;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
else
|
if (IsHovering() && !HasAuraType(SPELL_AURA_HOVER))
|
||||||
{
|
{
|
||||||
if (HasUnitMovementFlag(MOVEMENTFLAG_CAN_FLY) || HasUnitMovementFlag(MOVEMENTFLAG_FLYING) || HasUnitMovementFlag(MOVEMENTFLAG_HOVER))
|
|
||||||
{
|
|
||||||
SetCanFly(false);
|
|
||||||
RemoveUnitMovementFlag(MOVEMENTFLAG_FLYING);
|
|
||||||
if (!HasAuraType(SPELL_AURA_HOVER))
|
|
||||||
SetHover(false);
|
SetHover(false);
|
||||||
changed = true;
|
changed = true;
|
||||||
}
|
}
|
||||||
if (HasUnitMovementFlag(MOVEMENTFLAG_DISABLE_GRAVITY) && !HasUnitMovementFlag(MOVEMENTFLAG_SWIMMING) && !HasUnitMovementFlag(MOVEMENTFLAG_HOVER))
|
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (HasUnitMovementFlag(MOVEMENTFLAG_CAN_FLY) || HasUnitMovementFlag(MOVEMENTFLAG_FLYING))
|
||||||
|
{
|
||||||
|
SetCanFly(false);
|
||||||
|
RemoveUnitMovementFlag(MOVEMENTFLAG_FLYING);
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!IsHovering() && IsAlive() && (c->CanHover() || HasAuraType(SPELL_AURA_HOVER)))
|
||||||
|
{
|
||||||
|
SetHover(true);
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (HasUnitMovementFlag(MOVEMENTFLAG_DISABLE_GRAVITY) && !HasUnitMovementFlag(MOVEMENTFLAG_SWIMMING))
|
||||||
{
|
{
|
||||||
SetDisableGravity(false);
|
SetDisableGravity(false);
|
||||||
changed = true;
|
changed = true;
|
||||||
|
|||||||
@@ -282,7 +282,6 @@ public:
|
|||||||
if (!_summoned)
|
if (!_summoned)
|
||||||
{
|
{
|
||||||
me->SetDisableGravity(true);
|
me->SetDisableGravity(true);
|
||||||
me->SetHover(true);
|
|
||||||
me->SetCanFly(true);
|
me->SetCanFly(true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -355,7 +354,6 @@ public:
|
|||||||
if (_summoned)
|
if (_summoned)
|
||||||
{
|
{
|
||||||
me->SetDisableGravity(false);
|
me->SetDisableGravity(false);
|
||||||
me->SetHover(false);
|
|
||||||
me->SetCanFly(false);
|
me->SetCanFly(false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -452,8 +450,8 @@ public:
|
|||||||
break;
|
break;
|
||||||
case POINT_LAND_GROUND:
|
case POINT_LAND_GROUND:
|
||||||
{
|
{
|
||||||
|
_isInAirPhase = false;
|
||||||
me->SetDisableGravity(false);
|
me->SetDisableGravity(false);
|
||||||
me->SetHover(false);
|
|
||||||
me->SetCanFly(false);
|
me->SetCanFly(false);
|
||||||
me->SetSpeed(MOVE_RUN, me->GetCreatureTemplate()->speed_run);
|
me->SetSpeed(MOVE_RUN, me->GetCreatureTemplate()->speed_run);
|
||||||
me->SetReactState(REACT_AGGRESSIVE);
|
me->SetReactState(REACT_AGGRESSIVE);
|
||||||
@@ -594,6 +592,7 @@ public:
|
|||||||
me->SetControlled(false, UNIT_STATE_ROOT);
|
me->SetControlled(false, UNIT_STATE_ROOT);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_isInAirPhase = true;
|
||||||
_didFirstFlyPhase = true;
|
_didFirstFlyPhase = true;
|
||||||
Talk(SAY_AIR_PHASE);
|
Talk(SAY_AIR_PHASE);
|
||||||
me->SetReactState(REACT_PASSIVE);
|
me->SetReactState(REACT_PASSIVE);
|
||||||
@@ -659,7 +658,7 @@ public:
|
|||||||
me->GetMotionMaster()->MoveLand(POINT_LAND_GROUND, SindragosaLandPos, 10.0f);
|
me->GetMotionMaster()->MoveLand(POINT_LAND_GROUND, SindragosaLandPos, 10.0f);
|
||||||
break;
|
break;
|
||||||
case EVENT_THIRD_PHASE_CHECK:
|
case EVENT_THIRD_PHASE_CHECK:
|
||||||
if (!me->HasByteFlag(UNIT_FIELD_BYTES_1, UNIT_BYTES_1_OFFSET_ANIM_TIER, UNIT_BYTE1_FLAG_HOVER))
|
if (!_isInAirPhase)
|
||||||
{
|
{
|
||||||
Talk(SAY_PHASE_2);
|
Talk(SAY_PHASE_2);
|
||||||
events.ScheduleEvent(EVENT_ICE_TOMB, urand(7000, 10000));
|
events.ScheduleEvent(EVENT_ICE_TOMB, urand(7000, 10000));
|
||||||
@@ -697,6 +696,7 @@ public:
|
|||||||
bool _didFirstFlyPhase;
|
bool _didFirstFlyPhase;
|
||||||
bool _isBelow20Pct;
|
bool _isBelow20Pct;
|
||||||
bool _isThirdPhase;
|
bool _isThirdPhase;
|
||||||
|
bool _isInAirPhase;
|
||||||
};
|
};
|
||||||
|
|
||||||
CreatureAI* GetAI(Creature* creature) const override
|
CreatureAI* GetAI(Creature* creature) const override
|
||||||
|
|||||||
@@ -3316,8 +3316,6 @@ public:
|
|||||||
npc_icc_nerubar_broodkeeperAI(Creature* creature) : ScriptedAI(creature)
|
npc_icc_nerubar_broodkeeperAI(Creature* creature) : ScriptedAI(creature)
|
||||||
{
|
{
|
||||||
me->SetDisableGravity(true);
|
me->SetDisableGravity(true);
|
||||||
me->SetCanFly(true);
|
|
||||||
me->SetHover(true);
|
|
||||||
_didWebBeam = false;
|
_didWebBeam = false;
|
||||||
me->m_SightDistance = 100.0f; // for MoveInLineOfSight distance
|
me->m_SightDistance = 100.0f; // for MoveInLineOfSight distance
|
||||||
}
|
}
|
||||||
@@ -3338,16 +3336,18 @@ public:
|
|||||||
if (!_didWebBeam && who->GetTypeId() == TYPEID_PLAYER && me->GetExactDist2d(who) < 70.0f)
|
if (!_didWebBeam && who->GetTypeId() == TYPEID_PLAYER && me->GetExactDist2d(who) < 70.0f)
|
||||||
{
|
{
|
||||||
_didWebBeam = true;
|
_didWebBeam = true;
|
||||||
float nx = me->GetPositionX() + cos(me->GetOrientation()) * 2.0f;
|
float nx = me->GetPositionX();
|
||||||
float ny = me->GetPositionY() + sin(me->GetOrientation()) * 2.0f;
|
float ny = me->GetPositionY();
|
||||||
float nz = me->GetMap()->GetHeight(nx, ny, 50.0f);
|
float nz = me->GetFloorZ();
|
||||||
me->SetHomePosition(nx, ny, nz, me->GetOrientation());
|
me->SetHomePosition(nx, ny, nz, me->GetOrientation());
|
||||||
me->CastSpell(me, SPELL_WEB_BEAM, false);
|
me->CastSpell(me, SPELL_WEB_BEAM, false);
|
||||||
me->GetMotionMaster()->MovePoint(1, nx, ny, nz, false);
|
me->GetMotionMaster()->MovePoint(1, nx, ny, nz, false);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (me->HasUnitMovementFlag(MOVEMENTFLAG_CAN_FLY))
|
|
||||||
|
if (me->IsLevitating())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
ScriptedAI::MoveInLineOfSight(who);
|
ScriptedAI::MoveInLineOfSight(who);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -3358,11 +3358,9 @@ public:
|
|||||||
|
|
||||||
void JustReachedHome() override
|
void JustReachedHome() override
|
||||||
{
|
{
|
||||||
if (me->IsHovering())
|
if (me->IsLevitating())
|
||||||
{
|
{
|
||||||
me->SetDisableGravity(false);
|
me->SetDisableGravity(false);
|
||||||
me->SetCanFly(false);
|
|
||||||
me->SetHover(false);
|
|
||||||
me->NearTeleportTo(me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(), me->GetOrientation());
|
me->NearTeleportTo(me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(), me->GetOrientation());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -3371,11 +3369,10 @@ public:
|
|||||||
{
|
{
|
||||||
if (type == POINT_MOTION_TYPE && id == 1)
|
if (type == POINT_MOTION_TYPE && id == 1)
|
||||||
{
|
{
|
||||||
if (me->IsHovering())
|
if (me->IsLevitating())
|
||||||
{
|
{
|
||||||
me->SetDisableGravity(false);
|
me->SetDisableGravity(false);
|
||||||
me->SetCanFly(false);
|
me->SetOrientation(0.0f);
|
||||||
me->SetHover(false);
|
|
||||||
me->NearTeleportTo(me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(), me->GetOrientation());
|
me->NearTeleportTo(me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(), me->GetOrientation());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -3383,7 +3380,7 @@ public:
|
|||||||
|
|
||||||
bool CanAIAttack(const Unit* /*target*/) const override
|
bool CanAIAttack(const Unit* /*target*/) const override
|
||||||
{
|
{
|
||||||
return !me->HasUnitMovementFlag(MOVEMENTFLAG_CAN_FLY);
|
return !me->IsLevitating();
|
||||||
}
|
}
|
||||||
|
|
||||||
void UpdateAI(uint32 diff) override
|
void UpdateAI(uint32 diff) override
|
||||||
|
|||||||
Reference in New Issue
Block a user