fix #380: Chat tab opacity sliders were missing their retail row captions

Root cause: PlayerOptionPage::AddSliderOption never sets a row's own
name-label text — the "Inactive Opacity"/"Active Opacity" caption comes
from a SEPARATE DAT-resident runtime catalog (DID 0x78000000, resolved
via the same two-level DBCache::GetDIDFromEnumStatic master-map/submap
lookup ChatOptionsDatDefaults already uses for enum 0x16/category 2,
here for enum 0x15/category 2) that nothing in the codebase ever
queried, so both slider rows rendered with no caption at all.

Fix: new ChatOptionsDatCaptions.TryRead resolves the DID-0x78000000
catalog's per-property name/tooltip entries (matched by the same
owning-property enum ChatOptionsDatDefaults already keys its defaults
by) and ChatOptionsPageController.BuildOpacitySliders stamps each
slider's own row caption/tooltip from it — falling back to no text
(never invented English) if resolution fails. Regressed by
ChatOptionsPageControllerTests.
Bind_WiresEachSlidersOwnRowCaption_FromTheResolvedDatCatalog and the
companion Bind_MissingCaption_RendersNoText_NeverInventsEnglish case,
plus a live-mount probe (OptionsPanelLiveMountProbeTests.
ProbeChatOpacityCaptions) confirming the production TryRead call
resolves "Inactive Opacity"/"Active Opacity" against the real DAT.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
Erik 2026-08-11 23:01:22 +02:00
parent c0b3d8f233
commit 2a248c0d48
8 changed files with 415 additions and 10 deletions

View file

@ -51,14 +51,42 @@ we fail to draw (preferred: draw the authored one) before synthesizing.
## #380 — Chat tab: the two opacity sliders are missing their retail row captions
**Status:** OPEN — filed 2026-08-11 at Campaign OP gate 4 (user report:
"I also miss the text next to the bars for Inactive and Active Opacity").
acdream's General Chat Options section renders the two sliders with only
the Transparent/Opaque endpoint labels; retail also captions each slider
row (inactive vs active opacity). Resolve the captions from the authored
layout/DAT strings (never invented English) — check whether the authored
elements exist and fail to resolve (the #375 resolver class) or are
missing from our template handling.
**Status:** ROOT-CAUSED + FIXED (this commit) — pending the user's
re-gate. Filed 2026-08-11 at Campaign OP gate 4 (user report: "I also
miss the text next to the bars for Inactive and Active Opacity").
**ROOT CAUSE — a DAT-resident runtime catalog, not a compiled symbol,
that nothing ever queried.** `PlayerOptionPage::AddSliderOption` never
sets a row's name-label text (byte-verified — no `StringInfo` write in
its pseudo-C body); the caption comes from a SEPARATE mechanism,
`UIOption_Slider::SetGameplayOptionProperty @0x00485030`'s own
`UIOption::InqGameplayOptionNameAndTooltip @0x004ef750` catalog lookup —
a SECOND `DBCache::GetDIDFromEnumStatic` sub-map lookup
(`(0x15, 2)`, sibling to the ALREADY-PORTED `(0x16, 2)` defaults lookup)
resolving to DID `0x78000000` (confirmed a DIFFERENT object from the
defaults catalog's `0x78000001`), a `DBProperties` with one `ArrayBase-
Property` of per-`GameplayOptionProperty` entries (name/tooltip
`StringInfo` + the owning property id). Live-DAT-read: the array has
exactly two entries, resolving via string table `0x2300000D` (the SAME
table #372 already established as this campaign's runtime-string home)
to "Inactive Opacity" / "Active Opacity" — the user's own two words.
**Fix:** `ChatOptionsDatCaptions.TryRead` ports the lookup (mirroring the
existing `ChatOptionsDatDefaults` shape); `ChatOptionsPageController`
wires the resolved captions onto element `0x1000021B` (the row's own
name-label child, present on BOTH slider templates but never referenced
by this controller before) and the tooltips onto each slider. Regressed
by `tests/AcDream.App.Tests/UI/Layout/ChatOptionsPageControllerTests.cs`
(`Bind_WiresEachSlidersOwnRowCaption_FromTheResolvedDatCatalog`,
`Bind_MissingCaption_RendersNoText_NeverInventsEnglish`) and a new live-
mount probe (`ProbeChatOpacityCaptions` in
`OptionsPanelLiveMountProbeTests.cs`) that exercises the production
`ChatOptionsDatCaptions.TryRead` against the real DAT and asserts the
exact two strings.
**Re-gate (§OP5, opacity sliders section): both slider rows should now
show their own caption ("Inactive Opacity" / "Active Opacity") next to
the bar, not just the Transparent/Opaque endpoint labels on the second
slider.**
## #379 — Chat-window opacity applies to ALL retained windows/panels, not only the chat windows