feat: Cursor in einer Beschreibung wählt ihren Knoten aus

Bisher fiel die Hervorhebung weg, sobald der Cursor von der Knotenzeile auf die
`"`-Zeile darunter rückte: Die trägt keinen Knoten, also fand die Zeilensuche
nichts. Falsche Auskunft — sie trägt keinen EIGENEN Knoten, gehört aber zu
einem, und wer in ihr schreibt, arbeitet an genau diesem.

Gilt für beide Formen, nicht nur die Kurzform: Die Zuordnung entsteht an
derselben Stelle im Parser, an der auch die `---`-Blöcke landen, und dort trägt
die Begründung sogar weiter — der Langtext steht am Dateiende, weit weg von
seinem Knoten. Zugeordnet werden Textzeilen, Block-Kopfzeile (sie nennt den
Knoten) und Leerzeilen innerhalb eines Blocks; nicht der `---`-Trenner und
nichts unter unbekannter ID.

`node.descLines` entsteht im Parser, der Renderer gibt sie als
`data-desc-lines="3 4 5"` aus, app.js trifft sie per `[data-desc-lines~="N"]`.
Bewusst getrennt von `descLines` (dem Text): Dort fallen Leerzeilen zu einem
Absatztrenner zusammen und Blocktext unter unbekannter ID kommt gar nicht an.

Beide Richtungen gehen jetzt über eine Auflösung (`nodeOfLine()`) — sonst wäre
der ausdrückliche Alt+Klick aus einer Beschreibung heraus stumm geblieben, und
das ist gerade der Ort, an dem man ihn braucht.

5 neue Tests (204 gesamt). SPEC §9 und D40 (Nachtrag 2) nachgezogen.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
mhoennig
2026-08-23 08:01:56 +02:00
co-authored by Claude Fable 5
parent e223734d58
commit 24a70ca49e
7 changed files with 122 additions and 13 deletions
+4
View File
@@ -208,6 +208,10 @@ verworfene Elemente. Quelle sind ES-Module unter `src/`; `index.html` ist der
Zeilenhöhe × n scheitert an weichen Umbrüchen. Ausgelöst per Alt+Klick,
Alt+Enter und langem Druck; der Klick-Handler **muss `preventDefault()`** rufen,
sonst lädt Alt+Klick auf einen Link-Knoten das Ziel herunter. Gegenrichtung:
Welcher Knoten zu einer Zeile gehört, entscheidet **eine** Stelle:
`nodeOfLine()` — erst `data-line`, sonst `data-desc-lines~=` (Cursor in einer
Beschreibung wählt ihren Knoten, D40-Nachtrag 2). Beide Richtungen gehen
darüber; wer eine neue Zeilensuche schreibt, nimmt sie ebenfalls.
`syncCaret()` setzt die Klasse `current` auf den Knoten der Cursor-Zeile;
`render()` stellt sie nach jedem Neubau wieder her (ohne zu scrollen). Die
CSS-Regel braucht den `#out`-Präfix (`ul.or .node{box-shadow:none}` ist