port: an authored value becomes measured, and a difference-only check gets an origin

The Decoder corrected their own focus delivery: the persistence run's item names
were two positions out, from a reader using design-space rows against captures
carrying Xenia's chrome and a 1.060 scale. Two things follow.

initial_focus_kind moves from authored to measured. NEW GAME on a fresh boot, 2/2
fresh boots, both the first menu entry. The value did not change; its standing
did, and the upgrade is not because the measurement agrees with me -- they had
said my agreeing with their records was no evidence, which was correct, and this
is a direct reading independent of the reasoning that chose NEW GAME here. "First
entry" is load-bearing: since the menu remembers its cursor, a reading taken
later measures history, which is the objection that voided the earlier
TUTORIAL-versus-NEW-GAME disagreement. The superseded reasoning is kept under
(was) lines -- the field existing and being labelled honestly is what made
arriving at a measurement a label change rather than an archaeology problem, the
third time that has paid off after loop_start_s and the +0x08 read.

My check_focus_persists anchor survived a correction it should not have been able
to detect. It anchors on the heading, the conclusion, not on the item names. That
is lucky rather than designed: the conclusion is geometry-free -- ring at y 384.0
before the round trip and 385.5 after, an equality immune to a constant offset --
while the names were not. The check would not have caught the label error, and
nothing in it distinguishes anchored-on-a-robust-claim from anchored-above-the-
part-that-was-wrong.

Their generalisation: a control that only checks differences is blind to the
origin. check_splash_dwell is that shape -- it compares the widest gap between
keyframe times, and a reader with every time shifted by a constant passes. Added
check_splash_times, asserting the absolute list the contract prints. Origin and
difference now fail independently.

Writing that control reproduced the error one level down: its perturbation
literal was written from memory of the prose, with a space where the document has
a newline, so it reported its own anchor gone. A control written from a memory of
the source rather than from the source is the class of error these checks exist
to catch. Thirteen controls, all firing.

Q2 closed: fixed same day, and the row was worse than I reported -- the splashes
were also mis-paired as 10/11, one half each of two different pairs.

EXTRAS remains unmeasured; the run meant to settle it navigated to OPTIONS
believing it was EXTRAS. Every asserting check passes.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01N7FiFFFwbvG2uxdcEh8HyF
This commit is contained in:
Sylpheed port agent
2026-08-30 22:03:58 +00:00
parent bb0b2dfe7e
commit 73710ac2e3
4 changed files with 141 additions and 15 deletions

View File

@@ -151,7 +151,7 @@ HANDOFF.
| Milestone | Needs | HANDOFF | State |
|---|---|---|---|
| P0P7 — Q2's map of `GP_TITLE` | **list entries 10, 11, 13 and 14 in the Q2 row** | `12c9f04` | 🟡 **the count is right and the enumeration is short; not blocking.** Q2 says *"`GP_TITLE` is 8 screens shipped twice, EN/JP"* and lists `2/3`, `4/7`, `5/8`, `6/9`, `0/1`, `12/15`**six states of the eight**. The two boot splashes, `publisher_logo` (10/13) and `developer_logos` (11/14), appear nowhere in it. ✅ The headline is confirmed by my export's entry map: 4 UI states + 2 loading variants + **2 splashes** = 8, shipped twice = the 16 entries the archive holds. 🔴 A reader counting Q2 gets twelve and has no slot for the splashes — **and this is the row already corrected once for an ordinal-versus-entry error**, which is the mistake four unlisted entries feed. The port is unaffected: both splashes are exported, named, and verified against captures at RMSE 2.17 and 3.05. |
| ~~P0P7 — Q2's map of `GP_TITLE`~~ | ~~list entries 10, 11, 13 and 14 in the Q2 row~~ | `12c9f04` |**FIXED SAME DAY, and the row was worse than I reported.** All eight states are enumerated now and the per-entry names are committed as reference data, so the next reader checks rather than counts. ⚠️ My report said the splashes were *missing*; they were also **mis-paired as 10/11**, which is one half each of two different pairs — 10/13 is `palogo_sqex`, 11/14 is `gamearts`/`seta`/`anima`, matching my export's entry map exactly. Original text: 🟡 **the count is right and the enumeration is short; not blocking.** Q2 says *"`GP_TITLE` is 8 screens shipped twice, EN/JP"* and lists `2/3`, `4/7`, `5/8`, `6/9`, `0/1`, `12/15`**six states of the eight**. The two boot splashes, `publisher_logo` (10/13) and `developer_logos` (11/14), appear nowhere in it. ✅ The headline is confirmed by my export's entry map: 4 UI states + 2 loading variants + **2 splashes** = 8, shipped twice = the 16 entries the archive holds. 🔴 A reader counting Q2 gets twelve and has no slot for the splashes — **and this is the row already corrected once for an ordinal-versus-entry error**, which is the mistake four unlisted entries feed. The port is unaffected: both splashes are exported, named, and verified against captures at RMSE 2.17 and 3.05. |
## Ask for the HUMAN, 2026-08-30 — derived from HANDOFF `27938aa`

