From 00292ca3b4665c3ee9be56182b95e3818c03544e Mon Sep 17 00:00:00 2001 From: Brues <5278969+brues-code@users.noreply.github.com> Date: Sun, 26 Jul 2026 18:30:59 -0500 Subject: [PATCH] Focus/Nameplates now respond solely to UNIT_* events commit 70b1e66c2d43624864d672130fd9846ba8b6a76f Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sun Jul 26 18:30:18 2026 -0500 Use SetSize/SetShown and simplify minimap/map commit 7b6bfe99758787c9347df25feb64998bfcc7228c Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 11:27:14 2026 -0500 Include raidpet frames in /pftest test mode The unit-frame test toggle (showall) only previews frames that exist and are positioned. Raidpet frames are created when raidpet.visible == "1", but LayoutPets' collapse mode only positions pets whose raidpet unit actually exists, so solo/in test mode they stayed hidden. Add a showall branch to LayoutPets that mirror-lays every pet cell and shows it (bypassing collapse and the roster gate), still guarded by the existing showpets check so nothing happens when raidpet is disabled. Call LayoutPets from the /pftest handler so the grid updates immediately on toggle-on and restores to the normal layout on toggle-off. commit 4c65c38647c4046a06c87991803c3e59aad83dd0 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 10:34:33 2026 -0500 Remove unused RangeCache local in UnitInRange commit 6c96bbbe6ca4a97801f5d787271534d6a524f2e4 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 10:34:33 2026 -0500 Use Clamp() for the two-sided clamps in ui-widgets Replace the hand-rolled math.min/math.max and if/elseif clamp idioms in the status bar and scroll frame with Clamp(). Equivalent for every value seen (min <= max always holds), just clearer. commit 830e0a0be19383f12ca09aa13e9a274b1d8cb9bc Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 10:34:33 2026 -0500 Drop vanilla GetItemInfo shim for C_Item.GetItemInfo The compat/vanilla.lua GetItemInfo override reshaped vanilla's tuple into retail order by inserting nil at slot 4 (itemLevel), but truncated at 8 fields, dropping itemEquipLoc/itemTexture. ClassicAPI's global GetItemInfo keeps the vanilla shape (its hook only warms the item cache), so the shim stayed necessary but incomplete. Remove it and point the three callers at ClassicAPI's C_Item.GetItemInfo, which returns the full 18-field retail tuple. Positions 1-8 are identical to the old shim output, so bags/roll are unchanged; character.lua's itemSlot (equipLoc, field 9) was always nil under the truncating shim and now resolves correctly for ShaguScore. commit c0da63657dcea7282c66351656729ce9e939d854 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 10:09:34 2026 -0500 Various cleanup Removes version compatibility checks for TBC/Vanilla, consolidating code to target a single WoW version. Refactors repetitive SetWidth/SetHeight calls to SetSize for cleaner code. Removes duplicate function definitions from unitxp module and simplifies conditional show/hide operations using SetShown. commit 11a6302c2d3a39843a839894d4646fd78e13b944 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 09:53:37 2026 -0500 Delegate pfUI.api.strsplit to ClassicAPI's strsplit Replace the Lua pattern-based implementation with a thin wrapper around ClassicAPI's C-level strsplit. Keeps the pfUI.api.strsplit entry point for backwards compatibility with addons that call it, while dropping the redundant reimplementation. Behavioral note: the old version used ([^delim]+) which silently collapsed empty fields; delegating to real strsplit now preserves them ("a,,b" -> "a", "", "b"). All in-repo callers split numeric color tuples, version strings, or build name-keyed lookup tables, none of which are affected by empty-field preservation. commit 67c126eac8003b7862f4e8e3f663c4fbbf817e8a Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 01:01:02 2026 -0500 Bump ClassicAPI minimum version to 1.8.0 commit a6cf157518fe0969b77d4dea8e4c4ba0dc525670 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 00:49:50 2026 -0500 read spell rank via C_Spell.GetSpellSubtext The rank string comes from the spell subtext ("Rank N"), which ClassicAPI's C_Spell.GetSpellSubtext returns directly -- so drop nampower's GetSpellRecField(spellId, "rank") here. The existing "Rank " gsub parse is unchanged. commit 4b1ba99b4f0c6019dd815fd0a730295dbe1d6a21 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 00:33:20 2026 -0500 Move player info overlay onto ClassicAPI (drop Nampower) The haste/spell-power overlay read both values through Nampower and disabled itself entirely without it. Move both to ClassicAPI so it works on any ClassicAPI client: - Spell power: GetSpellPower("net") (nampower) -> GetSpellBonusDamage(i) (ClassicAPI, same per-school field). Merged the build+scan into one loop; the default school seeds the tiebreak so equal schools still favor it. - Haste: GetUnitField("player", "modCastSpeed") -> UnitSpellHaste("player"), which returns the haste percentage directly (the (1/modCastSpeed-1)*100 conversion is now baked in, off the same UNIT_MOD_CAST_SPEED field, signed). - Dropped the "if not GetUnitField then return" gate -- UpdateInfoText no longer touches Nampower, so the overlay runs everywhere. commit 7df4aa6d506b4af6d55e0a10867583d44928a689 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Sat Jul 25 00:32:44 2026 -0500 Hook the real global _G.UnitHealth for feign death Inside a RegisterModule body, `function UnitHealth(...)` defines UnitHealth on the pfUI environment, not the real global -- so the feign-death real-HP fix only reached callers that resolve UnitHealth through pfUI's env, and missed _G consumers (Blizzard frames, other addons). Hook _G.UnitHealth explicitly (and capture oldUnitHealth from _G) so the un-gate applies everywhere. commit b0bf2fd86996797bfc60161f706fe4c4f791c48f Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Fri Jul 24 21:10:58 2026 -0500 Refactor nampower module Simplify reactive spell storage by using spell IDs instead of texture/name tables. Update to use modern C_Spell APIs (GetSpellTexture, GetSpellName) instead of manual texture paths. Consolidate SetWidth/SetHeight calls to SetSize and use print() instead of DEFAULT_CHAT_FRAME:AddMessage(). commit 0b069613332fa18482d8189d60d837594093d104 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Fri Jul 24 20:54:23 2026 -0500 Use GetNamePlateForUnit for target lookups; drop dead ScanGuid block - Replace the three GetNamePlateForGUID(UnitGUID("target")) round-trips with GetNamePlateForUnit("target"), which resolves the token to a GUID internally -- no UnitGUID string detour, and it returns nil for no-target/no-plate so the UnitExists guards collapse. GetNamePlateForGUID is left for raw-GUID cases. - Remove the dead libunitscan.ScanGuid nameplate block (ScanGuid was deleted from libunitscan long ago, so the guard was never true) -- it carried the last GetUnitField("npcFlags") read. commit 3e6210086e78d92b072c0866e73ad4210ce88752 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Fri Jul 24 20:54:23 2026 -0500 Drop Nampower stats system and polling from unit frames GetUnitStats now reads health/power straight from UnitHealth/UnitPower (the descriptor fields the server broadcasts) -- for a real unit token GetUnitField read nothing different, so the whole Nampower-vs-fallback apparatus was measuring a distinction that no longer exists. Removed: - The stats system: pfUI.uf.stats, pfUIStatsFrame + UpdateStatsDisplay, the lastUnitStats change-cache, the /pfuistats slash command, and every counter increment (event/heartbeat/earlyReturn/throttledSkip/nampower/fallback). - All GetUnitField health reads (GetUnitStats, heal-prediction, health-gradient color) -- collapsed to the UnitHealth/UnitHealthMax they already fell back to. - The heartbeat-polling backstop and its fallbackThrottle/lastEventUpdate deps. Frames now refresh on events only; eventless frames still use their own tick, and range/aggro still run in the eventless-actions block. commit 63001b7b0c305ce7c40cefd5ffe0cea1d9308c0f Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Fri Jul 24 20:09:42 2026 -0500 Move nameplates onto ClassicAPI stable nameplate tokens ClassicAPI now assigns retail-exact, per-plate-stable "nameplateN" tokens and fires vanilla UNIT_* events for them, so the nameplate module can key off the token instead of Nampower/SuperWoW GUID primitives: - Events: UNIT_AURA_GUID/UNIT_FLAGS_GUID -> UNIT_AURA/UNIT_FLAGS, matched by the "nameplateN" token (guarded on the token prefix, since these also fire for target/party/raid). Registered unconditionally -- no GetUnitField gate. - Health: GetUnitField(guid, "health"/"maxHealth") -> UnitHealth/UnitHealthMax on the plate's cached token. Same UNIT_FIELD_HEALTH the server broadcasts (real HP on Turtle; the ~= 100 scaled-vs-real guard is unchanged). - Combat/target in GetCombatStateColor: GetUnitField("flags") + HasFlag -> UnitAffectingCombat(token); GetUnitField("target") + SuperWoW "target" -> the "nameplateNtarget" chain. Dropped the now-dead HasFlag, UNIT_FLAG_IN_COMBAT, and guidTargetTokenCache. - GetCastInfo now takes the token directly; every caller already holds it, so the UnitTokenFromGUID(guid) round-trip is gone (unused module-wide now). NAME_PLATE_UNIT_ADDED caches the token as plate.nameplate.unit alongside the GUID; REMOVED clears both. GUID is retained only as the stable cache key (debuffCache/threatMemory/combatColorCache). Only GetUnitField("npcFlags") remains -- it has no token/vanilla equivalent. commit ce1c49fcbb13db9db03f5c6470750d7e8b2d9aa3 Author: Brues <5278969+brues-code@users.noreply.github.com> Date: Fri Jul 24 18:20:06 2026 -0500 Make focus/focustarget event-driven via ClassicAPI unit events ClassicAPI now fires UNIT_* (health/mana/aura/...) with arg1 == "focus" and arg1 == "focustarget", observed per-unit like target/party/raid. Both frames already registered those events (focus/focustarget are in pfValidUnits) and their OnEvent already matches arg1 == label, so the 0.2s polling ticks were pure workarounds for the missing events. Drop both ticks; the frames now refresh on-event like target, with range/glow still on the shared 0.5s state pass and PLAYER_FOCUS_CHANGED still driving assign/clear. --- api/api.lua | 20 +- api/ui-widgets.lua | 80 ++--- api/unitframes.lua | 438 ++----------------------- compat/vanilla.lua | 9 - libs/libdebuff.lua | 2 +- libs/libpredict.lua | 10 +- modules/bags.lua | 2 +- modules/castbar.lua | 4 +- modules/feigndeath.lua | 4 +- modules/focus.lua | 8 +- modules/map.lua | 6 +- modules/minimap.lua | 35 +- modules/nameplates.lua | 180 ++++------ modules/nampower.lua | 24 +- modules/player.lua | 23 +- modules/raid.lua | 7 + modules/roll.lua | 2 +- modules/unitxp.lua | 20 -- modules/whisperproxy.lua | 3 +- modules/xpbar.lua | 12 +- pfUI.lua | 2 +- skins/blizzard/auction.lua | 13 +- skins/blizzard/battlefield.lua | 3 +- skins/blizzard/battlefield_minimap.lua | 3 +- skins/blizzard/character.lua | 14 +- skins/blizzard/lft.lua | 6 +- skins/blizzard/questlog.lua | 30 +- skins/blizzard/readycheck.lua | 15 +- skins/blizzard/talents.lua | 9 +- 29 files changed, 220 insertions(+), 764 deletions(-) diff --git a/api/api.lua b/api/api.lua index b98a4e0b..878ed9c9 100644 --- a/api/api.lua +++ b/api/api.lua @@ -64,6 +64,10 @@ end -- Requires UnitXP_SP3 function pfUI.api.UnitInLineOfSight(unit1, unit2) if not pfUI.api.HasUnitXP() then return nil end + if not unit2 then + unit2 = unit1 + unit1 = "player" + end local success, inSight = pcall(UnitXP, "inSight", unit1, unit2) if success then return inSight end return nil @@ -74,6 +78,10 @@ end -- Requires UnitXP_SP3 function pfUI.api.UnitIsBehind(unit1, unit2) if not pfUI.api.HasUnitXP() then return nil end + if not unit2 then + unit2 = unit1 + unit1 = "player" + end local success, behind = pcall(UnitXP, "behind", unit1, unit2) if success then return behind end return nil @@ -84,17 +92,18 @@ gfind = string.gmatch or string.gfind mod = math.mod or mod -- [ strsplit ] --- Splits a string using a delimiter. +-- Splits a string using a delimiter. Thin wrapper that delegates to +-- ClassicAPI's C-level strsplit, kept as a pfUI.api entry point for +-- backwards compatibility with addons that call pfUI.api.strsplit. +-- Note: unlike the old Lua implementation, empty fields are preserved +-- (e.g. "a,,b" -> "a", "", "b"), matching real strsplit semantics. -- 'delimiter' [string] characters that will be interpreted as delimiter -- characters (bytes) in the string. -- 'subject' [string] String to split. -- return: [list] a list of strings. function pfUI.api.strsplit(delimiter, subject) if not subject then return nil end - local delimiter, fields = delimiter or ":", {} - local pattern = string.format("([^%s]+)", delimiter) - string.gsub(subject, pattern, function(c) fields[table.getn(fields)+1] = c end) - return unpack(fields) + return _G.strsplit(delimiter or ":", subject) end -- [ isempty ] @@ -131,7 +140,6 @@ end -- It takes care of the rangecheck module if existing. -- unit [string] A unit to query (string, unitID) -- return: [bool] "1" if in range otherwise "nil" -local RangeCache = {} function pfUI.api.UnitInRange(unit) if not UnitExists(unit) or not UnitIsVisible(unit) then return nil diff --git a/api/ui-widgets.lua b/api/ui-widgets.lua index 0de64bf6..46bc7fc0 100644 --- a/api/ui-widgets.lua +++ b/api/ui-widgets.lua @@ -21,8 +21,7 @@ do -- statusbars local handlers = { ["DisplayValue"] = function(self, val) - val = val > self.max and self.max or val - val = val < self.min and self.min or val + val = Clamp(val, self.min, self.max) -- remove animation queue if val == self.val_ then @@ -38,8 +37,7 @@ do -- statusbars point = height / (self.max - self.min) * (val - self.min) -- keep values in limits - point = math.min(height, point) - point = math.max(0, point) + point = Clamp(point, 0, height) -- set point to zero if value and max is zero if val == 0 then point = 0 end @@ -57,8 +55,7 @@ do -- statusbars point = width / (self.max - self.min) * (val - self.min) -- keep values in limits - point = math.min(width, point) - point = math.max(0, point) + point = Clamp(point, 0, width) -- set point to zero if value and max is zero if val == 0 then point = 0 end @@ -138,15 +135,8 @@ do -- statusbars end do -- dropdown - local _, class = UnitClass("player") - local color = PFUI_CLASS_COLORS[class] - local function ListEntryOnShow() - if this.parent.id == this.id then - this.icon:Show() - else - this.icon:Hide() - end + this.icon:SetShown(this.parent.id == this.id) end local function ListEntryOnClick() @@ -288,8 +278,7 @@ do -- dropdown frame.icon = frame:CreateTexture(nil, "OVERLAY") frame.icon:SetPoint("RIGHT", frame, "RIGHT", -2, 0) - frame.icon:SetHeight(16) - frame.icon:SetWidth(16) + frame.icon:SetSize(16, 16) frame.icon:SetTexture("Interface\\Buttons\\UI-CheckBox-Check") frame.text = frame:CreateFontString(nil, "OVERLAY") @@ -329,8 +318,7 @@ do -- dropdown local button = CreateFrame("Button", nil, frame) button:SetPoint("RIGHT", frame, "RIGHT", -2, 0) - button:SetWidth(16) - button:SetHeight(16) + button:SetSize(16, 16) button:SetScript("OnClick", ListButtonOnClick) SkinArrowButton(button, "down") button.icon:SetVertexColor(1,.9,.1) @@ -380,8 +368,7 @@ function pfUI.api.CreateTabChild(self, title, bwidth, bheight, bottom, static) end -- set dimensions - b:SetHeight(button_height) - b:SetWidth(button_width) + b:SetSize(button_width, button_height) b:SetID(childcount) if not self.align or self.align == "LEFT" then @@ -516,13 +503,7 @@ function pfUI.api.CreateScrollFrame(name, parent) local max = f:GetVerticalScrollRange() local new = current - step - if new >= max then - f:SetVerticalScroll(max) - elseif new <= 0 then - f:SetVerticalScroll(0) - else - f:SetVerticalScroll(new) - end + f:SetVerticalScroll(Clamp(new, 0, max)) f:UpdateScrollState() end @@ -539,8 +520,7 @@ function pfUI.api.CreateScrollChild(name, parent) local f = CreateFrame("Frame", name, parent) -- dummy values required - f:SetWidth(1) - f:SetHeight(1) + f:SetSize(1, 1) f:SetAllPoints(parent) parent:SetScrollChild(f) @@ -607,8 +587,7 @@ end function pfUI.api.SetHighlight(frame, cr, cg, cb) if not frame then return end if not cr or not cg or not cb then - local _, class = UnitClass("player") - cr, cg, cb = GetClassColor(class) + cr, cg, cb = GetClassColor(UnitClassBase('player')) end frame.cr, frame.cg, frame.cb = cr, cg, cb, ca @@ -653,8 +632,7 @@ function pfUI.api.SkinButton(button, cr, cg, cb, icon, disableHighlight) if not b then b = button end if not b then return end if not cr or not cg or not cb then - local _, class = UnitClass("player") - cr, cg, cb = GetClassColor(class) + cr, cg, cb = GetClassColor(UnitClassBase('player')) end pfUI.api.CreateBackdrop(b, nil, true) b:SetNormalTexture("") @@ -702,8 +680,7 @@ function pfUI.api.SkinCollapseButton(button, all) b.icon = _G[name] or CreateFrame("Button", name, b) if all then size = 14 end - b.icon:SetWidth(size) - b.icon:SetHeight(size) + b.icon:SetSize(size, size) b.icon:SetPoint("LEFT", 2, 2) CreateBackdrop(b.icon) b.icon.text = b.icon:CreateFontString(nil, "OVERLAY") @@ -732,12 +709,10 @@ end function pfUI.api.SkinRotateButton(button) pfUI.api.CreateBackdrop(button) - local _, class = UnitClass("player") - local color = PFUI_CLASS_COLORS[class] - local cr, cg, cb = color.r , color.g, color.b + local cr, cg, cb = GetClassColor(UnitClassBase('player')) - button:SetWidth(button:GetWidth() - 18) - button:SetHeight(button:GetHeight() - 18) + local btnW, btnH = button:GetSize() + button:SetSize(btnW - 18, btnH - 18) button:GetNormalTexture():SetTexCoord(0.3, 0.29, 0.3, 0.65, 0.69, 0.29, 0.69, 0.65) button:GetPushedTexture():SetTexCoord(0.3, 0.29, 0.3, 0.65, 0.69, 0.29, 0.69, 0.65) @@ -759,8 +734,7 @@ function pfUI.api.SkinCloseButton(button, parentFrame, offsetX, offsetY) SkinButton(button, 1, .25, .25) - button:SetWidth(15) - button:SetHeight(15) + button:SetSize(15, 15) if parentFrame then button:ClearAllPoints() @@ -787,8 +761,7 @@ function pfUI.api.SkinArrowButton(button, dir, size) button:SetDisabledTexture(nil) if size then - button:SetWidth(size) - button:SetHeight(size) + button:SetSize(size, size) end if not button.icon then @@ -894,8 +867,7 @@ function pfUI.api.SkinCheckbox(frame, size) frame:SetPushedTexture("") frame:SetHighlightTexture("") if size then - frame:SetWidth(size) - frame:SetHeight(size) + frame:SetSize(size, size) end CreateBackdrop(frame) SetAllPointsOffset(frame.backdrop, frame, 4) @@ -936,9 +908,7 @@ function pfUI.api.SkinDropDown(frame, cr, cg, cb, useSmall) end if not cr or not cg or not cb then - local _, class = UnitClass("player") - local color = PFUI_CLASS_COLORS[class] - cr, cg, cb = color.r , color.g, color.b + cr, cg, cb = GetClassColor(UnitClassBase('player')) end SetHighlight(button, cr, cg, cb) @@ -1108,8 +1078,7 @@ function pfUI.api.CreateQuestionDialog(text, yes, no, editbox, onclose) -- buttons question.yes = CreateFrame("Button", "pfQuestionDialogYes", question, "UIPanelButtonTemplate") pfUI.api.SkinButton(question.yes) - question.yes:SetWidth(100) - question.yes:SetHeight(22) + question.yes:SetSize(100, 22) question.yes:SetText(yescap) question.yes:SetScript("OnClick", function() if yes then yes() end @@ -1124,8 +1093,7 @@ function pfUI.api.CreateQuestionDialog(text, yes, no, editbox, onclose) question.no = CreateFrame("Button", "pfQuestionDialogNo", question, "UIPanelButtonTemplate") pfUI.api.SkinButton(question.no) - question.no:SetWidth(100) - question.no:SetHeight(22) + question.no:SetSize(100, 22) question.no:SetText(nocap) question.no:SetScript("OnClick", function() if no then no() end @@ -1141,8 +1109,7 @@ function pfUI.api.CreateQuestionDialog(text, yes, no, editbox, onclose) question.close = CreateFrame("Button", "pfQuestionDialogClose", question) question.close:SetPoint("TOPRIGHT", -border, -border) pfUI.api.CreateBackdrop(question.close) - question.close:SetHeight(10) - question.close:SetWidth(10) + question.close:SetSize(10, 10) question.close.texture = question.close:CreateTexture("pfQuestionDialogCloseTex") question.close.texture:SetTexture(pfUI.media["img:close"]) question.close.texture:ClearAllPoints() @@ -1244,9 +1211,8 @@ function pfUI.api.CreateInfoBox(text, time, parent, height) infobox.duration = time infobox.lastshow = GetTime() - infobox:SetWidth(infobox.text:GetStringWidth() + 50) + infobox:SetSize(infobox.text:GetStringWidth() + 50, height) infobox:SetParent(parent) - infobox:SetHeight(height) infobox:SetFrameStrata("FULLSCREEN_DIALOG") infobox:Show() diff --git a/api/unitframes.lua b/api/unitframes.lua index 33c922aa..0e588f5a 100644 --- a/api/unitframes.lua +++ b/api/unitframes.lua @@ -21,6 +21,7 @@ end -- slash command to toggle unitframe test mode pfUI.api.RegisterSlashCommand("PFTEST", { "/pftest", "/pfuftest" }, function() pfUI.uf.showall = not pfUI.uf.showall + if pfUI.uf.raid and pfUI.uf.raid.LayoutPets then pfUI.uf.raid:LayoutPets() end end, true) -- HoT buff indicators that need name verification because their icons are @@ -126,75 +127,16 @@ visibilityscan:SetScript("OnUpdate", function() end) -- ============================================================================ --- GetUnitStats - Nampower Integration for Health + Power +-- GetUnitStats - health + power for a unit token. -- Returns: hp, maxHp, power, maxPower, powerType --- IMPORTANT: Uses _G.UnitExists directly to avoid conflicts with Nampower's --- use UnitGUID(unit) for GUID lookup (Nampower 3.0.0+) -- ============================================================================ - --- Cache für Stats-Tracking (nur Änderungen zählen) -pfUI.api.lastUnitStats = pfUI.api.lastUnitStats or {} - -function pfUI.api.GetUnitStats(unitstr, trackStats) - local hp, maxHp, power, maxPower, powerType - local usedNampower = false - - powerType = UnitPowerType(unitstr) or 0 - power = UnitPower(unitstr, powerType) - maxPower = UnitPowerMax(unitstr, powerType) - - -- Try GetUnitField first if available (for all units: players, pets, NPCs) - if GetUnitField then - -- Use the standard check first, then get guid separately - local exists = _G.UnitExists(unitstr) - if exists then - local guid = _G.UnitGUID(unitstr) - hp = GetUnitField(guid, "health") - maxHp = GetUnitField(guid, "maxHealth") - -- Check if Nampower gave valid health data - if hp and hp > 0 and maxHp and maxHp > 0 then - usedNampower = true - -- Track Nampower success - NUR bei echten Änderungen - if trackStats and pfUI.uf and pfUI.uf.stats and pfUI.uf.stats.enabled then - local lastStats = pfUI.api.lastUnitStats[unitstr] - if not lastStats or lastStats.hp ~= hp or lastStats.maxHp ~= maxHp or - lastStats.power ~= power or lastStats.maxPower ~= maxPower then - pfUI.uf.stats.nampowerUsed = (pfUI.uf.stats.nampowerUsed or 0) + 1 - pfUI.api.lastUnitStats[unitstr] = { - hp = hp, - maxHp = maxHp, - power = power, - maxPower = maxPower - } - end - end - return hp, maxHp, power or 0, maxPower or 1, powerType - end - end - end - - -- Fallback to standard API (for players when Nampower fails) - hp = UnitHealth(unitstr) or 0 - maxHp = UnitHealthMax(unitstr) or 1 - - -- Track Fallback usage - NUR bei echten Änderungen - if trackStats and not usedNampower then - if pfUI.uf and pfUI.uf.stats and pfUI.uf.stats.enabled then - local lastStats = pfUI.api.lastUnitStats[unitstr] - if not lastStats or lastStats.hp ~= hp or lastStats.maxHp ~= maxHp or - lastStats.power ~= power or lastStats.maxPower ~= maxPower then - pfUI.uf.stats.fallbackUsed = (pfUI.uf.stats.fallbackUsed or 0) + 1 - pfUI.api.lastUnitStats[unitstr] = { - hp = hp, - maxHp = maxHp, - power = power, - maxPower = maxPower - } - end - end - end - - return hp, maxHp, power, maxPower, powerType +function pfUI.api.GetUnitStats(unitstr) + local powerType = UnitPowerType(unitstr) or 0 + return UnitHealth(unitstr) or 0, + UnitHealthMax(unitstr) or 1, + UnitPower(unitstr, powerType) or 0, + UnitPowerMax(unitstr, powerType) or 1, + powerType end local aggrodata = { } @@ -378,19 +320,16 @@ function pfUI.uf:UpdateFrameSize() if self.config.portrait == "left" or self.config.portrait == "right" then if ptwidth == "-1" and ptheight == "-1" then -- align portrait size to frame - self.portrait:SetWidth(real_height) - self.portrait:SetHeight(real_height) + self.portrait:SetSize(real_height, real_height) portrait = real_height + spacing + 2*default_border else -- use custom portrait size - self.portrait:SetWidth(ptwidth) - self.portrait:SetHeight(ptheight) + self.portrait:SetSize(ptwidth, ptheight) portrait = ptwidth + spacing + 2*default_border end end - self:SetWidth(width + portrait) - self:SetHeight(real_height) + self:SetSize(width + portrait, real_height) end function pfUI.uf:UpdateConfig() @@ -427,8 +366,7 @@ function pfUI.uf:UpdateConfig() f.glow:SetScript("OnUpdate", pfUI.uf.glow.UpdateGlowAnimation) f.glow:Hide() - f.combat:SetWidth(tonumber(f.config.squaresize)) - f.combat:SetHeight(tonumber(f.config.squaresize)) + f.combat:SetSize(tonumber(f.config.squaresize), tonumber(f.config.squaresize)) f.combat:ClearAllPoints() f.combat:SetPoint(f.config.squarepos, 0, 0) f.combat:Hide() @@ -436,8 +374,7 @@ function pfUI.uf:UpdateConfig() f.hp:ClearAllPoints() f.hp:SetPoint("TOP", 0, 0) - f.hp:SetWidth(f.config.width) - f.hp:SetHeight(f.config.height) + f.hp:SetSize(f.config.width, f.config.height) if tonumber(f.config.height) < 0 then f.hp:Hide() end pfUI.api.CreateBackdrop(f.hp, default_border) @@ -589,11 +526,7 @@ function pfUI.uf:UpdateConfig() end if f.group then - if f.config.raidgrouplabel == "1" then - f.group:Show() - else - f.group:Hide() - end + f.group:SetShown(f.config.raidgrouplabel == "1") local xoff = tonumber(f.config.grouplabelxoff) or 0 local yoff = tonumber(f.config.grouplabelyoff) or 8 @@ -662,8 +595,7 @@ function pfUI.uf:UpdateConfig() f.powerCenterText:SetPoint("TOPLEFT",f.power.bar, "TOPLEFT", f.config.txtpowercenteroffx, 1 + tonumber(f.config.txtpowercenteroffy)) f.powerCenterText:SetPoint("BOTTOMRIGHT",f.power.bar, "BOTTOMRIGHT", f.config.txtpowercenteroffx, f.config.txtpowercenteroffy) - f.incHeal:SetHeight(f.config.height) - f.incHeal:SetWidth(f.config.width) + f.incHeal:SetSize(f.config.width, f.config.height) f.incHeal.texture:SetTexture(pfUI.media["img:bar"]) local cr, cg, cb, ca = GetStringColor(f.config.healcolor) cr, cg, cb, ca = tonumber(cr), tonumber(cg), tonumber(cb), tonumber(ca) @@ -679,53 +611,46 @@ function pfUI.uf:UpdateConfig() end f.ressIcon:SetFrameLevel(16) - f.ressIcon:SetWidth(32) - f.ressIcon:SetHeight(32) + f.ressIcon:SetSize(32, 32) f.ressIcon:SetPoint("CENTER", f, "CENTER", 0, 4) f.ressIcon.texture:SetTexture(pfUI.media["img:ress"]) f.ressIcon.texture:SetAllPoints(f.ressIcon) f.ressIcon:Hide() - f.leaderIcon:SetWidth(10) - f.leaderIcon:SetHeight(10) + f.leaderIcon:SetSize(10, 10) f.leaderIcon:SetPoint("CENTER", f, "TOPLEFT", 0, 0) f.leaderIcon.texture:SetTexture("Interface\\GROUPFRAME\\UI-Group-LeaderIcon") f.leaderIcon.texture:SetAllPoints(f.leaderIcon) f.leaderIcon:Hide() - f.lootIcon:SetWidth(10) - f.lootIcon:SetHeight(10) + f.lootIcon:SetSize(10, 10) f.lootIcon:SetPoint("CENTER", f, "LEFT", 0, 0) f.lootIcon.texture:SetTexture("Interface\\GROUPFRAME\\UI-Group-MasterLooter") f.lootIcon.texture:SetAllPoints(f.lootIcon) f.lootIcon:Hide() - f.pvpIcon:SetWidth(f.config.pvpiconsize) - f.pvpIcon:SetHeight(f.config.pvpiconsize) + f.pvpIcon:SetSize(f.config.pvpiconsize, f.config.pvpiconsize) f.pvpIcon:SetPoint(f.config.pvpiconalign, f, f.config.pvpiconalign, f.config.pvpiconoffx, f.config.pvpiconoffy) f.pvpIcon.texture:SetTexture(pfUI.media["img:pvp"]) f.pvpIcon.texture:SetAllPoints(f.pvpIcon) f.pvpIcon.texture:SetVertexColor(1,1,1,.5) f.pvpIcon:Hide() - f.raidIcon:SetWidth(f.config.raidiconsize) - f.raidIcon:SetHeight(f.config.raidiconsize) + f.raidIcon:SetSize(f.config.raidiconsize, f.config.raidiconsize) f.raidIcon:SetPoint("CENTER", f, f.config.raidiconalign, f.config.raidiconoffx, f.config.raidiconoffy) local raidIconTex = C.unitframes.blizzard_raidicons == "1" and "Interface\\TargetingFrame\\UI-RaidTargetingIcons" or pfUI.media["img:raidicons"] f.raidIcon.texture:SetTexture(raidIconTex) f.raidIcon.texture:SetAllPoints(f.raidIcon) f.raidIcon:Hide() - f.restIcon:SetWidth(16) - f.restIcon:SetHeight(16) + f.restIcon:SetSize(16, 16) f.restIcon:SetPoint("TOP", f, "TOPLEFT", 0, -1) f.restIcon.texture:SetTexture("Interface\\CharacterFrame\\UI-StateIcon", true) f.restIcon.texture:SetTexCoord(0, .5, 0, .421875) f.restIcon.texture:SetAllPoints(f.restIcon) f.restIcon:Hide() - f.happinessIcon:SetWidth(tonumber(C.unitframes.pet.happinesssize)) - f.happinessIcon:SetHeight(tonumber(C.unitframes.pet.happinesssize)) + f.happinessIcon:SetSize(tonumber(C.unitframes.pet.happinesssize), tonumber(C.unitframes.pet.happinesssize)) f.happinessIcon:SetPoint("CENTER", f, "TOPLEFT", default_border, -default_border) f.happinessIcon.texture:SetTexture(pfUI.media["img:neutral"]) f.happinessIcon.texture:SetAllPoints(f.happinessIcon) @@ -896,11 +821,7 @@ function pfUI.uf:UpdateConfig() -- immediately show/hide existing cooldown text if f.debuffs[i].cd.pfCooldownText then - if cooldown_text == 1 then - f.debuffs[i].cd.pfCooldownText:Show() - else - f.debuffs[i].cd.pfCooldownText:Hide() - end + f.debuffs[i].cd.pfCooldownText:SetShown(cooldown_text == 1) end f.debuffs[i].id = i @@ -1030,8 +951,6 @@ function pfUI.uf.OnEvent() this.update_full = true -- UNIT_XXX Events elseif arg1 and (arg1 == this.label .. this.id or (UnitGUID and arg1 == UnitGUID(this.label .. this.id))) then - this.lastEventUpdate = GetTime() - if event == "UNIT_PORTRAIT_UPDATE" or event == "UNIT_MODEL_CHANGED" then this.update_portrait = true elseif event == "UNIT_AURA" then @@ -1053,154 +972,19 @@ local _GetTime = GetTime pfUI.uf.now = 0 -- ============================================================================ --- GLOBAL FALLBACK THROTTLE - Limits total fallback updates across ALL frames --- ============================================================================ -pfUI.uf.fallbackThrottle = { - lastUpdate = 0, - interval = 0.1, -- 10 updates per second total (not per frame!) - updatesThisInterval = 0, - maxUpdatesPerInterval = 5 -- Max 5 frames can update per interval -} - --- ============================================================================ --- STATS SYSTEM - Performance tracking for Nampower vs Fallback --- ============================================================================ -pfUI.uf.stats = { - eventUpdates = 0, - heartbeatUpdates = 0, - earlyReturns = 0, - nampowerUsed = 0, - fallbackUsed = 0, - throttledSkips = 0, - startTime = 0, - enabled = true -} - --- Stats Frame (Live Display) -pfUI.uf.statsFrame = CreateFrame("Frame", "pfUIStatsFrame", UIParent) -pfUI.uf.statsFrame:SetWidth(200) -pfUI.uf.statsFrame:SetHeight(220) -pfUI.uf.statsFrame:SetPoint("TOPRIGHT", UIParent, "TOPRIGHT", -10, -200) -pfUI.uf.statsFrame:SetBackdrop({ - bgFile = "Interface\\Tooltips\\UI-Tooltip-Background", - edgeFile = "Interface\\Tooltips\\UI-Tooltip-Border", - tile = true, tileSize = 16, edgeSize = 8, - insets = { left = 3, right = 3, top = 3, bottom = 3 } -}) -pfUI.uf.statsFrame:SetBackdropColor(0, 0, 0, 0.8) -pfUI.uf.statsFrame:EnableMouse(true) -pfUI.uf.statsFrame:SetMovable(true) -pfUI.uf.statsFrame:SetClampedToScreen(true) -pfUI.uf.statsFrame:RegisterForDrag("LeftButton") -pfUI.uf.statsFrame:SetScript("OnDragStart", function() this:StartMoving() end) -pfUI.uf.statsFrame:SetScript("OnDragStop", function() this:StopMovingOrSizing() end) -pfUI.uf.statsFrame:Hide() - --- Stats Title -pfUI.uf.statsFrame.title = pfUI.uf.statsFrame:CreateFontString(nil, "OVERLAY", "GameFontNormalLarge") -pfUI.uf.statsFrame.title:SetPoint("TOP", pfUI.uf.statsFrame, "TOP", 0, -8) -pfUI.uf.statsFrame.title:SetText("Performance") - --- Stats Text (multi-line) -pfUI.uf.statsFrame.text = pfUI.uf.statsFrame:CreateFontString(nil, "OVERLAY", "GameFontNormalSmall") -pfUI.uf.statsFrame.text:SetPoint("TOPLEFT", pfUI.uf.statsFrame, "TOPLEFT", 10, -30) -pfUI.uf.statsFrame.text:SetWidth(180) -pfUI.uf.statsFrame.text:SetHeight(180) -pfUI.uf.statsFrame.text:SetJustifyH("LEFT") -pfUI.uf.statsFrame.text:SetJustifyV("TOP") -pfUI.uf.statsFrame.text:SetText("Initializing...") - --- Update function for stats display -pfUI.uf.UpdateStatsDisplay = function() - local elapsed = GetTime() - pfUI.uf.stats.startTime - if elapsed < 0.1 then return end - - local eventRate = pfUI.uf.stats.eventUpdates / elapsed - local heartbeatRate = pfUI.uf.stats.heartbeatUpdates / elapsed - local totalFrameUpdates = eventRate + heartbeatRate - - -- Calculate Nampower vs Fallback percentages (ONLY counts actual data changes!) - local totalDataChanges = pfUI.uf.stats.nampowerUsed + pfUI.uf.stats.fallbackUsed - local nampowerPct = totalDataChanges > 0 and math.floor((pfUI.uf.stats.nampowerUsed / totalDataChanges) * 100) or 0 - local fallbackPct = totalDataChanges > 0 and math.floor((pfUI.uf.stats.fallbackUsed / totalDataChanges) * 100) or 0 - - -- Calculate data change rate (how often HP/Mana actually changes) - local dataChangeRate = totalDataChanges / elapsed - - local statsText = string.format( - "Time: %.1fs\n" .. - "|cffaaaaaa--- Frame Updates ---|r\n" .. - "Event: %.1f/s (%d)\n" .. - "Heartbeat: %.1f/s (%d)\n" .. - "Total: %.1f/s\n" .. - "\n" .. - "|cffaaaaaa--- Data Changes ---|r\n" .. - "Rate: %.1f/s (%d)\n" .. - "|cff00ff00NP: %d%% (%d)|r\n" .. - "|cffff8800FB: %d%% (%d)|r", - elapsed, - eventRate, - pfUI.uf.stats.eventUpdates, - heartbeatRate, - pfUI.uf.stats.heartbeatUpdates, - totalFrameUpdates, - dataChangeRate, - totalDataChanges, - nampowerPct, - pfUI.uf.stats.nampowerUsed, - fallbackPct, - pfUI.uf.stats.fallbackUsed - ) - - pfUI.uf.statsFrame.text:SetText(statsText) -end - --- Stats update timer -pfUI.uf.statsUpdateTimer = 0 - --- Cache cleanup timer (clean lastUnitStats every 30s to prevent memory leak) -pfUI.uf.cacheCleanupTimer = 0 - --- ============================================================================ --- OnUpdate with Heartbeat Polling and Fallback +-- OnUpdate - eventless per-frame work (range check, aggro glow) and draining +-- the event-set update flags. Frames refresh on events only; no polling. -- ============================================================================ function pfUI.uf.OnUpdate() local now = _GetTime() pfUI.uf.now = now - - -- Update stats display (throttled to 0.2s) - if pfUI.uf.statsFrame and pfUI.uf.statsFrame:IsShown() then - if (pfUI.uf.statsUpdateTimer or 0) <= now then - pfUI.uf.statsUpdateTimer = now + 0.2 - if pfUI.uf.stats.startTime > 0 then - pfUI.uf.UpdateStatsDisplay() - end - end - end - - -- Cleanup lastUnitStats cache every 30 seconds to prevent memory leak - if (pfUI.uf.cacheCleanupTimer or 0) <= now then - pfUI.uf.cacheCleanupTimer = now + 30 - - -- Only keep cache for units that currently exist - if pfUI.api.lastUnitStats then - for unitstr in pairs(pfUI.api.lastUnitStats) do - if not _G.UnitExists(unitstr) then - pfUI.api.lastUnitStats[unitstr] = nil - end - end - end - end - + -- update combat feedback (no throttle - needs immediate feedback) if this.feedbackText then CombatFeedback_OnUpdate(arg1) end -- Throttle raid/party frames for performance if this.label == "raid" or this.label == "party" then if (this.throttleTick or 0) > now then - if pfUI.uf.stats and pfUI.uf.stats.enabled then - pfUI.uf.stats.throttledSkips = pfUI.uf.stats.throttledSkips + 1 - end return end this.throttleTick = now + 0.1 -- Default: 10 FPS @@ -1284,19 +1068,7 @@ function pfUI.uf.OnUpdate() local unit = this.label .. this.id local heal = libpredict:UnitGetIncomingHeals(unit) - -- O(1) Nampower lookup via GUID (same pattern as nameplates.lua) - local health, maxHealth - if GetUnitField then - local guid = UnitGUID(unit) - if guid then - health = GetUnitField(guid, "health") - maxHealth = GetUnitField(guid, "maxHealth") - end - end - -- Fallback to standard API - if not health or not maxHealth or maxHealth == 0 then - health, maxHealth = UnitHealth(unit), UnitHealthMax(unit) - end + local health, maxHealth = UnitHealth(unit), UnitHealthMax(unit) if heal - health - maxHealth ~= this.predictstate then local overhealperc = tonumber(this.config.overhealperc) @@ -1353,86 +1125,6 @@ function pfUI.uf.OnUpdate() -- EVENT-BASED UPDATES (Health, Mana, Auras, etc.) -- ============================================================================ - -- Check if we have pending updates from events - local hasUpdates = this.update_full or this.update_base or - this.update_aura or this.update_portrait or - this.update_pvp or this.update_indicators - - -- Track event-triggered updates (not API calls, just frame updates) - if hasUpdates and pfUI.uf.stats and pfUI.uf.stats.enabled then - pfUI.uf.stats.eventUpdates = pfUI.uf.stats.eventUpdates + 1 - end - - -- Heartbeat Polling: If no events pending, check if we need fallback - if not hasUpdates then - local timeSinceEvent = this.lastEventUpdate and (now - this.lastEventUpdate) or 999 - - -- If >0.5s since last event and unit exists, try heartbeat - if timeSinceEvent > 0.5 and this.label and _G.UnitExists(this.label .. this.id) then - local needsFallback = false - - -- Check if Nampower can provide data - if GetUnitField then - -- Use _G.UnitExists to avoid conflicts with range checking - local unitstr = this.label .. this.id - local exists = _G.UnitExists(unitstr) - if exists then - local _, guid = _G.UnitExists(unitstr) - if guid then - local hp = GetUnitField(guid, "health") - if not hp or hp == 0 then - needsFallback = true - end - else - needsFallback = true - end - else - needsFallback = true - end - else - needsFallback = true - end - - if needsFallback then - -- GLOBAL Throttle: Limit fallback updates across ALL frames - local throttle = pfUI.uf.fallbackThrottle - - -- Reset counter each interval - if now - throttle.lastUpdate > throttle.interval then - throttle.lastUpdate = now - throttle.updatesThisInterval = 0 - end - - -- Check if we've exceeded max updates this interval - if throttle.updatesThisInterval >= throttle.maxUpdatesPerInterval then - if pfUI.uf.stats and pfUI.uf.stats.enabled then - pfUI.uf.stats.earlyReturns = pfUI.uf.stats.earlyReturns + 1 - end - return - end - - throttle.updatesThisInterval = throttle.updatesThisInterval + 1 - - -- Nampower not available or no data - trigger fallback update - this.update_base = true - if pfUI.uf.stats and pfUI.uf.stats.enabled then - pfUI.uf.stats.heartbeatUpdates = pfUI.uf.stats.heartbeatUpdates + 1 - end - else - -- Nampower working fine, no update needed - if pfUI.uf.stats and pfUI.uf.stats.enabled then - pfUI.uf.stats.earlyReturns = pfUI.uf.stats.earlyReturns + 1 - end - return - end - else - -- Too soon or unit doesn't exist - if pfUI.uf.stats and pfUI.uf.stats.enabled then - pfUI.uf.stats.earlyReturns = pfUI.uf.stats.earlyReturns + 1 - end - return - end - end -- process indicator update events if this.update_indicators then @@ -2316,7 +2008,7 @@ function pfUI.uf:RefreshUnit(unit, component) -- base frame if component == "all" or component == "base" then -- Unit HP/MP with Nampower Integration - local hp, hpmax, power, powermax, powerType = pfUI.api.GetUnitStats(unitstr, true) + local hp, hpmax, power, powermax, powerType = pfUI.api.GetUnitStats(unitstr) -- Store original values for color calculations (before invert_healthbar modifies hp) local hp_orig, hpmax_orig = hp, hpmax @@ -2891,7 +2583,7 @@ function pfUI.uf:GetStatusValue(unit, pos) end -- Get stats with Nampower Integration - local hp, hpmax, mp, mpmax, powerType = pfUI.api.GetUnitStats(unitstr, true) + local hp, hpmax, mp, mpmax, powerType = pfUI.api.GetUnitStats(unitstr) local rhp, rhpmax = hp, hpmax -- Use libhealth for mob health estimation (overrides Nampower/Standard) @@ -3047,19 +2739,7 @@ function pfUI.uf.GetColor(self, preset) r, g, b = color.r, color.g, color.b elseif preset == "health" and config["healthcolor"] == "1" then - -- O(1) Nampower lookup for health gradient color - local hp, hpmax - if GetUnitField then - local guid = UnitGUID(unitstr) - if guid then - hp = GetUnitField(guid, "health") - hpmax = GetUnitField(guid, "maxHealth") - end - end - -- Fallback to standard API - if not hp or not hpmax then - hp, hpmax = UnitHealth(unitstr), UnitHealthMax(unitstr) - end + local hp, hpmax = UnitHealth(unitstr), UnitHealthMax(unitstr) if hpmax and hpmax > 0 then r, g, b = GetColorGradient(hp / hpmax) else @@ -3081,59 +2761,3 @@ function pfUI.uf.GetColor(self, preset) return rgbhex(r,g,b) end --- ============================================================================ --- Slash Commands for Stats Frame --- ============================================================================ -pfUI.api.RegisterSlashCommand("PFUISTATS", { "/pfuistats", "/ufstats" }, function(msg) - msg = string.lower(msg or "") - - if not pfUI.uf.stats then - DEFAULT_CHAT_FRAME:AddMessage("|cffff0000ERROR:|r Stats not initialized!") - return - end - - -- Initialize startTime on first use - if pfUI.uf.stats.startTime == 0 then - pfUI.uf.stats.startTime = GetTime() - end - - if msg == "reset" then - pfUI.uf.stats.eventUpdates = 0 - pfUI.uf.stats.heartbeatUpdates = 0 - pfUI.uf.stats.earlyReturns = 0 - pfUI.uf.stats.nampowerUsed = 0 - pfUI.uf.stats.fallbackUsed = 0 - pfUI.uf.stats.throttledSkips = 0 - pfUI.uf.stats.startTime = GetTime() - DEFAULT_CHAT_FRAME:AddMessage("|cff00ff00pfUI Stats:|r Reset!") - - elseif msg == "toggle" then - pfUI.uf.stats.enabled = not pfUI.uf.stats.enabled - local status = pfUI.uf.stats.enabled and "|cff00ff00ON|r" or "|cffff0000OFF|r" - DEFAULT_CHAT_FRAME:AddMessage("|cff00ff00pfUI Stats:|r Tracking: " .. status) - - elseif msg == "show" then - if pfUI.uf.statsFrame then - pfUI.uf.statsFrame:Show() - DEFAULT_CHAT_FRAME:AddMessage("|cff00ff00pfUI Stats:|r Frame shown") - end - - elseif msg == "hide" then - if pfUI.uf.statsFrame then - pfUI.uf.statsFrame:Hide() - DEFAULT_CHAT_FRAME:AddMessage("|cff00ff00pfUI Stats:|r Frame hidden") - end - - else - -- Toggle frame (default action) - if pfUI.uf.statsFrame then - if pfUI.uf.statsFrame:IsShown() then - pfUI.uf.statsFrame:Hide() - DEFAULT_CHAT_FRAME:AddMessage("|cff00ff00pfUI Stats:|r Frame hidden") - else - pfUI.uf.statsFrame:Show() - DEFAULT_CHAT_FRAME:AddMessage("|cff00ff00pfUI Stats:|r Frame shown") - end - end - end -end, true) \ No newline at end of file diff --git a/compat/vanilla.lua b/compat/vanilla.lua index 0e2dc39f..26e698a0 100644 --- a/compat/vanilla.lua +++ b/compat/vanilla.lua @@ -29,15 +29,6 @@ UNITFRAME_SECURE_TEMPLATE = nil --[[ Vanilla API Extensions ]]-- -do -- GetItemInfo - local name, link, rarity, minlevel, itype, isubtype, stack - function GetItemInfo(item) - if not item then return end - name, link, rarity, minlevel, itype, isubtype, stack = _G.GetItemInfo(item) - return name, link, rarity, nil, minlevel, itype, isubtype, stack - end -end - do -- RunMacroText local obj = { ["GetText"] = function(self) return self.text end } obj = setmetatable(obj, {__index = function(tab,key) diff --git a/libs/libdebuff.lua b/libs/libdebuff.lua index cd0da210..2fb3e79f 100644 --- a/libs/libdebuff.lua +++ b/libs/libdebuff.lua @@ -1125,7 +1125,7 @@ if hasNampower then -- Rank aus spellId ermitteln local rankNum = 0 - local rankString = GetSpellRecField(spellId, "rank") + local rankString = C_Spell.GetSpellSubtext(spellId) if rankString and rankString ~= "" then rankNum = tonumber((string.gsub(rankString, "Rank ", ""))) or 0 end diff --git a/libs/libpredict.lua b/libs/libpredict.lua index 7f42c96f..84b65b7f 100644 --- a/libs/libpredict.lua +++ b/libs/libpredict.lua @@ -291,7 +291,7 @@ pfUI.libdebuff_spell_start_other_hooks["libpredict"] = function(spellId, casterG local targetName = resolveNameFromGuid(targetGuid) if not targetName then return end - local rankStr = GetSpellRecField and GetSpellRecField(spellId, "rank") or "" + local rankStr = C_Spell.GetSpellSubtext(spellId) or "" local spellKey = spellName .. (rankStr or "") local amount = foreignCache[casterName] and foreignCache[casterName][spellKey] @@ -355,11 +355,9 @@ pfUI.libdebuff_spell_go_hooks["libpredict"] = function(spellId, a1, a2, a3, a4, elseif hotType == "Renew" then duration = renewDuration or 15 end local rank = 0 - if GetSpellRecField then - local rankStr = GetSpellRecField(spellId, "rank") - if rankStr and rankStr ~= "" then - rank = tonumber((string.gsub(rankStr, "Rank ", ""))) or 0 - end + local rankSub = C_Spell.GetSpellSubtext(spellId) + if rankSub and rankSub ~= "" then + rank = tonumber((string.gsub(rankSub, "Rank ", ""))) or 0 end local playerName = UnitName("player") libpredict:Hot(playerName, targetName, hotType, duration, nil, "SPELL_GO_SELF", rank) diff --git a/modules/bags.lua b/modules/bags.lua index d8b1198b..99116b88 100644 --- a/modules/bags.lua +++ b/modules/bags.lua @@ -448,7 +448,7 @@ pfUI:RegisterModule("bags", function () end end - local _, _, q, _, _, _, itype = GetItemInfo(itemID) + local _, _, q, _, _, _, itype = C_Item.GetItemInfo(itemID) -- running advanced item color scan if C.appearance.bags.borderonlygear == "0" and texture and quality and quality < 1 then diff --git a/modules/castbar.lua b/modules/castbar.lua index ffbcaaf9..1c6acfc9 100644 --- a/modules/castbar.lua +++ b/modules/castbar.lua @@ -93,8 +93,8 @@ pfUI:RegisterModule("castbar", function () cb.bar:SetStatusBarColor(strsplit(",", C.appearance.castbar[isChannel and "channelcolor" or "castbarcolor"])) local rank = "" - if spellID and GetSpellRecField then - rank = GetSpellRecField(spellID, "rank") or "" + if spellID then + rank = C_Spell.GetSpellSubtext(spellID) or "" end local spellname = (cb.showname and name) and (name .. " ") or "" local rankstr = (cb.showrank and rank ~= "") and string.format("|cffaaffcc[%s]|r", rank) or "" diff --git a/modules/feigndeath.lua b/modules/feigndeath.lua index 221ca609..053680f3 100644 --- a/modules/feigndeath.lua +++ b/modules/feigndeath.lua @@ -1,6 +1,6 @@ pfUI:RegisterModule("feigndeath", function () - local oldUnitHealth = UnitHealth - function UnitHealth(unit) + local oldUnitHealth = _G.UnitHealth + _G.UnitHealth = function(unit) if UnitIsFeignDeath(unit) then local hp = GetUnitField(unit, "health") if hp and hp > 0 then return hp end diff --git a/modules/focus.lua b/modules/focus.lua index ee6e395a..207e7f8b 100644 --- a/modules/focus.lua +++ b/modules/focus.lua @@ -2,20 +2,22 @@ pfUI:RegisterModule("focus", function () -- do not go further on disabled UFs if C.unitframes.disable == "1" then return end - pfUI.uf.focus = pfUI.uf:CreateUnitFrame("Focus", nil, C.unitframes.focus, .2) + pfUI.uf.focus = pfUI.uf:CreateUnitFrame("Focus", nil, C.unitframes.focus) pfUI.uf.focus:UpdateFrameSize() pfUI.uf.focus:SetPoint("BOTTOMLEFT", UIParent, "BOTTOM", 220, 220) UpdateMovable(pfUI.uf.focus) pfUI.uf.focus:Hide() - pfUI.uf.focustarget = pfUI.uf:CreateUnitFrame("FocusTarget", nil, C.unitframes.focustarget, .2) + pfUI.uf.focustarget = pfUI.uf:CreateUnitFrame("FocusTarget", nil, C.unitframes.focustarget) pfUI.uf.focustarget:UpdateFrameSize() pfUI.uf.focustarget:SetPoint("BOTTOMLEFT", pfUI.uf.focus, "TOP", 0, 10) UpdateMovable(pfUI.uf.focustarget) pfUI.uf.focustarget:Hide() -- PLAYER_FOCUS_CHANGED drives immediate refresh on focus assign / clear. - -- The frame's 0.2s tick keeps health/power/aura data fresh between events. + -- Between events, ClassicAPI fires UNIT_* (health/mana/aura/...) with + -- arg1 == "focus" and arg1 == "focustarget", so both frames update + -- event-driven like target and need no polling tick. local refresher = CreateFrame("Frame") refresher:RegisterEvent("PLAYER_FOCUS_CHANGED") refresher:SetScript("OnEvent", function() diff --git a/modules/map.lua b/modules/map.lua index 2c906e7e..f8738b27 100644 --- a/modules/map.lua +++ b/modules/map.lua @@ -25,11 +25,7 @@ pfUI:RegisterModule("map", function () pfUI.map = { UpdateConfig = UpdateTooltipScale } function _G.ToggleWorldMap() - if WorldMapFrame:IsShown() then - WorldMapFrame:Hide() - else - WorldMapFrame:Show() - end + WorldMapFrame:SetShown(not WorldMapFrame:IsShown()) end C.position["WorldMapFrame"] = C.position["WorldMapFrame"] or { alpha = 1.0, scale = 0.7 } diff --git a/modules/minimap.lua b/modules/minimap.lua index ead0c510..29748fd9 100644 --- a/modules/minimap.lua +++ b/modules/minimap.lua @@ -33,11 +33,9 @@ pfUI:RegisterModule("minimap", function () pfUI.minimap.UpdateConfig = function(self) size = tonumber(C.appearance.minimap.size) or 140 - pfUI.minimap:SetWidth(size) - pfUI.minimap:SetHeight(size) + pfUI.minimap:SetSize(size, size) - Minimap:SetWidth(size) - Minimap:SetHeight(size) + Minimap:SetSize(size, size) -- vanilla+tbc: do the best to detect the minimap arrow local arrowscale = tonumber(C.appearance.minimap.arrowscale) @@ -158,8 +156,7 @@ pfUI:RegisterModule("minimap", function () pfUI.minimapCoordinates:SetPoint("BOTTOMLEFT", 3, 3) end - pfUI.minimapCoordinates:SetHeight(C.global.font_size) - pfUI.minimapCoordinates:SetWidth(Minimap:GetWidth()) + pfUI.minimapCoordinates:SetSize(Minimap:GetWidth(), C.global.font_size) pfUI.minimapCoordinates.text = pfUI.minimapCoordinates:CreateFontString("MinimapCoordinatesText", "LOW", "GameFontNormal") pfUI.minimapCoordinates.text:SetFont(pfUI.font_default, C.global.font_size, "OUTLINE") pfUI.minimapCoordinates.text:SetTextColor(1,1,1,1) @@ -171,19 +168,14 @@ pfUI:RegisterModule("minimap", function () pfUI.minimapCoordinates.text:SetJustifyH("LEFT") end - if C.appearance.minimap.coordstext ~= "on" then - pfUI.minimapCoordinates:Hide() - else - pfUI.minimapCoordinates:Show() - end + pfUI.minimapCoordinates:SetShown(C.appearance.minimap.coordstext == "on") -- Create zone text frame in top center of minimap pfUI.minimapZone = CreateFrame("Frame", "pfMinimapZone", pfUI.minimap) pfUI.minimapZone:RegisterEvent("MINIMAP_ZONE_CHANGED") pfUI.minimapZone:RegisterEvent("PLAYER_ENTERING_WORLD") pfUI.minimapZone:SetPoint("TOP", 0, -3) - pfUI.minimapZone:SetHeight(C.global.font_size + 2) - pfUI.minimapZone:SetWidth(Minimap:GetWidth()) + pfUI.minimapZone:SetSize(Minimap:GetWidth(), C.global.font_size + 2) pfUI.minimapZone.text = pfUI.minimapZone:CreateFontString("minimapZoneText", "LOW", "GameFontNormal") pfUI.minimapZone.text:SetFont(pfUI.font_default, C.global.font_size + 2, "OUTLINE") pfUI.minimapZone.text:SetAllPoints(pfUI.minimapZone) @@ -205,17 +197,13 @@ pfUI:RegisterModule("minimap", function () elseif pvp == "contested" then pfUI.minimapZone.text:SetTextColor(1.0, 0.7, 0) else - pfUI.minimapZone.text:SetTextColor(1, 1, 1, 1) + pfUI.minimapZone.text:SetTextColor(WHITE_FONT_COLOR:GetRGBA()) end pfUI.minimapZone.text:SetText(GetMinimapZoneText()) end end) - if C.appearance.minimap.zonetext ~= "on" then - pfUI.minimapZone:Hide() - else - pfUI.minimapZone:Show() - end + pfUI.minimapZone:SetShown(C.appearance.minimap.zonetext == "on") -- Minimap hover event -- Update and toggle showing of coordinates and zone text on mouse enter/leave @@ -241,8 +229,7 @@ pfUI:RegisterModule("minimap", function () pfUI.minimap.pvpicon:RegisterEvent("UPDATE_FACTION") pfUI.minimap.pvpicon:RegisterEvent("UNIT_FACTION") pfUI.minimap.pvpicon:SetFrameStrata("HIGH") - pfUI.minimap.pvpicon:SetWidth(16) - pfUI.minimap.pvpicon:SetHeight(16) + pfUI.minimap.pvpicon:SetSize(16, 16) pfUI.minimap.pvpicon:SetAlpha(.5) pfUI.minimap.pvpicon:SetParent(pfUI.minimap) pfUI.minimap.pvpicon:SetPoint("BOTTOMRIGHT", pfUI.minimap, "BOTTOMRIGHT", -5, 5) @@ -251,11 +238,7 @@ pfUI:RegisterModule("minimap", function () pfUI.minimap.pvpicon.texture:SetAllPoints(pfUI.minimap.pvpicon) pfUI.minimap.pvpicon:SetScript("OnEvent", function() - if C.unitframes.player.showPVPMinimap == "1" and UnitIsPVP("player") then - pfUI.minimap.pvpicon:Show() - else - pfUI.minimap.pvpicon:Hide() - end + pfUI.minimap.pvpicon:SetShown(C.unitframes.player.showPVPMinimap == "1" and UnitIsPVP("player")) end) end) diff --git a/modules/nameplates.lua b/modules/nameplates.lua index 6e158ea6..d1baf17d 100644 --- a/modules/nameplates.lua +++ b/modules/nameplates.lua @@ -61,13 +61,11 @@ pfUI:RegisterModule("nameplates", function () local raidGuidCache = {} -- guid -> name (rebuilt on RAID_ROSTER_UPDATE/PARTY_MEMBERS_CHANGED) - -- Resolve a plate GUID to its cast/channel info via C_Spell. Returns a + -- Resolve a unit token to its cast/channel info via C_Spell. Returns a -- compact struct (spellName / icon / startTime / endTime / duration / - -- isChannel) or nil when the unit isn't casting / the GUID can't map to a - -- live token. - local function GetCastInfo(guid) - if not guid then return nil end - local unit = UnitTokenFromGUID(guid) + -- isChannel) or nil when the unit isn't casting. Callers already hold the + -- nameplate token, so there's no GUID->token round-trip. + local function GetCastInfo(unit) if not unit then return nil end local name, _, texture, startMs, endMs, _, _, _, spellID = C_Spell.UnitCastingInfo(unit) local isChannel @@ -87,7 +85,6 @@ pfUI:RegisterModule("nameplates", function () } end - local guidTargetTokenCache = {} -- guid -> "target" interned string local debuffCache = {} -- guid -> { [spellID] = { start, duration } } -- Reusable per-plate debuff display buffer (avoid GC churn from per-call table creation) local debuffDisplayBuf = {} -- [i] = { effect, texture, stacks, dtype, duration, timeleft } @@ -165,12 +162,6 @@ pfUI:RegisterModule("nameplates", function () -- cache default border color local er, eg, eb, ea = GetStringColor(pfUI_config.appearance.border.color) - -- Vanilla Lua 5.0 bitwise check: math.mod(math.floor(value / flag), 2) ~= 0 - local function HasFlag(flags, flag) - return math.mod(math.floor(flags / flag), 2) ~= 0 - end - - local UNIT_FLAG_IN_COMBAT = 524288 -- 0x00080000 local NULL_GUID = "0x0000000000000000" local function RebuildRaidGuidCache() @@ -189,10 +180,11 @@ pfUI:RegisterModule("nameplates", function () local combatColorCache = {} -- guid -> { color, expires } - local function GetCombatStateColor(guid) + local function GetCombatStateColor(guid, token) -- PERF: Quick exit if player not in combat if not UnitAffectingCombat("player") then return false end - if UnitCanAssist("player", guid) then return false end + if not token then return false end + if UnitCanAssist("player", token) then return false end -- PERF: 0.2s throttle per guid - color changes are not time-critical local now = frameState.now @@ -201,24 +193,17 @@ pfUI:RegisterModule("nameplates", function () return cached.color end - local flags = GetUnitField and GetUnitField(guid, "flags") - if not flags then return false end - if not HasFlag(flags, UNIT_FLAG_IN_COMBAT) then return false end + if not UnitAffectingCombat(token) then return false end - local mobTargetGuid = GetUnitField and GetUnitField(guid, "target") + -- The mob's current target via the nameplate token chain (ClassicAPI): + -- "nameplateNtarget" resolves to whatever this plate's unit is targeting, + -- so no GetUnitField("target") or SuperWoW "target" token needed. + local target = token .. "target" + local mobTargetGuid = UnitGUID(target) local hasTarget = mobTargetGuid and mobTargetGuid ~= NULL_GUID - - -- PERF: cache the SuperWoW-style "target" unit token. The concat - -- intern-hits Lua's string pool every call; caching once per guid - -- saves the hash+lookup. Cleared in NAME_PLATE_UNIT_REMOVED. - local target = guidTargetTokenCache[guid] - if not target then - target = guid .. "target" - guidTargetTokenCache[guid] = target - end local color = false - local castInfo = GetCastInfo(guid) + local castInfo = GetCastInfo(token) local isCasting = castInfo and castInfo.endTime and now < castInfo.endTime local targetingPlayer = hasTarget and UnitIsUnit(target, "player") @@ -466,10 +451,8 @@ nameplates:RegisterEvent("PARTY_MEMBERS_CHANGED") nameplates:RegisterEvent("NAME_PLATE_CREATED") nameplates:RegisterEvent("NAME_PLATE_UNIT_ADDED") nameplates:RegisterEvent("NAME_PLATE_UNIT_REMOVED") -if GetUnitField then - nameplates:RegisterEvent("UNIT_FLAGS_GUID") - nameplates:RegisterEvent("UNIT_AURA_GUID") -end +nameplates:RegisterEvent("UNIT_AURA") +nameplates:RegisterEvent("UNIT_FLAGS") nameplates:SetScript("OnEvent", function() -- Stop event handling during logout to prevent crash 132 @@ -542,10 +525,12 @@ end end elseif event == "NAME_PLATE_UNIT_ADDED" then - -- arg1 = "nameplateN" unit token; resolve to GUID for cache keys + -- arg1 = "nameplateN" unit token. Cache the GUID for cache keys and the + -- token itself for token-based UnitX reads (stable per plate lifetime). local plate = C_NamePlate.GetNamePlateForUnit(arg1) if plate and plate.nameplate then plate.nameplate.cachedGuid = UnitGUID(arg1) + plate.nameplate.unit = arg1 nameplates.OnShow(plate) end visiblePlateCount = visiblePlateCount + 1 @@ -558,53 +543,54 @@ end if guid then if debuffCache[guid] then debuffCache[guid] = nil end if threatMemory[guid] then threatMemory[guid] = nil end - if guidTargetTokenCache[guid] then guidTargetTokenCache[guid] = nil end if combatColorCache[guid] then combatColorCache[guid] = nil end local plate = C_NamePlate.GetNamePlateForUnit(arg1) if plate and plate.nameplate and plate.nameplate.cachedGuid == guid then plate.nameplate.cachedGuid = nil + plate.nameplate.unit = nil end end - elseif event == "UNIT_FLAGS_GUID" then - -- Nampower: fires instantly when any unit's flags change (e.g. stun, combat enter/leave) - -- arg1 = guid — directly flag that nameplate for immediate update, bypassing throttle - local plate = C_NamePlate.GetNamePlateForGUID(arg1) - if plate and plate.nameplate then - plate.nameplate.eventcache = true + elseif event == "UNIT_FLAGS" then + -- ClassicAPI: fires with arg1 == "nameplateN" when a unit's flags change + -- (stun, combat enter/leave). Flag that plate for an immediate update, + -- bypassing the throttle. Guard on the token prefix -- UNIT_FLAGS also + -- fires for target/party/raid, which aren't ours to handle here. + if arg1 and strfind(arg1, "^nameplate") then + local plate = C_NamePlate.GetNamePlateForUnit(arg1) + if plate and plate.nameplate then + plate.nameplate.eventcache = true + end end - elseif event == "UNIT_AURA_GUID" then - -- Nampower: fires when a unit's aura set changes (add/remove/modify). - -- arg1 = guid. Flag the matching plate so OnUpdate triggers a fresh - -- C_UnitAuras read on the next tick instead of waiting on the 0.5s - -- throttle — covers expirations, dispels, refreshes, and stack changes - -- in one event. - local plate = C_NamePlate.GetNamePlateForGUID(arg1) - if plate and plate.nameplate then - plate.nameplate.auraUpdate = true + elseif event == "UNIT_AURA" then + -- ClassicAPI: fires with arg1 == "nameplateN" when a unit's aura set + -- changes (add/remove/modify). Flag the matching plate so OnUpdate does a + -- fresh C_UnitAuras read next tick instead of waiting on the 0.5s + -- throttle -- covers expirations, dispels, refreshes, and stack changes + -- in one event. Guard on the token prefix (UNIT_AURA also fires for + -- target/party/raid). + if arg1 and strfind(arg1, "^nameplate") then + local plate = C_NamePlate.GetNamePlateForUnit(arg1) + if plate and plate.nameplate then + plate.nameplate.auraUpdate = true + end end elseif event == "PLAYER_TARGET_CHANGED" then - -- Flag target plate for update via GUID registry - local targetGuid = UnitGUID("target") - if targetGuid then - local plate = C_NamePlate.GetNamePlateForGUID(targetGuid) - if plate and plate.nameplate then - plate.nameplate.targetUpdate = true - end + -- Flag the target's plate for update + local plate = C_NamePlate.GetNamePlateForUnit("target") + if plate and plate.nameplate then + plate.nameplate.targetUpdate = true end -- Also propagate to all plates for alpha/strata updates this.eventcache = true elseif event == "PLAYER_COMBO_POINTS" or event == "UNIT_COMBO_POINTS" then - -- Only flag the target plate for combo point update - local targetGuid = UnitGUID("target") - if targetGuid then - local plate = C_NamePlate.GetNamePlateForGUID(targetGuid) - if plate and plate.nameplate then - plate.nameplate.comboUpdate = true - end + -- Only flag the target's plate for combo point update + local plate = C_NamePlate.GetNamePlateForUnit("target") + if plate and plate.nameplate then + plate.nameplate.comboUpdate = true end else this.eventcache = true @@ -986,16 +972,14 @@ end -- always make sure to keep plate visible plate:Show() - if target and cfg.targetglow then - plate.glow:Show() else plate.glow:Hide() - end + plate.glow:SetShown(target and cfg.targetglow) -- target indicator if cfg.outcombatstate then local guid = plate.cachedGuid or "" -- determine color based on combat state - local color = GetCombatStateColor(guid) + local color = GetCombatStateColor(guid, plate.unit) if not color then color = combatstate.NONE end -- set border color @@ -1070,7 +1054,7 @@ end if guild and C.nameplates.showguildname == "1" then plate.guild:SetText(guild) - if guild == GetGuildInfo("player") then + if UnitIsInMyGuild(plate.unit) then plate.guild:SetTextColor(0, 0.9, 0, 1) else plate.guild:SetTextColor(0.8, 0.8, 0.8, 1) @@ -1089,15 +1073,15 @@ end if cfg.showhp then local rhp, rhpmax, estimated - local guid = plate.cachedGuid - if guid and GetUnitField then - local npHp = GetUnitField(guid, "health") - local npMaxHp = GetUnitField(guid, "maxHealth") + local unit = plate.unit + if unit then + local npHp = UnitHealth(unit) + local npMaxHp = UnitHealthMax(unit) if npHp and npHp > 0 and npMaxHp and npMaxHp > 0 and npMaxHp ~= 100 then rhp, rhpmax = npHp, npMaxHp end end - + -- Fallback to existing methods if not rhp then if hpmax > 100 or (round(hpmax/100*hp) ~= hp) then @@ -1148,7 +1132,7 @@ end if cfg.barcombatstate then local guid = plate.cachedGuid or "" - local color = GetCombatStateColor(guid) + local color = GetCombatStateColor(guid, plate.unit) if color then r, g, b, a = color.r, color.g, color.b, color.a @@ -1268,19 +1252,7 @@ end end nameplates.OnShow = function(frame) - local frame = frame or this - local nameplate = frame.nameplate - - -- cachedGuid is set by NAME_PLATE_UNIT_ADDED before this fires - local guid = nameplate.cachedGuid - if guid and pfUI.api.libunitscan and pfUI.api.libunitscan.ScanGuid then - -- notify libunitscan so it can cache unit data without mouseover - local name = nameplate.original.name:GetText() - local npcFlags = GetUnitField(guid, "npcFlags") or 0 - pfUI.api.libunitscan.ScanGuid(guid, name, npcFlags == 0) - end - - nameplates:OnDataChanged(nameplate) + nameplates:OnDataChanged((frame or this).nameplate) end nameplates.OnUpdate = function(frame, state) @@ -1300,7 +1272,7 @@ end -- smooth animation without overloading the central loop. local isCastingNonTarget = not target and nameplate.castbar and nameplate.castbar:IsShown() if not isCastingNonTarget and not target and cfg.showcastbar and nameplate.cachedGuid then - local castInfo = GetCastInfo(nameplate.cachedGuid) + local castInfo = GetCastInfo(nameplate.unit) if castInfo and castInfo.endTime > now then isCastingNonTarget = true end @@ -1372,8 +1344,7 @@ end if C.nameplates["overlap"] == "1" then if frame:GetWidth() > 1 then - frame:SetWidth(1) - frame:SetHeight(1) + frame:SetSize(1, 1) end else if not nameplate.dwidth then @@ -1381,8 +1352,9 @@ end end if floor(frame:GetWidth()) ~= nameplate.dwidth then - frame:SetWidth(nameplate:GetWidth() * UIParent:GetScale()) - frame:SetHeight(nameplate:GetHeight() * UIParent:GetScale()) + local nameW, nameH = nameplate:GetSize() + local uiScale = UIParent:GetScale() + frame:SetSize(nameW * uiScale, nameH * uiScale) end end @@ -1439,13 +1411,7 @@ end -- trigger update when name color changed (includes combat state check) local r, g, b = original.name:GetTextColor() - local inCombatWithPlayer = false - if cfg.namefightcolor then - local guid = nameplate.cachedGuid - if guid then - inCombatWithPlayer = UnitAffectingCombat(guid) and UnitAffectingCombat("player") - end - end + local inCombatWithPlayer = cfg.namefightcolor and UnitAffectingCombat(nameplate.unit) and UnitAffectingCombat("player") if r + g + b ~= nameplate.cache.namecolor or (cfg.namefightcolor and nameplate.cache.inCombat ~= inCombatWithPlayer) then nameplate.cache.namecolor = r + g + b @@ -1493,7 +1459,7 @@ end nameplate.health.targetHeight = hc end - local w, h = nameplate.health:GetWidth(), nameplate.health:GetHeight() + local w, h = nameplate.health:GetSize() local wc, hc = nameplate.health.targetWidth, nameplate.health.targetHeight if wc and hc then @@ -1513,7 +1479,7 @@ end end end elseif nameplate.health.zoomed or nameplate.health.zoomTransition then - local w, h = nameplate.health:GetWidth(), nameplate.health:GetHeight() + local w, h = nameplate.health:GetSize() local wc = cfg.width local hc = cfg.heighthealth @@ -1522,8 +1488,7 @@ end elseif h > hc + 0.5 then nameplate.health:SetHeight(h*0.95) else - nameplate.health:SetWidth(wc) - nameplate.health:SetHeight(hc) + nameplate.health:SetSize(wc, hc) nameplate.health.zoomTransition = nil nameplate.health.zoomed = nil nameplate.health.targetWidth = nil @@ -1589,7 +1554,7 @@ end -- Shared castbar update logic (used by both dedicated frame and central loop) nameplates.UpdateCastbar = function(nameplate, now) if not nameplate or not nameplate.castbar then return end - local castInfo = GetCastInfo(nameplate.cachedGuid) + local castInfo = GetCastInfo(nameplate.unit) if not castInfo or castInfo.endTime < now then nameplate.castbar.isShown = nil nameplate.castbar.lastEndTime = nil @@ -1635,10 +1600,7 @@ end if (this.tick or 0) > now then return end this.tick = now + throttle - local targetGuid = UnitExists("target") and UnitGUID("target") - if not targetGuid then return end - - local frame = C_NamePlate.GetNamePlateForGUID(targetGuid) + local frame = C_NamePlate.GetNamePlateForUnit("target") if not frame or not frame.nameplate then return end nameplates.UpdateCastbar(frame.nameplate, now) diff --git a/modules/nampower.lua b/modules/nampower.lua index 66052cc3..87b1bafa 100644 --- a/modules/nampower.lua +++ b/modules/nampower.lua @@ -52,8 +52,7 @@ pfUI:RegisterModule("nampower", function () return end - local eventCode = arg1 - local spellId = arg2 + local eventCode, spellId = arg1, arg2 if eventCode == NORMAL_QUEUED or eventCode == NON_GCD_QUEUED or eventCode == ON_SWING_QUEUED then local texture = C_Spell.GetSpellTexture(spellId) @@ -78,16 +77,16 @@ pfUI:RegisterModule("nampower", function () -- Reactive spells by class local reactiveSpells = { WARRIOR = { - { name = "Overpower", texture = "Interface\\Icons\\Ability_MeleeDamage" }, - { name = "Revenge", texture = "Interface\\Icons\\Ability_Warrior_Revenge" }, - { name = "Execute", texture = "Interface\\Icons\\INV_Sword_48" }, + 7384, -- Overpower + 6572, -- Revenge + 5283, -- Execute }, ROGUE = { - { name = "Riposte", texture = "Interface\\Icons\\Ability_Warrior_Challange" }, + 76, -- Riposte }, HUNTER = { - { name = "Mongoose Bite", texture = "Interface\\Icons\\Ability_Hunter_SwiftStrike" }, - { name = "Counterattack", texture = "Interface\\Icons\\Ability_Warrior_Challange" }, + 1495, -- Mongoose Bite + 19306, -- Counterattack }, } @@ -96,8 +95,7 @@ pfUI:RegisterModule("nampower", function () pfUI.reactive = CreateFrame("Frame", "pfReactiveIndicator", UIParent) pfUI.reactive:SetFrameStrata("HIGH") local spellCount = table.getn(spells) - pfUI.reactive:SetWidth(size * spellCount + 4 * (spellCount - 1)) - pfUI.reactive:SetHeight(size) + pfUI.reactive:SetSize(size * spellCount + 4 * (spellCount - 1), size) pfUI.reactive:SetPoint("CENTER", UIParent, "CENTER", 0, -200) pfUI.reactive:Hide() @@ -109,7 +107,7 @@ pfUI:RegisterModule("nampower", function () icon.texture = icon:CreateTexture(nil, "ARTWORK") icon.texture:SetAllPoints(icon) - icon.texture:SetTexture(spell.texture) + icon.texture:SetTexture(C_Spell.GetSpellTexture(spell)) icon.texture:SetTexCoord(.08, .92, .08, .92) icon.glow = icon:CreateTexture(nil, "OVERLAY") @@ -120,7 +118,7 @@ pfUI:RegisterModule("nampower", function () CreateBackdrop(icon) icon:Hide() - icon.spellName = spell.name + icon.spellName = C_Spell.GetSpellName(spell) pfUI.reactive.icons[i] = icon end @@ -148,7 +146,7 @@ pfUI:RegisterModule("nampower", function () local arg = (msg and msg ~= "") and msg or "greens" local target = tonumber(arg) or arg DisenchantAll(target) - DEFAULT_CHAT_FRAME:AddMessage("|cff33ffccpfUI|r: DisenchantAll(" .. tostring(target) .. ")") + print("|cff33ffccpfUI|r: DisenchantAll(" .. tostring(target) .. ")") end, true) end diff --git a/modules/player.lua b/modules/player.lua index d52f5c9c..98db1614 100644 --- a/modules/player.lua +++ b/modules/player.lua @@ -47,7 +47,7 @@ pfUI:RegisterModule("player", function () return string.format("%02X%02X%02X", r * 255, g * 255, b * 255) end - -- SP school colors indexed by GetSpellPower("net") return order + -- SP school colors indexed by GetSpellBonusDamage's 1-based school order -- (1=phys, 2=holy, 3=fire, 4=nature, 5=frost, 6=shadow, 7=arcane) local spColors = { "FFFFFF", "FFFF80", "FF8000", "4DFF4D", "80FFFF", "9482C9", "FFFFFF" } @@ -60,16 +60,14 @@ pfUI:RegisterModule("player", function () -- Compute and cache the haste/SP text; called from OnUpdate, throttled to 0.25s local function UpdateInfoText() - if not GetUnitField then return end -- do nothing for older nampower - local cfg = playerFrame.config if not cfg then return end - -- display_haste: "0"=hidden, "1"=show modCastSpeed (gear haste). Talent- - -- side cast-time reductions show up in the actual cast bar via - -- C_Spell.UnitCastingInfo; double-folding them into this overlay was - -- mixing two different concepts into one number. + -- display_haste: "0"=hidden, "1"=show cast-speed haste (UnitSpellHaste, + -- from UNIT_MOD_CAST_SPEED). Talent/spell-specific cast-time reductions + -- show up in the actual cast bar via C_Spell.UnitCastingInfo; folding them + -- in here too was mixing two different concepts into one number. local showHaste = cfg.display_haste == "1" local showSP = cfg.display_spellpower == "1" @@ -79,21 +77,20 @@ pfUI:RegisterModule("player", function () return end - local haste = GetUnitField("player", "modCastSpeed") + local haste = UnitSpellHaste("player") local text = "" if showHaste and isSpellCaster and haste then local hasteHex = cfgColorToHex(cfg.display_haste_color) or "FFFFFF" - text = string.format("|cff%s%.1f%%|r", hasteHex, (1 / haste - 1) * 100) + text = string.format("|cff%s%.1f%%|r", hasteHex, haste) end if showSP and isSpellCaster then - local schools = { GetSpellPower("net") } local defSchool = spDefaultSchool[myclass] or 2 - local maxSP = schools[defSchool] or 0 + local maxSP = GetSpellBonusDamage(defSchool) or 0 local maxColor = spColors[defSchool] - for i = 2, 7 do -- skip physical (1) - local v = schools[i] or 0 + for i = 2, 7 do -- skip physical (1); default school seeds the tiebreak + local v = GetSpellBonusDamage(i) or 0 if v > maxSP then maxSP = v maxColor = spColors[i] diff --git a/modules/raid.lua b/modules/raid.lua index e71d8cb0..1be1c174 100644 --- a/modules/raid.lua +++ b/modules/raid.lua @@ -131,6 +131,13 @@ pfUI:RegisterModule("raid", function () pet:UpdateVisibility() end + if pfUI.uf.showall then + for id = 1, maxraid do + if self.pets[id] then place(self.pets[id], id, id) end + end + return + end + if C.unitframes.raidpet.collapse == "1" then -- Pack the pets that exist into the leading cells, no gaps. local k = 0 diff --git a/modules/roll.lua b/modules/roll.lua index e0253e08..7cab0d11 100644 --- a/modules/roll.lua +++ b/modules/roll.lua @@ -42,7 +42,7 @@ pfUI:RegisterModule("roll", function () end local _, _, itemLink = string.find(hyperlink, "(item:%d+:%d+:%d+:%d+)") - local itemName = GetItemInfo(itemLink) + local itemName = C_Item.GetItemInfo(itemLink) -- delete obsolete tables if pfUI.roll.cache[itemName] and pfUI.roll.cache[itemName]["TIMESTAMP"] < GetTime() - 60 then diff --git a/modules/unitxp.lua b/modules/unitxp.lua index 33a9ddf6..8f69202d 100644 --- a/modules/unitxp.lua +++ b/modules/unitxp.lua @@ -331,26 +331,6 @@ pfUI:RegisterModule("unitxp", function () return success and found end - pfUI.api.UnitInLineOfSight = function(unit1, unit2) - if not unit2 then - unit2 = unit1 - unit1 = "player" - end - local success, inSight = pcall(UnitXP, "inSight", unit1, unit2) - if success then return inSight end - return nil - end - - pfUI.api.UnitIsBehind = function(unit1, unit2) - if not unit2 then - unit2 = unit1 - unit1 = "player" - end - local success, behind = pcall(UnitXP, "behind", unit1, unit2) - if success then return behind end - return nil - end - -- Debug command to test UnitXP indicators pfUI.api.RegisterSlashCommand("PFUNITXP", { "/pfunitxp" }, function() local chat = DEFAULT_CHAT_FRAME diff --git a/modules/whisperproxy.lua b/modules/whisperproxy.lua index 308d34cc..79fce12f 100644 --- a/modules/whisperproxy.lua +++ b/modules/whisperproxy.lua @@ -3,8 +3,7 @@ pfUI:RegisterModule("whisperproxy", function () local proxy = CreateFrame("Button", "pfWhisperProxy", pfUI.chat.left.panelTop) proxy:SetPoint("TOPRIGHT", pfUI.chat.left, "TOPRIGHT", -22, -5) - proxy:SetWidth(12) - proxy:SetHeight(12) + proxy:SetSize(12, 12) proxy.tex = proxy:CreateTexture(nil, "OVERLAY") proxy.tex:SetAllPoints() proxy.tex:SetTexture(pfUI.media["img:proxy"]) diff --git a/modules/xpbar.lua b/modules/xpbar.lua index bdcbbd3e..ca1cfcf3 100644 --- a/modules/xpbar.lua +++ b/modules/xpbar.lua @@ -183,11 +183,7 @@ end local self = self or this if self.text_mouse == "1" then - if MouseIsOver(self) then - self.bar.text:Show() - else - self.bar.text:Hide() - end + self.bar.text:SetShown(MouseIsOver(self)) end if self.always then return end @@ -352,11 +348,7 @@ end b.bar.text:SetJustifyH("CENTER") b.bar.text:SetFont(pfUI.font_default, C.global.font_size, "OUTLINE") - if b.text == "1" then - b.bar.text:Show() - else - b.bar.text:Hide() - end + b.bar.text:SetShown(b.text == "1") b.restedbar = b.restedbar or CreateFrame("StatusBar", nil, b) b.restedbar:SetStatusBarTexture(pfUI.media[C.panel.xp.texture]) diff --git a/pfUI.lua b/pfUI.lua index 2e3ea610..4e9d9863 100644 --- a/pfUI.lua +++ b/pfUI.lua @@ -23,7 +23,7 @@ do -- ClassicAPI dependency check. -- pfUI relies pervasively on the modern C_* / SuperWoW / nameplate / focus -- API surface that ClassicAPI polyfills, so presence is required. - local PFUI_CLASSIC_API_MIN = 10705 -- (X*10000 + Y*100 + Z) + local PFUI_CLASSIC_API_MIN = 10800 -- (X*10000 + Y*100 + Z) local PFUI_CLASSIC_API_LATEST = PFUI_CLASSIC_API_MIN local PFUI_CLASSIC_API_WEBSITE = "https://github.com/brues-code/ClassicAPI" local PFUI_CLASSIC_API_LATEST_URL = PFUI_CLASSIC_API_WEBSITE .. "/releases/latest" diff --git a/skins/blizzard/auction.lua b/skins/blizzard/auction.lua index d1bb2711..12047cfe 100644 --- a/skins/blizzard/auction.lua +++ b/skins/blizzard/auction.lua @@ -2,15 +2,10 @@ pfUI:RegisterSkin("Auctionhouse", function () local rawborder, border = GetBorderSize() local bpad = rawborder > 1 and border - GetPerfectPixel() or GetPerfectPixel() HookAddonOrVariable("Blizzard_AuctionUI", function() - -- Compatibility - if BrowseResetButton then -- tbc - SkinButton(BrowseResetButton) - else -- vanilla - SkinArrowButton(BidPrevPageButton, "left", 18) - SkinArrowButton(BidNextPageButton, "right", 18) - SkinArrowButton(AuctionsPrevPageButton, "left", 18) - SkinArrowButton(AuctionsNextPageButton, "right", 18) - end + SkinArrowButton(BidPrevPageButton, "left", 18) + SkinArrowButton(BidNextPageButton, "right", 18) + SkinArrowButton(AuctionsPrevPageButton, "left", 18) + SkinArrowButton(AuctionsNextPageButton, "right", 18) hooksecurefunc("AuctionFrame_OnShow", function() AuctionFrame:ClearAllPoints() diff --git a/skins/blizzard/battlefield.lua b/skins/blizzard/battlefield.lua index 6d1d0d0a..3a7818d2 100644 --- a/skins/blizzard/battlefield.lua +++ b/skins/blizzard/battlefield.lua @@ -52,8 +52,7 @@ pfUI:RegisterSkin("Battlefield", function () end) BattlefieldFrame.textbox = CreateFrame("Frame", "BattlefieldFrameTextBox", BattlefieldFrame) - BattlefieldFrame.textbox:SetWidth(320) - BattlefieldFrame.textbox:SetHeight(110) + BattlefieldFrame.textbox:SetSize(320, 110) CreateBackdrop(BattlefieldFrame.textbox) BattlefieldFrame.textbox:SetPoint("BOTTOM", BattlefieldFrame.backdrop, "BOTTOM", 0, 36) BattlefieldFrameZoneDescription:ClearAllPoints() diff --git a/skins/blizzard/battlefield_minimap.lua b/skins/blizzard/battlefield_minimap.lua index 5b541092..e56a30d0 100644 --- a/skins/blizzard/battlefield_minimap.lua +++ b/skins/blizzard/battlefield_minimap.lua @@ -6,8 +6,7 @@ pfUI:RegisterSkin("Battlefield Minimap", function () CreateBackdrop(BattlefieldMinimap, nil, nil, 0) CreateBackdropShadow(BattlefieldMinimap) - BattlefieldMinimap:SetWidth(220) - BattlefieldMinimap:SetHeight(146) + BattlefieldMinimap:SetSize(220, 146) SkinCloseButton(BattlefieldMinimapCloseButton, BattlefieldMinimap, 0, 0) diff --git a/skins/blizzard/character.lua b/skins/blizzard/character.lua index 27f1664d..271e532d 100644 --- a/skins/blizzard/character.lua +++ b/skins/blizzard/character.lua @@ -131,7 +131,7 @@ pfUI:RegisterSkin("Character", function () if ShaguScore and itemID then local itemLevel = C_Item.GetCurrentItemLevel({ equipmentSlotIndex = slotId }) - local _, _, quality, _, _, _, _, _, itemSlot, _ = GetItemInfo(itemID) + local _, _, quality, _, _, _, _, _, itemSlot, _ = C_Item.GetItemInfo(itemID) local score = ShaguScore:Calculate(itemSlot, quality, itemLevel) if score and score > 0 and quality and quality > 0 then local r,g,b = GetItemQualityColor(quality) @@ -177,8 +177,7 @@ pfUI:RegisterSkin("Character", function () for i,c in pairs(magicResTextureCords) do local magicResFrame = _G["MagicResFrame"..i] - magicResFrame:SetWidth(26) - magicResFrame:SetHeight(26) + magicResFrame:SetSize(26, 26) CreateBackdrop(magicResFrame) SetAllPointsOffset(magicResFrame.backdrop, magicResFrame, 2) local icon = GetNoNameObject(magicResFrame, "Texture", "BACKGROUND", "ResistanceIcons") @@ -236,8 +235,7 @@ pfUI:RegisterSkin("Character", function () for i,c in pairs(magicResTextureCords) do local magicResFrame = _G["PetMagicResFrame"..i] - magicResFrame:SetWidth(26) - magicResFrame:SetHeight(26) + magicResFrame:SetSize(26, 26) CreateBackdrop(magicResFrame) SetAllPointsOffset(magicResFrame.backdrop, magicResFrame, 2) local icon = GetNoNameObject(magicResFrame, "Texture", "BACKGROUND", "ResistanceIcons") @@ -257,8 +255,7 @@ pfUI:RegisterSkin("Character", function () local war = _G["ReputationBar"..i.."AtWarCheck"] StripTextures(war) - war:SetWidth(13) - war:SetHeight(13) + war:SetSize(13, 13) war:ClearAllPoints() war:SetPoint("LEFT", bar.backdrop, "RIGHT", 6, 0) war.icon = war:CreateTexture(nil, "OVERLAY") @@ -356,8 +353,7 @@ pfUI:RegisterSkin("Character", function () SkillDetailStatusBar:SetParent(SkillDetailScrollFrame) StripTextures(SkillDetailStatusBarUnlearnButton) - SkillDetailStatusBarUnlearnButton:SetWidth(20) - SkillDetailStatusBarUnlearnButton:SetHeight(20) + SkillDetailStatusBarUnlearnButton:SetSize(20, 20) SkillDetailStatusBarUnlearnButton:SetHitRectInsets(0,0,0,0) SkillDetailStatusBarUnlearnButton:ClearAllPoints() SkillDetailStatusBarUnlearnButton:SetPoint("LEFT", SkillDetailStatusBar, "RIGHT", 6, 0) diff --git a/skins/blizzard/lft.lua b/skins/blizzard/lft.lua index d80c2e17..d87662c0 100644 --- a/skins/blizzard/lft.lua +++ b/skins/blizzard/lft.lua @@ -167,12 +167,10 @@ pfUI:RegisterSkin("Turtle LFT", function () local sep = LFTGroupReadyFrame:CreateTexture(nil, "ARTWORK") sep:SetTexture("Interface\\FrameXML\\LFT\\images\\ui-lfg-separator") sep:SetPoint("TOPLEFT", LFTGroupReadyFrame, "TOPLEFT", 10, -125) - sep:SetWidth(288) - sep:SetHeight(16) + sep:SetSize(288, 16) -- Restore role icon (updated dynamically by LFT_GroupReadyShow) - LFTGroupReadyFrameRoleTexture:SetWidth(56) - LFTGroupReadyFrameRoleTexture:SetHeight(56) + LFTGroupReadyFrameRoleTexture:SetSize(56, 56) LFTGroupReadyFrameRoleTexture:ClearAllPoints() LFTGroupReadyFrameRoleTexture:SetPoint("LEFT", LFTGroupReadyFrame, "LEFT", 20, -20) LFTGroupReadyFrameRoleTexture:Show() diff --git a/skins/blizzard/questlog.lua b/skins/blizzard/questlog.lua index 35152106..adef8344 100644 --- a/skins/blizzard/questlog.lua +++ b/skins/blizzard/questlog.lua @@ -6,31 +6,15 @@ pfUI:RegisterSkin("Quest Log", function () _G.MAX_WATCHABLE_QUESTS = 20 -- TODO do -- quest log frame - -- Compatibility - local QUEST_COUNT - if QuestLogCount then -- tbc - QUEST_COUNT = QuestLogCount - - StripTextures(QUEST_COUNT) - QUEST_COUNT:ClearAllPoints() - hooksecurefunc("QuestLogUpdateQuestCount", function(numQuests) - QUEST_COUNT:ClearAllPoints() - QUEST_COUNT:SetPoint("BOTTOMRIGHT", QuestLogFrame, "TOPRIGHT", 0, -50) - end) - else -- vanilla - QUEST_COUNT = QuestLogQuestCount - - QUEST_COUNT:ClearAllPoints() - QUEST_COUNT:SetPoint("TOPRIGHT", -10, -30) - end + QuestLogQuestCount:ClearAllPoints() + QuestLogQuestCount:SetPoint("TOPRIGHT", -10, -30) hooksecurefunc("QuestLog_OnShow", function() QuestLogFrame:ClearAllPoints() QuestLogFrame:SetPoint("TOPLEFT", 10, -104) end) - QuestLogFrame:SetWidth(676) - QuestLogFrame:SetHeight(440) + QuestLogFrame:SetSize(676, 440) QuestLogFrame:DisableDrawLayer("BACKGROUND") StripTextures(QuestLogFrame, true) @@ -64,10 +48,9 @@ pfUI:RegisterSkin("Quest Log", function () QuestLogFrameLevelsCheckButtonText:SetText(T["Quest Levels"]) CreateBackdrop(QuestLogTrack) - QuestLogTrack:SetHeight(8) - QuestLogTrack:SetWidth(8) + QuestLogTrack:SetSize(8, 8) QuestLogTrack:ClearAllPoints() - QuestLogTrack:SetPoint("RIGHT", QUEST_COUNT, "LEFT", -5, 0) + QuestLogTrack:SetPoint("RIGHT", QuestLogQuestCount, "LEFT", -5, 0) StripTextures(QuestLogTrack) QuestLogTrackTracking:SetTexture(.8,.8,.8,1) @@ -228,8 +211,7 @@ pfUI:RegisterSkin("Quest Log", function () SetAllPointsOffset(item.backdrop, item, 4) SetHighlight(item) - icon:SetWidth(ysize) - icon:SetHeight(ysize) + icon:SetSize(ysize, ysize) icon:ClearAllPoints() icon:SetPoint("LEFT", 6, 0) icon:SetTexCoord(.08, .92, .08, .92) diff --git a/skins/blizzard/readycheck.lua b/skins/blizzard/readycheck.lua index 30212ce3..f7cadb33 100644 --- a/skins/blizzard/readycheck.lua +++ b/skins/blizzard/readycheck.lua @@ -1,13 +1,5 @@ pfUI:RegisterSkin("Readycheck", function () HookAddonOrVariable("Blizzard_RaidUI", function() - -- Compatibility - local update_func - if ReadyCheckFrame_OnUpdate then -- tbc - update_func = "ReadyCheckFrame_OnUpdate" - else -- vanilla - update_func = "ReadyCheck_OnUpdate" - end - StripTextures(ReadyCheckFrame, true) CreateBackdrop(ReadyCheckFrame, nil, nil, .75) CreateBackdropShadow(ReadyCheckFrame) @@ -25,8 +17,7 @@ pfUI:RegisterSkin("Readycheck", function () local frame = CreateFrame("Button", nil, ReadyCheckFrame) frame:SetPoint("TOP", ReadyCheckFrameText, "BOTTOM", 0, -6) - frame:SetWidth(220) - frame:SetHeight(10) + frame:SetSize(220, 10) frame.bar = CreateFrame("StatusBar", "ReadyCheckFrameStatusBar", ReadyCheckFrame) frame.bar:SetStatusBarTexture(pfUI.media["img:bar"]) @@ -35,7 +26,7 @@ pfUI:RegisterSkin("Readycheck", function () frame.bar.text = frame.bar:CreateFontString("Status", "DIALOG", "GameFontNormal") frame.bar.text:SetFontObject(GameFontWhite) frame.bar.text:SetFont(pfUI.font_default, 12, "OUTLINE") - frame.bar.text:SetPoint("CENTER", 0, 0) + frame.bar.text:SetPoint("CENTER") local max hooksecurefunc("ShowReadyCheck", function() @@ -43,7 +34,7 @@ pfUI:RegisterSkin("Readycheck", function () frame.bar:SetMinMaxValues(0, max) end) - hooksecurefunc(update_func, function() + hooksecurefunc("ReadyCheck_OnUpdate", function() if not ReadyCheckFrame.timer then return end local perc = ReadyCheckFrame.timer/max diff --git a/skins/blizzard/talents.lua b/skins/blizzard/talents.lua index 737dff7c..1ba18243 100644 --- a/skins/blizzard/talents.lua +++ b/skins/blizzard/talents.lua @@ -4,14 +4,7 @@ pfUI:RegisterSkin("Talents", function () HookAddonOrVariable("Blizzard_TalentUI", function() -- Compatibility - local TALENT_FRAME, TALENT_FRAME_NAME - if PlayerTalentFrame then -- tbc - TALENT_FRAME = _G.PlayerTalentFrame - else -- vanilla - TALENT_FRAME = _G.TalentFrame - end - TALENT_FRAME_NAME = TALENT_FRAME:GetName() - + local TALENT_FRAME, TALENT_FRAME_NAME = _G.TalentFrame, _G.TalentFrame:GetName() StripTextures(TALENT_FRAME) CreateBackdrop(TALENT_FRAME, nil, nil, .75)