fix(overlay): fix changelog modal keyboard nav and version parsing

- Extract shared modal-focus-guard module reused by changelog and session-help modals
- Only fold the selected changelog entry on Enter/Space; leave close/refresh buttons and nested folds to their own activation
- Stop re-stealing focus after a mouse click already selected an entry
- Parse prerelease and build metadata separately in version headings (e.g. 0.15.0-rc.1+build.2)
- Resolve tray menu test assertions by label instead of index
This commit is contained in:
2026-08-05 02:48:10 -07:00
parent 3a97239ade
commit 4e8abcc25e
8 changed files with 721 additions and 261 deletions
+8 -3
View File
@@ -1,6 +1,10 @@
import type { ChangelogEntry, ChangelogItem, ChangelogSection } from '../../types/changelog';
const VERSION_HEADING = /^##\s+v(\d+\.\d+\.\d+(?:[-+][0-9A-Za-z.-]+)?)\s*(?:\(([^)]*)\))?\s*$/;
// Prerelease and build metadata are matched separately: a single `[-+]`-led
// group cannot span `-rc.1+build.2`, and an unmatched heading silently folds
// that release's notes into the previous entry.
const VERSION_HEADING =
/^##\s+v(\d+\.\d+\.\d+(?:-[0-9A-Za-z.-]+)?(?:\+[0-9A-Za-z.-]+)?)\s*(?:\(([^)]*)\))?\s*$/;
const SECTION_HEADING = /^###\s+(.+?)\s*$/;
const BULLET = /^(\s*)[-*]\s+(.*)$/;
@@ -106,8 +110,9 @@ export function parseChangelog(markdown: string): ChangelogEntry[] {
continue;
}
// A blank line ends the current bullet run; an indented non-bullet line is a
// wrapped continuation of the bullet above it.
// An indented non-bullet line continues the bullet above it, including
// across a blank line: that is CommonMark's continuation paragraph, and
// dropping the open bullets here would silently discard the text.
if (!trimmed) {
continue;
}