Reader mode — the focus overlay (plan)
Status: draft — recorded 2026-06-14 (Fritz). Next-session candidate. Fritz: "I really like the layout, it keeps the context nicely. One thing that would help: a quick reader mode that overlays in the middle the document you want to focus on" — since the trail has multiple columns, sometimes you want to sink into one document.
One-line
A reader overlay: the focused document rendered centered, at a comfortable measure, over the dimmed trail — context preserved behind it, one click (or Back) to return. A lens over the trail, NOT a new pane: the reasoning chain is untouched; you're just reading one link of it up close.
Why it fits the room
The trail's whole thesis is "context is spatial, never amputated." Reader mode
honors that: the columns stay on screen, dimmed — you can see where you are,
you just zoom your attention. It's the opposite of a modal that hides
everything; the context is still there, deliberately. Complements focus
(which pane gets the margin + live read) with a deeper "solo read" lens.
THE design decision: reader is URL state, not client state (ADR 0003)
Reader mode is a query param on the trail URL — /t/<trail>?reader=<paneIndex>
(0-based; omitted ⇒ no overlay; out of range ⇒ ignored). Consequences, all the
htmx-hard wins the trail already banks:
- Shareable: a link can say "here's the chain, start by reading pane 2."
- Browser Back closes it — temporal history over spatial state, free, no JS.
- Zero client state — the whole overlay renders server-side from the URL.
- Coexists with
?focus=(reader implies attention on that pane; keep both or fold focus into reader — settle when building).
Render
- The full canvas renders as today, with a dimmed backdrop layer over it.
- A centered reader panel renders the pane's already-fetched Document at the Tufte reading measure (≈60ch body + margin), so it's the same prose the column shows, just unconstrained by column width and centered.
- No extra world read: reader shows the Document already fetched for that pane (focused-live or cached) — the overlay is pure presentation.
- Margin stays (status, tags, provenance, backlinks, graph/edit/new/append affordances): reading mode is not a dead-end — you can still branch and act. Possibly collapsible; default shown (the trust layer is the point).
- SSR + CSS only; ADR 0003's canvas island stays unspent. Degrades: no CSS ⇒ the doc just renders after the canvas; no JS ⇒ close via the link / Back.
Affordance + close
- Each pane (header/spine) gets a "reader" control → link to
trailURL?reader=<i>. - Close: an explicit ✕ AND the backdrop itself are
<a>links back to the bare trail URL (no reader param). Optional Esc-to-close via a one-line _hyperscript snippet (an ADR 0003-sanctioned tiny concession) — or rely on Back. Recommend the snippet; it's the expected reader-mode gesture.
Load-bearing UX decision: does reader persist across link clicks?
- RECOMMENDED — persist: a link clicked inside the reader continues the
trail AND stays in reader on the newly-focused pane (read straight through the
argument without surfacing). Implemented by the reader panel's links using
trailAfterClickthen settingreader=<new focus index>. This is the feature's whole point ("focus on the document you want," then the next). - Alternative (simpler v1): links exit reader to the canvas, focused on the new pane. Less magical; falls out for free. Decide with Fritz; recommend persist.
Architecture (web-only — no port/service/domain change)
trail.go: parse thereaderquery param into thetrailstruct (e.g.Reader int, -1 = none);trailURLoptionally encodes it; a helper builds the reader/close links. The codec stays the single source of truth.trail_handlers.go: whenReaderis set and in range, render the canvas plus the reader-overlay view model (reuse the focused pane's Document; for persist-on-navigate, rewrite the reader panel's links to carry the new reader index).- Templates: a
readeroverlay block (backdrop + centered panel reusing the doc-body + doc-meta partials). CSS: backdrop, centered panel, dim. - Restrict to prose panes (doc/listing/tag); a floor/graph pane in reader is just a bigger SVG — allow later if wanted, not v1.
Tests
Codec round-trip with ?reader=; overlay renders the addressed pane; ✕/backdrop
link back to the bare trail; persist-on-navigate link rewriting; out-of-range
ignored; no-reader URL renders exactly today's canvas (no regression);
auth-gated affordances still present in the reader margin.
Scope / non-goals
- A presentation lens, not a pane kind — the trail path never changes.
- No client zoom/pan, no JS reader engine (htmx + CSS + at most a 1-line Esc hyperscript).
- Doc/listing/tag panes only for v1.
Open before building (settle with Fritz)
- Persist-on-navigate vs exit-on-navigate (recommend persist).
?reader=as its own param vs foldingfocusinto it.- Esc-to-close hyperscript vs Back-only.
- Margin shown vs collapsible in reader.
This is a self-contained next-session feature: web-layer only, no new reads, no broker/deploy coupling. Slots into the Reading Room family as "R4 — reader mode."