summaryrefslogtreecommitdiffstats
path: root/input-keys.c
diff options
context:
space:
mode:
authornicm <nicm>2015-04-19 21:34:21 +0000
committernicm <nicm>2015-04-19 21:34:21 +0000
commitbf635e7741f7b881f67ec7e4a5caa02f7ff3d786 (patch)
treec2da2accbb948824e54043a1539b2e3ca9187168 /input-keys.c
parentee123c248951450100475717f5bd45f292d9bb4d (diff)
Rewrite of tmux mouse support which was a mess. Instead of having
options for "mouse-this" and "mouse-that", mouse events may be bound as keys and there is one option "mouse" that turns on mouse support entirely (set -g mouse on). See the new MOUSE SUPPORT section of the man page for description of the key names and new flags (-t= to specify the pane or window under mouse as a target, and send-keys -M to pass through a mouse event). The default builtin bindings for the mouse are: bind -n MouseDown1Pane select-pane -t=; send-keys -M bind -n MouseDown1Status select-window -t= bind -n MouseDrag1Pane copy-mode -M bind -n MouseDrag1Border resize-pane -M To get the effect of turning mode-mouse off, do: unbind -n MouseDrag1Pane unbind -temacs-copy MouseDrag1Pane The old mouse options are now gone, set-option -q may be used to suppress warnings if mixing configuration files.
Diffstat (limited to 'input-keys.c')
-rw-r--r--input-keys.c97
1 files changed, 49 insertions, 48 deletions
diff --git a/input-keys.c b/input-keys.c
index f2d010d8..ae00e4a9 100644
--- a/input-keys.c
+++ b/input-keys.c
@@ -31,6 +31,8 @@
* direction with output).
*/
+void input_key_mouse(struct window_pane *, struct mouse_event *);
+
struct input_key_ent {
int key;
const char *data;
@@ -135,7 +137,7 @@ const struct input_key_ent input_keys[] = {
/* Translate a key code into an output key sequence. */
void
-input_key(struct window_pane *wp, int key)
+input_key(struct window_pane *wp, int key, struct mouse_event *m)
{
const struct input_key_ent *ike;
u_int i;
@@ -143,7 +145,14 @@ input_key(struct window_pane *wp, int key)
char *out;
u_char ch;
- log_debug("writing key 0x%x", key);
+ log_debug("writing key 0x%x (%s)", key, key_string_lookup_key(key));
+
+ /* If this is a mouse key, pass off to mouse function. */
+ if (KEYC_IS_MOUSE(key)) {
+ if (m != NULL && m->wp != -1 && (u_int)m->wp == wp->id)
+ input_key_mouse(wp, m);
+ return;
+ }
/*
* If this is a normal 7-bit key, just send it, with a leading escape
@@ -200,55 +209,47 @@ input_key(struct window_pane *wp, int key)
/* Translate mouse and output. */
void
-input_mouse(struct window_pane *wp, struct session *s, struct mouse_event *m)
+input_key_mouse(struct window_pane *wp, struct mouse_event *m)
{
- char buf[40];
- size_t len;
- struct paste_buffer *pb;
- int event;
-
- if (wp->screen->mode & ALL_MOUSE_MODES) {
- /*
- * Use the SGR (1006) extension only if the application
- * requested it and the underlying terminal also sent the event
- * in this format (this is because an old style mouse release
- * event cannot be converted into the new SGR format, since the
- * released button is unknown). Otherwise pretend that tmux
- * doesn't speak this extension, and fall back to the UTF-8
- * (1005) extension if the application requested, or to the
- * legacy format.
- */
- if (m->sgr && (wp->screen->mode & MODE_MOUSE_SGR)) {
- len = xsnprintf(buf, sizeof buf, "\033[<%u;%u;%u%c",
- m->sgr_xb, m->x + 1, m->y + 1,
- m->sgr_rel ? 'm' : 'M');
- } else if (wp->screen->mode & MODE_MOUSE_UTF8) {
- len = xsnprintf(buf, sizeof buf, "\033[M");
- 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->xb > 223)
- return;
- len = xsnprintf(buf, sizeof buf, "\033[M");
- buf[len++] = m->xb + 32;
- buf[len++] = m->x + 33;
- buf[len++] = m->y + 33;
- }
- bufferevent_write(wp->event, buf, len);
+ char buf[40];
+ size_t len;
+ u_int x, y;
+
+ if ((wp->screen->mode & ALL_MOUSE_MODES) == 0)
+ return;
+ if (!window_pane_visible(wp))
+ return;
+ if (cmd_mouse_at(wp, m, &x, &y, 0) != 0)
return;
- }
- if (options_get_number(&wp->window->options, "mode-mouse") != 1)
+ /* If this pane is not in button mode, discard motion events. */
+ if (!(wp->screen->mode & MODE_MOUSE_BUTTON) && (m->b & MOUSE_MASK_DRAG))
return;
- event = m->event & (MOUSE_EVENT_CLICK|MOUSE_EVENT_WHEEL);
- if (wp->mode == NULL && m->button == 1 && event == MOUSE_EVENT_CLICK) {
- pb = paste_get_top();
- if (pb != NULL)
- paste_send_pane(pb, wp, "\r", 1);
- } else 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, s, m);
+
+ /*
+ * Use the SGR (1006) extension only if the application requested it
+ * and the underlying terminal also sent the event in this format (this
+ * is because an old style mouse release event cannot be converted into
+ * the new SGR format, since the released button is unknown). Otherwise
+ * pretend that tmux doesn't speak this extension, and fall back to the
+ * UTF-8 (1005) extension if the application requested, or to the
+ * legacy format.
+ */
+ if (m->sgr_type != ' ' && (wp->screen->mode & MODE_MOUSE_SGR)) {
+ len = xsnprintf(buf, sizeof buf, "\033[<%u;%u;%u%c",
+ m->sgr_b, x + 1, y + 1, m->sgr_type);
+ } else 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(x + 33, &buf[len]);
+ len += utf8_split2(y + 33, &buf[len]);
+ } else {
+ if (m->b > 223)
+ return;
+ len = xsnprintf(buf, sizeof buf, "\033[M");
+ buf[len++] = m->b + 32;
+ buf[len++] = x + 33;
+ buf[len++] = y + 33;
}
+ bufferevent_write(wp->event, buf, len);
}