mirror of
https://github.com/backnotprop/plannotator.git
synced 2026-09-14 14:17:26 +08:00
1d30b973c4
* feat(editor): Mod+E toggles markdown edit mode in place (#1479) * fix(editor): scope the edit-mode exit chord and wire its tests into CI - Early-return the dedicated Mod+E exit listener when the event target is an INPUT/TEXTAREA outside .cm-editor, so native text fields (Ask AI box, annotation textareas) keep their own Mod+E instead of committing and exiting the edit session underneath them; match the key case-insensitively so Caps Lock cannot dead-key the exit. CodeMirror's content DOM is contenteditable, so the editor path is untouched. Also note in code that mounting atomic-editor's selectionToolbar() would claim Mod-e and dead-key the chord. - New DOM test pinning the ownership split (foreign textarea keeps the session open; the chord from inside CodeMirror still exits), revert-verified against the guard. - De-flake "never discards an unsaved source-backed buffer silently": the single setTimeout(0) after a contentEditable DOM mutation raced CodeMirror's MutationObserver, which happy-dom intermittently never re-delivers after CM's stop()/start() observer cycling — the buffer is now dirtied through the editor's own dispatch, with a bounded poll for the toolstrip's Save readout. 8/8 stable under CI's exact invocation preceded by another App suite (previously ~3/8 failures). - Add App.editModeShortcut.test.tsx to the DOM-gated file enumeration in .github/workflows/test.yml so the suite actually runs in CI. --------- Co-authored-by: Michael Ramos <mdramos8@gmail.com>
31 lines
1.4 KiB
TypeScript
31 lines
1.4 KiB
TypeScript
/**
|
|
* Which element a markdown edit session's scroll offset actually lives on.
|
|
*
|
|
* The Viewer ↔ MarkdownEditor swap replaces the document area's children, and a
|
|
* real browser clamps the scroll container to the top the moment the old subtree
|
|
* leaves it — that is the jump #1479 reports. Carrying the offset across the
|
|
* swap needs the right target, and the target depends on the shell:
|
|
*
|
|
* - The desktop layout leaves the editor unbounded, so CodeMirror grows to
|
|
* full content height inside the document viewport: the VIEWPORT scrolls and
|
|
* `.cm-scroller` never overflows (restoring into it is a silent no-op).
|
|
* - A height-bounded shell (compact touch) bounds the editor, so CodeMirror
|
|
* scrolls itself and `.cm-scroller` is the scroller.
|
|
*
|
|
* Resolve the element that can actually scroll when the offset is READ (before
|
|
* the swap): the surface on screen has settled by then, so its overflow test is
|
|
* trustworthy. Restoring is deliberately not routed through this test — the
|
|
* surface that just mounted has no reliable measurement yet; see the restore
|
|
* effect in `App.tsx`.
|
|
*/
|
|
export function scrollableEditSurface(
|
|
editorScroller: HTMLElement | null,
|
|
documentViewport: HTMLElement | null,
|
|
isEditing: boolean,
|
|
): HTMLElement | null {
|
|
if (isEditing && editorScroller && editorScroller.scrollHeight > editorScroller.clientHeight) {
|
|
return editorScroller;
|
|
}
|
|
return documentViewport;
|
|
}
|