keys: passwords, titles and names without the pointer

A keystore or encrypted key asks for its password as soon as it is
opened, asks again after a wrong one, and Enter on the file pane asks
once more after Escape — the button was the only way in before. Enter on
a sealed file opens the vault the same way.

`:name` on its own, while writing, moves up into the title, and Enter,
Escape, Down or Tab there goes back into the text; the title could not be
reached from the editor at all. `R` starts the command line from the
current name — of the row, the open document, the card or the list —
instead of an empty one.

`s` on a shared document and `y` both ask y/N before they cut readers
off: y is what a vim hand presses to yank, and it retired the live link
without a word.
This commit is contained in:
nvrl committed 2026-10-20 13:44:37 +02:00
1 parent 4bf8634991
commit 007fb1d3e3
7 files changed
+109 -27

No files matched your search

+22 -2
View File
@@ -20,6 +20,24 @@
let reader = $state<HTMLElement>()
let article = $state<HTMLElement>()
let title = $state<HTMLInputElement>()
// `:name` with nothing after it, while writing: up into the title.
$effect(() => {
const field = title
if (!field) return
// A turn later: vim gives the focus back to the text once its `:` line
// has run, and that would land after this.
const focus = () =>
setTimeout(() => {
field.focus()
field.select()
})
hooks.focusTitle = focus
return () => {
if (hooks.focusTitle === focus) hooks.focusTitle = () => {}
}
})
/*
* j/k reach this pane through the window handler in App.svelte, which has no
@@ -138,13 +156,15 @@
{#if workspace.editing}
<input
class="title"
bind:this={title}
placeholder="Untitled"
bind:value={workspace.draft.name}
oninput={() => workspace.touch()}
onkeydown={(event) => {
if (event.key === 'Enter') {
// The title is the line above the text: any of these goes back down.
if (['Enter', 'Escape', 'ArrowDown', 'Tab'].includes(event.key) && !event.shiftKey) {
event.preventDefault()
document.querySelector<HTMLElement>('.cm-content')?.focus()
hooks.focusEditor()
}
}}
/>