summaryrefslogtreecommitdiff
path: root/usr.bin/tmux
diff options
context:
space:
mode:
authorNicholas Marriott <nicm@cvs.openbsd.org>2009-12-08 07:49:32 +0000
committerNicholas Marriott <nicm@cvs.openbsd.org>2009-12-08 07:49:32 +0000
commit2369386e1772765350c8c7f0d241c6ca180df375 (patch)
tree80017d99b5ec107ea49dda2b708632368f5b81d7 /usr.bin/tmux
parentfd9da06a12f03edbaba0a1705fb1251094b452dc (diff)
Permit panes to be referred to as "top", "bottom", "top-left" etc, if the right
pane can be identified.
Diffstat (limited to 'usr.bin/tmux')
-rw-r--r--usr.bin/tmux/Makefile4
-rw-r--r--usr.bin/tmux/cmd.c43
-rw-r--r--usr.bin/tmux/layout-string.c167
-rw-r--r--usr.bin/tmux/tmux.114
-rw-r--r--usr.bin/tmux/tmux.h5
5 files changed, 213 insertions, 20 deletions
diff --git a/usr.bin/tmux/Makefile b/usr.bin/tmux/Makefile
index 6c73736cdfe..d787518121f 100644
--- a/usr.bin/tmux/Makefile
+++ b/usr.bin/tmux/Makefile
@@ -1,4 +1,4 @@
-# $OpenBSD: Makefile,v 1.32 2009/12/03 17:44:02 nicm Exp $
+# $OpenBSD: Makefile,v 1.33 2009/12/08 07:49:31 nicm Exp $
PROG= tmux
SRCS= attributes.c cfg.c client.c clock.c \
@@ -32,7 +32,7 @@ SRCS= attributes.c cfg.c client.c clock.c \
cmd-pipe-pane.c cmd-capture-pane.c cmd.c \
colour.c environ.c grid-view.c grid-utf8.c grid.c input-keys.c \
imsg.c imsg-buffer.c input.c key-bindings.c key-string.c \
- layout-set.c layout.c log.c job.c \
+ layout-set.c layout-string.c layout.c log.c job.c \
mode-key.c names.c options.c paste.c procname.c \
resize.c screen-redraw.c screen-write.c screen.c session.c status.c \
server-fn.c server.c server-client.c server-window.c \
diff --git a/usr.bin/tmux/cmd.c b/usr.bin/tmux/cmd.c
index ec9a405f1c6..007ae1f3c30 100644
--- a/usr.bin/tmux/cmd.c
+++ b/usr.bin/tmux/cmd.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: cmd.c,v 1.35 2009/12/03 22:50:10 nicm Exp $ */
+/* $OpenBSD: cmd.c,v 1.36 2009/12/08 07:49:31 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -856,12 +856,12 @@ struct winlink *
cmd_find_pane(struct cmd_ctx *ctx,
const char *arg, struct session **sp, struct window_pane **wpp)
{
- struct session *s;
- struct winlink *wl;
- const char *period;
- char *winptr, *paneptr;
- const char *errstr;
- u_int idx;
+ struct session *s;
+ struct winlink *wl;
+ struct layout_cell *lc;
+ const char *period, *errstr;
+ char *winptr, *paneptr;
+ u_int idx;
/* Get the current session. */
if ((s = cmd_current_session(ctx)) == NULL) {
@@ -895,20 +895,27 @@ cmd_find_pane(struct cmd_ctx *ctx,
*wpp = wl->window->active;
else {
idx = strtonum(paneptr, 0, INT_MAX, &errstr);
- if (errstr != NULL) {
- ctx->error(ctx, "pane %s: %s", errstr, paneptr);
- goto error;
- }
+ if (errstr != NULL)
+ goto lookup_string;
*wpp = window_pane_at_index(wl->window, idx);
- if (*wpp == NULL) {
- ctx->error(ctx, "no such pane: %u", idx);
- goto error;
- }
+ if (*wpp == NULL)
+ goto lookup_string;
}
xfree(winptr);
return (wl);
+lookup_string:
+ /* Try pane string description. */
+ if ((lc = layout_find_string(s->curw->window, paneptr)) == NULL) {
+ ctx->error(ctx, "can't find pane: %s", paneptr);
+ goto error;
+ }
+ *wpp = lc->wp;
+
+ xfree(winptr);
+ return (s->curw);
+
no_period:
/* Try as a pane number alone. */
idx = strtonum(arg, 0, INT_MAX, &errstr);
@@ -922,6 +929,12 @@ no_period:
return (s->curw);
lookup_window:
+ /* Try pane string description. */
+ if ((lc = layout_find_string(s->curw->window, arg)) != NULL) {
+ *wpp = lc->wp;
+ return (s->curw);
+ }
+
/* Try as a window and use the active pane. */
if ((wl = cmd_find_window(ctx, arg, sp)) != NULL)
*wpp = wl->window->active;
diff --git a/usr.bin/tmux/layout-string.c b/usr.bin/tmux/layout-string.c
new file mode 100644
index 00000000000..4392e5cecc7
--- /dev/null
+++ b/usr.bin/tmux/layout-string.c
@@ -0,0 +1,167 @@
+/* $Id: layout-string.c,v 1.1 2009/12/08 07:49:31 nicm Exp $ */
+
+/*
+ * Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
+ * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
+ * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <sys/types.h>
+
+#include <stdlib.h>
+#include <string.h>
+
+#include "tmux.h"
+
+/*
+ * Figure out the pane position based on a description. Fairly simple right
+ * now, just understands a set of strings: left, right, top, bottom, top-left
+ * top-right, bottom-left, bottom-right.
+ */
+
+struct layout_cell *layout_find_top(struct layout_cell *);
+struct layout_cell *layout_find_bottom(struct layout_cell *);
+struct layout_cell *layout_find_left(struct layout_cell *);
+struct layout_cell *layout_find_right(struct layout_cell *);
+struct layout_cell *layout_find_topleft(struct layout_cell *);
+struct layout_cell *layout_find_topright(struct layout_cell *);
+struct layout_cell *layout_find_bottomleft(struct layout_cell *);
+struct layout_cell *layout_find_bottomright(struct layout_cell *);
+
+/* Find the cell; returns NULL if string not understood. */
+struct layout_cell *
+layout_find_string(struct window *w, const char *s)
+{
+ struct layout_cell *lc = w->layout_root;
+
+ if (strcasecmp(s, "top") == 0)
+ lc = layout_find_top(lc);
+ else if (strcasecmp(s, "bottom") == 0)
+ lc = layout_find_bottom(lc);
+ else if (strcasecmp(s, "left") == 0)
+ lc = layout_find_left(lc);
+ else if (strcasecmp(s, "right") == 0)
+ lc = layout_find_right(lc);
+ else if (strcasecmp(s, "top-left") == 0)
+ lc = layout_find_topleft(lc);
+ else if (strcasecmp(s, "top-right") == 0)
+ lc = layout_find_topright(lc);
+ else if (strcasecmp(s, "bottom-left") == 0)
+ lc = layout_find_bottomleft(lc);
+ else if (strcasecmp(s, "bottom-right") == 0)
+ lc = layout_find_bottomright(lc);
+
+ if (lc == NULL || lc->type != LAYOUT_WINDOWPANE)
+ return (NULL);
+ return (lc);
+}
+
+/*
+ * Find the top cell. Because splits in the same direction are stored as a
+ * list, this is just the first in the list. Return NULL if no topmost cell.
+ * For an unnested cell (not split), the top cell is always itself.
+ */
+struct layout_cell *
+layout_find_top(struct layout_cell *lc)
+{
+ if (lc->type == LAYOUT_WINDOWPANE)
+ return (lc);
+ else if (lc->type == LAYOUT_TOPBOTTOM)
+ return (TAILQ_FIRST(&lc->cells));
+ return (NULL);
+}
+
+/*
+ * Find the bottom cell. Similarly to the top cell, this is just the last in
+ * the list.
+ */
+struct layout_cell *
+layout_find_bottom(struct layout_cell *lc)
+{
+ if (lc->type == LAYOUT_WINDOWPANE)
+ return (lc);
+ else if (lc->type == LAYOUT_TOPBOTTOM)
+ return (TAILQ_LAST(&lc->cells, layout_cells));
+ return (NULL);
+}
+
+/* Find the left cell. */
+struct layout_cell *
+layout_find_left(struct layout_cell *lc)
+{
+ if (lc->type == LAYOUT_WINDOWPANE)
+ return (lc);
+ else if (lc->type == LAYOUT_LEFTRIGHT)
+ return (TAILQ_FIRST(&lc->cells));
+ return (NULL);
+}
+
+/* Find the right cell. */
+struct layout_cell *
+layout_find_right(struct layout_cell *lc)
+{
+ if (lc->type == LAYOUT_WINDOWPANE)
+ return (lc);
+ else if (lc->type == LAYOUT_LEFTRIGHT)
+ return (TAILQ_LAST(&lc->cells, layout_cells));
+ return (NULL);
+}
+
+/*
+ * Find the top-left cell. This means recursing until there are no more moves
+ * to be made.
+ */
+struct layout_cell *
+layout_find_topleft(struct layout_cell *lc)
+{
+ if (lc->type == LAYOUT_WINDOWPANE)
+ return (lc);
+ lc = TAILQ_FIRST(&lc->cells);
+ return (layout_find_topleft(lc));
+}
+
+/* Find the top-right cell. */
+struct layout_cell *
+layout_find_topright(struct layout_cell *lc)
+{
+ if (lc->type == LAYOUT_WINDOWPANE)
+ return (lc);
+ if (lc->type == LAYOUT_LEFTRIGHT)
+ lc = TAILQ_LAST(&lc->cells, layout_cells);
+ else
+ lc = TAILQ_FIRST(&lc->cells);
+ return (layout_find_topright(lc));
+}
+
+/* Find the bottom-left cell. */
+struct layout_cell *
+layout_find_bottomleft(struct layout_cell *lc)
+{
+ if (lc->type == LAYOUT_WINDOWPANE)
+ return (lc);
+ if (lc->type == LAYOUT_LEFTRIGHT)
+ lc = TAILQ_FIRST(&lc->cells);
+ else
+ lc = TAILQ_LAST(&lc->cells, layout_cells);
+ return (layout_find_bottomleft(lc));
+}
+
+/* Find the bottom-right cell. */
+struct layout_cell *
+layout_find_bottomright(struct layout_cell *lc)
+{
+ if (lc->type == LAYOUT_WINDOWPANE)
+ return (lc);
+ lc = TAILQ_LAST(&lc->cells, layout_cells);
+ return (layout_find_bottomright(lc));
+}
diff --git a/usr.bin/tmux/tmux.1 b/usr.bin/tmux/tmux.1
index 66c2e3c7b3b..41956c0890a 100644
--- a/usr.bin/tmux/tmux.1
+++ b/usr.bin/tmux/tmux.1
@@ -1,4 +1,4 @@
-.\" $OpenBSD: tmux.1,v 1.131 2009/12/03 22:54:34 nicm Exp $
+.\" $OpenBSD: tmux.1,v 1.132 2009/12/08 07:49:31 nicm Exp $
.\"
.\" Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
.\"
@@ -14,7 +14,7 @@
.\" IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
.\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
.\"
-.Dd $Mdocdate: December 3 2009 $
+.Dd $Mdocdate: December 8 2009 $
.Dt TMUX 1
.Os
.Sh NAME
@@ -323,6 +323,16 @@ If neither a colon nor period appears,
first attempts to use the argument as a pane index; if that fails, it is looked
up as for
.Ar target-window .
+One of the strings
+.Em top ,
+.Em bottom ,
+.Em left ,
+.Em right ,
+.Em top-left ,
+.Em top-right ,
+.Em bottom-left or
+.Em bottom-right
+may be used instead of a pane index.
.Pp
Multiple commands may be specified together as part of a
.Em command sequence .
diff --git a/usr.bin/tmux/tmux.h b/usr.bin/tmux/tmux.h
index 2fe2a2c28c5..b6594da58eb 100644
--- a/usr.bin/tmux/tmux.h
+++ b/usr.bin/tmux/tmux.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: tmux.h,v 1.192 2009/12/03 22:50:10 nicm Exp $ */
+/* $OpenBSD: tmux.h,v 1.193 2009/12/08 07:49:31 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -1844,6 +1844,9 @@ u_int layout_set_next(struct window *);
u_int layout_set_previous(struct window *);
void layout_set_active_changed(struct window *);
+/* layout-string.c */
+struct layout_cell *layout_find_string(struct window *, const char *);
+
/* window-clock.c */
extern const struct window_mode window_clock_mode;