summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNicholas Marriott <nicholas.marriott@gmail.com>2020-05-16 14:57:36 +0100
committerNicholas Marriott <nicholas.marriott@gmail.com>2020-05-16 14:57:36 +0100
commit57fe03dc5a132ee131de457afa5724ec735ae811 (patch)
tree2166e2cd9bc841e1e423629c75dc2240302ceb48
parent53c84fd4aa87b4ff80e79ef79155f13c69f1aebc (diff)
Move lazy resize from the pane to the window, there is no point in resizing the
window unless it is the current window, and if we do and don't resize the pane until later there are problems if the size changes from A to B then back to A.
-rw-r--r--resize.c25
-rw-r--r--server-client.c62
-rw-r--r--tmux.h6
-rw-r--r--window.c5
4 files changed, 62 insertions, 36 deletions
diff --git a/resize.c b/resize.c
index 15d146d8..68717e35 100644
--- a/resize.c
+++ b/resize.c
@@ -61,6 +61,7 @@ resize_window(struct window *w, u_int sx, u_int sy, int xpixel, int ypixel)
tty_update_window_offset(w);
server_redraw_window(w);
notify_window("window-layout-changed", w);
+ w->flags &= ~WINDOW_RESIZE;
}
static int
@@ -346,16 +347,30 @@ recalculate_size(struct window *w)
changed = 0;
break;
}
- if (changed && w->sx == sx && w->sy == sy)
- changed = 0;
+ if (w->flags & WINDOW_RESIZE) {
+ if (changed && w->new_sx == sx && w->new_sy == sy)
+ changed = 0;
+ } else {
+ if (changed && w->sx == sx && w->sy == sy)
+ changed = 0;
+ }
if (!changed) {
tty_update_window_offset(w);
return;
}
- log_debug("%s: @%u changed to %u,%u (%ux%u)", __func__, w->id, sx, sy,
- xpixel, ypixel);
- resize_window(w, sx, sy, xpixel, ypixel);
+ log_debug("%s: @%u new size %u,%u", __func__, w->id, sx, sy);
+ if (type == WINDOW_SIZE_MANUAL)
+ resize_window(w, sx, sy, xpixel, ypixel);
+ else {
+ w->new_sx = sx;
+ w->new_sy = sy;
+ w->new_xpixel = xpixel;
+ w->new_ypixel = ypixel;
+
+ w->flags |= WINDOW_RESIZE;
+ tty_update_window_offset(w);
+ }
}
void
diff --git a/server-client.c b/server-client.c
index 87a4f533..24a564c0 100644
--- a/server-client.c
+++ b/server-client.c
@@ -31,8 +31,9 @@
#include "tmux.h"
static void server_client_free(int, short, void *);
-static void server_client_check_focus(struct window_pane *);
-static void server_client_check_resize(struct window_pane *);
+static void server_client_check_pane_focus(struct window_pane *);
+static void server_client_check_pane_resize(struct window_pane *);
+static void server_client_check_window_resize(struct window *);
static key_code server_client_check_mouse(struct client *, struct key_event *);
static void server_client_repeat_timer(int, short, void *);
static void server_client_click_timer(int, short, void *);
@@ -1339,10 +1340,13 @@ server_client_loop(void)
struct client *c;
struct window *w;
struct window_pane *wp;
- struct winlink *wl;
- struct session *s;
- int focus, attached, resize;
+ int focus;
+
+ /* Check for window resize. This is done before redrawing. */
+ RB_FOREACH(w, windows, &windows)
+ server_client_check_window_resize(w);
+ /* Check clients. */
TAILQ_FOREACH(c, &clients, entry) {
server_client_check_exit(c);
if (c->session != NULL) {
@@ -1354,34 +1358,14 @@ server_client_loop(void)
/*
* Any windows will have been redrawn as part of clients, so clear
* their flags now. Also check pane focus and resize.
- *
- * As an optimization, panes in windows that are in an attached session
- * but not the current window are not resized (this reduces the amount
- * of work needed when, for example, resizing an X terminal a
- * lot). Windows in no attached session are resized immediately since
- * that is likely to have come from a command like split-window and be
- * what the user wanted.
*/
focus = options_get_number(global_options, "focus-events");
RB_FOREACH(w, windows, &windows) {
- attached = resize = 0;
- TAILQ_FOREACH(wl, &w->winlinks, wentry) {
- s = wl->session;
- if (s->attached != 0)
- attached = 1;
- if (s->attached != 0 && s->curw == wl) {
- resize = 1;
- break;
- }
- }
- if (!attached)
- resize = 1;
TAILQ_FOREACH(wp, &w->panes, entry) {
if (wp->fd != -1) {
if (focus)
- server_client_check_focus(wp);
- if (resize)
- server_client_check_resize(wp);
+ server_client_check_pane_focus(wp);
+ server_client_check_pane_resize(wp);
}
wp->flags &= ~PANE_REDRAW;
}
@@ -1389,6 +1373,26 @@ server_client_loop(void)
}
}
+/* Check if window needs to be resized. */
+static void
+server_client_check_window_resize(struct window *w)
+{
+ struct winlink *wl;
+
+ if (~w->flags & WINDOW_RESIZE)
+ return;
+
+ TAILQ_FOREACH(wl, &w->winlinks, wentry) {
+ if (wl->session->attached != 0 && wl->session->curw == wl)
+ break;
+ }
+ if (wl == NULL)
+ return;
+
+ log_debug("%s: resizing window @%u", __func__, w->id);
+ resize_window(w, w->new_sx, w->new_sy, w->new_xpixel, w->new_ypixel);
+}
+
/* Check if we need to force a resize. */
static int
server_client_resize_force(struct window_pane *wp)
@@ -1470,7 +1474,7 @@ server_client_resize_event(__unused int fd, __unused short events, void *data)
/* Check if pane should be resized. */
static void
-server_client_check_resize(struct window_pane *wp)
+server_client_check_pane_resize(struct window_pane *wp)
{
if (~wp->flags & PANE_RESIZE)
return;
@@ -1488,7 +1492,7 @@ server_client_check_resize(struct window_pane *wp)
/* Check whether pane should be focused. */
static void
-server_client_check_focus(struct window_pane *wp)
+server_client_check_pane_focus(struct window_pane *wp)
{
struct client *c;
int push;
diff --git a/tmux.h b/tmux.h
index 65164ccc..a9786990 100644
--- a/tmux.h
+++ b/tmux.h
@@ -1012,12 +1012,18 @@ struct window {
u_int xpixel;
u_int ypixel;
+ u_int new_sx;
+ u_int new_sy;
+ u_int new_xpixel;
+ u_int new_ypixel;
+
int flags;
#define WINDOW_BELL 0x1
#define WINDOW_ACTIVITY 0x2
#define WINDOW_SILENCE 0x4
#define WINDOW_ZOOMED 0x8
#define WINDOW_WASZOOMED 0x10
+#define WINDOW_RESIZE 0x20
#define WINDOW_ALERTFLAGS (WINDOW_BELL|WINDOW_ACTIVITY|WINDOW_SILENCE)
int alerts_queued;
diff --git a/window.c b/window.c
index 7cb098dd..b35ab8ab 100644
--- a/window.c
+++ b/window.c
@@ -438,13 +438,15 @@ window_pane_send_resize(struct window_pane *wp, int yadjust)
{
struct window *w = wp->window;
struct winsize ws;
+ u_int sy = wp->sy + yadjust;
if (wp->fd == -1)
return;
+ log_debug("%s: %%%u resize to %u,%u", __func__, wp->id, wp->sx, sy);
memset(&ws, 0, sizeof ws);
ws.ws_col = wp->sx;
- ws.ws_row = wp->sy + yadjust;
+ ws.ws_row = sy;
ws.ws_xpixel = w->xpixel * ws.ws_col;
ws.ws_ypixel = w->ypixel * ws.ws_row;
if (ioctl(wp->fd, TIOCSWINSZ, &ws) == -1)
@@ -1001,7 +1003,6 @@ window_pane_resize(struct window_pane *wp, u_int sx, u_int sy)
wme = TAILQ_FIRST(&wp->modes);
if (wme != NULL && wme->mode->resize != NULL)
wme->mode->resize(wme, sx, sy);
-
wp->flags |= (PANE_RESIZE|PANE_RESIZED);
}