diff --git a/CHANGES b/CHANGES index 9d64f62a2..592a42aef 100644 --- a/CHANGES +++ b/CHANGES @@ -1,7 +1,6 @@ CHANGES FROM 3.7c TO 3.8 -* Add copy-mode -c to start with the current cursor column as the preferred - column, rather than initially following line ends. +* Add copy-mode -c to disable end-of-line following during vertical movement. * Many improvements to floating panes: diff --git a/regress/copy-mode-entry-column.sh b/regress/copy-mode-entry-column.sh index 6e98ddfd9..16b2db113 100644 --- a/regress/copy-mode-entry-column.sh +++ b/regress/copy-mode-entry-column.sh @@ -179,6 +179,27 @@ for entry_line in 'prompt> ' ' '; do fi x cancel done + + # Returning to the entry mark must not reenable EOL following. + $TMUX copy-mode -c || fail "copy-mode -c failed" + x cursor-up + check_cursor 8,2 + x jump-to-mark + check_cursor 8,3 + $TMUX copy-mode || fail "second copy-mode failed" + x cursor-up + check_cursor 8,2 + x cancel + + # A new ordinary visit restores the default. Adding -c to an already + # active visit does not change its policy. + $TMUX copy-mode || fail "copy-mode failed" + $TMUX copy-mode -c || fail "second copy-mode -c failed" + x cursor-up + end=20 + [ "$mode" = emacs ] || end=19 + check_cursor "$end,2" + x cancel done done diff --git a/tmux.1 b/tmux.1 index d52002341..4cc2a6ac3 100644 --- a/tmux.1 +++ b/tmux.1 @@ -2616,9 +2616,9 @@ command is: Enter copy mode. .Pp .Fl c -initializes the preferred cursor column to the column at which copy mode is -entered, rather than initially following the end of each line. -Subsequent cursor movements use the normal copy mode behaviour. +disables end-of-line following during vertical movement for the duration of +copy mode. +Normal cursor limits and selection behaviour are unchanged. .Pp .Fl u enters copy mode and scrolls one page up and diff --git a/window-copy.c b/window-copy.c index ed1afb6c1..e915148c3 100644 --- a/window-copy.c +++ b/window-copy.c @@ -106,8 +106,6 @@ static int window_copy_search_down(struct window_mode_entry *, int); static void window_copy_goto_line(struct window_mode_entry *, const char *); static void window_copy_update_cursor(struct window_mode_entry *, u_int, u_int); -static void window_copy_update_preferred_column( - struct window_copy_mode_data *, u_int); static void window_copy_start_selection(struct window_mode_entry *); static int window_copy_mouse_in_selection(struct window_mode_entry *, u_int, u_int, int *, int *); @@ -332,6 +330,7 @@ struct window_copy_mode_data { u_int lastcx; /* position in last line w/ content */ u_int lastsx; /* size of last line w/ content */ + int columnflag; /* do not follow line ends */ u_int mx; /* mark position */ u_int my; @@ -616,11 +615,9 @@ window_copy_init(struct window_mode_entry *wme, window_copy_sync_snapshot(data, base->grid); data->cx = cx; - if (args_has(args, 'c')) { - /* Preserve the entry column on the first vertical move. */ + data->columnflag = args_has(args, 'c'); + if (data->columnflag) data->lastcx = cx; - data->lastsx = UINT_MAX; - } if (cy < screen_hsize(data->backing)) { data->cy = 0; data->oy = screen_hsize(data->backing) - cy; @@ -834,7 +831,10 @@ window_copy_scroll1(struct window_mode_entry *wme, struct window_pane *wp, oy = screen_hsize(data->backing) + data->cy - data->oy; ox = window_copy_find_length(wme, oy); - window_copy_update_preferred_column(data, ox); + if (data->cx != ox) { + data->lastcx = data->cx; + data->lastsx = ox; + } data->cx = data->lastcx; if (delta >= 0) { @@ -865,8 +865,8 @@ window_copy_scroll1(struct window_mode_entry *wme, struct window_pane *wp, if (data->screen.sel == NULL || !data->rectflag) { py = screen_hsize(data->backing) + data->cy - data->oy; px = window_copy_find_length(wme, py); - if ((data->cx >= data->lastsx && data->cx != px) || - data->cx > px) + if ((!data->columnflag && data->cx >= data->lastsx && + data->cx != px) || data->cx > px) window_copy_cursor_end_of_line(wme); } @@ -898,7 +898,10 @@ window_copy_pageup1(struct window_mode_entry *wme, int half_page) oy = screen_hsize(data->backing) + data->cy - data->oy; ox = window_copy_find_length(wme, oy); - window_copy_update_preferred_column(data, ox); + if (data->cx != ox) { + data->lastcx = data->cx; + data->lastsx = ox; + } data->cx = data->lastcx; n = 1; @@ -921,8 +924,8 @@ window_copy_pageup1(struct window_mode_entry *wme, int half_page) if (data->screen.sel == NULL || !data->rectflag) { py = screen_hsize(data->backing) + data->cy - data->oy; px = window_copy_find_length(wme, py); - if ((data->cx >= data->lastsx && data->cx != px) || - data->cx > px) + if ((!data->columnflag && data->cx >= data->lastsx && + data->cx != px) || data->cx > px) window_copy_cursor_end_of_line(wme); } @@ -954,7 +957,10 @@ window_copy_pagedown1(struct window_mode_entry *wme, int half_page, oy = screen_hsize(data->backing) + data->cy - data->oy; ox = window_copy_find_length(wme, oy); - window_copy_update_preferred_column(data, ox); + if (data->cx != ox) { + data->lastcx = data->cx; + data->lastsx = ox; + } data->cx = data->lastcx; n = 1; @@ -977,8 +983,8 @@ window_copy_pagedown1(struct window_mode_entry *wme, int half_page, if (data->screen.sel == NULL || !data->rectflag) { py = screen_hsize(data->backing) + data->cy - data->oy; px = window_copy_find_length(wme, py); - if ((data->cx >= data->lastsx && data->cx != px) || - data->cx > px) + if ((!data->columnflag && data->cx >= data->lastsx && + data->cx != px) || data->cx > px) window_copy_cursor_end_of_line(wme); } @@ -6310,22 +6316,6 @@ window_copy_find_length(struct window_mode_entry *wme, u_int py) return (grid_line_length(data->backing->grid, py)); } -static void -window_copy_update_preferred_column(struct window_copy_mode_data *data, - u_int sx) -{ - if (data->lastsx == UINT_MAX) { - /* Treat the entry column as inside a line. */ - data->lastsx = data->lastcx + 1; - if (data->cx == data->lastcx) - return; - } - if (data->cx != sx) { - data->lastcx = data->cx; - data->lastsx = sx; - } -} - static u_int window_copy_cursor_limit(struct window_mode_entry *wme, u_int py, int allow_onemore) @@ -6512,8 +6502,10 @@ window_copy_cursor_up(struct window_mode_entry *wme, int scroll_only) norectsel = data->screen.sel == NULL || !data->rectflag; oy = screen_hsize(data->backing) + data->cy - data->oy; ox = window_copy_find_length(wme, oy); - if (norectsel) - window_copy_update_preferred_column(data, ox); + if (norectsel && data->cx != ox) { + data->lastcx = data->cx; + data->lastsx = ox; + } if (data->lineflag == LINE_SEL_LEFT_RIGHT && oy == data->sely) window_copy_other_end(wme); @@ -6550,8 +6542,8 @@ window_copy_cursor_up(struct window_mode_entry *wme, int scroll_only) if (norectsel) { py = screen_hsize(data->backing) + data->cy - data->oy; px = window_copy_find_length(wme, py); - if ((data->cx >= data->lastsx && data->cx != px) || - data->cx > px) + if ((!data->columnflag && data->cx >= data->lastsx && + data->cx != px) || data->cx > px) { window_copy_update_cursor(wme, px, data->cy); if (window_copy_update_selection(wme, 1, 0)) @@ -6590,8 +6582,10 @@ window_copy_cursor_down(struct window_mode_entry *wme, int scroll_only) norectsel = data->screen.sel == NULL || !data->rectflag; oy = screen_hsize(data->backing) + data->cy - data->oy; ox = window_copy_find_length(wme, oy); - if (norectsel) - window_copy_update_preferred_column(data, ox); + if (norectsel && data->cx != ox) { + data->lastcx = data->cx; + data->lastsx = ox; + } if (data->lineflag == LINE_SEL_RIGHT_LEFT && oy == data->endsely) window_copy_other_end(wme); @@ -6620,8 +6614,8 @@ window_copy_cursor_down(struct window_mode_entry *wme, int scroll_only) if (norectsel) { py = screen_hsize(data->backing) + data->cy - data->oy; px = window_copy_find_length(wme, py); - if ((data->cx >= data->lastsx && data->cx != px) || - data->cx > px) + if ((!data->columnflag && data->cx >= data->lastsx && + data->cx != px) || data->cx > px) { window_copy_update_cursor(wme, px, data->cy); if (window_copy_update_selection(wme, 1, 0))