diff options
author | Treeston <treeston.mmoc@gmail.com> | 2018-05-04 10:36:56 +0200 |
---|---|---|
committer | Shauren <shauren.trinity@gmail.com> | 2021-09-26 16:07:40 +0200 |
commit | 4634cfaa9f1e7064147f2c81a146234405f4e121 (patch) | |
tree | 84b2a0c425dcb7031ab3d132422c6f0f991cf0ed /src | |
parent | f1ac141f25500a0f6ffd3c32b1185de2d9f9c940 (diff) |
Core/Threat: Fix taunt behavior in some edge cases
(cherry picked from commit 1b7ec4bc841cd51e17bb21a3d4b774102f195c46)
Diffstat (limited to 'src')
-rw-r--r-- | src/server/game/Combat/ThreatManager.cpp | 56 | ||||
-rw-r--r-- | src/server/game/Combat/ThreatManager.h | 8 |
2 files changed, 33 insertions, 31 deletions
diff --git a/src/server/game/Combat/ThreatManager.cpp b/src/server/game/Combat/ThreatManager.cpp index d6c744dd43b..d9f3d0d4b4b 100644 --- a/src/server/game/Combat/ThreatManager.cpp +++ b/src/server/game/Combat/ThreatManager.cpp @@ -106,26 +106,28 @@ ThreatReference::OnlineState ThreatReference::SelectOnlineState() return ONLINE_STATE_ONLINE; } -void ThreatReference::UpdateTauntState(bool victimIsTaunting) +void ThreatReference::UpdateTauntState(TauntState state) { - if (victimIsTaunting) + if (state < TAUNT_STATE_TAUNT) // not taunting { - _taunted = TAUNT_STATE_TAUNT; - HeapNotifyIncreased(); - return; + // Check for SPELL_AURA_MOD_DETAUNT (applied from owner to victim) + for (AuraEffect const* eff : _victim->GetAuraEffectsByType(SPELL_AURA_MOD_DETAUNT)) + if (eff->GetCasterGUID() == _owner->GetGUID()) + { + state = TAUNT_STATE_DETAUNT; + break; + } } - // Check for SPELL_AURA_MOD_DETAUNT (applied from owner to victim) - for (AuraEffect const* eff : _victim->GetAuraEffectsByType(SPELL_AURA_MOD_DETAUNT)) - if (eff->GetCasterGUID() == _owner->GetGUID()) - { - _taunted = TAUNT_STATE_DETAUNT; - HeapNotifyDecreased(); - return; - } + if (state == _taunted) + return; + + std::swap(state, _taunted); - _taunted = TAUNT_STATE_NONE; - HeapNotifyChanged(); + if (_taunted < state) + HeapNotifyDecreased(); + else + HeapNotifyIncreased(); } void ThreatReference::ClearThreat(bool sendRemove) @@ -422,21 +424,21 @@ void ThreatManager::MatchUnitThreatToHighestThreat(Unit* target) void ThreatManager::TauntUpdate() { std::list<AuraEffect*> const& tauntEffects = _owner->GetAuraEffectsByType(SPELL_AURA_MOD_TAUNT); - auto threatEnd = _myThreatListEntries.end(); - ThreatReference* tauntRef = nullptr; + + uint32 state = ThreatReference::TAUNT_STATE_TAUNT; + std::unordered_map<ObjectGuid, ThreatReference::TauntState> tauntStates; // Only the last taunt effect applied by something still on our threat list is considered - for (auto it = tauntEffects.rbegin(), end = tauntEffects.rend(); it != end; ++it) + for (auto it = tauntEffects.begin(), end = tauntEffects.end(); it != end; ++it) + tauntStates[(*it)->GetCasterGUID()] = ThreatReference::TauntState(state++); + + for (auto const& pair : _myThreatListEntries) { - auto threatIt = _myThreatListEntries.find((*it)->GetCasterGUID()); - if (threatIt == threatEnd) - continue; - if (!threatIt->second->IsAvailable()) - continue; - tauntRef = threatIt->second; - break; + auto it = tauntStates.find(pair.first); + if (it != tauntStates.end()) + pair.second->UpdateTauntState(it->second); + else + pair.second->UpdateTauntState(); } - for (auto const& pair : _myThreatListEntries) - pair.second->UpdateTauntState(pair.second == tauntRef); } void ThreatManager::ResetAllThreat() diff --git a/src/server/game/Combat/ThreatManager.h b/src/server/game/Combat/ThreatManager.h index 09717ff66fb..a10807cb061 100644 --- a/src/server/game/Combat/ThreatManager.h +++ b/src/server/game/Combat/ThreatManager.h @@ -244,7 +244,7 @@ class TC_GAME_API ThreatManager class TC_GAME_API ThreatReference { public: - enum TauntState { TAUNT_STATE_DETAUNT = -1, TAUNT_STATE_NONE = 0, TAUNT_STATE_TAUNT = 1 }; + enum TauntState : uint32 { TAUNT_STATE_DETAUNT = 0, TAUNT_STATE_NONE = 1, TAUNT_STATE_TAUNT = 2 }; enum OnlineState { ONLINE_STATE_ONLINE = 2, ONLINE_STATE_SUPPRESSED = 1, ONLINE_STATE_OFFLINE = 0 }; Unit* GetOwner() const { return _owner; } @@ -254,8 +254,8 @@ class TC_GAME_API ThreatReference bool IsOnline() const { return (_online >= ONLINE_STATE_ONLINE); } bool IsAvailable() const { return (_online > ONLINE_STATE_OFFLINE); } bool IsOffline() const { return (_online <= ONLINE_STATE_OFFLINE); } - TauntState GetTauntState() const { return _taunted; } - bool IsTaunting() const { return _taunted == TAUNT_STATE_TAUNT; } + TauntState GetTauntState() const { return IsTaunting() ? TAUNT_STATE_TAUNT : _taunted; } + bool IsTaunting() const { return _taunted >= TAUNT_STATE_TAUNT; } bool IsDetaunted() const { return _taunted == TAUNT_STATE_DETAUNT; } void SetThreat(float amount) { _baseAmount = amount; HeapNotifyChanged(); } @@ -270,7 +270,7 @@ class TC_GAME_API ThreatReference ThreatReference(ThreatManager* mgr, Unit* victim, float amount) : _owner(mgr->_owner), _mgr(mgr), _victim(victim), _baseAmount(amount), _tempModifier(0), _online(SelectOnlineState()), _taunted(TAUNT_STATE_NONE) { } static bool FlagsAllowFighting(Unit const* a, Unit const* b); OnlineState SelectOnlineState(); - void UpdateTauntState(bool victimIsTaunting); + void UpdateTauntState(TauntState state = TAUNT_STATE_NONE); Unit* const _owner; ThreatManager* const _mgr; void HeapNotifyIncreased() { _mgr->_sortedThreatList.increase(_handle); } |