https://git.reactos.org/?p=reactos.git;a=commitdiff;h=4093681ad0f66fda0a9a6d...
commit 4093681ad0f66fda0a9a6d65a6a6af8fed1941b4 Author: Andreas Maier staubim@quantentunnel.de AuthorDate: Sat Jun 1 19:09:44 2019 +0200 Commit: Mark Jansen mark.jansen@reactos.org CommitDate: Thu Aug 15 21:11:45 2019 +0200
[COMCTL32] Saturated images: Take mask-images in account.
This fixes CORE-14209 - Some icons not drawn in IDA Free --- dll/win32/comctl32/imagelist.c | 58 +++++++++++++++++++++++++++++------------- 1 file changed, 41 insertions(+), 17 deletions(-)
diff --git a/dll/win32/comctl32/imagelist.c b/dll/win32/comctl32/imagelist.c index c7c780bbee3..4b4b0647642 100644 --- a/dll/win32/comctl32/imagelist.c +++ b/dll/win32/comctl32/imagelist.c @@ -1281,7 +1281,7 @@ ImageList_DrawEx (HIMAGELIST himl, INT i, HDC hdc, INT x, INT y, }
#ifdef __REACTOS__ -static BOOL alpha_blend_image( HIMAGELIST himl, HDC srce_dc, HDC dest_dc, int dest_x, int dest_y, +static BOOL alpha_blend_image( HIMAGELIST himl, HDC srce_dc, HDC srce_dcMask, HDC dest_dc, int dest_x, int dest_y, #else static BOOL alpha_blend_image( HIMAGELIST himl, HDC dest_dc, int dest_x, int dest_y, #endif @@ -1316,7 +1316,7 @@ static BOOL alpha_blend_image( HIMAGELIST himl, HDC dest_dc, int dest_x, int des #endif SelectObject( hdc, bmp ); #ifdef __REACTOS__ - if (!BitBlt( hdc, 0, 0, cx, cy, srce_dc, src_x, src_y, SRCCOPY )) + if (!BitBlt(hdc, 0, 0, cx, cy, srce_dc, src_x, src_y, SRCCOPY)) { TRACE("BitBlt failed\n"); goto done; @@ -1375,7 +1375,7 @@ static BOOL alpha_blend_image( HIMAGELIST himl, HDC dest_dc, int dest_x, int des info->bmiColors[1].rgbGreen = 0xff; info->bmiColors[1].rgbBlue = 0xff; info->bmiColors[1].rgbReserved = 0; - if (!(mask = CreateDIBSection( himl->hdcMask, info, DIB_RGB_COLORS, &mask_bits, 0, 0 ))) + if (!(mask = CreateDIBSection( srce_dcMask, info, DIB_RGB_COLORS, &mask_bits, 0, 0))) { TRACE("CreateDIBSection failed %i\n", GetLastError()); goto done; @@ -1386,13 +1386,13 @@ static BOOL alpha_blend_image( HIMAGELIST himl, HDC dest_dc, int dest_x, int des SelectObject(hdc, bmp); goto done; } - if (!BitBlt(hdc, 0, 0, cx, cy, himl->hdcMask, src_x, src_y, SRCCOPY)) + if (!BitBlt( hdc, 0, 0, cx, cy, srce_dcMask, src_x, src_y, SRCCOPY)) { TRACE("BitBlt failed %i\n", GetLastError()); SelectObject(hdc, bmp); goto done; } - if (SelectObject(hdc, bmp) == NULL) + if (SelectObject( hdc, bmp) == NULL) { TRACE("SelectObject failed %i\n", GetLastError()); goto done; @@ -1414,11 +1414,12 @@ done: }
#ifdef __REACTOS__ -HDC saturate_image( HIMAGELIST himl, HDC dest_dc, int dest_x, int dest_y, - int src_x, int src_y, int cx, int cy, COLORREF rgbFg) +BOOL saturate_image(HIMAGELIST himl, HDC dest_dc, int dest_x, int dest_y, + int src_x, int src_y, int cx, int cy, COLORREF rgbFg, + HDC *hdcImageListDC, HDC *hdcMaskListDC) { - HDC hdc = NULL; - HBITMAP bmp = 0; + HDC hdc = NULL, hdcMask = NULL; + HBITMAP bmp = 0, bmpMask = 0; BITMAPINFO *info;
unsigned int *ptr; @@ -1470,16 +1471,37 @@ HDC saturate_image( HIMAGELIST himl, HDC dest_dc, int dest_x, int dest_y, *ptr = RGBA(mixed_color, mixed_color, mixed_color, GetAValue(orig_color)); }
+ if (himl->hdcMask) + { + hdcMask = CreateCompatibleDC(NULL); + bmpMask = CreateCompatibleBitmap(hdcMask, cx, cy); + + SelectObject(hdcMask, bmpMask); + + if (!BitBlt(hdcMask, 0, 0, cx, cy, himl->hdcMask, src_x, src_y, SRCCOPY)) + { + ERR("BitBlt failed %i\n", GetLastError()); + DeleteDC(hdcMask); + hdcMask = NULL; + goto done; + } + TRACE("mask ok\n"); + } + done:
if (bmp) DeleteObject(bmp); + if (bmpMask) + DeleteObject(bmpMask);
if (info) HeapFree(GetProcessHeap(), 0, info);
/* return the handle to our desaturated dc, that will substitute its original counterpart in the next calls */ - return hdc; + *hdcMaskListDC = hdcMask; + *hdcImageListDC = hdc; + return (hdc != NULL); } #endif /* __REACTOS__ */
@@ -1511,7 +1533,7 @@ ImageList_DrawIndirect (IMAGELISTDRAWPARAMS *pimldp) POINT pt; BOOL has_alpha; #ifdef __REACTOS__ - HDC hdcSaturated = NULL; + HDC hdcSaturated = NULL, hdcSaturatedMask = NULL; #endif
if (!pimldp || !(himl = pimldp->himl)) return FALSE; @@ -1569,12 +1591,12 @@ ImageList_DrawIndirect (IMAGELISTDRAWPARAMS *pimldp) */ if (fState & ILS_SATURATE) { - hdcSaturated = saturate_image(himl, pimldp->hdcDst, pimldp->x, pimldp->y, - pt.x, pt.y, cx, cy, pimldp->rgbFg); - - if (hdcSaturated != NULL) + if (saturate_image(himl, pimldp->hdcDst, pimldp->x, pimldp->y, + pt.x, pt.y, cx, cy, pimldp->rgbFg, + &hdcSaturated, &hdcSaturatedMask)) { hImageListDC = hdcSaturated; + hMaskListDC = hdcSaturatedMask; /* shitty way of getting subroutines to blit at the right place (top left corner), as our modified imagelist only contains a single image for performance reasons */ pt.x = 0; @@ -1604,7 +1626,7 @@ ImageList_DrawIndirect (IMAGELISTDRAWPARAMS *pimldp) if (bIsTransparent) { #ifdef __REACTOS__ - bResult = alpha_blend_image( himl, hImageListDC, pimldp->hdcDst, pimldp->x, pimldp->y, + bResult = alpha_blend_image( himl, hImageListDC, hMaskListDC, pimldp->hdcDst, pimldp->x, pimldp->y, #else bResult = alpha_blend_image( himl, pimldp->hdcDst, pimldp->x, pimldp->y, #endif @@ -1618,7 +1640,7 @@ ImageList_DrawIndirect (IMAGELISTDRAWPARAMS *pimldp) hOldBrush = SelectObject (hImageDC, CreateSolidBrush (colour)); PatBlt( hImageDC, 0, 0, cx, cy, PATCOPY ); #ifdef __REACTOS__ - alpha_blend_image( himl, hImageListDC, hImageDC, 0, 0, pt.x, pt.y, cx, cy, func, fStyle, blend_col ); + alpha_blend_image( himl, hImageListDC, hMaskListDC, hImageDC, 0, 0, pt.x, pt.y, cx, cy, func, fStyle, blend_col ); #else alpha_blend_image( himl, hImageDC, 0, 0, pt.x, pt.y, cx, cy, func, fStyle, blend_col ); #endif @@ -1748,6 +1770,8 @@ cleanup: #ifdef __REACTOS__ if (hdcSaturated) DeleteDC(hdcSaturated); + if (hdcSaturatedMask) + DeleteDC(hdcSaturatedMask); #endif DeleteObject(hBlendMaskBmp); DeleteObject(hImageBmp);