diff --git a/sim/common/item_effects.go b/sim/common/item_effects.go index aad98b77a..06af84565 100644 --- a/sim/common/item_effects.go +++ b/sim/common/item_effects.go @@ -233,18 +233,27 @@ func init() { // Chance on hit: Increases Attack Power against Undead by 200 for 10 sec. // 1 PPM from Armaments Discord itemhelpers.CreateWeaponProcAura(ArgentAvenger, "Argent Avenger", 1.0, func(character *core.Character) *core.Aura { + matchingTargets := core.FilterSlice( + character.Env.Encounter.TargetUnits, + func(unit *core.Unit) bool { return unit.MobType == proto.MobType_MobTypeUndead }, + ) + return character.GetOrRegisterAura(core.Aura{ ActionID: core.ActionID{SpellID: 17352}, Label: "Argent Avenger", Duration: time.Second * 10, OnGain: func(aura *core.Aura, sim *core.Simulation) { - if character.CurrentTarget.MobType == proto.MobType_MobTypeUndead { - character.PseudoStats.MobTypeAttackPower += 200 + for _, target := range matchingTargets { + for _, at := range character.AttackTables[target.UnitIndex] { + at.BonusAttackPowerTaken += 200 + } } }, OnExpire: func(aura *core.Aura, sim *core.Simulation) { - if character.CurrentTarget.MobType == proto.MobType_MobTypeUndead { - character.PseudoStats.MobTypeAttackPower -= 200 + for _, target := range matchingTargets { + for _, at := range character.AttackTables[target.UnitIndex] { + at.BonusAttackPowerTaken -= 200 + } } }, }) @@ -893,13 +902,8 @@ func init() { }) // https://www.wowhead.com/classic/item=10696/enchanted-azsharite-felbane-sword - core.NewItemEffect(EnchantedAzshariteSword, func(agent core.Agent) { - character := agent.GetCharacter() - - if character.CurrentTarget.MobType == proto.MobType_MobTypeElemental { - character.PseudoStats.MobTypeAttackPower += 33 - } - }) + // Equip: +33 Attack Power when fighting Demons. + core.NewMobTypeAttackPowerEffect(EnchantedAzshariteSword, []proto.MobType{proto.MobType_MobTypeDemon}, 33) // https://www.wowhead.com/classic/item=18202/eskhandars-left-claw // Chance on hit: Slows enemy's movement by 60% and causes them to bleed for 150 damage over 30 sec. @@ -998,13 +1002,8 @@ func init() { }) // https://www.wowhead.com/classic/item=18310/fiendish-machete - core.NewItemEffect(FiendishMachete, func(agent core.Agent) { - character := agent.GetCharacter() - - if character.CurrentTarget.MobType == proto.MobType_MobTypeElemental { - character.PseudoStats.MobTypeAttackPower += 36 - } - }) + // Equip: +36 Attack Power when fighting Elementals. + core.NewMobTypeAttackPowerEffect(FiendishMachete, []proto.MobType{proto.MobType_MobTypeElemental}, 36) // https://www.wowhead.com/classic/item=870/fiery-war-axe itemhelpers.CreateWeaponProcSpell(FieryWarAxe, "Fiery War Axe", 1.0, func(character *core.Character) *core.Spell { @@ -1803,13 +1802,7 @@ func init() { itemhelpers.CreateWeaponCoHProcDamage(PendulumOfDoom, "Pendulum of Doom", 0.5, 10373, core.SpellSchoolPhysical, 250, 100, 0, core.DefenseTypeMelee) // https://www.wowhead.com/classic/item=12709/pips-skinner - core.NewItemEffect(PipsSkinner, func(agent core.Agent) { - character := agent.GetCharacter() - - if character.CurrentTarget.MobType == proto.MobType_MobTypeBeast { - character.PseudoStats.MobTypeAttackPower += 45 - } - }) + core.NewMobTypeAttackPowerEffect(PipsSkinner, []proto.MobType{proto.MobType_MobTypeBeast}, 45) // https://www.wowhead.com/classic/item=18816/perditions-blade // Chance on hit: Blasts a target for 40 to 56 Fire damage. @@ -1877,7 +1870,7 @@ func init() { BonusCoefficient: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - damage := 5.0 + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower()) + damage := 5.0 + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower(target)) for _, aoeTarget := range sim.Encounter.TargetUnits { spell.CalcAndDealDamage(sim, aoeTarget, damage, spell.OutcomeMeleeSpecialHitAndCrit) } diff --git a/sim/common/item_sets/item_sets_pve.go b/sim/common/item_sets/item_sets_pve.go index d965af6c8..745d9db0a 100644 --- a/sim/common/item_sets/item_sets_pve.go +++ b/sim/common/item_sets/item_sets_pve.go @@ -374,8 +374,17 @@ var ItemSetUndeadSlayersArmor = core.NewItemSet(core.ItemSet{ // Increases your damage against undead by 2%. 3: func(agent core.Agent) { character := agent.GetCharacter() - if character.CurrentTarget.MobType == proto.MobType_MobTypeUndead { - character.PseudoStats.DamageDealtMultiplier *= 1.02 + + delta := 1.02 + for _, target := range character.Env.Encounter.TargetUnits { + if target.MobType != proto.MobType_MobTypeUndead { + continue + } + + for _, at := range character.AttackTables[target.UnitIndex] { + at.DamageDealtMultiplier *= delta + at.CritMultiplier *= delta + } } }, }, diff --git a/sim/core/attack.go b/sim/core/attack.go index d101c248e..2f28ca02d 100644 --- a/sim/core/attack.go +++ b/sim/core/attack.go @@ -467,7 +467,7 @@ func (unit *Unit) EnableAutoAttacks(agent Agent, options AutoAttackOptions) { autoInProgress := *spell - baseDamage := autoInProgress.Unit.MHWeaponDamage(sim, autoInProgress.MeleeAttackPower()) + baseDamage := autoInProgress.Unit.MHWeaponDamage(sim, autoInProgress.MeleeAttackPower(target)) result := autoInProgress.CalcDamage(sim, target, baseDamage, autoInProgress.OutcomeMeleeWhite) StartDelayedAction(sim, DelayedActionOptions{ @@ -496,7 +496,7 @@ func (unit *Unit) EnableAutoAttacks(agent Agent, options AutoAttackOptions) { ApplyEffects: func(sim *Simulation, target *Unit, spell *Spell) { autoInProgress := *spell - baseDamage := autoInProgress.Unit.OHWeaponDamage(sim, autoInProgress.MeleeAttackPower()) + baseDamage := autoInProgress.Unit.OHWeaponDamage(sim, autoInProgress.MeleeAttackPower(target)) result := autoInProgress.CalcDamage(sim, target, baseDamage, autoInProgress.OutcomeMeleeWhite) StartDelayedAction(sim, DelayedActionOptions{ diff --git a/sim/core/consumes.go b/sim/core/consumes.go index 723d2cfb5..260c31615 100644 --- a/sim/core/consumes.go +++ b/sim/core/consumes.go @@ -106,8 +106,14 @@ func addImbueStats(character *Character, imbue proto.WeaponImbue, isMh bool, sha stats.SpellCrit: 1 * SpellCritRatingPerCritChance, }) case proto.WeaponImbue_BlessedWizardOil: - if character.CurrentTarget.MobType == proto.MobType_MobTypeUndead { - character.PseudoStats.MobTypeSpellPower += 60 + for _, target := range character.Env.Encounter.TargetUnits { + if target.MobType != proto.MobType_MobTypeUndead { + continue + } + + for _, at := range character.AttackTables[target.UnitIndex] { + at.BonusSpellDamageTaken += 60 + } } // Mana Oils @@ -152,8 +158,14 @@ func addImbueStats(character *Character, imbue proto.WeaponImbue, isMh bool, sha character.AddBonusRangedCritRating(-2.0) } case proto.WeaponImbue_ConsecratedSharpeningStone: - if character.CurrentTarget.MobType == proto.MobType_MobTypeUndead { - character.PseudoStats.MobTypeAttackPower += 100 + for _, target := range character.Env.Encounter.TargetUnits { + if target.MobType != proto.MobType_MobTypeUndead { + continue + } + + for _, at := range character.AttackTables[target.UnitIndex] { + at.BonusAttackPowerTaken += 100 + } } // Weightstones diff --git a/sim/core/debuffs.go b/sim/core/debuffs.go index 78cd79521..7b0a2a0a1 100644 --- a/sim/core/debuffs.go +++ b/sim/core/debuffs.go @@ -806,10 +806,14 @@ func HuntersMarkAura(target *Unit, points int32) *Aura { aura.NewExclusiveEffect("HuntersMark", true, ExclusiveEffect{ Priority: bonus, OnGain: func(ee *ExclusiveEffect, sim *Simulation) { - ee.Aura.Unit.PseudoStats.BonusRangedAttackPowerTaken += bonus + for _, unit := range sim.Environment.Raid.AllUnits { + unit.AttackTables[target.UnitIndex][proto.CastType_CastTypeRanged].BonusAttackPowerTaken += bonus + } }, OnExpire: func(ee *ExclusiveEffect, sim *Simulation) { - ee.Aura.Unit.PseudoStats.BonusRangedAttackPowerTaken -= bonus + for _, unit := range sim.Environment.Raid.AllUnits { + unit.AttackTables[target.UnitIndex][proto.CastType_CastTypeRanged].BonusAttackPowerTaken -= bonus + } }, }) @@ -824,10 +828,14 @@ func ExposeWeaknessAura(target *Unit) *Aura { Label: "Expose Weakness", Duration: time.Second * 7, OnGain: func(aura *Aura, sim *Simulation) { - target.PseudoStats.BonusRangedAttackPowerTaken += bonus + for _, unit := range sim.Environment.Raid.AllUnits { + unit.AttackTables[target.UnitIndex][proto.CastType_CastTypeRanged].BonusAttackPowerTaken += bonus + } }, OnExpire: func(aura *Aura, sim *Simulation) { - target.PseudoStats.BonusRangedAttackPowerTaken -= bonus + for _, unit := range sim.Environment.Raid.AllUnits { + unit.AttackTables[target.UnitIndex][proto.CastType_CastTypeRanged].BonusAttackPowerTaken -= bonus + } }, }) diff --git a/sim/core/item_effects.go b/sim/core/item_effects.go index dda0c7162..e2e89018e 100644 --- a/sim/core/item_effects.go +++ b/sim/core/item_effects.go @@ -150,20 +150,65 @@ func NewSimpleStatDefensiveTrinketEffect(itemID int32, bonus stats.Stats, durati }, nil) } -// TODO: These should ideally be done at the AttackTable level +// Apply a +X Attack Power when fighting Mob Type effect +// These effects seem to always apply to both melee and ranged attack power in-game +// Apply Aura: Mod Melee Attack Power vs Creature (Mob Type) +// Apply Aura: Mod Ranged Attack Power vs Creature (Mob Type) func NewMobTypeAttackPowerEffect(itemID int32, mobTypes []proto.MobType, bonus float64) { NewItemEffect(itemID, func(agent Agent) { character := agent.GetCharacter() - if slices.Contains(mobTypes, character.CurrentTarget.MobType) { - character.PseudoStats.MobTypeAttackPower += bonus - } + + matchingTargets := FilterSlice( + character.Env.Encounter.TargetUnits, + func(unit *Unit) bool { return slices.Contains(mobTypes, unit.MobType) }, + ) + + MakePermanent(character.GetOrRegisterAura(Aura{ + Label: fmt.Sprintf("Mob type Attack Power Bonus - %s (%d)", mobTypes, itemID), + OnGain: func(aura *Aura, sim *Simulation) { + for _, target := range matchingTargets { + for _, at := range character.AttackTables[target.UnitIndex] { + at.BonusAttackPowerTaken += bonus + } + } + }, + OnExpire: func(aura *Aura, sim *Simulation) { + for _, target := range matchingTargets { + for _, at := range character.AttackTables[target.UnitIndex] { + at.BonusAttackPowerTaken -= bonus + } + } + }, + })) }) } + +// Apply a +X Spell Damage when fighting Mob Type effect func NewMobTypeSpellPowerEffect(itemID int32, mobTypes []proto.MobType, bonus float64) { NewItemEffect(itemID, func(agent Agent) { character := agent.GetCharacter() - if slices.Contains(mobTypes, character.CurrentTarget.MobType) { - character.PseudoStats.MobTypeSpellPower += bonus - } + + matchingTargets := FilterSlice( + character.Env.Encounter.TargetUnits, + func(unit *Unit) bool { return slices.Contains(mobTypes, unit.MobType) }, + ) + + MakePermanent(character.GetOrRegisterAura(Aura{ + Label: fmt.Sprintf("Mob type Spell Damage Bonus - %s (%d)", mobTypes, itemID), + OnGain: func(aura *Aura, sim *Simulation) { + for _, target := range matchingTargets { + for _, at := range character.AttackTables[target.UnitIndex] { + at.BonusSpellDamageTaken += bonus + } + } + }, + OnExpire: func(aura *Aura, sim *Simulation) { + for _, target := range matchingTargets { + for _, at := range character.AttackTables[target.UnitIndex] { + at.BonusSpellDamageTaken -= bonus + } + } + }, + })) }) -} \ No newline at end of file +} diff --git a/sim/core/spell_result.go b/sim/core/spell_result.go index c953e49ea..7ade80aa9 100644 --- a/sim/core/spell_result.go +++ b/sim/core/spell_result.go @@ -99,16 +99,17 @@ func (spell *Spell) ThreatFromDamage(outcome HitOutcome, damage float64) float64 } } -func (spell *Spell) MeleeAttackPower() float64 { - return spell.Unit.stats[stats.AttackPower] + spell.Unit.PseudoStats.MobTypeAttackPower +func (spell *Spell) MeleeAttackPower(target *Unit) float64 { + return spell.Unit.stats[stats.AttackPower] + + spell.Unit.AttackTables[target.Index][spell.CastType].BonusAttackPowerTaken } func (spell *Spell) RangedAttackPower(target *Unit, ignoreTargetModifiers bool) float64 { return TernaryFloat64(ignoreTargetModifiers, spell.Unit.stats[stats.RangedAttackPower], spell.Unit.stats[stats.RangedAttackPower]+ - spell.Unit.PseudoStats.MobTypeAttackPower+ - target.PseudoStats.BonusRangedAttackPowerTaken) + spell.Unit.AttackTables[target.Index][spell.CastType].BonusAttackPowerTaken, + ) } func (spell *Spell) PhysicalHitChance(attackTable *AttackTable) float64 { @@ -128,8 +129,14 @@ func (spell *Spell) PhysicalCritCheck(sim *Simulation, attackTable *AttackTable) return sim.RandomFloat("Physical Crit Roll") < spell.PhysicalCritChance(attackTable) } -// The combined bonus damage (aka spell power) for this spell's school(s). -func (spell *Spell) GetBonusDamage() float64 { +// The combined bonus damage (aka spell power) for this spell's school(s) **including** mob type specific spell power. +func (spell *Spell) GetBonusDamage(target *Unit) float64 { + return spell.GetSchoolDamage() + + spell.Unit.AttackTables[target.Index][spell.CastType].BonusSpellDamageTaken +} + +// The combined bonus damage (aka spell power) for this spell's school(s) **excluding** mob type specific spell power. +func (spell *Spell) GetSchoolDamage() float64 { var schoolBonusDamage float64 switch spell.SchoolIndex { @@ -178,8 +185,7 @@ func (spell *Spell) GetBonusDamage() float64 { return spell.BonusDamage + schoolBonusDamage + spell.Unit.GetStat(stats.SpellPower) + - spell.Unit.GetStat(stats.SpellDamage) + - spell.Unit.PseudoStats.MobTypeSpellPower + spell.Unit.GetStat(stats.SpellDamage) } func (spell *Spell) SpellHitChance(target *Unit) float64 { @@ -310,14 +316,16 @@ func (spell *Spell) calcDamageInternal(sim *Simulation, target *Unit, baseDamage spell.ApplyPostOutcomeDamageModifiers(sim, result) afterPostOutcome := result.Damage + bonusDamage := spell.GetBonusDamage(target) + spell.Unit.Log( sim, "%s %s [DEBUG] MAP+Bonus: %0.01f, RAP+Bonus: %0.01f, SP+Bonus: %0.01f, BaseDamage:%0.01f, AfterAttackerMods:%0.01f, AfterResistances:%0.01f, AfterTargetMods:%0.01f, AfterOutcome:%0.01f, AfterPostOutcome:%0.01f", target.LogLabel(), spell.ActionID, - spell.Unit.GetStat(stats.AttackPower)+TernaryFloat64(spell.SchoolIndex == stats.SchoolIndexPhysical, spell.GetBonusDamage(), 0), - spell.Unit.GetStat(stats.RangedAttackPower)+TernaryFloat64(spell.SchoolIndex == stats.SchoolIndexPhysical, spell.GetBonusDamage(), 0), - spell.GetBonusDamage(), + spell.Unit.GetStat(stats.AttackPower)+TernaryFloat64(spell.SchoolIndex == stats.SchoolIndexPhysical, bonusDamage, 0), + spell.Unit.GetStat(stats.RangedAttackPower)+TernaryFloat64(spell.SchoolIndex == stats.SchoolIndexPhysical, bonusDamage, 0), + bonusDamage, baseDamage, afterAttackMods, afterResistances, @@ -337,7 +345,7 @@ func (spell *Spell) CalcDamage(sim *Simulation, target *Unit, baseDamage float64 baseDamage *= spell.BaseDamageMultiplierAdditive if spell.BonusCoefficient > 0 { - baseDamage += spell.BonusCoefficient * spell.GetBonusDamage() + baseDamage += spell.BonusCoefficient * spell.GetBonusDamage(target) } return spell.calcDamageInternal(sim, target, baseDamage, attackerMultiplier, false, outcomeApplier) @@ -350,7 +358,7 @@ func (spell *Spell) CalcPeriodicDamage(sim *Simulation, target *Unit, baseDamage attackerMultiplier *= dot.DamageMultiplier if dot.BonusCoefficient > 0 { - baseDamage += dot.BonusCoefficient * spell.GetBonusDamage() + baseDamage += dot.BonusCoefficient * spell.GetBonusDamage(target) } return spell.calcDamageInternal(sim, target, baseDamage, attackerMultiplier, true, outcomeApplier) @@ -364,7 +372,7 @@ func (dot *Dot) Snapshot(target *Unit, baseDamage float64, isRollover bool) { if !isRollover { dot.SnapshotBaseDamage = baseDamage * dot.Spell.BaseDamageMultiplierAdditive if dot.BonusCoefficient > 0 { - dot.SnapshotBaseDamage += dot.BonusCoefficient * dot.Spell.GetBonusDamage() + dot.SnapshotBaseDamage += dot.BonusCoefficient * dot.Spell.GetBonusDamage(target) } attackTable := dot.Spell.Unit.AttackTables[target.UnitIndex][dot.Spell.CastType] diff --git a/sim/core/spell_school_test.go b/sim/core/spell_school_test.go index f488c874c..225e72f93 100644 --- a/sim/core/spell_school_test.go +++ b/sim/core/spell_school_test.go @@ -283,14 +283,37 @@ func Test_MultiSchoolResistanceArmor(t *testing.T) { func Test_MultiSchoolSpellPower(t *testing.T) { caster := &Unit{ - Type: PlayerUnit, - Level: 60, + Type: PlayerUnit, + Level: 60, + stats: stats.Stats{}, + PseudoStats: stats.NewPseudoStats(), + AttackTables: make([]map[proto.CastType]*AttackTable, 1), + } + + target := &Unit{ + Type: EnemyUnit, + Level: 63, stats: stats.Stats{}, PseudoStats: stats.NewPseudoStats(), + UnitIndex: 0, } spell := &Spell{ - Unit: caster, + Unit: caster, + CastType: proto.CastType_CastTypeMainHand, + } + + caster.AttackTables[target.UnitIndex] = make(map[proto.CastType]*AttackTable, 1) + caster.AttackTables[target.UnitIndex][spell.CastType] = &AttackTable{ + Attacker: caster, + Defender: target, + Weapon: &Item{}, + + CritMultiplier: 1, + + DamageDealtMultiplier: 1, + DamageTakenMultiplier: 1, + HealingDealtMultiplier: 1, } for schoolIndex1 := stats.SchoolIndexArcane; schoolIndex1 < stats.SchoolLen; schoolIndex1++ { @@ -357,7 +380,7 @@ func Test_MultiSchoolSpellPower(t *testing.T) { return } - power := spell.GetBonusDamage() + power := spell.GetBonusDamage(target) if power != highestValue { t.Errorf("Expected %f to be highest power value found, but got %f for school %d!", highestValue, power, schoolMask) return diff --git a/sim/core/stats/stats.go b/sim/core/stats/stats.go index 5bce8902c..63119ca81 100644 --- a/sim/core/stats/stats.go +++ b/sim/core/stats/stats.go @@ -426,9 +426,6 @@ type PseudoStats struct { IncreasedMissChance float64 // Insect Swarm and Scorpid Sting DodgeReduction float64 // Target dodge reduction effects e.g. "reduces its target's chance to Dodge by X%" - MobTypeAttackPower float64 // Bonus AP against mobs of the current type. - MobTypeSpellPower float64 // Bonus SP against mobs of the current type. - ThreatMultiplier float64 // Modulates the threat generated. Affected by things like salv. DamageDealtMultiplier float64 // All damage @@ -481,9 +478,8 @@ type PseudoStats struct { ReducedCritTakenChance float64 // Reduces chance to be crit. - BonusRangedAttackPowerTaken float64 // Hunters mark - BonusMeleeHitRatingTaken float64 // Formerly Imp FF and SW Radiance; - BonusSpellHitRatingTaken float64 // Imp FF + BonusMeleeHitRatingTaken float64 // Formerly Imp FF and SW Radiance; + BonusSpellHitRatingTaken float64 // Imp FF BonusHealingTaken float64 // Talisman of Troll Divinity diff --git a/sim/core/target.go b/sim/core/target.go index 262291aae..d57323f61 100644 --- a/sim/core/target.go +++ b/sim/core/target.go @@ -3,6 +3,7 @@ package core import ( "strconv" "time" + "github.com/wowsims/classic/sim/core/proto" "github.com/wowsims/classic/sim/core/stats" ) @@ -264,7 +265,7 @@ type AttackTable struct { BaseParryChance float64 BaseGlanceChance float64 BaseCritChance float64 - BaseCrushChance float64 + BaseCrushChance float64 GlanceMultiplierMin float64 GlanceMultiplierMax float64 @@ -279,6 +280,9 @@ type AttackTable struct { DamageTakenMultiplier float64 // defender debuff, applied in applyTargetModifiers() HealingDealtMultiplier float64 + BonusAttackPowerTaken float64 // For effects like mob type attack power bonuses. + BonusSpellDamageTaken float64 // For effects like mob type spell damage bonuses. + // This is for "Apply Aura: Mod Damage Done By Caster" effects. // If set, the damage taken multiplier is multiplied by the callbacks result. DamageDoneByCasterMultiplier func(spell *Spell, attackTable *AttackTable) float64 @@ -360,7 +364,7 @@ func NewAttackTable(attacker *Unit, defender *Unit, weapon *Item) *AttackTable { } else { table.BaseBlockChance = 0 } - + table.BaseCrushChance = UnitLevelFloat64(attacker.Level-defender.Level, 0.0, 0.0, 0.0, 0.15) table.BaseMissChance = 0.05 + levelDelta table.BaseDodgeChance = levelDelta // base dodge applied with class base stats diff --git a/sim/druid/claw.go b/sim/druid/claw.go index be05dc69a..347b29292 100644 --- a/sim/druid/claw.go +++ b/sim/druid/claw.go @@ -34,7 +34,7 @@ func (druid *Druid) registerClawSpell() { BonusCoefficient: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeSpecialHitAndCrit) diff --git a/sim/druid/ferocious_bite.go b/sim/druid/ferocious_bite.go index 435126e2e..91b8ae5e2 100644 --- a/sim/druid/ferocious_bite.go +++ b/sim/druid/ferocious_bite.go @@ -95,7 +95,7 @@ func (druid *Druid) newFerociousBiteSpellConfig(rank FerociousBiteRankInfo) core ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { comboPoints := float64(druid.ComboPoints()) - attackPower := spell.MeleeAttackPower() + attackPower := spell.MeleeAttackPower(target) excessEnergy := druid.CurrentEnergy() baseDamage := rank.dmgBase + rank.dmgRange*sim.RandomFloat("Ferocious Bite") + diff --git a/sim/druid/rip.go b/sim/druid/rip.go index 113290382..5cc7190d4 100644 --- a/sim/druid/rip.go +++ b/sim/druid/rip.go @@ -105,7 +105,7 @@ func (druid *Druid) newRipSpellConfig(ripRank RipRankInfo) core.SpellConfig { cpScaling := core.TernaryFloat64(cp == 5, 4, cp) baseDamage := ripRank.dmgTickBase + ripRank.dmgTickPerCombo*cp // AP scaling is 6% per combo point from 1 to 4, and 24% again for 5 - tickDamage := baseDamage + 0.01*cpScaling*dot.Spell.MeleeAttackPower() + tickDamage := baseDamage + 0.01*cpScaling*dot.Spell.MeleeAttackPower(target) dot.Snapshot(target, tickDamage, isRollover) }, OnTick: func(sim *core.Simulation, target *core.Unit, dot *core.Dot) { diff --git a/sim/druid/shred.go b/sim/druid/shred.go index d7fb66cb4..c7e3ce100 100644 --- a/sim/druid/shred.go +++ b/sim/druid/shred.go @@ -47,7 +47,7 @@ func (druid *Druid) registerShredSpell() { BonusCoefficient: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeSpecialHitAndCrit) @@ -58,7 +58,7 @@ func (druid *Druid) registerShredSpell() { } }, ExpectedInitialDamage: func(sim *core.Simulation, target *core.Unit, spell *core.Spell, _ bool) *core.SpellResult { - baseDamage := flatDamageBonus + spell.Unit.AutoAttacks.MH().CalculateAverageWeaponDamage(spell.MeleeAttackPower()) + baseDamage := flatDamageBonus + spell.Unit.AutoAttacks.MH().CalculateAverageWeaponDamage(spell.MeleeAttackPower(target)) baseres := spell.CalcDamage(sim, target, baseDamage, spell.OutcomeExpectedMagicAlwaysHit) diff --git a/sim/hunter/raptor_strike.go b/sim/hunter/raptor_strike.go index 8f0a56db9..f05f1e2cc 100644 --- a/sim/hunter/raptor_strike.go +++ b/sim/hunter/raptor_strike.go @@ -83,7 +83,7 @@ func (hunter *Hunter) newRaptorStrikeHitSpell(rank int) *core.Spell { BonusCoefficient: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - damage := baseDamage + hunter.MHWeaponDamage(sim, spell.MeleeAttackPower()) + damage := baseDamage + hunter.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) spell.CalcAndDealDamage(sim, target, damage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) }, }) diff --git a/sim/paladin/soc.go b/sim/paladin/soc.go index 290bce383..92192c5ab 100644 --- a/sim/paladin/soc.go +++ b/sim/paladin/soc.go @@ -105,7 +105,7 @@ func (paladin *Paladin) registerSealOfCommand() { BonusCoefficient: 0.29, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - baseDamage := spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcDamage(sim, target, baseDamage, spell.OutcomeMeleeSpecialHitAndCrit) core.StartDelayedAction(sim, core.DelayedActionOptions{ diff --git a/sim/paladin/sor.go b/sim/paladin/sor.go index 2529675b4..ebcb4ef58 100644 --- a/sim/paladin/sor.go +++ b/sim/paladin/sor.go @@ -114,7 +114,7 @@ func (paladin *Paladin) registerSealOfRighteousness() { ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { // effectively scales with coeff x 2, and damage dealt multipliers affect half the damage taken bonus - baseDamage := damage*improvedSoR + spell.BonusCoefficient*(spell.GetBonusDamage()+target.GetSchoolBonusDamageTaken(spell)) + baseDamage := damage*improvedSoR + spell.BonusCoefficient*(spell.GetBonusDamage(target)+target.GetSchoolBonusDamageTaken(spell)) spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeSpecialCritOnly) }, }) diff --git a/sim/rogue/ambush.go b/sim/rogue/ambush.go index 7be0858a9..4124e8300 100644 --- a/sim/rogue/ambush.go +++ b/sim/rogue/ambush.go @@ -58,7 +58,7 @@ func (rogue *Rogue) registerAmbushSpell() { ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { rogue.BreakStealth(sim) - baseDamage := (flatDamageBonus + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower())) + baseDamage := (flatDamageBonus + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower(target))) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeSpecialNoBlockDodgeParry) @@ -68,6 +68,5 @@ func (rogue *Rogue) registerAmbushSpell() { spell.IssueRefund(sim) } }, - }) } diff --git a/sim/rogue/backstab.go b/sim/rogue/backstab.go index f2258c6df..691d12222 100644 --- a/sim/rogue/backstab.go +++ b/sim/rogue/backstab.go @@ -58,7 +58,7 @@ func (rogue *Rogue) registerBackstabSpell() { ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { rogue.BreakStealth(sim) - baseDamage := (flatDamageBonus + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower())) + baseDamage := (flatDamageBonus + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower(target))) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) if result.Landed() { diff --git a/sim/rogue/eviscerate.go b/sim/rogue/eviscerate.go index c1a8baaae..e37f6a0a2 100644 --- a/sim/rogue/eviscerate.go +++ b/sim/rogue/eviscerate.go @@ -32,7 +32,7 @@ func (rogue *Rogue) registerEviscerate() { 25: 6762, 40: 8624, 50: 11299, - 60: core.TernaryInt32(core.IncludeAQ, 31016, 11300), + 60: core.TernaryInt32(core.IncludeAQ, 31016, 11300), }[rogue.Level] rogue.Eviscerate = rogue.RegisterSpell(core.SpellConfig{ @@ -74,7 +74,7 @@ func (rogue *Rogue) registerEviscerate() { flatBaseDamage := flatDamage + comboDamageBonus*float64(comboPoints) baseDamage := sim.Roll(flatBaseDamage, flatBaseDamage+damageVariance) + - 0.03*float64(comboPoints)*spell.MeleeAttackPower() + 0.03*float64(comboPoints)*spell.MeleeAttackPower(target) result := spell.CalcDamage(sim, target, baseDamage, spell.OutcomeMeleeSpecialHitAndCrit) diff --git a/sim/rogue/garrote.go b/sim/rogue/garrote.go index 22e6330a1..5c8d12c93 100644 --- a/sim/rogue/garrote.go +++ b/sim/rogue/garrote.go @@ -57,7 +57,7 @@ func (rogue *Rogue) registerGarrote() { NumberOfTicks: 6, TickLength: time.Second * 3, OnSnapshot: func(sim *core.Simulation, target *core.Unit, dot *core.Dot, isRollover bool) { - damage := baseDamage + dot.Spell.MeleeAttackPower()*0.03 + damage := baseDamage + dot.Spell.MeleeAttackPower(target)*0.03 dot.Snapshot(target, damage, isRollover) }, OnTick: func(sim *core.Simulation, target *core.Unit, dot *core.Dot) { diff --git a/sim/rogue/ghostly_strike.go b/sim/rogue/ghostly_strike.go index 027af6ef3..a57f409df 100644 --- a/sim/rogue/ghostly_strike.go +++ b/sim/rogue/ghostly_strike.go @@ -56,7 +56,7 @@ func (rogue *Rogue) registerGhostlyStrikeSpell() { ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { rogue.BreakStealth(sim) - baseDamage := spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) diff --git a/sim/rogue/hemorrhage.go b/sim/rogue/hemorrhage.go index 9ea2a9ee6..85d071009 100644 --- a/sim/rogue/hemorrhage.go +++ b/sim/rogue/hemorrhage.go @@ -17,7 +17,7 @@ func (rogue *Rogue) registerHemorrhageSpell() { var hemoAuras core.AuraArray hemoAuras = rogue.NewEnemyAuraArray(func(target *core.Unit) *core.Aura { - return core.HemorrhageAura(target) + return core.HemorrhageAura(target) }) rogue.Hemorrhage = rogue.RegisterSpell(core.SpellConfig{ @@ -47,7 +47,7 @@ func (rogue *Rogue) registerHemorrhageSpell() { ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { rogue.BreakStealth(sim) - baseDamage := spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) diff --git a/sim/rogue/riposte.go b/sim/rogue/riposte.go index 8faab2e55..6a6423085 100644 --- a/sim/rogue/riposte.go +++ b/sim/rogue/riposte.go @@ -40,7 +40,7 @@ func (rogue *Rogue) applyRiposte() { ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { riposteReady.Deactivate(sim) - damage := rogue.MHWeaponDamage(sim, spell.MeleeAttackPower()) + damage := rogue.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) spell.CalcAndDealDamage(sim, target, damage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) }, }) diff --git a/sim/rogue/rupture.go b/sim/rogue/rupture.go index 60890697a..69aa1254e 100644 --- a/sim/rogue/rupture.go +++ b/sim/rogue/rupture.go @@ -51,7 +51,7 @@ func (rogue *Rogue) registerRupture() { TickLength: time.Second * 2, OnSnapshot: func(sim *core.Simulation, target *core.Unit, dot *core.Dot, isRollover bool) { - dot.Snapshot(target, rogue.RuptureDamage(rogue.ComboPoints()), isRollover) + dot.Snapshot(target, rogue.RuptureDamage(target, rogue.ComboPoints()), isRollover) }, OnTick: func(sim *core.Simulation, target *core.Unit, dot *core.Dot) { dot.CalcAndDealPeriodicSnapshotDamage(sim, target, dot.OutcomeTick) @@ -76,7 +76,7 @@ func (rogue *Rogue) registerRupture() { rogue.Finishers = append(rogue.Finishers, rogue.Rupture) } -func (rogue *Rogue) RuptureDamage(comboPoints int32) float64 { +func (rogue *Rogue) RuptureDamage(target *core.Unit, comboPoints int32) float64 { baseTickDamage := map[int32]float64{ 25: 8, 40: 18, @@ -92,7 +92,7 @@ func (rogue *Rogue) RuptureDamage(comboPoints int32) float64 { }[rogue.Level] return baseTickDamage + comboTickDamage*float64(comboPoints) + - []float64{0, 0.04 / 4, 0.10 / 5, 0.18 / 6, 0.21 / 7, 0.24 / 8}[comboPoints]*rogue.Rupture.MeleeAttackPower() + []float64{0, 0.04 / 4, 0.10 / 5, 0.18 / 6, 0.21 / 7, 0.24 / 8}[comboPoints]*rogue.Rupture.MeleeAttackPower(target) } func (rogue *Rogue) RuptureTicks(comboPoints int32) int32 { diff --git a/sim/rogue/sinister_strike.go b/sim/rogue/sinister_strike.go index a87dbf827..b8d6f16aa 100644 --- a/sim/rogue/sinister_strike.go +++ b/sim/rogue/sinister_strike.go @@ -50,7 +50,7 @@ func (rogue *Rogue) registerSinisterStrikeSpell() { ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { rogue.BreakStealth(sim) - baseDamage := flatDamageBonus + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := flatDamageBonus + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) if result.Landed() { diff --git a/sim/shaman/elemental/TestElemental.results b/sim/shaman/elemental/TestElemental.results index b2c0a6da3..39f3eddce 100644 --- a/sim/shaman/elemental/TestElemental.results +++ b/sim/shaman/elemental/TestElemental.results @@ -543,7 +543,7 @@ stat_weights_results: { weights: 0 weights: 0 weights: 0 - weights: -0.35865 + weights: -0.38185 weights: 0 weights: 0.71195 weights: 0 @@ -553,7 +553,7 @@ stat_weights_results: { weights: 0.65983 weights: 0 weights: 0 - weights: 9.52138 + weights: 9.47772 weights: 6.05155 weights: 0 weights: 0 @@ -1394,71 +1394,71 @@ dps_results: { dps_results: { key: "TestElemental-Phase6-AllItems-Champion'sEarthshaker" value: { - dps: 695.68707 - tps: 657.22231 + dps: 699.69045 + tps: 661.22569 } } dps_results: { key: "TestElemental-Phase6-AllItems-Champion'sStormcaller" value: { - dps: 705.08068 - tps: 665.68662 + dps: 709.12419 + tps: 669.73012 } } dps_results: { key: "TestElemental-Phase6-AllItems-GiftoftheGatheringStorm" value: { - dps: 795.47178 - tps: 750.33516 + dps: 798.33769 + tps: 753.20108 } } dps_results: { key: "TestElemental-Phase6-AllItems-Stormcaller'sGarb" value: { - dps: 831.0716 - tps: 784.17815 + dps: 833.67109 + tps: 786.77764 } } dps_results: { key: "TestElemental-Phase6-AllItems-TheEarthfury" value: { - dps: 652.14582 - tps: 615.23685 + dps: 654.02206 + tps: 617.11309 } } dps_results: { key: "TestElemental-Phase6-AllItems-TheEarthshatterer" value: { - dps: 629.35099 - tps: 593.89411 + dps: 629.7204 + tps: 594.26352 } } dps_results: { key: "TestElemental-Phase6-AllItems-TheFiveThunders" value: { - dps: 697.8153 - tps: 660.26617 + dps: 700.57486 + tps: 663.02572 } } dps_results: { key: "TestElemental-Phase6-AllItems-TheTenStorms" value: { - dps: 713.13749 - tps: 675.51439 + dps: 715.59893 + tps: 677.97582 } } dps_results: { key: "TestElemental-Phase6-AllItems-Warlord'sEarthshaker" value: { - dps: 740.86856 - tps: 698.84153 + dps: 743.68459 + tps: 701.65755 } } dps_results: { key: "TestElemental-Phase6-Average-Default" value: { - dps: 903.5537 - tps: 850.97053 + dps: 906.53526 + tps: 853.95209 } } dps_results: { @@ -1548,7 +1548,7 @@ dps_results: { dps_results: { key: "TestElemental-Phase6-SwitchInFrontOfTarget-Default" value: { - dps: 903.87467 - tps: 850.15307 + dps: 906.14785 + tps: 852.42625 } } diff --git a/sim/shaman/stormstrike.go b/sim/shaman/stormstrike.go index 0f69351bd..c8c4cf6a9 100644 --- a/sim/shaman/stormstrike.go +++ b/sim/shaman/stormstrike.go @@ -40,7 +40,7 @@ func (shaman *Shaman) registerStormstrikeSpell() { ThreatMultiplier: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - baseDamage := shaman.MHWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := shaman.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) if result.Landed() { diff --git a/sim/shaman/windfury_weapon.go b/sim/shaman/windfury_weapon.go index bb5424125..36ebf765d 100644 --- a/sim/shaman/windfury_weapon.go +++ b/sim/shaman/windfury_weapon.go @@ -47,7 +47,7 @@ func (shaman *Shaman) newWindfuryImbueSpell(isMH bool) *core.Spell { ThreatMultiplier: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - mAP := spell.MeleeAttackPower() + bonusAP*ewMultiplier*ewMultiplier + mAP := spell.MeleeAttackPower(target) + bonusAP*ewMultiplier*ewMultiplier baseDamage := weaponDamageFunc(sim, mAP) spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) }, diff --git a/sim/warrior/bloodthirst.go b/sim/warrior/bloodthirst.go index c5c2db77e..905fba68e 100644 --- a/sim/warrior/bloodthirst.go +++ b/sim/warrior/bloodthirst.go @@ -41,7 +41,7 @@ func (warrior *Warrior) registerBloodthirstSpell(cdTimer *core.Timer) { BonusCoefficient: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - baseDamage := 0.45 * spell.MeleeAttackPower() + baseDamage := 0.45 * spell.MeleeAttackPower(target) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeSpecialHitAndCrit) if !result.Landed() { spell.IssueRefund(sim) diff --git a/sim/warrior/deep_wounds.go b/sim/warrior/deep_wounds.go index e9b238865..6e39b685b 100644 --- a/sim/warrior/deep_wounds.go +++ b/sim/warrior/deep_wounds.go @@ -75,11 +75,11 @@ func (warrior *Warrior) procDeepWounds(sim *core.Simulation, target *core.Unit, if isOh { attackTableOh := warrior.AttackTables[target.UnitIndex][proto.CastType_CastTypeOffHand] adm := warrior.AutoAttacks.OHAuto().AttackerDamageMultiplier(attackTableOh, true) - awd = warrior.AutoAttacks.OH().CalculateAverageWeaponDamage(dot.Spell.MeleeAttackPower()) * 0.5 * adm + awd = warrior.AutoAttacks.OH().CalculateAverageWeaponDamage(dot.Spell.MeleeAttackPower(target)) * 0.5 * adm } else { // MH attackTableMh := warrior.AttackTables[target.UnitIndex][proto.CastType_CastTypeMainHand] adm := warrior.AutoAttacks.MHAuto().AttackerDamageMultiplier(attackTableMh, true) - awd = warrior.AutoAttacks.MH().CalculateAverageWeaponDamage(dot.Spell.MeleeAttackPower()) * adm + awd = warrior.AutoAttacks.MH().CalculateAverageWeaponDamage(dot.Spell.MeleeAttackPower(target)) * adm } newDamage := awd * 0.2 * float64(warrior.Talents.DeepWounds) // 60% of average attackers damage diff --git a/sim/warrior/heroic_strike_cleave.go b/sim/warrior/heroic_strike_cleave.go index b0dcf9af5..af391764e 100644 --- a/sim/warrior/heroic_strike_cleave.go +++ b/sim/warrior/heroic_strike_cleave.go @@ -30,7 +30,7 @@ func (warrior *Warrior) registerHeroicStrikeSpell(realismICD *core.Cooldown) { BonusCoefficient: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) if !result.Landed() { @@ -75,7 +75,7 @@ func (warrior *Warrior) registerCleaveSpell(realismICD *core.Cooldown) { ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { for idx := range results { - baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) results[idx] = spell.CalcDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) target = sim.Environment.NextTargetUnit(target) } diff --git a/sim/warrior/mortal_strike.go b/sim/warrior/mortal_strike.go index ef1926ad9..872be80af 100644 --- a/sim/warrior/mortal_strike.go +++ b/sim/warrior/mortal_strike.go @@ -44,7 +44,7 @@ func (warrior *Warrior) registerMortalStrikeSpell(cdTimer *core.Timer) { BonusCoefficient: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - baseDamage := bonusDamage + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := bonusDamage + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) diff --git a/sim/warrior/overpower.go b/sim/warrior/overpower.go index 6d6849a8f..68786b180 100644 --- a/sim/warrior/overpower.go +++ b/sim/warrior/overpower.go @@ -64,7 +64,7 @@ func (warrior *Warrior) registerOverpowerSpell(cdTimer *core.Timer) { BonusCoefficient: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - baseDamage := bonusDamage + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := bonusDamage + spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeSpecialNoBlockDodgeParry) warrior.OverpowerAura.Deactivate(sim) diff --git a/sim/warrior/shield_slam.go b/sim/warrior/shield_slam.go index 7d7ac0571..8019d748c 100644 --- a/sim/warrior/shield_slam.go +++ b/sim/warrior/shield_slam.go @@ -52,7 +52,7 @@ func (warrior *Warrior) registerShieldSlamSpell() { BonusCoefficient: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - damage := sim.Roll(damageLow, damageHigh) + warrior.BlockValue()*2 + apCoef*spell.MeleeAttackPower() + damage := sim.Roll(damageLow, damageHigh) + warrior.BlockValue()*2 + apCoef*spell.MeleeAttackPower(target) result := spell.CalcAndDealDamage(sim, target, damage, spell.OutcomeMeleeSpecialHitAndCrit) if !result.Landed() { diff --git a/sim/warrior/slam.go b/sim/warrior/slam.go index 5809437de..7c743a294 100644 --- a/sim/warrior/slam.go +++ b/sim/warrior/slam.go @@ -44,9 +44,8 @@ func (warrior *Warrior) registerSlamSpell() { FlatThreatBonus: 140, // Should this be 54 or the old 140 value from before SoD? BonusCoefficient: 1, - ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := flatDamageBonus + spell.Unit.MHWeaponDamage(sim, spell.MeleeAttackPower(target)) result := spell.CalcAndDealDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) if !result.Landed() { diff --git a/sim/warrior/sweeping_strikes.go b/sim/warrior/sweeping_strikes.go index 062a057e0..3686651a1 100644 --- a/sim/warrior/sweeping_strikes.go +++ b/sim/warrior/sweeping_strikes.go @@ -42,7 +42,7 @@ func (warrior *Warrior) registerSweepingStrikesCD() { ThreatMultiplier: 1, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - damage := spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower()) + damage := spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower(target)) spell.CalcAndDealDamage(sim, target, damage, spell.OutcomeMeleeSpecialCritOnly) }, }) diff --git a/sim/warrior/whirlwind.go b/sim/warrior/whirlwind.go index 965fc0c86..f2272fd6f 100644 --- a/sim/warrior/whirlwind.go +++ b/sim/warrior/whirlwind.go @@ -38,7 +38,7 @@ func (warrior *Warrior) registerWhirlwindSpell() { ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { for idx := range results { - baseDamage := spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower()) + baseDamage := spell.Unit.MHNormalizedWeaponDamage(sim, spell.MeleeAttackPower(target)) results[idx] = spell.CalcDamage(sim, target, baseDamage, spell.OutcomeMeleeWeaponSpecialHitAndCrit) target = sim.Environment.NextTargetUnit(target) } @@ -48,4 +48,4 @@ func (warrior *Warrior) registerWhirlwindSpell() { } }, }) -} \ No newline at end of file +}