diff options
Diffstat (limited to 'docs')
| -rw-r--r-- | docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md | 5 | ||||
| -rw-r--r-- | docs/superpowers/specs/2026-08-20-compose-and-send-design.md | 55 |
2 files changed, 56 insertions, 4 deletions
diff --git a/docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md b/docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md index 165f96e..f01c94e 100644 --- a/docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md +++ b/docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md @@ -202,6 +202,7 @@ taking that too literally. | 130 | A message cannot be attached to another message directly | v2 | S | open, 2026-08-20, from the item 123 brainstorm. **Blocked on 123.** A `message/rfc822` part, which GMime builds natively. The manual route exists from 123's first commit: `save_message` writes the `.eml` and it is attached as a file | | 131 | The markdown dialect and extensions are fixed | v2 | S | open, 2026-08-20, from the item 123 brainstorm. **Blocked on 123.** Configurable in the shape Hugo's config uses. Deliberately fixed initially: CommonMark plus autolink, strikethrough and tasklist | | 132 | Every action must have a shortcut, and that no longer serves | policy | S | open, 2026-08-20, raised by the user during the item 123 brainstorm. `everyActionHasAShortcut` was written when the action list was short; item 123 adds six more, and each new action consumes a chord whether or not anyone would press it. Replacement is the shape `everyActionIsReachableFromAMenu()` already has: menu reachability required, shortcuts a chosen subset. **Not** done inside 123, which would confuse two changes | +| 133 | The composer shows no markdown syntax highlighting | v2 | S | open, 2026-08-20, from the item 123 brainstorm. **Blocked on 123.** A `QSyntaxHighlighter` over the composer's editor, so `**bold**` reads as bold while the buffer stays plain markdown. Standard Qt, no dependency. Deliberately after 123's formatting toolbar: agreeing with the grammar about nesting and about code spans suppressing what is inside them is the expensive part, and the toolbar is what makes the feature usable | Sizes are rough: XS under an hour, S a sitting, M a session. @@ -1029,7 +1030,9 @@ by the user's own note. The brainstorm opened items 128 to 132: an outbox, inline images, attaching a message to a message, a configurable markdown dialect, and a review of the every-action-has-a-shortcut rule. -**Size: L.** Four new units, six new actions, and one new build dependency, +**Size: L.** Four new units, six new actions, a formatting toolbar over the +markdown source (whose shortcuts live in the composer's own scope and do not +touch `KeyMap`), and one new build dependency, `cmark-gfm`. That dependency is cheap: it ships in stock Slackware (`cmark-gfm-0.29.0.gfm.13-x86_64-3`, verified 2026-08-20), so it needs a `pkg_check_modules` line here and **no** `REQUIRES` entry in the SlackBuild, diff --git a/docs/superpowers/specs/2026-08-20-compose-and-send-design.md b/docs/superpowers/specs/2026-08-20-compose-and-send-design.md index 3171280..28a025a 100644 --- a/docs/superpowers/specs/2026-08-20-compose-and-send-design.md +++ b/docs/superpowers/specs/2026-08-20-compose-and-send-design.md @@ -125,9 +125,14 @@ knowing what is actually on disk. ### The body is markdown, rendered by cmark-gfm -The editor is plain text. What is typed is markdown, and it is what the -`text/plain` part carries, unmodified. The `text/html` part is generated from -it. +The editor holds plain text and what is typed is markdown. That source is what +the `text/plain` part carries, unmodified; the `text/html` part is generated +from it. + +**Plain-text storage does not mean a bare text box.** The two are separate +decisions and it is worth stating the second explicitly, because "the editor is +plain text" reads as "you are on your own with the syntax". The composer carries +a formatting toolbar with `Ctrl+B`-style shortcuts, described below. **cmark-gfm, not a hand-written parser for a limited set.** A three-rule parser and a real markdown parser share no code, so the first is deleted entirely when @@ -164,6 +169,39 @@ markdown is a display facility whose `toHtml()` emits markup styled for `QTextEdit`, which would need unpicking before it is fit to send: the same throwaway problem one level up. +### The composer has a formatting toolbar + +Each button is a **text transformation over the markdown source**, not +rich-text editing. Nothing about the buffer changes: it stays markdown that the +user can also type by hand. + +| Button | Wraps in | Shortcut | +|---|---|---| +| Bold | `**` | `Ctrl+B` | +| Italic | `*` | `Ctrl+I` | +| Code | `` ` `` | `Ctrl+`` ` `` | +| Strikethrough | `~~` | none | +| Link | `[text](url)` | `Ctrl+K` | +| Quote | `> ` per line | none | + +**Selection-aware.** With a selection, the tokens wrap it and the selection is +preserved. With none, the pair is inserted with the cursor between them, so +typing continues inside. Quote is line-based rather than a wrap, applying to +every line the selection touches. + +**These shortcuts do not touch `KeyMap`.** They belong to the composer window, +which is a separate shortcut scope, so `Ctrl+B` here does not consume `Ctrl+B` +from the main window's map and does not participate in the +every-action-has-a-shortcut rule. Keeping the two namespaces apart matters for +item 132. + +**No live syntax highlighting** in this design. A `QSyntaxHighlighter` colouring +`**bold**` in the editor is standard Qt and needs no dependency, but it has to +agree with the markdown grammar about nesting and about code spans suppressing +what is inside them, which is the sort of thing that looks nearly right and +stays annoying for years. It is a follow-up, better judged after living with the +toolbar. + ### Whether the HTML part is sent is per-message `sendHtml` decides whether the message is `multipart/alternative` (plain + @@ -511,6 +549,12 @@ and it is pure logic, so it is tested apart from the window. All five of the user's addresses stripped from a reply-all; every account-resolution rule including the multi-maildir ambiguity; subject prefixing. +**The formatting toolbar** is tested through its transformations, not through +the widget: wrap with a selection, insert with none, quote applying per line, +and the cursor landing between the tokens in the empty-selection case. That last +one is the property a user notices immediately when it is wrong, and it is +invisible to a test that only compares the resulting text. + **In `test_mainwindow`**: action enablement against a receive-only account, the ribbon appearing, and `everyActionIsReachableFromAMenu()` covering the six new actions for free. `WorkerBackedWindow` gains a knob for writing an account @@ -536,6 +580,11 @@ Deliberately out of scope here, each worth its own backlog entry. `save_message` exists from the first commit. - **Configurable markdown dialect and extensions**, in the shape Hugo's configuration uses. +- **Live markdown syntax highlighting in the composer.** A + `QSyntaxHighlighter` over the editor, so `**bold**` reads as bold while the + buffer stays plain markdown. Deliberately after the toolbar: the grammar + agreement it needs is the expensive part, and the toolbar is what makes the + feature usable. - **Review "every action has a shortcut".** `everyActionHasAShortcut` was written when the action list was short. Six more actions takes the count past the point where a chord for everything is useful, and each new action consumes |
