Add a cursor-colour option, from Alexis Hildebrandt in GitHub issue

2959.
pull/2967/head
nicm 2021-11-01 09:34:49 +00:00
parent 4fe5aa99fb
commit 8d2286b769
7 changed files with 96 additions and 30 deletions

47
input.c
View File

@ -137,10 +137,12 @@ static void input_reset_cell(struct input_ctx *);
static void input_osc_4(struct input_ctx *, const char *);
static void input_osc_10(struct input_ctx *, const char *);
static void input_osc_11(struct input_ctx *, const char *);
static void input_osc_12(struct input_ctx *, const char *);
static void input_osc_52(struct input_ctx *, const char *);
static void input_osc_104(struct input_ctx *, const char *);
static void input_osc_110(struct input_ctx *, const char *);
static void input_osc_111(struct input_ctx *, const char *);
static void input_osc_112(struct input_ctx *, const char *);
/* Transition entry/exit handlers. */
static void input_clear(struct input_ctx *);
@ -2310,8 +2312,7 @@ input_exit_osc(struct input_ctx *ictx)
input_osc_11(ictx, p);
break;
case 12:
if (utf8_isvalid(p) && *p != '?') /* ? is colour request */
screen_set_cursor_colour(sctx->s, p);
input_osc_12(ictx, p);
break;
case 52:
input_osc_52(ictx, p);
@ -2326,8 +2327,7 @@ input_exit_osc(struct input_ctx *ictx)
input_osc_111(ictx, p);
break;
case 112:
if (*p == '\0') /* no arguments allowed */
screen_set_cursor_colour(sctx->s, "");
input_osc_112(ictx, p);
break;
default:
log_debug("%s: unknown '%u'", __func__, option);
@ -2489,7 +2489,9 @@ input_osc_colour_reply(struct input_ctx *ictx, u_int n, int c)
u_char r, g, b;
const char *end;
if (c == 8 || (~c & COLOUR_FLAG_RGB))
if (c != -1)
c = colour_force_rgb(c);
if (c == -1)
return;
colour_split_rgb(c, &r, &g, &b);
@ -2564,7 +2566,7 @@ input_osc_10(struct input_ctx *ictx, const char *p)
}
}
/* Handle the OSC 110 sequence for resetting background colour. */
/* Handle the OSC 110 sequence for resetting foreground colour. */
static void
input_osc_110(struct input_ctx *ictx, const char *p)
{
@ -2624,6 +2626,39 @@ input_osc_111(struct input_ctx *ictx, const char *p)
}
}
/* Handle the OSC 12 sequence for setting and querying cursor colour. */
static void
input_osc_12(struct input_ctx *ictx, const char *p)
{
struct window_pane *wp = ictx->wp;
int c;
if (strcmp(p, "?") == 0) {
if (wp != NULL) {
c = ictx->ctx.s->ccolour;
if (c == -1)
c = ictx->ctx.s->default_ccolour;
input_osc_colour_reply(ictx, 12, c);
}
return;
}
if ((c = input_osc_parse_colour(p)) == -1) {
log_debug("bad OSC 12: %s", p);
return;
}
screen_set_cursor_colour(ictx->ctx.s, c);
}
/* Handle the OSC 112 sequence for resetting cursor colour. */
static void
input_osc_112(struct input_ctx *ictx, const char *p)
{
if (*p == '\0') /* no arguments allowed */
screen_set_cursor_colour(ictx->ctx.s, -1);
}
/* Handle the OSC 52 sequence for setting the clipboard. */
static void
input_osc_52(struct input_ctx *ictx, const char *p)

View File

