Patch 9.0.0132
Problem:    Multi-byte characters in virtual text not handled correctly.
Solution:   Count screen cells instead of bytes.
Files:      src/charset.c, src/drawline.c, src/testdir/test_textprop.vim,
            src/testdir/dumps/Test_prop_inserts_text_1.dump,
            src/testdir/dumps/Test_prop_inserts_text_2.dump,
            src/testdir/dumps/Test_prop_with_text_after_1.dump


*** ../vim-9.0.0131/src/charset.c       2022-08-01 12:06:37.302107057 +0100
--- src/charset.c       2022-08-01 16:26:19.058848297 +0100
***************
*** 1097,1105 ****
            {
                char_u *p = ((char_u **)wp->w_buffer->b_textprop_text.ga_data)[
                                                               -tp->tp_id - 1];
!               int len = (int)STRLEN(p);
  
-               // TODO: count screen cells
                if (tp->tp_col == MAXCOL)
                {
                    // TODO: truncating
--- 1097,1104 ----
            {
                char_u *p = ((char_u **)wp->w_buffer->b_textprop_text.ga_data)[
                                                               -tp->tp_id - 1];
!               int len = vim_strsize(p);
  
                if (tp->tp_col == MAXCOL)
                {
                    // TODO: truncating
***************
*** 1454,1461 ****
      if (cursor != NULL)
      {
  #ifdef FEAT_PROP_POPUP
!       // cursor is after inserted text
!       vcol += cts.cts_cur_text_width;
  #endif
        if (*ptr == TAB
                && (State & MODE_NORMAL)
--- 1453,1461 ----
      if (cursor != NULL)
      {
  #ifdef FEAT_PROP_POPUP
!       if ((State & MODE_INSERT) == 0)
!           // cursor is after inserted text
!           vcol += cts.cts_cur_text_width;
  #endif
        if (*ptr == TAB
                && (State & MODE_NORMAL)
*** ../vim-9.0.0131/src/drawline.c      2022-08-01 15:52:51.727352432 +0100
--- src/drawline.c      2022-08-01 16:46:29.446876135 +0100
***************
*** 279,285 ****
      int               screen_row;             // row on the screen, incl 
w_winrow
  
      char_u    extra[21];              // "%ld " and 'fdc' must fit in here
!     int               n_extra = 0;            // number of extra chars
      char_u    *p_extra = NULL;        // string of extra chars, plus NUL
      char_u    *p_extra_free = NULL;   // p_extra needs to be freed
      int               c_extra = NUL;          // extra chars, all the same
--- 279,285 ----
      int               screen_row;             // row on the screen, incl 
w_winrow
  
      char_u    extra[21];              // "%ld " and 'fdc' must fit in here
!     int               n_extra = 0;            // number of extra bytes
      char_u    *p_extra = NULL;        // string of extra chars, plus NUL
      char_u    *p_extra_free = NULL;   // p_extra needs to be freed
      int               c_extra = NUL;          // extra chars, all the same
***************
*** 1560,1566 ****
                            c_final = NUL;
                            n_extra = (int)STRLEN(p);
                            extra_attr = used_attr;
!                           n_attr = n_extra;
                            text_prop_attr = 0;
                            if (*ptr == NUL)
                                // don't combine char attr after EOL
--- 1560,1566 ----
                            c_final = NUL;
                            n_extra = (int)STRLEN(p);
                            extra_attr = used_attr;
!                           n_attr = mb_charlen(p);
                            text_prop_attr = 0;
                            if (*ptr == NUL)
                                // don't combine char attr after EOL
***************
*** 1573,1581 ****
                                char_u  *l;
  
                                // Right-align: fill with spaces
-                               // TODO: count screen columns
                                if (right)
!                                   added -= n_extra;
                                if (added < 0 || (below && col == 0))
                                    added = 0;
                                l = alloc(n_extra + added + 1);
--- 1573,1580 ----
                                char_u  *l;
  
                                // Right-align: fill with spaces
                                if (right)
!                                   added -= vim_strsize(p_extra);
                                if (added < 0 || (below && col == 0))
                                    added = 0;
                                l = alloc(n_extra + added + 1);
*** ../vim-9.0.0131/src/testdir/test_textprop.vim       2022-08-01 
16:11:02.656646804 +0100
--- src/testdir/test_textprop.vim       2022-08-01 16:45:22.883239515 +0100
***************
*** 2199,2206 ****
        call prop_add(1, 18, #{type: 'someprop', text: 'SOME '})
        call prop_add(1, 38, #{type: 'otherprop', text: "OTHER\t"})
        call prop_add(1, 69, #{type: 'moreprop', text: 'MORE '})
-       redraw
        normal $
    END
    call writefile(lines, 'XscriptPropsWithText')
    let buf = RunVimInTerminal('-S XscriptPropsWithText', #{rows: 6, cols: 60})
--- 2199,2209 ----
        call prop_add(1, 18, #{type: 'someprop', text: 'SOME '})
        call prop_add(1, 38, #{type: 'otherprop', text: "OTHER\t"})
        call prop_add(1, 69, #{type: 'moreprop', text: 'MORE '})
        normal $
+ 
+       call setline(2, 'prepost')
+       call prop_type_add('multibyte', #{highlight: 'Visual'})
+       call prop_add(2, 4, #{type: 'multibyte', text: 'söme和平téxt'})
    END
    call writefile(lines, 'XscriptPropsWithText')
    let buf = RunVimInTerminal('-S XscriptPropsWithText', #{rows: 6, cols: 60})
***************
*** 2228,2233 ****
--- 2231,2239 ----
        call setline(2, 'Last line.')
        call prop_add(2, 0, #{type: 'afterprop', text: ' After Last ', 
text_align: 'after'})
        normal G$
+ 
+       call setline(3, 'right here')
+       call prop_add(3, 0, #{type: 'rightprop', text: 'söme和平téxt', 
text_align: 'right'})
    END
    call writefile(lines, 'XscriptPropsWithTextAfter')
    let buf = RunVimInTerminal('-S XscriptPropsWithTextAfter', #{rows: 6, cols: 
60})
*** ../vim-9.0.0131/src/testdir/dumps/Test_prop_inserts_text_1.dump     
2022-08-01 15:52:51.727352432 +0100
--- src/testdir/dumps/Test_prop_inserts_text_1.dump     2022-08-01 
16:40:19.065219675 +0100
***************
*** 1,6 ****
  |i+0&#ffffff0|n|s|e|r|t| |s|o|m|e| |t|e|x|t| |S+0#ffffff16#e000002|O|M|E| 
|h+0#0000000#ffffff0|e|r|e| |a|n|d| |o|t|h|e|r| |t|e|x|t| 
|O+0&#ffff4012|T|H|E|R| |t+0&#ffffff0|h|e|r|e| |a|n|d| |s|o
  |m|e| |m|o|r|e| |t|e|x|t| |a|f|t|e|r| |M+0&#5fd7ff255|O|R|E| 
|w+0&#ffffff0|r|a|p@1|i|n>g| @27
  |~+0#4040ff13&| @58
  |~| @58
- |~| @58
  | +0#0000000&@41|1|,|7|6|-|9|2| @6|A|l@1| 
--- 1,6 ----
  |i+0&#ffffff0|n|s|e|r|t| |s|o|m|e| |t|e|x|t| |S+0#ffffff16#e000002|O|M|E| 
|h+0#0000000#ffffff0|e|r|e| |a|n|d| |o|t|h|e|r| |t|e|x|t| 
|O+0&#ffff4012|T|H|E|R| |t+0&#ffffff0|h|e|r|e| |a|n|d| |s|o
  |m|e| |m|o|r|e| |t|e|x|t| |a|f|t|e|r| |M+0&#5fd7ff255|O|R|E| 
|w+0&#ffffff0|r|a|p@1|i|n>g| @27
+ |p|r|e|s+0&#e0e0e08|ö|m|e|和*&|平|t+&|é|x|t|p+0&#ffffff0|o|s|t| @40
  |~+0#4040ff13&| @58
  |~| @58
  | +0#0000000&@41|1|,|7|6|-|9|2| @6|A|l@1| 
*** ../vim-9.0.0131/src/testdir/dumps/Test_prop_inserts_text_2.dump     
2022-08-01 15:52:51.727352432 +0100
--- src/testdir/dumps/Test_prop_inserts_text_2.dump     2022-08-01 
16:40:20.213210932 +0100
***************
*** 1,6 ****
  | +0#0000e05#a8a8a8255@1|i+0#0000000#ffffff0|n|s|e|r|t| |s|o|m|e| |t|e|x|t| 
|S+0#ffffff16#e000002|O|M|E| |h+0#0000000#ffffff0|e|r|e| |a|n|d| |o|t|h|e|r| 
|t|e|x|t| |O+0&#ffff4012|T|H|E|R| |t+0&#ffffff0|h|e|r|e| |a|n|d| 
  | +0#0000e05#a8a8a8255@1|s+0#0000000#ffffff0|o|m|e| |m|o|r|e| |t|e|x|t| 
|a|f|t|e|r| |M+0&#5fd7ff255|O|R|E| |w+0&#ffffff0|r|a|p@1|i|n>g| @23
  |~+0#4040ff13&| @58
  |~| @58
- |~| @58
  | +0#0000000&@41|1|,|7|6|-|9|2| @6|A|l@1| 
--- 1,6 ----
  | +0#0000e05#a8a8a8255@1|i+0#0000000#ffffff0|n|s|e|r|t| |s|o|m|e| |t|e|x|t| 
|S+0#ffffff16#e000002|O|M|E| |h+0#0000000#ffffff0|e|r|e| |a|n|d| |o|t|h|e|r| 
|t|e|x|t| |O+0&#ffff4012|T|H|E|R| |t+0&#ffffff0|h|e|r|e| |a|n|d| 
  | +0#0000e05#a8a8a8255@1|s+0#0000000#ffffff0|o|m|e| |m|o|r|e| |t|e|x|t| 
|a|f|t|e|r| |M+0&#5fd7ff255|O|R|E| |w+0&#ffffff0|r|a|p@1|i|n>g| @23
+ | 
+0#0000e05#a8a8a8255@1|p+0#0000000#ffffff0|r|e|s+0&#e0e0e08|ö|m|e|和*&|平|t+&|é|x|t|p+0&#ffffff0|o|s|t|
 @38
  |~+0#4040ff13&| @58
  |~| @58
  | +0#0000000&@41|1|,|7|6|-|9|2| @6|A|l@1| 
*** ../vim-9.0.0131/src/testdir/dumps/Test_prop_with_text_after_1.dump  
2022-08-01 11:17:36.761985329 +0100
--- src/testdir/dumps/Test_prop_with_text_after_1.dump  2022-08-01 
16:46:41.130814366 +0100
***************
*** 1,6 ****
  |s+0&#ffffff0|o|m|e| |t|e|x|t| |h|e|r|e| |a|n|d| |o|t|h|e|r| |t|e|x|t| 
|t|h|e|r|e| +0&#ffff4012|A|F|T|E|R| | +0&#ffffff0@10| 
+0#ffffff16#e000002|R|I|G|H|T| 
  | +0#0000000#5fd7ff255|B|E|L|O|W| | +0&#ffffff0@52
  |L|a|s|t| |l|i|n|e>.| +0&#ffff4012|A|f|t|e|r| |L|a|s|t| | +0&#ffffff0@37
! |~+0#4040ff13&| @58
! |~| @58
  | +0#0000000&@41|2|,|1|0| @9|A|l@1| 
--- 1,6 ----
  |s+0&#ffffff0|o|m|e| |t|e|x|t| |h|e|r|e| |a|n|d| |o|t|h|e|r| |t|e|x|t| 
|t|h|e|r|e| +0&#ffff4012|A|F|T|E|R| | +0&#ffffff0@10| 
+0#ffffff16#e000002|R|I|G|H|T| 
  | +0#0000000#5fd7ff255|B|E|L|O|W| | +0&#ffffff0@52
  |L|a|s|t| |l|i|n|e>.| +0&#ffff4012|A|f|t|e|r| |L|a|s|t| | +0&#ffffff0@37
! |r|i|g|h|t| |h|e|r|e| @37|s+0#ffffff16#e000002|ö|m|e|和*&|平|t+&|é|x|t
! |~+0#4040ff13#ffffff0| @58
  | +0#0000000&@41|2|,|1|0| @9|A|l@1| 
*** ../vim-9.0.0131/src/version.c       2022-08-01 16:11:02.656646804 +0100
--- src/version.c       2022-08-01 16:48:07.838372781 +0100
***************
*** 737,738 ****
--- 737,740 ----
  {   /* Add new patch number below this line */
+ /**/
+     132,
  /**/

-- 
Your fault: core dumped

 /// Bram Moolenaar -- [email protected] -- http://www.Moolenaar.net   \\\
///                                                                      \\\
\\\        sponsor Vim, vote for features -- http://www.Vim.org/sponsor/ ///
 \\\            help me help AIDS victims -- http://ICCF-Holland.org    ///

-- 
-- 
You received this message from the "vim_dev" maillist.
Do not top-post! Type your reply below the text you are replying to.
For more information, visit http://www.vim.org/maillist.php

--- 
You received this message because you are subscribed to the Google Groups 
"vim_dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To view this discussion on the web visit 
https://groups.google.com/d/msgid/vim_dev/20220801155134.0A2311C05BA%40moolenaar.net.

Raspunde prin e-mail lui