aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorariel- <ariel-@users.noreply.github.com>2018-02-20 17:27:02 -0300
committerariel- <ariel-@users.noreply.github.com>2018-02-20 17:34:12 -0300
commitba27711145d1b015578aedb48ea8532b4f0bec75 (patch)
treea6d2b520e9966ca3d618688166fd987e9ad0ab59
parent1cc3d33cfe7e51d66925d5df536a952165a88094 (diff)
Core/Entities: unit states cleanup
- Added new UNIT_STATE_FOCUSING for creature focus system, this will stop creatures adding/clearing the UNIT_STATE_CANNOT_TURN mask (eg UNIT_STATE_STUNNED if stunned while focusing a spell) - Added UNIT_STATE_CHARMED that gets set/removed on any charm type (UNIT_STATE_POSSESSED is only for possess as it's name suggests) - The new states are checked against mask to know whenever client needs to regain character control Closes and fixes #21460
-rw-r--r--src/server/game/Entities/Creature/Creature.cpp4
-rw-r--r--src/server/game/Entities/Player/Player.cpp4
-rw-r--r--src/server/game/Entities/Unit/Unit.cpp52
-rw-r--r--src/server/game/Entities/Unit/Unit.h16
4 files changed, 45 insertions, 31 deletions
diff --git a/src/server/game/Entities/Creature/Creature.cpp b/src/server/game/Entities/Creature/Creature.cpp
index 34cffce71c6..c142fcf91f4 100644
--- a/src/server/game/Entities/Creature/Creature.cpp
+++ b/src/server/game/Entities/Creature/Creature.cpp
@@ -3089,7 +3089,7 @@ void Creature::FocusTarget(Spell const* focusSpell, WorldObject const* target)
}
if (noTurnDuringCast)
- AddUnitState(UNIT_STATE_CANNOT_TURN);
+ AddUnitState(UNIT_STATE_FOCUSING);
}
bool Creature::IsFocusing(Spell const* focusSpell, bool withDelay)
@@ -3143,7 +3143,7 @@ void Creature::ReleaseFocus(Spell const* focusSpell, bool withDelay)
MustReacquireTarget();
if (m_focusSpell->GetSpellInfo()->HasAttribute(SPELL_ATTR5_DONT_TURN_DURING_CAST))
- ClearUnitState(UNIT_STATE_CANNOT_TURN);
+ ClearUnitState(UNIT_STATE_FOCUSING);
m_focusSpell = nullptr;
m_focusDelay = (!IsPet() && withDelay) ? GameTime::GetGameTimeMS() : 0; // don't allow re-target right away to prevent visual bugs
diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp
index 6874c6a1f77..0eebe6d823a 100644
--- a/src/server/game/Entities/Player/Player.cpp
+++ b/src/server/game/Entities/Player/Player.cpp
@@ -23756,6 +23756,10 @@ void Player::ResurrectUsingRequestDataImpl()
void Player::SetClientControl(Unit* target, bool allowMove)
{
+ // still affected by some aura that shouldn't allow control, only allow on last such aura to be removed
+ if (allowMove && target->HasUnitState(UNIT_STATE_CANT_CLIENT_CONTROL))
+ return;
+
WorldPacket data(SMSG_CLIENT_CONTROL_UPDATE, target->GetPackGUID().size()+1);
data << target->GetPackGUID();
data << uint8(allowMove ? 1 : 0);
diff --git a/src/server/game/Entities/Unit/Unit.cpp b/src/server/game/Entities/Unit/Unit.cpp
index bc9c1bd2789..a919a322b6d 100644
--- a/src/server/game/Entities/Unit/Unit.cpp
+++ b/src/server/game/Entities/Unit/Unit.cpp
@@ -12026,19 +12026,24 @@ void Unit::SetControlled(bool apply, UnitState state)
return;
}
- // Unit States might have been already cleared but auras still present. I need to check with HasAuraType
- if (HasAuraType(SPELL_AURA_MOD_STUN))
- SetStunned(true);
+ ApplyControlStatesIfNeeded();
+ }
+}
+
+void Unit::ApplyControlStatesIfNeeded()
+{
+ // Unit States might have been already cleared but auras still present. I need to check with HasAuraType
+ if (HasUnitState(UNIT_STATE_STUNNED) || HasAuraType(SPELL_AURA_MOD_STUN))
+ SetStunned(true);
- if (HasAuraType(SPELL_AURA_MOD_ROOT))
- SetRooted(true);
+ if (HasUnitState(UNIT_STATE_ROOT) || HasAuraType(SPELL_AURA_MOD_ROOT))
+ SetRooted(true);
- if (HasAuraType(SPELL_AURA_MOD_CONFUSE))
- SetConfused(true);
+ if (HasUnitState(UNIT_STATE_CONFUSED) || HasAuraType(SPELL_AURA_MOD_CONFUSE))
+ SetConfused(true);
- if (HasAuraType(SPELL_AURA_MOD_FEAR))
- SetFeared(true);
- }
+ if (HasUnitState(UNIT_STATE_FLEEING) || HasAuraType(SPELL_AURA_MOD_FEAR))
+ SetFeared(true);
}
void Unit::SetStunned(bool apply)
@@ -12163,12 +12168,11 @@ void Unit::SetFeared(bool apply)
}
}
- if (Player* player = ToPlayer())
+ // block / allow control to real player in control (eg charmer)
+ if (GetTypeId() == TYPEID_PLAYER)
{
- if (apply)
- player->SetClientControl(this, false);
- else if (!HasUnitState(UNIT_STATE_LOST_CONTROL))
- player->SetClientControl(this, true);
+ if (m_playerMovingMe)
+ m_playerMovingMe->SetClientControl(this, !apply);
}
}
@@ -12190,12 +12194,11 @@ void Unit::SetConfused(bool apply)
}
}
- if (Player* player = ToPlayer())
+ // block / allow control to real player in control (eg charmer)
+ if (GetTypeId() == TYPEID_PLAYER)
{
- if (apply)
- player->SetClientControl(this, false);
- else if (!HasUnitState(UNIT_STATE_LOST_CONTROL))
- player->SetClientControl(this, true);
+ if (m_playerMovingMe)
+ m_playerMovingMe->SetClientControl(this, !apply);
}
}
@@ -12359,6 +12362,8 @@ bool Unit::SetCharmedBy(Unit* charmer, CharmType type, AuraApplication const* au
break;
}
}
+
+ AddUnitState(UNIT_STATE_CHARMED);
return true;
}
@@ -12464,8 +12469,7 @@ void Unit::RemoveCharmedBy(Unit* charmer)
IsAIEnabled = false;
}
- if (!HasUnitState(UNIT_STATE_LOST_CONTROL))
- player->SetClientControl(this, true);
+ player->SetClientControl(this, true);
}
EngageWithTarget(charmer);
@@ -12475,6 +12479,10 @@ void Unit::RemoveCharmedBy(Unit* charmer)
playerCharmer->SendRemoveControlBar();
else if (GetTypeId() == TYPEID_PLAYER || (GetTypeId() == TYPEID_UNIT && !IsGuardian()))
DeleteCharmInfo();
+
+ // reset confused movement for example
+ ApplyControlStatesIfNeeded();
+ ClearUnitState(UNIT_STATE_CHARMED);
}
void Unit::RestoreFaction()
diff --git a/src/server/game/Entities/Unit/Unit.h b/src/server/game/Entities/Unit/Unit.h
index d4e52edf7ec..16c9e87afee 100644
--- a/src/server/game/Entities/Unit/Unit.h
+++ b/src/server/game/Entities/Unit/Unit.h
@@ -211,11 +211,11 @@ enum UnitState : uint32
{
UNIT_STATE_DIED = 0x00000001, // player has fake death aura
UNIT_STATE_MELEE_ATTACKING = 0x00000002, // player is melee attacking someone
- //UNIT_STATE_MELEE_ATTACK_BY = 0x00000004, // player is melee attack by someone
+ UNIT_STATE_CHARMED = 0x00000004, // having any kind of charm aura on self
UNIT_STATE_STUNNED = 0x00000008,
UNIT_STATE_ROAMING = 0x00000010,
UNIT_STATE_CHASE = 0x00000020,
- //UNIT_STATE_SEARCHING = 0x00000040,
+ UNIT_STATE_FOCUSING = 0x00000040,
UNIT_STATE_FLEEING = 0x00000080,
UNIT_STATE_IN_FLIGHT = 0x00000100, // player is in flight mode
UNIT_STATE_FOLLOW = 0x00000200,
@@ -225,7 +225,7 @@ enum UnitState : uint32
UNIT_STATE_ISOLATED = 0x00002000, // area auras do not affect other players
UNIT_STATE_ATTACK_PLAYER = 0x00004000,
UNIT_STATE_CASTING = 0x00008000,
- UNIT_STATE_POSSESSED = 0x00010000,
+ UNIT_STATE_POSSESSED = 0x00010000, // being possessed by another unit
UNIT_STATE_CHARGING = 0x00020000,
UNIT_STATE_JUMPING = 0x00040000,
UNIT_STATE_MOVE = 0x00100000,
@@ -238,8 +238,8 @@ enum UnitState : uint32
UNIT_STATE_FOLLOW_MOVE = 0x08000000,
UNIT_STATE_IGNORE_PATHFINDING = 0x10000000, // do not use pathfinding in any MovementGenerator
- UNIT_STATE_ALL_STATE_SUPPORTED = UNIT_STATE_DIED | UNIT_STATE_MELEE_ATTACKING | UNIT_STATE_STUNNED | UNIT_STATE_ROAMING | UNIT_STATE_CHASE
- | UNIT_STATE_FLEEING | UNIT_STATE_IN_FLIGHT | UNIT_STATE_FOLLOW | UNIT_STATE_ROOT | UNIT_STATE_CONFUSED
+ UNIT_STATE_ALL_STATE_SUPPORTED = UNIT_STATE_DIED | UNIT_STATE_MELEE_ATTACKING | UNIT_STATE_CHARMED | UNIT_STATE_STUNNED | UNIT_STATE_ROAMING | UNIT_STATE_CHASE
+ | UNIT_STATE_FOCUSING | UNIT_STATE_FLEEING | UNIT_STATE_IN_FLIGHT | UNIT_STATE_FOLLOW | UNIT_STATE_ROOT | UNIT_STATE_CONFUSED
| UNIT_STATE_DISTRACTED | UNIT_STATE_ISOLATED | UNIT_STATE_ATTACK_PLAYER | UNIT_STATE_CASTING
| UNIT_STATE_POSSESSED | UNIT_STATE_CHARGING | UNIT_STATE_JUMPING | UNIT_STATE_MOVE | UNIT_STATE_ROTATING
| UNIT_STATE_EVADE | UNIT_STATE_ROAMING_MOVE | UNIT_STATE_CONFUSED_MOVE | UNIT_STATE_FLEEING_MOVE
@@ -248,10 +248,11 @@ enum UnitState : uint32
UNIT_STATE_UNATTACKABLE = UNIT_STATE_IN_FLIGHT,
UNIT_STATE_MOVING = UNIT_STATE_ROAMING_MOVE | UNIT_STATE_CONFUSED_MOVE | UNIT_STATE_FLEEING_MOVE | UNIT_STATE_CHASE_MOVE | UNIT_STATE_FOLLOW_MOVE,
UNIT_STATE_CONTROLLED = UNIT_STATE_CONFUSED | UNIT_STATE_STUNNED | UNIT_STATE_FLEEING,
+ UNIT_STATE_CANT_CLIENT_CONTROL = UNIT_STATE_CONFUSED | UNIT_STATE_CHARMED | UNIT_STATE_POSSESSED | UNIT_STATE_FLEEING | UNIT_STATE_POSSESSED,
UNIT_STATE_LOST_CONTROL = UNIT_STATE_CONTROLLED | UNIT_STATE_POSSESSED | UNIT_STATE_JUMPING | UNIT_STATE_CHARGING,
+ UNIT_STATE_CANNOT_AUTOATTACK = UNIT_STATE_CONTROLLED | UNIT_STATE_CHARGING | UNIT_STATE_CASTING,
UNIT_STATE_SIGHTLESS = UNIT_STATE_LOST_CONTROL | UNIT_STATE_EVADE,
- UNIT_STATE_CANNOT_AUTOATTACK = UNIT_STATE_LOST_CONTROL | UNIT_STATE_CASTING,
- UNIT_STATE_CANNOT_TURN = UNIT_STATE_LOST_CONTROL | UNIT_STATE_ROTATING,
+ UNIT_STATE_CANNOT_TURN = UNIT_STATE_LOST_CONTROL | UNIT_STATE_ROTATING | UNIT_STATE_FOCUSING,
UNIT_STATE_NOT_MOVE = UNIT_STATE_ROOT | UNIT_STATE_STUNNED | UNIT_STATE_DIED | UNIT_STATE_DISTRACTED,
UNIT_STATE_ALL_ERASABLE = UNIT_STATE_ALL_STATE_SUPPORTED & ~(UNIT_STATE_IGNORE_PATHFINDING),
@@ -1596,6 +1597,7 @@ class TC_GAME_API Unit : public WorldObject
float GetPositionZMinusOffset() const;
void SetControlled(bool apply, UnitState state);
+ void ApplyControlStatesIfNeeded();
///-----------Combo point system-------------------
// This unit having CP on other units