feat(ui): context- and state-aware bottom keybinding strip (#27)
Per ADR-0051 (closing issue #27): the bottom status line is now a keystrokes-only, state-selected strip. A pure status_bar_bindings() picks the binding set by priority (first match wins): sidebar focus → Ctrl-O next pane · ↑↓/PgUp/PgDn scroll · Esc input completion live → Tab/Shift-Tab cycle · Esc cancel · Enter run history nav → ↑↓ browse · Esc clear · Enter run editing → Esc clear · Ctrl-A/E home/end · Ctrl-W del word · Enter run default (empty) → Ctrl-O sidebar · Tab complete · ↑ history · Enter run The editing state surfaces the #29 readline keys (ADR-0049's deferred advertisement). Typed-command words (mode advanced/simple, the ':' one-shot) and Ctrl-C quit leave the strip; simple mode's empty-input hint gains a '`mode advanced` for SQL' pointer (advanced mode shows none — a switcher knows the way back, and help covers it). Mechanism: status_bar_bindings + a thin renderer (unit-testable); App::is_browsing_history() exposes the private history_cursor; the mode pointer lives in resolve_hint_lines. Catalog: 12 new shortcut labels + panel.hint_mode_advanced (en-US.yaml + keys.rs, validator 1:1), 5 dead strip strings removed. Forks user-chosen: editing state shows #29 keys; quit omitted; no width-drop machinery (longest strip ~65 cols fits; a width-budget test keeps it lean). Modal-aware strip is OOS (pre-existing). Tests: 9 Tier-1 unit (per-state key sets, width budget, mode pointer), 1 Tier-3 rewritten, 15 full-panel snapshots re-accepted (reviewed). 2467 pass / 0 fail / 0 skip, clippy clean.
This commit is contained in:
+11
@@ -646,6 +646,17 @@ impl App {
|
||||
}
|
||||
}
|
||||
|
||||
/// Whether the user is currently browsing a recalled history entry
|
||||
/// (Up/Down navigation, unedited). Exposes the private
|
||||
/// `history_cursor` predicate so the context-aware status strip
|
||||
/// (ADR-0051) can select its history-navigation state. Editing the
|
||||
/// recalled line ends navigation (`cancel_history_navigation`), so
|
||||
/// this is `false` again the moment the user types.
|
||||
#[must_use]
|
||||
pub const fn is_browsing_history(&self) -> bool {
|
||||
self.history_cursor.is_some()
|
||||
}
|
||||
|
||||
/// The input view the **live-feedback** walkers (completion, ambient
|
||||
/// hint, validity verdict, highlight overlays) should see, plus the
|
||||
/// byte offset stripped from the front and the cursor mapped into the
|
||||
|
||||
Reference in New Issue
Block a user