From 872b227209854b9c80b7a7777d9a141dbef70722 Mon Sep 17 00:00:00 2001 From: Erik Date: Mon, 24 Aug 2026 21:08:05 +0200 Subject: [PATCH] =?UTF-8?q?docs(CT):=20CT4=20header=20contract=20read=20ve?= =?UTF-8?q?rbatim=20=E2=80=94=20UpdateCharacterInfo=20@0x004F0770=20+=20Up?= =?UTF-8?q?datePKStatus=20@0x004F00A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Name via AllegianceData::GetFullName, heritage line composed with the display title, level fallback literal, PK line from StringTable 0x23000001 ID_StatManagement_Header_PKStatus_* keys (the chat-label mechanism). Co-Authored-By: Claude Fable 5 --- ...6-08-24-character-panel-parity-campaign.md | 24 +++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/docs/plans/2026-08-24-character-panel-parity-campaign.md b/docs/plans/2026-08-24-character-panel-parity-campaign.md index 8de1aad3..126cae02 100644 --- a/docs/plans/2026-08-24-character-panel-parity-campaign.md +++ b/docs/plans/2026-08-24-character-panel-parity-campaign.md @@ -70,6 +70,30 @@ display title; the PK strings are exactly "Player Killer" / cross-anchor `CharExamineUI::SetAppraiseInfo @0x004B45F0`). CT5 reads the composing function verbatim before writing a line of C#. +### CT4 contract (read verbatim 2026-08-24, Fable) +`gmStatManagementUI::UpdateCharacterInfo @0x004F0770`: +- **Name line** (`0x10000231`): `ACCWeenieObject::GetObjectName(player, + NAME_SINGULAR)` run through `AllegianceData::GetFullName` with a + default-constructed allegiance record (implementer reads GetFullName + before porting — it may add rank prefixes when allegiance data exists). +- **Heritage line** (`0x10000232`): + `AppraisalSystem::InqGenderHeritageDisplay(gender=Int 0x71, + heritage=Int 0xBC, 0)` ("Female Aluvian"); then, when + `CharacterTitleTable::GetCharacterTitleFromID(m_titleID)` resolves, + `AppendText(separator @data_794358)` + `AppendText(titleString)` → + "Female Aluvian War Mage". Recover the separator literal with the + PE-read recipe (`claude-memory/reference_pe_byte_decode.md`). +- **Level** (`0x1000023B`): `InqInt(0x19)` present → + `Formatted(@data_7a0184)`; absent → literal `@data_7b0f34`. +- **PK line** (`0x10000233`): `UpdatePKStatus @0x004F00A0` — three-way + `IsPK` / `IsPKLite` / neither → StringInfo from table enum + `0x10000001` (= StringTable `0x23000001`, same compute_str_hash + mechanism the chat labels use) with keys + `ID_StatManagement_Header_PKStatus_PK` / `_PKL` / `_NPK`. +- Related key family for the footer/meter (already-shipped surfaces — + audit only if CT1 finds drift): `ID_StatManagement_Footer_*`, + `ID_StatManagement_Header_XPToLevelMeterInfinity`. + ### Already in-tree - Tab/page ids wired (`TabTitlesId 0x10000538`, `TitlesPageId 0x10000539`); pages currently show retail-authored closed visuals.