patch 9.2.0035: syntax highlighting lost in popup with opacity

Commit: 
https://github.com/vim/vim/commit/782345c9e6d4539c462d8e51b8eb82c28fa1232a
Author: Yasuhiro Matsumoto <[email protected]>
Date:   Sat Feb 21 09:55:18 2026 +0000

    patch 9.2.0035: syntax highlighting lost in popup with opacity
    
    Problem:  syntax highlighting lost in popup with opacity lower than 100
              (after v9.2.0017)
    Solution: Before blending, combine the popup's window color attribute
              with the character's own attribute using hl_combine_attr()
              (Yasuhiro Matsumoto).
    
    related: #19272
    closes:  #19478
    
    Signed-off-by: Yasuhiro Matsumoto <[email protected]>
    Signed-off-by: Christian Brabandt <[email protected]>

diff --git a/src/screen.c b/src/screen.c
index 74e4a40e3..6e6f11b70 100644
--- a/src/screen.c
+++ b/src/screen.c
@@ -666,10 +666,15 @@ screen_line(
            opacity_blank = TRUE;
            // Keep the underlying character and blend its foreground color
            // from popup background color to original color.
+           // Combine the popup window color with the character's own
+           // attribute (e.g. match highlight) so that its background
+           // color is preserved on blank cells.
+           int char_attr = ScreenAttrs[off_from];
            int popup_attr = get_wcr_attr(screen_opacity_popup);
+           int combined = hl_combine_attr(popup_attr, char_attr);
            int blend = screen_opacity_popup->w_popup_blend;
            ScreenAttrs[off_to] = hl_blend_attr(ScreenAttrs[off_to],
-                                               popup_attr, blend, TRUE);
+                                               combined, blend, TRUE);
            screen_char(off_to, row, col + coloff);
            // For wide background character, also update the second cell.
            if (bg_char_cells == 2)
@@ -818,11 +823,14 @@ skip_opacity:
                    && (flags & SLF_POPUP)
                    && screen_opacity_popup->w_popup_blend > 0)
            {
+               int char_attr = ScreenAttrs[off_from];
                int popup_attr = get_wcr_attr(screen_opacity_popup);
                int blend = screen_opacity_popup->w_popup_blend;
-               // Blend popup attr with default background (0)
-               // FALSE = keep popup foreground color, blend background only
-               ScreenAttrs[off_to] = hl_blend_attr(0, popup_attr, blend, 
FALSE);
+               // Combine popup window color with the character's own
+               // attribute (e.g. syntax highlighting) so that the
+               // character's foreground color is preserved.
+               int combined = hl_combine_attr(popup_attr, char_attr);
+               ScreenAttrs[off_to] = hl_blend_attr(0, combined, blend, FALSE);
            }
 #endif
 
diff --git a/src/testdir/dumps/Test_popupwin_opacity_hl_100.dump 
b/src/testdir/dumps/Test_popupwin_opacity_hl_100.dump
new file mode 100644
index 000000000..f087349e4
--- /dev/null
+++ b/src/testdir/dumps/Test_popupwin_opacity_hl_100.dump
@@ -0,0 +1,10 @@
+>1+0&#ffffff0| @73
+|2| @73
+|3| @7|f+0#ff404010#5fd7ff255|o@1| @1|b+0#0000000&|a|r| +0&#ffffff0@57
+|4| @7|b+0&#5fd7ff255|a|z| @4| +0&#ffffff0@57
+|5| @73
+|6| @73
+|7| @73
+|8| @73
+|9| @73
+@57|1|,|1| @10|T|o|p| 
diff --git a/src/testdir/dumps/Test_popupwin_opacity_hl_80.dump 
b/src/testdir/dumps/Test_popupwin_opacity_hl_80.dump
new file mode 100644
index 000000000..89700f9c4
--- /dev/null
+++ b/src/testdir/dumps/Test_popupwin_opacity_hl_80.dump
@@ -0,0 +1,10 @@
+>1+0&#ffffff0| @73
+|2| @73
+|3| @7|f+0#ff404010#5fd7ff255|o@1| @1|b+0#0000000&|a|r| +0&#ffffff0@57
+|4| @7|b+0&#5fd7ff255|a|z| @4| +0&#ffffff0@57
+|5| @73
+|6| @73
+|7| @73
+|8| @73
+|9| @73
+|:| @55|1|,|1| @10|T|o|p| 
diff --git a/src/testdir/test_popupwin.vim b/src/testdir/test_popupwin.vim
index a608fbaf5..c00ac29a7 100644
--- a/src/testdir/test_popupwin.vim
+++ b/src/testdir/test_popupwin.vim
@@ -4653,6 +4653,40 @@ func Test_popupwin_bottom_position_without_decoration()
   call StopVimInTerminal(buf)
 endfunc
 
+func Test_popup_opacity_highlight()
+  CheckScreendump
+
+  " Verify that match highlighting is preserved when opacity < 100,
+  " both for non-blank characters and trailing blank cells.
+  let lines =<< trim END
+       call setline(1, range(1, 100))
+       hi PopupColor ctermbg=lightblue
+       hi MyHl ctermfg=red
+
+       " 'foo  ' includes trailing spaces to test the opacity blank path.
+       let winid = popup_create(['foo  bar', 'baz'],
+           \ #{line: 3, col: 10, highlight: 'PopupColor', opacity: 100})
+       call win_execute(winid, "call matchadd('MyHl', 'foo  ')")
+  END
+  call writefile(lines, 'XtestPopupOpacity', 'D')
+  let buf = RunVimInTerminal('-S XtestPopupOpacity', #{rows: 10})
+  call VerifyScreenDump(buf, 'Test_popupwin_opacity_hl_100', {})
+
+  " opacity=80: highlighted text should still be visible
+  call term_sendkeys(buf, ":call popup_clear()\<CR>")
+  call TermWait(buf)
+  call term_sendkeys(buf, ":let winid = popup_create(['foo  bar', 'baz'],"
+       \ .. " #{line: 3, col: 10, highlight: 'PopupColor', opacity: 80})\<CR>")
+  call TermWait(buf)
+  call term_sendkeys(buf, ":call win_execute(winid,"
+       \ .. " \"call matchadd('MyHl', 'foo  ')\")\<CR>")
+  call TermWait(buf)
+  call term_sendkeys(buf, ":\<CR>")
+  call VerifyScreenDump(buf, 'Test_popupwin_opacity_hl_80', {})
+
+  call StopVimInTerminal(buf)
+endfunc
+
 func Test_popup_getwininfo_tabnr()
   tab split
   let winid1 = popup_create('sup', #{tabpage: 1})
diff --git a/src/version.c b/src/version.c
index b7510a5e9..9e140b13f 100644
--- a/src/version.c
+++ b/src/version.c
@@ -734,6 +734,8 @@ static char *(features[]) =
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    35,
 /**/
     34,
 /**/

-- 
-- 
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 visit 
https://groups.google.com/d/msgid/vim_dev/E1vtjmS-005dRF-89%40256bit.org.

Raspunde prin e-mail lui