Merge remote-tracking branch 'refs/remotes/tmux-openbsd/master'

* refs/remotes/tmux-openbsd/master:
  Add a -K flag to new-pane to make a modal pane capture all keys like popups used to.
This commit is contained in:
tmux update bot
2026-08-19 13:10:09 +00:00
4 changed files with 57 additions and 19 deletions

View File

@@ -1,4 +1,4 @@
/* $OpenBSD: cmd-split-window.c,v 1.148 2026/08/07 08:10:53 nicm Exp $ */ /* $OpenBSD: cmd-split-window.c,v 1.149 2026/08/19 10:56:10 nicm Exp $ */
/* /*
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com> * Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
@@ -40,8 +40,8 @@ const struct cmd_entry cmd_new_pane_entry = {
.name = "new-pane", .name = "new-pane",
.alias = "newp", .alias = "newp",
.args = { "bB:Cc:de:EfF:hIkl:LMm:Op:PR:s:S:t:T:vWx:X:y:Y:Z", 0, -1, NULL }, .args = { "bB:Cc:de:EfF:hIkl:KLMm:Op:PR:s:S:t:T:vWx:X:y:Y:Z", 0, -1, NULL },
.usage = "[-bCdefhIklMOPvWZ] [-B border-lines] " .usage = "[-bCdefhIkKLMOPvWZ] [-B border-lines] "
"[-c start-directory] [-e environment] " "[-c start-directory] [-e environment] "
"[-F format] [-l size] [-m message] [-p percentage] " "[-F format] [-l size] [-m message] [-p percentage] "
"[-s style] [-S active-border-style] " "[-s style] [-S active-border-style] "
@@ -202,6 +202,8 @@ cmd_split_window_exec(struct cmd *self, struct cmdq_item *item)
*/ */
goto fail; goto fail;
} }
if (args_has(args, 'K') && args_has(args, 'O'))
new_wp->flags |= PANE_CAPTUREALLKEYS;
if (args_has(args, 'C') && args_has(args, 'O')) if (args_has(args, 'C') && args_has(args, 'O'))
new_wp->flags |= PANE_CLOSEONCLICK; new_wp->flags |= PANE_CLOSEONCLICK;

View File

