Contribute rewrite Phase 4: §8.10 gutter accent in CM6 raw pane
Restores the §8.10 paragraph-margin marker layer Phase 1 dropped when
Tiptap left, this time against the CM6 raw pane on the left half of
the Contribute split. The matching inline tracked-insert/tracked-
delete overlay Phase 3 shipped lives on the preview pane to the
right; the two visual layers answer different questions on the two
halves of the split — "did anything change in this region?" (gutter,
amber, scannable) vs. "what changed here?" (inline, green/red,
precise) — and are deliberately separate signals.
New file: frontend/src/components/diffGutterExtension.js. The
extension exposes a `setBaseline` StateEffect and a gutter that marks
every line whose text differs from the same-indexed line of the
baseline (the last server-confirmed branch body). Per-line, not
paragraph-block — CM6's natural unit; collapsing to paragraph ranges
is more spec-faithful but adds code, and the per-line stance is the
pre-fancy default. A TODO is left for a future paragraph-collapse
pass if the result reads noisy.
MarkdownSourceEditor.jsx changes:
- Install the gutter extension in the editor's extension list.
- Seed the baseline to `initialDoc` at construct time.
- In the existing `initialDoc`-watching effect, dispatch the doc
replacement AND a `setBaseline` effect in the SAME transaction so
there's no one-frame window where the new doc reads as "divergent"
against the old baseline. This carries through every server-
confirmed branch refresh that RFCView already wires (accept,
decline, manual flush, branch switch); no RFCView changes needed
because all four paths already re-push `initialDoc` after pulling
fresh state.
Design calls per the Phase 4 prompt's open list:
• Per-line marks, not paragraph-block ranges. Pre-fancy stance.
• Amber (#f59e0b) thin 3px vertical bar, distinct from the
preview pane's green-on-light / red-on-light tracked-change
inline overlay. Reads as "in-flight / not yet on the server."
• Baseline reset on every branchView refresh (accept / decline /
manual flush / branch switch), matching RFCView's existing
originalSourceLinesRef discipline. Gutter then reads as "what's
in the buffer but not on the server."
• No hover / no click. The inline overlay already carries the
click-to-card binding; the gutter is scannable only.
Known caveats kept deliberately:
• Insert/delete shifts. Adding a line in the middle shifts every
subsequent line's index and the naive compare lights up
everything below — tolerated as the honest "you've touched
stuff below this point" cue. A future LCS-anchored pass could
fix it; Phase 4 doesn't need to.
SPEC §8.10:
- First paragraph rewritten to name the CM6 raw pane as the gutter's
home and replace the stale "ProseMirror plugin" wording with the
CodeMirror gutter framing. Mirrors how Phase 3 named the preview
pane as the inline overlay's home.
- DiffView retirement paragraph adjusted: gutter and inline overlay
together (across the split) cover its review affordance, not
"both layers in the same surface" — the layers are deliberately on
different surfaces.
Verification:
- Vite preview sandbox eval — standalone CM6 mount, dispatch tests
across construct (no marks on identity), per-line edit (mark on
exactly the touched line, confirmed by Y-coordinate matching the
line-number gutter element), baseline reset clears, atomic
doc+baseline dispatch leaves zero marks (the RFCView accept-flow
path), insert-in-middle exhibits the expected cascade, and
computed-style proof for the amber bar (`#f59e0b`, 3px wide,
positioned left of the line-numbers gutter at x=21 vs x=24).
- Screenshot captures the bar on the touched line only.
- 125 backend integration tests still green.
- Live RFCView accept → branch refresh → gutter clear flow against a
real branch was not driven (backend not running this session,
carrying forward Phase 2/3's verification gap). The sandbox-level
proof covers the atomic dispatch correctness; the next session
with a backend up should drive that golden path before piling
Phase 5 work on top.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -829,18 +829,20 @@ declined predecessor still visible.
|
||||
|
||||
### 8.10 Tracked-change markup and the review-mode toggle
|
||||
|
||||
Two visual layers carry change information in the editor. The first
|
||||
is a paragraph-margin marker — a thin gutter accent on any paragraph
|
||||
that differs from the branch's open-session baseline, rendered by a
|
||||
ProseMirror plugin against a baseline snapshot taken when the editor
|
||||
opens. The second is inline `tracked-delete` / `tracked-insert`
|
||||
markup at the exact range of an accepted change, with the deleted
|
||||
text shown struck-through and the inserted text shown in an additive
|
||||
Two visual layers carry change information in the Contribute split.
|
||||
The first is a paragraph-margin marker on the left raw-source pane —
|
||||
a thin gutter accent on any line that differs from the branch's
|
||||
open-session baseline, rendered by a CodeMirror gutter extension
|
||||
against a baseline reset on every server-confirmed branch refresh
|
||||
(accept, decline, manual flush, branch switch). The second is inline
|
||||
`tracked-delete` / `tracked-insert` markup on the right preview pane
|
||||
at the exact range of an accepted change, with the deleted text
|
||||
shown struck-through and the inserted text shown in an additive
|
||||
style; both carry the change's ID via a data attribute, enabling the
|
||||
click-to-card binding from §8.8. The margin marker is scannable
|
||||
("did anything change in this region?"); the inline markup is
|
||||
precise ("what changed here?"). The two answer different questions
|
||||
and both are kept.
|
||||
on the two halves of the split and both are kept.
|
||||
|
||||
The inline markup lives in the rendered preview surface, not on the
|
||||
writable editor. With the Contribute-mode split (§8.3) the raw markdown
|
||||
@@ -865,10 +867,9 @@ selection-quote that drove the change, and the AI's `reason`.
|
||||
DiffView is the legacy read-only render surface invoked via the
|
||||
Contribute-mode toolbar toggle (§8.15) — a full-editor swap-in that
|
||||
reads the same `changes` table. It is retained as an interim path while
|
||||
the preview-pane overlay matures and is slated for retirement once
|
||||
gutter markers (the §8.10 paragraph-margin layer) land in the preview
|
||||
itself; at that point both visual layers live in the same surface and
|
||||
the toolbar toggle collapses.
|
||||
the split-pane layers mature, and is slated for retirement once
|
||||
the raw-pane gutter and the preview-pane inline overlay together cover
|
||||
its review affordance; at that point the toolbar toggle collapses.
|
||||
|
||||
### 8.11 Manual edits and collisions with AI proposals
|
||||
|
||||
|
||||
Reference in New Issue
Block a user