fix(chargen): Campaign CC gate round 1 re-test 2 — R3-3 skills info-box VerticalJustify
The info-box title (0x100003fb, Y=435 H=100) and description (0x100003fc, Y=460 H=100) panes' own authored boxes overlap by 75px, live-DAT-measured — retail relies on vertical justification, not disjoint rects, to keep them visually separate. Neither pane authors dat property 0x15, so both fall to this port's shared unauthored-VJustify default (currently Center). Byte-traced retail's real ctor default (UIElement_Text::UIElement_Text @0x004685ff, m_eVerticalJustification = 4) against UIElement_Text:: CalcJustification @0x00467260's actual enum semantics (1=Center, 3-or-5= the far edge/Bottom, anything else INCLUDING the ctor's own default of 4 = the near edge/Top): the correct unauthored default is Top, not Center — a genuine client-wide enum-mapping bug in this port. Under Top both panes render near their own box's top edge (25px apart, no collision); under Center both cluster toward the middle of their overlapping boxes. Scoped fix: CharacterCreationSkillsPage force-sets VerticalJustify=Top on both panes directly, rather than fixing the shared mapping/default — that bug is client-wide and could regress already-shipped FROZEN surfaces (vitals, chat, main game UI, Options) that may rely on the current Center default. The shared fix is filed as ISSUES #410 / register AD-104 for its own dedicated investigation + regression sweep. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
parent
7d6a7898f6
commit
7f6e93033f
4 changed files with 143 additions and 1 deletions
|
|
@ -24,6 +24,87 @@ What does NOT go here:
|
|||
- Every session: scan OPEN issues at start; promote/close anything we touched during the session before ending.
|
||||
- Promoting to a Phase: mark as `DONE (promoted to Phase X)` + commit SHA where the Phase entry landed.
|
||||
|
||||
## #410 — Client-wide VJustify (vertical text justification) enum mapping + unauthored default are wrong (retail default is Top, not Center)
|
||||
|
||||
**Status:** OPEN
|
||||
**Severity:** MEDIUM (silently mispositions every DAT-imported `UiText` that
|
||||
relies on the unauthored default, or that authors a raw vertical-
|
||||
justification value other than 1 — currently invisible unless two
|
||||
elements' boxes are close/overlapping the way the Skills info-box panes
|
||||
are, but could affect vertical alignment anywhere client-wide)
|
||||
|
||||
Found during Campaign CC gate round 1 re-test 2's R3-3 investigation
|
||||
(`docs/research/2026-08-16-campaign-cc-gate-round1-findings.md`). The
|
||||
Skills page's info-box title (`0x100003fb`) and description (`0x100003fc`)
|
||||
panes author NO dat property `0x15` (vertical justification) — live-DAT-
|
||||
probe-confirmed absent on both — so both fall to whatever this port's
|
||||
unauthored default resolves to, currently `VJustify.Center`
|
||||
(`ElementReader.cs`'s `VJustify` field default and
|
||||
`ElementReader.cs`/`DatWidgetFactory.cs`'s import-time mapping switches).
|
||||
|
||||
Byte-traced against retail:
|
||||
|
||||
- `UIElement_Text::UIElement_Text` (ctor) `@0x004685ff`: unconditionally
|
||||
sets `this->m_eVerticalJustification = 4` (and
|
||||
`m_eHorizontalJustification = 2` at `@0x004685f5`) BEFORE any dat
|
||||
property is applied — i.e. retail's real unauthored default is the raw
|
||||
value **4**, not whatever a "sensible default" might suggest.
|
||||
- `UIElement_Text::CalcJustification` `@0x00467260`: the ACTUAL enum
|
||||
semantics, shared by both the horizontal and vertical branches via one
|
||||
`ecx_5` comparison — `ecx_5 == 1` → **Center**; `ecx_5 == 3 || ecx_5 == 5`
|
||||
→ the FAR edge (**Right** for horizontal, **Bottom** for vertical); any
|
||||
OTHER value (0, 2, 4, ...) → `edi = 0`, the NEAR edge (**Left** for
|
||||
horizontal, **Top** for vertical).
|
||||
|
||||
Cross-referencing: the ctor's own vertical default of 4 resolves via this
|
||||
real semantic table to **Top**, not Center. This port's
|
||||
`ElementReader.cs:507`'s import-time switch (`2u=>Top, 4u=>Bottom,
|
||||
_=>Center`) and `DatWidgetFactory.cs:704`'s build-time switch are BOTH
|
||||
wrong relative to the real table — only raw value `2` (coincidentally
|
||||
falling into the correct "near edge" bucket) and `1` (Center, matching the
|
||||
`_=>Center` catch-all by coincidence) currently resolve correctly; `0`,
|
||||
`3`, `4`, and `5` all resolve to the wrong bucket. The `ElementInfo.VJustify`
|
||||
field default (`VJustify.Center`) is ALSO wrong — it should be `Top` to
|
||||
match the ctor's real resolved value.
|
||||
|
||||
**Why this is filed instead of fixed here:** the blast radius is
|
||||
client-wide — every DAT-imported `UiText` that reaches the
|
||||
`Centered`/`RightAligned`/`OneLine` static paths or the multi-line
|
||||
honored-justification path (`_honorDatVerticalJustification`, set
|
||||
unconditionally by `ConfigureDatState` for every DAT-imported text
|
||||
element) is affected, including already-shipped, visually-verified,
|
||||
FROZEN surfaces (vitals numbers, chat, main game UI, Options panel) that
|
||||
may be relying on the CURRENT (wrong) Center default for their existing
|
||||
correct-looking vertical alignment. Flipping the shared default/mapping
|
||||
without a full client-wide regression sweep risks reintroducing
|
||||
regressions in surfaces this session has no budget to re-verify. R3-3's
|
||||
own fix (`CharacterCreationSkillsPage`'s constructor) scopes the
|
||||
correction to ONLY the two Skills info-box panes via an explicit
|
||||
`VerticalJustify = VJustify.Top` post-construction assignment — a
|
||||
targeted, decomp-grounded correction that does not touch the shared
|
||||
mapping.
|
||||
|
||||
**Fix direction when this issue is picked up:** (1) correct
|
||||
`ElementReader.cs`'s import-time switch AND `DatWidgetFactory.cs`'s
|
||||
build-time switch to the real table above (`1=>Center, 3 or 5=>Bottom,
|
||||
else=>Top`) for BOTH horizontal and vertical justification (audit the
|
||||
horizontal switch too — it currently special-cases `0u or 2u=>Left`
|
||||
instead of "everything except 1/3/5"; likely benign today since 2 is the
|
||||
only unauthored horizontal default in practice, but should be corrected
|
||||
for the same reason); (2) flip `ElementInfo.VJustify`'s field default to
|
||||
`Top`; (3) fix `ElementReader.cs:435`'s `Merge` sentinel
|
||||
(`derived.VJustify != VJustify.Center ? derived : base_`) to use the NEW
|
||||
default (`Top`) as the "unset" sentinel instead, or restructure to a
|
||||
nullable/explicit-override tracking shape so the merge doesn't rely on a
|
||||
magic default value at all; (4) a full client-wide live-DAT sweep of every
|
||||
Type-12/Button element that authors OR omits property `0x15`/`0x14`,
|
||||
cross-checked against a fresh full visual pass of chat, main game UI,
|
||||
Options, and every chargen page (this port's own `CharacterCreationSkillsPage`
|
||||
override from R3-3 should be REMOVED once the shared default is corrected,
|
||||
since it would then be redundant); (5) the exact same audit for the
|
||||
horizontal `HJustify` mapping while in this code, since it shares the
|
||||
`CalcJustification` function and the same class of latent bug.
|
||||
|
||||
## #409 — Client-wide UI tooltip system is unshipped (GF-16, deferred out of Campaign CC gate round 1)
|
||||
|
||||
**Status:** OPEN
|
||||
|
|
|
|||
File diff suppressed because one or more lines are too long
Loading…
Add table
Add a link
Reference in a new issue