mirror of
https://github.com/tmux/tmux.git
synced 2024-11-17 09:58:52 +00:00
Add a way (refresh-client -r) for control mode clients to provide OSC 10
and 11 responses to tmux so they can set the default foreground and background colours, from George Nachman in GitHub issue 4014.
This commit is contained in:
parent
db1665868f
commit
093b5a5518
@ -34,9 +34,10 @@ const struct cmd_entry cmd_refresh_client_entry = {
|
||||
.name = "refresh-client",
|
||||
.alias = "refresh",
|
||||
|
||||
.args = { "A:B:cC:Df:F:l::LRSt:U", 0, 1, NULL },
|
||||
.args = { "A:B:cC:Df:r:F:l::LRSt:U", 0, 1, NULL },
|
||||
.usage = "[-cDlLRSU] [-A pane:state] [-B name:what:format] "
|
||||
"[-C XxY] [-f flags] " CMD_TARGET_CLIENT_USAGE " [adjustment]",
|
||||
"[-C XxY] [-f flags] [-r pane:report]" CMD_TARGET_CLIENT_USAGE
|
||||
" [adjustment]",
|
||||
|
||||
.flags = CMD_AFTERHOOK|CMD_CLIENT_TFLAG,
|
||||
.exec = cmd_refresh_client_exec
|
||||
@ -193,6 +194,34 @@ cmd_refresh_client_clipboard(struct cmd *self, struct cmdq_item *item)
|
||||
return (CMD_RETURN_NORMAL);
|
||||
}
|
||||
|
||||
static void
|
||||
cmd_refresh_report(struct tty *tty, const char *value)
|
||||
{
|
||||
struct window_pane *wp;
|
||||
u_int pane;
|
||||
size_t size = 0;
|
||||
char *copy, *split;
|
||||
|
||||
if (*value != '%')
|
||||
return;
|
||||
copy = xstrdup(value);
|
||||
if ((split = strchr(copy, ':')) == NULL)
|
||||
goto out;
|
||||
*split++ = '\0';
|
||||
|
||||
if (sscanf(copy, "%%%u", &pane) != 1)
|
||||
goto out;
|
||||
wp = window_pane_find_by_id(pane);
|
||||
if (wp == NULL)
|
||||
goto out;
|
||||
|
||||
tty_keys_colours(tty, split, strlen(split), &size, &wp->control_fg,
|
||||
&wp->control_bg);
|
||||
|
||||
out:
|
||||
free(copy);
|
||||
}
|
||||
|
||||
static enum cmd_retval
|
||||
cmd_refresh_client_exec(struct cmd *self, struct cmdq_item *item)
|
||||
{
|
||||
@ -262,6 +291,8 @@ cmd_refresh_client_exec(struct cmd *self, struct cmdq_item *item)
|
||||
server_client_set_flags(tc, args_get(args, 'F'));
|
||||
if (args_has(args, 'f'))
|
||||
server_client_set_flags(tc, args_get(args, 'f'));
|
||||
if (args_has(args, 'r'))
|
||||
cmd_refresh_report(tty, args_get(args, 'r'));
|
||||
|
||||
if (args_has(args, 'A')) {
|
||||
if (~tc->flags & CLIENT_CONTROL)
|
||||
|
64
input.c
64
input.c
@ -2652,6 +2652,44 @@ input_get_bg_client(struct window_pane *wp)
|
||||
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. */
|
||||
static void
|
||||
input_osc_10(struct input_ctx *ictx, const char *p)
|
||||
@ -2663,11 +2701,14 @@ input_osc_10(struct input_ctx *ictx, const char *p)
|
||||
if (strcmp(p, "?") == 0) {
|
||||
if (wp == NULL)
|
||||
return;
|
||||
tty_default_colours(&defaults, wp);
|
||||
if (COLOUR_DEFAULT(defaults.fg))
|
||||
c = input_get_fg_client(wp);
|
||||
else
|
||||
c = defaults.fg;
|
||||
c = input_get_fg_control_client(wp);
|
||||
if (c == -1) {
|
||||
tty_default_colours(&defaults, wp);
|
||||
if (COLOUR_DEFAULT(defaults.fg))
|
||||
c = input_get_fg_client(wp);
|
||||
else
|
||||
c = defaults.fg;
|
||||
}
|
||||
input_osc_colour_reply(ictx, 10, c);
|
||||
return;
|
||||
}
|
||||
@ -2711,11 +2752,14 @@ input_osc_11(struct input_ctx *ictx, const char *p)
|
||||
if (strcmp(p, "?") == 0) {
|
||||
if (wp == NULL)
|
||||
return;
|
||||
tty_default_colours(&defaults, wp);
|
||||
if (COLOUR_DEFAULT(defaults.bg))
|
||||
c = input_get_bg_client(wp);
|
||||
else
|
||||
c = defaults.bg;
|
||||
c = input_get_bg_control_client(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);
|
||||
return;
|
||||
}
|
||||
|
7
tmux.1
7
tmux.1
@ -1357,6 +1357,7 @@ specified multiple times.
|
||||
.Op Fl B Ar name:what:format
|
||||
.Op Fl C Ar size
|
||||
.Op Fl f Ar flags
|
||||
.Op Fl r Ar pane:report
|
||||
.Op Fl l Op Ar target-pane
|
||||
.Op Fl t Ar target-client
|
||||
.Op Ar adjustment
|
||||
@ -1467,6 +1468,12 @@ for all windows in the attached session.
|
||||
.Fl f
|
||||
sets a comma-separated list of client flags, see
|
||||
.Ic attach-session .
|
||||
.Fl r
|
||||
allows a control mode client to provide information about a pane via a report
|
||||
(such as the response to OSC 10).
|
||||
The argument is a pane ID (with a leading
|
||||
.Ql % ) ,
|
||||
a colon, then a report escape sequence.
|
||||
.Pp
|
||||
.Fl l
|
||||
requests the clipboard from the client using the
|
||||
|
5
tmux.h
5
tmux.h
@ -1100,6 +1100,9 @@ struct window_pane {
|
||||
int border_gc_set;
|
||||
struct grid_cell border_gc;
|
||||
|
||||
int control_bg;
|
||||
int control_fg;
|
||||
|
||||
TAILQ_ENTRY(window_pane) entry; /* link in list of all panes */
|
||||
TAILQ_ENTRY(window_pane) sentry; /* link in list of last visited */
|
||||
RB_ENTRY(window_pane) tree_entry;
|
||||
@ -2407,6 +2410,8 @@ const struct utf8_data *tty_acs_rounded_borders(int);
|
||||
void tty_keys_build(struct tty *);
|
||||
void tty_keys_free(struct tty *);
|
||||
int tty_keys_next(struct tty *);
|
||||
int tty_keys_colours(struct tty *, const char *, size_t, size_t *,
|
||||
int *, int *);
|
||||
|
||||
/* arguments.c */
|
||||
void args_set(struct args *, u_char, struct args_value *, int);
|
||||
|
22
tty-keys.c
22
tty-keys.c
@ -59,7 +59,6 @@ static int tty_keys_device_attributes2(struct tty *, const char *, size_t,
|
||||
size_t *);
|
||||
static int tty_keys_extended_device_attributes(struct tty *, const char *,
|
||||
size_t, size_t *);
|
||||
static int tty_keys_colours(struct tty *, const char *, size_t, size_t *);
|
||||
|
||||
/* A key tree entry. */
|
||||
struct tty_key {
|
||||
@ -721,7 +720,7 @@ tty_keys_next(struct tty *tty)
|
||||
}
|
||||
|
||||
/* Is this a colours response? */
|
||||
switch (tty_keys_colours(tty, buf, len, &size)) {
|
||||
switch (tty_keys_colours(tty, buf, len, &size, &tty->fg, &tty->bg)) {
|
||||
case 0: /* yes */
|
||||
key = KEYC_UNKNOWN;
|
||||
goto complete_key;
|
||||
@ -1490,8 +1489,9 @@ tty_keys_extended_device_attributes(struct tty *tty, const char *buf,
|
||||
* Handle foreground or background input. Returns 0 for success, -1 for
|
||||
* failure, 1 for partial.
|
||||
*/
|
||||
static int
|
||||
tty_keys_colours(struct tty *tty, const char *buf, size_t len, size_t *size)
|
||||
int
|
||||
tty_keys_colours(struct tty *tty, const char *buf, size_t len, size_t *size,
|
||||
int *fg, int *bg)
|
||||
{
|
||||
struct client *c = tty->client;
|
||||
u_int i;
|
||||
@ -1542,11 +1542,17 @@ tty_keys_colours(struct tty *tty, const char *buf, size_t len, size_t *size)
|
||||
|
||||
n = colour_parseX11(tmp);
|
||||
if (n != -1 && buf[3] == '0') {
|
||||
log_debug("%s: foreground is %s", c->name, colour_tostring(n));
|
||||
tty->fg = n;
|
||||
if (c != NULL)
|
||||
log_debug("%s fg is %s", c->name, colour_tostring(n));
|
||||
else
|
||||
log_debug("fg is %s", colour_tostring(n));
|
||||
*fg = n;
|
||||
} else if (n != -1) {
|
||||
log_debug("%s: background is %s", c->name, colour_tostring(n));
|
||||
tty->bg = n;
|
||||
if (c != NULL)
|
||||
log_debug("%s bg is %s", c->name, colour_tostring(n));
|
||||
else
|
||||
log_debug("bg is %s", colour_tostring(n));
|
||||
*bg = n;
|
||||
}
|
||||
|
||||
return (0);
|
||||
|
Loading…
Reference in New Issue
Block a user