]> git.ipfire.org Git - thirdparty/vim.git/commitdiff
patch 9.0.1836: display wrong with virttext, linebreak and breakindent v9.0.1836
authorzeertzjq <zeertzjq@outlook.com>
Fri, 1 Sep 2023 16:49:30 +0000 (18:49 +0200)
committerChristian Brabandt <cb@256bit.org>
Fri, 1 Sep 2023 16:49:30 +0000 (18:49 +0200)
Problem:  Wrong display with "above" virtual text and 'linebreak' or
          'breakindent' and 'showbreak'.
Solution: Exclude size of "above" virtual text when calculating them.

closes: #13000

Signed-off-by: Christian Brabandt <cb@256bit.org>
Co-authored-by: zeertzjq <zeertzjq@outlook.com>
12 files changed:
src/charset.c
src/drawline.c
src/testdir/dumps/Test_prop_above_and_before_1.dump [new file with mode: 0644]
src/testdir/dumps/Test_prop_above_and_before_2.dump [new file with mode: 0644]
src/testdir/dumps/Test_prop_above_and_before_3.dump [new file with mode: 0644]
src/testdir/dumps/Test_prop_above_and_before_4.dump [new file with mode: 0644]
src/testdir/dumps/Test_prop_above_and_before_5.dump [new file with mode: 0644]
src/testdir/dumps/Test_prop_above_linebreak_1.dump [new file with mode: 0644]
src/testdir/dumps/Test_prop_above_linebreak_2.dump [new file with mode: 0644]
src/testdir/test_textprop.vim
src/textprop.c
src/version.c

index 3495a0ee179075942cb500b89c2188220d36d69a..dc8fa44833bcbd6b70a1947b4bfb42e9e904570d 100644 (file)
@@ -1209,17 +1209,18 @@ win_lbr_chartabsize(
                        cells = text_prop_position(wp, tp, vcol,
                             (vcol + size) % (wp->w_width - col_off) + col_off,
                                              &n_extra, &p, NULL, NULL, FALSE);
-#ifdef FEAT_LINEBREAK
+#  ifdef FEAT_LINEBREAK
                        no_sbr = TRUE;  // don't use 'showbreak' now
-#endif
+#  endif
                    }
                    else
                        cells = vim_strsize(p);
                    cts->cts_cur_text_width += cells;
                    if (tp->tp_flags & TP_FLAG_ALIGN_ABOVE)
                        cts->cts_first_char += cells;
+                   else
+                       size += cells;
                    cts->cts_start_incl = tp->tp_flags & TP_FLAG_START_INCL;
