From c695c0c085ea7a603f740479eccdc2cf7836e626 Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Mon, 15 Oct 2012 21:53:30 +0000 Subject: [PATCH 01/13] Fix some function prototypes from Helmut Tessarek. --- cmd-list-clients.c | 2 +- cmd-list-keys.c | 2 +- cmd-new-window.c | 2 +- cmd-swap-window.c | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/cmd-list-clients.c b/cmd-list-clients.c index ba479689..92d25a9d 100644 --- a/cmd-list-clients.c +++ b/cmd-list-clients.c @@ -28,7 +28,7 @@ * List all clients. */ -int cmd_list_clients_exec(struct cmd *, struct cmd_ctx *); +enum cmd_retval cmd_list_clients_exec(struct cmd *, struct cmd_ctx *); const struct cmd_entry cmd_list_clients_entry = { "list-clients", "lsc", diff --git a/cmd-list-keys.c b/cmd-list-keys.c index d93f368b..ff6421ad 100644 --- a/cmd-list-keys.c +++ b/cmd-list-keys.c @@ -97,7 +97,7 @@ cmd_list_keys_exec(struct cmd *self, struct cmd_ctx *ctx) return (CMD_RETURN_NORMAL); } -int +enum cmd_retval cmd_list_keys_table(struct cmd *self, struct cmd_ctx *ctx) { struct args *args = self->args; diff --git a/cmd-new-window.c b/cmd-new-window.c index 1d9a1e66..2f111935 100644 --- a/cmd-new-window.c +++ b/cmd-new-window.c @@ -26,7 +26,7 @@ * Create a new window. */ -int cmd_new_window_exec(struct cmd *, struct cmd_ctx *); +enum cmd_retval cmd_new_window_exec(struct cmd *, struct cmd_ctx *); const struct cmd_entry cmd_new_window_entry = { "new-window", "neww", diff --git a/cmd-swap-window.c b/cmd-swap-window.c index afd55e0b..b2e2c119 100644 --- a/cmd-swap-window.c +++ b/cmd-swap-window.c @@ -26,7 +26,7 @@ * Swap one window with another. */ -int cmd_swap_window_exec(struct cmd *, struct cmd_ctx *); +enum cmd_retval cmd_swap_window_exec(struct cmd *, struct cmd_ctx *); const struct cmd_entry cmd_swap_window_entry = { "swap-window", "swapw", From 589b4b8c6a54541441d10e2578bca05d4b0153a0 Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Thu, 25 Oct 2012 11:11:58 +0000 Subject: [PATCH 02/13] Fix typo bell->bells from Thomas Adam. --- tmux.1 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tmux.1 b/tmux.1 index db60f8e0..c5c45b75 100644 --- a/tmux.1 +++ b/tmux.1 @@ -2039,7 +2039,7 @@ window of that session, .Ic none means all bells are ignored and .Ic current -means only bell in windows other than the current window are ignored. +means only bells in windows other than the current window are ignored. .It Xo Ic bell-on-alert .Op Ic on | off .Xc From 596e9d80681cf77459dd31f084daa468a766a9d8 Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Thu, 25 Oct 2012 11:14:46 +0000 Subject: [PATCH 03/13] Fix bad size in memcpy from Romain Francoise. --- window.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/window.c b/window.c index 71225a9b..07e6ae1b 100644 --- a/window.c +++ b/window.c @@ -1193,7 +1193,7 @@ winlink_clear_flags(struct winlink *wl) void window_mode_attrs(struct grid_cell *gc, struct options *oo) { - memcpy(gc, &grid_default_cell, sizeof gc); + memcpy(gc, &grid_default_cell, sizeof *gc); colour_set_fg(gc, options_get_number(oo, "mode-fg")); colour_set_bg(gc, options_get_number(oo, "mode-bg")); gc->attr |= options_get_number(oo, "mode-attr"); From 18236c1c1bd9afc994971fe2806dac905242be98 Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Thu, 25 Oct 2012 11:16:53 +0000 Subject: [PATCH 04/13] Fix BELL_NONE which had been broken in some code reorganisation or other also don't redraw unnecessarily. From Seiji Ohashi. --- server-window.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/server-window.c b/server-window.c index 8f3e2b63..8b34fc6c 100644 --- a/server-window.c +++ b/server-window.c @@ -75,12 +75,14 @@ server_window_check_bell(struct session *s, struct winlink *wl) if (s->curw != wl || s->flags & SESSION_UNATTACHED) wl->flags |= WINLINK_BELL; if (s->flags & SESSION_UNATTACHED) - return (1); + return (0); if (s->curw->window == wl->window) w->flags &= ~WINDOW_BELL; visual = options_get_number(&s->options, "visual-bell"); action = options_get_number(&s->options, "bell-action"); + if (action == BELL_NONE) + return (0); for (i = 0; i < ARRAY_LENGTH(&clients); i++) { c = ARRAY_ITEM(&clients, i); if (c == NULL || c->session != s) From 2a609b332f6cdc2ef6f3ffb525a3c74ada738ec4 Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Thu, 25 Oct 2012 11:26:47 +0000 Subject: [PATCH 05/13] Add ability to active pane in list-windows and find-window formats, from Carl Henrik Lunde. --- cmd-find-window.c | 1 + cmd-list-windows.c | 1 + 2 files changed, 2 insertions(+) diff --git a/cmd-find-window.c b/cmd-find-window.c index 340f6e1a..f2b20ae7 100644 --- a/cmd-find-window.c +++ b/cmd-find-window.c @@ -193,6 +193,7 @@ cmd_find_window_exec(struct cmd *self, struct cmd_ctx *ctx) ARRAY_ITEM(&find_list, i).list_ctx); format_session(cdata->ft, s); format_winlink(cdata->ft, s, wm); + format_window_pane(cdata->ft, wm->window->active); window_choose_add(wl->window->active, cdata); } diff --git a/cmd-list-windows.c b/cmd-list-windows.c index 146d29aa..0485e4a3 100644 --- a/cmd-list-windows.c +++ b/cmd-list-windows.c @@ -99,6 +99,7 @@ cmd_list_windows_session( format_add(ft, "line", "%u", n); format_session(ft, s); format_winlink(ft, s, wl); + format_window_pane(ft, wl->window->active); line = format_expand(ft, template); ctx->print(ctx, "%s", line); From d210d99ccecfaa2ef23a65609dc8cbb26bcfe236 Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Fri, 26 Oct 2012 14:35:42 +0000 Subject: [PATCH 06/13] Make mouse event structure clearer by defining events (up, click, drag) and simplifying how buttons and wheels are represented, from Ailin Nemui. Should be no functional changes. --- input-keys.c | 12 ++++----- layout.c | 41 ++++++++++++++-------------- server-client.c | 68 +++++++++++++++++++++------------------------- tmux.h | 72 ++++++++++++++++++++++++++++++------------------- tty-keys.c | 56 +++++++++++++++++++++++++++++++------- window-choose.c | 2 +- window-copy.c | 10 +++---- window.c | 2 +- 8 files changed, 155 insertions(+), 108 deletions(-) diff --git a/input-keys.c b/input-keys.c index bd1c6157..eee469e8 100644 --- a/input-keys.c +++ b/input-keys.c @@ -200,7 +200,7 @@ input_key(struct window_pane *wp, int key) /* Translate mouse and output. */ void -input_mouse(struct window_pane *wp, struct mouse_event *m) +input_mouse(struct window_pane *wp, struct session *s, struct mouse_event *m) { char buf[10]; size_t len; @@ -208,14 +208,14 @@ input_mouse(struct window_pane *wp, struct mouse_event *m) if (wp->screen->mode & ALL_MOUSE_MODES) { if (wp->screen->mode & MODE_MOUSE_UTF8) { len = xsnprintf(buf, sizeof buf, "\033[M"); - len += utf8_split2(m->b + 32, &buf[len]); + len += utf8_split2(m->xb + 32, &buf[len]); len += utf8_split2(m->x + 33, &buf[len]); len += utf8_split2(m->y + 33, &buf[len]); } else { - if (m->b > 223 || m->x >= 222 || m->y > 222) + if (m->xb > 223 || m->x >= 222 || m->y > 222) return; len = xsnprintf(buf, sizeof buf, "\033[M"); - buf[len++] = m->b + 32; + buf[len++] = m->xb + 32; buf[len++] = m->x + 33; buf[len++] = m->y + 33; } @@ -223,12 +223,12 @@ input_mouse(struct window_pane *wp, struct mouse_event *m) return; } - if ((m->b & 3) != 1 && + if ((m->xb & 3) != 1 && options_get_number(&wp->window->options, "mode-mouse") == 1) { if (window_pane_set_mode(wp, &window_copy_mode) == 0) { window_copy_init_from_pane(wp); if (wp->mode->mouse != NULL) - wp->mode->mouse(wp, NULL, m); + wp->mode->mouse(wp, s, m); } return; } diff --git a/layout.c b/layout.c index a0e624fb..adae0ec3 100644 --- a/layout.c +++ b/layout.c @@ -488,50 +488,51 @@ layout_resize_pane(struct window_pane *wp, enum layout_type type, int change) } void -layout_resize_pane_mouse(struct client *c, struct mouse_event *mouse) +layout_resize_pane_mouse(struct client *c) { struct window *w; struct window_pane *wp; + struct mouse_event *m = &c->tty.mouse; int pane_border; w = c->session->curw->window; pane_border = 0; - if ((c->last_mouse.b & MOUSE_BUTTON) != MOUSE_UP && - (c->last_mouse.b & MOUSE_RESIZE_PANE)) { + if (m->event & MOUSE_EVENT_DRAG && m->flags & MOUSE_RESIZE_PANE) { TAILQ_FOREACH(wp, &w->panes, entry) { - if (wp->xoff + wp->sx == c->last_mouse.x && - wp->yoff <= 1 + c->last_mouse.y && - wp->yoff + wp->sy >= c->last_mouse.y) { + if (wp->xoff + wp->sx == m->lx && + wp->yoff <= 1 + m->ly && + wp->yoff + wp->sy >= m->ly) { layout_resize_pane(wp, LAYOUT_LEFTRIGHT, - mouse->x - c->last_mouse.x); + m->x - m->lx); pane_border = 1; } - if (wp->yoff + wp->sy == c->last_mouse.y && - wp->xoff <= 1 + c->last_mouse.x && - wp->xoff + wp->sx >= c->last_mouse.x) { + if (wp->yoff + wp->sy == m->ly && + wp->xoff <= 1 + m->lx && + wp->xoff + wp->sx >= m->lx) { layout_resize_pane(wp, LAYOUT_TOPBOTTOM, - mouse->y - c->last_mouse.y); + m->y - m->ly); pane_border = 1; } } if (pane_border) server_redraw_window(w); - } else if (mouse->b != MOUSE_UP && - mouse->b == (mouse->b & MOUSE_BUTTON)) { + } else if (~m->event & MOUSE_EVENT_UP) { TAILQ_FOREACH(wp, &w->panes, entry) { - if ((wp->xoff + wp->sx == mouse->x && - wp->yoff <= 1 + mouse->y && - wp->yoff + wp->sy >= mouse->y) || - (wp->yoff + wp->sy == mouse->y && - wp->xoff <= 1 + mouse->x && - wp->xoff + wp->sx >= mouse->x)) { + if ((wp->xoff + wp->sx == m->x && + wp->yoff <= 1 + m->y && + wp->yoff + wp->sy >= m->y) || + (wp->yoff + wp->sy == m->y && + wp->xoff <= 1 + m->x && + wp->xoff + wp->sx >= m->x)) { pane_border = 1; } } } if (pane_border) - mouse->b |= MOUSE_RESIZE_PANE; + m->flags |= MOUSE_RESIZE_PANE; + else + m->flags &= ~MOUSE_RESIZE_PANE; } int diff --git a/server-client.c b/server-client.c index 7f5bfe13..3db11ecb 100644 --- a/server-client.c +++ b/server-client.c @@ -28,8 +28,7 @@ #include "tmux.h" -void server_client_check_mouse(struct client *, struct window_pane *, - struct mouse_event *); +void server_client_check_mouse(struct client *, struct window_pane *); void server_client_repeat_timer(int, short, void *); void server_client_check_exit(struct client *); void server_client_check_redraw(struct client *); @@ -87,8 +86,12 @@ server_client_create(int fd) c->prompt_buffer = NULL; c->prompt_index = 0; - c->last_mouse.b = MOUSE_UP; - c->last_mouse.x = c->last_mouse.y = -1; + c->tty.mouse.xb = c->tty.mouse.button = 3; + c->tty.mouse.x = c->tty.mouse.y = -1; + c->tty.mouse.lx = c->tty.mouse.ly = -1; + c->tty.mouse.sx = c->tty.mouse.sy = -1; + c->tty.mouse.event = MOUSE_EVENT_UP; + c->tty.mouse.flags = 0; evtimer_set(&c->repeat_timer, server_client_repeat_timer, c); @@ -271,37 +274,28 @@ server_client_status_timer(void) /* Check for mouse keys. */ void -server_client_check_mouse( - struct client *c, struct window_pane *wp, struct mouse_event *mouse) +server_client_check_mouse(struct client *c, struct window_pane *wp) { - struct session *s = c->session; - struct options *oo = &s->options; - int statusat; + struct session *s = c->session; + struct options *oo = &s->options; + struct mouse_event *m = &c->tty.mouse; + int statusat; statusat = status_at_line(c); /* Is this a window selection click on the status line? */ - if (statusat != -1 && mouse->y == (u_int)statusat && + if (statusat != -1 && m->y == (u_int)statusat && options_get_number(oo, "mouse-select-window")) { - if (mouse->b == MOUSE_UP && c->last_mouse.b != MOUSE_UP) { - status_set_window_at(c, mouse->x); - recalculate_sizes(); - return; - } - if (mouse->b & MOUSE_45) { - if ((mouse->b & MOUSE_BUTTON) == MOUSE_1) { + if (m->event & MOUSE_EVENT_CLICK) { + status_set_window_at(c, m->x); + } else if (m->event == MOUSE_EVENT_WHEEL) { + if (m->wheel == MOUSE_WHEEL_UP) session_previous(c->session, 0); - server_redraw_session(s); - recalculate_sizes(); - } - if ((mouse->b & MOUSE_BUTTON) == MOUSE_2) { + else if (m->wheel == MOUSE_WHEEL_DOWN) session_next(c->session, 0); - server_redraw_session(s); - recalculate_sizes(); - } - return; + server_redraw_session(s); } - memcpy(&c->last_mouse, mouse, sizeof c->last_mouse); + recalculate_sizes(); return; } @@ -310,27 +304,25 @@ server_client_check_mouse( * top and limit if at the bottom. From here on a struct mouse * represents the offset onto the window itself. */ - if (statusat == 0 &&mouse->y > 0) - mouse->y--; - else if (statusat > 0 && mouse->y >= (u_int)statusat) - mouse->y = statusat - 1; + if (statusat == 0 && m->y > 0) + m->y--; + else if (statusat > 0 && m->y >= (u_int)statusat) + m->y = statusat - 1; /* Is this a pane selection? Allow down only in copy mode. */ if (options_get_number(oo, "mouse-select-pane") && - ((!(mouse->b & MOUSE_DRAG) && mouse->b != MOUSE_UP) || - wp->mode != &window_copy_mode)) { - window_set_active_at(wp->window, mouse->x, mouse->y); + (m->event == MOUSE_EVENT_DOWN || wp->mode != &window_copy_mode)) { + window_set_active_at(wp->window, m->x, m->y); server_redraw_window_borders(wp->window); wp = wp->window->active; /* may have changed */ } /* Check if trying to resize pane. */ if (options_get_number(oo, "mouse-resize-pane")) - layout_resize_pane_mouse(c, mouse); + layout_resize_pane_mouse(c); /* Update last and pass through to client. */ - memcpy(&c->last_mouse, mouse, sizeof c->last_mouse); - window_pane_mouse(wp, c->session, mouse); + window_pane_mouse(wp, c->session, m); } /* Handle data key input from client. */ @@ -385,7 +377,7 @@ server_client_handle_key(struct client *c, int key) if (key == KEYC_MOUSE) { if (c->flags & CLIENT_READONLY) return; - server_client_check_mouse(c, wp, &c->tty.mouse); + server_client_check_mouse(c, wp); return; } @@ -524,7 +516,7 @@ server_client_reset_state(struct client *c) * a smooth appearance. */ mode = s->mode; - if ((c->last_mouse.b & MOUSE_RESIZE_PANE) && + if ((c->tty.mouse.flags & MOUSE_RESIZE_PANE) && !(mode & (MODE_MOUSE_BUTTON|MODE_MOUSE_ANY))) mode |= MODE_MOUSE_BUTTON; diff --git a/tmux.h b/tmux.h index e5ad1718..2e2d982f 100644 --- a/tmux.h +++ b/tmux.h @@ -1119,29 +1119,6 @@ struct session { RB_HEAD(sessions, session); ARRAY_DECL(sessionslist, struct session *); -/* - * Mouse input. xterm mouse mode is fairly silly. Buttons are in the bottom two - * bits: 0 = button 1; 1 = button 2; 2 = button 3; 3 = buttons released. Bits - * 3, 4 and 5 are for keys. Bit 6 is set for dragging and 7 for mouse buttons 4 - * and 5. - */ -struct mouse_event { - u_int b; -#define MOUSE_1 0 -#define MOUSE_2 1 -#define MOUSE_3 2 -#define MOUSE_UP 3 -#define MOUSE_BUTTON 3 -#define MOUSE_SHIFT 4 -#define MOUSE_ESCAPE 8 -#define MOUSE_CTRL 16 -#define MOUSE_DRAG 32 -#define MOUSE_45 64 -#define MOUSE_RESIZE_PANE 128 /* marker for resizing */ - u_int x; - u_int y; -}; - /* TTY information. */ struct tty_key { char ch; @@ -1170,6 +1147,47 @@ struct tty_term { }; LIST_HEAD(tty_terms, tty_term); +/* Mouse wheel states. */ +#define MOUSE_WHEEL_UP 0 +#define MOUSE_WHEEL_DOWN 1 + +/* Mouse events. */ +#define MOUSE_EVENT_DOWN (1 << 0) +#define MOUSE_EVENT_DRAG (1 << 1) +#define MOUSE_EVENT_UP (1 << 2) +#define MOUSE_EVENT_CLICK (1 << 3) +#define MOUSE_EVENT_WHEEL (1 << 4) + +/* Mouse flags. */ +#define MOUSE_RESIZE_PANE (1 << 0) + +/* + * Mouse input. When sent by xterm: + * + * - buttons are in the bottom two bits: 0 = b1; 1 = b2; 2 = b3; 3 = released + * - bits 3, 4 and 5 are for keys + * - bit 6 is set for dragging + * - bit 7 for buttons 4 and 5 + */ +struct mouse_event { + u_int xb; + + u_int x; + u_int lx; + u_int sx; + + u_int y; + u_int ly; + u_int sy; + + u_int button; + u_int clicks; + + int wheel; + int event; + int flags; +}; + struct tty { struct client *client; @@ -1330,8 +1348,6 @@ struct client { struct session *session; struct session *last_session; - struct mouse_event last_mouse; - int wlmouse; int references; @@ -1926,7 +1942,8 @@ void input_parse(struct window_pane *); /* input-key.c */ void input_key(struct window_pane *, int); -void input_mouse(struct window_pane *, struct mouse_event *); +void input_mouse(struct window_pane *, struct session *, + struct mouse_event *); /* xterm-keys.c */ char *xterm_keys_lookup(int); @@ -2170,8 +2187,7 @@ void layout_free(struct window *); void layout_resize(struct window *, u_int, u_int); void layout_resize_pane( struct window_pane *, enum layout_type, int); -void layout_resize_pane_mouse( - struct client *c, struct mouse_event *mouse); +void layout_resize_pane_mouse(struct client *c); void layout_assign_pane(struct layout_cell *, struct window_pane *); struct layout_cell *layout_split_pane( struct window_pane *, enum layout_type, int, int); diff --git a/tty-keys.c b/tty-keys.c index f375a07b..6d18d791 100644 --- a/tty-keys.c +++ b/tty-keys.c @@ -611,7 +611,7 @@ tty_keys_mouse(struct tty *tty, const char *buf, size_t len, size_t *size) { struct mouse_event *m = &tty->mouse; struct utf8_data utf8data; - u_int i, value; + u_int i, value, x, y, b; /* * Standard mouse sequences are \033[M followed by three characters @@ -622,6 +622,7 @@ tty_keys_mouse(struct tty *tty, const char *buf, size_t len, size_t *size) */ *size = 0; + x = y = b = 0; /* First three bytes are always \033[M. */ if (buf[0] != '\033') @@ -661,21 +662,58 @@ tty_keys_mouse(struct tty *tty, const char *buf, size_t len, size_t *size) } if (i == 0) - m->b = value; + b = value; else if (i == 1) - m->x = value; + x = value; else - m->y = value; + y = value; } log_debug("mouse input: %.*s", (int) *size, buf); /* Check and return the mouse input. */ - if (m->b < 32 || m->x < 33 || m->y < 33) + if (b < 32 || x < 33 || y < 33) return (-1); - m->b -= 32; - m->x -= 33; - m->y -= 33; - log_debug("mouse position: x=%u y=%u b=%u", m->x, m->y, m->b); + b -= 32; + x -= 33; + y -= 33; + log_debug("mouse position: x=%u y=%u b=%u", x, y, b); + + /* Fill in mouse structure. */ + if (~m->event & MOUSE_EVENT_WHEEL) { + m->lx = m->x; + m->ly = m->y; + } + m->xb = b; + if (b & 64) { /* wheel button */ + b &= 3; + if (b == 0) + m->wheel = MOUSE_WHEEL_UP; + else if (b == 1) + m->wheel = MOUSE_WHEEL_DOWN; + m->event = MOUSE_EVENT_WHEEL; + } else if ((b & 3) == 3) { + if (~m->event & MOUSE_EVENT_DRAG && x == m->x && y == m->y) { + m->event = MOUSE_EVENT_CLICK; + } else + m->event = MOUSE_EVENT_DRAG; + m->event |= MOUSE_EVENT_UP; + } else { + if (b & 32) /* drag motion */ + m->event = MOUSE_EVENT_DRAG; + else { + if (m->event & MOUSE_EVENT_UP && x == m->x && y == m->y) + m->clicks = (m->clicks + 1) % 3; + else + m->clicks = 0; + m->sx = x; + m->sy = y; + m->event = MOUSE_EVENT_DOWN; + } + m->button = (b & 3); + } + m->x = x; + m->y = y; + return (0); } diff --git a/window-choose.c b/window-choose.c index 019f4125..ab0d803b 100644 --- a/window-choose.c +++ b/window-choose.c @@ -623,7 +623,7 @@ window_choose_mouse( struct window_choose_mode_item *item; u_int idx; - if ((m->b & 3) == 3) + if (~m->event & MOUSE_EVENT_CLICK) return; if (m->x >= screen_size_x(s)) return; diff --git a/window-copy.c b/window-copy.c index bed645f0..97899595 100644 --- a/window-copy.c +++ b/window-copy.c @@ -829,11 +829,11 @@ window_copy_mouse( return; /* If mouse wheel (buttons 4 and 5), scroll. */ - if ((m->b & MOUSE_45)) { - if ((m->b & MOUSE_BUTTON) == MOUSE_1) { + if (m->event == MOUSE_EVENT_WHEEL) { + if (m->wheel == MOUSE_WHEEL_UP) { for (i = 0; i < 5; i++) window_copy_cursor_up(wp, 0); - } else if ((m->b & MOUSE_BUTTON) == MOUSE_2) { + } else if (m->wheel == MOUSE_WHEEL_DOWN) { for (i = 0; i < 5; i++) window_copy_cursor_down(wp, 0); if (data->oy == 0) @@ -847,7 +847,7 @@ window_copy_mouse( * pressed, or stop the selection on their release. */ if (s->mode & MODE_MOUSE_BUTTON) { - if ((m->b & MOUSE_BUTTON) != MOUSE_UP) { + if (~m->event & MOUSE_EVENT_UP) { window_copy_update_cursor(wp, m->x, m->y); if (window_copy_update_selection(wp)) window_copy_redraw_screen(wp); @@ -857,7 +857,7 @@ window_copy_mouse( } /* Otherwise if other buttons pressed, start selection and motion. */ - if ((m->b & MOUSE_BUTTON) != MOUSE_UP) { + if (~m->event & MOUSE_EVENT_UP) { s->mode &= ~MODE_MOUSE_STANDARD; s->mode |= MODE_MOUSE_BUTTON; diff --git a/window.c b/window.c index 07e6ae1b..fc9fa5f3 100644 --- a/window.c +++ b/window.c @@ -1011,7 +1011,7 @@ window_pane_mouse( options_get_number(&wp->window->options, "mode-mouse")) wp->mode->mouse(wp, sess, m); } else if (wp->fd != -1) - input_mouse(wp, m); + input_mouse(wp, sess, m); } int From 241a746f3219d90ec2fd081fe9e81a681d9e6cbd Mon Sep 17 00:00:00 2001 From: okan Date: Wed, 31 Oct 2012 19:11:18 +0000 Subject: [PATCH 07/13] fix an off-by-one ok nicm@ --- cmd-set-environment.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmd-set-environment.c b/cmd-set-environment.c index 67f28af5..9cebc951 100644 --- a/cmd-set-environment.c +++ b/cmd-set-environment.c @@ -57,7 +57,7 @@ cmd_set_environment_exec(struct cmd *self, struct cmd_ctx *ctx) return (CMD_RETURN_ERROR); } - if (args->argc < 1) + if (args->argc < 2) value = NULL; else value = args->argv[1]; From c68efec6c0f1a6ecf4950e4ddada4430fdea4156 Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Mon, 5 Nov 2012 13:13:04 +0000 Subject: [PATCH 08/13] Show last client activity time in default choose-client list. --- tmux.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/tmux.h b/tmux.h index 2e2d982f..4a5326cf 100644 --- a/tmux.h +++ b/tmux.h @@ -100,7 +100,8 @@ extern char **environ; #define CHOOSE_CLIENT_TEMPLATE \ "#{client_tty}: #{session_name} " \ "[#{client_width}x#{client_height} #{client_termname}]" \ - "#{?client_utf8, (utf8),} #{?client_readonly, (ro),}" + "#{?client_utf8, (utf8),}#{?client_readonly, (ro),} " \ + "(last used #{client_activity_string})" /* Default templates for choose-tree. */ #define CHOOSE_TREE_SESSION_TEMPLATE \ From cb4553bd06645713c83ae169893eb1db6038c566 Mon Sep 17 00:00:00 2001 From: Thomas Adam Date: Thu, 8 Nov 2012 21:14:32 +0000 Subject: [PATCH 09/13] Add .mailmap for commit author translations Because it's not possible to enumerate up-front all of the committers to tmux coming from OpenBSD, at the time a commit is imported in to git from the OpenBSD CVS repository, the author information is not known to Git, necessarily. But it's possible to alter for output the respective author after the fact, via Git's .mailmap file. It is this file which will therefore provide a new mapping of OpenBSD commiter to an actual real name and real email address. --- .mailmap | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 .mailmap diff --git a/.mailmap b/.mailmap new file mode 100644 index 00000000..d8344641 --- /dev/null +++ b/.mailmap @@ -0,0 +1,21 @@ +Bob Beck beck +Igor Sobrado sobrado +Jacek Masiulaniec jacekm +Jason McIntyre jcm +Joel Sing jsing +Marc Espie espie +Matthew Dempsky matthew +Matthias Kilian kili +Matthieu Herrb matthieu +Miod Vallat miod +Nicholas Marriott nicm +Okan Demirmen okan +Philip Guenther guenther +Pierre-Yves Ritschard pyr +Ray Lai ray +Ryan McBride mcbride +Stefan Sperling stsp +Stuart Henderson sthen +Ted Unangst tedu +Theo Deraadt deraadt +William Yodlowsky william From e4679172e3f4307b14f0e1715dc33ca640dc038b Mon Sep 17 00:00:00 2001 From: Thomas Adam Date: Thu, 8 Nov 2012 21:39:35 +0000 Subject: [PATCH 10/13] Sanitise additional .mailmap entries This sanitises multiple author addresses some more, mapping them back to one common entity. --- .mailmap | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.mailmap b/.mailmap index d8344641..a7a401ff 100644 --- a/.mailmap +++ b/.mailmap @@ -9,6 +9,8 @@ Matthias Kilian kili Matthieu Herrb matthieu Miod Vallat miod Nicholas Marriott nicm +Nicholas Marriott no_author + Okan Demirmen okan Philip Guenther guenther Pierre-Yves Ritschard pyr @@ -18,4 +20,5 @@ Stefan Sperling stsp Stuart Henderson sthen Ted Unangst tedu Theo Deraadt deraadt +Thomas Adam Thomas William Yodlowsky william From 827b311c8172f3543f9c38dc1d7740bba1d9aeaa Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Mon, 19 Nov 2012 10:38:06 +0000 Subject: [PATCH 11/13] Use a utility function for common code to show errors in config file, from Thomas Adam. --- cfg.c | 22 ++++++++++++++++++++++ cmd-new-session.c | 16 +++------------- server.c | 21 +++++---------------- tmux.h | 1 + 4 files changed, 31 insertions(+), 29 deletions(-) diff --git a/cfg.c b/cfg.c index ead99818..ae7d9a30 100644 --- a/cfg.c +++ b/cfg.c @@ -173,3 +173,25 @@ load_cfg(const char *path, struct cmd_ctx *ctxin, struct causelist *causes) return (retval); } + +void +show_cfg_causes(struct session *s) +{ + struct window_pane *wp; + char *cause; + u_int i; + + if (s == NULL || ARRAY_EMPTY(&cfg_causes)) + return; + + wp = s->curw->window->active; + + window_pane_set_mode(wp, &window_copy_mode); + window_copy_init_for_output(wp); + for (i = 0; i < ARRAY_LENGTH(&cfg_causes); i++) { + cause = ARRAY_ITEM(&cfg_causes, i); + window_copy_add(wp, "%s", cause); + free(cause); + } + ARRAY_FREE(&cfg_causes); +} diff --git a/cmd-new-session.c b/cmd-new-session.c index cd1bc2b1..0fcea353 100644 --- a/cmd-new-session.c +++ b/cmd-new-session.c @@ -58,14 +58,13 @@ cmd_new_session_exec(struct cmd *self, struct cmd_ctx *ctx) struct args *args = self->args; struct session *s, *old_s, *groupwith; struct window *w; - struct window_pane *wp; struct environ env; struct termios tio, *tiop; struct passwd *pw; const char *newname, *target, *update, *cwd, *errstr; char *cmd, *cause; int detached, idx; - u_int sx, sy, i; + u_int sx, sy; newname = args_get(args, 's'); if (newname != NULL) { @@ -257,17 +256,8 @@ cmd_new_session_exec(struct cmd *self, struct cmd_ctx *ctx) * If there are still configuration file errors to display, put the new * session's current window into more mode and display them now. */ - if (cfg_finished && !ARRAY_EMPTY(&cfg_causes)) { - wp = s->curw->window->active; - window_pane_set_mode(wp, &window_copy_mode); - window_copy_init_for_output(wp); - for (i = 0; i < ARRAY_LENGTH(&cfg_causes); i++) { - cause = ARRAY_ITEM(&cfg_causes, i); - window_copy_add(wp, "%s", cause); - free(cause); - } - ARRAY_FREE(&cfg_causes); - } + if (cfg_finished) + show_cfg_causes(s); return (detached ? CMD_RETURN_NORMAL : CMD_RETURN_ATTACH); } diff --git a/server.c b/server.c index 740f71d9..bad22270 100644 --- a/server.c +++ b/server.c @@ -106,11 +106,8 @@ server_create_socket(void) int server_start(int lockfd, char *lockfile) { - struct window_pane *wp; - int pair[2]; - char *cause; - struct timeval tv; - u_int i; + int pair[2]; + struct timeval tv; /* The first client is special and gets a socketpair; create it. */ if (socketpair(AF_UNIX, SOCK_STREAM, PF_UNSPEC, pair) != 0) @@ -178,17 +175,9 @@ server_start(int lockfd, char *lockfile) * If there is a session already, put the current window and pane into * more mode. */ - if (!RB_EMPTY(&sessions) && !ARRAY_EMPTY(&cfg_causes)) { - wp = RB_MIN(sessions, &sessions)->curw->window->active; - window_pane_set_mode(wp, &window_copy_mode); - window_copy_init_for_output(wp); - for (i = 0; i < ARRAY_LENGTH(&cfg_causes); i++) { - cause = ARRAY_ITEM(&cfg_causes, i); - window_copy_add(wp, "%s", cause); - free(cause); - } - ARRAY_FREE(&cfg_causes); - } + if (!RB_EMPTY(&sessions) && !ARRAY_EMPTY(&cfg_causes)) + show_cfg_causes(RB_MIN(sessions, &sessions)); + cfg_finished = 1; server_add_accept(0); diff --git a/tmux.h b/tmux.h index 4a5326cf..2a36c2da 100644 --- a/tmux.h +++ b/tmux.h @@ -1520,6 +1520,7 @@ extern int cfg_finished; extern struct causelist cfg_causes; void printflike2 cfg_add_cause(struct causelist *, const char *, ...); int load_cfg(const char *, struct cmd_ctx *, struct causelist *); +void show_cfg_causes(struct session *); /* format.c */ int format_cmp(struct format_entry *, struct format_entry *); From 9a7e5bd1d30ab60ef6cebfedfbdb37c6a05e9bcb Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Mon, 19 Nov 2012 10:50:24 +0000 Subject: [PATCH 12/13] Clarify some points about config files, notably that they are only read at server start. From Thomas Adam. --- tmux.1 | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/tmux.1 b/tmux.1 index c5c45b75..4bf55443 100644 --- a/tmux.1 +++ b/tmux.1 @@ -124,13 +124,19 @@ loads the system configuration file from .Pa /etc/tmux.conf , if present, then looks for a user configuration file at .Pa ~/.tmux.conf . +.Pp The configuration file is a set of .Nm commands which are executed in sequence when the server is first started. -.Pp -If a command in the configuration file fails, .Nm -will report an error and exit without executing further commands. +loads configuration files once when the server process has started. +The +.Ic source-file +command may be used to load a file later. +.Pp +.Nm +shows any error messages from commands in configuration files in the first +session created, and continues to process the rest of the configuration file. .It Fl L Ar socket-name .Nm stores the server socket in a directory under From 0679eb6a6d6bab129264784009e70333b34ca6a8 Mon Sep 17 00:00:00 2001 From: Nicholas Marriott Date: Mon, 19 Nov 2012 10:51:25 +0000 Subject: [PATCH 13/13] Add halfpage commands to mode command string table (missed by accident), from Thomas Adam. --- mode-key.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/mode-key.c b/mode-key.c index eae405ee..821f1ef4 100644 --- a/mode-key.c +++ b/mode-key.c @@ -105,6 +105,8 @@ const struct mode_key_cmdstr mode_key_cmdstr_copy[] = { { MODEKEYCOPY_DOWN, "cursor-down" }, { MODEKEYCOPY_ENDOFLINE, "end-of-line" }, { MODEKEYCOPY_GOTOLINE, "goto-line" }, + { MODEKEYCOPY_HALFPAGEDOWN, "halfpage-down" }, + { MODEKEYCOPY_HALFPAGEUP, "halfpage-up" }, { MODEKEYCOPY_HISTORYBOTTOM, "history-bottom" }, { MODEKEYCOPY_HISTORYTOP, "history-top" }, { MODEKEYCOPY_JUMP, "jump-forward" },