mirror of
https://github.com/tmux/tmux.git
synced 2025-04-21 20:08:48 +00:00
Merge branch 'tmux:master' into issue-4412-choose-tree-format-prints-wrong-values
This commit is contained in:
commit
86b6480081
.github/ISSUE_TEMPLATE
.gitignoreSYNCINGalerts.cclient.ccmd-break-pane.ccmd-capture-pane.ccmd-display-menu.ccmd-display-message.ccmd-if-shell.ccmd-join-pane.ccmd-list-keys.ccmd-queue.ccmd-run-shell.ccmd-select-pane.ccmd-send-keys.ccmd-split-window.ccmd-swap-pane.ccmd.ccolour.cconfigure.acformat.cinput-keys.cinput.cmode-tree.coptions-table.coptions.cscreen-redraw.cserver-client.csession.cstatus.ctmux.1tmux.htty-keys.ctty.cwindow-copy.cwindow-customize.cwindow.c@ -1,3 +1,12 @@
|
|||||||
|
---
|
||||||
|
name: Use this issue template
|
||||||
|
about: Please read https://github.com/tmux/tmux/blob/master/.github/CONTRIBUTING.md
|
||||||
|
title: ''
|
||||||
|
labels: ''
|
||||||
|
assignees: ''
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
### Issue description
|
### Issue description
|
||||||
|
|
||||||
Please read https://github.com/tmux/tmux/blob/master/.github/CONTRIBUTING.md
|
Please read https://github.com/tmux/tmux/blob/master/.github/CONTRIBUTING.md
|
35
.gitignore
vendored
35
.gitignore
vendored
@ -1,23 +1,24 @@
|
|||||||
*.o
|
|
||||||
*~
|
|
||||||
*.diff
|
|
||||||
*.patch
|
|
||||||
*.core
|
*.core
|
||||||
core
|
*.dSYM
|
||||||
tags
|
*.diff
|
||||||
|
*.o
|
||||||
|
*.patch
|
||||||
|
*.swp
|
||||||
|
*~
|
||||||
.deps/
|
.deps/
|
||||||
compat/.dirstamp
|
.dirstamp
|
||||||
aclocal.m4
|
|
||||||
autom4te.cache/
|
|
||||||
config.log
|
|
||||||
config.status
|
|
||||||
etc/
|
|
||||||
tmux
|
|
||||||
Makefile
|
Makefile
|
||||||
Makefile.in
|
Makefile.in
|
||||||
configure
|
aclocal.m4
|
||||||
tmux.1.*
|
autom4te.cache/
|
||||||
*.dSYM
|
|
||||||
cmd-parse.c
|
cmd-parse.c
|
||||||
|
compat/.dirstamp
|
||||||
|
config.log
|
||||||
|
config.status
|
||||||
|
configure
|
||||||
|
core
|
||||||
|
etc/
|
||||||
fuzz/*-fuzzer
|
fuzz/*-fuzzer
|
||||||
.dirstamp
|
tags
|
||||||
|
tmux
|
||||||
|
tmux.1.*
|
||||||
|
32
SYNCING
32
SYNCING
@ -1,17 +1,17 @@
|
|||||||
Preamble
|
Preamble
|
||||||
========
|
========
|
||||||
|
|
||||||
Tmux portable relies on repositories "tmux" and "tmux-openbsd".
|
Tmux portable relies on repositories "tmux" and "tmux-obsd".
|
||||||
Here's a description of them:
|
Here's a description of them:
|
||||||
|
|
||||||
* "tmux" is the portable version, the one which contains code for other
|
* "tmux" is the portable version, the one which contains code for other
|
||||||
operating systems, and autotools, etc., which isn't found or needed in the
|
operating systems, and autotools, etc., which isn't found or needed in the
|
||||||
OpenBSD base system.
|
OpenBSD base system.
|
||||||
|
|
||||||
* "tmux-openbsd" is the version of tmux in OpenBSD base system which provides
|
* "tmux-obsd" is the version of tmux in OpenBSD base system which provides
|
||||||
the basis of the portable tmux version.
|
the basis of the portable tmux version.
|
||||||
|
|
||||||
Note: The "tmux-openbsd" repository is actually handled by "git cvsimport"
|
Note: The "tmux-obsd" repository is actually handled by "git cvsimport"
|
||||||
running at 15 minute intervals, so a commit made to OpenBSD's tmux CVS
|
running at 15 minute intervals, so a commit made to OpenBSD's tmux CVS
|
||||||
repository will take at least that long to appear in this git repository.
|
repository will take at least that long to appear in this git repository.
|
||||||
(It might take longer, depending on the CVS mirror used to import the
|
(It might take longer, depending on the CVS mirror used to import the
|
||||||
@ -34,11 +34,11 @@ this information has ever been set before.
|
|||||||
Cloning repositories
|
Cloning repositories
|
||||||
====================
|
====================
|
||||||
|
|
||||||
This involves having both tmux and tmux-openbsd cloned, as in:
|
This involves having both tmux and tmux-obsd cloned, as in:
|
||||||
|
|
||||||
% cd /some/where/useful
|
% cd /some/where/useful
|
||||||
% git clone https://github.com/tmux/tmux.git
|
% git clone https://github.com/tmux/tmux.git
|
||||||
% git clone https://github.com/ThomasAdam/tmux-openbsd.git
|
% git clone https://github.com/ThomasAdam/tmux-obsd.git
|
||||||
|
|
||||||
Note that you do not need additional checkouts to manage the sync -- an
|
Note that you do not need additional checkouts to manage the sync -- an
|
||||||
existing clone of either repositories will suffice. So if you already have
|
existing clone of either repositories will suffice. So if you already have
|
||||||
@ -47,30 +47,30 @@ these checkouts existing, skip that.
|
|||||||
Adding in git-remotes
|
Adding in git-remotes
|
||||||
=====================
|
=====================
|
||||||
|
|
||||||
Because the portable "tmux" git repository and the "tmux-openbsd"
|
Because the portable "tmux" git repository and the "tmux-obsd"
|
||||||
repository do not inherently share any history between each other, the
|
repository do not inherently share any history between each other, the
|
||||||
history has been faked between them. This "faking of history" is something
|
history has been faked between them. This "faking of history" is something
|
||||||
which has to be told to git for the purposes of comparing the "tmux" and
|
which has to be told to git for the purposes of comparing the "tmux" and
|
||||||
"tmux-openbsd" repositories for syncing. To do this, we must reference the
|
"tmux-obsd" repositories for syncing. To do this, we must reference the
|
||||||
clone of the "tmux-openbsd" repository from the "tmux" repository, as
|
clone of the "tmux-obsd" repository from the "tmux" repository, as
|
||||||
shown by the following command:
|
shown by the following command:
|
||||||
|
|
||||||
% cd /path/to/tmux
|
% cd /path/to/tmux
|
||||||
% git remote add obsd-tmux file:///path/to/tmux-openbsd
|
% git remote add obsd-tmux file:///path/to/tmux-obsd
|
||||||
|
|
||||||
So that now, the remote "obsd-tmux" can be used to reference branches and
|
So that now, the remote "obsd-tmux" can be used to reference branches and
|
||||||
commits from the "tmux-openbsd" repository, but from the context of the
|
commits from the "tmux-obsd" repository, but from the context of the
|
||||||
portable "tmux" repository, which makes sense because it's the "tmux"
|
portable "tmux" repository, which makes sense because it's the "tmux"
|
||||||
repository which will have the updates applied to them.
|
repository which will have the updates applied to them.
|
||||||
|
|
||||||
Fetching updates
|
Fetching updates
|
||||||
================
|
================
|
||||||
|
|
||||||
To ensure the latest commits from "tmux-openbsd" can be found from within
|
To ensure the latest commits from "tmux-obsd" can be found from within
|
||||||
"tmux", we have to ensure the "master" branch from "tmux-openbsd" is
|
"tmux", we have to ensure the "master" branch from "tmux-obsd" is
|
||||||
up-to-date first, and then reference that update in "tmux", as in:
|
up-to-date first, and then reference that update in "tmux", as in:
|
||||||
|
|
||||||
% cd /path/to/tmux-openbsd
|
% cd /path/to/tmux-obsd
|
||||||
% git checkout master
|
% git checkout master
|
||||||
% git pull
|
% git pull
|
||||||
|
|
||||||
@ -82,9 +82,9 @@ Then back in "tmux":
|
|||||||
Creating the necessary branches
|
Creating the necessary branches
|
||||||
===============================
|
===============================
|
||||||
|
|
||||||
Now that "tmux" can see commits and branches from "tmux-openbsd" by way
|
Now that "tmux" can see commits and branches from "tmux-obsd" by way
|
||||||
of the remote name "obsd-tmux", we can now create the master branch from
|
of the remote name "obsd-tmux", we can now create the master branch from
|
||||||
"tmux-openbsd" in the "tmux" repository:
|
"tmux-obsd" in the "tmux" repository:
|
||||||
|
|
||||||
% git checkout -b obsd-master obsd-tmux/master
|
% git checkout -b obsd-master obsd-tmux/master
|
||||||
|
|
||||||
@ -92,7 +92,7 @@ Adding in the fake history points
|
|||||||
=================================
|
=================================
|
||||||
|
|
||||||
To tie both the "master" branch from "tmux" and the "obsd-master"
|
To tie both the "master" branch from "tmux" and the "obsd-master"
|
||||||
branch from "tmux-openbsd" together, the fake history points added to the
|
branch from "tmux-obsd" together, the fake history points added to the
|
||||||
"tmux" repository need to be added. To do this, we must add an
|
"tmux" repository need to be added. To do this, we must add an
|
||||||
additional refspec line, as in:
|
additional refspec line, as in:
|
||||||
|
|
||||||
|
8
alerts.c
8
alerts.c
@ -315,11 +315,11 @@ alerts_set_message(struct winlink *wl, const char *type, const char *option)
|
|||||||
if (visual == VISUAL_OFF)
|
if (visual == VISUAL_OFF)
|
||||||
continue;
|
continue;
|
||||||
if (c->session->curw == wl) {
|
if (c->session->curw == wl) {
|
||||||
status_message_set(c, -1, 1, 0, "%s in current window",
|
status_message_set(c, -1, 1, 0, 0,
|
||||||
type);
|
"%s in current window", type);
|
||||||
} else {
|
} else {
|
||||||
status_message_set(c, -1, 1, 0, "%s in window %d", type,
|
status_message_set(c, -1, 1, 0, 0,
|
||||||
wl->idx);
|
"%s in window %d", type, wl->idx);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
7
client.c
7
client.c
@ -266,8 +266,13 @@ client_main(struct event_base *base, int argc, char **argv, uint64_t flags,
|
|||||||
if (cmd_list_any_have(pr->cmdlist, CMD_STARTSERVER))
|
if (cmd_list_any_have(pr->cmdlist, CMD_STARTSERVER))
|
||||||
flags |= CLIENT_STARTSERVER;
|
flags |= CLIENT_STARTSERVER;
|
||||||
cmd_list_free(pr->cmdlist);
|
cmd_list_free(pr->cmdlist);
|
||||||
} else
|
} else {
|
||||||
|
fprintf(stderr, "%s\n", pr->error);
|
||||||
|
args_free_values(values, argc);
|
||||||
|
free(values);
|
||||||
free(pr->error);
|
free(pr->error);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
args_free_values(values, argc);
|
args_free_values(values, argc);
|
||||||
free(values);
|
free(values);
|
||||||
}
|
}
|
||||||
|
@ -99,7 +99,7 @@ cmd_break_pane_exec(struct cmd *self, struct cmdq_item *item)
|
|||||||
|
|
||||||
w = wp->window = window_create(w->sx, w->sy, w->xpixel, w->ypixel);
|
w = wp->window = window_create(w->sx, w->sy, w->xpixel, w->ypixel);
|
||||||
options_set_parent(wp->options, w->options);
|
options_set_parent(wp->options, w->options);
|
||||||
wp->flags |= PANE_STYLECHANGED;
|
wp->flags |= (PANE_STYLECHANGED|PANE_THEMECHANGED);
|
||||||
TAILQ_INSERT_HEAD(&w->panes, wp, entry);
|
TAILQ_INSERT_HEAD(&w->panes, wp, entry);
|
||||||
w->active = wp;
|
w->active = wp;
|
||||||
w->latest = tc;
|
w->latest = tc;
|
||||||
|
@ -39,8 +39,8 @@ const struct cmd_entry cmd_capture_pane_entry = {
|
|||||||
.name = "capture-pane",
|
.name = "capture-pane",
|
||||||
.alias = "capturep",
|
.alias = "capturep",
|
||||||
|
|
||||||
.args = { "ab:CeE:JNpPqS:Tt:", 0, 0, NULL },
|
.args = { "ab:CeE:JMNpPqS:Tt:", 0, 0, NULL },
|
||||||
.usage = "[-aCeJNpPqT] " CMD_BUFFER_USAGE " [-E end-line] "
|
.usage = "[-aCeJMNpPqT] " CMD_BUFFER_USAGE " [-E end-line] "
|
||||||
"[-S start-line] " CMD_TARGET_PANE_USAGE,
|
"[-S start-line] " CMD_TARGET_PANE_USAGE,
|
||||||
|
|
||||||
.target = { 't', CMD_FIND_PANE, 0 },
|
.target = { 't', CMD_FIND_PANE, 0 },
|
||||||
@ -107,14 +107,16 @@ static char *
|
|||||||
cmd_capture_pane_history(struct args *args, struct cmdq_item *item,
|
cmd_capture_pane_history(struct args *args, struct cmdq_item *item,
|
||||||
struct window_pane *wp, size_t *len)
|
struct window_pane *wp, size_t *len)
|
||||||
{
|
{
|
||||||
struct grid *gd;
|
struct grid *gd;
|
||||||
const struct grid_line *gl;
|
const struct grid_line *gl;
|
||||||
struct grid_cell *gc = NULL;
|
struct screen *s;
|
||||||
int n, join_lines, flags = 0;
|
struct grid_cell *gc = NULL;
|
||||||
u_int i, sx, top, bottom, tmp;
|
struct window_mode_entry *wme;
|
||||||
char *cause, *buf, *line;
|
int n, join_lines, flags = 0;
|
||||||
const char *Sflag, *Eflag;
|
u_int i, sx, top, bottom, tmp;
|
||||||
size_t linelen;
|
char *cause, *buf, *line;
|
||||||
|
const char *Sflag, *Eflag;
|
||||||
|
size_t linelen;
|
||||||
|
|
||||||
sx = screen_size_x(&wp->base);
|
sx = screen_size_x(&wp->base);
|
||||||
if (args_has(args, 'a')) {
|
if (args_has(args, 'a')) {
|
||||||
@ -126,8 +128,20 @@ cmd_capture_pane_history(struct args *args, struct cmdq_item *item,
|
|||||||
}
|
}
|
||||||
return (xstrdup(""));
|
return (xstrdup(""));
|
||||||
}
|
}
|
||||||
} else
|
s = &wp->base;
|
||||||
|
} else if (args_has(args, 'M')) {
|
||||||
|
wme = TAILQ_FIRST(&wp->modes);
|
||||||
|
if (wme != NULL && wme->mode->get_screen != NULL) {
|
||||||
|
s = wme->mode->get_screen (wme);
|
||||||
|
gd = s->grid;
|
||||||
|
} else {
|
||||||
|
s = &wp->base;
|
||||||
|
gd = wp->base.grid;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
s = &wp->base;
|
||||||
gd = wp->base.grid;
|
gd = wp->base.grid;
|
||||||
|
}
|
||||||
|
|
||||||
Sflag = args_get(args, 'S');
|
Sflag = args_get(args, 'S');
|
||||||
if (Sflag != NULL && strcmp(Sflag, "-") == 0)
|
if (Sflag != NULL && strcmp(Sflag, "-") == 0)
|
||||||
@ -181,7 +195,7 @@ cmd_capture_pane_history(struct args *args, struct cmdq_item *item,
|
|||||||
|
|
||||||
buf = NULL;
|
buf = NULL;
|
||||||
for (i = top; i <= bottom; i++) {
|
for (i = top; i <= bottom; i++) {
|
||||||
line = grid_string_cells(gd, 0, i, sx, &gc, flags, wp->screen);
|
line = grid_string_cells(gd, 0, i, sx, &gc, flags, s);
|
||||||
linelen = strlen(line);
|
linelen = strlen(line);
|
||||||
|
|
||||||
buf = cmd_capture_pane_append(buf, len, line, linelen);
|
buf = cmd_capture_pane_append(buf, len, line, linelen);
|
||||||
|
@ -41,7 +41,7 @@ const struct cmd_entry cmd_display_menu_entry = {
|
|||||||
.args = { "b:c:C:H:s:S:MOt:T:x:y:", 1, -1, cmd_display_menu_args_parse },
|
.args = { "b:c:C:H:s:S:MOt:T:x:y:", 1, -1, cmd_display_menu_args_parse },
|
||||||
.usage = "[-MO] [-b border-lines] [-c target-client] "
|
.usage = "[-MO] [-b border-lines] [-c target-client] "
|
||||||
"[-C starting-choice] [-H selected-style] [-s style] "
|
"[-C starting-choice] [-H selected-style] [-s style] "
|
||||||
"[-S border-style] " CMD_TARGET_PANE_USAGE "[-T title] "
|
"[-S border-style] " CMD_TARGET_PANE_USAGE " [-T title] "
|
||||||
"[-x position] [-y position] name key command ...",
|
"[-x position] [-y position] name key command ...",
|
||||||
|
|
||||||
.target = { 't', CMD_FIND_PANE, 0 },
|
.target = { 't', CMD_FIND_PANE, 0 },
|
||||||
@ -58,7 +58,7 @@ const struct cmd_entry cmd_display_popup_entry = {
|
|||||||
.usage = "[-BCE] [-b border-lines] [-c target-client] "
|
.usage = "[-BCE] [-b border-lines] [-c target-client] "
|
||||||
"[-d start-directory] [-e environment] [-h height] "
|
"[-d start-directory] [-e environment] [-h height] "
|
||||||
"[-s style] [-S border-style] " CMD_TARGET_PANE_USAGE
|
"[-s style] [-S border-style] " CMD_TARGET_PANE_USAGE
|
||||||
"[-T title] [-w width] [-x position] [-y position] "
|
" [-T title] [-w width] [-x position] [-y position] "
|
||||||
"[shell-command]",
|
"[shell-command]",
|
||||||
|
|
||||||
.target = { 't', CMD_FIND_PANE, 0 },
|
.target = { 't', CMD_FIND_PANE, 0 },
|
||||||
|
@ -39,8 +39,8 @@ const struct cmd_entry cmd_display_message_entry = {
|
|||||||
.name = "display-message",
|
.name = "display-message",
|
||||||
.alias = "display",
|
.alias = "display",
|
||||||
|
|
||||||
.args = { "ac:d:lINpt:F:v", 0, 1, NULL },
|
.args = { "aCc:d:lINpt:F:v", 0, 1, NULL },
|
||||||
.usage = "[-aIlNpv] [-c target-client] [-d delay] [-F format] "
|
.usage = "[-aCIlNpv] [-c target-client] [-d delay] [-F format] "
|
||||||
CMD_TARGET_PANE_USAGE " [message]",
|
CMD_TARGET_PANE_USAGE " [message]",
|
||||||
|
|
||||||
.target = { 't', CMD_FIND_PANE, CMD_FIND_CANFAIL },
|
.target = { 't', CMD_FIND_PANE, CMD_FIND_CANFAIL },
|
||||||
@ -69,6 +69,7 @@ cmd_display_message_exec(struct cmd *self, struct cmdq_item *item)
|
|||||||
const char *template;
|
const char *template;
|
||||||
char *msg, *cause;
|
char *msg, *cause;
|
||||||
int delay = -1, flags, Nflag = args_has(args, 'N');
|
int delay = -1, flags, Nflag = args_has(args, 'N');
|
||||||
|
int Cflag = args_has(args, 'C');
|
||||||
struct format_tree *ft;
|
struct format_tree *ft;
|
||||||
u_int count = args_count(args);
|
u_int count = args_count(args);
|
||||||
struct evbuffer *evb;
|
struct evbuffer *evb;
|
||||||
@ -150,7 +151,7 @@ cmd_display_message_exec(struct cmd *self, struct cmdq_item *item)
|
|||||||
server_client_print(tc, 0, evb);
|
server_client_print(tc, 0, evb);
|
||||||
evbuffer_free(evb);
|
evbuffer_free(evb);
|
||||||
} else if (tc != NULL)
|
} else if (tc != NULL)
|
||||||
status_message_set(tc, delay, 0, Nflag, "%s", msg);
|
status_message_set(tc, delay, 0, Nflag, Cflag, "%s", msg);
|
||||||
free(msg);
|
free(msg);
|
||||||
|
|
||||||
format_free(ft);
|
format_free(ft);
|
||||||
|
@ -157,7 +157,7 @@ cmd_if_shell_callback(struct job *job)
|
|||||||
if (cmdlist == NULL) {
|
if (cmdlist == NULL) {
|
||||||
if (cdata->item == NULL) {
|
if (cdata->item == NULL) {
|
||||||
*error = toupper((u_char)*error);
|
*error = toupper((u_char)*error);
|
||||||
status_message_set(c, -1, 1, 0, "%s", error);
|
status_message_set(c, -1, 1, 0, 0, "%s", error);
|
||||||
} else
|
} else
|
||||||
cmdq_error(cdata->item, "%s", error);
|
cmdq_error(cdata->item, "%s", error);
|
||||||
free(error);
|
free(error);
|
||||||
|
@ -149,7 +149,7 @@ cmd_join_pane_exec(struct cmd *self, struct cmdq_item *item)
|
|||||||
|
|
||||||
src_wp->window = dst_w;
|
src_wp->window = dst_w;
|
||||||
options_set_parent(src_wp->options, dst_w->options);
|
options_set_parent(src_wp->options, dst_w->options);
|
||||||
src_wp->flags |= PANE_STYLECHANGED;
|
src_wp->flags |= (PANE_STYLECHANGED|PANE_THEMECHANGED);
|
||||||
if (flags & SPAWN_BEFORE)
|
if (flags & SPAWN_BEFORE)
|
||||||
TAILQ_INSERT_BEFORE(dst_wp, src_wp, entry);
|
TAILQ_INSERT_BEFORE(dst_wp, src_wp, entry);
|
||||||
else
|
else
|
||||||
|
@ -91,7 +91,7 @@ cmd_list_keys_print_notes(struct cmdq_item *item, struct args *args,
|
|||||||
struct key_binding *bd;
|
struct key_binding *bd;
|
||||||
const char *key;
|
const char *key;
|
||||||
char *tmp, *note;
|
char *tmp, *note;
|
||||||
int found = 0;
|
int found = 0;
|
||||||
|
|
||||||
table = key_bindings_get_table(tablename, 0);
|
table = key_bindings_get_table(tablename, 0);
|
||||||
if (table == NULL)
|
if (table == NULL)
|
||||||
@ -114,8 +114,8 @@ cmd_list_keys_print_notes(struct cmdq_item *item, struct args *args,
|
|||||||
note = xstrdup(bd->note);
|
note = xstrdup(bd->note);
|
||||||
tmp = utf8_padcstr(key, keywidth + 1);
|
tmp = utf8_padcstr(key, keywidth + 1);
|
||||||
if (args_has(args, '1') && tc != NULL) {
|
if (args_has(args, '1') && tc != NULL) {
|
||||||
status_message_set(tc, -1, 1, 0, "%s%s%s", prefix, tmp,
|
status_message_set(tc, -1, 1, 0, 0, "%s%s%s", prefix,
|
||||||
note);
|
tmp, note);
|
||||||
} else
|
} else
|
||||||
cmdq_print(item, "%s%s%s", prefix, tmp, note);
|
cmdq_print(item, "%s%s%s", prefix, tmp, note);
|
||||||
free(tmp);
|
free(tmp);
|
||||||
@ -298,8 +298,8 @@ cmd_list_keys_exec(struct cmd *self, struct cmdq_item *item)
|
|||||||
free(cp);
|
free(cp);
|
||||||
|
|
||||||
if (args_has(args, '1') && tc != NULL) {
|
if (args_has(args, '1') && tc != NULL) {
|
||||||
status_message_set(tc, -1, 1, 0, "bind-key %s",
|
status_message_set(tc, -1, 1, 0, 0,
|
||||||
tmp);
|
"bind-key %s", tmp);
|
||||||
} else
|
} else
|
||||||
cmdq_print(item, "bind-key %s", tmp);
|
cmdq_print(item, "bind-key %s", tmp);
|
||||||
free(key);
|
free(key);
|
||||||
@ -321,6 +321,31 @@ out:
|
|||||||
return (CMD_RETURN_NORMAL);
|
return (CMD_RETURN_NORMAL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
cmd_list_single_command(const struct cmd_entry *entry, struct format_tree *ft,
|
||||||
|
const char *template, struct cmdq_item *item)
|
||||||
|
{
|
||||||
|
const char *s;
|
||||||
|
char *line;
|
||||||
|
|
||||||
|
format_add(ft, "command_list_name", "%s", entry->name);
|
||||||
|
if (entry->alias != NULL)
|
||||||
|
s = entry->alias;
|
||||||
|
else
|
||||||
|
s = "";
|
||||||
|
format_add(ft, "command_list_alias", "%s", s);
|
||||||
|
if (entry->usage != NULL)
|
||||||
|
s = entry->usage;
|
||||||
|
else
|
||||||
|
s = "";
|
||||||
|
format_add(ft, "command_list_usage", "%s", s);
|
||||||
|
|
||||||
|
line = format_expand(ft, template);
|
||||||
|
if (*line != '\0')
|
||||||
|
cmdq_print(item, "%s", line);
|
||||||
|
free(line);
|
||||||
|
}
|
||||||
|
|
||||||
static enum cmd_retval
|
static enum cmd_retval
|
||||||
cmd_list_keys_commands(struct cmd *self, struct cmdq_item *item)
|
cmd_list_keys_commands(struct cmd *self, struct cmdq_item *item)
|
||||||
{
|
{
|
||||||
@ -328,8 +353,8 @@ cmd_list_keys_commands(struct cmd *self, struct cmdq_item *item)
|
|||||||
const struct cmd_entry **entryp;
|
const struct cmd_entry **entryp;
|
||||||
const struct cmd_entry *entry;
|
const struct cmd_entry *entry;
|
||||||
struct format_tree *ft;
|
struct format_tree *ft;
|
||||||
const char *template, *s, *command;
|
const char *template, *command;
|
||||||
char *line;
|
char *cause;
|
||||||
|
|
||||||
if ((template = args_get(args, 'F')) == NULL) {
|
if ((template = args_get(args, 'F')) == NULL) {
|
||||||
template = "#{command_list_name}"
|
template = "#{command_list_name}"
|
||||||
@ -341,30 +366,19 @@ cmd_list_keys_commands(struct cmd *self, struct cmdq_item *item)
|
|||||||
format_defaults(ft, NULL, NULL, NULL, NULL);
|
format_defaults(ft, NULL, NULL, NULL, NULL);
|
||||||
|
|
||||||
command = args_string(args, 0);
|
command = args_string(args, 0);
|
||||||
for (entryp = cmd_table; *entryp != NULL; entryp++) {
|
if (command == NULL) {
|
||||||
entry = *entryp;
|
for (entryp = cmd_table; *entryp != NULL; entryp++)
|
||||||
if (command != NULL &&
|
cmd_list_single_command(*entryp, ft, template, item);
|
||||||
(strcmp(entry->name, command) != 0 &&
|
} else {
|
||||||
(entry->alias == NULL ||
|
entry = cmd_find(command, &cause);
|
||||||
strcmp(entry->alias, command) != 0)))
|
if (entry != NULL)
|
||||||
continue;
|
cmd_list_single_command(entry, ft, template, item);
|
||||||
|
else {
|
||||||
format_add(ft, "command_list_name", "%s", entry->name);
|
cmdq_error(item, "%s", cause);
|
||||||
if (entry->alias != NULL)
|
free(cause);
|
||||||
s = entry->alias;
|
format_free(ft);
|
||||||
else
|
return (CMD_RETURN_ERROR);
|
||||||
s = "";
|
}
|
||||||
format_add(ft, "command_list_alias", "%s", s);
|
|
||||||
if (entry->usage != NULL)
|
|
||||||
s = entry->usage;
|
|
||||||
else
|
|
||||||
s = "";
|
|
||||||
format_add(ft, "command_list_usage", "%s", s);
|
|
||||||
|
|
||||||
line = format_expand(ft, template);
|
|
||||||
if (*line != '\0')
|
|
||||||
cmdq_print(item, "%s", line);
|
|
||||||
free(line);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
format_free(ft);
|
format_free(ft);
|
||||||
|
@ -892,7 +892,7 @@ cmdq_error(struct cmdq_item *item, const char *fmt, ...)
|
|||||||
c->retval = 1;
|
c->retval = 1;
|
||||||
} else {
|
} else {
|
||||||
*msg = toupper((u_char) *msg);
|
*msg = toupper((u_char) *msg);
|
||||||
status_message_set(c, -1, 1, 0, "%s", msg);
|
status_message_set(c, -1, 1, 0, 0, "%s", msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
free(msg);
|
free(msg);
|
||||||
|
@ -204,7 +204,7 @@ cmd_run_shell_timer(__unused int fd, __unused short events, void* arg)
|
|||||||
if (cmdlist == NULL) {
|
if (cmdlist == NULL) {
|
||||||
if (cdata->item == NULL) {
|
if (cdata->item == NULL) {
|
||||||
*error = toupper((u_char)*error);
|
*error = toupper((u_char)*error);
|
||||||
status_message_set(c, -1, 1, 0, "%s", error);
|
status_message_set(c, -1, 1, 0, 0, "%s", error);
|
||||||
} else
|
} else
|
||||||
cmdq_error(cdata->item, "%s", error);
|
cmdq_error(cdata->item, "%s", error);
|
||||||
free(error);
|
free(error);
|
||||||
|
@ -149,12 +149,14 @@ cmd_select_pane_exec(struct cmd *self, struct cmdq_item *item)
|
|||||||
markedwp = marked_pane.wp;
|
markedwp = marked_pane.wp;
|
||||||
|
|
||||||
if (lastwp != NULL) {
|
if (lastwp != NULL) {
|
||||||
lastwp->flags |= (PANE_REDRAW|PANE_STYLECHANGED);
|
lastwp->flags |= (PANE_REDRAW|PANE_STYLECHANGED|
|
||||||
|
PANE_THEMECHANGED);
|
||||||
server_redraw_window_borders(lastwp->window);
|
server_redraw_window_borders(lastwp->window);
|
||||||
server_status_window(lastwp->window);
|
server_status_window(lastwp->window);
|
||||||
}
|
}
|
||||||
if (markedwp != NULL) {
|
if (markedwp != NULL) {
|
||||||
markedwp->flags |= (PANE_REDRAW|PANE_STYLECHANGED);
|
markedwp->flags |= (PANE_REDRAW|PANE_STYLECHANGED|
|
||||||
|
PANE_THEMECHANGED);
|
||||||
server_redraw_window_borders(markedwp->window);
|
server_redraw_window_borders(markedwp->window);
|
||||||
server_status_window(markedwp->window);
|
server_status_window(markedwp->window);
|
||||||
}
|
}
|
||||||
@ -169,7 +171,7 @@ cmd_select_pane_exec(struct cmd *self, struct cmdq_item *item)
|
|||||||
return (CMD_RETURN_ERROR);
|
return (CMD_RETURN_ERROR);
|
||||||
}
|
}
|
||||||
options_set_string(oo, "window-active-style", 0, "%s", style);
|
options_set_string(oo, "window-active-style", 0, "%s", style);
|
||||||
wp->flags |= (PANE_REDRAW|PANE_STYLECHANGED);
|
wp->flags |= (PANE_REDRAW|PANE_STYLECHANGED|PANE_THEMECHANGED);
|
||||||
}
|
}
|
||||||
if (args_has(args, 'g')) {
|
if (args_has(args, 'g')) {
|
||||||
cmdq_print(item, "%s", options_get_string(oo, "window-style"));
|
cmdq_print(item, "%s", options_get_string(oo, "window-style"));
|
||||||
|
@ -217,7 +217,7 @@ cmd_send_keys_exec(struct cmd *self, struct cmdq_item *item)
|
|||||||
if (args_has(args, 'R')) {
|
if (args_has(args, 'R')) {
|
||||||
colour_palette_clear(&wp->palette);
|
colour_palette_clear(&wp->palette);
|
||||||
input_reset(wp->ictx, 1);
|
input_reset(wp->ictx, 1);
|
||||||
wp->flags |= (PANE_STYLECHANGED|PANE_REDRAW);
|
wp->flags |= (PANE_STYLECHANGED|PANE_THEMECHANGED|PANE_REDRAW);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (count == 0) {
|
if (count == 0) {
|
||||||
|
@ -42,7 +42,7 @@ const struct cmd_entry cmd_split_window_entry = {
|
|||||||
.args = { "bc:de:fF:hIl:p:Pt:vZ", 0, -1, NULL },
|
.args = { "bc:de:fF:hIl:p:Pt:vZ", 0, -1, NULL },
|
||||||
.usage = "[-bdefhIPvZ] [-c start-directory] [-e environment] "
|
.usage = "[-bdefhIPvZ] [-c start-directory] [-e environment] "
|
||||||
"[-F format] [-l size] " CMD_TARGET_PANE_USAGE
|
"[-F format] [-l size] " CMD_TARGET_PANE_USAGE
|
||||||
"[shell-command]",
|
" [shell-command]",
|
||||||
|
|
||||||
.target = { 't', CMD_FIND_PANE, 0 },
|
.target = { 't', CMD_FIND_PANE, 0 },
|
||||||
|
|
||||||
|
@ -101,10 +101,10 @@ cmd_swap_pane_exec(struct cmd *self, struct cmdq_item *item)
|
|||||||
|
|
||||||
src_wp->window = dst_w;
|
src_wp->window = dst_w;
|
||||||
options_set_parent(src_wp->options, dst_w->options);
|
options_set_parent(src_wp->options, dst_w->options);
|
||||||
src_wp->flags |= PANE_STYLECHANGED;
|
src_wp->flags |= (PANE_STYLECHANGED|PANE_THEMECHANGED);
|
||||||
dst_wp->window = src_w;
|
dst_wp->window = src_w;
|
||||||
options_set_parent(dst_wp->options, src_w->options);
|
options_set_parent(dst_wp->options, src_w->options);
|
||||||
dst_wp->flags |= PANE_STYLECHANGED;
|
dst_wp->flags |= (PANE_STYLECHANGED|PANE_THEMECHANGED);
|
||||||
|
|
||||||
sx = src_wp->sx; sy = src_wp->sy;
|
sx = src_wp->sx; sy = src_wp->sy;
|
||||||
xoff = src_wp->xoff; yoff = src_wp->yoff;
|
xoff = src_wp->xoff; yoff = src_wp->yoff;
|
||||||
|
2
cmd.c
2
cmd.c
@ -444,7 +444,7 @@ cmd_get_alias(const char *name)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Look up a command entry by name. */
|
/* Look up a command entry by name. */
|
||||||
static const struct cmd_entry *
|
const struct cmd_entry *
|
||||||
cmd_find(const char *name, char **cause)
|
cmd_find(const char *name, char **cause)
|
||||||
{
|
{
|
||||||
const struct cmd_entry **loop, *entry, *found = NULL;
|
const struct cmd_entry **loop, *entry, *found = NULL;
|
||||||
|
40
colour.c
40
colour.c
@ -182,6 +182,46 @@ colour_tostring(int c)
|
|||||||
return ("invalid");
|
return ("invalid");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Convert background colour to theme. */
|
||||||
|
enum client_theme
|
||||||
|
colour_totheme(int c)
|
||||||
|
{
|
||||||
|
int r, g, b, brightness;
|
||||||
|
|
||||||
|
if (c == -1)
|
||||||
|
return (THEME_UNKNOWN);
|
||||||
|
|
||||||
|
if (c & COLOUR_FLAG_RGB) {
|
||||||
|
r = (c >> 16) & 0xff;
|
||||||
|
g = (c >> 8) & 0xff;
|
||||||
|
b = (c >> 0) & 0xff;
|
||||||
|
|
||||||
|
brightness = r + g + b;
|
||||||
|
if (brightness > 382)
|
||||||
|
return (THEME_LIGHT);
|
||||||
|
return (THEME_DARK);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (c & COLOUR_FLAG_256)
|
||||||
|
return (colour_totheme(colour_256toRGB(c)));
|
||||||
|
|
||||||
|
switch (c) {
|
||||||
|
case 0:
|
||||||
|
case 90:
|
||||||
|
return (THEME_DARK);
|
||||||
|
case 7:
|
||||||
|
case 97:
|
||||||
|
return (THEME_LIGHT);
|
||||||
|
default:
|
||||||
|
if (c >= 0 && c <= 7)
|
||||||
|
return (colour_totheme(colour_256toRGB(c)));
|
||||||
|
if (c >= 90 && c <= 97)
|
||||||
|
return (colour_totheme(colour_256toRGB(8 + c - 90)));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return (THEME_UNKNOWN);
|
||||||
|
}
|
||||||
|
|
||||||
/* Convert colour from string. */
|
/* Convert colour from string. */
|
||||||
int
|
int
|
||||||
colour_fromstring(const char *s)
|
colour_fromstring(const char *s)
|
||||||
|
@ -638,9 +638,9 @@ else
|
|||||||
AC_LIBOBJ(err)
|
AC_LIBOBJ(err)
|
||||||
fi
|
fi
|
||||||
|
|
||||||
# Look for imsg_init in libutil.
|
# Look for imsg_add in libutil.
|
||||||
AC_SEARCH_LIBS(imsg_init, util, found_imsg_init=yes, found_imsg_init=no)
|
AC_SEARCH_LIBS(imsg_add, util, found_imsg_add=yes, found_imsg_add=no)
|
||||||
if test "x$found_imsg_init" = xyes; then
|
if test "x$found_imsg_add" = xyes; then
|
||||||
AC_DEFINE(HAVE_IMSG)
|
AC_DEFINE(HAVE_IMSG)
|
||||||
else
|
else
|
||||||
AC_LIBOBJ(imsg)
|
AC_LIBOBJ(imsg)
|
||||||
|
20
format.c
20
format.c
@ -1544,6 +1544,23 @@ format_cb_client_written(struct format_tree *ft)
|
|||||||
return (NULL);
|
return (NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Callback for client_theme. */
|
||||||
|
static void *
|
||||||
|
format_cb_client_theme(struct format_tree *ft)
|
||||||
|
{
|
||||||
|
if (ft->c != NULL) {
|
||||||
|
switch (ft->c->theme) {
|
||||||
|
case THEME_DARK:
|
||||||
|
return (xstrdup("dark"));
|
||||||
|
case THEME_LIGHT:
|
||||||
|
return (xstrdup("light"));
|
||||||
|
case THEME_UNKNOWN:
|
||||||
|
return (NULL);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (NULL);
|
||||||
|
}
|
||||||
|
|
||||||
/* Callback for config_files. */
|
/* Callback for config_files. */
|
||||||
static void *
|
static void *
|
||||||
format_cb_config_files(__unused struct format_tree *ft)
|
format_cb_config_files(__unused struct format_tree *ft)
|
||||||
@ -2881,6 +2898,9 @@ static const struct format_table_entry format_table[] = {
|
|||||||
{ "client_termtype", FORMAT_TABLE_STRING,
|
{ "client_termtype", FORMAT_TABLE_STRING,
|
||||||
format_cb_client_termtype
|
format_cb_client_termtype
|
||||||
},
|
},
|
||||||
|
{ "client_theme", FORMAT_TABLE_STRING,
|
||||||
|
format_cb_client_theme
|
||||||
|
},
|
||||||
{ "client_tty", FORMAT_TABLE_STRING,
|
{ "client_tty", FORMAT_TABLE_STRING,
|
||||||
format_cb_client_tty
|
format_cb_client_tty
|
||||||
},
|
},
|
||||||
|
12
input-keys.c
12
input-keys.c
@ -53,9 +53,15 @@ static struct input_key_entry input_key_defaults[] = {
|
|||||||
{ .key = KEYC_PASTE_START,
|
{ .key = KEYC_PASTE_START,
|
||||||
.data = "\033[200~"
|
.data = "\033[200~"
|
||||||
},
|
},
|
||||||
|
{ .key = KEYC_PASTE_START|KEYC_IMPLIED_META,
|
||||||
|
.data = "\033[200~"
|
||||||
|
},
|
||||||
{ .key = KEYC_PASTE_END,
|
{ .key = KEYC_PASTE_END,
|
||||||
.data = "\033[201~"
|
.data = "\033[201~"
|
||||||
},
|
},
|
||||||
|
{ .key = KEYC_PASTE_END|KEYC_IMPLIED_META,
|
||||||
|
.data = "\033[201~"
|
||||||
|
},
|
||||||
|
|
||||||
/* Function keys. */
|
/* Function keys. */
|
||||||
{ .key = KEYC_F1,
|
{ .key = KEYC_F1,
|
||||||
@ -307,6 +313,12 @@ static struct input_key_entry input_key_defaults[] = {
|
|||||||
{ .key = KEYC_DC|KEYC_BUILD_MODIFIERS,
|
{ .key = KEYC_DC|KEYC_BUILD_MODIFIERS,
|
||||||
.data = "\033[3;_~"
|
.data = "\033[3;_~"
|
||||||
},
|
},
|
||||||
|
{ .key = KEYC_REPORT_DARK_THEME,
|
||||||
|
.data = "\033[?997;1n"
|
||||||
|
},
|
||||||
|
{ .key = KEYC_REPORT_LIGHT_THEME,
|
||||||
|
.data = "\033[?997;2n"
|
||||||
|
},
|
||||||
};
|
};
|
||||||
static const key_code input_key_modifiers[] = {
|
static const key_code input_key_modifiers[] = {
|
||||||
0,
|
0,
|
||||||
|
139
input.c
139
input.c
@ -133,7 +133,7 @@ static void printflike(2, 3) input_reply(struct input_ctx *, const char *, ...);
|
|||||||
static void input_set_state(struct input_ctx *,
|
static void input_set_state(struct input_ctx *,
|
||||||
const struct input_transition *);
|
const struct input_transition *);
|
||||||
static void input_reset_cell(struct input_ctx *);
|
static void input_reset_cell(struct input_ctx *);
|
||||||
|
static void input_report_current_theme(struct input_ctx *);
|
||||||
static void input_osc_4(struct input_ctx *, const char *);
|
static void input_osc_4(struct input_ctx *, const char *);
|
||||||
static void input_osc_8(struct input_ctx *, const char *);
|
static void input_osc_8(struct input_ctx *, const char *);
|
||||||
static void input_osc_10(struct input_ctx *, const char *);
|
static void input_osc_10(struct input_ctx *, const char *);
|
||||||
@ -243,6 +243,7 @@ enum input_csi_type {
|
|||||||
INPUT_CSI_DECSTBM,
|
INPUT_CSI_DECSTBM,
|
||||||
INPUT_CSI_DL,
|
INPUT_CSI_DL,
|
||||||
INPUT_CSI_DSR,
|
INPUT_CSI_DSR,
|
||||||
|
INPUT_CSI_DSR_PRIVATE,
|
||||||
INPUT_CSI_ECH,
|
INPUT_CSI_ECH,
|
||||||
INPUT_CSI_ED,
|
INPUT_CSI_ED,
|
||||||
INPUT_CSI_EL,
|
INPUT_CSI_EL,
|
||||||
@ -251,6 +252,7 @@ enum input_csi_type {
|
|||||||
INPUT_CSI_IL,
|
INPUT_CSI_IL,
|
||||||
INPUT_CSI_MODOFF,
|
INPUT_CSI_MODOFF,
|
||||||
INPUT_CSI_MODSET,
|
INPUT_CSI_MODSET,
|
||||||
|
INPUT_CSI_QUERY_PRIVATE,
|
||||||
INPUT_CSI_RCP,
|
INPUT_CSI_RCP,
|
||||||
INPUT_CSI_REP,
|
INPUT_CSI_REP,
|
||||||
INPUT_CSI_RM,
|
INPUT_CSI_RM,
|
||||||
@ -259,8 +261,8 @@ enum input_csi_type {
|
|||||||
INPUT_CSI_SD,
|
INPUT_CSI_SD,
|
||||||
INPUT_CSI_SGR,
|
INPUT_CSI_SGR,
|
||||||
INPUT_CSI_SM,
|
INPUT_CSI_SM,
|
||||||
INPUT_CSI_SM_PRIVATE,
|
|
||||||
INPUT_CSI_SM_GRAPHICS,
|
INPUT_CSI_SM_GRAPHICS,
|
||||||
|
INPUT_CSI_SM_PRIVATE,
|
||||||
INPUT_CSI_SU,
|
INPUT_CSI_SU,
|
||||||
INPUT_CSI_TBC,
|
INPUT_CSI_TBC,
|
||||||
INPUT_CSI_VPA,
|
INPUT_CSI_VPA,
|
||||||
@ -304,6 +306,8 @@ static const struct input_table_entry input_csi_table[] = {
|
|||||||
{ 'm', ">", INPUT_CSI_MODSET },
|
{ 'm', ">", INPUT_CSI_MODSET },
|
||||||
{ 'n', "", INPUT_CSI_DSR },
|
{ 'n', "", INPUT_CSI_DSR },
|
||||||
{ 'n', ">", INPUT_CSI_MODOFF },
|
{ 'n', ">", INPUT_CSI_MODOFF },
|
||||||
|
{ 'n', "?", INPUT_CSI_DSR_PRIVATE },
|
||||||
|
{ 'p', "?$", INPUT_CSI_QUERY_PRIVATE },
|
||||||
{ 'q', " ", INPUT_CSI_DECSCUSR },
|
{ 'q', " ", INPUT_CSI_DECSCUSR },
|
||||||
{ 'q', ">", INPUT_CSI_XDA },
|
{ 'q', ">", INPUT_CSI_XDA },
|
||||||
{ 'r', "", INPUT_CSI_DECSTBM },
|
{ 'r', "", INPUT_CSI_DECSTBM },
|
||||||
@ -1531,6 +1535,20 @@ input_csi_dispatch(struct input_ctx *ictx)
|
|||||||
if (n != -1)
|
if (n != -1)
|
||||||
screen_write_deleteline(sctx, n, bg);
|
screen_write_deleteline(sctx, n, bg);
|
||||||
break;
|
break;
|
||||||
|
case INPUT_CSI_DSR_PRIVATE:
|
||||||
|
switch (input_get(ictx, 0, 0, 0)) {
|
||||||
|
case 996:
|
||||||
|
input_report_current_theme(ictx);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case INPUT_CSI_QUERY_PRIVATE:
|
||||||
|
switch (input_get(ictx, 0, 0, 0)) {
|
||||||
|
case 2031:
|
||||||
|
input_reply(ictx, "\033[?2031;2$y");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
case INPUT_CSI_DSR:
|
case INPUT_CSI_DSR:
|
||||||
switch (input_get(ictx, 0, 0, 0)) {
|
switch (input_get(ictx, 0, 0, 0)) {
|
||||||
case -1:
|
case -1:
|
||||||
@ -1781,6 +1799,9 @@ input_csi_dispatch_rm_private(struct input_ctx *ictx)
|
|||||||
case 2004:
|
case 2004:
|
||||||
screen_write_mode_clear(sctx, MODE_BRACKETPASTE);
|
screen_write_mode_clear(sctx, MODE_BRACKETPASTE);
|
||||||
break;
|
break;
|
||||||
|
case 2031:
|
||||||
|
screen_write_mode_clear(sctx, MODE_THEME_UPDATES);
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
log_debug("%s: unknown '%c'", __func__, ictx->ch);
|
log_debug("%s: unknown '%c'", __func__, ictx->ch);
|
||||||
break;
|
break;
|
||||||
@ -1876,6 +1897,9 @@ input_csi_dispatch_sm_private(struct input_ctx *ictx)
|
|||||||
case 2004:
|
case 2004:
|
||||||
screen_write_mode_set(sctx, MODE_BRACKETPASTE);
|
screen_write_mode_set(sctx, MODE_BRACKETPASTE);
|
||||||
break;
|
break;
|
||||||
|
case 2031:
|
||||||
|
screen_write_mode_set(sctx, MODE_THEME_UPDATES);
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
log_debug("%s: unknown '%c'", __func__, ictx->ch);
|
log_debug("%s: unknown '%c'", __func__, ictx->ch);
|
||||||
break;
|
break;
|
||||||
@ -2697,84 +2721,6 @@ bad:
|
|||||||
free(id);
|
free(id);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* Get a client with a foreground for the pane. There isn't much to choose
|
|
||||||
* between them so just use the first.
|
|
||||||
*/
|
|
||||||
static int
|
|
||||||
input_get_fg_client(struct window_pane *wp)
|
|
||||||
{
|
|
||||||
struct window *w = wp->window;
|
|
||||||
struct client *loop;
|
|
||||||
|
|
||||||
TAILQ_FOREACH(loop, &clients, entry) {
|
|
||||||
if (loop->flags & CLIENT_UNATTACHEDFLAGS)
|
|
||||||
continue;
|
|
||||||
if (loop->session == NULL || !session_has(loop->session, w))
|
|
||||||
continue;
|
|
||||||
if (loop->tty.fg == -1)
|
|
||||||
continue;
|
|
||||||
return (loop->tty.fg);
|
|
||||||
}
|
|
||||||
return (-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Get a client with a background for the pane. */
|
|
||||||
static int
|
|
||||||
input_get_bg_client(struct window_pane *wp)
|
|
||||||
{
|
|
||||||
struct window *w = wp->window;
|
|
||||||
struct client *loop;
|
|
||||||
|
|
||||||
TAILQ_FOREACH(loop, &clients, entry) {
|
|
||||||
if (loop->flags & CLIENT_UNATTACHEDFLAGS)
|
|
||||||
continue;
|
|
||||||
if (loop->session == NULL || !session_has(loop->session, w))
|
|
||||||
continue;
|
|
||||||
if (loop->tty.bg == -1)
|
|
||||||
continue;
|
|
||||||
return (loop->tty.bg);
|
|
||||||
}
|
|
||||||
return (-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If any control mode client exists that has provided a bg color, return it.
|
|
||||||
* Otherwise, return -1.
|
|
||||||
*/
|
|
||||||
static int
|
|
||||||
input_get_bg_control_client(struct window_pane *wp)
|
|
||||||
{
|
|
||||||
struct client *c;
|
|
||||||
|
|
||||||
if (wp->control_bg == -1)
|
|
||||||
return (-1);
|
|
||||||
|
|
||||||
TAILQ_FOREACH(c, &clients, entry) {
|
|
||||||
if (c->flags & CLIENT_CONTROL)
|
|
||||||
return (wp->control_bg);
|
|
||||||
}
|
|
||||||
return (-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If any control mode client exists that has provided a fg color, return it.
|
|
||||||
* Otherwise, return -1.
|
|
||||||
*/
|
|
||||||
static int
|
|
||||||
input_get_fg_control_client(struct window_pane *wp)
|
|
||||||
{
|
|
||||||
struct client *c;
|
|
||||||
|
|
||||||
if (wp->control_fg == -1)
|
|
||||||
return (-1);
|
|
||||||
|
|
||||||
TAILQ_FOREACH(c, &clients, entry) {
|
|
||||||
if (c->flags & CLIENT_CONTROL)
|
|
||||||
return (wp->control_fg);
|
|
||||||
}
|
|
||||||
return (-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Handle the OSC 10 sequence for setting and querying foreground colour. */
|
/* Handle the OSC 10 sequence for setting and querying foreground colour. */
|
||||||
static void
|
static void
|
||||||
@ -2787,11 +2733,11 @@ input_osc_10(struct input_ctx *ictx, const char *p)
|
|||||||
if (strcmp(p, "?") == 0) {
|
if (strcmp(p, "?") == 0) {
|
||||||
if (wp == NULL)
|
if (wp == NULL)
|
||||||
return;
|
return;
|
||||||
c = input_get_fg_control_client(wp);
|
c = window_pane_get_fg_control_client(wp);
|
||||||
if (c == -1) {
|
if (c == -1) {
|
||||||
tty_default_colours(&defaults, wp);
|
tty_default_colours(&defaults, wp);
|
||||||
if (COLOUR_DEFAULT(defaults.fg))
|
if (COLOUR_DEFAULT(defaults.fg))
|
||||||
c = input_get_fg_client(wp);
|
c = window_pane_get_fg(wp);
|
||||||
else
|
else
|
||||||
c = defaults.fg;
|
c = defaults.fg;
|
||||||
}
|
}
|
||||||
@ -2832,20 +2778,12 @@ static void
|
|||||||
input_osc_11(struct input_ctx *ictx, const char *p)
|
input_osc_11(struct input_ctx *ictx, const char *p)
|
||||||
{
|
{
|
||||||
struct window_pane *wp = ictx->wp;
|
struct window_pane *wp = ictx->wp;
|
||||||
struct grid_cell defaults;
|
|
||||||
int c;
|
int c;
|
||||||
|
|
||||||
if (strcmp(p, "?") == 0) {
|
if (strcmp(p, "?") == 0) {
|
||||||
if (wp == NULL)
|
if (wp == NULL)
|
||||||
return;
|
return;
|
||||||
c = input_get_bg_control_client(wp);
|
c = window_pane_get_bg(wp);
|
||||||
if (c == -1) {
|
|
||||||
tty_default_colours(&defaults, wp);
|
|
||||||
if (COLOUR_DEFAULT(defaults.bg))
|
|
||||||
c = input_get_bg_client(wp);
|
|
||||||
else
|
|
||||||
c = defaults.bg;
|
|
||||||
}
|
|
||||||
input_osc_colour_reply(ictx, 11, c);
|
input_osc_colour_reply(ictx, 11, c);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -2857,7 +2795,7 @@ input_osc_11(struct input_ctx *ictx, const char *p)
|
|||||||
if (ictx->palette != NULL) {
|
if (ictx->palette != NULL) {
|
||||||
ictx->palette->bg = c;
|
ictx->palette->bg = c;
|
||||||
if (wp != NULL)
|
if (wp != NULL)
|
||||||
wp->flags |= PANE_STYLECHANGED;
|
wp->flags |= (PANE_STYLECHANGED|PANE_THEMECHANGED);
|
||||||
screen_write_fullredraw(&ictx->ctx);
|
screen_write_fullredraw(&ictx->ctx);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -2873,7 +2811,7 @@ input_osc_111(struct input_ctx *ictx, const char *p)
|
|||||||
if (ictx->palette != NULL) {
|
if (ictx->palette != NULL) {
|
||||||
ictx->palette->bg = 8;
|
ictx->palette->bg = 8;
|
||||||
if (wp != NULL)
|
if (wp != NULL)
|
||||||
wp->flags |= PANE_STYLECHANGED;
|
wp->flags |= (PANE_STYLECHANGED|PANE_THEMECHANGED);
|
||||||
screen_write_fullredraw(&ictx->ctx);
|
screen_write_fullredraw(&ictx->ctx);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -3064,3 +3002,18 @@ input_set_buffer_size(size_t buffer_size)
|
|||||||
log_debug("%s: %lu -> %lu", __func__, input_buffer_size, buffer_size);
|
log_debug("%s: %lu -> %lu", __func__, input_buffer_size, buffer_size);
|
||||||
input_buffer_size = buffer_size;
|
input_buffer_size = buffer_size;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
input_report_current_theme(struct input_ctx *ictx)
|
||||||
|
{
|
||||||
|
switch (window_pane_get_theme(ictx->wp)) {
|
||||||
|
case THEME_DARK:
|
||||||
|
input_reply(ictx, "\033[?997;1n");
|
||||||
|
break;
|
||||||
|
case THEME_LIGHT:
|
||||||
|
input_reply(ictx, "\033[?997;2n");
|
||||||
|
break;
|
||||||
|
case THEME_UNKNOWN:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
22
mode-tree.c
22
mode-tree.c
@ -66,6 +66,7 @@ struct mode_tree_data {
|
|||||||
u_int line_size;
|
u_int line_size;
|
||||||
|
|
||||||
u_int depth;
|
u_int depth;
|
||||||
|
u_int maxdepth;
|
||||||
|
|
||||||
u_int width;
|
u_int width;
|
||||||
u_int height;
|
u_int height;
|
||||||
@ -196,6 +197,8 @@ mode_tree_build_lines(struct mode_tree_data *mtd,
|
|||||||
int flat = 1;
|
int flat = 1;
|
||||||
|
|
||||||
mtd->depth = depth;
|
mtd->depth = depth;
|
||||||
|
if (depth > mtd->maxdepth)
|
||||||
|
mtd->maxdepth = depth;
|
||||||
TAILQ_FOREACH(mti, mtl, entry) {
|
TAILQ_FOREACH(mti, mtl, entry) {
|
||||||
mtd->line_list = xreallocarray(mtd->line_list,
|
mtd->line_list = xreallocarray(mtd->line_list,
|
||||||
mtd->line_size + 1, sizeof *mtd->line_list);
|
mtd->line_size + 1, sizeof *mtd->line_list);
|
||||||
@ -528,6 +531,7 @@ mode_tree_build(struct mode_tree_data *mtd)
|
|||||||
TAILQ_INIT(&mtd->saved);
|
TAILQ_INIT(&mtd->saved);
|
||||||
|
|
||||||
mode_tree_clear_lines(mtd);
|
mode_tree_clear_lines(mtd);
|
||||||
|
mtd->maxdepth = 0;
|
||||||
mode_tree_build_lines(mtd, &mtd->children, 0);
|
mode_tree_build_lines(mtd, &mtd->children, 0);
|
||||||
|
|
||||||
if (mtd->line_list != NULL && tag == UINT64_MAX)
|
if (mtd->line_list != NULL && tag == UINT64_MAX)
|
||||||
@ -658,7 +662,7 @@ mode_tree_draw(struct mode_tree_data *mtd)
|
|||||||
char *text, *start, *key;
|
char *text, *start, *key;
|
||||||
const char *tag, *symbol;
|
const char *tag, *symbol;
|
||||||
size_t size, n;
|
size_t size, n;
|
||||||
int keylen, pad;
|
int keylen, pad, namelen[mtd->maxdepth + 1];
|
||||||
|
|
||||||
if (mtd->line_size == 0)
|
if (mtd->line_size == 0)
|
||||||
return;
|
return;
|
||||||
@ -682,6 +686,15 @@ mode_tree_draw(struct mode_tree_data *mtd)
|
|||||||
keylen = mti->keylen + 3;
|
keylen = mti->keylen + 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (i = 0; i < mtd->maxdepth + 1; i++)
|
||||||
|
namelen[i] = 0;
|
||||||
|
for (i = 0; i < mtd->line_size; i++) {
|
||||||
|
line = &mtd->line_list[i];
|
||||||
|
mti = line->item;
|
||||||
|
if ((int)strlen(mti->name) > namelen[line->depth])
|
||||||
|
namelen[line->depth] = strlen(mti->name);
|
||||||
|
}
|
||||||
|
|
||||||
for (i = 0; i < mtd->line_size; i++) {
|
for (i = 0; i < mtd->line_size; i++) {
|
||||||
if (i < mtd->offset)
|
if (i < mtd->offset)
|
||||||
continue;
|
continue;
|
||||||
@ -731,8 +744,9 @@ mode_tree_draw(struct mode_tree_data *mtd)
|
|||||||
tag = "*";
|
tag = "*";
|
||||||
else
|
else
|
||||||
tag = "";
|
tag = "";
|
||||||
xasprintf(&text, "%-*s%s%s%s%s", keylen, key, start, mti->name,
|
xasprintf(&text, "%-*s%s%*s%s%s", keylen, key, start,
|
||||||
tag, (mti->text != NULL) ? ": " : "" );
|
namelen[line->depth], mti->name, tag,
|
||||||
|
(mti->text != NULL) ? ": " : "" );
|
||||||
width = utf8_cstrwidth(text);
|
width = utf8_cstrwidth(text);
|
||||||
if (width > w)
|
if (width > w)
|
||||||
width = w;
|
width = w;
|
||||||
@ -1297,7 +1311,7 @@ mode_tree_run_command(struct client *c, struct cmd_find_state *fs,
|
|||||||
if (status == CMD_PARSE_ERROR) {
|
if (status == CMD_PARSE_ERROR) {
|
||||||
if (c != NULL) {
|
if (c != NULL) {
|
||||||
*error = toupper((u_char)*error);
|
*error = toupper((u_char)*error);
|
||||||
status_message_set(c, -1, 1, 0, "%s", error);
|
status_message_set(c, -1, 1, 0, 0, "%s", error);
|
||||||
}
|
}
|
||||||
free(error);
|
free(error);
|
||||||
}
|
}
|
||||||
|
@ -1454,6 +1454,8 @@ const struct options_table_entry options_table[] = {
|
|||||||
OPTIONS_TABLE_HOOK("client-focus-out", ""),
|
OPTIONS_TABLE_HOOK("client-focus-out", ""),
|
||||||
OPTIONS_TABLE_HOOK("client-resized", ""),
|
OPTIONS_TABLE_HOOK("client-resized", ""),
|
||||||
OPTIONS_TABLE_HOOK("client-session-changed", ""),
|
OPTIONS_TABLE_HOOK("client-session-changed", ""),
|
||||||
|
OPTIONS_TABLE_HOOK("client-light-theme", ""),
|
||||||
|
OPTIONS_TABLE_HOOK("client-dark-theme", ""),
|
||||||
OPTIONS_TABLE_HOOK("command-error", ""),
|
OPTIONS_TABLE_HOOK("command-error", ""),
|
||||||
OPTIONS_TABLE_PANE_HOOK("pane-died", ""),
|
OPTIONS_TABLE_PANE_HOOK("pane-died", ""),
|
||||||
OPTIONS_TABLE_PANE_HOOK("pane-exited", ""),
|
OPTIONS_TABLE_PANE_HOOK("pane-exited", ""),
|
||||||
|
@ -1165,7 +1165,7 @@ options_push_changes(const char *name)
|
|||||||
if (strcmp(name, "window-style") == 0 ||
|
if (strcmp(name, "window-style") == 0 ||
|
||||||
strcmp(name, "window-active-style") == 0) {
|
strcmp(name, "window-active-style") == 0) {
|
||||||
RB_FOREACH(wp, window_pane_tree, &all_window_panes)
|
RB_FOREACH(wp, window_pane_tree, &all_window_panes)
|
||||||
wp->flags |= PANE_STYLECHANGED;
|
wp->flags |= (PANE_STYLECHANGED|PANE_THEMECHANGED);
|
||||||
}
|
}
|
||||||
if (strcmp(name, "pane-colours") == 0) {
|
if (strcmp(name, "pane-colours") == 0) {
|
||||||
RB_FOREACH(wp, window_pane_tree, &all_window_panes)
|
RB_FOREACH(wp, window_pane_tree, &all_window_panes)
|
||||||
|
@ -433,11 +433,15 @@ screen_redraw_make_pane_status(struct client *c, struct window_pane *wp,
|
|||||||
const char *fmt;
|
const char *fmt;
|
||||||
struct format_tree *ft;
|
struct format_tree *ft;
|
||||||
char *expanded;
|
char *expanded;
|
||||||
int pane_status = rctx->pane_status;
|
int pane_status = rctx->pane_status, sb_w = 0;
|
||||||
|
int pane_scrollbars = rctx->pane_scrollbars;
|
||||||
u_int width, i, cell_type, px, py;
|
u_int width, i, cell_type, px, py;
|
||||||
struct screen_write_ctx ctx;
|
struct screen_write_ctx ctx;
|
||||||
struct screen old;
|
struct screen old;
|
||||||
|
|
||||||
|
if (window_pane_show_scrollbar(wp, pane_scrollbars))
|
||||||
|
sb_w = wp->scrollbar_style.width + wp->scrollbar_style.pad;
|
||||||
|
|
||||||
ft = format_create(c, NULL, FORMAT_PANE|wp->id, FORMAT_STATUS);
|
ft = format_create(c, NULL, FORMAT_PANE|wp->id, FORMAT_STATUS);
|
||||||
format_defaults(ft, c, c->session, c->session->curw, wp);
|
format_defaults(ft, c, c->session, c->session->curw, wp);
|
||||||
|
|
||||||
@ -451,7 +455,7 @@ screen_redraw_make_pane_status(struct client *c, struct window_pane *wp,
|
|||||||
if (wp->sx < 4)
|
if (wp->sx < 4)
|
||||||
wp->status_size = width = 0;
|
wp->status_size = width = 0;
|
||||||
else
|
else
|
||||||
wp->status_size = width = wp->sx - 4;
|
wp->status_size = width = wp->sx + sb_w - 2;
|
||||||
|
|
||||||
memcpy(&old, &wp->status_screen, sizeof old);
|
memcpy(&old, &wp->status_screen, sizeof old);
|
||||||
screen_init(&wp->status_screen, width, 1, 0);
|
screen_init(&wp->status_screen, width, 1, 0);
|
||||||
|
@ -56,11 +56,11 @@ static void server_client_set_title(struct client *);
|
|||||||
static void server_client_set_path(struct client *);
|
static void server_client_set_path(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 void server_client_dispatch(struct imsg *, void *);
|
static void server_client_dispatch(struct imsg *, void *);
|
||||||
static void server_client_dispatch_command(struct client *, struct imsg *);
|
static void server_client_dispatch_command(struct client *, struct imsg *);
|
||||||
static void server_client_dispatch_identify(struct client *, struct imsg *);
|
static void server_client_dispatch_identify(struct client *, struct imsg *);
|
||||||
static void server_client_dispatch_shell(struct client *);
|
static void server_client_dispatch_shell(struct client *);
|
||||||
|
static void server_client_report_theme(struct client *, enum client_theme);
|
||||||
|
|
||||||
/* Compare client windows. */
|
/* Compare client windows. */
|
||||||
static int
|
static int
|
||||||
@ -152,6 +152,7 @@ server_client_clear_overlay(struct client *c)
|
|||||||
c->overlay_draw = NULL;
|
c->overlay_draw = NULL;
|
||||||
c->overlay_key = NULL;
|
c->overlay_key = NULL;
|
||||||
c->overlay_free = NULL;
|
c->overlay_free = NULL;
|
||||||
|
c->overlay_resize = NULL;
|
||||||
c->overlay_data = NULL;
|
c->overlay_data = NULL;
|
||||||
|
|
||||||
c->tty.flags &= ~(TTY_FREEZE|TTY_NOCURSOR);
|
c->tty.flags &= ~(TTY_FREEZE|TTY_NOCURSOR);
|
||||||
@ -299,6 +300,7 @@ server_client_create(int fd)
|
|||||||
|
|
||||||
c->tty.sx = 80;
|
c->tty.sx = 80;
|
||||||
c->tty.sy = 24;
|
c->tty.sy = 24;
|
||||||
|
c->theme = THEME_UNKNOWN;
|
||||||
|
|
||||||
status_init(c);
|
status_init(c);
|
||||||
c->flags |= CLIENT_FOCUSED;
|
c->flags |= CLIENT_FOCUSED;
|
||||||
@ -400,6 +402,7 @@ server_client_set_session(struct client *c, struct session *s)
|
|||||||
recalculate_sizes();
|
recalculate_sizes();
|
||||||
window_update_focus(s->curw->window);
|
window_update_focus(s->curw->window);
|
||||||
session_update_activity(s, NULL);
|
session_update_activity(s, NULL);
|
||||||
|
session_theme_changed(s);
|
||||||
gettimeofday(&s->last_attached_time, NULL);
|
gettimeofday(&s->last_attached_time, NULL);
|
||||||
s->curw->flags &= ~WINLINK_ALERTFLAGS;
|
s->curw->flags &= ~WINLINK_ALERTFLAGS;
|
||||||
s->curw->window->latest = c;
|
s->curw->window->latest = c;
|
||||||
@ -2242,13 +2245,13 @@ out:
|
|||||||
static int
|
static int
|
||||||
server_client_is_bracket_paste(struct client *c, key_code key)
|
server_client_is_bracket_paste(struct client *c, key_code key)
|
||||||
{
|
{
|
||||||
if (key == KEYC_PASTE_START) {
|
if ((key & KEYC_MASK_KEY) == KEYC_PASTE_START) {
|
||||||
c->flags |= CLIENT_BRACKETPASTING;
|
c->flags |= CLIENT_BRACKETPASTING;
|
||||||
log_debug("%s: bracket paste on", c->name);
|
log_debug("%s: bracket paste on", c->name);
|
||||||
return (0);
|
return (0);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (key == KEYC_PASTE_END) {
|
if ((key & KEYC_MASK_KEY) == KEYC_PASTE_END) {
|
||||||
c->flags &= ~CLIENT_BRACKETPASTING;
|
c->flags &= ~CLIENT_BRACKETPASTING;
|
||||||
log_debug("%s: bracket paste off", c->name);
|
log_debug("%s: bracket paste off", c->name);
|
||||||
return (0);
|
return (0);
|
||||||
@ -2383,6 +2386,16 @@ server_client_key_callback(struct cmdq_item *item, void *data)
|
|||||||
event->key = key;
|
event->key = key;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Handle theme reporting keys. */
|
||||||
|
if (key == KEYC_REPORT_LIGHT_THEME) {
|
||||||
|
server_client_report_theme(c, THEME_LIGHT);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
if (key == KEYC_REPORT_DARK_THEME) {
|
||||||
|
server_client_report_theme(c, THEME_DARK);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
/* Find affected pane. */
|
/* Find affected pane. */
|
||||||
if (!KEYC_IS_MOUSE(key) || cmd_find_from_mouse(&fs, m, 0) != 0)
|
if (!KEYC_IS_MOUSE(key) || cmd_find_from_mouse(&fs, m, 0) != 0)
|
||||||
cmd_find_from_client(&fs, c, 0);
|
cmd_find_from_client(&fs, c, 0);
|
||||||
@ -2673,6 +2686,12 @@ server_client_loop(void)
|
|||||||
}
|
}
|
||||||
check_window_name(w);
|
check_window_name(w);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Send theme updates. */
|
||||||
|
RB_FOREACH(w, windows, &windows) {
|
||||||
|
TAILQ_FOREACH(wp, &w->panes, entry)
|
||||||
|
window_pane_send_theme_update(wp);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Check if window needs to be resized. */
|
/* Check if window needs to be resized. */
|
||||||
@ -3909,3 +3928,21 @@ out:
|
|||||||
if (!parse)
|
if (!parse)
|
||||||
free(msg);
|
free(msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
server_client_report_theme(struct client *c, enum client_theme theme)
|
||||||
|
{
|
||||||
|
if (theme == THEME_LIGHT) {
|
||||||
|
c->theme = THEME_LIGHT;
|
||||||
|
notify_client("client-light-theme", c);
|
||||||
|
} else {
|
||||||
|
c->theme = THEME_DARK;
|
||||||
|
notify_client("client-dark-theme", c);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Request foreground and background colour again. Don't forward 2031 to
|
||||||
|
* panes until a response is received.
|
||||||
|
*/
|
||||||
|
tty_puts(&c->tty, "\033]10;?\033\\\033]11;?\033\\");
|
||||||
|
}
|
||||||
|
13
session.c
13
session.c
@ -751,3 +751,16 @@ session_renumber_windows(struct session *s)
|
|||||||
RB_FOREACH_SAFE(wl, winlinks, &old_wins, wl1)
|
RB_FOREACH_SAFE(wl, winlinks, &old_wins, wl1)
|
||||||
winlink_remove(&old_wins, wl);
|
winlink_remove(&old_wins, wl);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Set the PANE_THEMECHANGED flag for every pane in this session. */
|
||||||
|
void
|
||||||
|
session_theme_changed(struct session *s)
|
||||||
|
{
|
||||||
|
struct window_pane *wp;
|
||||||
|
struct winlink *wl;
|
||||||
|
|
||||||
|
RB_FOREACH(wl, winlinks, &s->windows) {
|
||||||
|
TAILQ_FOREACH(wp, &wl->window->panes, entry)
|
||||||
|
wp->flags |= PANE_THEMECHANGED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
6
status.c
6
status.c
@ -470,7 +470,7 @@ status_redraw(struct client *c)
|
|||||||
/* Set a status line message. */
|
/* Set a status line message. */
|
||||||
void
|
void
|
||||||
status_message_set(struct client *c, int delay, int ignore_styles,
|
status_message_set(struct client *c, int delay, int ignore_styles,
|
||||||
int ignore_keys, const char *fmt, ...)
|
int ignore_keys, int no_freeze, const char *fmt, ...)
|
||||||
{
|
{
|
||||||
struct timeval tv;
|
struct timeval tv;
|
||||||
va_list ap;
|
va_list ap;
|
||||||
@ -514,7 +514,9 @@ status_message_set(struct client *c, int delay, int ignore_styles,
|
|||||||
c->message_ignore_keys = ignore_keys;
|
c->message_ignore_keys = ignore_keys;
|
||||||
c->message_ignore_styles = ignore_styles;
|
c->message_ignore_styles = ignore_styles;
|
||||||
|
|
||||||
c->tty.flags |= (TTY_NOCURSOR|TTY_FREEZE);
|
if (!no_freeze)
|
||||||
|
c->tty.flags |= TTY_FREEZE;
|
||||||
|
c->tty.flags |= TTY_NOCURSOR;
|
||||||
c->flags |= CLIENT_REDRAWSTATUS;
|
c->flags |= CLIENT_REDRAWSTATUS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
25
tmux.1
25
tmux.1
@ -2331,6 +2331,15 @@ repeats the last search and
|
|||||||
does the same but reverses the direction (forward becomes backward and backward
|
does the same but reverses the direction (forward becomes backward and backward
|
||||||
becomes forward).
|
becomes forward).
|
||||||
.Pp
|
.Pp
|
||||||
|
The default incremental search key bindings,
|
||||||
|
.Ql C-r
|
||||||
|
and
|
||||||
|
.Ql C-s ,
|
||||||
|
are designed to emulate
|
||||||
|
.Xr emacs 1 .
|
||||||
|
When first pressed they allow a new search term to be entered; if pressed with
|
||||||
|
an empty search term they repeat the previously used search term.
|
||||||
|
.Pp
|
||||||
The
|
The
|
||||||
.Ql next-prompt
|
.Ql next-prompt
|
||||||
and
|
and
|
||||||
@ -2547,7 +2556,7 @@ but a different format may be specified with
|
|||||||
.Fl F .
|
.Fl F .
|
||||||
.Tg capturep
|
.Tg capturep
|
||||||
.It Xo Ic capture-pane
|
.It Xo Ic capture-pane
|
||||||
.Op Fl aAepPqCJN
|
.Op Fl aepPqCJMN
|
||||||
.Op Fl b Ar buffer-name
|
.Op Fl b Ar buffer-name
|
||||||
.Op Fl E Ar end-line
|
.Op Fl E Ar end-line
|
||||||
.Op Fl S Ar start-line
|
.Op Fl S Ar start-line
|
||||||
@ -2566,6 +2575,9 @@ is given, the alternate screen is used, and the history is not accessible.
|
|||||||
If no alternate screen exists, an error will be returned unless
|
If no alternate screen exists, an error will be returned unless
|
||||||
.Fl q
|
.Fl q
|
||||||
is given.
|
is given.
|
||||||
|
Similarly, if the pane is in a mode,
|
||||||
|
.Fl M
|
||||||
|
uses the screen for the mode.
|
||||||
If
|
If
|
||||||
.Fl e
|
.Fl e
|
||||||
is given, the output includes escape sequences for text and background
|
is given, the output includes escape sequences for text and background
|
||||||
@ -5857,6 +5869,12 @@ with
|
|||||||
.Ql bar/
|
.Ql bar/
|
||||||
throughout.
|
throughout.
|
||||||
.Pp
|
.Pp
|
||||||
|
Multiple modifiers may be separated with a semicolon (;) as in
|
||||||
|
.Ql #{T;=10:status-left} ,
|
||||||
|
which limits the resulting
|
||||||
|
.Xr strftime 3 -expanded
|
||||||
|
string to at most 10 characters.
|
||||||
|
.Pp
|
||||||
In addition, the last line of a shell command's output may be inserted using
|
In addition, the last line of a shell command's output may be inserted using
|
||||||
.Ql #() .
|
.Ql #() .
|
||||||
For example,
|
For example,
|
||||||
@ -6744,7 +6762,7 @@ The following keys are available in menus:
|
|||||||
.El
|
.El
|
||||||
.Tg display
|
.Tg display
|
||||||
.It Xo Ic display-message
|
.It Xo Ic display-message
|
||||||
.Op Fl aIlNpv
|
.Op Fl aCIlNpv
|
||||||
.Op Fl c Ar target-client
|
.Op Fl c Ar target-client
|
||||||
.Op Fl d Ar delay
|
.Op Fl d Ar delay
|
||||||
.Op Fl t Ar target-pane
|
.Op Fl t Ar target-pane
|
||||||
@ -6767,6 +6785,9 @@ option is used; a delay of zero waits for a key press.
|
|||||||
.Ql N
|
.Ql N
|
||||||
ignores key presses and closes only after the delay expires.
|
ignores key presses and closes only after the delay expires.
|
||||||
If
|
If
|
||||||
|
.Fl C
|
||||||
|
is given, the pane will continue to be updated while the message is displayed.
|
||||||
|
If
|
||||||
.Fl l
|
.Fl l
|
||||||
is given,
|
is given,
|
||||||
.Ar message
|
.Ar message
|
||||||
|
40
tmux.h
40
tmux.h
@ -176,7 +176,8 @@ struct winlink;
|
|||||||
|
|
||||||
/* Is this a paste key? */
|
/* Is this a paste key? */
|
||||||
#define KEYC_IS_PASTE(key) \
|
#define KEYC_IS_PASTE(key) \
|
||||||
((key) == KEYC_PASTE_START || (key) == KEYC_PASTE_END)
|
(((key) & KEYC_MASK_KEY) == KEYC_PASTE_START || \
|
||||||
|
((key) & KEYC_MASK_KEY) == KEYC_PASTE_END)
|
||||||
|
|
||||||
/* Multiple click timeout. */
|
/* Multiple click timeout. */
|
||||||
#define KEYC_CLICK_TIMEOUT 300
|
#define KEYC_CLICK_TIMEOUT 300
|
||||||
@ -377,6 +378,10 @@ enum {
|
|||||||
KEYC_KP_ZERO,
|
KEYC_KP_ZERO,
|
||||||
KEYC_KP_PERIOD,
|
KEYC_KP_PERIOD,
|
||||||
|
|
||||||
|
/* Theme reporting. */
|
||||||
|
KEYC_REPORT_DARK_THEME,
|
||||||
|
KEYC_REPORT_LIGHT_THEME,
|
||||||
|
|
||||||
/* End of special keys. */
|
/* End of special keys. */
|
||||||
KEYC_BASE_END
|
KEYC_BASE_END
|
||||||
};
|
};
|
||||||
@ -644,6 +649,7 @@ enum tty_code_code {
|
|||||||
#define MODE_CURSOR_VERY_VISIBLE 0x10000
|
#define MODE_CURSOR_VERY_VISIBLE 0x10000
|
||||||
#define MODE_CURSOR_BLINKING_SET 0x20000
|
#define MODE_CURSOR_BLINKING_SET 0x20000
|
||||||
#define MODE_KEYS_EXTENDED_2 0x40000
|
#define MODE_KEYS_EXTENDED_2 0x40000
|
||||||
|
#define MODE_THEME_UPDATES 0x80000
|
||||||
|
|
||||||
#define ALL_MODES 0xffffff
|
#define ALL_MODES 0xffffff
|
||||||
#define ALL_MOUSE_MODES (MODE_MOUSE_STANDARD|MODE_MOUSE_BUTTON|MODE_MOUSE_ALL)
|
#define ALL_MOUSE_MODES (MODE_MOUSE_STANDARD|MODE_MOUSE_BUTTON|MODE_MOUSE_ALL)
|
||||||
@ -1090,6 +1096,7 @@ struct window_mode {
|
|||||||
struct mouse_event *);
|
struct mouse_event *);
|
||||||
void (*formats)(struct window_mode_entry *,
|
void (*formats)(struct window_mode_entry *,
|
||||||
struct format_tree *);
|
struct format_tree *);
|
||||||
|
struct screen *(*get_screen)(struct window_mode_entry *);
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Active window mode. */
|
/* Active window mode. */
|
||||||
@ -1154,8 +1161,9 @@ struct window_pane {
|
|||||||
#define PANE_STATUSDRAWN 0x400
|
#define PANE_STATUSDRAWN 0x400
|
||||||
#define PANE_EMPTY 0x800
|
#define PANE_EMPTY 0x800
|
||||||
#define PANE_STYLECHANGED 0x1000
|
#define PANE_STYLECHANGED 0x1000
|
||||||
#define PANE_UNSEENCHANGES 0x2000
|
#define PANE_THEMECHANGED 0x2000
|
||||||
#define PANE_REDRAWSCROLLBAR 0x4000
|
#define PANE_UNSEENCHANGES 0x4000
|
||||||
|
#define PANE_REDRAWSCROLLBAR 0x8000
|
||||||
|
|
||||||
u_int sb_slider_y;
|
u_int sb_slider_y;
|
||||||
u_int sb_slider_h;
|
u_int sb_slider_h;
|
||||||
@ -1863,6 +1871,16 @@ struct overlay_ranges {
|
|||||||
u_int nx[OVERLAY_MAX_RANGES];
|
u_int nx[OVERLAY_MAX_RANGES];
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Client theme, this is worked out from the background colour if not reported
|
||||||
|
* by terminal.
|
||||||
|
*/
|
||||||
|
enum client_theme {
|
||||||
|
THEME_UNKNOWN,
|
||||||
|
THEME_LIGHT,
|
||||||
|
THEME_DARK
|
||||||
|
};
|
||||||
|
|
||||||
/* Client connection. */
|
/* Client connection. */
|
||||||
typedef int (*prompt_input_cb)(struct client *, void *, const char *, int);
|
typedef int (*prompt_input_cb)(struct client *, void *, const char *, int);
|
||||||
typedef void (*prompt_free_cb)(void *);
|
typedef void (*prompt_free_cb)(void *);
|
||||||
@ -1922,6 +1940,7 @@ struct client {
|
|||||||
struct mouse_event click_event;
|
struct mouse_event click_event;
|
||||||
|
|
||||||
struct status_line status;
|
struct status_line status;
|
||||||
|
enum client_theme theme;
|
||||||
|
|
||||||
#define CLIENT_TERMINAL 0x1
|
#define CLIENT_TERMINAL 0x1
|
||||||
#define CLIENT_LOGIN 0x2
|
#define CLIENT_LOGIN 0x2
|
||||||
@ -2641,6 +2660,7 @@ int cmd_find_from_nothing(struct cmd_find_state *, int);
|
|||||||
|
|
||||||
/* cmd.c */
|
/* cmd.c */
|
||||||
extern const struct cmd_entry *cmd_table[];
|
extern const struct cmd_entry *cmd_table[];
|
||||||
|
const struct cmd_entry *cmd_find(const char *, char **);
|
||||||
void printflike(3, 4) cmd_log_argv(int, char **, const char *, ...);
|
void printflike(3, 4) cmd_log_argv(int, char **, const char *, ...);
|
||||||
void cmd_prepend_argv(int *, char ***, const char *);
|
void cmd_prepend_argv(int *, char ***, const char *);
|
||||||
void cmd_append_argv(int *, char ***, const char *);
|
void cmd_append_argv(int *, char ***, const char *);
|
||||||
@ -2890,7 +2910,7 @@ struct style_range *status_get_range(struct client *, u_int, u_int);
|
|||||||
void status_init(struct client *);
|
void status_init(struct client *);
|
||||||
void status_free(struct client *);
|
void status_free(struct client *);
|
||||||
int status_redraw(struct client *);
|
int status_redraw(struct client *);
|
||||||
void printflike(5, 6) status_message_set(struct client *, int, int, int,
|
void printflike(6, 7) status_message_set(struct client *, int, int, int, int,
|
||||||
const char *, ...);
|
const char *, ...);
|
||||||
void status_message_clear(struct client *);
|
void status_message_clear(struct client *);
|
||||||
int status_message_redraw(struct client *);
|
int status_message_redraw(struct client *);
|
||||||
@ -2942,7 +2962,8 @@ int colour_join_rgb(u_char, u_char, u_char);
|
|||||||
void colour_split_rgb(int, u_char *, u_char *, u_char *);
|
void colour_split_rgb(int, u_char *, u_char *, u_char *);
|
||||||
int colour_force_rgb(int);
|
int colour_force_rgb(int);
|
||||||
const char *colour_tostring(int);
|
const char *colour_tostring(int);
|
||||||
int colour_fromstring(const char *s);
|
enum client_theme colour_totheme(int);
|
||||||
|
int colour_fromstring(const char *);
|
||||||
int colour_256toRGB(int);
|
int colour_256toRGB(int);
|
||||||
int colour_256to16(int);
|
int colour_256to16(int);
|
||||||
int colour_byname(const char *);
|
int colour_byname(const char *);
|
||||||
@ -3243,6 +3264,13 @@ void window_set_fill_character(struct window *);
|
|||||||
void window_pane_default_cursor(struct window_pane *);
|
void window_pane_default_cursor(struct window_pane *);
|
||||||
int window_pane_mode(struct window_pane *);
|
int window_pane_mode(struct window_pane *);
|
||||||
int window_pane_show_scrollbar(struct window_pane *, int);
|
int window_pane_show_scrollbar(struct window_pane *, int);
|
||||||
|
int window_pane_get_bg(struct window_pane *);
|
||||||
|
int window_pane_get_fg(struct window_pane *);
|
||||||
|
int window_pane_get_fg_control_client(struct window_pane *);
|
||||||
|
int window_pane_get_bg_control_client(struct window_pane *);
|
||||||
|
int window_get_bg_client(struct window_pane *);
|
||||||
|
enum client_theme window_pane_get_theme(struct window_pane *);
|
||||||
|
void window_pane_send_theme_update(struct window_pane *);
|
||||||
|
|
||||||
/* layout.c */
|
/* layout.c */
|
||||||
u_int layout_count_cells(struct layout_cell *);
|
u_int layout_count_cells(struct layout_cell *);
|
||||||
@ -3440,11 +3468,11 @@ void session_group_synchronize_from(struct session *);
|
|||||||
u_int session_group_count(struct session_group *);
|
u_int session_group_count(struct session_group *);
|
||||||
u_int session_group_attached_count(struct session_group *);
|
u_int session_group_attached_count(struct session_group *);
|
||||||
void session_renumber_windows(struct session *);
|
void session_renumber_windows(struct session *);
|
||||||
|
void session_theme_changed(struct session *);
|
||||||
|
|
||||||
/* utf8.c */
|
/* utf8.c */
|
||||||
enum utf8_state utf8_towc (const struct utf8_data *, wchar_t *);
|
enum utf8_state utf8_towc (const struct utf8_data *, wchar_t *);
|
||||||
enum utf8_state utf8_fromwc(wchar_t wc, struct utf8_data *);
|
enum utf8_state utf8_fromwc(wchar_t wc, struct utf8_data *);
|
||||||
int utf8_in_table(wchar_t, const wchar_t *, u_int);
|
|
||||||
void utf8_update_width_cache(void);
|
void utf8_update_width_cache(void);
|
||||||
utf8_char utf8_build_one(u_char);
|
utf8_char utf8_build_one(u_char);
|
||||||
enum utf8_state utf8_from_data(const struct utf8_data *, utf8_char *);
|
enum utf8_state utf8_from_data(const struct utf8_data *, utf8_char *);
|
||||||
|
15
tty-keys.c
15
tty-keys.c
@ -208,11 +208,15 @@ static const struct tty_default_key_raw tty_default_raw_keys[] = {
|
|||||||
{ "\033[O", KEYC_FOCUS_OUT },
|
{ "\033[O", KEYC_FOCUS_OUT },
|
||||||
|
|
||||||
/* Paste keys. */
|
/* Paste keys. */
|
||||||
{ "\033[200~", KEYC_PASTE_START },
|
{ "\033[200~", KEYC_PASTE_START|KEYC_IMPLIED_META },
|
||||||
{ "\033[201~", KEYC_PASTE_END },
|
{ "\033[201~", KEYC_PASTE_END|KEYC_IMPLIED_META },
|
||||||
|
|
||||||
/* Extended keys. */
|
/* Extended keys. */
|
||||||
{ "\033[1;5Z", '\011'|KEYC_CTRL|KEYC_SHIFT },
|
{ "\033[1;5Z", '\011'|KEYC_CTRL|KEYC_SHIFT },
|
||||||
|
|
||||||
|
/* Theme reporting. */
|
||||||
|
{ "\033[?997;1n", KEYC_REPORT_DARK_THEME },
|
||||||
|
{ "\033[?997;2n", KEYC_REPORT_LIGHT_THEME },
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Default xterm keys. */
|
/* Default xterm keys. */
|
||||||
@ -791,10 +795,12 @@ tty_keys_next(struct tty *tty)
|
|||||||
switch (tty_keys_colours(tty, buf, len, &size, &tty->fg, &tty->bg)) {
|
switch (tty_keys_colours(tty, buf, len, &size, &tty->fg, &tty->bg)) {
|
||||||
case 0: /* yes */
|
case 0: /* yes */
|
||||||
key = KEYC_UNKNOWN;
|
key = KEYC_UNKNOWN;
|
||||||
|
session_theme_changed(tty->client->session);
|
||||||
goto complete_key;
|
goto complete_key;
|
||||||
case -1: /* no, or not valid */
|
case -1: /* no, or not valid */
|
||||||
break;
|
break;
|
||||||
case 1: /* partial */
|
case 1: /* partial */
|
||||||
|
session_theme_changed(tty->client->session);
|
||||||
goto partial_key;
|
goto partial_key;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -931,6 +937,11 @@ partial_key:
|
|||||||
delay = options_get_number(global_options, "escape-time");
|
delay = options_get_number(global_options, "escape-time");
|
||||||
if (delay == 0)
|
if (delay == 0)
|
||||||
delay = 1;
|
delay = 1;
|
||||||
|
if ((tty->flags & TTY_ALL_REQUEST_FLAGS) != TTY_ALL_REQUEST_FLAGS) {
|
||||||
|
log_debug("%s: increasing delay for active DA query", c->name);
|
||||||
|
if (delay < 500)
|
||||||
|
delay = 500;
|
||||||
|
}
|
||||||
tv.tv_sec = delay / 1000;
|
tv.tv_sec = delay / 1000;
|
||||||
tv.tv_usec = (delay % 1000) * 1000L;
|
tv.tv_usec = (delay % 1000) * 1000L;
|
||||||
|
|
||||||
|
8
tty.c
8
tty.c
@ -356,6 +356,11 @@ tty_start_tty(struct tty *tty)
|
|||||||
if (tty_term_has(tty->term, TTYC_ENBP))
|
if (tty_term_has(tty->term, TTYC_ENBP))
|
||||||
tty_putcode(tty, TTYC_ENBP);
|
tty_putcode(tty, TTYC_ENBP);
|
||||||
|
|
||||||
|
if (tty->term->flags & TERM_VT100LIKE) {
|
||||||
|
/* Subscribe to theme changes and request theme now. */
|
||||||
|
tty_puts(tty, "\033[?2031h\033[?996n");
|
||||||
|
}
|
||||||
|
|
||||||
evtimer_set(&tty->start_timer, tty_start_timer_callback, tty);
|
evtimer_set(&tty->start_timer, tty_start_timer_callback, tty);
|
||||||
evtimer_add(&tty->start_timer, &tv);
|
evtimer_add(&tty->start_timer, &tv);
|
||||||
|
|
||||||
@ -468,6 +473,9 @@ tty_stop_tty(struct tty *tty)
|
|||||||
tty_raw(tty, tty_term_string(tty->term, TTYC_DSMG));
|
tty_raw(tty, tty_term_string(tty->term, TTYC_DSMG));
|
||||||
tty_raw(tty, tty_term_string(tty->term, TTYC_RMCUP));
|
tty_raw(tty, tty_term_string(tty->term, TTYC_RMCUP));
|
||||||
|
|
||||||
|
if (tty->term->flags & TERM_VT100LIKE)
|
||||||
|
tty_raw(tty, "\033[?2031l");
|
||||||
|
|
||||||
setblocking(c->fd, 1);
|
setblocking(c->fd, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -40,6 +40,7 @@ static void window_copy_free(struct window_mode_entry *);
|
|||||||
static void window_copy_resize(struct window_mode_entry *, u_int, u_int);
|
static void window_copy_resize(struct window_mode_entry *, u_int, u_int);
|
||||||
static void window_copy_formats(struct window_mode_entry *,
|
static void window_copy_formats(struct window_mode_entry *,
|
||||||
struct format_tree *);
|
struct format_tree *);
|
||||||
|
static struct screen *window_copy_get_screen(struct window_mode_entry *);
|
||||||
static void window_copy_scroll1(struct window_mode_entry *,
|
static void window_copy_scroll1(struct window_mode_entry *,
|
||||||
struct window_pane *wp, int, u_int, int);
|
struct window_pane *wp, int, u_int, int);
|
||||||
static void window_copy_pageup1(struct window_mode_entry *, int);
|
static void window_copy_pageup1(struct window_mode_entry *, int);
|
||||||
@ -160,6 +161,7 @@ const struct window_mode window_copy_mode = {
|
|||||||
.key_table = window_copy_key_table,
|
.key_table = window_copy_key_table,
|
||||||
.command = window_copy_command,
|
.command = window_copy_command,
|
||||||
.formats = window_copy_formats,
|
.formats = window_copy_formats,
|
||||||
|
.get_screen = window_copy_get_screen
|
||||||
};
|
};
|
||||||
|
|
||||||
const struct window_mode window_view_mode = {
|
const struct window_mode window_view_mode = {
|
||||||
@ -171,6 +173,7 @@ const struct window_mode window_view_mode = {
|
|||||||
.key_table = window_copy_key_table,
|
.key_table = window_copy_key_table,
|
||||||
.command = window_copy_command,
|
.command = window_copy_command,
|
||||||
.formats = window_copy_formats,
|
.formats = window_copy_formats,
|
||||||
|
.get_screen = window_copy_get_screen
|
||||||
};
|
};
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
@ -972,6 +975,14 @@ window_copy_formats(struct window_mode_entry *wme, struct format_tree *ft)
|
|||||||
window_copy_cursor_hyperlink_cb);
|
window_copy_cursor_hyperlink_cb);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static struct screen *
|
||||||
|
window_copy_get_screen(struct window_mode_entry *wme)
|
||||||
|
{
|
||||||
|
struct window_copy_mode_data *data = wme->data;
|
||||||
|
|
||||||
|
return (data->backing);
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
window_copy_size_changed(struct window_mode_entry *wme)
|
window_copy_size_changed(struct window_mode_entry *wme)
|
||||||
{
|
{
|
||||||
@ -4252,6 +4263,8 @@ window_copy_match_at_cursor(struct window_copy_mode_data *data)
|
|||||||
buf = xrealloc(buf, len + 2);
|
buf = xrealloc(buf, len + 2);
|
||||||
buf[len] = '\t';
|
buf[len] = '\t';
|
||||||
len++;
|
len++;
|
||||||
|
} else if (gc.flags & GRID_FLAG_PADDING) {
|
||||||
|
/* nothing to do */
|
||||||
} else {
|
} else {
|
||||||
buf = xrealloc(buf, len + gc.data.size + 1);
|
buf = xrealloc(buf, len + gc.data.size + 1);
|
||||||
memcpy(buf + len, gc.data.data, gc.data.size);
|
memcpy(buf + len, gc.data.data, gc.data.size);
|
||||||
|
@ -1000,7 +1000,7 @@ window_customize_set_option_callback(struct client *c, void *itemdata,
|
|||||||
|
|
||||||
fail:
|
fail:
|
||||||
*cause = toupper((u_char)*cause);
|
*cause = toupper((u_char)*cause);
|
||||||
status_message_set(c, -1, 1, 0, "%s", cause);
|
status_message_set(c, -1, 1, 0, 0, "%s", cause);
|
||||||
free(cause);
|
free(cause);
|
||||||
return (0);
|
return (0);
|
||||||
}
|
}
|
||||||
@ -1203,7 +1203,7 @@ window_customize_set_command_callback(struct client *c, void *itemdata,
|
|||||||
|
|
||||||
fail:
|
fail:
|
||||||
*error = toupper((u_char)*error);
|
*error = toupper((u_char)*error);
|
||||||
status_message_set(c, -1, 1, 0, "%s", error);
|
status_message_set(c, -1, 1, 0, 0, "%s", error);
|
||||||
free(error);
|
free(error);
|
||||||
return (0);
|
return (0);
|
||||||
}
|
}
|
||||||
|
284
window.c
284
window.c
@ -70,6 +70,8 @@ struct window_pane_input_data {
|
|||||||
static struct window_pane *window_pane_create(struct window *, u_int, u_int,
|
static struct window_pane *window_pane_create(struct window *, u_int, u_int,
|
||||||
u_int);
|
u_int);
|
||||||
static void window_pane_destroy(struct window_pane *);
|
static void window_pane_destroy(struct window_pane *);
|
||||||
|
static void window_pane_full_size_offset(struct window_pane *wp,
|
||||||
|
u_int *xoff, u_int *yoff, u_int *sx, u_int *sy);
|
||||||
|
|
||||||
RB_GENERATE(windows, window, entry, window_cmp);
|
RB_GENERATE(windows, window, entry, window_cmp);
|
||||||
RB_GENERATE(winlinks, winlink, entry, winlink_cmp);
|
RB_GENERATE(winlinks, winlink, entry, winlink_cmp);
|
||||||
@ -591,34 +593,15 @@ struct window_pane *
|
|||||||
window_get_active_at(struct window *w, u_int x, u_int y)
|
window_get_active_at(struct window *w, u_int x, u_int y)
|
||||||
{
|
{
|
||||||
struct window_pane *wp;
|
struct window_pane *wp;
|
||||||
int pane_scrollbars;
|
u_int xoff, yoff, sx, sy;
|
||||||
u_int sb_pos, sb_w, xoff, sx;
|
|
||||||
|
|
||||||
pane_scrollbars = options_get_number(w->options, "pane-scrollbars");
|
|
||||||
sb_pos = options_get_number(w->options, "pane-scrollbars-position");
|
|
||||||
|
|
||||||
TAILQ_FOREACH(wp, &w->panes, entry) {
|
TAILQ_FOREACH(wp, &w->panes, entry) {
|
||||||
if (!window_pane_visible(wp))
|
if (!window_pane_visible(wp))
|
||||||
continue;
|
continue;
|
||||||
|
window_pane_full_size_offset(wp, &xoff, &yoff, &sx, &sy);
|
||||||
if (pane_scrollbars == PANE_SCROLLBARS_ALWAYS ||
|
|
||||||
(pane_scrollbars == PANE_SCROLLBARS_MODAL &&
|
|
||||||
window_pane_mode(wp) != WINDOW_PANE_NO_MODE)) {
|
|
||||||
sb_w = wp->scrollbar_style.width +
|
|
||||||
wp->scrollbar_style.pad;
|
|
||||||
} else
|
|
||||||
sb_w = 0;
|
|
||||||
|
|
||||||
if (sb_pos == PANE_SCROLLBARS_LEFT) {
|
|
||||||
xoff = wp->xoff - sb_w;
|
|
||||||
sx = wp->sx + sb_w;
|
|
||||||
} else { /* sb_pos == PANE_SCROLLBARS_RIGHT */
|
|
||||||
xoff = wp->xoff;
|
|
||||||
sx = wp->sx + sb_w;
|
|
||||||
}
|
|
||||||
if (x < xoff || x > xoff + sx)
|
if (x < xoff || x > xoff + sx)
|
||||||
continue;
|
continue;
|
||||||
if (y < wp->yoff || y > wp->yoff + wp->sy)
|
if (y < yoff || y > yoff + sy)
|
||||||
continue;
|
continue;
|
||||||
return (wp);
|
return (wp);
|
||||||
}
|
}
|
||||||
@ -950,7 +933,7 @@ window_pane_create(struct window *w, u_int sx, u_int sy, u_int hlimit)
|
|||||||
wp = xcalloc(1, sizeof *wp);
|
wp = xcalloc(1, sizeof *wp);
|
||||||
wp->window = w;
|
wp->window = w;
|
||||||
wp->options = options_create(w->options);
|
wp->options = options_create(w->options);
|
||||||
wp->flags = PANE_STYLECHANGED;
|
wp->flags = (PANE_STYLECHANGED|PANE_THEMECHANGED);
|
||||||
|
|
||||||
wp->id = next_window_pane_id++;
|
wp->id = next_window_pane_id++;
|
||||||
RB_INSERT(window_pane_tree, &all_window_panes, wp);
|
RB_INSERT(window_pane_tree, &all_window_panes, wp);
|
||||||
@ -1359,6 +1342,36 @@ window_pane_choose_best(struct window_pane **list, u_int size)
|
|||||||
return (best);
|
return (best);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Get full size and offset of a window pane including the area of the
|
||||||
|
* scrollbars if they were visible but not including the border(s).
|
||||||
|
*/
|
||||||
|
static void
|
||||||
|
window_pane_full_size_offset(struct window_pane *wp, u_int *xoff, u_int *yoff,
|
||||||
|
u_int *sx, u_int *sy)
|
||||||
|
{
|
||||||
|
struct window *w = wp->window;
|
||||||
|
int pane_scrollbars;
|
||||||
|
u_int sb_w, sb_pos;
|
||||||
|
|
||||||
|
pane_scrollbars = options_get_number(w->options, "pane-scrollbars");
|
||||||
|
sb_pos = options_get_number(w->options, "pane-scrollbars-position");
|
||||||
|
|
||||||
|
if (window_pane_show_scrollbar(wp, pane_scrollbars))
|
||||||
|
sb_w = wp->scrollbar_style.width + wp->scrollbar_style.pad;
|
||||||
|
else
|
||||||
|
sb_w = 0;
|
||||||
|
if (sb_pos == PANE_SCROLLBARS_LEFT) {
|
||||||
|
*xoff = wp->xoff - sb_w;
|
||||||
|
*sx = wp->sx + sb_w;
|
||||||
|
} else { /* sb_pos == PANE_SCROLLBARS_RIGHT */
|
||||||
|
*xoff = wp->xoff;
|
||||||
|
*sx = wp->sx + sb_w;
|
||||||
|
}
|
||||||
|
*yoff = wp->yoff;
|
||||||
|
*sy = wp->sy;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Find the pane directly above another. We build a list of those adjacent to
|
* Find the pane directly above another. We build a list of those adjacent to
|
||||||
* top edge and then choose the best.
|
* top edge and then choose the best.
|
||||||
@ -1370,6 +1383,7 @@ window_pane_find_up(struct window_pane *wp)
|
|||||||
struct window_pane *next, *best, **list;
|
struct window_pane *next, *best, **list;
|
||||||
u_int edge, left, right, end, size;
|
u_int edge, left, right, end, size;
|
||||||
int status, found;
|
int status, found;
|
||||||
|
u_int xoff, yoff, sx, sy;
|
||||||
|
|
||||||
if (wp == NULL)
|
if (wp == NULL)
|
||||||
return (NULL);
|
return (NULL);
|
||||||
@ -1379,7 +1393,9 @@ window_pane_find_up(struct window_pane *wp)
|
|||||||
list = NULL;
|
list = NULL;
|
||||||
size = 0;
|
size = 0;
|
||||||
|
|
||||||
edge = wp->yoff;
|
window_pane_full_size_offset(wp, &xoff, &yoff, &sx, &sy);
|
||||||
|
|
||||||
|
edge = yoff;
|
||||||
if (status == PANE_STATUS_TOP) {
|
if (status == PANE_STATUS_TOP) {
|
||||||
if (edge == 1)
|
if (edge == 1)
|
||||||
edge = w->sy + 1;
|
edge = w->sy + 1;
|
||||||
@ -1391,20 +1407,21 @@ window_pane_find_up(struct window_pane *wp)
|
|||||||
edge = w->sy + 1;
|
edge = w->sy + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
left = wp->xoff;
|
left = xoff;
|
||||||
right = wp->xoff + wp->sx;
|
right = xoff + sx;
|
||||||
|
|
||||||
TAILQ_FOREACH(next, &w->panes, entry) {
|
TAILQ_FOREACH(next, &w->panes, entry) {
|
||||||
|
window_pane_full_size_offset(next, &xoff, &yoff, &sx, &sy);
|
||||||
if (next == wp)
|
if (next == wp)
|
||||||
continue;
|
continue;
|
||||||
if (next->yoff + next->sy + 1 != edge)
|
if (yoff + sy + 1 != edge)
|
||||||
continue;
|
continue;
|
||||||
end = next->xoff + next->sx - 1;
|
end = xoff + sx - 1;
|
||||||
|
|
||||||
found = 0;
|
found = 0;
|
||||||
if (next->xoff < left && end > right)
|
if (xoff < left && end > right)
|
||||||
found = 1;
|
found = 1;
|
||||||
else if (next->xoff >= left && next->xoff <= right)
|
else if (xoff >= left && xoff <= right)
|
||||||
found = 1;
|
found = 1;
|
||||||
else if (end >= left && end <= right)
|
else if (end >= left && end <= right)
|
||||||
found = 1;
|
found = 1;
|
||||||
@ -1427,6 +1444,7 @@ window_pane_find_down(struct window_pane *wp)
|
|||||||
struct window_pane *next, *best, **list;
|
struct window_pane *next, *best, **list;
|
||||||
u_int edge, left, right, end, size;
|
u_int edge, left, right, end, size;
|
||||||
int status, found;
|
int status, found;
|
||||||
|
u_int xoff, yoff, sx, sy;
|
||||||
|
|
||||||
if (wp == NULL)
|
if (wp == NULL)
|
||||||
return (NULL);
|
return (NULL);
|
||||||
@ -1436,7 +1454,9 @@ window_pane_find_down(struct window_pane *wp)
|
|||||||
list = NULL;
|
list = NULL;
|
||||||
size = 0;
|
size = 0;
|
||||||
|
|
||||||
edge = wp->yoff + wp->sy + 1;
|
window_pane_full_size_offset(wp, &xoff, &yoff, &sx, &sy);
|
||||||
|
|
||||||
|
edge = yoff + sy + 1;
|
||||||
if (status == PANE_STATUS_TOP) {
|
if (status == PANE_STATUS_TOP) {
|
||||||
if (edge >= w->sy)
|
if (edge >= w->sy)
|
||||||
edge = 1;
|
edge = 1;
|
||||||
@ -1452,16 +1472,17 @@ window_pane_find_down(struct window_pane *wp)
|
|||||||
right = wp->xoff + wp->sx;
|
right = wp->xoff + wp->sx;
|
||||||
|
|
||||||
TAILQ_FOREACH(next, &w->panes, entry) {
|
TAILQ_FOREACH(next, &w->panes, entry) {
|
||||||
|
window_pane_full_size_offset(next, &xoff, &yoff, &sx, &sy);
|
||||||
if (next == wp)
|
if (next == wp)
|
||||||
continue;
|
continue;
|
||||||
if (next->yoff != edge)
|
if (yoff != edge)
|
||||||
continue;
|
continue;
|
||||||
end = next->xoff + next->sx - 1;
|
end = xoff + sx - 1;
|
||||||
|
|
||||||
found = 0;
|
found = 0;
|
||||||
if (next->xoff < left && end > right)
|
if (xoff < left && end > right)
|
||||||
found = 1;
|
found = 1;
|
||||||
else if (next->xoff >= left && next->xoff <= right)
|
else if (xoff >= left && xoff <= right)
|
||||||
found = 1;
|
found = 1;
|
||||||
else if (end >= left && end <= right)
|
else if (end >= left && end <= right)
|
||||||
found = 1;
|
found = 1;
|
||||||
@ -1484,6 +1505,7 @@ window_pane_find_left(struct window_pane *wp)
|
|||||||
struct window_pane *next, *best, **list;
|
struct window_pane *next, *best, **list;
|
||||||
u_int edge, top, bottom, end, size;
|
u_int edge, top, bottom, end, size;
|
||||||
int found;
|
int found;
|
||||||
|
u_int xoff, yoff, sx, sy;
|
||||||
|
|
||||||
if (wp == NULL)
|
if (wp == NULL)
|
||||||
return (NULL);
|
return (NULL);
|
||||||
@ -1492,24 +1514,27 @@ window_pane_find_left(struct window_pane *wp)
|
|||||||
list = NULL;
|
list = NULL;
|
||||||
size = 0;
|
size = 0;
|
||||||
|
|
||||||
edge = wp->xoff;
|
window_pane_full_size_offset(wp, &xoff, &yoff, &sx, &sy);
|
||||||
|
|
||||||
|
edge = xoff;
|
||||||
if (edge == 0)
|
if (edge == 0)
|
||||||
edge = w->sx + 1;
|
edge = w->sx + 1;
|
||||||
|
|
||||||
top = wp->yoff;
|
top = yoff;
|
||||||
bottom = wp->yoff + wp->sy;
|
bottom = yoff + sy;
|
||||||
|
|
||||||
TAILQ_FOREACH(next, &w->panes, entry) {
|
TAILQ_FOREACH(next, &w->panes, entry) {
|
||||||
|
window_pane_full_size_offset(next, &xoff, &yoff, &sx, &sy);
|
||||||
if (next == wp)
|
if (next == wp)
|
||||||
continue;
|
continue;
|
||||||
if (next->xoff + next->sx + 1 != edge)
|
if (xoff + sx + 1 != edge)
|
||||||
continue;
|
continue;
|
||||||
end = next->yoff + next->sy - 1;
|
end = yoff + sy - 1;
|
||||||
|
|
||||||
found = 0;
|
found = 0;
|
||||||
if (next->yoff < top && end > bottom)
|
if (yoff < top && end > bottom)
|
||||||
found = 1;
|
found = 1;
|
||||||
else if (next->yoff >= top && next->yoff <= bottom)
|
else if (yoff >= top && yoff <= bottom)
|
||||||
found = 1;
|
found = 1;
|
||||||
else if (end >= top && end <= bottom)
|
else if (end >= top && end <= bottom)
|
||||||
found = 1;
|
found = 1;
|
||||||
@ -1532,6 +1557,7 @@ window_pane_find_right(struct window_pane *wp)
|
|||||||
struct window_pane *next, *best, **list;
|
struct window_pane *next, *best, **list;
|
||||||
u_int edge, top, bottom, end, size;
|
u_int edge, top, bottom, end, size;
|
||||||
int found;
|
int found;
|
||||||
|
u_int xoff, yoff, sx, sy;
|
||||||
|
|
||||||
if (wp == NULL)
|
if (wp == NULL)
|
||||||
return (NULL);
|
return (NULL);
|
||||||
@ -1540,7 +1566,9 @@ window_pane_find_right(struct window_pane *wp)
|
|||||||
list = NULL;
|
list = NULL;
|
||||||
size = 0;
|
size = 0;
|
||||||
|
|
||||||
edge = wp->xoff + wp->sx + 1;
|
window_pane_full_size_offset(wp, &xoff, &yoff, &sx, &sy);
|
||||||
|
|
||||||
|
edge = xoff + sx + 1;
|
||||||
if (edge >= w->sx)
|
if (edge >= w->sx)
|
||||||
edge = 0;
|
edge = 0;
|
||||||
|
|
||||||
@ -1548,16 +1576,17 @@ window_pane_find_right(struct window_pane *wp)
|
|||||||
bottom = wp->yoff + wp->sy;
|
bottom = wp->yoff + wp->sy;
|
||||||
|
|
||||||
TAILQ_FOREACH(next, &w->panes, entry) {
|
TAILQ_FOREACH(next, &w->panes, entry) {
|
||||||
|
window_pane_full_size_offset(next, &xoff, &yoff, &sx, &sy);
|
||||||
if (next == wp)
|
if (next == wp)
|
||||||
continue;
|
continue;
|
||||||
if (next->xoff != edge)
|
if (xoff != edge)
|
||||||
continue;
|
continue;
|
||||||
end = next->yoff + next->sy - 1;
|
end = yoff + sy - 1;
|
||||||
|
|
||||||
found = 0;
|
found = 0;
|
||||||
if (next->yoff < top && end > bottom)
|
if (yoff < top && end > bottom)
|
||||||
found = 1;
|
found = 1;
|
||||||
else if (next->yoff >= top && next->yoff <= bottom)
|
else if (yoff >= top && yoff <= bottom)
|
||||||
found = 1;
|
found = 1;
|
||||||
else if (end >= top && end <= bottom)
|
else if (end >= top && end <= bottom)
|
||||||
found = 1;
|
found = 1;
|
||||||
@ -1723,6 +1752,8 @@ window_set_fill_character(struct window *w)
|
|||||||
ud = utf8_fromcstr(value);
|
ud = utf8_fromcstr(value);
|
||||||
if (ud != NULL && ud[0].width == 1)
|
if (ud != NULL && ud[0].width == 1)
|
||||||
w->fill_character = ud;
|
w->fill_character = ud;
|
||||||
|
else
|
||||||
|
free(ud);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1756,3 +1787,162 @@ window_pane_show_scrollbar(struct window_pane *wp, int sb_option)
|
|||||||
return (1);
|
return (1);
|
||||||
return (0);
|
return (0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
window_pane_get_bg(struct window_pane *wp)
|
||||||
|
{
|
||||||
|
int c;
|
||||||
|
struct grid_cell defaults;
|
||||||
|
|
||||||
|
c = window_pane_get_bg_control_client(wp);
|
||||||
|
if (c == -1) {
|
||||||
|
tty_default_colours(&defaults, wp);
|
||||||
|
if (COLOUR_DEFAULT(defaults.bg))
|
||||||
|
c = window_get_bg_client(wp);
|
||||||
|
else
|
||||||
|
c = defaults.bg;
|
||||||
|
}
|
||||||
|
return (c);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Get a client with a background for the pane. */
|
||||||
|
int
|
||||||
|
window_get_bg_client(struct window_pane *wp)
|
||||||
|
{
|
||||||
|
struct window *w = wp->window;
|
||||||
|
struct client *loop;
|
||||||
|
|
||||||
|
TAILQ_FOREACH(loop, &clients, entry) {
|
||||||
|
if (loop->flags & CLIENT_UNATTACHEDFLAGS)
|
||||||
|
continue;
|
||||||
|
if (loop->session == NULL || !session_has(loop->session, w))
|
||||||
|
continue;
|
||||||
|
if (loop->tty.bg == -1)
|
||||||
|
continue;
|
||||||
|
return (loop->tty.bg);
|
||||||
|
}
|
||||||
|
return (-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* If any control mode client exists that has provided a bg color, return it.
|
||||||
|
* Otherwise, return -1.
|
||||||
|
*/
|
||||||
|
int
|
||||||
|
window_pane_get_bg_control_client(struct window_pane *wp)
|
||||||
|
{
|
||||||
|
struct client *c;
|
||||||
|
|
||||||
|
if (wp->control_bg == -1)
|
||||||
|
return (-1);
|
||||||
|
|
||||||
|
TAILQ_FOREACH(c, &clients, entry) {
|
||||||
|
if (c->flags & CLIENT_CONTROL)
|
||||||
|
return (wp->control_bg);
|
||||||
|
}
|
||||||
|
return (-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Get a client with a foreground for the pane. There isn't much to choose
|
||||||
|
* between them so just use the first.
|
||||||
|
*/
|
||||||
|
int
|
||||||
|
window_pane_get_fg(struct window_pane *wp)
|
||||||
|
{
|
||||||
|
struct window *w = wp->window;
|
||||||
|
struct client *loop;
|
||||||
|
|
||||||
|
TAILQ_FOREACH(loop, &clients, entry) {
|
||||||
|
if (loop->flags & CLIENT_UNATTACHEDFLAGS)
|
||||||
|
continue;
|
||||||
|
if (loop->session == NULL || !session_has(loop->session, w))
|
||||||
|
continue;
|
||||||
|
if (loop->tty.fg == -1)
|
||||||
|
continue;
|
||||||
|
return (loop->tty.fg);
|
||||||
|
}
|
||||||
|
return (-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* If any control mode client exists that has provided a fg color, return it.
|
||||||
|
* Otherwise, return -1.
|
||||||
|
*/
|
||||||
|
int
|
||||||
|
window_pane_get_fg_control_client(struct window_pane *wp)
|
||||||
|
{
|
||||||
|
struct client *c;
|
||||||
|
|
||||||
|
if (wp->control_fg == -1)
|
||||||
|
return (-1);
|
||||||
|
|
||||||
|
TAILQ_FOREACH(c, &clients, entry) {
|
||||||
|
if (c->flags & CLIENT_CONTROL)
|
||||||
|
return (wp->control_fg);
|
||||||
|
}
|
||||||
|
return (-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
enum client_theme
|
||||||
|
window_pane_get_theme(struct window_pane *wp)
|
||||||
|
{
|
||||||
|
struct window *w = wp->window;
|
||||||
|
struct client *loop;
|
||||||
|
enum client_theme theme;
|
||||||
|
int found_light = 0, found_dark = 0;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Derive theme from pane background color, if it's not the default
|
||||||
|
* colour.
|
||||||
|
*/
|
||||||
|
theme = colour_totheme(window_pane_get_bg(wp));
|
||||||
|
if (theme != THEME_UNKNOWN)
|
||||||
|
return (theme);
|
||||||
|
|
||||||
|
/* Try to find a client that has a theme. */
|
||||||
|
TAILQ_FOREACH(loop, &clients, entry) {
|
||||||
|
if (loop->flags & CLIENT_UNATTACHEDFLAGS)
|
||||||
|
continue;
|
||||||
|
if (loop->session == NULL || !session_has(loop->session, w))
|
||||||
|
continue;
|
||||||
|
switch (loop->theme) {
|
||||||
|
case THEME_LIGHT:
|
||||||
|
found_light = 1;
|
||||||
|
break;
|
||||||
|
case THEME_DARK:
|
||||||
|
found_dark = 1;
|
||||||
|
break;
|
||||||
|
case THEME_UNKNOWN:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (found_dark && !found_light)
|
||||||
|
return (THEME_DARK);
|
||||||
|
if (found_light && !found_dark)
|
||||||
|
return (THEME_LIGHT);
|
||||||
|
return (THEME_UNKNOWN);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
window_pane_send_theme_update(struct window_pane *wp)
|
||||||
|
{
|
||||||
|
if (~wp->flags & PANE_THEMECHANGED)
|
||||||
|
return;
|
||||||
|
if (~wp->screen->mode & MODE_THEME_UPDATES)
|
||||||
|
return;
|
||||||
|
|
||||||
|
switch (window_pane_get_theme(wp)) {
|
||||||
|
case THEME_LIGHT:
|
||||||
|
input_key_pane(wp, KEYC_REPORT_LIGHT_THEME, NULL);
|
||||||
|
break;
|
||||||
|
case THEME_DARK:
|
||||||
|
input_key_pane(wp, KEYC_REPORT_DARK_THEME, NULL);
|
||||||
|
break;
|
||||||
|
case THEME_UNKNOWN:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
wp->flags &= ~PANE_THEMECHANGED;
|
||||||
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user