Skip to content

Commit c07d2d9

Browse files
author
nicm
committed
swap-pane command.
1 parent ca3d714 commit c07d2d9

8 files changed

+300
-13
lines changed

GNUmakefile

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# $Id: GNUmakefile,v 1.79 2009-04-01 18:21:22 nicm Exp $
1+
# $Id: GNUmakefile,v 1.80 2009-04-02 23:28:15 nicm Exp $
22

33
.PHONY: clean
44

@@ -37,7 +37,7 @@ SRCS= tmux.c server.c server-msg.c server-fn.c buffer.c buffer-poll.c status.c \
3737
cmd-resize-pane-up.c cmd-resize-pane-down.c cmd-kill-pane.c \
3838
cmd-up-pane.c cmd-down-pane.c cmd-choose-window.c cmd-choose-session.c \
3939
cmd-suspend-client.c cmd-find-window.c cmd-load-buffer.c \
40-
cmd-copy-buffer.c cmd-break-pane.c cmd-next-layout.c \
40+
cmd-copy-buffer.c cmd-break-pane.c cmd-swap-pane.c cmd-next-layout.c \
4141
window-clock.c window-scroll.c window-more.c window-copy.c \
4242
window-choose.c \
4343
options.c options-cmd.c paste.c colour.c utf8.c clock.c \

Makefile

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# $Id: Makefile,v 1.118 2009-04-02 22:12:28 nicm Exp $
1+
# $Id: Makefile,v 1.119 2009-04-02 23:28:16 nicm Exp $
22

33
.SUFFIXES: .c .o .y .h
44
.PHONY: clean update-index.html upload-index.html
@@ -40,7 +40,7 @@ SRCS= tmux.c server.c server-msg.c server-fn.c buffer.c buffer-poll.c status.c \
4040
cmd-resize-pane-up.c cmd-resize-pane-down.c cmd-kill-pane.c \
4141
cmd-up-pane.c cmd-down-pane.c cmd-choose-window.c cmd-choose-session.c \
4242
cmd-suspend-client.c cmd-find-window.c cmd-load-buffer.c \
43-
cmd-copy-buffer.c cmd-break-pane.c cmd-next-layout.c \
43+
cmd-copy-buffer.c cmd-break-pane.c cmd-swap-pane.c cmd-next-layout.c \
4444
window-clock.c window-scroll.c window-more.c window-copy.c \
4545
window-choose.c \
4646
options.c options-cmd.c paste.c colour.c utf8.c clock.c \

TODO

+2-1
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@
8585
- test bug sshing from freebsd console
8686
- layout/split stuff:
8787
horiz split command, and similar resizing commands as for vert split
88-
swap-pane command
88+
rotate-window (-pane?) to rotate panes so first becomes last
8989
display the layout in a readable format somewhere
9090
previous-layout command
9191
select-layout command
@@ -97,6 +97,7 @@
9797
speed improvements?
9898
hardcoded 81 for left-vertical is nasty
9999
- document new layout stuff: next-layout
100+
- document swap-pane
100101
- document repeat behaviour and -r on bind-key
101102
- document status-keys
102103
- document break-pane

cmd-server-info.c

+4-4
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/* $Id: cmd-server-info.c,v 1.13 2009-04-01 18:21:28 nicm Exp $ */
1+
/* $Id: cmd-server-info.c,v 1.14 2009-04-02 23:28:16 nicm Exp $ */
22