View File

@@ -9,7 +9,7 @@ dies, which is what this file is for.
<!-- INDEX: generated by tools/port/index-decisions -- do not hand-edit -->
244 sections. Search this before re-deriving anything.
245 sections. Search this before re-deriving anything.
* [P0 — the exporter, 2026-08-28](#p0--the-exporter-2026-08-28)
* [P1 — Godot draws the screen, 2026-08-28](#p1--godot-draws-the-screen-2026-08-28)
@@ -255,6 +255,7 @@ dies, which is what this file is for.
* [🔴 Correction, same day: I encoded an absence of measurement as a finding](#correction-same-day-i-encoded-an-absence-of-measurement-as-a-finding)
* [The `kind` sweep I said I owed: 15 labels, and 7 rested on a neighbour's argument](#the-kind-sweep-i-said-i-owed-15-labels-and-7-rested-on-a-neighbours-argument)
* [A refutation attempt on Q2's map of `GP_TITLE` — the count is right, the list is short](#a-refutation-attempt-on-q2s-map-of-gp_title--the-count-is-right-the-list-is-short)
* [An authored value became a measured one, and a difference-only check got an origin](#an-authored-value-became-a-measured-one-and-a-difference-only-check-got-an-origin)
<!-- /INDEX -->
## P0 — the exporter, 2026-08-28
@@ -12706,3 +12707,63 @@ off-by-three to hide. The splashes are not obscure to the contract either; the
Not a defect in the port — `publisher_logo` and `developer_logos` are exported,
named and verified against captures at RMSE 2.17 and 3.05. Reported because the
map is what the next reader will trust.
## An authored value became a measured one, and a difference-only check got an origin
The Decoder corrected their own focus delivery today: the item names in the
persistence run were **two positions out** — reported `TUTORIAL → EXTRAS →
EXTRAS`, actually `NEW GAME → TUTORIAL → TUTORIAL` — from a reader using
design-space rows against captures carrying Xenia's chrome and a 1.060 scale.
### ✅ `initial_focus` is no longer authored
**`NEW GAME` on a fresh boot, 2/2 fresh boots, both the first menu entry.**
`initial_focus_kind` moves from `authored` to `measured`.
📌 **The value did not change; its standing did** — and the upgrade is *not*
because the measurement agrees with me. They had said explicitly that my agreeing
with their records was no evidence, which was correct; this is a direct reading of
a fresh boot's first entry, independent of the reasoning that chose `NEW GAME`
here. **"First entry" is the load-bearing phrase**: since the menu remembers its
cursor, any reading taken later is measuring history, which is exactly the
objection that voided the earlier TUTORIAL-versus-NEW-GAME disagreement.
The superseded reasoning is kept under `(was)` lines rather than deleted. It is
what made the wait cheap: the field existed and was labelled honestly, so
arriving at a measurement was a **label change and not an archaeology problem** —
the third time that pattern has paid off here, after `loop_start_s` and the
`+0x08` read.
### 🔴 My anchor survived a correction it should not have been able to detect
`check_focus_persists` anchors on the **heading** — the conclusion — not on the
item names, so the correction did not break it. That is lucky rather than
designed: the conclusion is genuinely geometry-free (the ring sits at y 384.0
before the round trip and 385.5 after, an *equality* immune to a constant
offset), while the names were not. **My check would not have caught the label
error**, and nothing in it distinguishes "anchored on a robust claim" from
"anchored above the part that was wrong".
### The generalisation, and where it bit me
Their statement of it: **a control that only checks differences is blind to the
origin.** Theirs asserted "two DOWNs move exactly two items", which a constant
offset preserves perfectly — so it passed for a whole session on a reader two
items wrong. Ground truth caught it; the control could not.
🔴 **`check_splash_dwell` is that shape.** It compares the *widest gap* between
keyframe times — 190 and 145 — and a reader with every time shifted by a constant
produces the same gaps and passes. Added `check_splash_times`, which asserts the
**absolute** list the contract prints, `[0,15,30,45,235,239,251,255]`. Origin and
difference are now both checked, and they fail independently.
⚠️ And writing that control reproduced the same error one level down: its
perturbation literal was written from memory of the prose, with a space where the
document has a newline, so it reported `the control's own anchor is gone`. The
check's `\s*` had spanned the line break; the control's literal did not. **A
control written from a memory of the source rather than from the source is the
class of error these checks exist to catch.** Thirteen controls now, all firing.
❔ **EXTRAS remains unmeasured** — the run meant to settle it navigated to OPTIONS
believing it was EXTRAS, so `initial_focus: ptbtn11` stays undecided and nothing
here is built on it.