5842eb7a2b
Traduction - Identifiants en anglais dans tout le module : addon, ecrans d'accueil, outils Python, banc d'essai et patcheur C#. - Fichiers au nom francais renommes (Gabarits.lua -> Templates.lua, Textes_*.lua -> Texts_*.lua, deployer.py -> deploy.py, tools/patcheur -> tools/patcher, etc.). - Commandes /fui et options de deploy.py en anglais (--check, --server, --remove-dbc). - Cles des variables sauvegardees et de data/dbc/statistics.json traduites, sans reprise des anciennes cles. - API de la micro-barre : ForeverUI.AddMicroButton(def) avec les champs name, atlasSet, after, tooltip, onClick, ready, et ForeverUI.UpdateMicro(name, isOpen). - Commentaires reecrits en anglais, courts, sans dates ni historique ; les fonctions au nom peu parlant et leurs parametres sont expliques. Code mort - Exports, fonctions et variables jamais lus retires. - Retires a la demande des modules : ForeverUI.PvPJauge, les exports FondEntete / TuilerEntete / Polices de TradeSkill, l'art legacy-up-c60, honorfill(half)blue et inv_misc_book_09, leurs entrees d'atlas et les parties d'outils correspondantes. Verifications : liaisons des noms comparees avant et apres, banc vert, chemins de textures inchanges, generateurs reproduisant les fichiers, patcheur identique octet pour octet. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
213 lines
8.0 KiB
Lua
213 lines
8.0 KiB
Lua
-- ForeverUI: tooltips in camelot's style (SharedTooltipTemplate, TooltipDefaultLayout).
|
|
-- The <Backdrop> of the client templates is replaced by a nine-slice made of the tooltip's
|
|
-- own regions (a child frame would cover the lines), stretched rather than tiled (3.3.5 tiles
|
|
-- only whole images). SetBackdropColor/SetBackdropBorderColor tint the pieces; a new backdrop
|
|
-- hides them. Compare tooltips get camelot's CompareHeader; 3.3.5 has no EQUIPPED string, so
|
|
-- it shows CURRENTLY_EQUIPPED, moved from the tooltip's first line.
|
|
|
|
local ForeverUI = ForeverUI or {}
|
|
_G.ForeverUI = ForeverUI
|
|
|
|
local T = {}
|
|
ForeverUI.Tooltips = T
|
|
|
|
local SEP = string.char(92)
|
|
local CLIENT_EDGE = string.lower("Interface" .. SEP .. "Tooltips" .. SEP .. "UI-Tooltip-Border")
|
|
|
|
-- TooltipDefaultLayout, in nineSliceSetup's order and anchors:
|
|
-- name, atlas, point (for an edge: opposite point and its two corners)
|
|
local PIECES = {
|
|
{ "TopLeftCorner", "tooltip-nineslice-cornertopleft", "TOPLEFT" },
|
|
{ "TopRightCorner", "tooltip-nineslice-cornertopright", "TOPRIGHT" },
|
|
{ "BottomLeftCorner", "tooltip-nineslice-cornerbottomleft", "BOTTOMLEFT" },
|
|
{ "BottomRightCorner", "tooltip-nineslice-cornerbottomright", "BOTTOMRIGHT" },
|
|
{ "TopEdge", "_tooltip-nineslice-edgetop", "TOPLEFT", "TOPRIGHT", "TopLeftCorner", "TopRightCorner" },
|
|
{ "BottomEdge", "_tooltip-nineslice-edgebottom", "BOTTOMLEFT", "BOTTOMRIGHT", "BottomLeftCorner", "BottomRightCorner" },
|
|
{ "LeftEdge", "!tooltip-nineslice-edgeleft", "TOPLEFT", "BOTTOMLEFT", "TopLeftCorner", "BottomLeftCorner" },
|
|
{ "RightEdge", "!tooltip-nineslice-edgeright", "TOPRIGHT", "BOTTOMRIGHT", "TopRightCorner", "BottomRightCorner" },
|
|
}
|
|
local CENTER = { atlas = "tooltip-nineslice-center", x = -4, y = 4, x1 = 4, y1 = -4 }
|
|
|
|
-- SharedTooltip_OnLoad
|
|
local SCREEN_INSETS = { 0, 0, 25, 0 }
|
|
|
|
-- CompareHeader
|
|
local HEADER = { width = 100, height = 22, y = -1, margin = 30, atlas = "tooltip-compare-label" }
|
|
|
|
-- UIPanelCloseButtonNoScripts, at ItemRefTooltip's TOPRIGHT (2, 2)
|
|
local CLOSE_BUTTON = { side = 24, x = 2, y = 2 }
|
|
|
|
-- client tooltip frames that are not GameTooltips
|
|
local TOOLTIP_FRAMES = { "FriendsTooltip", "PartyMemberBuffTooltip", "SmallTextTooltip" }
|
|
|
|
-- tooltips embedded in a window (IsEmbedded): left alone
|
|
local EXCLUDED = { ItemSocketingDescription = true }
|
|
|
|
-- true if the frame has the backdrop set by the client templates
|
|
local function hasClientBackground(f)
|
|
local background = f.GetBackdrop and f:GetBackdrop()
|
|
local edge = background and background.edgeFile
|
|
return type(edge) == "string" and string.lower(string.gsub(edge, "/", SEP)) == CLIENT_EDGE
|
|
end
|
|
|
|
-- center: true tints the center (SetCenterColor), false the eight other pieces
|
|
-- (SetBorderColor)
|
|
local function applyTint(tooltipFrame, center, r, g, b, a)
|
|
local p = tooltipFrame.foreverNineSlice
|
|
if not p or not r then return end
|
|
for name, t in pairs(p) do
|
|
if (name == "Center") == center then
|
|
t:SetVertexColor(r, g, b, a or 1)
|
|
end
|
|
end
|
|
end
|
|
|
|
-- Replaces the 3.3.5 backdrop with camelot's nine-slice. Returns the pieces by name.
|
|
function T.Skin(tooltipFrame)
|
|
if not tooltipFrame or tooltipFrame.foreverNineSlice then return tooltipFrame and tooltipFrame.foreverNineSlice end
|
|
tooltipFrame:SetBackdrop(nil)
|
|
|
|
local p = {}
|
|
for _, m in ipairs(PIECES) do
|
|
local t = tooltipFrame:CreateTexture(nil, "BORDER")
|
|
ForeverUI.SetAtlas(t, m[2])
|
|
if m[4] then
|
|
t:SetPoint(m[3], p[m[5]], m[4], 0, 0)
|
|
t:SetPoint(m[4], p[m[6]], m[3], 0, 0)
|
|
else
|
|
t:SetPoint(m[3], tooltipFrame, m[3], 0, 0)
|
|
end
|
|
p[m[1]] = t
|
|
end
|
|
local c = tooltipFrame:CreateTexture(nil, "BACKGROUND")
|
|
ForeverUI.SetAtlas(c, CENTER.atlas)
|
|
c:SetPoint("TOPLEFT", p.TopLeftCorner, "BOTTOMRIGHT", CENTER.x, CENTER.y)
|
|
c:SetPoint("BOTTOMRIGHT", p.BottomRightCorner, "TOPLEFT", CENTER.x1, CENTER.y1)
|
|
p.Center = c
|
|
tooltipFrame.foreverNineSlice = p
|
|
|
|
local background, edge = TOOLTIP_DEFAULT_BACKGROUND_COLOR, TOOLTIP_DEFAULT_COLOR
|
|
applyTint(tooltipFrame, true, background.r, background.g, background.b, 1)
|
|
applyTint(tooltipFrame, false, edge.r, edge.g, edge.b, 1)
|
|
hooksecurefunc(tooltipFrame, "SetBackdropColor", function(self, r, g, b, a)
|
|
applyTint(self, true, r, g, b, a)
|
|
end)
|
|
hooksecurefunc(tooltipFrame, "SetBackdropBorderColor", function(self, r, g, b, a)
|
|
applyTint(self, false, r, g, b, a)
|
|
end)
|
|
hooksecurefunc(tooltipFrame, "SetBackdrop", function(self, other)
|
|
for _, t in pairs(self.foreverNineSlice) do
|
|
if other then t:Hide() else t:Show() end
|
|
end
|
|
end)
|
|
|
|
if tooltipFrame:GetObjectType() == "GameTooltip" then
|
|
tooltipFrame:SetClampRectInsets(SCREEN_INSETS[1], SCREEN_INSETS[2], SCREEN_INSETS[3], SCREEN_INSETS[4])
|
|
end
|
|
return p
|
|
end
|
|
|
|
-- Skins every tooltip made on the client templates, including those of addons loaded later.
|
|
function T.Scan()
|
|
local f = EnumerateFrames()
|
|
while f do
|
|
if not f.foreverNineSlice and f:GetObjectType() == "GameTooltip"
|
|
and not EXCLUDED[f:GetName() or ""] and hasClientBackground(f) then
|
|
T.Skin(f)
|
|
end
|
|
f = EnumerateFrames(f)
|
|
end
|
|
end
|
|
|
|
-- ------------------------------------------------------------ Comparison
|
|
|
|
-- camelot's CompareHeader of a compare tooltip, created once
|
|
local function header(tooltipFrame)
|
|
local h = tooltipFrame.foreverHeader
|
|
if h then return h end
|
|
h = CreateFrame("Frame", nil, tooltipFrame)
|
|
h:SetWidth(HEADER.width)
|
|
h:SetHeight(HEADER.height)
|
|
h:SetPoint("BOTTOMLEFT", tooltipFrame, "TOPLEFT", 0, HEADER.y)
|
|
local background = h:CreateTexture(nil, "BACKGROUND")
|
|
ForeverUI.SetAtlas(background, HEADER.atlas, true)
|
|
background:SetAllPoints(h)
|
|
local label = h:CreateFontString(nil, "ARTWORK", "GameTooltipText")
|
|
label:SetPoint("CENTER", h, "CENTER", 0, 0)
|
|
label:SetTextColor(NORMAL_FONT_COLOR.r, NORMAL_FONT_COLOR.g, NORMAL_FONT_COLOR.b)
|
|
h.Label = label
|
|
h:Hide()
|
|
tooltipFrame.foreverHeader = h
|
|
-- camelot: OnTooltipCleared hides CompareHeader
|
|
tooltipFrame:HookScript("OnTooltipCleared", function(self)
|
|
self.foreverHeader:Hide()
|
|
end)
|
|
return h
|
|
end
|
|
|
|
-- Runs after the client: moves the "Currently Equipped" first line into the header.
|
|
-- mainTooltip: the tooltip being compared (GameTooltip by default).
|
|
function T.Compare(mainTooltip)
|
|
mainTooltip = mainTooltip or GameTooltip
|
|
local list = mainTooltip and mainTooltip.shoppingTooltips
|
|
if not list or not CURRENTLY_EQUIPPED then return end
|
|
for _, tooltipFrame in ipairs(list) do
|
|
local name = tooltipFrame:GetName()
|
|
local row = name and _G[name .. "TextLeft1"]
|
|
if tooltipFrame:IsShown() and row and row:GetText() == CURRENTLY_EQUIPPED then
|
|
T.Skin(tooltipFrame)
|
|
local h = header(tooltipFrame)
|
|
h.Label:SetText(CURRENTLY_EQUIPPED)
|
|
h:SetWidth(h.Label:GetStringWidth() + HEADER.margin)
|
|
h:SetFrameLevel(math.max(tooltipFrame:GetFrameLevel() - 1, 0))
|
|
h:Show()
|
|
row:SetText("")
|
|
-- the client recomputes the tooltip's size on Show
|
|
tooltipFrame:Show()
|
|
end
|
|
end
|
|
end
|
|
|
|
-- ------------------------------------------------------------ Close button
|
|
|
|
local function skinCloseButton(b)
|
|
if not b or b.foreverCloseButton then return end
|
|
b:SetWidth(CLOSE_BUTTON.side)
|
|
b:SetHeight(CLOSE_BUTTON.side)
|
|
b:ClearAllPoints()
|
|
b:SetPoint("TOPRIGHT", b:GetParent(), "TOPRIGHT", CLOSE_BUTTON.x, CLOSE_BUTTON.y)
|
|
for _, state in ipairs({ { "GetNormalTexture", "redbutton-exit" },
|
|
{ "GetPushedTexture", "redbutton-exit-pressed" },
|
|
{ "GetHighlightTexture", "redbutton-highlight" } }) do
|
|
local t = b[state[1]] and b[state[1]](b)
|
|
if t then
|
|
ForeverUI.SetAtlas(t, state[2], true)
|
|
t:ClearAllPoints()
|
|
t:SetAllPoints(b)
|
|
if state[2] == "redbutton-highlight" then t:SetBlendMode("ADD") end
|
|
end
|
|
end
|
|
b.foreverCloseButton = true
|
|
end
|
|
|
|
-- ------------------------------------------------------------ Setup
|
|
|
|
for _, name in ipairs(TOOLTIP_FRAMES) do
|
|
local f = _G[name]
|
|
if f and hasClientBackground(f) then
|
|
T.Skin(f)
|
|
end
|
|
end
|
|
T.Scan()
|
|
skinCloseButton(ItemRefCloseButton)
|
|
hooksecurefunc("GameTooltip_ShowCompareItem", T.Compare)
|
|
|
|
-- addons loaded later (Blizzard_DebugTools...) and those creating tooltips at login
|
|
local watcher = CreateFrame("Frame")
|
|
watcher:RegisterEvent("ADDON_LOADED")
|
|
watcher:RegisterEvent("PLAYER_LOGIN")
|
|
watcher:SetScript("OnEvent", function()
|
|
T.Scan()
|
|
end)
|
|
T.watcher = watcher
|