diff options
| author | Can Celik <ogulcancelik@gmail.com> | 2026-08-01 04:27:50 +0300 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2026-08-01 04:27:50 +0300 |
| commit | b76adc155d979705a353fd6dc87c702f9dfc6c22 (patch) | |
| tree | f613254e0cfbfd2b4450a6a5f3ee7c0ba8136976 /src/app/input/navigate.rs | |
| parent | 8d190eddda2c74afa3dc043f8ec8020ffd7b5a94 (diff) | |
fix(input): preserve native key lifecycle across routing (#2142)
refs #2077
Co-authored-by: Jonathan Liebig <jonathan.liebig@gmail.com>
Diffstat (limited to 'src/app/input/navigate.rs')
| -rw-r--r-- | src/app/input/navigate.rs | 75 |
1 files changed, 40 insertions, 35 deletions
diff --git a/src/app/input/navigate.rs b/src/app/input/navigate.rs index 93dfe77d..6d0f7f22 100644 --- a/src/app/input/navigate.rs +++ b/src/app/input/navigate.rs @@ -31,14 +31,14 @@ pub(crate) fn terminal_direct_navigation_action( pub(crate) fn terminal_direct_non_indexed_navigation_action( state: &AppState, - key: TerminalKey, + key: &TerminalKey, ) -> Option<NavigateAction> { non_indexed_action_for_key(state, key, BindingDispatch::Direct) } pub(crate) fn terminal_direct_indexed_navigation_action( state: &AppState, - key: TerminalKey, + key: &TerminalKey, ) -> Option<NavigateAction> { indexed_navigation_action(state, key, BindingDispatch::Direct) } @@ -65,7 +65,7 @@ impl App { return; } - if self.state.is_prefix_key(raw_key) { + if self.state.is_prefix_key(&raw_key) { if self.state.copy_mode_pane_is_focused() { self.state.cancel_copy_mode(&self.terminal_runtimes); } @@ -81,20 +81,20 @@ impl App { } if let Some(action) = - non_indexed_action_for_key(&self.state, raw_key, BindingDispatch::Prefix) + non_indexed_action_for_key(&self.state, &raw_key, BindingDispatch::Prefix) { self.execute_prefix_key_action(action); return; } - if let Some(binding) = command_for_key(&self.state, raw_key, BindingDispatch::Prefix) { + if let Some(binding) = command_for_key(&self.state, &raw_key, BindingDispatch::Prefix) { self.cancel_copy_mode_if_active(); self.launch_custom_command(binding, ActionContext::Prefix); return; } if let Some(action) = - indexed_navigation_action(&self.state, raw_key, BindingDispatch::Prefix) + indexed_navigation_action(&self.state, &raw_key, BindingDispatch::Prefix) { self.execute_prefix_key_action(action); return; @@ -128,7 +128,7 @@ impl App { let key = raw_key.as_key_event(); self.state.update_dismissed = true; - if key.code == KeyCode::Esc || self.state.is_prefix_key(raw_key) { + if key.code == KeyCode::Esc || self.state.is_prefix_key(&raw_key) { leave_navigate_mode(&mut self.state); return; } @@ -138,7 +138,7 @@ impl App { .keybinds .navigate .workspace_up - .matches_direct_key(raw_key) + .matches_direct_key(&raw_key) { self.state.move_selected_workspace_by_visible_delta(-1); return; @@ -148,18 +148,18 @@ impl App { .keybinds .navigate .workspace_down - .matches_direct_key(raw_key) + .matches_direct_key(&raw_key) { self.state.move_selected_workspace_by_visible_delta(1); return; } - if let Some(action) = navigate_reserved_action_for_key(&self.state, raw_key) { + if let Some(action) = navigate_reserved_action_for_key(&self.state, &raw_key) { self.execute_tui_navigate_action(action, ActionContext::Navigate); return; } - if let Some(action) = navigate_mode_non_indexed_action_for_key(&self.state, raw_key) { + if let Some(action) = navigate_mode_non_indexed_action_for_key(&self.state, &raw_key) { if action == NavigateAction::EditScrollback { self.launch_focused_scrollback_editor(); } else { @@ -169,12 +169,12 @@ impl App { return; } - if let Some(binding) = command_for_key(&self.state, raw_key, BindingDispatch::Prefix) { + if let Some(binding) = command_for_key(&self.state, &raw_key, BindingDispatch::Prefix) { self.launch_custom_command(binding, ActionContext::Navigate); return; } - if let Some(action) = navigate_mode_indexed_action_for_key(&self.state, raw_key) { + if let Some(action) = navigate_mode_indexed_action_for_key(&self.state, &raw_key) { self.execute_tui_navigate_action(action, ActionContext::Navigate); self.selection_autoscroll_deadline = None; } @@ -773,7 +773,7 @@ impl App { return false; }; - let bytes = rt.encode_terminal_key(key); + let bytes = rt.encode_terminal_key(key.clone()); if bytes.is_empty() || rt.try_send_bytes(Bytes::from(bytes)).is_err() { return false; } @@ -1136,7 +1136,7 @@ pub(crate) enum BindingDispatch { pub(crate) fn command_for_key( state: &AppState, - key: TerminalKey, + key: &TerminalKey, dispatch: BindingDispatch, ) -> Option<crate::config::CustomCommandKeybind> { state @@ -1150,7 +1150,7 @@ pub(crate) fn command_for_key( .cloned() } -fn unmodified_digit_for_key(key: TerminalKey) -> Option<char> { +fn unmodified_digit_for_key(key: &TerminalKey) -> Option<char> { ('1'..='9').find(|digit| { crate::config::terminal_key_matches_combo( key, @@ -1164,7 +1164,7 @@ fn unmodified_digit_for_key(key: TerminalKey) -> Option<char> { #[cfg(test)] pub(super) fn handle_navigate_reserved_key(state: &mut AppState, key: TerminalKey) -> bool { - if let Some(c) = unmodified_digit_for_key(key) { + if let Some(c) = unmodified_digit_for_key(&key) { let idx = (c as usize) - ('1' as usize); if let Some(ws_idx) = state.workspace_at_visible_position(idx) { state.switch_workspace(ws_idx); @@ -1203,7 +1203,12 @@ pub(super) fn handle_navigate_reserved_key(state: &mut AppState, key: TerminalKe } } - if state.keybinds.navigate.workspace_up.matches_direct_key(key) { + if state + .keybinds + .navigate + .workspace_up + .matches_direct_key(&key) + { state.move_selected_workspace_by_visible_delta(-1); return true; } @@ -1211,24 +1216,24 @@ pub(super) fn handle_navigate_reserved_key(state: &mut AppState, key: TerminalKe .keybinds .navigate .workspace_down - .matches_direct_key(key) + .matches_direct_key(&key) { state.move_selected_workspace_by_visible_delta(1); return true; } - if state.keybinds.navigate.pane_left.matches_direct_key(key) { + if state.keybinds.navigate.pane_left.matches_direct_key(&key) { state.navigate_pane(NavDirection::Left); return true; } - if state.keybinds.navigate.pane_down.matches_direct_key(key) { + if state.keybinds.navigate.pane_down.matches_direct_key(&key) { state.navigate_pane(NavDirection::Down); return true; } - if state.keybinds.navigate.pane_up.matches_direct_key(key) { + if state.keybinds.navigate.pane_up.matches_direct_key(&key) { state.navigate_pane(NavDirection::Up); return true; } - if state.keybinds.navigate.pane_right.matches_direct_key(key) { + if state.keybinds.navigate.pane_right.matches_direct_key(&key) { state.navigate_pane(NavDirection::Right); return true; } @@ -1236,7 +1241,7 @@ pub(super) fn handle_navigate_reserved_key(state: &mut AppState, key: TerminalKe false } -fn navigate_reserved_action_for_key(state: &AppState, key: TerminalKey) -> Option<NavigateAction> { +fn navigate_reserved_action_for_key(state: &AppState, key: &TerminalKey) -> Option<NavigateAction> { if let Some(c) = unmodified_digit_for_key(key) { return Some(NavigateAction::SwitchWorkspace( (c as usize) - ('1' as usize), @@ -1303,12 +1308,12 @@ pub(crate) fn handle_navigate_key(state: &mut AppState, key: KeyEvent) { state.update_dismissed = true; let terminal_key = TerminalKey::from(key); - if state.is_prefix_key(terminal_key) || key.code == KeyCode::Esc { + if state.is_prefix_key(&terminal_key) || key.code == KeyCode::Esc { leave_navigate_mode(state); return; } - if handle_navigate_reserved_key(state, terminal_key) { + if handle_navigate_reserved_key(state, terminal_key.clone()) { return; } @@ -1396,7 +1401,7 @@ fn copy_mode_survives_prefix_action(action: NavigateAction) -> bool { fn indexed_navigation_action( state: &AppState, - key: TerminalKey, + key: &TerminalKey, dispatch: BindingDispatch, ) -> Option<NavigateAction> { let kb = &state.keybinds; @@ -1440,7 +1445,7 @@ fn indexed_navigation_action( fn action_matches( bindings: &crate::config::ActionKeybinds, - key: TerminalKey, + key: &TerminalKey, dispatch: BindingDispatch, ) -> bool { match dispatch { @@ -1455,13 +1460,13 @@ fn action_for_key( key: TerminalKey, dispatch: BindingDispatch, ) -> Option<NavigateAction> { - non_indexed_action_for_key(state, key, dispatch) - .or_else(|| indexed_navigation_action(state, key, dispatch)) + non_indexed_action_for_key(state, &key, dispatch) + .or_else(|| indexed_navigation_action(state, &key, dispatch)) } fn non_indexed_action_for_key( state: &AppState, - key: TerminalKey, + key: &TerminalKey, dispatch: BindingDispatch, ) -> Option<NavigateAction> { let kb = &state.keybinds; @@ -1536,7 +1541,7 @@ fn navigate_mode_action_for_key(state: &AppState, key: TerminalKey) -> Option<Na fn navigate_mode_non_indexed_action_for_key( state: &AppState, - key: TerminalKey, + key: &TerminalKey, ) -> Option<NavigateAction> { let action = non_indexed_action_for_key(state, key, BindingDispatch::Prefix)?; if matches!( @@ -1553,7 +1558,7 @@ fn navigate_mode_non_indexed_action_for_key( fn navigate_mode_indexed_action_for_key( state: &AppState, - key: TerminalKey, + key: &TerminalKey, ) -> Option<NavigateAction> { indexed_navigation_action(state, key, BindingDispatch::Prefix) } @@ -2719,9 +2724,9 @@ command = "echo literal" state.keybinds = config.keybinds(); let key = TerminalKey::new(KeyCode::Char('!'), KeyModifiers::empty()); - assert!(command_for_key(&state, key, BindingDispatch::Prefix).is_some()); + assert!(command_for_key(&state, &key, BindingDispatch::Prefix).is_some()); assert_eq!( - indexed_navigation_action(&state, key, BindingDispatch::Prefix), + indexed_navigation_action(&state, &key, BindingDispatch::Prefix), Some(NavigateAction::SwitchWorkspace(0)) ); } |
