diff --git a/src/game/Entities/StatSystem.cpp b/src/game/Entities/StatSystem.cpp index 50933b01ba..6eeda806f1 100644 --- a/src/game/Entities/StatSystem.cpp +++ b/src/game/Entities/StatSystem.cpp @@ -244,6 +244,7 @@ void Player::UpdateAttackPowerAndDamage(bool ranged) uint16 index = UNIT_FIELD_ATTACK_POWER; uint16 index_mod = UNIT_FIELD_ATTACK_POWER_MODS; uint16 index_mult = UNIT_FIELD_ATTACK_POWER_MULTIPLIER; + AttackPowerMod mod = AttackPowerMod::MELEE_ATTACK_POWER; if (ranged) { @@ -251,6 +252,8 @@ void Player::UpdateAttackPowerAndDamage(bool ranged) index_mod = UNIT_FIELD_RANGED_ATTACK_POWER_MODS; index_mult = UNIT_FIELD_RANGED_ATTACK_POWER_MULTIPLIER; + mod = AttackPowerMod::RANGED_ATTACK_POWER; + switch (getClass()) { case CLASS_HUNTER: val2 = level * 2.0f + GetStat(STAT_AGILITY) - 10.0f; break; @@ -313,7 +316,8 @@ void Player::UpdateAttackPowerAndDamage(bool ranged) float attPowerMultiplier = GetModifierValue(unitMod, TOTAL_PCT) - 1.0f; SetInt32Value(index, (uint32)base_attPower); // UNIT_FIELD_(RANGED)_ATTACK_POWER field - SetInt32Value(index_mod, (uint32)attPowerMod); // UNIT_FIELD_(RANGED)_ATTACK_POWER_MODS field + SetInt16Value(index_mod, 0, m_attackPowerMod[size_t(mod)][size_t(AttackPowerModSign::MOD_SIGN_POS)]); + SetInt16Value(index_mod, 1, m_attackPowerMod[size_t(mod)][size_t(AttackPowerModSign::MOD_SIGN_NEG)]); SetFloatValue(index_mult, attPowerMultiplier); // UNIT_FIELD_(RANGED)_ATTACK_POWER_MULTIPLIER field // automatically update weapon damage after attack power modification @@ -811,6 +815,7 @@ void Creature::UpdateAttackPowerAndDamage(bool ranged) uint16 index = UNIT_FIELD_ATTACK_POWER; uint16 index_mod = UNIT_FIELD_ATTACK_POWER_MODS; uint16 index_mult = UNIT_FIELD_ATTACK_POWER_MULTIPLIER; + AttackPowerMod mod = AttackPowerMod::MELEE_ATTACK_POWER; if (ranged) { @@ -818,6 +823,8 @@ void Creature::UpdateAttackPowerAndDamage(bool ranged) index_mod = UNIT_FIELD_RANGED_ATTACK_POWER_MODS; index_mult = UNIT_FIELD_RANGED_ATTACK_POWER_MULTIPLIER; + mod = AttackPowerMod::RANGED_ATTACK_POWER; + val2 = GetStat(STAT_AGILITY) - 10.0f; } else @@ -843,7 +850,8 @@ void Creature::UpdateAttackPowerAndDamage(bool ranged) float attPowerMultiplier = GetModifierValue(unitMod, TOTAL_PCT) - 1.0f; SetInt32Value(index, (uint32)base_attPower); // UNIT_FIELD_(RANGED)_ATTACK_POWER field - SetInt32Value(index_mod, (uint32)attPowerMod); // UNIT_FIELD_(RANGED)_ATTACK_POWER_MODS field + SetInt16Value(index_mod, 0, m_attackPowerMod[size_t(mod)][size_t(AttackPowerModSign::MOD_SIGN_POS)]); + SetInt16Value(index_mod, 1, m_attackPowerMod[size_t(mod)][size_t(AttackPowerModSign::MOD_SIGN_NEG)]); SetFloatValue(index_mult, attPowerMultiplier); // UNIT_FIELD_(RANGED)_ATTACK_POWER_MULTIPLIER field // automatically update weapon damage after attack power modification @@ -1034,13 +1042,14 @@ void Pet::UpdateAttackPowerAndDamage(bool ranged) // in BASE_VALUE of UNIT_MOD_ATTACK_POWER for creatures we store data of meleeattackpower field in DB float base_attPower = GetModifierValue(unitMod, BASE_VALUE) * GetModifierValue(unitMod, BASE_PCT); - float attPowerMod = GetModifierValue(unitMod, TOTAL_VALUE); + // float attPowerMod = GetModifierValue(unitMod, TOTAL_VALUE); float attPowerMultiplier = GetModifierValue(unitMod, TOTAL_PCT) - 1.0f; // UNIT_FIELD_(RANGED)_ATTACK_POWER field SetInt32Value(UNIT_FIELD_ATTACK_POWER, (int32)base_attPower); // UNIT_FIELD_(RANGED)_ATTACK_POWER_MODS field - SetInt32Value(UNIT_FIELD_ATTACK_POWER_MODS, (int32)attPowerMod); + SetInt16Value(UNIT_FIELD_ATTACK_POWER_MODS, 0, m_attackPowerMod[size_t(AttackPowerMod::MELEE_ATTACK_POWER)][size_t(AttackPowerModSign::MOD_SIGN_POS)]); + SetInt16Value(UNIT_FIELD_ATTACK_POWER_MODS, 1, m_attackPowerMod[size_t(AttackPowerMod::MELEE_ATTACK_POWER)][size_t(AttackPowerModSign::MOD_SIGN_NEG)]); // UNIT_FIELD_(RANGED)_ATTACK_POWER_MULTIPLIER field SetFloatValue(UNIT_FIELD_ATTACK_POWER_MULTIPLIER, attPowerMultiplier); diff --git a/src/game/Entities/Unit.cpp b/src/game/Entities/Unit.cpp index 2b3e7c5b40..7b4811f792 100644 --- a/src/game/Entities/Unit.cpp +++ b/src/game/Entities/Unit.cpp @@ -384,6 +384,10 @@ Unit::Unit() : // implement 50% base damage from offhand m_auraModifiersGroup[UNIT_MOD_DAMAGE_OFFHAND][TOTAL_PCT] = 0.5f; + for (auto& i : m_attackPowerMod) + for (auto& k : i) + k = 0; + for (float& m_createStat : m_createStats) m_createStat = 0.0f; @@ -9358,6 +9362,15 @@ bool Unit::HandleStatModifier(UnitMods unitMod, UnitModifierType modifierType, f case BASE_VALUE: case TOTAL_VALUE: m_auraModifiersGroup[unitMod][modifierType] += apply ? amount : -amount; + + if (modifierType == TOTAL_VALUE) + { + auto sign = amount > 0 ? AttackPowerModSign::MOD_SIGN_POS : AttackPowerModSign::MOD_SIGN_NEG; + if (unitMod == UNIT_MOD_ATTACK_POWER) + m_attackPowerMod[size_t(AttackPowerMod::MELEE_ATTACK_POWER)][size_t(sign)] += apply ? amount : -amount; + else if (unitMod == UNIT_MOD_ATTACK_POWER_RANGED) + m_attackPowerMod[size_t(AttackPowerMod::RANGED_ATTACK_POWER)][size_t(sign)] += apply ? amount : -amount; + } break; case BASE_PCT: case TOTAL_PCT: @@ -9548,7 +9561,7 @@ float Unit::GetTotalAttackPowerValue(WeaponAttackType attType) const return 0.0f; return ap * (1.0f + GetFloatValue(UNIT_FIELD_RANGED_ATTACK_POWER_MULTIPLIER)); } - int32 ap = GetInt32Value(UNIT_FIELD_ATTACK_POWER) + GetInt32Value(UNIT_FIELD_ATTACK_POWER_MODS); + int32 ap = GetInt32Value(UNIT_FIELD_ATTACK_POWER) + GetUInt16Value(UNIT_FIELD_ATTACK_POWER_MODS, 0) - GetUInt16Value(UNIT_FIELD_ATTACK_POWER_MODS, 1); if (ap < 0) return 0.0f; return ap * (1.0f + GetFloatValue(UNIT_FIELD_ATTACK_POWER_MULTIPLIER)); diff --git a/src/game/Entities/Unit.h b/src/game/Entities/Unit.h index ae95443a86..e0acc910a2 100644 --- a/src/game/Entities/Unit.h +++ b/src/game/Entities/Unit.h @@ -2554,6 +2554,21 @@ class Unit : public WorldObject AuraList m_modAuras[TOTAL_AURAS]; float m_auraModifiersGroup[UNIT_MOD_END][MODIFIER_TYPE_END]; + enum class AttackPowerMod + { + MELEE_ATTACK_POWER = 0, + RANGED_ATTACK_POWER = 1, + ATTACK_POWER_MOD_MAX + }; + + enum class AttackPowerModSign + { + MOD_SIGN_POS, + MOD_SIGN_NEG, + MOD_SIGN_MAX + }; + float m_attackPowerMod[size_t(AttackPowerMod::ATTACK_POWER_MOD_MAX)][size_t(AttackPowerModSign::MOD_SIGN_MAX)]; + WeaponDamageInfo m_weaponDamageInfo; bool m_canModifyStats;