Repository navigation
Match REPL colours, pane surfaces and drawers to the reference (#881, 1/3) - #885
Merged
Merged
Conversation
XMD source and JSON keep their own colours wherever this screen shows them verbatim, panes and drawers have surfaces of their own, and a drawer says where the reading behind it stops. A row whose characters mean different things now carries immutable token runs: plain view data, issued by the composition module, concatenating to exactly the text the row draws. The ops builder emits one text operation per run inside the one element the row was measured as, so a row reading as several things is still one node, one bound and one pointer target. A private `presentation-text.ts` says what the characters of the two readings this screen shows verbatim are — executable Markdown source and a serialized JSON value — one line at a time, classifying nothing it was not handed. It validates nothing, evaluates nothing and rewrites nothing, and JSON is classified from a value this product already parsed rather than from a guess about arbitrary text. Focus no longer repaints a row. It adds weight, and the cue in front of the row is the one run the focus colour belongs to, so the row a keystroke reaches stays readable as the thing it is while selection keeps its own surface. The application paints its own uncovered area, a question or permission drawer is named in the waiting accent, a field's name and the value in it are told apart, and the contextual drawer is bounded by a rule along the top of its rectangle and inset one cell on each side. Both belong to the measured rectangle: the content window is measured at what they leave, which costs that window one row and two columns at every profile and is why UI16 and UI17 now reach `[submit]` and the validation row through one `[v later]`.
The engine wraps each text operation on its own, and a row is one cell tall: several stretches whose total is wider than the element each show their own first line and leave the cells their remainder went to blank. A 400-column generated tag in a 118-column drawer came out with its quoted values missing — found by capturing the gallery, which the focused tests could not reach because every example in them fits. A row carries its stretches only when the element it was measured in holds them whole, read off the constraint the element was opened with. A row the engine must wrap is drawn as the one thing it is, which is the reading this screen has always shown. The regression commits a tag far wider than any supported drawer and holds every written cell to being the next character of the source.
Planner feedback on f0b8eb1: three frozen requirements were unmet. **R1.** An overflowing row went through a single-colour fallback, so the Plan preview read as ordinary source and, at 72×20, a populated field painted its visible value as though it were the field's name. The fallback existed because the engine wraps each text operation on its own. The stretches are now cut at the room the element has instead: nothing wraps, every character the row can show keeps the role it has and the order it was in, and the cue in front of a focused row is still the one cyan thing. A row whose width the flow decides — only the pass that is asking what the widths are draws one — is unchanged. The overflow regression now asserts the delimiter, tag, attribute, quoted value, reference and prose roles on the overflowing row itself, that no row is one colour throughout, and that the narrow populated form keeps its field's name and its value apart. The gallery audit no longer accepts a tag drawn as one stretch. **R2.** The new assertions read expected RGB from the production palette, which would have stayed green through a palette drift. They now read a fixture transcribed from the corrected Terminal Interface archive — its `S`, `C` and `Y` constants, with the archive hash and the sources they came from — so the two sides of every comparison are independent. Changing one palette entry by a single bit now fails three rows. **R3.** The frozen resize endpoints are taken with the populated project question open, so the refusal and the recovery prove the editable question and its values survive, rather than substituting the permission drawer.
This was referenced Oct 10, 2026
taras
added this pull request to stack #888
October 10, 2026 02:32
taras
marked this pull request as ready for review
October 10, 2026 02:40
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Stack 1/3 — followed by #886 and #887. Merge bottom-up.
Why
The REPL’s flat colours and weak pane/drawer separation obscure the hierarchy in the original Terminal Interface reference. This is slice 1 of #881: colours, surfaces and drawers.
What changes
Before: a row has one text colour, focus can overwrite semantic emphasis, and drawers have little separation from the reading behind them.
After: source and JSON characters carry their semantic colours, including overflowing rows; focus adds weight and a cyan cue. Pane backgrounds, the gold drawer rule and inset, waiting-accent titles, and distinct field names/values follow the reference.
How it works
Immutable private token runs travel with a row’s plain view data. Layout emits bounded text operations inside the same measured element, retaining one node and one target per row. XMD/JSON classification changes presentation without validating or rewriting the text.
Review guide
Start with
packages/cli/src/repl/description.ts,presentation-text.tsandpresentation-style.ts; then review run clipping inlayout.ts, drawer surfaces inapplication.ts, andrepl-presentation-style.test.ts.What must stay true
How to verify it
Focused feedback at accepted
080b6ec80ca74e614789e8d2252857ac281df7e5:deno task test packages/cli/tests/repl-presentation-style.test.ts packages/cli/tests/repl-layout-admission.test.ts packages/cli/tests/repl-forms.test.ts28 tests / 105 steps passed; whitespace gate passed. All 35 production/reference pairs were independently opened; five mutation controls fail their named assertions and restore source bytes.
Scope
Includes private token-run presentation, pane/drawer styling, the independent reference fixture and affected screen-reading assertions. Lifecycle, generated-source restructuring and History belong to the dependent slices.
Risks and limitations
The measured drawer rule costs one visible row; the existing later-window control preserves access to submit and validation. This publication uses the existing integration commit
c7d54769d56661bef38cee8549b148f3bf87a904, which mechanically merges accepted PR 1 with main4c0414be1010f69f11bff0d1d634623a5b08f886; no new product change or commit is introduced. The integrated stack was reviewed in PR 2 and PR 3.Draft publication only: delivery verification and required merge gates remain outstanding. The local visual packet and Planner acceptance are retained under
.reviewer/issue-881/; no public evidence attachment is claimed.Scope confirmation