Files
benilla-octo/crates/benilla-app/assets/ui/Fonts.xml
T
SamandClaude Fable 5 b5bc569156 the addon arc: the AddOns folder opens
- benilla loads real 1.12 addons from Interface/AddOns — TOC, XML and Lua through one loader, with per-addon saved variables, Bindings.xml and the lifecycle events addons expect
- both AddOns screens are in: the character-select list with per-addon enable state, and the ESC menu's in-game list
- the API surface is measured, not guessed — a corpus harness runs hundreds of real 1.12 addons and ranks exactly which globals, templates and verbs they demand
- the Lua dialect is the client's own, read off the binary — 5.0 semantics with the 1.12 additions, and UI source files are bytes, not UTF-8

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-08-11 18:18:31 +07:00

348 lines
18 KiB
XML

<Ui xmlns="http://www.blizzard.com/wow/ui/">
<!--
Benilla's named virtual Font objects: the COMPLETE set from the real 1.12.1 FrameXML
`Fonts.xml`, transcribed verbatim — names, TTF paths, heights, colors, outlines, and
(critically) which families carry a `<Shadow>` and which don't. The reference copy is
re-extractable from the client at any time with the `mpqx` bin (crates/benilla-mpq,
virtual path `Interface\FrameXML\Fonts.xml`); this is our own authored file (MIT/Apache),
only the TTFs themselves stream from the client at render.
Being COMPLETE is the point: the first partial transcription lacked `QuestFontNormalSmall`,
a window substituted `GameFontNormalSmall` for it, and the parchment objectives rendered
10px gold WITH the MasterFont drop shadow instead of 12px warm-brown WITHOUT one — a look
bug born entirely from a missing font object, invisible to every engine test. Substituting
"a similar font" is never safe (shadow/height/color all ride the name), so every name the
real FrameXML defines exists here.
A FontString picks a font object up with `inherits="GameFontNormal"`; `SetFontObject`
re-points it. Each object resolves {font path, height, color, outline, shadow} through its
`inherits` chain. NOTE the load-bearing asymmetry, straight from the ref: the `GameFont*`
families chain through `MasterFont` (whose only content is the (1,-1) black `<Shadow>`),
while `GameFontBlack`/`GameFontWhite`, the `NumberFont*` family (outlined instead), and the
parchment `QuestFont*` family (except the brown-shadowed `QuestTitleFont`) do NOT — dark
text on parchment is shadowless in the real client.
-->
<!-- The shared font-color globals, QUOTED from the real Fonts.xml's own <Script> block
(ref l.8-19) — the |cAARRGGBB escape prefixes the stat/tooltip builders concatenate, and
the two color tables tooltip AddLine calls read. Defined here (the ref's own home, loaded
first) so every window shares one verified set. -->
<Script><![CDATA[
-- ── The four font-PATH globals (ref Fonts.xml l.4-7) ──────────────────────────────────
-- This file quoted the reference's colour block (l.8-19) and skipped the four lines above
-- it. `STANDARD_TEXT_FONT` is the one that matters: **68 corpus addons name it**, and per
-- 1207's rule that number is read rather than quoted — 64 of them are copies of
-- `Dewdrop-2.0.lua` and only 4 are addon code. But Dewdrop is *the* Ace2 menu library, and
-- it calls `button.text:SetFont(STANDARD_TEXT_FONT, height)` **unguarded** at two of its
-- three sites (l.207 and l.496; only l.2294 writes `STANDARD_TEXT_FONT or "Fonts\\..."`),
-- so a nil global is a failed SetFont on every menu button the Ace2 ecosystem draws.
--
-- The other three come with it because they are the same four-line block and cost nothing:
-- UNIT_NAME_FONT (0 corpus addons), DAMAGE_TEXT_FONT (1), NAMEPLATE_FONT (1). All four are
-- the same face in 1.12 — the reference assigns FRIZQT__ to every one — and that identity
-- is the reference's, not a simplification of ours.
STANDARD_TEXT_FONT = "Fonts\\FRIZQT__.TTF" -- ref Fonts.xml l.4
UNIT_NAME_FONT = "Fonts\\FRIZQT__.TTF" -- l.5
DAMAGE_TEXT_FONT = "Fonts\\FRIZQT__.TTF" -- l.6
NAMEPLATE_FONT = "Fonts\\FRIZQT__.TTF" -- l.7
NORMAL_FONT_COLOR_CODE = "|cffffd200" -- ref Fonts.xml l.8
HIGHLIGHT_FONT_COLOR_CODE = "|cffffffff" -- l.9
RED_FONT_COLOR_CODE = "|cffff2020" -- l.10
GREEN_FONT_COLOR_CODE = "|cff20ff20" -- l.11
GRAY_FONT_COLOR_CODE = "|cff808080" -- l.12
FONT_COLOR_CODE_CLOSE = "|r" -- l.14
NORMAL_FONT_COLOR = { r = 1.0, g = 0.82, b = 0 } -- l.15
HIGHLIGHT_FONT_COLOR = { r = 1.0, g = 1.0, b = 1.0 } -- l.16
GRAY_FONT_COLOR = { r = 0.5, g = 0.5, b = 0.5 } -- l.17
GREEN_FONT_COLOR = { r = 0.1, g = 1.0, b = 0.1 } -- l.18
RED_FONT_COLOR = { r = 1.0, g = 0.1, b = 0.1 } -- l.19
-- Added this session (decision 0216 §8, the spellbook slice) — the ref's own l.20, the
-- one color this file was missing: a passive spell's name text (SpellBookFrame.lua:385).
PASSIVE_SPELL_FONT_COLOR = { r = 0.77, g = 0.64, b = 0 } -- l.20
-- The item-quality palette — **built from the engine verb, exactly as the reference
-- builds it** (ref UIParent.lua l.65-72, verbatim shape; decision 1199):
--
-- ITEM_QUALITY_COLORS = { }
-- for i = -1, 6 do … = GetItemQualityColor(i) end
--
-- It used to be seven hand-typed rows here. They were CLOSE and not exact — 0.62 where
-- the client's byte is 0x9d/255 = 0.6157, 0.64/0.21/0.93 where Epic is
-- 0xa3/0x35/0xee — and they carried no `.hex`, which the reference's table has and
-- which addons splice straight into a chat link. `GetItemQualityColor` is now a real
-- engine binding over wow-5875-re RF-0055's byte-verified table, so the rounding and
-- the second source both go.
--
-- The loop starts at -1 like the reference's: `UIParent.lua` reads one index before the
-- array there, and our binding answers Poor for it rather than reproducing that.
ITEM_QUALITY_COLORS = { }
for i = -1, 6 do
ITEM_QUALITY_COLORS[i] = { }
ITEM_QUALITY_COLORS[i].r,
ITEM_QUALITY_COLORS[i].g,
ITEM_QUALITY_COLORS[i].b,
ITEM_QUALITY_COLORS[i].hex = GetItemQualityColor(i)
end
-- ── RAID_CLASS_COLORS (ref Fonts.xml l.43-53), transcribed verbatim ───────────────────
--
-- The per-class colour every raid/party addon paints names with. **22 corpus addons** reach
-- it — nine of them through `Babble-Class-2.0`, but seven more by hand (KLHThreatMeter,
-- CT_RaidAssist, CT_ExpenseHistory, _LazyPig, FuBar_oRA2CooldownFu, and BigWigs in two
-- plugins) — and absent it is `bad argument #1 to 'pairs' (table expected, got nil)` at
-- file scope. That was the whole of the harness's remaining `table expected` row: three
-- addons, one missing table, found by asking the blocker table which addons were behind it.
--
-- TWO THINGS THAT LOOK WRONG AND ARE THE REFERENCE'S: `SHAMAN` carries the same pink as
-- `PALADIN` (shamans were Horde-only and paladins Alliance-only in 1.12, so the two never
-- shared a raid frame and Blizzard never gave shamans their own), and there is no `ROGUE`
-- yellow anywhere else in the client to reconcile it with. Transcribed as found; a later
-- client's palette is not this one's.
RAID_CLASS_COLORS = {
["HUNTER"] = { r = 0.67, g = 0.83, b = 0.45 },
["WARLOCK"] = { r = 0.58, g = 0.51, b = 0.79 },
["PRIEST"] = { r = 1.0, g = 1.0, b = 1.0 },
["PALADIN"] = { r = 0.96, g = 0.55, b = 0.73 },
["MAGE"] = { r = 0.41, g = 0.8, b = 0.94 },
["ROGUE"] = { r = 1.0, g = 0.96, b = 0.41 },
["DRUID"] = { r = 1.0, g = 0.49, b = 0.04 },
["SHAMAN"] = { r = 0.96, g = 0.55, b = 0.73 },
["WARRIOR"] = { r = 0.78, g = 0.61, b = 0.43 },
}
-- The three OTHER tables the reference's Fonts.xml `<Script>` block carries —
-- CHAT_FONT_HEIGHTS, MATERIAL_TEXT_COLOR_TABLE, MATERIAL_TITLETEXT_COLOR_TABLE — are
-- deliberately not here: **zero corpus addons name any of them**, and nothing benilla ships
-- reads them. They cost nine lines each the day something does.
]]></Script>
<!-- MasterFont: the shadow-only root the GameFont* families chain through (ref l.56). -->
<Font name="MasterFont" virtual="true">
<Shadow>
<Offset><AbsDimension x="1" y="-1"/></Offset>
<Color r="0" g="0" b="0"/>
</Shadow>
</Font>
<!-- SystemFont: FRIZQT, 15px, yellow (ref l.64). -->
<Font name="SystemFont" inherits="MasterFont" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="15"/></FontHeight>
<Color r="1.0" g="1.0" b="0"/>
</Font>
<!-- The GameFont body family: FRIZQT, 12px, gold; color variants override only <Color> (ref l.70-96). -->
<Font name="GameFontNormal" inherits="MasterFont" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="12"/></FontHeight>
<Color r="1.0" g="0.82" b="0"/>
</Font>
<Font name="GameFontHighlight" inherits="GameFontNormal" virtual="true">
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="GameFontDisable" inherits="GameFontNormal" virtual="true">
<Color r="0.5" g="0.5" b="0.5"/>
</Font>
<Font name="GameFontGreen" inherits="GameFontNormal" virtual="true">
<Color r="0.1" g="1.0" b="0.1"/>
</Font>
<Font name="GameFontRed" inherits="GameFontNormal" virtual="true">
<Color r="1.0" g="0.1" b="0.1"/>
</Font>
<!-- GameFontBlack/White: 12px FRIZQT with NO MasterFont chain — shadowless (ref l.88-96). -->
<Font name="GameFontBlack" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="12"/></FontHeight>
<Color r="0" g="0" b="0"/>
</Font>
<Font name="GameFontWhite" inherits="GameFontBlack" virtual="true">
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<!-- The GameFont Small family: FRIZQT, 10px, gold (ref l.97-125). -->
<Font name="GameFontNormalSmall" inherits="MasterFont" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="10"/></FontHeight>
<Color r="1.0" g="0.82" b="0"/>
</Font>
<Font name="GameFontHighlightSmall" inherits="GameFontNormalSmall" virtual="true">
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="GameFontDisableSmall" inherits="GameFontNormalSmall" virtual="true">
<Color r="0.5" g="0.5" b="0.5"/>
</Font>
<Font name="GameFontDarkGraySmall" inherits="GameFontNormalSmall" virtual="true">
<Color r="0.35" g="0.35" b="0.35"/>
</Font>
<Font name="GameFontGreenSmall" inherits="GameFontNormalSmall" virtual="true">
<Color r="0.1" g="1.0" b="0.1"/>
</Font>
<Font name="GameFontRedSmall" inherits="GameFontNormalSmall" virtual="true">
<Color r="1.0" g="0.1" b="0.1"/>
</Font>
<!-- Despite the name, the ref declares a SHADOW here, not an outline (ref l.119). -->
<Font name="GameFontHighlightSmallOutline" inherits="GameFontHighlightSmall" virtual="true">
<Shadow>
<Offset><AbsDimension x="1" y="-1"/></Offset>
<Color r="0" g="0" b="0"/>
</Shadow>
</Font>
<!-- The GameFont Large family: FRIZQT, 16px, gold (ref l.127-145). -->
<Font name="GameFontNormalLarge" inherits="MasterFont" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="16"/></FontHeight>
<Color r="1.0" g="0.82" b="0"/>
</Font>
<Font name="GameFontHighlightLarge" inherits="GameFontNormalLarge" virtual="true">
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="GameFontDisableLarge" inherits="GameFontNormalLarge" virtual="true">
<Color r="0.5" g="0.5" b="0.5"/>
</Font>
<Font name="GameFontGreenLarge" inherits="GameFontNormalLarge" virtual="true">
<Color r="0.1" g="1.0" b="0.1"/>
</Font>
<Font name="GameFontRedLarge" inherits="GameFontNormalLarge" virtual="true">
<Color r="1.0" g="0.1" b="0.1"/>
</Font>
<!-- FRIZQT, 20px, gold (ref l.145). -->
<Font name="GameFontNormalHuge" inherits="MasterFont" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="20"/></FontHeight>
<Color r="1.0" g="0.82" b="0"/>
</Font>
<!-- The Number family: ARIALN, outlined, white — NO shadow (ref l.150-179). -->
<Font name="NumberFontNormal" font="Fonts\ARIALN.TTF" outline="NORMAL" virtual="true">
<FontHeight><AbsValue val="14"/></FontHeight>
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="NumberFontNormalYellow" inherits="NumberFontNormal" virtual="true">
<Color r="1.0" g="0.82" b="0"/>
</Font>
<Font name="NumberFontNormalSmall" font="Fonts\ARIALN.TTF" outline="THICK" virtual="true" monochrome="true">
<FontHeight><AbsValue val="12"/></FontHeight>
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="NumberFontNormalSmallGray" inherits="NumberFontNormalSmall" outline="THICK" virtual="true">
<Color r="0.6" g="0.6" b="0.6"/>
</Font>
<Font name="NumberFontNormalLarge" font="Fonts\ARIALN.TTF" outline="NORMAL" virtual="true">
<FontHeight><AbsValue val="16"/></FontHeight>
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="NumberFontNormalHuge" font="Fonts\skurri.ttf" outline="THICK" virtual="true">
<FontHeight><AbsValue val="30"/></FontHeight>
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<!-- ChatFontNormal: ARIALN, 14px, white, (1,-1) black shadow (ref l.180). -->
<Font name="ChatFontNormal" font="Fonts\ARIALN.TTF" virtual="true">
<FontHeight><AbsValue val="14"/></FontHeight>
<Color r="1.0" g="1.0" b="1.0"/>
<Shadow>
<Offset><AbsDimension x="1" y="-1"/></Offset>
<Color r="0" g="0" b="0"/>
</Shadow>
</Font>
<!-- The quest/parchment fonts (ref l.191-215): MORPHEUS 18 title with a warm-brown (0.49,0.35,0.05)
shadow; the FRIZQT body fonts are dark-on-parchment and SHADOWLESS (QuestFontNormalSmall
chains through GameFontBlack, not MasterFont). -->
<Font name="QuestTitleFont" font="Fonts\MORPHEUS.ttf" virtual="true">
<FontHeight><AbsValue val="18"/></FontHeight>
<Color r="0" g="0" b="0"/>
<Shadow>
<Offset><AbsDimension x="1" y="-1"/></Offset>
<Color r="0.49" g="0.35" b="0.05"/>
</Shadow>
</Font>
<Font name="QuestFont" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="13"/></FontHeight>
<Color r="0" g="0" b="0"/>
</Font>
<Font name="QuestFontNormalSmall" inherits="GameFontBlack" virtual="true">
<Color r="0.30" g="0.18" b="0"/>
</Font>
<Font name="QuestFontHighlight" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="14"/></FontHeight>
<Color r="0" g="0" b="0"/>
</Font>
<!-- The MORPHEUS 15px book/mail body fonts (ref l.216-229). -->
<Font name="ItemTextFontNormal" font="Fonts\MORPHEUS.TTF" justifyH="LEFT" virtual="true">
<FontHeight><AbsValue val="15"/></FontHeight>
<Color r="0.18" g="0.12" b="0.06"/>
</Font>
<Font name="MailTextFontNormal" font="Fonts\MORPHEUS.TTF" justifyH="LEFT" virtual="true">
<FontHeight><AbsValue val="15"/></FontHeight>
<Color r="0.18" g="0.12" b="0.06"/>
</Font>
<!-- SubSpellFont: FRIZQT 10, dark brown (ref l.231). -->
<Font name="SubSpellFont" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="10"/></FontHeight>
<Color r="0.35" g="0.2" b="0"/>
</Font>
<!-- The dialog (StaticPopup) button pair: FRIZQT 16 (ref l.237-245). -->
<Font name="DialogButtonNormalText" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="16"/></FontHeight>
<Color r="1.0" g="0.82" b="0.0"/>
</Font>
<Font name="DialogButtonHighlightText" inherits="DialogButtonNormalText" virtual="true">
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<!-- The zone-announce banners: THICK-outlined FRIZQT; the ref's bare `<Shadow/>` transcribed
as-is (offset defaults, i.e. no visible offset) (ref l.246-257). -->
<Font name="ZoneTextFont" font="Fonts\FRIZQT__.TTF" outline="THICK" virtual="true">
<FontHeight><AbsValue val="102"/></FontHeight>
<Color r="1.0" g="0.9294" b="0.7607"/>
<Shadow/>
</Font>
<Font name="SubZoneTextFont" font="Fonts\FRIZQT__.TTF" outline="THICK" virtual="true">
<FontHeight><AbsValue val="26"/></FontHeight>
</Font>
<Font name="ErrorFont" inherits="GameFontNormalLarge" virtual="true"/>
<Font name="TextStatusBarText" inherits="NumberFontNormal" virtual="true"/>
<Font name="TextStatusBarTextSmall" font="Fonts\ARIALN.TTF" outline="NORMAL" virtual="true" monochrome="false">
<FontHeight><AbsValue val="12"/></FontHeight>
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="CombatLogFont" inherits="GameFontHighlight" justifyH="LEFT" virtual="true"/>
<!-- The tooltip family: FRIZQT white, no shadow (ref l.267-285). -->
<Font name="GameTooltipText" font="Fonts\FRIZQT__.TTF" justifyH="LEFT" virtual="true">
<FontHeight><AbsValue val="12"/></FontHeight>
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="GameTooltipTextSmall" font="Fonts\FRIZQT__.TTF" justifyH="LEFT" virtual="true">
<FontHeight><AbsValue val="10"/></FontHeight>
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="GameTooltipHeaderText" font="Fonts\FRIZQT__.TTF" justifyH="LEFT" virtual="true">
<FontHeight><AbsValue val="14"/></FontHeight>
<Color r="1.0" g="1.0" b="1.0"/>
</Font>
<Font name="WorldMapTextFont" font="Fonts\FRIZQT__.TTF" outline="THICK" virtual="true">
<FontHeight><AbsValue val="102"/></FontHeight>
<Color r="1.0" g="0.9294" b="0.7607"/>
<Shadow/>
</Font>
<!-- The invoice (auction mail) parchment fonts (ref l.293-304). -->
<Font name="InvoiceTextFontNormal" font="Fonts\FRIZQT__.TTF" justifyH="LEFT" virtual="true">
<FontHeight><AbsValue val="12"/></FontHeight>
<Color r="0.18" g="0.12" b="0.06"/>
</Font>
<Font name="InvoiceTextFontSmall" font="Fonts\FRIZQT__.TTF" justifyH="LEFT" virtual="true">
<FontHeight><AbsValue val="10"/></FontHeight>
<Color r="0.18" g="0.12" b="0.06"/>
</Font>
<!-- CombatTextFont: FRIZQT 25, gold, MasterFont shadow (ref l.305). -->
<Font name="CombatTextFont" inherits="MasterFont" font="Fonts\FRIZQT__.TTF" virtual="true">
<FontHeight><AbsValue val="25"/></FontHeight>
<Color r="1.0" g="0.82" b="0"/>
</Font>
</Ui>