// characters (zero if it's a TAB). Count the number of bytes to
// be deleted to make room for the new character, counting screen
// cells. May result in adding spaces to fill a gap.
- getvcol(curwin, &curwin->w_cursor, NULL, &vcol, NULL);
+ getvcol(curwin, &curwin->w_cursor, NULL, &vcol, NULL, 0);
new_vcol = vcol + chartabsize(buf, vcol);
while (oldp[col + oldlen] != NUL && vcol < new_vcol)
{
for ( ; *cts->cts_ptr != NUL && (len == MAXCOL || cts->cts_ptr < cts->cts_line + len);
MB_PTR_ADV(cts->cts_ptr))
{
- vcol += win_lbr_chartabsize(cts, NULL);
+ vcol += win_lbr_chartabsize(cts, NULL, NULL);
if (vcol > MAXCOL)
{
cts->cts_vcol = MAXCOL;
if (len == MAXCOL && cts->cts_has_prop_with_text && *cts->cts_ptr == NUL)
{
int head = 0;
- (void)win_lbr_chartabsize(cts, &head);
+ (void)win_lbr_chartabsize(cts, &head, NULL);
vcol += cts->cts_cur_text_width + head;
// when properties are above or below the empty line must also be
// counted
RET_WIN_BUF_CHARTABSIZE(curwin, curbuf, cts->cts_ptr, cts->cts_vcol)
#if defined(FEAT_LINEBREAK) || defined(FEAT_PROP_POPUP)
}
- return win_lbr_chartabsize(cts, NULL);
+ return win_lbr_chartabsize(cts, NULL, NULL);
#endif
}
* inserts text.
* This function is used very often, keep it fast!!!!
*
- * If "headp" not NULL, set "*headp" to the size of 'showbreak'/'breakindent'
+ * If "headp" isn't NULL, set "*headp" to the size of 'showbreak'/'breakindent'
* included in the return value.
* When "cts->cts_max_head_vcol" is positive, only count in "*headp" the size
* of 'showbreak'/'breakindent' before "cts->cts_max_head_vcol".
* When "cts->cts_max_head_vcol" is negative, only count in "*headp" the size
* of 'showbreak'/'breakindent' before where cursor should be placed.
*
- * Warning: "*headp" may not be set if it's 0, init to 0 before calling.
+ * If "tailp" isn't NULL, set "*tailp" to the size of 'linebreak' included in
+ * the return value.
+ *
+ * Warning: "*headp" and "*tailp" may not be set if the value is 0, init to 0
+ * before calling.
*/
int
win_lbr_chartabsize(
chartabsize_T *cts,
- int *headp UNUSED)
+ int *headp UNUSED,
+ int *tailp UNUSED)
{
win_T *wp = cts->cts_win;
#if defined(FEAT_PROP_POPUP) || defined(FEAT_LINEBREAK)
if (headp != NULL)
*headp = head;
+ int size_before_lbr = size;
int need_lbr = FALSE;
/*
* If 'linebreak' set check at a blank before a non-blank if the line
}
}
+ if (tailp != NULL)
+ *tailp = size - size_before_lbr;
+
# ifdef FEAT_PROP_POPUP
size += cts->cts_first_char;
# endif
* cursor: where the cursor is on this character (first char, except for TAB)
* end: on the last position of this character (TAB, ctrl)
*
+ * When 'linebreak' follows this character, "end" is set to the position before
+ * 'linebreak' if "flags" contains GETVCOL_END_EXCL_LBR, otherwise it's set to
+ * the end of 'linebreak'.
+ *
* This is used very often, keep it fast!
*/
void
pos_T *pos,
colnr_T *start,
colnr_T *cursor,
- colnr_T *end)
+ colnr_T *end,
+ int flags)
{
colnr_T vcol;
char_u *ptr; // points to current char
char_u *line; // start of the line
int incr;
int head;
+ int tail;
#ifdef FEAT_VARTABS
int *vts = wp->w_buffer->b_p_vts_array;
#endif
vcol += incr;
ptr = next_ptr;
}
+
+ tail = 0;
}
else
{
// A tab gets expanded, depending on the current column.
// Other things also take up space.
head = 0;
- incr = win_lbr_chartabsize(&cts, &head);
+ tail = 0;
+ incr = win_lbr_chartabsize(&cts, &head, &tail);
// make sure we don't go past the end of the line
if (*cts.cts_ptr == NUL)
{
if (start != NULL)
*start = vcol + head;
if (end != NULL)
- *end = vcol + incr - 1;
+ *end = vcol + incr - (flags & GETVCOL_END_EXCL_LBR ? tail : 0) - 1;
if (cursor != NULL)
{
if (*ptr == TAB
&& !(VIsual_active
&& (*p_sel == 'e' || LTOREQ_POS(*pos, VIsual)))
)
+ // TODO: subtracting "tail" may lead to better cursor position
*cursor = vcol + incr - 1; // cursor at end
else
{
curwin->w_p_list = FALSE;
if (posp->coladd)
- getvvcol(curwin, posp, NULL, &vcol, NULL);
+ getvvcol(curwin, posp, NULL, &vcol, NULL, 0);
else
- getvcol(curwin, posp, NULL, &vcol, NULL);
+ getvcol(curwin, posp, NULL, &vcol, NULL, 0);
curwin->w_p_list = list_save;
return vcol;
}
pos_T *pos,
colnr_T *start,
colnr_T *cursor,
- colnr_T *end)
+ colnr_T *end,
+ int flags)
{
colnr_T col;
colnr_T coladd;
if (virtual_active())
{
// For virtual mode, only want one value
- getvcol(wp, pos, &col, NULL, NULL);
+ getvcol(wp, pos, &col, NULL, NULL, flags);
coladd = pos->coladd;
endadd = 0;
*end = col + endadd;
}
else
- getvcol(wp, pos, start, cursor, end);
+ getvcol(wp, pos, start, cursor, end, flags);
}
/*
pos_T *pos1,
pos_T *pos2,
colnr_T *left,
- colnr_T *right)
+ colnr_T *right,
+ int flags)
{
colnr_T from1, from2, to1, to2;
if (LT_POSP(pos1, pos2))
{
- getvvcol(wp, pos1, &from1, NULL, &to1);
- getvvcol(wp, pos2, &from2, NULL, &to2);
+ getvvcol(wp, pos1, &from1, NULL, &to1, flags);
+ getvvcol(wp, pos2, &from2, NULL, &to2, flags);
}
else
{
- getvvcol(wp, pos2, &from1, NULL, &to1);
- getvvcol(wp, pos1, &from2, NULL, &to2);
+ getvvcol(wp, pos2, &from1, NULL, &to1, flags);
+ getvvcol(wp, pos1, &from2, NULL, &to2, flags);
}
if (from2 < from1)
*left = from2;
fp.col = (colnr_T)(p - l);
fp.lnum = lnum;
- getvcol(curwin, &fp, &col, NULL, NULL);
+ getvcol(curwin, &fp, &col, NULL, NULL, 0);
return (int)col;
}
p = skipwhite(p + len);
fp.lnum = curwin->w_cursor.lnum;
fp.col = (colnr_T)(p - line);
- getvcol(curwin, &fp, &col, NULL, NULL);
+ getvcol(curwin, &fp, &col, NULL, NULL, 0);
return (int)col;
}
fp.lnum = lnum;
fp.col = (colnr_T)(s - line);
- getvcol(curwin, &fp, &col, NULL, NULL);
+ getvcol(curwin, &fp, &col, NULL, NULL, 0);
return (int)col;
}
else
{
curwin->w_cursor.col = col;
- getvcol(curwin, &curwin->w_cursor, &vcol, NULL, NULL);
+ getvcol(curwin, &curwin->w_cursor, &vcol, NULL, NULL, 0);
amount = (int)vcol;
}
if (amount < curbuf->b_ind_cpp_baseclass)
if (trypos != NULL)
{
// find how indented the line beginning the comment is
- getvcol(curwin, trypos, &col, NULL, NULL);
+ getvcol(curwin, trypos, &col, NULL, NULL, 0);
amount = col;
goto theend;
}
int done = FALSE;
// find how indented the line beginning the comment is
- getvcol(curwin, comment_pos, &col, NULL, NULL);
+ getvcol(curwin, comment_pos, &col, NULL, NULL, 0);
amount = col;
*lead_start = NUL;
*lead_middle = NUL;
if (*look != NUL) // if something after it
comment_pos->col = (colnr_T)(skipwhite(look) - start);
}
- getvcol(curwin, comment_pos, &col, NULL, NULL);
+ getvcol(curwin, comment_pos, &col, NULL, NULL, 0);
amount = col;
if (curbuf->b_ind_in_comment2 || *look == NUL)
amount += curbuf->b_ind_in_comment;
// if we did the above "if".
if (our_paren_pos.col > 0)
{
- getvcol(curwin, &our_paren_pos, &col, NULL, NULL);
+ getvcol(curwin, &our_paren_pos, &col, NULL, NULL, 0);
if (cur_amount > (int)col)
cur_amount = col;
}
look = skipwhite(start);
if (*look == '{')
{
- getvcol(curwin, trypos, &col, NULL, NULL);
+ getvcol(curwin, trypos, &col, NULL, NULL, 0);
amount = col;
if (*start == '{')
start_brace = BRACE_IN_COL0;
wlv.fromcol = 0;
else
{
- getvvcol(wp, top, (colnr_T *)&wlv.fromcol, NULL, NULL);
+ getvvcol(wp, top, (colnr_T *)&wlv.fromcol,
+ NULL, NULL, 0);
if (gchar_pos(top) == NUL)
wlv.tocol = wlv.fromcol + 1;
}
pos = *bot;
if (*p_sel == 'e')
getvvcol(wp, &pos, (colnr_T *)&wlv.tocol,
- NULL, NULL);
+ NULL, NULL, 0);
else
{
getvvcol(wp, &pos, NULL, NULL,
- (colnr_T *)&wlv.tocol);
+ (colnr_T *)&wlv.tocol, 0);
++wlv.tocol;
}
}
{
if (lnum == curwin->w_cursor.lnum)
getvcol(curwin, &(curwin->w_cursor),
- (colnr_T *)&wlv.fromcol, NULL, NULL);
+ (colnr_T *)&wlv.fromcol, NULL, NULL, 0);
else
wlv.fromcol = 0;
if (lnum == curwin->w_cursor.lnum + search_match_lines)
{
pos.lnum = lnum;
pos.col = search_match_endcol;
- getvcol(curwin, &pos, (colnr_T *)&wlv.tocol, NULL, NULL);
+ getvcol(curwin, &pos, (colnr_T *)&wlv.tocol, NULL, NULL, 0);
}
else
wlv.tocol = MAXCOL;
{
chartabsize_T cts;
init_chartabsize_arg(&cts, wp, lnum, 0, line, line);
- (void)win_lbr_chartabsize(&cts, NULL);
+ (void)win_lbr_chartabsize(&cts, NULL, NULL);
vcol_first_char = cts.cts_first_char;
clear_chartabsize_arg(&cts);
}
while (cts.cts_vcol < v)
{
head = 0;
- charsize = win_lbr_chartabsize(&cts, &head);
+ charsize = win_lbr_chartabsize(&cts, &head, NULL);
cts.cts_vcol += charsize;
prev_ptr = cts.cts_ptr;
if (*prev_ptr == NUL)
// do not want virtual text counted here
cts.cts_has_prop_with_text = FALSE;
# endif
- wlv.n_extra = win_lbr_chartabsize(&cts, NULL) - 1;
+ // TODO: consider using "tailp" here
+ wlv.n_extra = win_lbr_chartabsize(&cts, NULL, NULL) - 1;
clear_chartabsize_arg(&cts);
if (on_last_col && c != TAB)
colnr_T tcol;
if (preedit_end_col == MAXCOL)
- getvcol(curwin, &(wp->w_cursor), &tcol, NULL, NULL);
+ getvcol(curwin, &(wp->w_cursor), &tcol, NULL, NULL, 0);
else
tcol = preedit_end_col;
if ((long)preedit_start_col <= wlv.vcol && wlv.vcol < (long)tcol)
if (wp->w_p_list && wp->w_lcs_chars.tab1 == NUL)
{
wp->w_p_list = FALSE;
- getvvcol(wp, &wp->w_cursor, NULL, &virtcol, NULL);
+ getvvcol(wp, &wp->w_cursor, NULL, &virtcol, NULL, 0);
wp->w_p_list = TRUE;
}
if (VIsual_mode == Ctrl_V)
{
colnr_T fromc, toc;
-#if defined(FEAT_LINEBREAK)
- int save_ve_flags = curwin->w_ve_flags;
- if (curwin->w_p_lbr)
- curwin->w_ve_flags = VE_ALL;
-#endif
- getvcols(wp, &VIsual, &curwin->w_cursor, &fromc, &toc);
+ getvcols(wp, &VIsual, &curwin->w_cursor, &fromc, &toc,
+ GETVCOL_END_EXCL_LBR);
++toc;
-#if defined(FEAT_LINEBREAK)
- curwin->w_ve_flags = save_ve_flags;
-#endif
// Highlight to the end of the line, unless 'virtualedit' has
// "block".
if (curwin->w_curswant == MAXCOL)
colnr_T t;
pos.col = (int)ml_get_buf_len(wp->w_buffer, pos.lnum);
- getvvcol(wp, &pos, NULL, NULL, &t);
+ getvvcol(wp, &pos, NULL, NULL, &t, 0);
if (toc < t)
toc = t;
}
{
// Get the number of screen cells used by the character we are
// going to delete.
- getvcol(curwin, &curwin->w_cursor, NULL, &start_vcol, NULL);
+ getvcol(curwin, &curwin->w_cursor, NULL, &start_vcol, NULL, 0);
orig_vcols = chartabsize(ml_get_cursor(), start_vcol);
}
if (has_mbyte)
}
// compute virtual column numbers of first white and cursor
- getvcol(curwin, &fpos, &vcol, NULL, NULL);
- getvcol(curwin, cursor, &want_vcol, NULL, NULL);
+ getvcol(curwin, &fpos, &vcol, NULL, NULL, 0);
+ getvcol(curwin, cursor, &want_vcol, NULL, NULL, 0);
init_chartabsize_arg(&cts, curwin, 0, vcol, tab, tab);
int lbr_saved = reset_lbr();
#endif
- getvvcol(curwin, p1, &sc1, NULL, &ec1);
- getvvcol(curwin, p2, &sc2, NULL, &ec2);
+ getvvcol(curwin, p1, &sc1, NULL, &ec1, 0);
+ getvvcol(curwin, p2, &sc2, NULL, &ec2, 0);
#ifdef FEAT_LINEBREAK
restore_lbr(lbr_saved);
if (fp->col > len)
fp->col = len;
}
- getvvcol(curwin, fp, &vcol_start, NULL, &vcol_end);
+ getvvcol(curwin, fp, &vcol_start, NULL, &vcol_end, 0);
++vcol_start;
++vcol_end;
}
print_line_no_prefix(lnum,
subflags.do_number, subflags.do_list);
- getvcol(curwin, &curwin->w_cursor, &sc, NULL, NULL);
+ getvcol(curwin, &curwin->w_cursor,
+ &sc, NULL, NULL, 0);
curwin->w_cursor.col = regmatch.endpos[0].col - 1;
if (curwin->w_cursor.col < 0)
curwin->w_cursor.col = 0;
- getvcol(curwin, &curwin->w_cursor, NULL, NULL, &ec);
+ getvcol(curwin, &curwin->w_cursor,
+ NULL, NULL, &ec, 0);
curwin->w_cursor.col = regmatch.startpos[0].col;
if (subflags.do_number || curwin->w_p_nu)
{
if (State & MODE_CMDLINE)
preedit_start_col = cmdline_getvcol_cursor();
else if (curwin != NULL && curwin->w_buffer != NULL)
- getvcol(curwin, &curwin->w_cursor, &preedit_start_col, NULL, NULL);
+ getvcol(curwin, &curwin->w_cursor, &preedit_start_col, NULL, NULL, 0);
// Prevent that preediting marks the buffer as changed.
xim_changed_while_preediting = curbuf->b_changed;
}
if (pos.lnum == 0 || *ml_get_pos(&pos) == NUL)
return -1;
- getvcol(curwin, &pos, &col, NULL, NULL);
+ getvcol(curwin, &pos, &col, NULL, NULL, 0);
return (int)col;
}
init_chartabsize_arg(&cts, wp, lnum, 0, line, line);
while (*cts.cts_ptr != NUL && --column >= 0)
{
- cts.cts_vcol += win_lbr_chartabsize(&cts, NULL);
+ cts.cts_vcol += win_lbr_chartabsize(&cts, NULL, NULL);
MB_PTR_ADV(cts.cts_ptr);
}
col = cts.cts_vcol;
if (*cts.cts_ptr == TAB && (State & MODE_NORMAL)
&& (!wp->w_p_list || wp->w_lcs_chars.tab1))
- col += win_lbr_chartabsize(&cts, NULL) - 1;
+ col += win_lbr_chartabsize(&cts, NULL, NULL) - 1;
clear_chartabsize_arg(&cts);
/*
{
colnr_T x;
- getvvcol(curwin, &curwin->w_cursor, &x, NULL, NULL);
+ getvvcol(curwin, &curwin->w_cursor, &x, NULL, NULL, 0);
return (int)x;
}
pos.lnum = curwin->w_cursor.lnum;
pos.col = col;
pos.coladd = coladd;
- getvvcol(curwin, &pos, &x, NULL, NULL);
+ getvvcol(curwin, &pos, &x, NULL, NULL, 0);
return (int)x;
}
#endif
// Count a tab for what it's worth (if list mode not on)
#ifdef FEAT_LINEBREAK
- csize = win_lbr_chartabsize(&cts, &head);
+ csize = win_lbr_chartabsize(&cts, &head, NULL);
MB_PTR_ADV(cts.cts_ptr);
#else
csize = lbr_chartabsize_adv(&cts);
{
colnr_T scol, ecol;
- getvcol(curwin, pos, &scol, NULL, &ecol);
+ getvcol(curwin, pos, &scol, NULL, &ecol, 0);
pos->coladd = ecol - scol;
}
}
{
int cs, ce;
- getvcol(win, &win->w_cursor, &cs, NULL, &ce);
+ getvcol(win, &win->w_cursor, &cs, NULL, &ce, 0);
if (win->w_cursor.coladd > ce - cs)
win->w_cursor.coladd = ce - cs;
}
// advance the cursor one more char. If this fails (last char of the
// line) adjust the scrolling.
colnr_T s, e;
- getvvcol(curwin, &curwin->w_cursor, &s, NULL, &e);
+ getvvcol(curwin, &curwin->w_cursor, &s, NULL, &e, 0);
if (e > (colnr_T)lastcol)
{
retval = TRUE;
else if (VIsual_mode == Ctrl_V)
{
getvcols(curwin, &curwin->w_cursor, &VIsual,
- &leftcol, &rightcol);
- getvcol(curwin, &m_pos, NULL, &m_pos.col, NULL);
+ &leftcol, &rightcol, 0);
+ getvcol(curwin, &m_pos, NULL, &m_pos.col, NULL, 0);
if (m_pos.col < leftcol || m_pos.col > rightcol)
jump_flags = MOUSE_MAY_STOP_VIS;
}
// that is in the quarter that the cursor is in.
if (VIsual_mode == Ctrl_V)
{
- getvcols(curwin, &start_visual, &end_visual, &leftcol, &rightcol);
+ getvcols(curwin, &start_visual, &end_visual,
+ &leftcol, &rightcol, 0);
if (curwin->w_curswant > (leftcol + rightcol) / 2)
end_visual.col = leftcol;
else
init_chartabsize_arg(&cts, wp, lnum, 0, line, line);
while (cts.cts_vcol < vcol && *cts.cts_ptr != NUL)
{
- int size = win_lbr_chartabsize(&cts, NULL);
+ int size = win_lbr_chartabsize(&cts, NULL, NULL);
if (cts.cts_vcol + size > vcol)
break;
cts.cts_vcol += size;
// Check that the cursor position is visible. Add columns for
// the marker displayed in the top-left if needed.
- getvvcol(curwin, &curwin->w_cursor, &vcol, NULL, NULL);
+ getvvcol(curwin, &curwin->w_cursor, &vcol, NULL, NULL, 0);
overlap = sms_marker_overlap(curwin, -1);
if (curwin->w_skipcol + overlap > vcol)
check_topline = TRUE;
#ifdef FEAT_PROP_POPUP
wp->w_virtcol_first_char = 0;
#endif
- getvvcol(wp, &wp->w_cursor, NULL, &(wp->w_virtcol), NULL);
+ getvvcol(wp, &wp->w_cursor, NULL, &(wp->w_virtcol), NULL, 0);
#ifdef FEAT_SYN_HL
redraw_for_cursorcolumn(wp);
#endif
else
#endif
getvvcol(curwin, &curwin->w_cursor,
- &startcol, &(curwin->w_virtcol), &endcol);
+ &startcol, &(curwin->w_virtcol), &endcol, 0);
// remove '$' from change command when cursor moves onto it
if (startcol > dollar_vcol)
else
# endif
{
- getvcol(wp, pos, &scol, &ccol, &ecol);
+ getvcol(wp, pos, &scol, &ccol, &ecol, 0);
// similar to what is done in validate_cursor_col()
col = scol;
p_sbr = empty_option;
curwin->w_p_sbr = empty_option;
#endif
- getvcols(curwin, &curwin->w_cursor, &VIsual, &leftcol, &rightcol);
+ getvcols(curwin, &curwin->w_cursor, &VIsual,
+ &leftcol, &rightcol, 0);
#ifdef FEAT_LINEBREAK
p_sbr = saved_sbr;
curwin->w_p_sbr = saved_w_sbr;
col = 0; // like the cursor is in col 0
else
#endif
- getvcol(curwin, &curwin->w_cursor, &col, NULL, NULL);
+ getvcol(curwin, &curwin->w_cursor, &col, NULL, NULL, 0);
if ((long)col > siso)
col -= siso;
else
col = 0; // like the cursor is in col 0
else
#endif
- getvcol(curwin, &curwin->w_cursor, NULL, NULL, &col);
+ getvcol(curwin, &curwin->w_cursor, NULL, NULL, &col, 0);
n = curwin->w_width - curwin_col_off();
if ((long)col + siso < n)
col = 0;
{
colnr_T scol, ecol;
- getvcol(curwin, &curwin->w_cursor, &scol, NULL, &ecol);
+ getvcol(curwin, &curwin->w_cursor, &scol, NULL, &ecol, 0);
curwin->w_cursor.coladd = ecol - scol;
}
else
if (cmdchar == 'O' && VIsual_mode == Ctrl_V)
{
old_cursor = curwin->w_cursor;
- getvcols(curwin, &old_cursor, &VIsual, &left, &right);
+ getvcols(curwin, &old_cursor, &VIsual, &left, &right, 0);
curwin->w_cursor.lnum = VIsual.lnum;
coladvance(left);
VIsual = curwin->w_cursor;
{
colnr_T vcol;
- getvvcol(curwin, &curwin->w_cursor, NULL, NULL, &vcol);
+ getvvcol(curwin, &curwin->w_cursor, NULL, NULL, &vcol, 0);
if (vcol >= curwin->w_leftcol + curwin->w_width - col_off)
--curwin->w_cursor.col;
}
mb_adjustpos(curbuf, pp);
if (virtual_active())
{
- getvcol(curwin, pp, &cs, NULL, &ce);
+ getvcol(curwin, pp, &cs, NULL, &ce, 0);
pp->coladd = ce - cs;
}
}
colnr_T scol, ecol;
// Coladd is set to the width of the last character.
- getvcol(curwin, &curwin->w_cursor, &scol, NULL, &ecol);
+ getvcol(curwin, &curwin->w_cursor, &scol, NULL, &ecol, 0);
curwin->w_cursor.coladd = ecol - scol + 1;
}
}
#ifdef FEAT_LINEBREAK
/*
+ * TODO: consider using "tailp" of win_lbr_chartabsize() instead of temporarily
+ * resetting 'linebreak'.
+ *
* Reset 'linebreak' and take care of side effects.
* Returns the previous value, to be passed to restore_lbr().
*/
startcol = start.col;
if (virtual_op)
{
- getvcol(curwin, &start, &cs, NULL, &ce);
+ getvcol(curwin, &start, &cs, NULL, &ce, false);
if (ce != cs && start.coladd > 0)
{
// Part of a tab selected -- but don't
endcol = end.col;
if (virtual_op)
{
- getvcol(curwin, &end, &cs, NULL, &ce);
+ getvcol(curwin, &end, &cs, NULL, &ce, false);
if (p[endcol] == NUL || (cs + end.coladd < ce
// Don't add space for double-wide
// char; endcol will be on last byte
oparg.block_mode = TRUE;
oparg.op_type = OP_NOP;
getvcols(curwin, &min_pos, &max_pos,
- &oparg.start_vcol, &oparg.end_vcol);
+ &oparg.start_vcol, &oparg.end_vcol, 0);
#ifdef FEAT_LINEBREAK
p_sbr = saved_sbr;
curwin->w_p_sbr = saved_w_sbr;
{
if (VIsual_mode == Ctrl_V && curwin->w_curswant < MAXCOL)
{
- getvcols(curwin, &min_pos, &max_pos, &min_pos.col,
- &max_pos.col);
+ getvcols(curwin, &min_pos, &max_pos,
+ &min_pos.col, &max_pos.col, 0);
vim_snprintf((char *)buf1, sizeof(buf1), _("%ld Cols; "),
(long)(oparg.end_vcol - oparg.start_vcol + 1));
}
if (has_mbyte)
mb_adjustpos(curwin->w_buffer, &oap->end);
- getvvcol(curwin, &(oap->start), &oap->start_vcol, NULL, &oap->end_vcol);
+ getvvcol(curwin, &(oap->start), &oap->start_vcol, NULL, &oap->end_vcol, 0);
if (!redo_VIsual_busy)
{
- getvvcol(curwin, &(oap->end), &start, NULL, &end);
+ getvvcol(curwin, &(oap->end), &start, NULL, &end, 0);
if (start < oap->start_vcol)
oap->start_vcol = start;
curwin->w_cursor.lnum <= oap->end.lnum;
++curwin->w_cursor.lnum)
{
- getvvcol(curwin, &curwin->w_cursor, NULL, NULL, &end);
+ getvvcol(curwin, &curwin->w_cursor, NULL, NULL, &end, 0);
if (end > oap->end_vcol)
oap->end_vcol = end;
}
{
if (VIsual_mode != Ctrl_V)
getvvcol(curwin, &(oap->end),
- NULL, NULL, &oap->end_vcol);
+ NULL, NULL, &oap->end_vcol, 0);
if (VIsual_mode == Ctrl_V || oap->line_count <= 1)
{
if (VIsual_mode != Ctrl_V)
getvvcol(curwin, &(oap->start),
- &oap->start_vcol, NULL, NULL);
+ &oap->start_vcol, NULL, NULL, 0);
resel_VIsual_vcol = oap->end_vcol - oap->start_vcol + 1;
}
else
// convert text column to mouse column
pos.col = col;
pos.coladd = 0;
- getvcol(textwp, &pos, &mcol, NULL, NULL);
+ getvcol(textwp, &pos, &mcol, NULL, NULL, 0);
wp->w_popup_mouse_mincol = mcol;
pos.col = col + (colnr_T)STRLEN(text) - 1;
- getvcol(textwp, &pos, NULL, NULL, &mcol);
+ getvcol(textwp, &pos, NULL, NULL, &mcol, 0);
wp->w_popup_mouse_maxcol = mcol;
vim_free(text);
}
void clear_chartabsize_arg(chartabsize_T *cts);
int lbr_chartabsize(chartabsize_T *cts);
int lbr_chartabsize_adv(chartabsize_T *cts);
-int win_lbr_chartabsize(chartabsize_T *cts, int *headp);
-void getvcol(win_T *wp, pos_T *pos, colnr_T *start, colnr_T *cursor, colnr_T *end);
+int win_lbr_chartabsize(chartabsize_T *cts, int *headp, int *tailp);
+void getvcol(win_T *wp, pos_T *pos, colnr_T *start, colnr_T *cursor, colnr_T *end, int flags);
colnr_T getvcol_nolist(pos_T *posp);
-void getvvcol(win_T *wp, pos_T *pos, colnr_T *start, colnr_T *cursor, colnr_T *end);
-void getvcols(win_T *wp, pos_T *pos1, pos_T *pos2, colnr_T *left, colnr_T *right);
+void getvvcol(win_T *wp, pos_T *pos, colnr_T *start, colnr_T *cursor, colnr_T *end, int flags);
+void getvcols(win_T *wp, pos_T *pos1, pos_T *pos2, colnr_T *left, colnr_T *right, int flags);
char_u *skipwhite(char_u *q);
char_u *skipwhite_and_nl(char_u *q);
int getwhitecols_curline(void);
}
else if (mode == Ctrl_V)
{
- getvvcol(wp, &top, &start, NULL, &end);
- getvvcol(wp, &bot, &start2, NULL, &end2);
+ getvvcol(wp, &top, &start, NULL, &end, 0);
+ getvvcol(wp, &bot, &start2, NULL, &end2, 0);
if (start2 < start)
start = start2;
if (end2 > end)
colnr_T vcol = 0;
getvvcol(curwin, &curwin->w_cursor,
- NULL, NULL, &vcol);
+ NULL, NULL, &vcol, 0);
++vcol;
n = vcol;
}
colnr_T vcol = 0;
getvvcol(curwin, &curwin->w_cursor,
- NULL, NULL, &vcol);
+ NULL, NULL, &vcol, 0);
n = ++vcol;
}
// \%{n}v \%{n}<v \%{n}>v
if (dir == FORWARD && c != NUL)
{
if (cur_ve_flags == VE_ALL)
- getvcol(curwin, &curwin->w_cursor, &col, NULL, &endcol2);
+ getvcol(curwin, &curwin->w_cursor, &col, NULL, &endcol2, 0);
else
- getvcol(curwin, &curwin->w_cursor, NULL, NULL, &col);
+ getvcol(curwin, &curwin->w_cursor, NULL, NULL, &col, 0);
if (has_mbyte)
// move to start of next multi-byte character
++col;
}
else
- getvcol(curwin, &curwin->w_cursor, &col, NULL, &endcol2);
+ getvcol(curwin, &curwin->w_cursor, &col, NULL, &endcol2, 0);
col += curwin->w_cursor.coladd;
if (cur_ve_flags == VE_ALL
pos.lnum = lnum;
pos.col = col;
pos.coladd = 0;
- getvcol(curwin, &pos, NULL, &vcol, NULL);
+ getvcol(curwin, &pos, NULL, &vcol, NULL, 0);
}
}
return;
if (!curwin->w_p_wrap)
- getvcol(curwin, lpos, NULL, &vcol, NULL);
+ getvcol(curwin, lpos, NULL, &vcol, NULL, 0);
int col_visible = (curwin->w_p_wrap
|| (vcol >= curwin->w_leftcol
--- /dev/null
+|f+0#0000001#a8a8a8255|o@1| |x+0#0000000#ffffff0@9| @5||+1&&| +0&&@53
+|f+0#0000001#a8a8a8255|o@1> +0#0000000#ffffff0@16||+1&&|~+0#4040ff13&| @52
+|x+0#0000000&@19||+1&&|~+0#4040ff13&| @52
+|~| @18||+1#0000000&|~+0#4040ff13&| @52
+|<+3#0000000&|a|m|e|]| |[|+|]| |2|,|4| @3|A|l@1| |[+1&&|N|o| |N|a|m|e|]| @26|0|,|0|-|1| @9|A|l@1
+|-+2&&@1| |V|I|S|U|A|L| |B|L|O|C|K| |-@1| +0&&@45|2|x|2|0| @6
--- /dev/null
+|f+0&#ffffff0|o+0#0000001#a8a8a8255@1| @4|b+0#0000000#ffffff0|a|r| @63
+|f|o+0#0000001#a8a8a8255@1|1|2|3|4|5|b+0#0000000#ffffff0|a|r| @63
+|f>o|o+0#0000001#a8a8a8255| @4|b+0#0000000#ffffff0|a|r| @63
+|~+0#4040ff13&| @73
+|~| @73
+|-+2#0000000&@1| |V|I|S|U|A|L| |B|L|O|C|K| |-@1| +0&&@28|3|x|7| @6|3|,|2| @10|A|l@1|
--- /dev/null
+|f+0&#ffffff0|o+0#0000001#a8a8a8255@1|<|f@3|>|b+0#0000000#ffffff0|a|r| @62
+|f|o+0#0000001#a8a8a8255@1|1|2|3|4|5|6|b+0#0000000#ffffff0|a|r| @62
+|f>o|o+0#0000001#a8a8a8255|<|f@3|>|b+0#0000000#ffffff0|a|r| @62
+|~+0#4040ff13&| @73
+|~| @73
+|-+2#0000000&@1| |V|I|S|U|A|L| |B|L|O|C|K| |-@1| +0&&@28|3|x|8| @6|3|,|2| @10|A|l@1|
--- /dev/null
+|x+0&#ffffff0@1|x+0#0000001#a8a8a8255@7|x+0#0000000#ffffff0@4| @59
+|x@1|x+0#0000001#a8a8a8255@1|f+0#0000000#ffffff0|o@1|:| |x+0#0000001#a8a8a8255|x+0#0000000#ffffff0@4| @59
+|x@1|x+0#0000001#a8a8a8255@1|b+0#0000000#ffffff0|a|r|:| >x@5| @59
+|~+0#4040ff13&| @73
+|~| @73
+|-+2#0000000&@1| |V|I|S|U|A|L| |B|L|O|C|K| |-@1| +0&&@28|3|x|8| @6|3|,|5|-|1|0| @7|A|l@1|
call StopVimInTerminal(buf)
endfunc
+func Test_visual_block_hl_with_linebreak()
+ CheckScreendump
+
+ let lines =<< trim END
+ func Case1()
+ 20vnew
+ setlocal linebreak
+ call setline(1, ['foo ' .. repeat('x', 10), 'foo ' .. repeat('x', 20)])
+ exe "normal! gg0\<C-V>3lj"
+ endfunc
+
+ func Case2()
+ setlocal nolinebreak
+ call setline(1, ["foo\tbar", 'foo12345bar', "foo\tbar"])
+ exe "normal! gg03l\<C-V>2j2h"
+ endfunc
+
+ func Case3()
+ setlocal nolinebreak
+ call setline(1, ["foo\uffffbar", 'foo123456bar', "foo\uffffbar"])
+ exe "normal! gg03l\<C-V>2j2h"
+ endfunc
+
+ func Case4()
+ setlocal nolinebreak
+ call setline(1, [repeat('x', 15), repeat('x', 10), repeat('x', 10)])
+ call prop_type_add('test', {})
+ call prop_add(2, 5, #{text: "foo: ",type: "test"})
+ call prop_add(3, 5, #{text: "bar: ",type: "test"})
+ exe "normal! gg02l\<C-V>2j2l"
+ endfunc
+
+ " FIXME: clipboard=autoselect sometimes changes Visual highlight
+ set clipboard=
+ END
+ call writefile(lines, 'XvisualBlockHlWithLinebreak', 'D')
+ let buf = RunVimInTerminal('-S XvisualBlockHlWithLinebreak', #{rows: 6})
+
+ " 'linebreak' after end char (initially fixed by patch 7.4.467)
+ call term_sendkeys(buf, ":call Case1()\r")
+ call VerifyScreenDump(buf, 'Test_visual_block_hl_with_linebreak_1', {})
+
+ " TAB as end char: 'linebreak' shouldn't break Visual block hl
+ call term_sendkeys(buf, "\<Esc>:bwipe! | call Case2()\r")
+ call VerifyScreenDump(buf, 'Test_visual_block_hl_with_linebreak_2', {})
+ call term_sendkeys(buf, "\<Esc>:setlocal linebreak\rgv")
+ call term_wait(buf, 50)
+ call VerifyScreenDump(buf, 'Test_visual_block_hl_with_linebreak_2', {})
+
+ " Unprintable end char: 'linebreak' shouldn't break Visual block hl
+ call term_sendkeys(buf, "\<Esc>:bwipe! | call Case3()\r")
+ call VerifyScreenDump(buf, 'Test_visual_block_hl_with_linebreak_3', {})
+ call term_sendkeys(buf, "\<Esc>:setlocal linebreak\rgv")
+ call term_wait(buf, 50)
+ call VerifyScreenDump(buf, 'Test_visual_block_hl_with_linebreak_3', {})
+
+ " Virtual text before end char: 'linebreak' shouldn't break Visual block hl
+ call term_sendkeys(buf, "\<Esc>:bwipe! | call Case4()\r")
+ call VerifyScreenDump(buf, 'Test_visual_block_hl_with_linebreak_4', {})
+ call term_sendkeys(buf, "\<Esc>:setlocal linebreak\rgv")
+ call term_wait(buf, 50)
+ call VerifyScreenDump(buf, 'Test_visual_block_hl_with_linebreak_4', {})
+
+ call term_sendkeys(buf, "\<Esc>")
+ call StopVimInTerminal(buf)
+endfunc
+
" vim: shiftwidth=2 sts=2 expandtab
static int included_patches[] =
{ /* Add new patch number below this line */
+/**/
+ 289,
/**/
288,
/**/
#define CF_INTERFACE 2 // inside an interface
#define CF_ABSTRACT_METHOD 4 // inside an abstract class
+// Flags used by getvcol()
+#define GETVCOL_END_EXCL_LBR 1
+
#endif // VIM__H