@@ -1,4 +1,4 @@
/* $OpenBSD: server-client.c,v 1.503 2026/08/17 07:56:56 nicm Exp $ */ /* $OpenBSD: server-client.c,v 1.504 2026/08/19 10:56:10 nicm Exp $ */
/* /*
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com> * Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
@@ -45,6 +45,7 @@ static void server_client_set_path(struct client *);
static void server_client_set_progress_bar(struct client *); static void server_client_set_progress_bar(struct client *);
static void server_client_reset_state(struct client *); static void server_client_reset_state(struct client *);
static void server_client_update_latest(struct client *); static void server_client_update_latest(struct client *);
static int server_client_handle_dead_key(struct window_pane *, key_code);
static void server_client_dispatch(struct imsg *, void *); static void server_client_dispatch(struct imsg *, void *);
static int server_client_dispatch_command(struct client *, struct imsg *); static int server_client_dispatch_command(struct client *, struct imsg *);
static int server_client_dispatch_identify(struct client *, struct imsg *); static int server_client_dispatch_identify(struct client *, struct imsg *);
@@ -1388,6 +1389,21 @@ server_client_repeat_time(struct client *c, struct key_binding *bd)
return (repeat); return (repeat);
} }
/* Handle a key press on a dead pane waiting for a key. */
static int
server_client_handle_dead_key(struct window_pane *wp, key_code key)
{
if (wp == NULL ||
(~wp->flags & PANE_EXITED) ||
KEYC_IS_MOUSE(key) ||
KEYC_IS_PASTE(key) ||
options_get_number(wp->options, "remain-on-exit") != 3)
return (0);
options_set_number(wp->options, "remain-on-exit", 0);
server_destroy_pane(wp, 0);
return (1);
}
/* /*
* Handle data key input from client. This owns and can modify the key event it * Handle data key input from client. This owns and can modify the key event it
* is given and is responsible for freeing it. * is given and is responsible for freeing it.
@@ -1473,6 +1489,14 @@ server_client_key_callback(struct cmdq_item *item, void *data)
server_client_is_assume_paste(c)) server_client_is_assume_paste(c))
goto paste_key; goto paste_key;
/* Forward keys directly if this pane is capturing all keys. */
if (wp != NULL &&
(wp->flags & PANE_CAPTUREALLKEYS) &&
(~wp->flags & PANE_EXITED) &&
!KEYC_IS_MOUSE(key) &&
TAILQ_EMPTY(&wp->modes))
goto forward_key;
/* /*
* Work out the current key table. If the pane is in a mode, use * Work out the current key table. If the pane is in a mode, use
* the mode table instead of the default key table. * the mode table instead of the default key table.
@@ -1637,15 +1661,8 @@ try_again:
} }
forward_key: forward_key:
if (wp != NULL && if (server_client_handle_dead_key(wp, key))
(wp->flags & PANE_EXITED) &&
!KEYC_IS_MOUSE(key) &&
!KEYC_IS_PASTE(key) &&
options_get_number(wp->options, "remain-on-exit") == 3) {
options_set_number(wp->options, "remain-on-exit", 0);
server_destroy_pane(wp, 0);
goto out; goto out;
}
if (c->flags & CLIENT_READONLY) if (c->flags & CLIENT_READONLY)
goto out; goto out;
if (wp != NULL) if (wp != NULL)
@@ -1733,9 +1750,9 @@ server_client_handle_key0(struct client *c, struct key_event *event,
} }
/* /*
* Key presses in overlay mode and the command prompt are a special * Key presses in overlay mode, for panes capturing all keys and in the
* case. The queue might be blocked so they need to be processed * command prompt are a special case. The queue might be blocked so they
* immediately rather than queued. * need to be processed immediately rather than queued.
*/ */
if (~c->flags & CLIENT_READONLY) { if (~c->flags & CLIENT_READONLY) {
if (c->message_string != NULL) { if (c->message_string != NULL) {
@@ -1755,6 +1772,21 @@ server_client_handle_key0(struct client *c, struct key_event *event,
} }
server_client_clear_overlay(c); server_client_clear_overlay(c);
wp = s->curw->window->active;
if (wp != NULL &&
(wp->flags & PANE_CAPTUREALLKEYS) &&
TAILQ_EMPTY(&wp->modes) &&
!KEYC_IS_MOUSE(event->key)) {
if (server_client_handle_dead_key(wp, event->key))
return (0);
if (~wp->flags & PANE_EXITED) {
window_pane_key(wp, c, s, s->curw, event->key,
&event->m);
return (0);
}
}
if (server_client_handle_menu_key(c, event)) if (server_client_handle_menu_key(c, event))
return (0); return (0);
if (c->prompt != NULL) { if (c->prompt != NULL) {

9
tmux.1
View File

@@ -1,4 +1,4 @@
.\" $OpenBSD: tmux.1,v 1.1156 2026/08/17 14:47:41 nicm Exp $ .\" $OpenBSD: tmux.1,v 1.1157 2026/08/19 10:56:10 nicm Exp $
.\" .\"
.\" Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com> .\" Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
.\" .\"
@@ -14,7 +14,7 @@
.\" IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
.\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
.\" .\"
.Dd $Mdocdate: August 17 2026 $ .Dd $Mdocdate: August 19 2026 $
.Dt TMUX 1 .Dt TMUX 1
.Os .Os
.Sh NAME .Sh NAME
@@ -3644,7 +3644,7 @@ but a different format may be specified with
.Fl F . .Fl F .
.Tg newp .Tg newp
.It Xo Ic new\-pane .It Xo Ic new\-pane
.Op Fl bCdefhIkLMOPvWZ .Op Fl bCdefhIkKLMOPvWZ
.Op Fl B Ar border\-lines .Op Fl B Ar border\-lines
.Op Fl c Ar start\-directory .Op Fl c Ar start\-directory
.Op Fl e Ar environment .Op Fl e Ar environment
@@ -3701,6 +3701,9 @@ A modal pane is always the active pane and prevents interaction with any other
panes while it is active. panes while it is active.
A window can only have one modal pane and it must be a floating pane. A window can only have one modal pane and it must be a floating pane.
With With
.Fl K ,
all keys, including the prefix key, are passed directly to the modal pane.
With
.Fl C , .Fl C ,
the modal pane is closed when the mouse is clicked outside it. the modal pane is closed when the mouse is clicked outside it.
.Pp .Pp

3
tmux.h
View File

@@ -1,4 +1,4 @@
/* $OpenBSD: tmux.h,v 1.1427 2026/08/18 09:01:20 nicm Exp $ */ /* $OpenBSD: tmux.h,v 1.1428 2026/08/19 10:56:10 nicm Exp $ */
/* /*
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com> * Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
@@ -1335,6 +1335,7 @@ struct window_pane {
#define PANE_CMDRUNNING 0x20000 #define PANE_CMDRUNNING 0x20000
#define PANE_ACTIVITY 0x40000 #define PANE_ACTIVITY 0x40000
#define PANE_CLOSEONCLICK 0x80000 #define PANE_CLOSEONCLICK 0x80000
#define PANE_CAPTUREALLKEYS 0x100000
bitstr_t *sync_dirty; bitstr_t *sync_dirty;
u_int sync_dirty_size; u_int sync_dirty_size;