From 8268af915a39c0f0d9ab4e44c888b6f673321432 Mon Sep 17 00:00:00 2001 From: Brues <5278969+brues-code@users.noreply.github.com> Date: Tue, 22 Sep 2026 21:19:12 -0500 Subject: [PATCH] energytick: let the five-second rule display as a separate bar or the old shade The shading bar sat on top of the power bar's own fill and shrank from the right as the window drained, which reads as part of the mana bar rather than a countdown over it -- the same problem nameplate castbars solve by living below the health bar instead of on it. Show Five Second Rule Style now picks between that: a real StatusBar below the power bar, backdrop and all, or the original translucent overlay for anyone who prefers it. The style is read once at module load like the other structural toggles here, not swapped live -- a /reload picks up a change. Height and color are only meaningful for the separate-bar style, so the GUI's Five Second Rule Height and the new appearance.castbar.fsrcolor picker apply to it alone; the overlay is unchanged from before. The sweep spark's own dim/solid signal (fsrEnd/fsrGain) is untouched by any of this -- it keeps dimming through an unconfirmed window regardless of which display, or none, is shown. Energy/Mana Ticks -- including both five-second-rule settings -- moves from Unit Frames > General to Unit Frames > Player, right after Powerbar: they are C.unitframes.player-only, so General was never the right tab, and Powerbar is the setting group they actually belong to. --- api/config.lua | 4 ++++ modules/energytick.lua | 51 ++++++++++++++++++++++++++++++++++++------ modules/gui.lua | 12 ++++++++-- 3 files changed, 58 insertions(+), 9 deletions(-) diff --git a/api/config.lua b/api/config.lua index 3f4ff2fc..5dd272a2 100644 --- a/api/config.lua +++ b/api/config.lua @@ -157,6 +157,7 @@ function pfUI:LoadConfig() pfUI:UpdateConfig("appearance", "castbar", "channelcolor", ".9,.9,.7,.8") pfUI:UpdateConfig("appearance", "castbar", "failcolor", "1,.2,.2,.8") pfUI:UpdateConfig("appearance", "castbar", "shieldcolor", ".8,.45,.45,.8") + pfUI:UpdateConfig("appearance", "castbar", "fsrcolor", ".9,.6,.2,.8") pfUI:UpdateConfig("appearance", "castbar", "texture", "Interface\\AddOns\\pfUI\\img\\bar") pfUI:UpdateConfig("appearance", "infight", "screen", "0") pfUI:UpdateConfig("appearance", "infight", "aggro", "0") @@ -325,6 +326,9 @@ function pfUI:LoadConfig() pfUI:UpdateConfig("unitframes", "player", "showRest", "0") pfUI:UpdateConfig("unitframes", "player", "energy", "1") pfUI:UpdateConfig("unitframes", "player", "manatick", "0") + pfUI:UpdateConfig("unitframes", "player", "showfsr", "1") + pfUI:UpdateConfig("unitframes", "player", "fsrheight", "4") + pfUI:UpdateConfig("unitframes", "player", "fsrstyle", "0") pfUI:UpdateConfig("unitframes", "player", "display_haste", "0") pfUI:UpdateConfig("unitframes", "player", "display_haste_color", "1,1,1,1") pfUI:UpdateConfig("unitframes", "player", "display_spellpower", "1") diff --git a/modules/energytick.lua b/modules/energytick.lua index ce787798..c088ad7a 100644 --- a/modules/energytick.lua +++ b/modules/energytick.lua @@ -89,6 +89,13 @@ pfUI:RegisterModule("energytick", function() return C.unitframes.player.pwidth ~= "-1" and C.unitframes.player.pwidth or C.unitframes.player.width end + local rawborder, default_border = GetBorderSize("unitframes") + local cbtexture = pfUI.media[C.appearance.castbar.texture] + + -- style is read once: switching it in the GUI needs a /reload, same as the + -- other structural (not cosmetic) toggles in this file + local fsrOverlay = C.unitframes.player.fsrstyle == "1" + -- was this gain the regen tick? if so, re-anchor the sweep on it local function lockTick(frame) local now, period = GetTime(), getAdjustedTickTimer() @@ -199,11 +206,21 @@ pfUI:RegisterModule("energytick", function() end this.tick = GetTime() + 0.020 -- ~50 FPS - -- five-second rule drains to nothing + -- five-second rule drains to nothing. The display is cosmetic and can be + -- hidden on its own; the window itself (fsrEnd/fsrGain) keeps running + -- either way -- it still dims the sweep spark below. local remaining = this.fsrEnd and (this.fsrEnd - GetTime()) or 0 if this.mode == "MANA" and remaining > 0 then - this.fsrbar:SetWidth(getBarWidth() * remaining / FIVE_SECOND_RULE) - this.fsrbar:Show() + if C.unitframes.player.showfsr == "1" then + if fsrOverlay then + this.fsrbar:SetWidth(getBarWidth() * remaining / FIVE_SECOND_RULE) + else + this.fsrbar:SetValue(remaining) + end + this.fsrbar:Show() + else + this.fsrbar:Hide() + end else this.fsrSpell, this.fsrEnd, this.fsrGain = nil, nil, nil this.fsrbar:Hide() @@ -240,10 +257,26 @@ pfUI:RegisterModule("energytick", function() this.spark:SetPoint("LEFT", pos - ((C.unitframes.player.pheight + 5) / 2), 0) end) - energytick.fsrbar = energytick:CreateTexture(nil, "ARTWORK") - energytick.fsrbar:SetTexture(1, 1, 1, .15) - energytick.fsrbar:SetPoint("TOPLEFT", 0, 0) - energytick.fsrbar:SetPoint("BOTTOMLEFT", 0, 0) + if fsrOverlay then + -- classic style: a translucent shade on top of the power bar's own fill + energytick.fsrbar = energytick:CreateTexture(nil, "ARTWORK") + energytick.fsrbar:SetTexture(1, 1, 1, .15) + energytick.fsrbar:SetPoint("TOPLEFT", 0, 0) + energytick.fsrbar:SetPoint("BOTTOMLEFT", 0, 0) + else + -- a real bar below the power bar, not an overlay on top of it -- the same + -- treatment nameplate castbars get relative to the health bar, so the + -- window can't be mistaken for missing mana + energytick.fsrbar = CreateFrame("StatusBar", nil, pfUI.uf.player) + energytick.fsrbar:SetStatusBarTexture(cbtexture) + energytick.fsrbar:SetMinMaxValues(0, FIVE_SECOND_RULE) + energytick.fsrbar:SetPoint("TOPLEFT", pfUI.uf.player.power.bar, "BOTTOMLEFT", 0, -default_border * 2) + energytick.fsrbar:SetPoint("TOPRIGHT", pfUI.uf.player.power.bar, "BOTTOMRIGHT", 0, -default_border * 2) + energytick.fsrbar:SetHeight(tonumber(C.unitframes.player.fsrheight) or 4) + energytick.fsrbar:SetStatusBarColor(GetStringColor(C.appearance.castbar.fsrcolor)) + CreateBackdrop(energytick.fsrbar, default_border) + CreateBackdropShadow(energytick.fsrbar) + end energytick.fsrbar:Hide() energytick.spark = energytick:CreateTexture(nil, "OVERLAY") @@ -256,6 +289,10 @@ pfUI:RegisterModule("energytick", function() function pfUI.uf.player.UpdateConfig() energytick.spark:SetHeight(C.unitframes.player.pheight + 15) energytick.spark:SetWidth(C.unitframes.player.pheight + 5) + if not fsrOverlay then + energytick.fsrbar:SetHeight(tonumber(C.unitframes.player.fsrheight) or 4) + energytick.fsrbar:SetStatusBarColor(GetStringColor(C.appearance.castbar.fsrcolor)) + end hookUpdateConfig(pfUI.uf.player) end end) diff --git a/modules/gui.lua b/modules/gui.lua index 457465d3..824913d2 100644 --- a/modules/gui.lua +++ b/modules/gui.lua @@ -2072,8 +2072,6 @@ pfUI:RegisterModule("gui", function () CreateConfig(nil, T["Combopoint Width"], C.unitframes, "combowidth") CreateConfig(nil, T["Combopoint Height"], C.unitframes, "comboheight") CreateConfig(nil, T["Show Resting"], C.unitframes.player, "showRest", "checkbox") - CreateConfig(nil, T["Enable Energy Ticks"], C.unitframes.player, "energy", "checkbox") - CreateConfig(nil, T["Enable Mana Ticks"], C.unitframes.player, "manatick", "checkbox") CreateConfig(nil, T["Detect Enemy Buffs"], C.unitframes, "buffdetect", "checkbox", nil, nil, nil, nil) CreateConfig(nil, T["Raid Mark Icon Style"], C.unitframes, "blizzard_raidicons", "dropdown", function() return {"1:Original Blizzard", "0:pfUI Design"} end) @@ -2320,6 +2318,15 @@ pfUI:RegisterModule("gui", function () CreateConfig(U[c], T["Right Text Y Offset"], C.unitframes[c], "txtpowerrightoffy") CreateConfig(U[c], T["Power Bar Anchor"], C.unitframes[c], "panchor", "dropdown", pfUI.gui.dropdowns.uf_powerbar_position) + if c == "player" then + CreateConfig(nil, T["Energy/Mana Ticks"], nil, nil, "header") + CreateConfig(nil, T["Enable Energy Ticks"], C.unitframes[c], "energy", "checkbox") + CreateConfig(nil, T["Enable Mana Ticks"], C.unitframes[c], "manatick", "checkbox") + CreateConfig(nil, T["Show Five Second Rule"], C.unitframes[c], "showfsr", "checkbox") + CreateConfig(nil, T["Five Second Rule Style"], C.unitframes[c], "fsrstyle", "dropdown", function() return {"0:Separate Bar", "1:Overlay"} end) + CreateConfig(nil, T["Five Second Rule Height"], C.unitframes[c], "fsrheight") + end + CreateConfig(U[c], T["Combat Text"], nil, nil, "header") CreateConfig(U[c], T["Show Combat Text"], C.unitframes[c], "hitindicator", "checkbox") CreateConfig(U[c], T["Combat Text Font"], C.unitframes[c], "hitindicatorfont", "dropdown", pfUI.gui.dropdowns.fonts) @@ -2793,6 +2800,7 @@ pfUI:RegisterModule("gui", function () CreateConfig(nil, T["Casting Color"], C.appearance.castbar, "castbarcolor", "color") CreateConfig(nil, T["Channeling Color"], C.appearance.castbar, "channelcolor", "color") CreateConfig(nil, T["Uninterruptible Color"], C.appearance.castbar, "shieldcolor", "color") + CreateConfig(nil, T["Five Second Rule Color"], C.appearance.castbar, "fsrcolor", "color") CreateConfig(nil, T["Castbar Texture"], C.appearance.castbar, "texture", "dropdown", pfUI.gui.dropdowns.uf_bartexture) CreateConfig(nil, T["Disable Blizzard Castbar"], C.castbar.player, "hide_blizz", "checkbox") end)