aboutsummaryrefslogtreecommitdiff
path: root/src/nvim/drawline.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/nvim/drawline.c')
-rw-r--r--src/nvim/drawline.c53
1 files changed, 26 insertions, 27 deletions
diff --git a/src/nvim/drawline.c b/src/nvim/drawline.c
index 753baa2675..fa2aecff86 100644
--- a/src/nvim/drawline.c
+++ b/src/nvim/drawline.c
@@ -132,9 +132,12 @@ typedef struct {
bool reset_extra_attr;
- int skip_cells; // nr of cells to skip for virtual text
- int skipped_cells; // nr of skipped virtual text cells
- bool more_virt_inline_chunks; // indicates if there is more inline virtual text after n_extra
+ int skip_cells; ///< nr of cells to skip for w_leftcol
+ ///< or w_skipcol or concealing
+ int skipped_cells; ///< nr of skipped cells for virtual text
+ ///< to be added to wlv.vcol later
+ bool more_virt_inline_chunks; ///< indicates if there is more inline virtual text
+ ///< after n_extra
} winlinevars_T;
/// for line_putchar. Contains the state that needs to be remembered from
@@ -1090,9 +1093,6 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
int n_attr3 = 0; // chars with overruling special attr
int saved_attr3 = 0; // char_attr saved for n_attr3
- int n_skip = 0; // nr of chars to skip for 'nowrap' or
- // concealing
-
int fromcol_prev = -2; // start of inverting after cursor
bool noinvcur = false; // don't invert the cursor
bool lnum_in_visual_area = false;
@@ -1500,10 +1500,13 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
char *prev_ptr = ptr;
chartabsize_T cts;
int charsize = 0;
+ int head = 0;
init_chartabsize_arg(&cts, wp, lnum, wlv.vcol, line, ptr);
+ cts.cts_max_head_vcol = (int)v;
while (cts.cts_vcol < v && *cts.cts_ptr != NUL) {
- charsize = win_lbr_chartabsize(&cts, NULL);
+ head = 0;
+ charsize = win_lbr_chartabsize(&cts, &head);
cts.cts_vcol += charsize;
prev_ptr = cts.cts_ptr;
MB_PTR_ADV(cts.cts_ptr);
@@ -1530,17 +1533,10 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
if (wlv.vcol > v) {
wlv.vcol -= charsize;
ptr = prev_ptr;
- // If the character fits on the screen, don't need to skip it.
- // Except for a TAB.
- if (utf_ptr2cells(ptr) >= charsize || *ptr == TAB) {
- n_skip = (int)(v - wlv.vcol);
- }
}
- // If there the text doesn't reach to the desired column, need to skip
- // "skip_cells" cells when virtual text follows.
- if ((!wp->w_p_wrap || (lnum == wp->w_topline && wp->w_skipcol > 0)) && v > wlv.vcol) {
- wlv.skip_cells = (int)(v - wlv.vcol);
+ if (v > wlv.vcol) {
+ wlv.skip_cells = (int)v - wlv.vcol - head;
}
// Adjust for when the inverted text is before the screen,
@@ -1808,9 +1804,6 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
decor_attr = 0;
search_attr_from_match = false;
}
- if (wlv.n_extra > 0) {
- n_skip = 0;
- }
}
}
@@ -2027,6 +2020,12 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
// Get a character from the line itself.
c0 = c = (uint8_t)(*ptr);
mb_c = c;
+
+ if (c == NUL) {
+ // no more cells to skip
+ wlv.skip_cells = 0;
+ }
+
// If the UTF-8 character is more than one byte: Decode it
// into "mb_c".
mb_l = utfc_ptr2len(ptr);
@@ -2118,7 +2117,7 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
// If a double-width char doesn't fit at the left side display a '<' in
// the first column. Don't do this for unprintable characters.
- if (n_skip > 0 && mb_l > 1 && wlv.n_extra == 0) {
+ if (wlv.skip_cells > 0 && mb_l > 1 && wlv.n_extra == 0) {
wlv.n_extra = 1;
wlv.c_extra = MB_FILLER_CHAR;
wlv.c_final = NUL;
@@ -2619,9 +2618,9 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
}
wlv.n_extra = 0;
wlv.n_attr = 0;
- } else if (n_skip == 0) {
+ } else if (wlv.skip_cells == 0) {
is_concealing = true;
- n_skip = 1;
+ wlv.skip_cells = 1;
}
mb_c = c;
mb_utf8 = check_mb_utf8(&c, u8cc);
@@ -2630,7 +2629,7 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
is_concealing = false;
}
- if (n_skip > 0 && did_decrement_ptr) {
+ if (wlv.skip_cells > 0 && did_decrement_ptr) {
// not showing the '>', put pointer back to avoid getting stuck
ptr++;
}
@@ -2641,7 +2640,7 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
if (!did_wcol && wlv.draw_state == WL_LINE
&& wp == curwin && lnum == wp->w_cursor.lnum
&& conceal_cursor_line(wp)
- && (int)wp->w_virtcol <= wlv.vcol + n_skip) {
+ && (int)wp->w_virtcol <= wlv.vcol + wlv.skip_cells) {
if (wp->w_p_rl) {
wp->w_wcol = grid->cols - wlv.col + wlv.boguscols - 1;
} else {
@@ -2946,7 +2945,7 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
// Store character to be displayed.
// Skip characters that are left of the screen for 'nowrap'.
- if (wlv.draw_state < WL_LINE || n_skip <= 0) {
+ if (wlv.draw_state < WL_LINE || wlv.skip_cells <= 0) {
// Store the character.
if (wp->w_p_rl && utf_char2cells(mb_c) > 1) {
// A double-wide character is: put first half in left cell.
@@ -2999,7 +2998,7 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
wlv.col++;
}
} else if (wp->w_p_cole > 0 && is_concealing) {
- n_skip--;
+ wlv.skip_cells--;
wlv.vcol_off++;
if (wlv.n_extra > 0) {
wlv.vcol_off += wlv.n_extra;
@@ -3055,7 +3054,7 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, bool number_onl
}
}
} else {
- n_skip--;
+ wlv.skip_cells--;
}
// The skipped cells need to be accounted for in vcol.