summaryrefslogtreecommitdiff
path: root/usr.bin/tmux
diff options
context:
space:
mode:
authorNicholas Marriott <nicm@cvs.openbsd.org>2009-08-08 15:57:50 +0000
committerNicholas Marriott <nicm@cvs.openbsd.org>2009-08-08 15:57:50 +0000
commit5fa0e8d702f63c630900111050a89c1e435a230a (patch)
treec2132663a47e4b498cab0d4be0eeec5589bbb4d7 /usr.bin/tmux
parent2d58dd87326d6060063b3fd69af5111759024a44 (diff)
Add a flags member to the grid_line struct and use it to differentiate lines
wrapped at the screen edge from those terminated by a newline. Then use this when copying to combine wrapped lines together into one.
Diffstat (limited to 'usr.bin/tmux')
-rw-r--r--usr.bin/tmux/input.c10
-rw-r--r--usr.bin/tmux/screen-write.c19
-rw-r--r--usr.bin/tmux/tmux.h9
-rw-r--r--usr.bin/tmux/window-copy.c38
4 files changed, 51 insertions, 25 deletions
diff --git a/usr.bin/tmux/input.c b/usr.bin/tmux/input.c
index 04defa7af95..16a6d9ee020 100644
--- a/usr.bin/tmux/input.c
+++ b/usr.bin/tmux/input.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: input.c,v 1.11 2009/08/07 00:12:13 nicm Exp $ */
+/* $OpenBSD: input.c,v 1.12 2009/08/08 15:57:49 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -635,7 +635,7 @@ input_handle_c0_control(u_char ch, struct input_ctx *ictx)
case '\0': /* NUL */
break;
case '\n': /* LF */
- screen_write_linefeed(&ictx->ctx);
+ screen_write_linefeed(&ictx->ctx, 0);
break;
case '\r': /* CR */
screen_write_carriagereturn(&ictx->ctx);
@@ -659,7 +659,7 @@ input_handle_c0_control(u_char ch, struct input_ctx *ictx)
} while (s->cx < screen_size_x(s) - 1);
break;
case '\013': /* VT */
- screen_write_linefeed(&ictx->ctx);
+ screen_write_linefeed(&ictx->ctx, 0);
break;
case '\016': /* SO */
ictx->cell.attr |= GRID_ATTR_CHARSET;
@@ -682,11 +682,11 @@ input_handle_c1_control(u_char ch, struct input_ctx *ictx)
switch (ch) {
case 'D': /* IND */
- screen_write_linefeed(&ictx->ctx);
+ screen_write_linefeed(&ictx->ctx, 0);
break;
case 'E': /* NEL */
screen_write_carriagereturn(&ictx->ctx);
- screen_write_linefeed(&ictx->ctx);
+ screen_write_linefeed(&ictx->ctx, 0);
break;
case 'H': /* HTS */
if (s->cx < screen_size_x(s))
diff --git a/usr.bin/tmux/screen-write.c b/usr.bin/tmux/screen-write.c
index fcf2c8170c1..50023b06dc0 100644
--- a/usr.bin/tmux/screen-write.c
+++ b/usr.bin/tmux/screen-write.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: screen-write.c,v 1.19 2009/07/30 20:41:48 nicm Exp $ */
+/* $OpenBSD: screen-write.c,v 1.20 2009/08/08 15:57:49 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -610,13 +610,20 @@ screen_write_mousemode(struct screen_write_ctx *ctx, int state)
/* Line feed (down with scroll). */
void
-screen_write_linefeed(struct screen_write_ctx *ctx)
+screen_write_linefeed(struct screen_write_ctx *ctx, int wrapped)
{
- struct screen *s = ctx->s;
- struct tty_ctx ttyctx;
+ struct screen *s = ctx->s;
+ struct grid_line *gl;
+ struct tty_ctx ttyctx;
screen_write_initctx(ctx, &ttyctx);
+ gl = &s->grid->linedata[s->grid->hsize + s->cy];
+ if (wrapped)
+ gl->flags |= GRID_LINE_WRAPPED;
+ else
+ gl->flags &= ~GRID_LINE_WRAPPED;
+
if (s->cy == s->rlower)
grid_view_scroll_region_up(s->grid, s->rupper, s->rlower);
else if (s->cy < screen_size_y(s) - 1)
@@ -782,10 +789,10 @@ screen_write_cell(
insert = 1;
}
- /* Check this will fit on the current line; scroll if not. */
+ /* Check this will fit on the current line and wrap if not. */
if (s->cx > screen_size_x(s) - width) {
screen_write_carriagereturn(ctx);
- screen_write_linefeed(ctx);
+ screen_write_linefeed(ctx, 1);
}
/* Sanity checks. */
diff --git a/usr.bin/tmux/tmux.h b/usr.bin/tmux/tmux.h
index 468cfef843a..622b537f0f4 100644
--- a/usr.bin/tmux/tmux.h
+++ b/usr.bin/tmux/tmux.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: tmux.h,v 1.71 2009/08/08 13:29:27 nicm Exp $ */
+/* $OpenBSD: tmux.h,v 1.72 2009/08/08 15:57:49 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -484,6 +484,9 @@ struct mode_key_table {
#define GRID_FLAG_PADDING 0x4
#define GRID_FLAG_UTF8 0x8
+/* Grid line flags. */
+#define GRID_LINE_WRAPPED 0x1
+
/* Grid cell data. */
struct grid_cell {
u_char attr;
@@ -507,6 +510,8 @@ struct grid_line {
u_int utf8size;
struct grid_utf8 *utf8data;
+
+ int flags;
} __packed;
/* Entire grid of cells. */
@@ -1504,7 +1509,7 @@ void screen_write_reverseindex(struct screen_write_ctx *);
void screen_write_scrollregion(struct screen_write_ctx *, u_int, u_int);
void screen_write_insertmode(struct screen_write_ctx *, int);
void screen_write_mousemode(struct screen_write_ctx *, int);
-void screen_write_linefeed(struct screen_write_ctx *);
+void screen_write_linefeed(struct screen_write_ctx *, int);
void screen_write_carriagereturn(struct screen_write_ctx *);
void screen_write_kcursormode(struct screen_write_ctx *, int);
void screen_write_kkeypadmode(struct screen_write_ctx *, int);
diff --git a/usr.bin/tmux/window-copy.c b/usr.bin/tmux/window-copy.c
index 35fae023161..4c6b3e6a839 100644
--- a/usr.bin/tmux/window-copy.c
+++ b/usr.bin/tmux/window-copy.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: window-copy.c,v 1.15 2009/08/08 13:29:27 nicm Exp $ */
+/* $OpenBSD: window-copy.c,v 1.16 2009/08/08 15:57:49 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -449,13 +449,11 @@ window_copy_copy_selection(struct window_pane *wp, struct client *c)
if (sy == ey)
window_copy_copy_line(wp, &buf, &off, sy, sx, ex);
else {
- xx = window_copy_find_length(wp, sy);
+ xx = screen_size_x(s);
window_copy_copy_line(wp, &buf, &off, sy, sx, xx);
if (ey - sy > 1) {
- for (i = sy + 1; i < ey; i++) {
- xx = window_copy_find_length(wp, i);
+ for (i = sy + 1; i < ey; i++)
window_copy_copy_line(wp, &buf, &off, i, 0, xx);
- }
}
window_copy_copy_line(wp, &buf, &off, ey, 0, ex);
}
@@ -473,14 +471,28 @@ void
window_copy_copy_line(struct window_pane *wp,
char **buf, size_t *off, u_int sy, u_int sx, u_int ex)
{
+ struct grid *gd = wp->base.grid;
const struct grid_cell *gc;
const struct grid_utf8 *gu;
- u_int i, j, xx;
+ struct grid_line *gl;
+ u_int i, j, xx, wrapped = 0;
if (sx > ex)
return;
- xx = window_copy_find_length(wp, sy);
+ /*
+ * Work out if the line was wrapped at the screen edge and all of it is
+ * on screen.
+ */
+ gl = &gd->linedata[sy];
+ if (gl->flags & GRID_LINE_WRAPPED && gl->cellsize <= gd->sx)
+ wrapped = 1;
+
+ /* If the line was wrapped, don't strip spaces (use the full length). */
+ if (wrapped)
+ xx = gl->cellsize;
+ else
+ xx = window_copy_find_length(wp, sy);
if (ex > xx)
ex = xx;
if (sx > xx)
@@ -488,14 +500,14 @@ window_copy_copy_line(struct window_pane *wp,
if (sx < ex) {
for (i = sx; i < ex; i++) {
- gc = grid_peek_cell(wp->base.grid, i, sy);
+ gc = grid_peek_cell(gd, i, sy);
if (gc->flags & GRID_FLAG_PADDING)
continue;
if (!(gc->flags & GRID_FLAG_UTF8)) {
*buf = xrealloc(*buf, 1, (*off) + 1);
(*buf)[(*off)++] = gc->data;
} else {
- gu = grid_peek_utf8(wp->base.grid, i, sy);
+ gu = grid_peek_utf8(gd, i, sy);
*buf = xrealloc(*buf, 1, (*off) + UTF8_SIZE);
for (j = 0; j < UTF8_SIZE; j++) {
if (gu->data[j] == 0xff)
@@ -506,9 +518,11 @@ window_copy_copy_line(struct window_pane *wp,
}
}
- *buf = xrealloc(*buf, 1, (*off) + 1);
- (*buf)[*off] = '\n';
- (*off)++;
+ /* Only add a newline if the line wasn't wrapped. */
+ if (!wrapped) {
+ *buf = xrealloc(*buf, 1, (*off) + 1);
+ (*buf)[(*off)++] = '\n';
+ }
}
int