-                   size += cells;
                    if (*s == TAB)
                    {
                        // tab size changes because of the inserted text
@@ -1263,9 +1264,9 @@ win_lbr_chartabsize(
        int     col_off_prev = win_col_off(wp);
        int     width2 = wp->w_width - col_off_prev + win_col_off2(wp);
        colnr_T wcol = vcol + col_off_prev;
-#ifdef FEAT_PROP_POPUP
+#  ifdef FEAT_PROP_POPUP
        wcol -= wp->w_virtcol_first_char;
-#endif
+#  endif
        colnr_T max_head_vcol = cts->cts_max_head_vcol;
        int     added = 0;
 
@@ -1319,7 +1320,7 @@ win_lbr_chartabsize(
                else if (max_head_vcol > vcol + head_prev + prev_rem)
                    head += (max_head_vcol - (vcol + head_prev + prev_rem)
                                             + width2 - 1) / width2 * head_mid;
-#ifdef FEAT_PROP_POPUP
+#  ifdef FEAT_PROP_POPUP
                else if (max_head_vcol < 0)
                {
                    int off = 0;
@@ -1329,7 +1330,7 @@ win_lbr_chartabsize(
                    if (off >= prev_rem)
                        head += (1 + (off - prev_rem) / width) * head_mid;
                }
-#endif
+#  endif
            }
        }
 
@@ -1385,6 +1386,9 @@ win_lbr_chartabsize(
        }
     }
 
+#  ifdef FEAT_PROP_POPUP
+    size += cts->cts_first_char;
+#  endif
     return size;
 # endif
 #endif
index 63bc96c4da08170b033d403ec182e70a2fb49be9..edcf55cf3fa95d233b805361cb1dee4d4e50bbef 100644 (file)
@@ -1650,6 +1650,18 @@ win_line(
     }
 #endif
 
+#if defined(FEAT_LINEBREAK) || defined(FEAT_PROP_POPUP)
+    colnr_T vcol_first_char = 0;
+    if (wp->w_p_lbr && !number_only)
+    {
+       chartabsize_T cts;
+       init_chartabsize_arg(&cts, wp, lnum, 0, line, line);
+       (void)win_lbr_chartabsize(&cts, NULL);
+       vcol_first_char = cts.cts_first_char;
+       clear_chartabsize_arg(&cts);
+    }
+#endif
+
     // 'nowrap' or 'wrap' and a single line that doesn't fit: Advance to the
     // first character to be displayed.
     if (wp->w_p_wrap)
@@ -2879,7 +2891,11 @@ win_line(
                    char_u  *p = ptr - (mb_off + 1);
                    chartabsize_T cts;
 
-                   init_chartabsize_arg(&cts, wp, lnum, wlv.vcol, line, p);
+                   init_chartabsize_arg(&cts, wp, lnum, wlv.vcol
+# ifdef FEAT_PROP_POPUP
+                                                            - vcol_first_char,
+# endif
+                                                                     line, p);
 # ifdef FEAT_PROP_POPUP
                    // do not want virtual text counted here
                    cts.cts_has_prop_with_text = FALSE;
diff --git a/src/testdir/dumps/Test_prop_above_and_before_1.dump b/src/testdir/dumps/Test_prop_above_and_before_1.dump
new file mode 100644 (file)
index 0000000..b44c5db
--- /dev/null
@@ -0,0 +1,6 @@
+|a+0&#ffffff0| @73
+| +0#e000e06&@1|1|2|3| +0#0000000&@69
+@2|b|:+0#e000e06&| |4|5|6| +0#0000000&>c| @64
+|~+0#4040ff13&| @73
+|~| @73
+| +0#0000000&@56|2|,|5|-|8|5| @7|A|l@1| 
diff --git a/src/testdir/dumps/Test_prop_above_and_before_2.dump b/src/testdir/dumps/Test_prop_above_and_before_2.dump
new file mode 100644 (file)
index 0000000..9fd4040
--- /dev/null
@@ -0,0 +1,6 @@
+|a+0&#ffffff0| @73
+| +0#e000e06&@1|1|2|3| +0#0000000&@69
+@2|b|:+0#e000e06&| |4|5|6> +0#0000000&|c| @64
+|~+0#4040ff13&| @73
+|~| @73
+| +0#0000000&@56|2|,|4|-|8|4| @7|A|l@1| 
diff --git a/src/testdir/dumps/Test_prop_above_and_before_3.dump b/src/testdir/dumps/Test_prop_above_and_before_3.dump
new file mode 100644 (file)
index 0000000..de63090
--- /dev/null
@@ -0,0 +1,6 @@
+|a+0&#ffffff0| @73
+| +0#e000e06&@1|1|2|3| +0#0000000&@69
+@2>b|:+0#e000e06&| |4|5|6| +0#0000000&|c| @64
+|~+0#4040ff13&| @73
+|~| @73
+| +0#0000000&@56|2|,|3|-|7|8| @7|A|l@1| 
diff --git a/src/testdir/dumps/Test_prop_above_and_before_4.dump b/src/testdir/dumps/Test_prop_above_and_before_4.dump
new file mode 100644 (file)
index 0000000..cf1a7a4
--- /dev/null
@@ -0,0 +1,6 @@
+|a+0&#ffffff0| @73
+| +0#e000e06&@1|1|2|3| +0#0000000&@69
+@1> |b|:+0#e000e06&| |4|5|6| +0#0000000&|c| @64
+|~+0#4040ff13&| @73
+|~| @73
+| +0#0000000&@56|2|,|2|-|7@1| @7|A|l@1| 
diff --git a/src/testdir/dumps/Test_prop_above_and_before_5.dump b/src/testdir/dumps/Test_prop_above_and_before_5.dump
new file mode 100644 (file)
index 0000000..d792715
--- /dev/null
@@ -0,0 +1,6 @@
+|a+0&#ffffff0| @73
+| +0#e000e06&@1|1|2|3| +0#0000000&@69
+> @1|b|:+0#e000e06&| |4|5|6| +0#0000000&|c| @64
+|~+0#4040ff13&| @73
+|~| @73
+| +0#0000000&@56|2|,|1|-|7|6| @7|A|l@1| 
diff --git a/src/testdir/dumps/Test_prop_above_linebreak_1.dump b/src/testdir/dumps/Test_prop_above_linebreak_1.dump
new file mode 100644 (file)
index 0000000..59b8108
--- /dev/null
@@ -0,0 +1,6 @@
+|1+0#e000e06#ffffff0|2|3| +0#0000000&@71
+|a| |b| @71
+|c| >d| @71
+|~+0#4040ff13&| @73
+|~| @73
+| +0#0000000&@56|2|,|3| @10|A|l@1| 
diff --git a/src/testdir/dumps/Test_prop_above_linebreak_2.dump b/src/testdir/dumps/Test_prop_above_linebreak_2.dump
new file mode 100644 (file)
index 0000000..e97974c
--- /dev/null
@@ -0,0 +1,6 @@
+|1+0#e000e06#ffffff0|2|3| +0#0000000&@71
+|a| >b| @71
+|c| |d| @71
+|~+0#4040ff13&| @73
+|~| @73
+| +0#0000000&@56|1|,|3|-|7|8| @7|A|l@1| 
index c0069125f0223acdc6d3bf721e8e1f3d4ad4ce2b..736d50bed7c254f7741f8c55581165088236a10e 100644 (file)
@@ -3523,6 +3523,51 @@ func Test_prop_above_with_number()
   call StopVimInTerminal(buf)
 endfunc
 
+func Test_prop_above_with_linebreak()
+  CheckRunVimInTerminal
+
+  let lines =<< trim END
+    setlocal linebreak breakindent breakindentopt=shift:4
+    call setline(1, ["a b", "c d"])
+    call prop_type_add('theprop' , #{highlight: 'Special'})
+    call prop_add(1, 0, #{type: 'theprop', text: '123', text_align: 'above'})
+    normal! 2gg$
+  END
+  call writefile(lines, 'XscriptPropAboveLinebreak', 'D')
+  let buf = RunVimInTerminal('-S XscriptPropAboveLinebreak', #{rows: 6})
+  call VerifyScreenDump(buf, 'Test_prop_above_linebreak_1', {})
+  call term_sendkeys(buf, 'k')
+  call VerifyScreenDump(buf, 'Test_prop_above_linebreak_2', {})
+
+  call StopVimInTerminal(buf)
+endfunc
+
+func Test_prop_above_and_before()
+  CheckRunVimInTerminal
+
+  let lines =<< trim END
+    setlocal linebreak breakindent breakindentopt=shift:2
+    call setline(1, ["a", "  b c"])
+    call prop_type_add('theprop' , #{highlight: 'Special'})
+    call prop_add(2, 0, #{type: 'theprop', text: '  123', text_align: 'above'})
+    call prop_add(2, 4, #{type: 'theprop', text: ': 456'} )
+    normal! 2gg$
+  END
+  call writefile(lines, 'XscriptPropAboveAndBefore', 'D')
+  let buf = RunVimInTerminal('-S XscriptPropAboveAndBefore', #{rows: 6})
+  call VerifyScreenDump(buf, 'Test_prop_above_and_before_1', {})
+  call term_sendkeys(buf, 'h')
+  call VerifyScreenDump(buf, 'Test_prop_above_and_before_2', {})
+  call term_sendkeys(buf, 'h')
+  call VerifyScreenDump(buf, 'Test_prop_above_and_before_3', {})
+  call term_sendkeys(buf, 'h')
+  call VerifyScreenDump(buf, 'Test_prop_above_and_before_4', {})
+  call term_sendkeys(buf, 'h')
+  call VerifyScreenDump(buf, 'Test_prop_above_and_before_5', {})
+
+  call StopVimInTerminal(buf)
+endfunc
+
 func Test_prop_below_split_line()
   CheckRunVimInTerminal
 
index c6e17951d4836bf8de445a1d481f83f86cf5cc17..dde389013f3544a4fe8975ea7055cd9e6f1989c0 100644 (file)
@@ -759,13 +759,12 @@ text_prop_compare(const void *s1, const void *s2)
     tp2 = &text_prop_compare_props[idx2];
     col1 = tp1->tp_col;
     col2 = tp2->tp_col;
-    if (col1 == MAXCOL && col2 == MAXCOL)
+    if (col1 == MAXCOL || col2 == MAXCOL)
     {
        int order1 = text_prop_order(tp1->tp_flags);
        int order2 = text_prop_order(tp2->tp_flags);
 
-       // both props add text before or after the line, sort on order where it
-       // is added
+       // sort on order where it is added
        if (order1 != order2)
            return order1 < order2 ? 1 : -1;
     }
index 71d71b7bb3a65e775e4a5c08aa6771a16321dc40..b31207dce24cb5ae32573180928c5dbb4b475d0c 100644 (file)
@@ -699,6 +699,8 @@ static char *(features[]) =
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    1836,
 /**/
     1835,
 /**/