- #456 Copy pass: sentence case for every setting title and section,
plainer names ("Hide joins and leaves", "Link previews", "Emoji
style: Twemoji", "Rejoin calls after a restart", "Also use the
browser's noise suppression", "Push-to-talk key"...) and grammar fixes
("when messages arrive", "Play a sound when a new message arrives",
blocked users "Enter their Matrix ID"). Labels only: no setting is
renamed in storage.
- #455 One theme control: Theme: System / Light / Dark. System shows the
light and dark variant pickers, Light or Dark one picker of that kind.
Replaces the System switch plus a Theme dropdown that was greyed out
whenever the switch was on. Uses the existing settings (no migration);
picking a variant also remembers it for System.
- #457 Remove the "Block Messages" stub from Notifications; the GIF
picker row only appears in builds with a GIF key.
- #458 (part 1) "Export/Import Messages Data" -> "Export/Import
encryption keys", with a sentence on when you need it.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017PCb59uY3UKqDqt7B6hzd5
SecurityBanner asked pickBanner whether another strip would show without
the dismissed set, so a dismissed Kuma announcement (often pinned for
weeks) still counted and suppressed the verify / backup nudge on every
device that had dismissed it. The dismissed set is now a shared jotai
atom (still persisted to localStorage) used by both banners. Adds a
Playwright regression.
Fixes#307
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017PCb59uY3UKqDqt7B6hzd5
One "security" strip, in the same top slot and style as the status banner
(#124), for this device, in priority order:
- "Verify this device" — cross-signing exists but this device isn't
verified (can't unlock backed-up history, untrusted to others). First,
because verifying with the recovery key also connects the backup.
- "Connect this device to your key backup" — a backup exists, this device
isn't using it.
- "Set up key backup" — no backup at all (includes accounts without
cross-signing; the setup flow does both).
The button opens Settings → Devices (existing flows); "Not now" snoozes.
Rules: nothing in a device's first 24 h; "Not now" snoozes that nudge 7
days; 3 dismissals stop it; never on a healthy device; waits until sync
has settled (never under "Connecting…"); outage/maintenance/connection
strips win. Per-device record in localStorage, wiped on logout. Mounted
inside the Matrix client context and an error boundary (an early version
outside the context crashed the app on load — caught before pushing).
Also: the status strip wraps its text on phones instead of truncating it
when there's no Details button (benefits #124's strips too).
Design approved on #123 (real-client screenshots there). Tests: 4 unit
(the #123 state table, loading, timing, stored record); e2e: nothing during
the grace period, "Set up key backup" → Settings → Devices, "Not now"
holds across a reload. Unit 1319, Playwright 29 passed.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01PPmy3tPq869XDW4njjVaKA