33
/*
44
* Copyright (c) 2008 Nicholas Marriott <[email protected]>
@@ -133,9 +133,9 @@ cmd_server_info_exec(unused struct cmd *self, struct cmd_ctx *ctx)
133133
sizeof (**gd->udata);
134134
}
135135
}
136-
ctx->print(ctx, "%6u: %s %lu %d %u/%u, %zu "
137-
"bytes; UTF-8 %u/%u, %zu bytes", j, wp->tty,
138-
(u_long) wp->pid, wp->fd, lines,
136+
ctx->print(ctx, "%6u: %p %s %lu %d %u/%u, %zu "
137+
"bytes; UTF-8 %u/%u, %zu bytes", j, wp,
138+
wp->tty, (u_long) wp->pid, wp->fd, lines,
139139
gd->hsize + gd->sy, size, ulines,
140140
gd->hsize + gd->sy, usize);
141141
j++;

cmd-swap-pane.c

+282
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,282 @@
1+
/* $Id: cmd-swap-pane.c,v 1.1 2009-04-02 23:28:16 nicm Exp $ */
2+
3+
/*
4+
* Copyright (c) 2007 Nicholas Marriott <[email protected]>
5+
*
6+
* Permission to use, copy, modify, and distribute this software for any
7+
* purpose with or without fee is hereby granted, provided that the above
8+
* copyright notice and this permission notice appear in all copies.
9+
*
10+
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11+
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12+
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13+
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14+
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
15+
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
16+
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17+
*/
18+
19+
#include <sys/types.h>
20+
21+
#include <stdlib.h>
22+
23+
#include "tmux.h"
24+
25+
/*
26+
* Swap two panes.
27+
*/
28+
29+
int cmd_swap_pane_parse(struct cmd *, int, char **, char **);
30+
int cmd_swap_pane_exec(struct cmd *, struct cmd_ctx *);
31+
void cmd_swap_pane_send(struct cmd *, struct buffer *);
32+
void cmd_swap_pane_recv(struct cmd *, struct buffer *);
33+
void cmd_swap_pane_free(struct cmd *);
34+
void cmd_swap_pane_init(struct cmd *, int);
35+
size_t cmd_swap_pane_print(struct cmd *, char *, size_t);
36+
37+
struct cmd_swap_pane_data {
38+
char *target;
39+
int src;
40+
int dst;
41+
int flag_detached;
42+
int flag_next;
43+
int flag_previous;
44+
};
45+
46+
const struct cmd_entry cmd_swap_pane_entry = {
47+
"swap-pane", "swapp",
48+
"[-dn] [-t target-window] [-p src-index] [-q dst-index]",
49+
0,
50+
cmd_swap_pane_init,
51+
cmd_swap_pane_parse,
52+
cmd_swap_pane_exec,
53+
cmd_swap_pane_send,
54+
cmd_swap_pane_recv,
55+
cmd_swap_pane_free,
56+
cmd_swap_pane_print
57+
};
58+
59+
void
60+
cmd_swap_pane_init(struct cmd *self, int key)
61+
{
62+
struct cmd_swap_pane_data *data;
63+
64+
self->data = data = xmalloc(sizeof *data);
65+
data->target = NULL;
66+
data->src = -1;
67+
data->dst = -1;
68+
data->flag_detached = 0;
69+
data->flag_next = 0;
70+
data->flag_previous = 0;
71+
72+
switch (key) {
73+
case '}':
74+
data->flag_next = 1;
75+
break;
76+
case '{':
77+
data->flag_previous = 1;
78+
break;
79+
}
80+
}
81+
82+
int
83+
cmd_swap_pane_parse(struct cmd *self, int argc, char **argv, char **cause)
84+
{
85+
struct cmd_swap_pane_data *data;
86+
int opt, n;
87+
const char *errstr;
88+
89+
self->entry->init(self, 0);
90+
data = self->data;
91+
92+
while ((opt = getopt(argc, argv, "dt:np:q:r")) != -1) {
93+
switch (opt) {
94+
case 'd':
95+
data->flag_detached = 1;
96+
break;
97+
case 'n':
98+
data->flag_next = 1;
99+
data->flag_previous = 0;
100+
data->dst = -1;
101+
break;
102+
case 't':
103+
if (data->target == NULL)
104+
data->target = xstrdup(optarg);
105+
break;
106+
case 'p':
107+
if (data->src == -1) {
108+
n = strtonum(optarg, 0, INT_MAX, &errstr);
109+
if (errstr != NULL) {
110+
xasprintf(cause, "src %s", errstr);
111+
goto error;
112+
}
113+
data->src = n;
114+
}
115+
break;
116+
case 'q':
117+
if (data->dst == -1) {
118+
n = strtonum(optarg, 0, INT_MAX, &errstr);
119+
if (errstr != NULL) {
120+
xasprintf(cause, "dst %s", errstr);
121+
goto error;
122+
}
123+
data->dst = n;
124+
}
125+
data->flag_next = 0;
126+
data->flag_previous = 0;
127+
break;
128+
case 'r':
129+
data->flag_next = 0;
130+
data->flag_previous = 1;
131+
data->dst = -1;
132+
break;
133+
134+
default:
135+
goto usage;
136+
}
137+
}
138+
argc -= optind;
139+
argv += optind;
140+
if (argc != 0)
141+
goto usage;
142+
143+
return (0);
144+
145+
usage:
146+
xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage);
147+
148+
error:
149+
self->entry->free(self);
150+
return (-1);
151+
}
152+
153+
int
154+
cmd_swap_pane_exec(struct cmd *self, struct cmd_ctx *ctx)
155+
{
156+
struct cmd_swap_pane_data *data = self->data;
157+
struct winlink *wl;
158+
struct window *w;
159+
struct window_pane *tmp_wp, *src_wp, *dst_wp;
160+
u_int xx, yy;
161+
162+
if (data == NULL)
163+
return (0);
164+
165+
if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL)
166+
return (-1);
167+
w = wl->window;
168+
169+
if (data->src == -1)
170+
src_wp = w->active;
171+
else {
172+
src_wp = window_pane_at_index(w, data->src);
173+
if (src_wp == NULL) {
174+
ctx->error(ctx, "no pane: %d", data->src);
175+
return (-1);
176+
}
177+
}
178+
if (data->dst == -1)
179+
dst_wp = w->active;
180+
else {
181+
dst_wp = window_pane_at_index(w, data->dst);
182+
if (dst_wp == NULL) {
183+
ctx->error(ctx, "no pane: %d", data->dst);
184+
return (-1);
185+
}
186+
}
187+
188+
if (data->dst == -1 && data->flag_next) {
189+
if ((dst_wp = TAILQ_NEXT(src_wp, entry)) == NULL)
190+
dst_wp = TAILQ_FIRST(&w->panes);
191+
}
192+
if (data->dst == -1 && data->flag_previous) {
193+
if ((dst_wp = TAILQ_PREV(src_wp, window_panes, entry)) == NULL)
194+
dst_wp = TAILQ_LAST(&w->panes, window_panes);
195+
}
196+
197+
if (src_wp == dst_wp)
198+
return (0);
199+
200+
tmp_wp = TAILQ_PREV(dst_wp, window_panes, entry);
201+
TAILQ_REMOVE(&w->panes, dst_wp, entry);
202+
TAILQ_REPLACE(&w->panes, src_wp, dst_wp, entry);
203+
if (tmp_wp == src_wp)
204+
tmp_wp = dst_wp;
205+
if (tmp_wp == NULL)
206+
TAILQ_INSERT_HEAD(&w->panes, src_wp, entry);
207+
else
208+
TAILQ_INSERT_AFTER(&w->panes, tmp_wp, src_wp, entry);
209+
210+
xx = src_wp->xoff;
211+
yy = src_wp->yoff;
212+
src_wp->xoff = dst_wp->xoff;
213+
src_wp->yoff = dst_wp->yoff;
214+
dst_wp->xoff = xx;
215+
dst_wp->yoff = yy;
216+
217+
xx = src_wp->sx;
218+
yy = src_wp->sy;
219+
window_pane_resize(src_wp, dst_wp->sx, dst_wp->sy);
220+
window_pane_resize(dst_wp, xx, yy);
221+
222+
if (!data->flag_detached) {
223+
window_set_active_pane(w, dst_wp);
224+
layout_refresh(w, 0);
225+
}
226+
227+
return (0);
228+
}
229+
230+
void
231+
cmd_swap_pane_send(struct cmd *self, struct buffer *b)
232+
{
233+
struct cmd_swap_pane_data *data = self->data;
234+
235+
buffer_write(b, data, sizeof *data);
236+
cmd_send_string(b, data->target);
237+
}
238+
239+
void
240+
cmd_swap_pane_recv(struct cmd *self, struct buffer *b)
241+
{
242+
struct cmd_swap_pane_data *data;
243+
244+
self->data = data = xmalloc(sizeof *data);
245+
buffer_read(b, data, sizeof *data);
246+
data->target = cmd_recv_string(b);
247+
}
248+
249+
void
250+
cmd_swap_pane_free(struct cmd *self)
251+
{
252+
struct cmd_swap_pane_data *data = self->data;
253+
254+
if (data->target != NULL)
255+
xfree(data->target);
256+
xfree(data);
257+
}
258+
259+
size_t
260+
cmd_swap_pane_print(struct cmd *self, char *buf, size_t len)
261+
{
262+
struct cmd_swap_pane_data *data = self->data;
263+
size_t off = 0;
264+
265+
off += xsnprintf(buf, len, "%s", self->entry->name);
266+
if (data == NULL)
267+
return (off);
268+
if (off < len && (data->flag_next || data->flag_detached)) {
269+
off += xsnprintf(buf + off, len - off, " -");
270+
if (off < len && data->flag_next)
271+
off += xsnprintf(buf + off, len - off, "d");
272+
if (off < len && data->flag_detached)
273+
off += xsnprintf(buf + off, len - off, "n");
274+
}
275+
if (off < len && data->target != NULL)
276+
off += cmd_prarg(buf + off, len - off, " -t ", data->target);
277+
if (off < len && data->src != -1)
278+
off += xsnprintf(buf + off, len - off, " -p %d", data->src);
279+
if (off < len && data->dst != -1)
280+
off += xsnprintf(buf + off, len - off, " -q %d", data->dst);
281+
return (off);
282+
}