@ -188,6 +188,7 @@ const struct options_name_map options_other_names[] = {
{ "display-panes-color", "display-panes-colour" },
{ "display-panes-active-color", "display-panes-active-colour" },
{ "clock-mode-color", "clock-mode-colour" },
{ "cursor-color", "cursor-colour" },
{ "pane-colors", "pane-colours" },
{ NULL, NULL }
};
@ -235,6 +236,13 @@ const struct options_table_entry options_table[] = {
"If empty, no command is run."
},
{ .name = "cursor-colour",
.type = OPTIONS_TABLE_COLOUR,
.scope = OPTIONS_TABLE_WINDOW|OPTIONS_TABLE_PANE,
.default_num = -1,
.text = "Colour of the cursor."
},
{ .name = "default-terminal",
.type = OPTIONS_TABLE_STRING,
.scope = OPTIONS_TABLE_SERVER,

View File

@ -1106,15 +1106,22 @@ options_push_changes(const char *name)
struct session *s;
struct window *w;
struct window_pane *wp;
int c;
if (strcmp(name, "automatic-rename") == 0) {
RB_FOREACH(w, windows, &windows) {
if (w->active == NULL)
continue;
if (options_get_number(w->options, "automatic-rename"))
if (options_get_number(w->options, name))
w->active->flags |= PANE_CHANGED;
}
}
if (strcmp(name, "cursor-colour") == 0) {
RB_FOREACH(wp, window_pane_tree, &all_window_panes) {
c = options_get_number(wp->options, name);
wp->screen->default_ccolour = c;
}
}
if (strcmp(name, "key-table") == 0) {
TAILQ_FOREACH(loop, &clients, entry)
server_client_set_key_table(loop, NULL);

View File

@ -82,7 +82,8 @@ screen_init(struct screen *s, u_int sx, u_int sy, u_int hlimit)
s->path = NULL;
s->cstyle = SCREEN_CURSOR_DEFAULT;
s->ccolour = xstrdup("");
s->ccolour = -1;
s->default_ccolour = -1;
s->tabs = NULL;
s->sel = NULL;
@ -126,7 +127,6 @@ screen_free(struct screen *s)
free(s->tabs);
free(s->path);
free(s->title);
free(s->ccolour);
if (s->write_list != NULL)
screen_write_free_list(s);
@ -190,10 +190,9 @@ screen_set_cursor_style(struct screen *s, u_int style)
/* Set screen cursor colour. */
void
screen_set_cursor_colour(struct screen *s, const char *colour)
screen_set_cursor_colour(struct screen *s, int colour)
{
free(s->ccolour);
s->ccolour = xstrdup(colour);
s->ccolour = colour;
}
/* Set screen title. */

3
tmux.1
View File

@ -4416,6 +4416,9 @@ The alternate screen feature preserves the contents of the window when an
interactive application starts and restores it on exit, so that any output
visible before the application starts reappears unchanged after it exits.
.Pp
.It Ic cursor-colour Ar colour
Set the colour of the cursor.
.Pp
.It Ic pane-colours[] Ar colour
The default colour palette.
Each entry in the array defines the colour

7
tmux.h
View File

@ -779,7 +779,8 @@ struct screen {
u_int cy; /* cursor y */
enum screen_cursor_style cstyle; /* cursor style */
char *ccolour; /* cursor colour */
int ccolour; /* cursor colour */
int default_ccolour;
u_int rupper; /* scroll region top */
u_int rlower; /* scroll region bottom */
@ -1276,7 +1277,7 @@ struct tty {
u_int cx;
u_int cy;
enum screen_cursor_style cstyle;
char *ccolour;
int ccolour;
int oflag;
u_int oox;
@ -2793,7 +2794,7 @@ void screen_reinit(struct screen *);
void screen_free(struct screen *);
void screen_reset_tabs(struct screen *);
void screen_set_cursor_style(struct screen *, u_int);
void screen_set_cursor_colour(struct screen *, const char *);
void screen_set_cursor_colour(struct screen *, int);
int screen_set_title(struct screen *, const char *);
void screen_set_path(struct screen *, const char *);
void screen_push_title(struct screen *);

43
tty.c
View File

@ -38,7 +38,7 @@ static int tty_client_ready(struct client *);
static void tty_set_italics(struct tty *);
static int tty_try_colour(struct tty *, int, const char *);
static void tty_force_cursor_colour(struct tty *, const char *);
static void tty_force_cursor_colour(struct tty *, int);
static void tty_cursor_pane(struct tty *, const struct tty_ctx *, u_int,
u_int);
static void tty_cursor_pane_unless_wrap(struct tty *,
@ -105,7 +105,7 @@ tty_init(struct tty *tty, struct client *c)
tty->client = c;
tty->cstyle = SCREEN_CURSOR_DEFAULT;
tty->ccolour = xstrdup("");
tty->ccolour = -1;
if (tcgetattr(c->fd, &tty->tio) != 0)
return (-1);
@ -341,8 +341,8 @@ tty_start_tty(struct tty *tty)
tty->flags |= TTY_STARTED;
tty_invalidate(tty);
if (*tty->ccolour != '\0')
tty_force_cursor_colour(tty, "");
if (tty->ccolour != -1)
tty_force_cursor_colour(tty, -1);
tty->mouse_drag_flag = 0;
tty->mouse_drag_update = NULL;
@ -406,7 +406,7 @@ tty_stop_tty(struct tty *tty)
}
if (tty->mode & MODE_BRACKETPASTE)
tty_raw(tty, tty_term_string(tty->term, TTYC_DSBP));
if (*tty->ccolour != '\0')
if (tty->ccolour != -1)
tty_raw(tty, tty_term_string(tty->term, TTYC_CR));
tty_raw(tty, tty_term_string(tty->term, TTYC_CNORM));
@ -451,7 +451,6 @@ void
tty_free(struct tty *tty)
{
tty_close(tty);
free(tty->ccolour);
}
void
@ -650,24 +649,38 @@ tty_set_title(struct tty *tty, const char *title)
}
static void
tty_force_cursor_colour(struct tty *tty, const char *ccolour)
tty_force_cursor_colour(struct tty *tty, int c)
{
if (*ccolour == '\0')
u_char r, g, b;
char s[13] = "";
if (c != -1)
c = colour_force_rgb(c);
if (c == tty->ccolour)
return;
if (c == -1)
tty_putcode(tty, TTYC_CR);
else
tty_putcode_ptr1(tty, TTYC_CS, ccolour);
free(tty->ccolour);
tty->ccolour = xstrdup(ccolour);
else {
colour_split_rgb(c, &r, &g, &b);
xsnprintf(s, sizeof s, "rgb:%02hhx/%02hhx/%02hhx", r, g, b);
tty_putcode_ptr1(tty, TTYC_CS, s);
}
tty->ccolour = c;
}
static void
tty_update_cursor(struct tty *tty, int mode, int changed, struct screen *s)
{
enum screen_cursor_style cstyle;
enum screen_cursor_style cstyle;
int ccolour;
/* Set cursor colour if changed. */
if (s != NULL && strcmp(s->ccolour, tty->ccolour) != 0)
tty_force_cursor_colour(tty, s->ccolour);
if (s != NULL) {
ccolour = s->ccolour;
if (s->ccolour == -1)
ccolour = s->default_ccolour;
tty_force_cursor_colour(tty, ccolour);
}
/* If cursor is off, set as invisible. */
if (~mode & MODE_CURSOR) {