diff --git a/Defaults/Layout_Defaults.lua b/Defaults/Layout_Defaults.lua index a073480d..18883253 100644 --- a/Defaults/Layout_Defaults.lua +++ b/Defaults/Layout_Defaults.lua @@ -169,22 +169,26 @@ Cell.defaults.layout = { ["health1"] = { ["format"] = "effective_percent", ["color"] = {"custom_color", {1, 1, 1}}, - ["hideIfEmptyOrFull"] = false, + ["colorByHealth"] = false, + ["hideIfEmptyOrFull"] = true, }, ["health2"] = { ["format"] = "none", ["color"] = {"custom_color", {1, 1, 1}}, - ["hideIfEmptyOrFull"] = false, + ["colorByHealth"] = false, + ["hideIfEmptyOrFull"] = true, ["delimiter"] = " ", }, ["shields"] = { ["format"] = "none", ["color"] = {"custom_color", {0, 1, 0}}, + ["colorByHealth"] = false, ["delimiter"] = "+", }, ["healAbsorbs"] = { ["format"] = "none", ["color"] = {"custom_color", {1, 0, 0}}, + ["colorByHealth"] = false, ["delimiter"] = "-", }, }, diff --git a/Defaults/Layout_Defaults_Cata_Wrath.lua b/Defaults/Layout_Defaults_Cata_Wrath.lua index 0ddc4ee4..aa8b7bc5 100644 --- a/Defaults/Layout_Defaults_Cata_Wrath.lua +++ b/Defaults/Layout_Defaults_Cata_Wrath.lua @@ -157,22 +157,26 @@ Cell.defaults.layout = { ["health1"] = { ["format"] = "effective_percent", ["color"] = {"custom_color", {1, 1, 1}}, - ["hideIfEmptyOrFull"] = false, + ["colorByHealth"] = false, + ["hideIfEmptyOrFull"] = true, }, ["health2"] = { ["format"] = "none", ["color"] = {"custom_color", {1, 1, 1}}, - ["hideIfEmptyOrFull"] = false, + ["colorByHealth"] = false, + ["hideIfEmptyOrFull"] = true, ["delimiter"] = " ", }, ["shields"] = { ["format"] = "none", ["color"] = {"custom_color", {0, 1, 0}}, + ["colorByHealth"] = false, ["delimiter"] = "+", }, ["healAbsorbs"] = { ["format"] = "none", ["color"] = {"custom_color", {1, 0, 0}}, + ["colorByHealth"] = false, ["delimiter"] = "-", }, }, diff --git a/Defaults/Layout_Defaults_Mists.lua b/Defaults/Layout_Defaults_Mists.lua index e77008e2..d68c17d8 100644 --- a/Defaults/Layout_Defaults_Mists.lua +++ b/Defaults/Layout_Defaults_Mists.lua @@ -164,22 +164,26 @@ Cell.defaults.layout = { ["health1"] = { ["format"] = "effective_percent", ["color"] = {"custom_color", {1, 1, 1}}, - ["hideIfEmptyOrFull"] = false, + ["colorByHealth"] = false, + ["hideIfEmptyOrFull"] = true, }, ["health2"] = { ["format"] = "none", ["color"] = {"custom_color", {1, 1, 1}}, - ["hideIfEmptyOrFull"] = false, + ["colorByHealth"] = false, + ["hideIfEmptyOrFull"] = true, ["delimiter"] = " ", }, ["shields"] = { ["format"] = "none", ["color"] = {"custom_color", {0, 1, 0}}, + ["colorByHealth"] = false, ["delimiter"] = "+", }, ["healAbsorbs"] = { ["format"] = "none", ["color"] = {"custom_color", {1, 0, 0}}, + ["colorByHealth"] = false, ["delimiter"] = "-", }, }, diff --git a/Defaults/Layout_Defaults_TBC_Vanilla.lua b/Defaults/Layout_Defaults_TBC_Vanilla.lua index d724785c..a9717f31 100644 --- a/Defaults/Layout_Defaults_TBC_Vanilla.lua +++ b/Defaults/Layout_Defaults_TBC_Vanilla.lua @@ -155,22 +155,26 @@ Cell.defaults.layout = { ["health1"] = { ["format"] = "effective_percent", ["color"] = {"custom_color", {1, 1, 1}}, - ["hideIfEmptyOrFull"] = false, + ["colorByHealth"] = false, + ["hideIfEmptyOrFull"] = true, }, ["health2"] = { ["format"] = "none", ["color"] = {"custom_color", {1, 1, 1}}, - ["hideIfEmptyOrFull"] = false, + ["colorByHealth"] = false, + ["hideIfEmptyOrFull"] = true, ["delimiter"] = " ", }, ["shields"] = { ["format"] = "none", ["color"] = {"custom_color", {0, 1, 0}}, + ["colorByHealth"] = false, ["delimiter"] = "+", }, ["healAbsorbs"] = { ["format"] = "none", ["color"] = {"custom_color", {1, 0, 0}}, + ["colorByHealth"] = false, ["delimiter"] = "-", }, }, diff --git a/Indicators/Built-in.lua b/Indicators/Built-in.lua index 43c4a6bf..be2e6c86 100644 --- a/Indicators/Built-in.lua +++ b/Indicators/Built-in.lua @@ -1952,17 +1952,33 @@ local formatter = { ["health_short"] = function(pattern, _, health, maxHealth, absorbs, healAbsorbs) return pattern:format(F.FormatNumber(health)) end, + ["health_short2"] = function(pattern, _, health, maxHealth, absorbs, healAbsorbs) + return pattern:format(F.FormatNumber(health, 2)) + end, ["health_percent"] = function(pattern, _, health, maxHealth, absorbs, healAbsorbs) return pattern:format(F.Round(health / maxHealth * 100)) end, - ["deficit"] = function(pattern, _, health, maxHealth, absorbs, healAbsorbs) - return pattern:format(health - maxHealth) + -- hideIfZero (the segment's "Hide if 0" setting): suppress the deficit text entirely + -- once a unit is topped off, instead of always showing "-0" / "0%". + ["deficit"] = function(pattern, hideIfZero, health, maxHealth, absorbs, healAbsorbs) + local deficit = health - maxHealth + if hideIfZero and deficit == 0 then return "" end + return pattern:format(deficit) + end, + ["deficit_short"] = function(pattern, hideIfZero, health, maxHealth, absorbs, healAbsorbs) + local deficit = health - maxHealth + if hideIfZero and deficit == 0 then return "" end + return pattern:format(F.FormatNumber(deficit)) end, - ["deficit_short"] = function(pattern, _, health, maxHealth, absorbs, healAbsorbs) - return pattern:format(F.FormatNumber(health - maxHealth)) + ["deficit_short2"] = function(pattern, hideIfZero, health, maxHealth, absorbs, healAbsorbs) + local deficit = health - maxHealth + if hideIfZero and deficit == 0 then return "" end + return pattern:format(F.FormatNumber(deficit, 2)) end, - ["deficit_percent"] = function(pattern, _, health, maxHealth, absorbs, healAbsorbs) - return pattern:format(F.Round((health - maxHealth) / maxHealth * 100)) + ["deficit_percent"] = function(pattern, hideIfZero, health, maxHealth, absorbs, healAbsorbs) + local deficit = health - maxHealth + if hideIfZero and deficit == 0 then return "" end + return pattern:format(F.Round(deficit / maxHealth * 100)) end, -- effective health @@ -1972,6 +1988,9 @@ local formatter = { ["effective_short"] = function(pattern, _, health, maxHealth, absorbs, healAbsorbs) return pattern:format(F.FormatNumber(health + absorbs - healAbsorbs)) end, + ["effective_short2"] = function(pattern, _, health, maxHealth, absorbs, healAbsorbs) + return pattern:format(F.FormatNumber(health + absorbs - healAbsorbs, 2)) + end, ["effective_percent"] = function(pattern, _, health, maxHealth, absorbs, healAbsorbs) return pattern:format(F.Round((health + absorbs - healAbsorbs) / maxHealth * 100)) end, @@ -1985,6 +2004,10 @@ local formatter = { if absorbs == 0 then return "" end return pattern:format(F.FormatNumber(absorbs)) end, + ["shields_short2"] = function(pattern, health, maxHealth, absorbs, healAbsorbs) + if absorbs == 0 then return "" end + return pattern:format(F.FormatNumber(absorbs, 2)) + end, ["shields_percent"] = function(pattern, health, maxHealth, absorbs, healAbsorbs) if absorbs == 0 then return "" end return pattern:format(F.Round(absorbs / maxHealth * 100)) @@ -1999,6 +2022,10 @@ local formatter = { if healAbsorbs == 0 then return "" end return pattern:format(F.FormatNumber(healAbsorbs)) end, + ["healabsorbs_short2"] = function(pattern, health, maxHealth, absorbs, healAbsorbs) + if healAbsorbs == 0 then return "" end + return pattern:format(F.FormatNumber(healAbsorbs, 2)) + end, ["healabsorbs_percent"] = function(pattern, health, maxHealth, absorbs, healAbsorbs) if healAbsorbs == 0 then return "" end return pattern:format(F.Round(healAbsorbs / maxHealth * 100)) @@ -2019,7 +2046,8 @@ local function BuildPattern(config) local suffix = config.format:find("percent$") and "%%" or "" - if config.color[1] == "class_color" then + -- colorByHealth: color is computed dynamically per update (see ApplyHealthGradientColor), so leave it unbaked here + if config.colorByHealth or config.color[1] == "class_color" then return prefix .. "%s" .. suffix else return prefix .. "|cff" .. F.ConvertRGBToHEX(F.ConvertRGB_256(unpack(config.color[2]))) .. "%s" .. suffix .. "|r" @@ -2043,6 +2071,9 @@ local function BuildSecretSegment(config) local isPercent = config.format:find("percent$") and true or false + -- colorByHealth needs live (secret-safe) percent evaluation which isn't available at C-level + -- here, so secret segments just fall back to their static base color (no gradient), + -- same as when colorByHealth is off - class_color still relies on the fontstring's ambient tint. local colorStart, colorEnd if config.color[1] == "class_color" then colorStart, colorEnd = "", "" @@ -2095,6 +2126,18 @@ local function HealthText_SetFormat(self, format) self.shields = BuildPattern(format.shields) self.healAbsorbs = BuildPattern(format.healAbsorbs) + -- hideIfEmptyOrFull: for deficit formats, suppress the "-0"/"0%" text once a unit is topped off + self.health1HideIfZero = format.health1.hideIfEmptyOrFull and true or false + self.health2HideIfZero = format.health2.hideIfEmptyOrFull and true or false + + -- colorByHealth: remember which segments need their color recomputed every update + -- (against the segment's own class/custom base color) instead of the baked-in one + self.health1GradientColor = format.health1.colorByHealth and format.health1.color or nil + self.health2GradientColor = format.health2.colorByHealth and format.health2.color or nil + self.shieldsGradientColor = format.shields.colorByHealth and format.shields.color or nil + self.healAbsorbsGradientColor = format.healAbsorbs.colorByHealth and format.healAbsorbs.color or nil + + -- Pre-build C-level format segments for use when values are secret. -- Each active component gets a segment with a %d/%s placeholder. -- Stored individually so the render path can skip zero-value absorb components. local segments = {} @@ -2116,6 +2159,26 @@ local function HealthText_SetFormat(self, format) end +-- Wraps an already-formatted segment string with a color computed from the current +-- health percent (ElvUI-style red -> yellow -> base color), when colorByHealth is enabled +-- for that segment. `colorConfig` is the segment's {mode, {r,g,b}} color table, or nil. +local function ApplyHealthGradientColor(text, colorConfig, percent, unit) + if text == "" or not colorConfig then + return text + end + + local r, g, b + if colorConfig[1] == "class_color" then + -- no live unit in the settings preview (e.g. widget:SetValue with a fake sample) - fall back to the player's class + r, g, b = unit and F.GetUnitClassColor(unit) or F.GetClassColor(Cell.vars.playerClass) + else + r, g, b = colorConfig[2][1], colorConfig[2][2], colorConfig[2][3] + end + r, g, b = F.GetHealthTextColor(percent, r, g, b) + + return "|cff" .. F.ConvertRGBToHEX(F.ConvertRGB_256(r, g, b)) .. text .. "|r" +end + local function HealthText_SetValue(self, health, maxHealth, shields, healAbsorbs, unit) -- safety net for any remaining Lua arithmetic in the formatters below. if not F.IsValueNonSecret(health) or not F.IsValueNonSecret(maxHealth) @@ -2179,11 +2242,20 @@ local function HealthText_SetValue(self, health, maxHealth, shields, healAbsorbs end maxHealth = maxHealth == 0 and 1 or maxHealth - self.text:SetFormattedText("%s%s%s%s", - self.GetHealth1(self.health1, false, health, maxHealth, shields, healAbsorbs), - self.GetHealth2(self.health2, false, health, maxHealth, shields, healAbsorbs), - self.GetShields(self.shields, health, maxHealth, shields, healAbsorbs), - self.GetHealAbsorbs(self.healAbsorbs, health, maxHealth, shields, healAbsorbs)) + if self.health1GradientColor or self.health2GradientColor or self.shieldsGradientColor or self.healAbsorbsGradientColor then + local percent = health / maxHealth + self.text:SetFormattedText("%s%s%s%s", + ApplyHealthGradientColor(self.GetHealth1(self.health1, self.health1HideIfZero, health, maxHealth, shields, healAbsorbs), self.health1GradientColor, percent, unit), + ApplyHealthGradientColor(self.GetHealth2(self.health2, self.health2HideIfZero, health, maxHealth, shields, healAbsorbs), self.health2GradientColor, percent, unit), + ApplyHealthGradientColor(self.GetShields(self.shields, health, maxHealth, shields, healAbsorbs), self.shieldsGradientColor, percent, unit), + ApplyHealthGradientColor(self.GetHealAbsorbs(self.healAbsorbs, health, maxHealth, shields, healAbsorbs), self.healAbsorbsGradientColor, percent, unit)) + else + self.text:SetFormattedText("%s%s%s%s", + self.GetHealth1(self.health1, self.health1HideIfZero, health, maxHealth, shields, healAbsorbs), + self.GetHealth2(self.health2, self.health2HideIfZero, health, maxHealth, shields, healAbsorbs), + self.GetShields(self.shields, health, maxHealth, shields, healAbsorbs), + self.GetHealAbsorbs(self.healAbsorbs, health, maxHealth, shields, healAbsorbs)) + end self:SetWidth(self.text:GetStringWidth()) end diff --git a/Locales/enUS.lua b/Locales/enUS.lua index 080633e3..c14cc23c 100644 --- a/Locales/enUS.lua +++ b/Locales/enUS.lua @@ -26,6 +26,9 @@ select(2, ...).L = setmetatable({ ["dispellableByMe"] = "Only show debuffs dispellable by me", ["nonPlayerAuras"] = "Only show non-player auras", ["nonPlayerAurasTip"] = "Hides lust aftereffects such as Exhaustion, Sated, Forbearance and Temporal Displacement. Encounter debuffs stay visible.", + ["colorByHealthTip"] = "Blend this segment's color from red (low health) to yellow to its normal color as health rises, like ElvUI.", + ["2 Decimals"] = "2 Decimals", + ["Hide the deficit text once a unit is topped off"] = "Hide the deficit text once a unit is topped off", ["Private Dispel Overlay"] = "Private Dispel Overlay", ["Show private dispel overlay"] = "Show private dispel overlay", ["Only dispellable by me"] = "Only dispellable by me", diff --git a/Utils.lua b/Utils.lua index 78c1f9e6..b5881d10 100644 --- a/Utils.lua +++ b/Utils.lua @@ -454,23 +454,25 @@ end local abs = math.abs if Cell.isAsian then - function F.FormatNumber(n) + function F.FormatNumber(n, decimals) + decimals = decimals or 1 if abs(n) >= 100000000 then - return F.Round(n / 100000000, 2) .. symbol_1B + return F.Round(n / 100000000, decimals) .. symbol_1B elseif abs(n) >= 10000 then - return F.Round(n / 10000, 1) .. symbol_10K + return F.Round(n / 10000, decimals) .. symbol_10K else return n end end else - function F.FormatNumber(n) + function F.FormatNumber(n, decimals) + decimals = decimals or 1 if abs(n) >= 1000000000 then - return F.Round(n / 1000000000, 2) .. "B" + return F.Round(n / 1000000000, decimals) .. "B" elseif abs(n) >= 1000000 then - return F.Round(n / 1000000, 2) .. "M" + return F.Round(n / 1000000, decimals) .. "M" elseif abs(n) >= 1000 then - return F.Round(n / 1000, 1) .. "K" + return F.Round(n / 1000, decimals) .. "K" else return n end @@ -1435,6 +1437,14 @@ function F.GetHealthBarColor(percent, isDeadOrGhost, r, g, b) return barR, barG, barB, lossR, lossG, lossB end +-- ElvUI-style health text coloring: red at 0% health, yellow at 50%, original color (e.g. class color) at 100% +function F.GetHealthTextColor(percent, r, g, b) + if not Cell.loaded then + return r, g, b + end + return F.ColorGradient(percent or 1, {1, 0, 0}, {1, 1, 0}, {r, g, b}) +end + ------------------------------------------------- -- units ------------------------------------------------- diff --git a/Widgets/Widgets_IndicatorSettings.lua b/Widgets/Widgets_IndicatorSettings.lua index 0a9c1b43..984125b2 100644 --- a/Widgets/Widgets_IndicatorSettings.lua +++ b/Widgets/Widgets_IndicatorSettings.lua @@ -941,6 +941,7 @@ local function CreateSetting_TextWidth(parent) end + local function CreateSetting_Alpha(parent) local widget @@ -1048,12 +1049,16 @@ local function CreateSetting_HealthFormat(parent) local health1Enabled = widget.format.health1.format ~= "none" widget.health1ColorDropdown:SetEnabled(health1Enabled) widget.health1ColorPicker:SetEnabled(health1Enabled) + widget.health1GradientCB:SetEnabled(health1Enabled) + widget.health1HideZeroCB:SetEnabled(health1Enabled) local health2Enabled = widget.format.health2.format ~= "none" widget.health2DelimiterEB:SetEnabled(health2Enabled) widget.health2DelimiterEB.confirmBtn:Hide() widget.health2ColorDropdown:SetEnabled(health2Enabled) widget.health2ColorPicker:SetEnabled(health2Enabled) + widget.health2GradientCB:SetEnabled(health2Enabled) + widget.health2HideZeroCB:SetEnabled(health2Enabled) if health2Enabled then widget.health2DelimiterText:SetTextColor(1, 1, 1) else @@ -1065,6 +1070,7 @@ local function CreateSetting_HealthFormat(parent) widget.shieldDelimiterEB.confirmBtn:Hide() widget.shieldColorDropdown:SetEnabled(shieldEnabled) widget.shieldColorPicker:SetEnabled(shieldEnabled) + widget.shieldGradientCB:SetEnabled(shieldEnabled) if shieldEnabled then widget.shieldDelimiterText:SetTextColor(1, 1, 1) else @@ -1076,6 +1082,7 @@ local function CreateSetting_HealthFormat(parent) widget.healAbsorbDelimiterEB.confirmBtn:Hide() widget.healAbsorbColorDropdown:SetEnabled(healAbsorbEnabled) widget.healAbsorbColorPicker:SetEnabled(healAbsorbEnabled) + widget.healAbsorbGradientCB:SetEnabled(healAbsorbEnabled) if healAbsorbEnabled then widget.healAbsorbDelimiterText:SetTextColor(1, 1, 1) else @@ -1100,18 +1107,22 @@ local function CreateSetting_HealthFormat(parent) end local effective = " |cff7b7b7b" .. L["Effective"] .. "|r" + local decimals2 = " |cff7b7b7b(" .. L["2 Decimals"] .. ")|r" local healthList = { {L["None"], "none"}, {(health + shield - healAbsorb) .. effective, "effective"}, {F.FormatNumber(health + shield - healAbsorb) .. effective, "effective_short"}, + {F.FormatNumber(health + shield - healAbsorb, 2) .. effective .. decimals2, "effective_short2"}, {F.Round((health + shield - healAbsorb) / healthMax * 100) .. "%" .. effective, "effective_percent"}, {F.Round((health + shield - healAbsorb) / healthMax * 100) .. effective, "effective_percent_no_sign"}, {health, "health"}, {F.FormatNumber(health), "health_short"}, + {F.FormatNumber(health, 2) .. decimals2, "health_short2"}, {F.Round(health / healthMax * 100) .. "%", "health_percent"}, {F.Round(health / healthMax * 100), "health_percent_no_sign"}, {health - healthMax, "deficit"}, {F.FormatNumber(health - healthMax), "deficit_short"}, + {F.FormatNumber(health - healthMax, 2) .. decimals2, "deficit_short2"}, {F.Round((health - healthMax) / healthMax * 100) .. "%", "deficit_percent"}, {F.Round((health - healthMax) / healthMax * 100), "deficit_percent_no_sign"}, } @@ -1156,6 +1167,19 @@ local function CreateSetting_HealthFormat(parent) end) widget.health1ColorPicker:SetPoint("LEFT", widget.health1ColorDropdown, "RIGHT", 5, 0) + widget.health1GradientCB = Cell.CreateCheckButton(widget, "", function(checked) + widget.format.health1.colorByHealth = checked + widget.func() + end, L["colorByHealthTip"]) + widget.health1GradientCB:SetPoint("LEFT", widget.health1ColorPicker, "RIGHT", 10, 0) + + -- only meaningful for the deficit formats, but harmless (ignored) for every other format + widget.health1HideZeroCB = Cell.CreateCheckButton(widget, "", function(checked) + widget.format.health1.hideIfEmptyOrFull = checked + widget.func() + end, L["hideIfEmptyOrFull"], L["Hide the deficit text once a unit is topped off"]) + widget.health1HideZeroCB:SetPoint("LEFT", widget.health1GradientCB, "RIGHT", 5, 0) + -- health2 ------------------------------ widget.health2FormatDropdown = Cell.CreateDropdown(widget, 127) widget.health2FormatDropdown:SetPoint("TOPLEFT", widget.health1ColorDropdown, "BOTTOMLEFT", 0, -35) @@ -1208,11 +1232,24 @@ local function CreateSetting_HealthFormat(parent) end) widget.health2ColorPicker:SetPoint("LEFT", widget.health2ColorDropdown, "RIGHT", 5, 0) + widget.health2GradientCB = Cell.CreateCheckButton(widget, "", function(checked) + widget.format.health2.colorByHealth = checked + widget.func() + end, L["colorByHealthTip"]) + widget.health2GradientCB:SetPoint("LEFT", widget.health2ColorPicker, "RIGHT", 10, 0) + + widget.health2HideZeroCB = Cell.CreateCheckButton(widget, "", function(checked) + widget.format.health2.hideIfEmptyOrFull = checked + widget.func() + end, L["hideIfEmptyOrFull"], L["Hide the deficit text once a unit is topped off"]) + widget.health2HideZeroCB:SetPoint("LEFT", widget.health2GradientCB, "RIGHT", 5, 0) + -- shield ------------------------------- local shieldList = { {L["None"], "none"}, {shield, "shields"}, {F.FormatNumber(shield), "shields_short"}, + {F.FormatNumber(shield, 2) .. decimals2, "shields_short2"}, {F.Round(shield / healthMax * 100) .. "%", "shields_percent"}, {F.Round(shield / healthMax * 100), "shields_percent_no_sign"}, } @@ -1270,11 +1307,18 @@ local function CreateSetting_HealthFormat(parent) end) widget.shieldColorPicker:SetPoint("LEFT", widget.shieldColorDropdown, "RIGHT", 5, 0) + widget.shieldGradientCB = Cell.CreateCheckButton(widget, "", function(checked) + widget.format.shields.colorByHealth = checked + widget.func() + end, L["colorByHealthTip"]) + widget.shieldGradientCB:SetPoint("LEFT", widget.shieldColorPicker, "RIGHT", 10, 0) + -- heal absorb -------------------------- local healAbsorbList = { {L["None"], "none"}, {healAbsorb, "healabsorbs"}, {F.FormatNumber(healAbsorb), "healabsorbs_short"}, + {F.FormatNumber(healAbsorb, 2) .. decimals2, "healabsorbs_short2"}, {F.Round(healAbsorb / healthMax * 100) .. "%", "healabsorbs_percent"}, {F.Round(healAbsorb / healthMax * 100), "healabsorbs_percent_no_sign"}, } @@ -1332,6 +1376,12 @@ local function CreateSetting_HealthFormat(parent) end) widget.healAbsorbColorPicker:SetPoint("LEFT", widget.healAbsorbColorDropdown, "RIGHT", 5, 0) + widget.healAbsorbGradientCB = Cell.CreateCheckButton(widget, "", function(checked) + widget.format.healAbsorbs.colorByHealth = checked + widget.func() + end, L["colorByHealthTip"]) + widget.healAbsorbGradientCB:SetPoint("LEFT", widget.healAbsorbColorPicker, "RIGHT", 10, 0) + -- callback function widget:SetFunc(func) widget.func = func @@ -1346,24 +1396,30 @@ local function CreateSetting_HealthFormat(parent) widget.health1FormatDropdown:SetSelectedValue(format.health1.format) widget.health1ColorDropdown:SetSelectedValue(format.health1.color[1]) widget.health1ColorPicker:SetColor(unpack(format.health1.color[2])) + widget.health1GradientCB:SetChecked(format.health1.colorByHealth) + widget.health1HideZeroCB:SetChecked(format.health1.hideIfEmptyOrFull) -- health2 widget.health2FormatDropdown:SetSelectedValue(format.health2.format) widget.health2DelimiterEB:SetText(format.health2.delimiter) widget.health2ColorDropdown:SetSelectedValue(format.health2.color[1]) widget.health2ColorPicker:SetColor(unpack(format.health2.color[2])) + widget.health2GradientCB:SetChecked(format.health2.colorByHealth) + widget.health2HideZeroCB:SetChecked(format.health2.hideIfEmptyOrFull) -- shields widget.shieldFormatDropdown:SetSelectedValue(format.shields.format) widget.shieldDelimiterEB:SetText(format.shields.delimiter) widget.shieldColorDropdown:SetSelectedValue(format.shields.color[1]) widget.shieldColorPicker:SetColor(unpack(format.shields.color[2])) + widget.shieldGradientCB:SetChecked(format.shields.colorByHealth) -- heal absorbs widget.healAbsorbFormatDropdown:SetSelectedValue(format.healAbsorbs.format) widget.healAbsorbDelimiterEB:SetText(format.healAbsorbs.delimiter) widget.healAbsorbColorDropdown:SetSelectedValue(format.healAbsorbs.color[1]) widget.healAbsorbColorPicker:SetColor(unpack(format.healAbsorbs.color[2])) + widget.healAbsorbGradientCB:SetChecked(format.healAbsorbs.colorByHealth) end else widget = settingWidgets["healthFormat"] @@ -1523,6 +1579,7 @@ local function CreateSetting_DurationVisibility(parent) return widget end +-- Midnight: simplified duration visibility with only Always/Never options -- (Blizzard's countdown text doesn't support percentage/time thresholds) local function CreateSetting_DurationVisibilitySimple(parent) local widget @@ -1559,6 +1616,7 @@ local function CreateSetting_DurationVisibilitySimple(parent) end function widget:SetDBValue(durationVisibility) + -- Coerce pre-Midnight threshold values (0.75, 10, etc.) to "Always" -- since Blizzard's countdown text only supports on/off, not thresholds. -- The saved value isn't modified — only the dropdown display is coerced. if durationVisibility and durationVisibility ~= false then @@ -1734,35 +1792,21 @@ local function CreateSetting_BarOrientation(parent) widget = Cell.CreateFrame("CellIndicatorSettings_BarOrientation", parent, 240, 50) settingWidgets["barOrientation"] = widget - widget.orientation = Cell.CreateDropdown(widget, 245) + widget.orientation = Cell.CreateDropdown(widget, 153) widget.orientation:SetPoint("TOPLEFT", 5, -20) widget.orientation:SetItems({ { - ["text"] = L["left-to-right"], - ["value"] = "left-to-right", + ["text"] = L["Horizontal"], + ["value"] = "horizontal", ["onClick"] = function() - widget.func("left-to-right") + widget.func("horizontal") end, }, { - ["text"] = L["right-to-left"], - ["value"] = "right-to-left", - ["onClick"] = function() - widget.func("right-to-left") - end, - }, - { - ["text"] = L["top-to-bottom"], - ["value"] = "top-to-bottom", - ["onClick"] = function() - widget.func("top-to-bottom") - end, - }, - { - ["text"] = L["bottom-to-top"], - ["value"] = "bottom-to-top", + ["text"] = L["Vertical"], + ["value"] = "vertical", ["onClick"] = function() - widget.func("bottom-to-top") + widget.func("vertical") end, }, }) @@ -1778,11 +1822,6 @@ local function CreateSetting_BarOrientation(parent) -- show db value function widget:SetDBValue(orientation) - if orientation == "horizontal" then - orientation = "left-to-right" - elseif orientation == "vertical" then - orientation = "top-to-bottom" - end widget.orientation:SetSelectedValue(orientation) end else @@ -4777,7 +4816,7 @@ local function CreateSetting_Auras(parent, index) -- show db value function widget:SetDBValue(title, t, noUpDownButtons, isZeroValid, hasColorPicker) widget.title = title - widget.t = t or {} + widget.t = t widget.noUpDownButtons = noUpDownButtons widget.isZeroValid = isZeroValid widget.hasColorPicker = hasColorPicker @@ -4786,14 +4825,14 @@ local function CreateSetting_Auras(parent, index) if not auraButtons[index] then auraButtons[index] = {} end - CreateAuraButtons(widget.frame, auraButtons[index], widget.t, noUpDownButtons, isZeroValid, hasColorPicker, function(n, diff) + CreateAuraButtons(widget.frame, auraButtons[index], t, noUpDownButtons, isZeroValid, hasColorPicker, function(n, diff) local height = (n + 1) * P.Scale(20) - n * P.Scale(1) widget.frame:SetHeight(height) widget:SetHeight(height + P.Scale(22) + P.Scale(7)) if diff then parent:SetHeight(parent:GetHeight() + P.Scale(diff)) end end, widget.usePicker) - local height = (#widget.t + 1) * P.Scale(20) - #widget.t * P.Scale(1) + local height = (#t + 1) * P.Scale(20) - #t * P.Scale(1) widget.frame:SetHeight(height) widget:SetHeight(height + P.Scale(22) + P.Scale(7)) end @@ -8059,6 +8098,7 @@ function Cell.CreateIndicatorSettings(parent, settingsTable) elseif string.find(setting, "^numPerLine:") then tinsert(widgetsTable, CreateSetting_NumPerLine(parent)) elseif string.find(setting, "^font%-noOffset:") then + -- Midnight: simplified font widget for paired font configs (no anchor/offset) tinsert(widgetsTable, CreateSetting_FontNoOffset(parent)) elseif string.find(setting, "^font") then tinsert(widgetsTable, CreateSetting_Font(parent, string.match(setting, "^(font%d?):?.*$")))