From 3233033b9609a8b34b834dbf7b535ab88b548c1e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Johan=20Hillerstr=C3=B6m?= Date: Wed, 7 Aug 2024 01:28:20 +0200 Subject: [PATCH 1/2] Allow Apparatus of Khaz'goroth to be used at any stack size --- sim/common/cata/other_effects.go | 281 +++++++++--------- sim/death_knight/frost/TestFrost.results | 8 +- sim/death_knight/unholy/TestUnholy.results | 8 +- sim/druid/feral/TestFeral.results | 8 +- sim/druid/guardian/TestGuardian.results | 8 +- sim/hunter/beast_mastery/TestBM.results | 8 +- sim/hunter/survival/TestSV.results | 8 +- .../retribution/TestRetribution.results | 8 +- .../assassination/TestAssassination.results | 8 +- sim/rogue/combat/TestCombat.results | 8 +- sim/rogue/subtlety/TestSubtlety.results | 8 +- .../enhancement/TestEnhancement.results | 8 +- sim/warrior/arms/TestArms.results | 8 +- 13 files changed, 183 insertions(+), 194 deletions(-) diff --git a/sim/common/cata/other_effects.go b/sim/common/cata/other_effects.go index bd83cc726f..42a581eac1 100644 --- a/sim/common/cata/other_effects.go +++ b/sim/common/cata/other_effects.go @@ -525,154 +525,17 @@ func init() { }) }) - core.NewItemEffect(68972, func(agent core.Agent) { - character := agent.GetCharacter() - - dummyAura := character.RegisterAura(core.Aura{ - Label: "Titanic Power", - ActionID: core.ActionID{SpellID: 96923}, - Duration: time.Second * 30, - MaxStacks: 5, - }) - - core.MakePermanent(core.MakeProcTriggerAura(&character.Unit, core.ProcTrigger{ - Name: "Titanic Power Aura", - ActionID: core.ActionID{ItemID: 68972}, - Callback: core.CallbackOnSpellHitDealt, - ProcMask: core.ProcMaskMelee, - ProcChance: 1, - Outcome: core.OutcomeCrit, - Handler: func(sim *core.Simulation, spell *core.Spell, result *core.SpellResult) { - dummyAura.Activate(sim) - dummyAura.AddStack(sim) - }, - })) - - statBonus := float64(508 * dummyAura.MaxStacks) - buffAuraCrit := character.NewTemporaryStatsAura("Blessing of the Shaper Crit", core.ActionID{SpellID: 96928}, stats.Stats{stats.MeleeCrit: statBonus, stats.SpellCrit: statBonus}, time.Second*15) - buffAuraHaste := character.NewTemporaryStatsAura("Blessing of the Shaper Haste", core.ActionID{SpellID: 96927}, stats.Stats{stats.MeleeHaste: statBonus, stats.SpellHaste: statBonus}, time.Second*15) - buffAuraMastery := character.NewTemporaryStatsAura("Blessing of the Shaper Mastery", core.ActionID{SpellID: 96929}, stats.Stats{stats.Mastery: statBonus}, time.Second*15) - - sharedCD := character.GetOffensiveTrinketCD() - trinketSpell := character.RegisterSpell(core.SpellConfig{ - ActionID: core.ActionID{ItemID: 68972}, - SpellSchool: core.SpellSchoolPhysical, - ProcMask: core.ProcMaskEmpty, - Flags: core.SpellFlagNoOnCastComplete, - Cast: core.CastConfig{ - SharedCD: core.Cooldown{ - Timer: sharedCD, - Duration: time.Second * 15, - }, - CD: core.Cooldown{ - Timer: character.NewTimer(), - Duration: time.Minute * 2, - }, - }, - - ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - statType := character.GetHighestStat([]stats.Stat{stats.MeleeCrit, stats.SpellCrit, stats.MeleeHaste, stats.SpellHaste, stats.Mastery}) - switch statType { - case stats.MeleeCrit, stats.SpellCrit: - buffAuraCrit.Activate(sim) - case stats.MeleeHaste, stats.SpellHaste: - buffAuraHaste.Activate(sim) - case stats.Mastery: - buffAuraMastery.Activate(sim) - default: - panic("unexpected statType") - } - dummyAura.Deactivate(sim) - }, - ExtraCastCondition: func(sim *core.Simulation, target *core.Unit) bool { - return dummyAura.GetStacks() == 5 - }, - }) - - character.AddMajorCooldown(core.MajorCooldown{ - Spell: trinketSpell, - Priority: core.CooldownPriorityDefault, - Type: core.CooldownTypeDPS, - ShouldActivate: func(s *core.Simulation, c *core.Character) bool { - return dummyAura.GetStacks() == 5 - }, - }) + // Normal + registerApparatusOfKhazGoroth(apparatusConfig{ + ItemID: 68972, + StatBonus: 508, }) - core.NewItemEffect(69113, func(agent core.Agent) { - character := agent.GetCharacter() - - dummyAura := character.RegisterAura(core.Aura{ - Label: "Titanic Power (Heroic)", - ActionID: core.ActionID{SpellID: 96923}, - Duration: time.Second * 30, - MaxStacks: 5, - }) - - core.MakePermanent(core.MakeProcTriggerAura(&character.Unit, core.ProcTrigger{ - Name: "Titanic Power Aura (Heroic)", - ActionID: core.ActionID{ItemID: 69113}, - Callback: core.CallbackOnSpellHitDealt, - ProcMask: core.ProcMaskMelee, - ProcChance: 1, - Outcome: core.OutcomeCrit, - Handler: func(sim *core.Simulation, spell *core.Spell, result *core.SpellResult) { - dummyAura.Activate(sim) - dummyAura.AddStack(sim) - }, - })) - - // TODO: discuss the following scenario: - // the trinket should allow to activate at any number of stacks, should we allow this behaviour at all to the users? - // would also mean that we need the temporary aura to be created on the fly after an environment is finalized - statBonus := float64(575 * dummyAura.MaxStacks) - buffAuraCrit := character.NewTemporaryStatsAura("Blessing of the Shaper Crit (Heroic)", core.ActionID{SpellID: 96928}, stats.Stats{stats.MeleeCrit: statBonus, stats.SpellCrit: statBonus}, time.Second*15) - buffAuraHaste := character.NewTemporaryStatsAura("Blessing of the Shaper Haste (Heroic)", core.ActionID{SpellID: 96927}, stats.Stats{stats.MeleeHaste: statBonus, stats.SpellHaste: statBonus}, time.Second*15) - buffAuraMastery := character.NewTemporaryStatsAura("Blessing of the Shaper Mastery (Heroic)", core.ActionID{SpellID: 96929}, stats.Stats{stats.Mastery: statBonus}, time.Second*15) - - sharedCD := character.GetOffensiveTrinketCD() - trinketSpell := character.RegisterSpell(core.SpellConfig{ - ActionID: core.ActionID{ItemID: 69113}, - SpellSchool: core.SpellSchoolPhysical, - ProcMask: core.ProcMaskEmpty, - Flags: core.SpellFlagNoOnCastComplete, - Cast: core.CastConfig{ - SharedCD: core.Cooldown{ - Timer: sharedCD, - Duration: time.Second * 15, - }, - CD: core.Cooldown{ - Timer: character.NewTimer(), - Duration: time.Minute * 2, - }, - }, - ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { - statType := character.GetHighestStat([]stats.Stat{stats.MeleeCrit, stats.SpellCrit, stats.MeleeHaste, stats.SpellHaste, stats.Mastery}) - switch statType { - case stats.MeleeCrit, stats.SpellCrit: - buffAuraCrit.Activate(sim) - case stats.MeleeHaste, stats.SpellHaste: - buffAuraHaste.Activate(sim) - case stats.Mastery: - buffAuraMastery.Activate(sim) - default: - panic("unexpected statType") - } - dummyAura.Deactivate(sim) - }, - ExtraCastCondition: func(sim *core.Simulation, target *core.Unit) bool { - return dummyAura.GetStacks() == 5 - }, - }) - - character.AddMajorCooldown(core.MajorCooldown{ - Spell: trinketSpell, - Priority: core.CooldownPriorityDefault, - Type: core.CooldownTypeDPS, - ShouldActivate: func(s *core.Simulation, c *core.Character) bool { - return dummyAura.GetStacks() == 5 - }, - }) + // Heroic + registerApparatusOfKhazGoroth(apparatusConfig{ + ItemID: 69113, + StatBonus: 575, + Heroic: true, }) core.NewItemEffect(68994, func(agent core.Agent) { @@ -761,3 +624,129 @@ func init() { }) }) } + +type apparatusConfig struct { + ItemID int32 + StatBonus float64 + Heroic bool +} + +func registerApparatusOfKhazGoroth(config apparatusConfig) { + core.NewItemEffect(config.ItemID, func(agent core.Agent) { + character := agent.GetCharacter() + + var stacks int32 + var buffs stats.Stats + + labelSuffix := core.Ternary(config.Heroic, " (Heroic)", "") + buffDuration := time.Second * 15 + buffAuraOnGain := func(aura *core.Aura, sim *core.Simulation) { + aura.SetStacks(sim, stacks) + character.AddStatsDynamic(sim, buffs) + } + buffAuraOnExpire := func(aura *core.Aura, sim *core.Simulation) { + character.AddStatsDynamic(sim, buffs.Invert()) + } + + buffAuraCrit := character.GetOrRegisterAura(core.Aura{ + Label: "Blessing of the Shaper Crit" + labelSuffix, + ActionID: core.ActionID{SpellID: 96928}, + MaxStacks: 5, + Duration: buffDuration, + OnGain: buffAuraOnGain, + OnExpire: buffAuraOnExpire, + }) + + buffAuraHaste := character.GetOrRegisterAura(core.Aura{ + Label: "Blessing of the Shaper Haste" + labelSuffix, + ActionID: core.ActionID{SpellID: 96927}, + MaxStacks: 5, + Duration: buffDuration, + OnGain: buffAuraOnGain, + OnExpire: buffAuraOnExpire, + }) + + buffAuraMastery := character.GetOrRegisterAura(core.Aura{ + Label: "Blessing of the Shaper Mastery" + labelSuffix, + ActionID: core.ActionID{SpellID: 96929}, + MaxStacks: 5, + Duration: buffDuration, + OnGain: buffAuraOnGain, + OnExpire: buffAuraOnExpire, + }) + + titanicPower := character.RegisterAura(core.Aura{ + Label: "Titanic Power" + labelSuffix, + ActionID: core.ActionID{SpellID: 96923}, + Duration: time.Second * 30, + MaxStacks: 5, + }) + + core.MakePermanent(core.MakeProcTriggerAura(&character.Unit, core.ProcTrigger{ + Name: "Titanic Power Aura" + labelSuffix, + ActionID: core.ActionID{SpellID: 96924}, + Callback: core.CallbackOnSpellHitDealt, + ProcMask: core.ProcMaskMelee, + ProcChance: 1, + Outcome: core.OutcomeCrit, + Handler: func(sim *core.Simulation, spell *core.Spell, result *core.SpellResult) { + if buffAuraCrit.IsActive() || buffAuraHaste.IsActive() || buffAuraMastery.IsActive() { + return + } + + titanicPower.Activate(sim) + titanicPower.AddStack(sim) + }, + })) + + trinketSpell := character.RegisterSpell(core.SpellConfig{ + ActionID: core.ActionID{ItemID: config.ItemID}, + SpellSchool: core.SpellSchoolPhysical, + ProcMask: core.ProcMaskEmpty, + Flags: core.SpellFlagNoOnCastComplete, + Cast: core.CastConfig{ + SharedCD: core.Cooldown{ + Timer: character.GetOffensiveTrinketCD(), + Duration: time.Second * 15, + }, + CD: core.Cooldown{ + Timer: character.NewTimer(), + Duration: time.Minute * 2, + }, + }, + ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { + statType := character.GetHighestStat([]stats.Stat{stats.MeleeCrit, stats.SpellCrit, stats.MeleeHaste, stats.SpellHaste, stats.Mastery}) + stacks = titanicPower.GetStacks() + statBonus := config.StatBonus * float64(stacks) + + switch statType { + case stats.MeleeCrit, stats.SpellCrit: + buffs = stats.Stats{stats.MeleeCrit: statBonus, stats.SpellCrit: statBonus} + buffAuraCrit.Activate(sim) + case stats.MeleeHaste, stats.SpellHaste: + buffs = stats.Stats{stats.MeleeHaste: statBonus, stats.SpellHaste: statBonus} + buffAuraHaste.Activate(sim) + case stats.Mastery: + buffs = stats.Stats{stats.Mastery: statBonus} + buffAuraMastery.Activate(sim) + default: + panic("unexpected statType") + } + + titanicPower.Deactivate(sim) + }, + ExtraCastCondition: func(sim *core.Simulation, target *core.Unit) bool { + return titanicPower.IsActive() + }, + }) + + character.AddMajorCooldown(core.MajorCooldown{ + Spell: trinketSpell, + Priority: core.CooldownPriorityDefault, + Type: core.CooldownTypeDPS, + ShouldActivate: func(sim *core.Simulation, character *core.Character) bool { + return titanicPower.IsActive() + }, + }) + }) +} diff --git a/sim/death_knight/frost/TestFrost.results b/sim/death_knight/frost/TestFrost.results index 00146f0d47..e1d0bbb577 100644 --- a/sim/death_knight/frost/TestFrost.results +++ b/sim/death_knight/frost/TestFrost.results @@ -77,16 +77,16 @@ dps_results: { dps_results: { key: "TestFrost-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 22036.10262 - tps: 20060.543 + dps: 21909.90806 + tps: 19989.14724 hps: 215.12703 } } dps_results: { key: "TestFrost-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 22201.03467 - tps: 20208.76484 + dps: 22067.1986 + tps: 20136.09603 hps: 215.12703 } } diff --git a/sim/death_knight/unholy/TestUnholy.results b/sim/death_knight/unholy/TestUnholy.results index 1f00620772..02d10c07fc 100644 --- a/sim/death_knight/unholy/TestUnholy.results +++ b/sim/death_knight/unholy/TestUnholy.results @@ -77,16 +77,16 @@ dps_results: { dps_results: { key: "TestUnholy-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 31621.40757 - tps: 23470.51463 + dps: 31463.48524 + tps: 23359.66173 hps: 473.88367 } } dps_results: { key: "TestUnholy-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 31871.2664 - tps: 23648.71678 + dps: 31707.61605 + tps: 23538.65395 hps: 473.88367 } } diff --git a/sim/druid/feral/TestFeral.results b/sim/druid/feral/TestFeral.results index ea38cc9829..3b18e7414f 100644 --- a/sim/druid/feral/TestFeral.results +++ b/sim/druid/feral/TestFeral.results @@ -72,15 +72,15 @@ dps_results: { dps_results: { key: "TestFeral-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 26010.16289 - tps: 36366.3166 + dps: 25884.26602 + tps: 36625.42619 } } dps_results: { key: "TestFeral-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 26164.81755 - tps: 36466.50053 + dps: 25984.84193 + tps: 36758.48515 } } dps_results: { diff --git a/sim/druid/guardian/TestGuardian.results b/sim/druid/guardian/TestGuardian.results index 1b1ab8b32d..fc74ad656b 100644 --- a/sim/druid/guardian/TestGuardian.results +++ b/sim/druid/guardian/TestGuardian.results @@ -72,15 +72,15 @@ dps_results: { dps_results: { key: "TestGuardian-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 7800.83542 - tps: 39070.13604 + dps: 7843.78516 + tps: 39285.30684 } } dps_results: { key: "TestGuardian-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 7833.11618 - tps: 39231.31568 + dps: 7887.29914 + tps: 39502.63676 } } dps_results: { diff --git a/sim/hunter/beast_mastery/TestBM.results b/sim/hunter/beast_mastery/TestBM.results index a2101880a4..1e3870de03 100644 --- a/sim/hunter/beast_mastery/TestBM.results +++ b/sim/hunter/beast_mastery/TestBM.results @@ -86,15 +86,15 @@ dps_results: { dps_results: { key: "TestBM-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 21087.82523 - tps: 17814.40527 + dps: 21097.03318 + tps: 17811.53822 } } dps_results: { key: "TestBM-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 21164.59151 - tps: 17896.62613 + dps: 21145.32226 + tps: 17859.07559 } } dps_results: { diff --git a/sim/hunter/survival/TestSV.results b/sim/hunter/survival/TestSV.results index 9548d0f039..fa1a02f9c3 100644 --- a/sim/hunter/survival/TestSV.results +++ b/sim/hunter/survival/TestSV.results @@ -86,15 +86,15 @@ dps_results: { dps_results: { key: "TestSV-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 24461.81628 - tps: 22098.30071 + dps: 24475.60132 + tps: 22111.63781 } } dps_results: { key: "TestSV-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 24461.81628 - tps: 22098.30071 + dps: 24478.64407 + tps: 22114.68056 } } dps_results: { diff --git a/sim/paladin/retribution/TestRetribution.results b/sim/paladin/retribution/TestRetribution.results index 0d8d47a69c..4657ae65b4 100644 --- a/sim/paladin/retribution/TestRetribution.results +++ b/sim/paladin/retribution/TestRetribution.results @@ -72,15 +72,15 @@ dps_results: { dps_results: { key: "TestRetribution-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 31403.53353 - tps: 31417.05972 + dps: 31409.3774 + tps: 31422.9036 } } dps_results: { key: "TestRetribution-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 31633.63822 - tps: 31647.16442 + dps: 31655.18248 + tps: 31668.70868 } } dps_results: { diff --git a/sim/rogue/assassination/TestAssassination.results b/sim/rogue/assassination/TestAssassination.results index 64fec3f24a..e736894d6d 100644 --- a/sim/rogue/assassination/TestAssassination.results +++ b/sim/rogue/assassination/TestAssassination.results @@ -72,15 +72,15 @@ dps_results: { dps_results: { key: "TestAssassination-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 29041.24752 - tps: 20619.28574 + dps: 28897.75384 + tps: 20517.40522 } } dps_results: { key: "TestAssassination-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 29245.3315 - tps: 20764.18536 + dps: 29047.38695 + tps: 20623.64473 } } dps_results: { diff --git a/sim/rogue/combat/TestCombat.results b/sim/rogue/combat/TestCombat.results index 45c5786185..0a06a7ce2c 100644 --- a/sim/rogue/combat/TestCombat.results +++ b/sim/rogue/combat/TestCombat.results @@ -79,15 +79,15 @@ dps_results: { dps_results: { key: "TestCombat-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 28292.44384 - tps: 20087.63513 + dps: 28117.49391 + tps: 19963.42068 } } dps_results: { key: "TestCombat-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 28439.07144 - tps: 20191.74072 + dps: 28237.39571 + tps: 20048.55096 } } dps_results: { diff --git a/sim/rogue/subtlety/TestSubtlety.results b/sim/rogue/subtlety/TestSubtlety.results index 68ab6907b4..c1a92151be 100644 --- a/sim/rogue/subtlety/TestSubtlety.results +++ b/sim/rogue/subtlety/TestSubtlety.results @@ -73,15 +73,15 @@ dps_results: { dps_results: { key: "TestSubtlety-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 23175.16269 - tps: 16454.36551 + dps: 22823.72908 + tps: 16204.84765 } } dps_results: { key: "TestSubtlety-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 23396.77387 - tps: 16611.70945 + dps: 22956.18869 + tps: 16298.89397 } } dps_results: { diff --git a/sim/shaman/enhancement/TestEnhancement.results b/sim/shaman/enhancement/TestEnhancement.results index 1072a7bda3..f961123921 100644 --- a/sim/shaman/enhancement/TestEnhancement.results +++ b/sim/shaman/enhancement/TestEnhancement.results @@ -79,15 +79,15 @@ dps_results: { dps_results: { key: "TestEnhancement-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 28806.25629 - tps: 19233.5887 + dps: 28652.49821 + tps: 19126.39149 } } dps_results: { key: "TestEnhancement-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 28929.79783 - tps: 19314.51526 + dps: 28774.34195 + tps: 19213.34186 } } dps_results: { diff --git a/sim/warrior/arms/TestArms.results b/sim/warrior/arms/TestArms.results index 6c2a4e6c3f..5233b24373 100644 --- a/sim/warrior/arms/TestArms.results +++ b/sim/warrior/arms/TestArms.results @@ -72,15 +72,15 @@ dps_results: { dps_results: { key: "TestArms-AllItems-ApparatusofKhaz'goroth-68972" value: { - dps: 33915.64794 - tps: 22723.80573 + dps: 33902.42086 + tps: 22710.57865 } } dps_results: { key: "TestArms-AllItems-ApparatusofKhaz'goroth-69113" value: { - dps: 34198.92908 - tps: 22918.66312 + dps: 34196.35596 + tps: 22916.09 } } dps_results: { From 4b011afa8846806e964f3dc9bbf970968846231b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Johan=20Hillerstr=C3=B6m?= Date: Fri, 9 Aug 2024 17:48:01 +0200 Subject: [PATCH 2/2] Add aura helper to clean up code --- sim/common/cata/other_effects.go | 80 +++++++++++++------------------- sim/core/aura_helpers.go | 12 +++++ 2 files changed, 43 insertions(+), 49 deletions(-) diff --git a/sim/common/cata/other_effects.go b/sim/common/cata/other_effects.go index 42a581eac1..289e6954c7 100644 --- a/sim/common/cata/other_effects.go +++ b/sim/common/cata/other_effects.go @@ -527,15 +527,15 @@ func init() { // Normal registerApparatusOfKhazGoroth(apparatusConfig{ - ItemID: 68972, - StatBonus: 508, + ItemID: 68972, + BonusPerStack: 508, }) // Heroic registerApparatusOfKhazGoroth(apparatusConfig{ - ItemID: 69113, - StatBonus: 575, - Heroic: true, + ItemID: 69113, + BonusPerStack: 575, + Heroic: true, }) core.NewItemEffect(68994, func(agent core.Agent) { @@ -626,54 +626,38 @@ func init() { } type apparatusConfig struct { - ItemID int32 - StatBonus float64 - Heroic bool + ItemID int32 + BonusPerStack float64 + Heroic bool } func registerApparatusOfKhazGoroth(config apparatusConfig) { core.NewItemEffect(config.ItemID, func(agent core.Agent) { character := agent.GetCharacter() - var stacks int32 - var buffs stats.Stats - labelSuffix := core.Ternary(config.Heroic, " (Heroic)", "") buffDuration := time.Second * 15 - buffAuraOnGain := func(aura *core.Aura, sim *core.Simulation) { - aura.SetStacks(sim, stacks) - character.AddStatsDynamic(sim, buffs) - } - buffAuraOnExpire := func(aura *core.Aura, sim *core.Simulation) { - character.AddStatsDynamic(sim, buffs.Invert()) - } - - buffAuraCrit := character.GetOrRegisterAura(core.Aura{ - Label: "Blessing of the Shaper Crit" + labelSuffix, - ActionID: core.ActionID{SpellID: 96928}, - MaxStacks: 5, - Duration: buffDuration, - OnGain: buffAuraOnGain, - OnExpire: buffAuraOnExpire, - }) - buffAuraHaste := character.GetOrRegisterAura(core.Aura{ - Label: "Blessing of the Shaper Haste" + labelSuffix, - ActionID: core.ActionID{SpellID: 96927}, - MaxStacks: 5, - Duration: buffDuration, - OnGain: buffAuraOnGain, - OnExpire: buffAuraOnExpire, - }) - - buffAuraMastery := character.GetOrRegisterAura(core.Aura{ - Label: "Blessing of the Shaper Mastery" + labelSuffix, - ActionID: core.ActionID{SpellID: 96929}, - MaxStacks: 5, - Duration: buffDuration, - OnGain: buffAuraOnGain, - OnExpire: buffAuraOnExpire, - }) + buffAuraCrit := character.NewTemporaryStatBuffWithStacks( + "Blessing of the Shaper Crit"+labelSuffix, + core.ActionID{SpellID: 96928}, + stats.Stats{stats.MeleeCrit: config.BonusPerStack, stats.SpellCrit: config.BonusPerStack}, + 5, + buffDuration) + + buffAuraHaste := character.NewTemporaryStatBuffWithStacks( + "Blessing of the Shaper Haste"+labelSuffix, + core.ActionID{SpellID: 96927}, + stats.Stats{stats.MeleeHaste: config.BonusPerStack, stats.SpellHaste: config.BonusPerStack}, + 5, + buffDuration) + + buffAuraMastery := character.NewTemporaryStatBuffWithStacks( + "Blessing of the Shaper Mastery"+labelSuffix, + core.ActionID{SpellID: 96929}, + stats.Stats{stats.Mastery: config.BonusPerStack}, + 5, + buffDuration) titanicPower := character.RegisterAura(core.Aura{ Label: "Titanic Power" + labelSuffix, @@ -716,19 +700,17 @@ func registerApparatusOfKhazGoroth(config apparatusConfig) { }, ApplyEffects: func(sim *core.Simulation, target *core.Unit, spell *core.Spell) { statType := character.GetHighestStat([]stats.Stat{stats.MeleeCrit, stats.SpellCrit, stats.MeleeHaste, stats.SpellHaste, stats.Mastery}) - stacks = titanicPower.GetStacks() - statBonus := config.StatBonus * float64(stacks) switch statType { case stats.MeleeCrit, stats.SpellCrit: - buffs = stats.Stats{stats.MeleeCrit: statBonus, stats.SpellCrit: statBonus} buffAuraCrit.Activate(sim) + buffAuraCrit.SetStacks(sim, titanicPower.GetStacks()) case stats.MeleeHaste, stats.SpellHaste: - buffs = stats.Stats{stats.MeleeHaste: statBonus, stats.SpellHaste: statBonus} buffAuraHaste.Activate(sim) + buffAuraHaste.SetStacks(sim, titanicPower.GetStacks()) case stats.Mastery: - buffs = stats.Stats{stats.Mastery: statBonus} buffAuraMastery.Activate(sim) + buffAuraMastery.SetStacks(sim, titanicPower.GetStacks()) default: panic("unexpected statType") } diff --git a/sim/core/aura_helpers.go b/sim/core/aura_helpers.go index d0af3fd5e0..8017cf1ca2 100644 --- a/sim/core/aura_helpers.go +++ b/sim/core/aura_helpers.go @@ -224,6 +224,18 @@ func MakePermanent(aura *Aura) *Aura { return aura } +func (character *Character) NewTemporaryStatBuffWithStacks(auraLabel string, actionID ActionID, bonusPerStack stats.Stats, maxStacks int32, duration time.Duration) *Aura { + return MakeStackingAura(character, StackingStatAura{ + Aura: Aura{ + Label: auraLabel, + ActionID: actionID, + Duration: duration, + MaxStacks: maxStacks, + }, + BonusPerStack: bonusPerStack, + }) +} + // Helper for the common case of making an aura that adds stats. func (character *Character) NewTemporaryStatsAura(auraLabel string, actionID ActionID, tempStats stats.Stats, duration time.Duration) *Aura { return character.NewTemporaryStatsAuraWrapped(auraLabel, actionID, tempStats, duration, nil)