changeset 30749:6fe513996997 v9.0.0709

patch 9.0.0709: virtual text "after" not correct with 'nowrap' Commit: https://github.com/vim/vim/commit/f167c7b42476f8ab5b32c3c5ccbdca914316e96b Author: Bram Moolenaar <Bram@vim.org> Date: Sun Oct 9 21:53:58 2022 +0100 patch 9.0.0709: virtual text "after" not correct with 'nowrap' Problem: Virtual text "after" not correct with 'nowrap'. Solution: Do not display "after" text prop on the next line when 'wrap' is off.
author Bram Moolenaar <Bram@vim.org>
date Sun, 09 Oct 2022 23:00:03 +0200
parents cf605526dbf9
children e398624e45b4
files src/charset.c src/drawline.c src/proto/drawline.pro src/testdir/dumps/Test_text_after_nowrap_1.dump src/testdir/test_textprop.vim src/version.c
diffstat 6 files changed, 55 insertions(+), 10 deletions(-) [+]
line wrap: on
line diff
--- a/src/charset.c
+++ b/src/charset.c
@@ -1178,7 +1178,7 @@ win_lbr_chartabsize(
 		    {
 			int n_extra = (int)STRLEN(p);
 
-			cells = text_prop_position(wp, tp,
+			cells = text_prop_position(wp, tp, vcol,
 			     (vcol + size) % (wp->w_width - col_off) + col_off,
 						     &n_extra, &p, NULL, NULL);
 #ifdef FEAT_LINEBREAK
--- a/src/drawline.c
+++ b/src/drawline.c
@@ -612,7 +612,8 @@ textprop_size_after_trunc(
 text_prop_position(
 	win_T	    *wp,
 	textprop_T  *tp,
-	int	    vcol,	    // current screen column
+	int	    vcol UNUSED,    // current text column
+	int	    scr_col,	    // current screen column
 	int	    *n_extra,	    // nr of bytes for virtual text
 	char_u	    **p_extra,	    // virtual text
 	int	    *n_attr,	    // attribute cells, NULL if not used
@@ -624,7 +625,7 @@ text_prop_position(
     int	    wrap = (tp->tp_flags & TP_FLAG_WRAP);
     int	    padding = tp->tp_col == MAXCOL && tp->tp_len > 1
 				  ? tp->tp_len - 1 : 0;
-    int	    col_with_padding = vcol + (below ? 0 : padding);
+    int	    col_with_padding = scr_col + (below ? 0 : padding);
     int	    room = wp->w_width - col_with_padding;
     int	    before = room;	// spaces before the text
     int	    after = 0;		// spaces after the text
@@ -1888,21 +1889,21 @@ win_line(
 		    for (pi = 0; pi < text_props_active; ++pi)
 		    {
 			int	    tpi = text_prop_idxs[pi];
+			textprop_T  *tp = &text_props[tpi];
 			proptype_T  *pt = text_prop_type_by_id(
-					wp->w_buffer, text_props[tpi].tp_type);
+					wp->w_buffer, tp->tp_type);
 
 			if (pt != NULL && (pt->pt_hl_id > 0
-						  || text_props[tpi].tp_id < 0)
-					  && text_props[tpi].tp_id != -MAXCOL)
+				     || tp->tp_id < 0) && tp->tp_id != -MAXCOL)
 			{
 			    if (pt->pt_hl_id > 0)
 				used_attr = syn_id2attr(pt->pt_hl_id);
 			    text_prop_type = pt;
 			    text_prop_attr =
 				   hl_combine_attr(text_prop_attr, used_attr);
+			    other_tpi = used_tpi;
 			    text_prop_flags = pt->pt_flags;
-			    text_prop_id = text_props[tpi].tp_id;
-			    other_tpi = used_tpi;
+			    text_prop_id = tp->tp_id;
 			    used_tpi = tpi;
 			}
 		    }
@@ -1972,6 +1973,7 @@ win_line(
 				// Shared with win_lbr_chartabsize(), must do
 				// exactly the same.
 				start_line = text_prop_position(wp, tp,
+						    wlv.vcol,
 						    wlv.col,
 						    &wlv.n_extra, &wlv.p_extra,
 						    &n_attr, &n_attr_skip);
@@ -2011,7 +2013,10 @@ win_line(
 			// If this is an "above" text prop and 'nowrap' the we
 			// must wrap anyway.
 			text_prop_above = above;
-			text_prop_follows = other_tpi != -1;
+			text_prop_follows = other_tpi != -1
+			    && (wp->w_p_wrap
+				   || (text_props[other_tpi].tp_flags
+			       & (TP_FLAG_ALIGN_BELOW | TP_FLAG_ALIGN_RIGHT)));
 		    }
 		}
 		else if (text_prop_next < text_prop_count
--- a/src/proto/drawline.pro
+++ b/src/proto/drawline.pro
@@ -1,4 +1,4 @@
 /* drawline.c */
-int text_prop_position(win_T *wp, textprop_T *tp, int vcol, int *n_extra, char_u **p_extra, int *n_attr, int *n_attr_skip);
+int text_prop_position(win_T *wp, textprop_T *tp, int vcol, int scr_col, int *n_extra, char_u **p_extra, int *n_attr, int *n_attr_skip);
 int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, int nochange, int number_only);
 /* vim: set ft=c : */
new file mode 100644
--- /dev/null
+++ b/src/testdir/dumps/Test_text_after_nowrap_1.dump
@@ -0,0 +1,8 @@
+|f+0&#ffffff0|i|r|s|t| |l|i|n|e| @1|a+0&#ffd7ff255|f|t|e|r| |t|h|e| |t|e|x|t| |a|f|t|e|r| |t|h|e| |t|e|x|t| |a|f|t|e|r| |t|h|e| |t|e|x|t| |a|f|t
+|s+0&#ffffff0|e|c|o|n|d| >l|i|n|e| |s|e|c|o|n|d| |l|i|n|e| |s|e|c|o|n|d| |l|i|n|e| |s|e|c|o|n|d| |l|i|n|e| |s|e|c|o|n|d| |l|i|n|e| 
+|t|h|i|r|d| @54
+|f|o|u|r|t|h| @53
+|~+0#4040ff13&| @58
+|~| @58
+|~| @58
+| +0#0000000&@41|2|,|8| @10|A|l@1| 
--- a/src/testdir/test_textprop.vim
+++ b/src/testdir/test_textprop.vim
@@ -3211,6 +3211,36 @@ func Test_long_text_below_with_padding()
   call StopVimInTerminal(buf)
 endfunc
 
+func Test_text_after_nowrap()
+  CheckRunVimInTerminal
+
+  " FIXME: the second property causes a hang
+  let lines =<< trim END
+      vim9script
+      setline(1, ['first line', 'second line '->repeat(50), 'third', 'fourth'])
+      set nowrap
+      prop_type_add('theprop', {highlight: 'DiffChange'})
+      prop_add(1, 0, {
+          type: 'theprop',
+          text: 'after the text '->repeat(5),
+          text_align: 'after',
+          text_padding_left: 2,
+      })
+      #prop_add(1, 0, {
+      #    type: 'theprop',
+      #    text: 'after the text '->repeat(5),
+      #    text_align: 'after',
+      #    text_padding_left: 2,
+      #})
+      normal 2Gw
+  END
+  call writefile(lines, 'XTextAfterNowrap', 'D')
+  let buf = RunVimInTerminal('-S XTextAfterNowrap', #{rows: 8, cols: 60})
+  call VerifyScreenDump(buf, 'Test_text_after_nowrap_1', {})
+
+  call StopVimInTerminal(buf)
+endfunc
+
 func Test_insert_text_change_arg()
   CheckRunVimInTerminal
 
--- a/src/version.c
+++ b/src/version.c
@@ -700,6 +700,8 @@ static char *(features[]) =
 static int included_patches[] =
 {   /* Add new patch number below this line */
 /**/
+    709,
+/**/
     708,
 /**/
     707,