cmd.c

+2-1
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/* $Id: cmd.c,v 1.87 2009-04-01 18:21:29 nicm Exp $ */
1+
/* $Id: cmd.c,v 1.88 2009-04-02 23:28:16 nicm Exp $ */
22

33
/*
44
* Copyright (c) 2007 Nicholas Marriott <[email protected]>
@@ -86,6 +86,7 @@ const struct cmd_entry *cmd_table[] = {
8686
&cmd_split_window_entry,
8787
&cmd_start_server_entry,
8888
&cmd_suspend_client_entry,
89+
&cmd_swap_pane_entry,
8990
&cmd_swap_window_entry,
9091
&cmd_switch_client_entry,
9192
&cmd_unbind_key_entry,

key-bindings.c

+4-2
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/* $Id: key-bindings.c,v 1.64 2009-04-01 18:21:30 nicm Exp $ */
1+
/* $Id: key-bindings.c,v 1.65 2009-04-02 23:28:16 nicm Exp $ */
22

33
/*
44
* Copyright (c) 2007 Nicholas Marriott <[email protected]>
@@ -102,6 +102,7 @@ key_bindings_init(void)
102102
{ '?', 0, &cmd_list_keys_entry },
103103
{ '[', 0, &cmd_copy_mode_entry },
104104
{ '\'', 0, &cmd_select_prompt_entry },
105+
{ '\032', /* C-z */ 0, &cmd_suspend_client_entry },
105106
{ ']', 0, &cmd_paste_buffer_entry },
106107
{ 'c', 0, &cmd_new_window_entry },
107108
{ 'd', 0, &cmd_detach_client_entry },
@@ -115,7 +116,8 @@ key_bindings_init(void)
115116
{ 't', 0, &cmd_clock_mode_entry },
116117
{ 'w', 0, &cmd_choose_window_entry },
117118
{ 'x', 0, &cmd_kill_pane_entry, },
118-
{ '\032', 0, &cmd_suspend_client_entry },
119+
{ '{', 0, &cmd_swap_pane_entry },
120+
{ '}', 0, &cmd_swap_pane_entry },
119121
{ META, 0, &cmd_send_prefix_entry },
120122
{ KEYC_PPAGE, 0, &cmd_scroll_mode_entry },
121123
{ KEYC_ADDESC('n'), 0, &cmd_next_window_entry },

0 commit comments

Comments
 (0)