From 61df50d70b7d80096e1a3ca758309308c35303c0 Mon Sep 17 00:00:00 2001 From: Mitchell Hashimoto Date: Mon, 29 Dec 2025 12:06:36 -0800 Subject: [PATCH] input: add `end_key_sequence` binding action End the currently active key sequence, if any, and flush the keys up to this point to the terminal, excluding the key that triggered this action. For example: `ctrl+w>escape=end_key_sequence` would encode `ctrl+w` to the terminal and exit the key sequence. Normally, an invalid sequence will reset the key sequence and flush all data including the invalid key. This action allows you to flush only the prior keys, which is useful when you want to bind something like a control key (`ctrl+w`) but not send additional inputs. --- src/Surface.zig | 8 ++++++++ src/input/Binding.zig | 15 +++++++++++++++ src/input/command.zig | 1 + 3 files changed, 24 insertions(+) diff --git a/src/Surface.zig b/src/Surface.zig index 614f40475..43ee440c2 100644 --- a/src/Surface.zig +++ b/src/Surface.zig @@ -5794,6 +5794,14 @@ pub fn performBindingAction(self: *Surface, action: input.Binding.Action) !bool return try self.deactivateAllKeyTables(); }, + .end_key_sequence => { + // End the key sequence and flush queued keys to the terminal, + // but don't encode the key that triggered this action. This + // will do that because leaf keys (keys with bindings) aren't + // in the queued encoding list. + self.endKeySequence(.flush, .retain); + }, + .crash => |location| switch (location) { .main => @panic("crash binding action, crashing intentionally"), diff --git a/src/input/Binding.zig b/src/input/Binding.zig index e7507b112..d5b24c61b 100644 --- a/src/input/Binding.zig +++ b/src/input/Binding.zig @@ -827,6 +827,20 @@ pub const Action = union(enum) { /// be undone or redone. redo, + /// End the currently active key sequence, if any, and flush the + /// keys up to this point to the terminal, excluding the key that + /// triggered this action. + /// + /// For example: `ctrl+w>escape=end_key_sequence` would encode + /// `ctrl+w` to the terminal and exit the key sequence. + /// + /// Normally, an invalid sequence will reset the key sequence and + /// flush all data including the invalid key. This action allows + /// you to flush only the prior keys, which is useful when you want + /// to bind something like a control key (`ctrl+w`) but not send + /// additional inputs. + end_key_sequence, + /// Activate a named key table (see `keybind` configuration documentation). /// The named key table will remain active until `deactivate_key_table` /// is called. If you want a one-shot key table activation, use the @@ -1316,6 +1330,7 @@ pub const Action = union(enum) { .activate_key_table_once, .deactivate_key_table, .deactivate_all_key_tables, + .end_key_sequence, .crash, => .surface, diff --git a/src/input/command.zig b/src/input/command.zig index 936f2211c..f089112db 100644 --- a/src/input/command.zig +++ b/src/input/command.zig @@ -696,6 +696,7 @@ fn actionCommands(action: Action.Key) []const Command { .activate_key_table_once, .deactivate_key_table, .deactivate_all_key_tables, + .end_key_sequence, .crash, => comptime &.{},