[PATCH 0/2] MR10094: gdi32/tests: Add tests for GdiTransparentBlt() with 32-bit DIB bitmaps.
Test that the alpha channels in 32-bit DIB bitmaps are ignored in GdiTransparentBlt(). Also add tests to show that the alpha channels are not ignored when converting 32-bit DIB bitmaps to mono bitmaps. This suggests that the alpha channels are ignored in GdiTransparentBlt(), not when generating the mono mask bitmap. -- https://gitlab.winehq.org/wine/wine/-/merge_requests/10094
From: Zhiyi Zhang <zzhang@codeweavers.com> Test that the alpha channels in 32-bit DIB bitmaps are ignored in GdiTransparentBlt(). Also add tests to show that the alpha channels are not ignored when converting 32-bit DIB bitmaps to mono bitmaps. This suggests that the alpha channels are ignored in GdiTransparentBlt(), not when generating the mono mask bitmap. --- dlls/gdi32/tests/bitmap.c | 73 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 73 insertions(+) diff --git a/dlls/gdi32/tests/bitmap.c b/dlls/gdi32/tests/bitmap.c index 773e0fad5ee..0d381541443 100644 --- a/dlls/gdi32/tests/bitmap.c +++ b/dlls/gdi32/tests/bitmap.c @@ -3125,6 +3125,7 @@ static void test_StretchBlt(void) BITMAPINFO biDst, biSrc; UINT32 expected[256]; RGBQUAD colors[2]; + COLORREF color; memset(&biDst, 0, sizeof(BITMAPINFO)); biDst.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); @@ -3434,6 +3435,34 @@ static void test_StretchBlt(void) DeleteObject(bmpDst); DeleteDC(hdcDst); + /* Test blitting from 32-bit bitmap to a mono bitmap when the 32-bit bitmap has 0xffffff as the + * background color and the pixel data is 0xffffffff. This shows that the raw pixel value is + * compared with the background color when calculating the destination mono bitmap pixel value */ + hdcDst = CreateCompatibleDC( hdcScreen ); + bmpDst = CreateBitmap( 1, 1, 1, 1, 0 ); + oldDst = SelectObject( hdcDst, bmpDst ); + hdcSrc = CreateCompatibleDC( hdcDst ); + biSrc.bmiHeader.biWidth = 1; + biSrc.bmiHeader.biHeight = 1; + biSrc.bmiHeader.biBitCount = 32; + bmpSrc = CreateDIBSection( hdcSrc, &biSrc, DIB_RGB_COLORS, (void **)&srcBuffer, NULL, 0 ); + oldSrc = SelectObject( hdcSrc, bmpSrc ); + + srcBuffer[0] = 0xfffffff; + SetBkColor( hdcSrc, RGB(0xff, 0xff, 0xff) ); + StretchBlt( hdcDst, 0, 0, 1, 1, hdcSrc, 0, 0, 1, 1, SRCCOPY ); + SetBkColor( hdcSrc, RGB(0xff, 0x0, 0x0) ); + StretchBlt( hdcSrc, 0, 0, 1, 1, hdcDst, 0, 0, 1, 1, SRCCOPY ); + color = GetPixel( hdcSrc, 0, 0 ); + ok( color == 0, "Got unexpected color %#lx\n", color ); + + SelectObject( hdcSrc, oldSrc ); + SelectObject( hdcDst, oldDst ); + DeleteObject( bmpSrc ); + DeleteObject( bmpDst ); + DeleteDC( hdcDst ); + DeleteDC( hdcSrc ); + DeleteDC(hdcScreen); } @@ -6314,6 +6343,49 @@ todo_wine_if (y == 25 || x == 40) DeleteDC( dc ); } +static void test_GdiTransparentBlt(void) +{ + HBITMAP bmp_dst, bmp_src, old_dst, old_src; + HDC hdc_screen, hdc_dst, hdc_src; + UINT32 *dst_buffer, *src_buffer; + BITMAPINFO bmi; + BOOL ret; + + hdc_screen = CreateCompatibleDC( 0 ); + hdc_dst = CreateCompatibleDC( hdc_screen ); + hdc_src = CreateCompatibleDC( hdc_dst ); + + memset( &bmi, 0, sizeof(BITMAPINFO) ); + bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); + bmi.bmiHeader.biWidth = 1; + bmi.bmiHeader.biHeight = 1; + bmi.bmiHeader.biPlanes = 1; + bmi.bmiHeader.biBitCount = 32; + bmi.bmiHeader.biCompression = BI_RGB; + + /* Test when the source pixel is 0xffffffff and the transparent color is 0xffffff. The alpha + * channel of the source pixel should be ignored for DIB bitmaps */ + bmp_dst = CreateDIBSection( hdc_screen, &bmi, DIB_RGB_COLORS, (void **)&dst_buffer, NULL, 0 ); + old_dst = SelectObject( hdc_dst, bmp_dst ); + bmp_src = CreateDIBSection( hdc_screen, &bmi, DIB_RGB_COLORS, (void **)&src_buffer, NULL, 0 ); + old_src = SelectObject( hdc_src, bmp_src ); + + dst_buffer[0] = 0x00123456; + src_buffer[0] = 0xffffffff; + ret = GdiTransparentBlt( hdc_dst, 0, 0, 1, 1, hdc_src, 0, 0, 1, 1, RGB(0xff, 0xff, 0xff) ); + ok( ret, "GdiTransparentBlt failed, error %lu.\n", GetLastError() ); + todo_wine + ok( dst_buffer[0] == 0x123456, "Got unexpected color %#x.\n", dst_buffer[0] ); + + SelectObject( hdc_src, old_src ); + SelectObject( hdc_dst, old_dst ); + DeleteObject( bmp_src ); + DeleteObject( bmp_dst ); + DeleteDC( hdc_src ); + DeleteDC( hdc_dst ); + DeleteDC( hdc_screen ); +} + START_TEST(bitmap) { HMODULE hdll; @@ -6342,6 +6414,7 @@ START_TEST(bitmap) test_CreateBitmap(); test_BitBlt(); test_StretchBlt(); + test_GdiTransparentBlt(); test_StretchDIBits(); test_GdiAlphaBlend(); test_GdiGradientFill(); -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10094
From: Zhiyi Zhang <zzhang@codeweavers.com> --- dlls/gdi32/tests/bitmap.c | 1 - dlls/win32u/bitblt.c | 8 ++------ 2 files changed, 2 insertions(+), 7 deletions(-) diff --git a/dlls/gdi32/tests/bitmap.c b/dlls/gdi32/tests/bitmap.c index 0d381541443..d4d04b26927 100644 --- a/dlls/gdi32/tests/bitmap.c +++ b/dlls/gdi32/tests/bitmap.c @@ -6374,7 +6374,6 @@ static void test_GdiTransparentBlt(void) src_buffer[0] = 0xffffffff; ret = GdiTransparentBlt( hdc_dst, 0, 0, 1, 1, hdc_src, 0, 0, 1, 1, RGB(0xff, 0xff, 0xff) ); ok( ret, "GdiTransparentBlt failed, error %lu.\n", GetLastError() ); - todo_wine ok( dst_buffer[0] == 0x123456, "Got unexpected color %#x.\n", dst_buffer[0] ); SelectObject( hdc_src, old_src ); diff --git a/dlls/win32u/bitblt.c b/dlls/win32u/bitblt.c index 7721d3b4b73..c6021dde98f 100644 --- a/dlls/win32u/bitblt.c +++ b/dlls/win32u/bitblt.c @@ -855,7 +855,6 @@ BOOL WINAPI NtGdiTransparentBlt( HDC hdcDest, int xDest, int yDest, int widthDes COLORREF oldBackground; COLORREF oldForeground; int oldStretchMode; - DIBSECTION dib; DC *dc_src; DC *dc_work; @@ -874,12 +873,9 @@ BOOL WINAPI NtGdiTransparentBlt( HDC hdcDest, int xDest, int yDest, int widthDes if (oldStretchMode == BLACKONWHITE || oldStretchMode == WHITEONBLACK) dc_src->attr->stretch_blt_mode = COLORONCOLOR; hdcWork = NtGdiCreateCompatibleDC( hdcDest ); - if ((get_gdi_object_type( hdcDest ) != NTGDI_OBJ_MEMDC || - NtGdiExtGetObjectW( NtGdiGetDCObject( hdcDest, NTGDI_OBJ_SURF ), - sizeof(dib), &dib ) == sizeof(BITMAP)) && - NtGdiGetDeviceCaps( hdcDest, BITSPIXEL ) == 32) + if (NtGdiGetDeviceCaps( hdcDest, BITSPIXEL ) == 32) { - /* screen DCs or DDBs are not supposed to have an alpha channel, so use a 24-bpp bitmap as copy */ + /* the alpha channel should be ignored. use a 24-bpp bitmap as copy */ BITMAPINFO info; info.bmiHeader.biSize = sizeof(info.bmiHeader); info.bmiHeader.biWidth = widthDest; -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10094
participants (2)
-
Zhiyi Zhang -
Zhiyi Zhang (@zhiyi)