[PATCH] user32: Create a mask from alpha channel when loading a 32 bpp icon. (v4)

Dmitry Timoshkov dmitry at baikal.ru
Wed Aug 22 01:00:13 CDT 2018


This patch fixes applications that draw the 32 bpp icons manually.

v4: directly create 1-bit mask from alpha.

Signed-off-by: Dmitry Timoshkov <dmitry at baikal.ru>
---
 dlls/user32/cursoricon.c | 43 ++++++++++++++++++++++++++++++++++++++++
 1 file changed, 43 insertions(+)

diff --git a/dlls/user32/cursoricon.c b/dlls/user32/cursoricon.c
index 0adb73bf56..7c09f50a5f 100644
--- a/dlls/user32/cursoricon.c
+++ b/dlls/user32/cursoricon.c
@@ -1296,6 +1296,49 @@ static HICON create_icon_from_bmi( const BITMAPINFO *bmi, DWORD maxsize, HMODULE
                        0, 0, bmi_width, bmi_height,
                        mask_bits, bmi_copy, DIB_RGB_COLORS, SRCCOPY );
     }
+    else
+    {
+        if (bmi_has_alpha( bmi, color_bits ))
+        {
+            LONG x, y, dst_stride = ((bmi_width + 31) / 8) & ~3;
+            unsigned char *alpha_mask_bits;
+
+            mask_size = bmi_height * dst_stride;
+            alpha_mask_bits = HeapAlloc( GetProcessHeap(), 0, mask_size );
+
+            if (alpha_mask_bits)
+            {
+                const unsigned char *src = color_bits;
+                unsigned char *dst = alpha_mask_bits;
+
+                for (y = 0; y < bmi_height; y++, dst += dst_stride)
+                {
+                    unsigned char *dst_byte = dst;
+
+                    for (x = 0; x < bmi_width; x += 8, dst_byte++)
+                    {
+                        unsigned char mask = 0x80;
+                        LONG bit_off;
+
+                        *dst_byte = 0;
+
+                        for (bit_off = 0; bit_off < 8; bit_off++, mask >>= 1, src += 4)
+                        {
+                            if (src[3] != 0xff && x + bit_off < bmi_width)
+                                *dst_byte |= mask;
+                        }
+                    }
+                }
+
+                SelectObject( hdc, mask );
+                StretchDIBits( hdc, 0, 0, width, height,
+                               0, 0, bmi_width, bmi_height,
+                               alpha_mask_bits, bmi_copy, DIB_RGB_COLORS, SRCCOPY );
+
+                HeapFree( GetProcessHeap(), 0, alpha_mask_bits );
+            }
+        }
+    }
     ret = TRUE;
 
 done:
-- 
2.17.1




More information about the wine-devel mailing list