mirror of
https://github.com/brues-code/pfUI.git
synced 2026-11-01 16:36:56 +00:00
UNIT_AURA says nothing about what changed and stays silent when a buff is refreshed or its duration packet lands, so a recast HoT kept its old timer until something else rebuilt the row. UNIT_AURA_DELTA reports added, updated and removed aura instances, refreshes included. Unit frames register it on their own token. An add, a removal or a full update rebuilds the auras as before; an update-only delta re-reads the slot behind each shown icon for its stacks and timer and redraws the buff indicators, without a relayout or a dispel scan. Frames that follow a GUID (the target-of-X chain) stay on UNIT_AURA, since the delta only fires for tokens. A finished aura layout announces itself as "unitframe:auras". buffwatch drops its 0.4s rescan: bars rebuild on the delta, on login and on a target change, and a timer wakes the frame when the next aura crosses the bar threshold. Bars re-anchor when the player or target frame lays out its aura rows, and a whitelist or blacklist click applies at once. Nameplates, the loss of control alert and the equipment manager's mount/stealth/dining check listen to the delta as well.
91 lines
3.3 KiB
Lua
91 lines
3.3 KiB
Lua
pfUI:RegisterModule("lossofcontrol", function ()
|
|
-- 5.x's loss of control alert. ClassicAPI's C_LossOfControl builds the
|
|
-- effects from the player's debuffs and from the school lockout of an
|
|
-- interrupt.
|
|
local strings = L["lossofcontrol"]
|
|
|
|
-- how much each effect takes away; the alert shows the strongest one
|
|
local PRIORITY = {
|
|
STUN = 3, FEAR = 3, CONFUSE = 3, CHARM = 3, POSSESS = 3, PACIFYSILENCE = 3,
|
|
SILENCE = 2, SCHOOL_INTERRUPT = 2, PACIFY = 2,
|
|
DISARM = 1, ROOT = 1,
|
|
}
|
|
|
|
-- the lockout packet does not name the interrupting spell
|
|
local INTERRUPT_ICON = "Interface\\Icons\\Ability_Kick"
|
|
|
|
local function IsStronger(data, best)
|
|
local priority, bestPriority = PRIORITY[data.locType], PRIORITY[best.locType]
|
|
if priority ~= bestPriority then return priority > bestPriority end
|
|
return (data.timeRemaining or math.huge) > (best.timeRemaining or math.huge)
|
|
end
|
|
|
|
local frame = CreateFrame("Frame", "pfLossOfControl", UIParent)
|
|
frame:SetSize(220, 48)
|
|
frame:SetPoint("CENTER", 0, 120)
|
|
frame:SetFrameStrata("HIGH")
|
|
frame:Hide()
|
|
|
|
frame.icon = CreateFrame("Frame", nil, frame)
|
|
frame.icon:SetSize(48, 48)
|
|
frame.icon:SetPoint("LEFT", 0, 0)
|
|
CreateBackdrop(frame.icon, nil, true)
|
|
|
|
frame.icon.tex = frame.icon:CreateTexture(nil, "ARTWORK")
|
|
HandleIcon(frame.icon, frame.icon.tex)
|
|
|
|
frame.cd = CreateFrame("Cooldown", nil, frame.icon, "CooldownFrameTemplate")
|
|
frame.cd:SetAllPoints(frame.icon.tex)
|
|
frame.cd.pfCooldownStyleAnimation = 1
|
|
frame.cd.pfCooldownType = "ALL"
|
|
|
|
frame.label = frame:CreateFontString(nil, "OVERLAY")
|
|
frame.label:SetFont(pfUI.font_default, 20, "OUTLINE")
|
|
frame.label:SetTextColor(NORMAL_FONT_COLOR:GetRGB())
|
|
frame.label:SetPoint("LEFT", frame.icon, "RIGHT", 8, 0)
|
|
|
|
frame.Refresh = function(self)
|
|
local best
|
|
for i = 1, C_LossOfControl.GetActiveLossOfControlDataCount() do
|
|
local data = C_LossOfControl.GetActiveLossOfControlData(i)
|
|
if not best or IsStronger(data, best) then best = data end
|
|
end
|
|
|
|
if not best then
|
|
if pfUI.unlock and pfUI.unlock:IsShown() then return end
|
|
self:Hide()
|
|
return
|
|
end
|
|
|
|
if best.locType == "SCHOOL_INTERRUPT" then
|
|
self.label:SetText(format(strings.LOSS_OF_CONTROL_DISPLAY_INTERRUPT_SCHOOL, C_Spell.GetSchoolString(best.lockoutSchool)))
|
|
self.icon.tex:SetTexture(INTERRUPT_ICON)
|
|
else
|
|
self.label:SetText(strings["LOSS_OF_CONTROL_DISPLAY_" .. best.locType])
|
|
self.icon.tex:SetTexture(best.iconTexture)
|
|
end
|
|
|
|
CooldownFrame_SetTimer(self.cd, best.startTime or 0, best.duration or 0, best.startTime and 1 or 0)
|
|
self:Show()
|
|
end
|
|
|
|
-- a refreshed debuff (UNIT_AURA_DELTA) or a second kick on the same school
|
|
-- (SPELL_UPDATE_COOLDOWN) changes the timer without a loss of control event
|
|
frame:SetScript("OnShow", function()
|
|
this:RegisterUnitEvent("UNIT_AURA_DELTA", "player")
|
|
this:RegisterEvent("SPELL_UPDATE_COOLDOWN")
|
|
end)
|
|
frame:SetScript("OnHide", function()
|
|
this:UnregisterAllEvents()
|
|
end)
|
|
frame:SetScript("OnEvent", function()
|
|
this:Refresh()
|
|
end)
|
|
|
|
pfUI.events:RegisterFrameEventAndCallback("LOSS_OF_CONTROL_ADDED", function() frame:Refresh() end)
|
|
pfUI.events:RegisterFrameEventAndCallback("LOSS_OF_CONTROL_UPDATE", function() frame:Refresh() end)
|
|
|
|
UpdateMovable(frame)
|
|
pfUI.lossofcontrol = frame
|
|
end)
|