diff options
author | Trazom62 <none@none> | 2010-04-09 20:10:55 +0200 |
---|---|---|
committer | Trazom62 <none@none> | 2010-04-09 20:10:55 +0200 |
commit | bca335f9bd4e11e42d13613d4e8a98695a990c8a (patch) | |
tree | 6041dbeeda0b147101f3d33326273a6c8e5fbfbd | |
parent | 0c22e5ac994ae5b039a4d011493428e1e88c6404 (diff) |
Implement Global Cooldown (originaly written for TC2 v2.4.3).
Thanks eugen.rivniy for the port.
Fixes issue #67.
--HG--
branch : trunk
-rw-r--r-- | src/game/Player.cpp | 45 | ||||
-rw-r--r-- | src/game/Player.h | 6 | ||||
-rw-r--r-- | src/game/Spell.cpp | 9 |
3 files changed, 59 insertions, 1 deletions
diff --git a/src/game/Player.cpp b/src/game/Player.cpp index 34b5bde73b0..762af7b0a48 100644 --- a/src/game/Player.cpp +++ b/src/game/Player.cpp @@ -498,6 +498,8 @@ Player::Player (WorldSession *session): Unit(), m_achievementMgr(this), m_reputa for (int i = 0; i < MAX_POWERS; ++i) m_powerFraction[i] = 0; + + m_globalCooldowns.clear(); } Player::~Player () @@ -1144,6 +1146,17 @@ void Player::Update(uint32 p_time) m_nextMailDelivereTime = 0; } + for (std::map<uint32, uint32>::iterator itr = m_globalCooldowns.begin(); itr != m_globalCooldowns.end(); ++itr) + { + if (itr->second) + { + if (itr->second > p_time) + itr->second -= p_time; + else + itr->second = 0; + } + } + // If this is set during update SetSpellModTakingSpell call is missing somewhere in the code // Having this would prevent more aura charges to be dropped, so let's crash //assert (!m_spellModTakingSpell); @@ -22034,6 +22047,38 @@ void Player::UpdateCharmedAI() } } +void Player::AddGlobalCooldown(SpellEntry const *spellInfo, Spell const *spell) +{ + if (!spellInfo || !spellInfo->StartRecoveryTime) + return; + + uint32 cdTime = spellInfo->StartRecoveryTime; + + if (!(spellInfo->Attributes & (SPELL_ATTR_UNK4|SPELL_ATTR_PASSIVE))) + cdTime *= GetFloatValue(UNIT_MOD_CAST_SPEED); + else if (IsRangedWeaponSpell(spellInfo) && !spell->IsAutoRepeat()) + cdTime *= m_modAttackSpeedPct[RANGED_ATTACK]; + + m_globalCooldowns[spellInfo->StartRecoveryCategory] = ((cdTime < 1000 || cdTime > 2000) ? 1000 : cdTime); +} + +bool Player::HasGlobalCooldown(SpellEntry const *spellInfo) const +{ + if (!spellInfo) + return false; + + std::map<uint32, uint32>::const_iterator itr = m_globalCooldowns.find(spellInfo->StartRecoveryCategory); + return itr != m_globalCooldowns.end() && (itr->second > sWorld.GetUpdateTime()); +} + +void Player::RemoveGlobalCooldown(SpellEntry const *spellInfo) +{ + if (!spellInfo) + return; + + m_globalCooldowns[spellInfo->StartRecoveryCategory] = 0; +} + uint32 Player::GetRuneBaseCooldown(uint8 index) { uint8 rune = GetBaseRune(index); diff --git a/src/game/Player.h b/src/game/Player.h index 938df014dbf..7919b85a198 100644 --- a/src/game/Player.h +++ b/src/game/Player.h @@ -1629,6 +1629,11 @@ class Player : public Unit, public GridObject<Player> void SetLastPotionId(uint32 item_id) { m_lastPotionId = item_id; } void UpdatePotionCooldown(Spell* spell = NULL); + // global cooldown + void AddGlobalCooldown(SpellEntry const *spellInfo, Spell const *spell); + bool HasGlobalCooldown(SpellEntry const *spellInfo) const; + void RemoveGlobalCooldown(SpellEntry const *spellInfo); + void setResurrectRequestData(uint64 guid, uint32 mapId, float X, float Y, float Z, uint32 health, uint32 mana) { m_resurrectGUID = guid; @@ -2608,6 +2613,7 @@ class Player : public Unit, public GridObject<Player> ReputationMgr m_reputationMgr; SpellCooldowns m_spellCooldowns; + std::map<uint32, uint32> m_globalCooldowns; // whole start recovery category stored in one uint32 m_ChampioningFaction; diff --git a/src/game/Spell.cpp b/src/game/Spell.cpp index 6bd54b344ff..29693d969e5 100644 --- a/src/game/Spell.cpp +++ b/src/game/Spell.cpp @@ -2756,6 +2756,9 @@ void Spell::prepare(SpellCastTargets const* targets, AuraEffect const * triggere m_caster->SetCurrentCastedSpell(this); SendSpellStart(); + if (m_caster->GetTypeId() == TYPEID_PLAYER) + m_caster->ToPlayer()->AddGlobalCooldown(m_spellInfo,this); + if (!m_casttime && !m_spellInfo->StartRecoveryTime && !m_castItemGUID //item: first cast may destroy item and second cast causes crash && GetCurrentContainer() == CURRENT_GENERIC_SPELL) @@ -2798,7 +2801,10 @@ void Spell::cancel() // spell is canceled-take mods and clear list if (m_caster->GetTypeId() == TYPEID_PLAYER) + { + m_caster->ToPlayer()->RemoveGlobalCooldown(m_spellInfo); m_caster->ToPlayer()->RemoveSpellMods(this); + } m_appliedMods.clear(); } break; @@ -4415,7 +4421,8 @@ SpellCastResult Spell::CheckCast(bool strict) if (!m_IsTriggeredSpell && m_caster->ToPlayer()->HasFlag(PLAYER_FLAGS, PLAYER_ALLOW_ONLY_ABILITY)) return SPELL_FAILED_SPELL_IN_PROGRESS; - if (m_caster->ToPlayer()->HasSpellCooldown(m_spellInfo->Id)) + if (m_caster->ToPlayer()->HasSpellCooldown(m_spellInfo->Id) || + (strict && !m_IsTriggeredSpell && m_caster->ToPlayer()->HasGlobalCooldown(m_spellInfo))) { if (m_triggeredByAuraSpell) return SPELL_FAILED_DONT_REPORT; |