You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
448 lines
16 KiB
448 lines
16 KiB
--------------------------------------------------------------------------------
|
|
-- Module Declaration
|
|
--
|
|
|
|
local mod, CL = BigWigs:NewBoss("Halondrus the Reclaimer", 2481, 2463)
|
|
if not mod then return end
|
|
mod:RegisterEnableMob(180906) -- Halondrus
|
|
mod:SetEncounterID(2529)
|
|
mod:SetRespawnTime(30)
|
|
|
|
--------------------------------------------------------------------------------
|
|
-- Locals
|
|
--
|
|
|
|
local reclaimCount = 1
|
|
local seismicTremorsCount = 1
|
|
local misslesCount = 1
|
|
local beamCount = 1
|
|
local prismCount = 1
|
|
local reclamationFormCount = 1
|
|
local relocationFormCount = 1
|
|
local shatterCount = 1
|
|
local intermission = false
|
|
local nextStageWarning = 82
|
|
|
|
--------------------------------------------------------------------------------
|
|
-- Timers
|
|
--
|
|
|
|
local missleTimersP3 = {17.1, 25.1, 36.5, 13} -- Earthbreaker Missiles
|
|
local intermissionTimersHeroic = {
|
|
[364979] = { -- Shatter
|
|
[1] = {36, 22.1, 0},
|
|
[2] = {29.9, 24.1, 18.0, 0},
|
|
},
|
|
[365297] = { -- Crushing Prism
|
|
[1] = {31.2, 0},
|
|
[2] = {47, 0},
|
|
},
|
|
[361676] = { -- Earthbreaker Missiles
|
|
[1] = {10.2, 26.1},
|
|
[2] = {6.1, 18.1, 26.1},
|
|
}
|
|
}
|
|
local intermissionTimersMythic = {
|
|
[364979] = { -- Shatter
|
|
[1] = {24.5, 22.1, 0},
|
|
[2] = {18.6, 24.1, 18.0, 0},
|
|
},
|
|
[365297] = { -- Crushing Prism
|
|
[1] = {5.6, 26.0, 14.0, 0},
|
|
[2] = {13.6, 18.1, 18.1, 0},
|
|
},
|
|
[361676] = { -- Earthbreaker Missiles
|
|
[1] = {10.5, 26.1, 37.7},
|
|
[2] = {6.1, 18.1, 26.1, 46.3},
|
|
}
|
|
}
|
|
local intermissionTimers = mod:Mythic() and intermissionTimersMythic or intermissionTimersHeroic
|
|
|
|
--------------------------------------------------------------------------------
|
|
-- Localization
|
|
--
|
|
|
|
local L = mod:GetLocale()
|
|
if L then
|
|
L.seismic_tremors = "Motes + Tremors" -- Seismic Tremors
|
|
L.earthbreaker_missiles = "Missiles" -- Earthbreaker Missiles
|
|
L.crushing_prism = "Prisms" -- Crushing Prism
|
|
L.prism = "Prism"
|
|
L.ephemeral_fissure = "Fissure"
|
|
|
|
L.bomb_dropped = "Bomb dropped"
|
|
|
|
L.custom_on_stop_timers = "Always show ability bars"
|
|
L.custom_on_stop_timers_desc = "Halondrus can delay its abilities. When this option is enabled, the bars for those abilities will stay on your screen."
|
|
end
|
|
|
|
--------------------------------------------------------------------------------
|
|
-- Initialization
|
|
--
|
|
|
|
local crushingPrismMarker = mod:AddMarkerOption(false, "player", 1, 365297, 1, 2, 3, 4) -- Crushing Prism
|
|
function mod:GetOptions()
|
|
return {
|
|
"stages",
|
|
"custom_on_stop_timers",
|
|
368969, -- Volatile Charge
|
|
360115, -- Reclaim XXX Shield tracker
|
|
367079, -- Seismic Tremors
|
|
360114, -- Ephemeral Fissure
|
|
361676, -- Earthbreaker Missiles
|
|
369207, -- Planetcracker Beam
|
|
{360977, "TANK"}, -- Lightshatter Beam
|
|
{365297, "SAY"}, -- Crushing Prism
|
|
crushingPrismMarker,
|
|
368363, -- Shattered Prism
|
|
364979, -- Shatter
|
|
368529, -- Eternity Overdrive
|
|
},{
|
|
["stages"] = "general",
|
|
[360115] = -23915, -- Stage One: The Reclaimer
|
|
[362056] = -23917, -- Stage Two: The Shimmering Cliffs
|
|
[368529] = -24707, -- Stage Three: A Broken Cycle
|
|
},{
|
|
[368969] = CL.bomb,
|
|
[367079] = L.seismic_tremors,
|
|
[360114] = L.ephemeral_fissure,
|
|
[361676] = L.earthbreaker_missiles,
|
|
[360977] = CL.beam,
|
|
[365297] = L.crushing_prism,
|
|
}
|
|
end
|
|
|
|
function mod:VerifyEnable(unit)
|
|
return UnitCanAttack("player", unit)
|
|
end
|
|
|
|
function mod:OnBossEnable()
|
|
self:Log("SPELL_CAST_START", "Reclaim", 360115)
|
|
self:Log("SPELL_AURA_APPLIED_DOSE", "ReclaimedDose", 360115)
|
|
self:Log("SPELL_AURA_REMOVED", "ReclaimRemoved", 360115)
|
|
self:Log("SPELL_CAST_START", "SeismicTremors", 367079)
|
|
self:Log("SPELL_CAST_START", "EarthbreakerMissiles", 361676)
|
|
self:Log("SPELL_CAST_START", "LightshatterBeam", 360977)
|
|
self:Log("SPELL_AURA_APPLIED", "LightshatterBeamApplied", 361309)
|
|
self:Log("SPELL_AURA_APPLIED_DOSE", "LightshatterBeamApplied", 361309)
|
|
self:Log("SPELL_AURA_APPLIED", "CrushingPrismApplied", 365297)
|
|
self:Log("SPELL_AURA_REMOVED", "CrushingPrismRemoved", 365297)
|
|
self:Log("SPELL_CAST_START", "ReclamationForm", 359235)
|
|
self:Log("SPELL_CAST_START", "RelocationForm", 359236)
|
|
self:Log("SPELL_CAST_SUCCESS", "RelocationFormDone", 359236)
|
|
self:Log("SPELL_CAST_START", "Shatter", 364979)
|
|
self:Log("SPELL_CAST_START", "EternityOverdrive", 368529)
|
|
|
|
-- Planetcracker Beam, Shattered Prism, Ephemeral Fissure
|
|
self:Log("SPELL_AURA_APPLIED", "GroundDamage", 369207, 368363, 360114)
|
|
self:Log("SPELL_PERIODIC_DAMAGE", "GroundDamage", 369207, 368363, 360114)
|
|
self:Log("SPELL_PERIODIC_MISSED", "GroundDamage", 369207, 368363, 360114)
|
|
|
|
self:Log("SPELL_AURA_APPLIED", "VolatileChargeApplied", 368969)
|
|
self:Log("SPELL_AURA_REMOVED", "VolatileChargeRemoved", 368969)
|
|
|
|
self:RegisterMessage("BigWigs_BarCreated", "BarCreated")
|
|
end
|
|
|
|
function mod:OnEngage()
|
|
self:SetStage(1)
|
|
seismicTremorsCount = 1
|
|
reclaimCount = 1
|
|
misslesCount = 1
|
|
beamCount = 1
|
|
prismCount = 1
|
|
reclamationFormCount = 1
|
|
relocationFormCount = 1
|
|
shatterCount = 1
|
|
intermission = false
|
|
nextStageWarning = 79.5
|
|
intermissionTimers = self:Mythic() and intermissionTimersMythic or intermissionTimersHeroic
|
|
|
|
if not self:Easy() then
|
|
self:CDBar(360977, 8, CL.beam) -- Lightshatter Beam
|
|
end
|
|
self:Bar(367079, self:Mythic() and 4.9 or 8, CL.count:format(L.seismic_tremors, seismicTremorsCount))
|
|
self:Bar(365297, self:Mythic() and 17 or 21.1, CL.count:format(L.crushing_prism, prismCount))
|
|
self:Bar(361676, self:Mythic() and 11 or 43.1, CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
self:Bar(360115, 61.2, CL.count:format(self:SpellName(360115), reclaimCount))
|
|
|
|
self:RegisterUnitEvent("UNIT_HEALTH", nil, "boss1")
|
|
end
|
|
|
|
--------------------------------------------------------------------------------
|
|
-- Event Handlers
|
|
--
|
|
|
|
function mod:UNIT_HEALTH(event, unit)
|
|
local currentHealth = self:GetHealth(unit)
|
|
if currentHealth < nextStageWarning then -- Intermission at 77.5% and 45%
|
|
self:Message("stages", "green", CL.soon:format(CL.intermission), false)
|
|
nextStageWarning = nextStageWarning - 32.5
|
|
if nextStageWarning < 40 then
|
|
self:UnregisterUnitEvent(event, unit)
|
|
end
|
|
end
|
|
end
|
|
|
|
do
|
|
local abilitysToPause = {
|
|
[361676] = true, -- Earthbreaker Missiles
|
|
[365297] = true, -- Crushing Prism
|
|
[367079] = true, -- Seismic Tremors
|
|
[360115] = true, -- Reclaim
|
|
[360977] = true, -- Lightshattter Beam
|
|
}
|
|
|
|
local castPattern = CL.cast:gsub("%%s", ".+")
|
|
|
|
local function stopAtZeroSec(bar)
|
|
if bar.remaining < 0.15 then -- Pause at 0.0
|
|
bar:SetDuration(0.01) -- Make the bar look full
|
|
bar:Start()
|
|
bar:Pause()
|
|
bar:SetTimeVisibility(false)
|
|
end
|
|
end
|
|
|
|
function mod:BarCreated(_, _, bar, _, key, text)
|
|
if self:GetOption("custom_on_stop_timers") and abilitysToPause[key] and not text:match(castPattern) then
|
|
bar:AddUpdateFunction(stopAtZeroSec)
|
|
end
|
|
end
|
|
end
|
|
|
|
function mod:VolatileChargeApplied(args)
|
|
if self:Me(args.destGUID) then
|
|
self:PersonalMessage(args.spellId, nil, CL.bomb)
|
|
self:Bar(args.spellId, 10, CL.explosion)
|
|
self:PlaySound(args.spellId, "alarm")
|
|
end
|
|
end
|
|
|
|
function mod:VolatileChargeRemoved(args)
|
|
if self:Me(args.destGUID) then
|
|
self:Message(args.spellId, "green", L.bomb_dropped)
|
|
self:StopBar(CL.explosion)
|
|
self:PlaySound(args.spellId, "info")
|
|
end
|
|
end
|
|
|
|
function mod:Reclaim(args)
|
|
self:StopBar(CL.count:format(args.spellName, reclaimCount))
|
|
self:StopBar(CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
self:StopBar(CL.count:format(L.seismic_tremors, seismicTremorsCount))
|
|
self:StopBar(CL.count:format(L.crushing_prism, prismCount))
|
|
self:StopBar(CL.beam) -- Lightshatter Beam
|
|
|
|
self:Message(args.spellId, "red", CL.count:format(args.spellName, reclaimCount))
|
|
self:PlaySound(args.spellId, "long")
|
|
self:CastBar(args.spellId, 4, CL.count:format(args.spellName, reclaimCount))
|
|
end
|
|
|
|
function mod:ReclaimedDose(args)
|
|
if args.amount > 2 and args.amount % 2 == 1 then -- ramps every 4, warn every other starting with 3
|
|
self:Message(args.spellId, "red", ("%dx %s (%d)"):format(args.amount, args.spellName, reclaimCount))
|
|
self:PlaySound(args.spellId, "alarm")
|
|
end
|
|
end
|
|
|
|
function mod:ReclaimRemoved(args)
|
|
self:Message(args.spellId, "green", CL.removed:format(CL.count:format(args.spellName, reclaimCount)))
|
|
self:PlaySound(args.spellId, "info")
|
|
reclaimCount = reclaimCount + 1
|
|
self:Bar(360115, 61.2, CL.count:format(self:SpellName(360115), reclaimCount))
|
|
|
|
if not self:Easy() then
|
|
self:CDBar(360977, 8, CL.beam) -- Lightshatter Beam
|
|
end
|
|
self:Bar(367079, 4.5, CL.count:format(L.seismic_tremors, seismicTremorsCount))
|
|
self:Bar(365297, self:Mythic() and 17 or 8, CL.count:format(L.crushing_prism, prismCount))
|
|
self:Bar(361676, 11, CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
end
|
|
|
|
function mod:SeismicTremors(args)
|
|
self:StopBar(CL.count:format(L.seismic_tremors, seismicTremorsCount))
|
|
self:Message(args.spellId, "yellow", CL.count:format(L.seismic_tremors, seismicTremorsCount))
|
|
self:PlaySound(args.spellId, "alert")
|
|
seismicTremorsCount = seismicTremorsCount + 1
|
|
if seismicTremorsCount <= reclaimCount * 2 then
|
|
self:Bar(args.spellId, self:Mythic() and 27.5 or 26, CL.count:format(L.seismic_tremors, seismicTremorsCount))
|
|
end
|
|
end
|
|
|
|
function mod:EarthbreakerMissiles(args)
|
|
self:StopBar(CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
self:Message(args.spellId, "orange", CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
self:PlaySound(args.spellId, "alert")
|
|
misslesCount = misslesCount + 1
|
|
if intermission then
|
|
self:CDBar(args.spellId, intermissionTimers[args.spellId][relocationFormCount-1][misslesCount], CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
elseif self:GetStage() == 3 then
|
|
if misslesCount < (self:Mythic() and 4 or 5) then
|
|
self:CDBar(args.spellId, missleTimersP3[misslesCount] or 0, CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
end
|
|
elseif self:Mythic() then
|
|
if misslesCount <= reclaimCount * 2 then
|
|
self:CDBar(args.spellId, 26, CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
end
|
|
elseif (reclaimCount > 1 or relocationFormCount > 1) and misslesCount <= reclaimCount * 2 then
|
|
-- only one earthbreaker before the first reclaim in normal/heroic
|
|
self:CDBar(args.spellId, 26, CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
end
|
|
end
|
|
|
|
function mod:LightshatterBeam(args)
|
|
self:Message(args.spellId, "purple", CL.beam)
|
|
self:PlaySound(args.spellId, "alert")
|
|
beamCount = beamCount + 1
|
|
if beamCount % 2 == 0 then
|
|
self:CDBar(args.spellId, 4.9, CL.beam)
|
|
else
|
|
self:CDBar(args.spellId, 7.0, CL.beam)
|
|
end
|
|
end
|
|
|
|
function mod:LightshatterBeamApplied(args)
|
|
if self:Tank() then
|
|
self:NewStackMessage(360977, "purple", args.destName, args.amount, nil, CL.beam)
|
|
if not self:Me(args.destGUID) and not self:Tanking("boss1") then
|
|
self:PlaySound(360977, "warning")
|
|
end
|
|
end
|
|
end
|
|
|
|
do
|
|
local prev = 0
|
|
local playerList = {}
|
|
function mod:CrushingPrismApplied(args)
|
|
local t = args.time
|
|
if t-prev > 5 then
|
|
prev = t
|
|
self:StopBar(CL.count:format(L.crushing_prism, prismCount))
|
|
prismCount = prismCount + 1
|
|
playerList = {}
|
|
if intermission then
|
|
self:CDBar(args.spellId, intermissionTimers[args.spellId][relocationFormCount-1][prismCount], CL.count:format(L.crushing_prism, prismCount))
|
|
elseif prismCount <= reclaimCount * 2 then
|
|
self:CDBar(args.spellId, 26, CL.count:format(L.crushing_prism, prismCount))
|
|
end
|
|
end
|
|
local count = #playerList+1
|
|
playerList[count] = args.destName
|
|
playerList[args.destName] = count -- Set raid marker
|
|
if self:Me(args.destGUID) then
|
|
self:PlaySound(args.spellId, "alarm")
|
|
self:Say(args.spellId, L.prism)
|
|
end
|
|
self:NewTargetsMessage(args.spellId, "yellow", playerList, nil, CL.count:format(L.crushing_prism, prismCount-1))
|
|
self:CustomIcon(crushingPrismMarker, args.destName, count)
|
|
end
|
|
|
|
function mod:CrushingPrismRemoved(args)
|
|
if self:Me(args.destGUID) then
|
|
self:Message(args.spellId, "green", CL.removed:format(L.prism))
|
|
self:PlaySound(args.spellId, "info")
|
|
end
|
|
self:CustomIcon(crushingPrismMarker, args.destName, 0)
|
|
end
|
|
end
|
|
|
|
function mod:ReclamationForm(args)
|
|
if not self:IsEngaged() then return end -- Casts it after respawning
|
|
|
|
local stage = self:GetStage()
|
|
stage = stage + 1
|
|
self:SetStage(stage)
|
|
self:Message("stages", "cyan", CL.stage:format(stage), false)
|
|
self:PlaySound("stages", "long")
|
|
self:CastBar("stages", 6, CL.cast:format(args.spellName), args.spellId)
|
|
reclamationFormCount = reclamationFormCount + 1
|
|
intermission = false
|
|
|
|
self:StopBar(CL.count:format(CL.intermission, reclamationFormCount))
|
|
self:StopBar(CL.count:format(L.crushing_prism, prismCount))
|
|
self:StopBar(CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
self:StopBar(CL.count:format(self:SpellName(362056), shatterCount))
|
|
|
|
seismicTremorsCount = 1
|
|
beamCount = 1
|
|
misslesCount = 1
|
|
prismCount = 1
|
|
reclaimCount = 1
|
|
|
|
if not self:Easy() then
|
|
self:Bar(360977, 14.1, CL.beam) -- Lightshatter Beam
|
|
end
|
|
if stage == 2 then
|
|
self:Bar(367079, 10, CL.count:format(L.seismic_tremors, seismicTremorsCount)) -- Seismic Tremors
|
|
self:Bar(361676, 18, CL.count:format(L.earthbreaker_missiles, misslesCount)) -- Earthbreaker Missiles
|
|
self:Bar(365297, 23, CL.count:format(L.crushing_prism, prismCount)) -- Crushing Prism
|
|
self:Bar(360115, 69.4, CL.count:format(self:SpellName(360115), reclaimCount)) -- Reclaim
|
|
elseif stage == 3 then
|
|
self:Bar(368529, 7.6) -- Eternity Overdrive
|
|
self:Bar(361676, missleTimersP3[misslesCount], CL.count:format(L.earthbreaker_missiles, misslesCount)) -- Earthbreaker Missiles
|
|
end
|
|
end
|
|
|
|
function mod:RelocationForm(args)
|
|
self:Message("stages", "cyan", CL.count:format(CL.intermission, relocationFormCount), args.spellId)
|
|
self:PlaySound("stages", "long")
|
|
self:CastBar("stages", 5.5, CL.cast:format(args.spellName), args.spellId)
|
|
self:CDBar("stages", relocationFormCount == 1 and 62 or 85, CL.stage:format(self:GetStage() + 1), args.spellId)
|
|
relocationFormCount = relocationFormCount + 1
|
|
|
|
self:StopBar(CL.beam) -- Lightshatter Beam
|
|
-- self:StopBar(CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
-- self:StopBar(CL.count:format(L.seismic_tremors, seismicTremorsCount))
|
|
-- self:StopBar(CL.count:format(L.crushing_prism, prismCount))
|
|
-- self:StopBar(CL.count:format(self:SpellName(360115), reclaimCount))
|
|
end
|
|
|
|
function mod:RelocationFormDone()
|
|
-- Some timers can still trigger just after _START, using _SUCCESS to start bars instead
|
|
self:StopBar(CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
self:StopBar(CL.count:format(L.seismic_tremors, seismicTremorsCount))
|
|
self:StopBar(CL.count:format(L.crushing_prism, prismCount))
|
|
self:StopBar(CL.count:format(self:SpellName(360115), reclaimCount))
|
|
|
|
intermission = true
|
|
misslesCount = 1
|
|
shatterCount = 1
|
|
prismCount = 1
|
|
|
|
self:CDBar(361676, intermissionTimers[361676][relocationFormCount-1][misslesCount], CL.count:format(L.earthbreaker_missiles, misslesCount))
|
|
self:CDBar(364979, intermissionTimers[364979][relocationFormCount-1][shatterCount], CL.count:format(self:SpellName(364979), shatterCount))
|
|
self:CDBar(365297, intermissionTimers[365297][relocationFormCount-1][prismCount], CL.count:format(L.crushing_prism, prismCount))
|
|
end
|
|
|
|
function mod:Shatter(args)
|
|
self:StopBar(CL.count:format(args.spellName, shatterCount))
|
|
self:Message(args.spellId, "yellow", CL.count:format(args.spellName, shatterCount))
|
|
self:PlaySound(args.spellId, "long")
|
|
self:CastBar(args.spellId, 6, CL.knockback)
|
|
shatterCount = shatterCount + 1
|
|
self:Bar(args.spellId, intermissionTimers[args.spellId][relocationFormCount-1][shatterCount], CL.count:format(args.spellName, shatterCount))
|
|
end
|
|
|
|
function mod:EternityOverdrive(args)
|
|
self:Message(args.spellId, "red")
|
|
self:PlaySound(args.spellId, "long")
|
|
end
|
|
|
|
do
|
|
local prev = 0
|
|
local message = {
|
|
[368363] = L.prism, -- Shattered Prism (Prism)
|
|
[360114] = L.ephemeral_fissure, -- Ephemeral Fissure (Fissure)
|
|
}
|
|
function mod:GroundDamage(args)
|
|
if self:Me(args.destGUID) then
|
|
local t = args.time
|
|
if t-prev > 2 then
|
|
prev = t
|
|
self:PlaySound(args.spellId, "underyou")
|
|
self:PersonalMessage(args.spellId, "underyou", message[args.spellId])
|
|
end
|
|
end
|
|
end
|
|
end
|
|
|