Rearrange members of HIMAGELIST to match Windows.

Reuse image and mask DCs.
This commit is contained in:
Vitaliy Margolen 2003-05-13 03:36:27 +00:00 committed by Alexandre Julliard
parent ed3417e349
commit e43edbd557
2 changed files with 177 additions and 267 deletions

View File

@ -100,8 +100,8 @@ static inline BOOL is_valid(HIMAGELIST himl)
static void static void
IMAGELIST_InternalExpandBitmaps (HIMAGELIST himl, INT nImageCount, INT cx, INT cy) IMAGELIST_InternalExpandBitmaps (HIMAGELIST himl, INT nImageCount, INT cx, INT cy)
{ {
HDC hdcImageList, hdcBitmap; HDC hdcBitmap;
HBITMAP hbmNewBitmap; HBITMAP hbmNewBitmap, hbmNull;
INT nNewWidth, nNewCount; INT nNewWidth, nNewCount;
if ((himl->cCurImage + nImageCount <= himl->cMaxImage) if ((himl->cCurImage + nImageCount <= himl->cMaxImage)
@ -113,7 +113,6 @@ IMAGELIST_InternalExpandBitmaps (HIMAGELIST himl, INT nImageCount, INT cx, INT c
nNewWidth = nNewCount * himl->cx; nNewWidth = nNewCount * himl->cx;
TRACE("Create expanded bitmaps : himl=%p x=%d y=%d count=%d\n", himl, nNewWidth, cy, nNewCount); TRACE("Create expanded bitmaps : himl=%p x=%d y=%d count=%d\n", himl, nNewWidth, cy, nNewCount);
hdcImageList = CreateCompatibleDC (0);
hdcBitmap = CreateCompatibleDC (0); hdcBitmap = CreateCompatibleDC (0);
hbmNewBitmap = hbmNewBitmap =
@ -121,11 +120,12 @@ IMAGELIST_InternalExpandBitmaps (HIMAGELIST himl, INT nImageCount, INT cx, INT c
if (hbmNewBitmap == 0) if (hbmNewBitmap == 0)
ERR("creating new image bitmap (x=%d y=%d)!\n", nNewWidth, cy); ERR("creating new image bitmap (x=%d y=%d)!\n", nNewWidth, cy);
SelectObject (hdcImageList, himl->hbmImage); hbmNull = SelectObject (hdcBitmap, hbmNewBitmap);
SelectObject (hdcBitmap, hbmNewBitmap);
BitBlt (hdcBitmap, 0, 0, himl->cCurImage * himl->cx, cy, BitBlt (hdcBitmap, 0, 0, himl->cCurImage * himl->cx, cy,
hdcImageList, 0, 0, SRCCOPY); himl->hdcImage, 0, 0, SRCCOPY);
SelectObject (hdcBitmap, hbmNull);
SelectObject (himl->hdcImage, hbmNewBitmap);
DeleteObject (himl->hbmImage); DeleteObject (himl->hbmImage);
himl->hbmImage = hbmNewBitmap; himl->hbmImage = hbmNewBitmap;
@ -136,17 +136,17 @@ IMAGELIST_InternalExpandBitmaps (HIMAGELIST himl, INT nImageCount, INT cx, INT c
if (hbmNewBitmap == 0) if (hbmNewBitmap == 0)
ERR("creating new mask bitmap!\n"); ERR("creating new mask bitmap!\n");
SelectObject (hdcImageList, himl->hbmMask);
SelectObject (hdcBitmap, hbmNewBitmap); SelectObject (hdcBitmap, hbmNewBitmap);
BitBlt (hdcBitmap, 0, 0, himl->cCurImage * himl->cx, cy, BitBlt (hdcBitmap, 0, 0, himl->cCurImage * himl->cx, cy,
hdcImageList, 0, 0, SRCCOPY); himl->hdcMask, 0, 0, SRCCOPY);
SelectObject (hdcBitmap, hbmNull);
SelectObject (himl->hdcMask, hbmNewBitmap);
DeleteObject (himl->hbmMask); DeleteObject (himl->hbmMask);
himl->hbmMask = hbmNewBitmap; himl->hbmMask = hbmNewBitmap;
} }
himl->cMaxImage = nNewCount; himl->cMaxImage = nNewCount;
DeleteDC (hdcImageList);
DeleteDC (hdcBitmap); DeleteDC (hdcBitmap);
} }
@ -169,11 +169,11 @@ IMAGELIST_InternalExpandBitmaps (HIMAGELIST himl, INT nImageCount, INT cx, INT c
INT WINAPI INT WINAPI
ImageList_Add (HIMAGELIST himl, HBITMAP hbmImage, HBITMAP hbmMask) ImageList_Add (HIMAGELIST himl, HBITMAP hbmImage, HBITMAP hbmMask)
{ {
HDC hdcImage, hdcBitmap; HDC hdcBitmap;
INT nFirstIndex, nImageCount; INT nFirstIndex, nImageCount;
INT nStartX; INT nStartX;
BITMAP bmp; BITMAP bmp;
HBITMAP hOldBitmapImage, hOldBitmap; HBITMAP hOldBitmap;
TRACE("himl=%p hbmimage=%p hbmmask=%p\n", himl, hbmImage, hbmMask); TRACE("himl=%p hbmimage=%p hbmmask=%p\n", himl, hbmImage, hbmMask);
if (!is_valid(himl)) if (!is_valid(himl))
@ -186,28 +186,24 @@ ImageList_Add (HIMAGELIST himl, HBITMAP hbmImage, HBITMAP hbmMask)
nStartX = himl->cCurImage * himl->cx; nStartX = himl->cCurImage * himl->cx;
hdcImage = CreateCompatibleDC(0);
hdcBitmap = CreateCompatibleDC(0); hdcBitmap = CreateCompatibleDC(0);
hOldBitmapImage = SelectObject(hdcImage, himl->hbmImage);
hOldBitmap = SelectObject(hdcBitmap, hbmImage); hOldBitmap = SelectObject(hdcBitmap, hbmImage);
/* Copy result to the imagelist /* Copy result to the imagelist
*/ */
BitBlt (hdcImage, nStartX, 0, bmp.bmWidth, bmp.bmHeight, BitBlt (himl->hdcImage, nStartX, 0, bmp.bmWidth, bmp.bmHeight,
hdcBitmap, 0, 0, SRCCOPY); hdcBitmap, 0, 0, SRCCOPY);
if(himl->hbmMask) if(himl->hbmMask)
{ {
HDC hdcMask, hdcTemp; HDC hdcTemp;
HBITMAP hOldBitmapMask, hOldBitmapTemp; HBITMAP hOldBitmapTemp;
hdcMask = CreateCompatibleDC (0);
hdcTemp = CreateCompatibleDC(0); hdcTemp = CreateCompatibleDC(0);
hOldBitmapMask = SelectObject(hdcMask, himl->hbmMask);
hOldBitmapTemp = SelectObject(hdcTemp, hbmMask); hOldBitmapTemp = SelectObject(hdcTemp, hbmMask);
BitBlt (hdcMask, BitBlt (himl->hdcMask,
nStartX, 0, bmp.bmWidth, bmp.bmHeight, nStartX, 0, bmp.bmWidth, bmp.bmHeight,
hdcTemp, hdcTemp,
0, 0, 0, 0,
@ -218,19 +214,14 @@ ImageList_Add (HIMAGELIST himl, HBITMAP hbmImage, HBITMAP hbmMask)
/* Remove the background from the image /* Remove the background from the image
*/ */
BitBlt (hdcImage, BitBlt (himl->hdcImage,
nStartX, 0, bmp.bmWidth, bmp.bmHeight, nStartX, 0, bmp.bmWidth, bmp.bmHeight,
hdcMask, himl->hdcMask,
nStartX, 0, nStartX, 0,
0x220326); /* NOTSRCAND */ 0x220326); /* NOTSRCAND */
SelectObject(hdcMask, hOldBitmapMask);
DeleteDC(hdcMask);
} }
SelectObject(hdcImage, hOldBitmapImage);
SelectObject(hdcBitmap, hOldBitmap); SelectObject(hdcBitmap, hOldBitmap);
DeleteDC(hdcImage);
DeleteDC(hdcBitmap); DeleteDC(hdcBitmap);
nFirstIndex = himl->cCurImage; nFirstIndex = himl->cCurImage;
@ -279,10 +270,10 @@ INT WINAPI ImageList_AddIcon (HIMAGELIST himl, HICON hIcon)
INT WINAPI INT WINAPI
ImageList_AddMasked (HIMAGELIST himl, HBITMAP hBitmap, COLORREF clrMask) ImageList_AddMasked (HIMAGELIST himl, HBITMAP hBitmap, COLORREF clrMask)
{ {
HDC hdcImage, hdcMask, hdcBitmap; HDC hdcMask, hdcBitmap;
INT nIndex, nImageCount, nMaskXOffset=0; INT nIndex, nImageCount, nMaskXOffset=0;
BITMAP bmp; BITMAP bmp;
HBITMAP hOldBitmap, hOldBitmapMask, hOldBitmapImage; HBITMAP hOldBitmap;
HBITMAP hMaskBitmap=0; HBITMAP hMaskBitmap=0;
COLORREF bkColor; COLORREF bkColor;
@ -300,16 +291,13 @@ ImageList_AddMasked (HIMAGELIST himl, HBITMAP hBitmap, COLORREF clrMask)
nIndex = himl->cCurImage; nIndex = himl->cCurImage;
himl->cCurImage += nImageCount; himl->cCurImage += nImageCount;
hdcMask = CreateCompatibleDC (0);
hdcImage = CreateCompatibleDC(0);
hdcBitmap = CreateCompatibleDC(0); hdcBitmap = CreateCompatibleDC(0);
hOldBitmapImage = SelectObject(hdcImage, himl->hbmImage);
hOldBitmap = SelectObject(hdcBitmap, hBitmap); hOldBitmap = SelectObject(hdcBitmap, hBitmap);
if(himl->hbmMask) if(himl->hbmMask)
{ {
hOldBitmapMask = SelectObject(hdcMask, himl->hbmMask); hdcMask = himl->hdcMask;
nMaskXOffset = nIndex * himl->cx; nMaskXOffset = nIndex * himl->cx;
} }
else else
@ -318,8 +306,9 @@ ImageList_AddMasked (HIMAGELIST himl, HBITMAP hBitmap, COLORREF clrMask)
Create a temp Mask so we can remove the background of Create a temp Mask so we can remove the background of
the Image (Windows does this even if there is no mask) the Image (Windows does this even if there is no mask)
*/ */
hdcMask = CreateCompatibleDC(0);
hMaskBitmap = CreateBitmap(bmp.bmWidth, bmp.bmHeight, 1, 1, NULL); hMaskBitmap = CreateBitmap(bmp.bmWidth, bmp.bmHeight, 1, 1, NULL);
hOldBitmapMask = SelectObject(hdcMask, hMaskBitmap); SelectObject(hdcMask, hMaskBitmap);
nMaskXOffset = 0; nMaskXOffset = 0;
} }
/* create monochrome image to the mask bitmap */ /* create monochrome image to the mask bitmap */
@ -350,22 +339,19 @@ ImageList_AddMasked (HIMAGELIST himl, HBITMAP hBitmap, COLORREF clrMask)
0x220326); /* NOTSRCAND */ 0x220326); /* NOTSRCAND */
/* Copy result to the imagelist /* Copy result to the imagelist
*/ */
BitBlt (hdcImage, BitBlt (himl->hdcImage,
nIndex * himl->cx, 0, bmp.bmWidth, bmp.bmHeight, nIndex * himl->cx, 0, bmp.bmWidth, bmp.bmHeight,
hdcBitmap, hdcBitmap,
0, 0, 0, 0,
SRCCOPY); SRCCOPY);
/* Clean up /* Clean up
*/ */
SelectObject(hdcMask,hOldBitmapMask);
SelectObject(hdcImage, hOldBitmapImage);
SelectObject(hdcBitmap, hOldBitmap); SelectObject(hdcBitmap, hOldBitmap);
DeleteDC(hdcMask);
DeleteDC(hdcImage);
DeleteDC(hdcBitmap); DeleteDC(hdcBitmap);
if(!himl->hbmMask) if(!himl->hbmMask)
{ {
DeleteObject(hMaskBitmap); DeleteObject(hMaskBitmap);
DeleteDC(hdcMask);
} }
return nIndex; return nIndex;
@ -393,7 +379,6 @@ BOOL WINAPI
ImageList_BeginDrag (HIMAGELIST himlTrack, INT iTrack, ImageList_BeginDrag (HIMAGELIST himlTrack, INT iTrack,
INT dxHotspot, INT dyHotspot) INT dxHotspot, INT dyHotspot)
{ {
HDC hdcSrc, hdcDst;
INT cx, cy; INT cx, cy;
TRACE("(himlTrack=%p iTrack=%d dx=%d dy=%d)\n", himlTrack, iTrack, TRACE("(himlTrack=%p iTrack=%d dx=%d dy=%d)\n", himlTrack, iTrack,
@ -417,21 +402,11 @@ ImageList_BeginDrag (HIMAGELIST himlTrack, INT iTrack,
InternalDrag.dxHotspot = dxHotspot; InternalDrag.dxHotspot = dxHotspot;
InternalDrag.dyHotspot = dyHotspot; InternalDrag.dyHotspot = dyHotspot;
hdcSrc = CreateCompatibleDC (0);
hdcDst = CreateCompatibleDC (0);
/* copy image */ /* copy image */
SelectObject (hdcSrc, himlTrack->hbmImage); BitBlt (InternalDrag.himl->hdcImage, 0, 0, cx, cy, himlTrack->hdcImage, iTrack * cx, 0, SRCCOPY);
SelectObject (hdcDst, InternalDrag.himl->hbmImage);
BitBlt (hdcDst, 0, 0, cx, cy, hdcSrc, iTrack * cx, 0, SRCCOPY);
/* copy mask */ /* copy mask */
SelectObject (hdcSrc, himlTrack->hbmMask); BitBlt (InternalDrag.himl->hdcMask, 0, 0, cx, cy, himlTrack->hdcMask, iTrack * cx, 0, SRCCOPY);
SelectObject (hdcDst, InternalDrag.himl->hbmMask);
BitBlt (hdcDst, 0, 0, cx, cy, hdcSrc, iTrack * cx, 0, SRCCOPY);
DeleteDC (hdcSrc);
DeleteDC (hdcDst);
InternalDrag.himl->cCurImage = 1; InternalDrag.himl->cCurImage = 1;
InternalDrag.bHSPending = TRUE; InternalDrag.bHSPending = TRUE;
@ -467,8 +442,6 @@ BOOL WINAPI
ImageList_Copy (HIMAGELIST himlDst, INT iDst, HIMAGELIST himlSrc, ImageList_Copy (HIMAGELIST himlDst, INT iDst, HIMAGELIST himlSrc,
INT iSrc, INT uFlags) INT iSrc, INT uFlags)
{ {
HDC hdcSrc, hdcDst;
TRACE("iDst=%d iSrc=%d\n", iDst, iSrc); TRACE("iDst=%d iSrc=%d\n", iDst, iSrc);
if (!is_valid(himlSrc) || !is_valid(himlDst)) if (!is_valid(himlSrc) || !is_valid(himlDst))
@ -478,16 +451,13 @@ ImageList_Copy (HIMAGELIST himlDst, INT iDst, HIMAGELIST himlSrc,
if ((iSrc < 0) || (iSrc >= himlSrc->cCurImage)) if ((iSrc < 0) || (iSrc >= himlSrc->cCurImage))
return FALSE; return FALSE;
hdcSrc = CreateCompatibleDC (0);
if (himlDst == himlSrc)
hdcDst = hdcSrc;
else
hdcDst = CreateCompatibleDC (0);
if (uFlags & ILCF_SWAP) { if (uFlags & ILCF_SWAP) {
/* swap */ /* swap */
HDC hdcBmp;
HBITMAP hbmTempImage, hbmTempMask; HBITMAP hbmTempImage, hbmTempMask;
hdcBmp = CreateCompatibleDC (0);
/* create temporary bitmaps */ /* create temporary bitmaps */
hbmTempImage = CreateBitmap (himlSrc->cx, himlSrc->cy, 1, hbmTempImage = CreateBitmap (himlSrc->cx, himlSrc->cy, 1,
himlSrc->uBitsPixel, NULL); himlSrc->uBitsPixel, NULL);
@ -496,74 +466,51 @@ ImageList_Copy (HIMAGELIST himlDst, INT iDst, HIMAGELIST himlSrc,
/* copy (and stretch) destination to temporary bitmaps.(save) */ /* copy (and stretch) destination to temporary bitmaps.(save) */
/* image */ /* image */
SelectObject (hdcSrc, himlDst->hbmImage); SelectObject (hdcBmp, hbmTempImage);
SelectObject (hdcDst, hbmTempImage); StretchBlt (hdcBmp, 0, 0, himlSrc->cx, himlSrc->cy,
StretchBlt (hdcDst, 0, 0, himlSrc->cx, himlSrc->cy, himlDst->hdcImage, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
hdcSrc, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
SRCCOPY); SRCCOPY);
/* mask */ /* mask */
SelectObject (hdcSrc, himlDst->hbmMask); SelectObject (hdcBmp, hbmTempMask);
SelectObject (hdcDst, hbmTempMask); StretchBlt (hdcBmp, 0, 0, himlSrc->cx, himlSrc->cy,
StretchBlt (hdcDst, 0, 0, himlSrc->cx, himlSrc->cy, himlDst->hdcMask, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
hdcSrc, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
SRCCOPY); SRCCOPY);
/* copy (and stretch) source to destination */ /* copy (and stretch) source to destination */
/* image */ /* image */
SelectObject (hdcSrc, himlSrc->hbmImage); StretchBlt (himlDst->hdcImage, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
SelectObject (hdcDst, himlDst->hbmImage); himlSrc->hdcImage, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
StretchBlt (hdcDst, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
hdcSrc, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
SRCCOPY); SRCCOPY);
/* mask */ /* mask */
SelectObject (hdcSrc, himlSrc->hbmMask); StretchBlt (himlDst->hdcMask, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
SelectObject (hdcDst, himlDst->hbmMask); himlSrc->hdcMask, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
StretchBlt (hdcDst, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
hdcSrc, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
SRCCOPY); SRCCOPY);
/* copy (without stretching) temporary bitmaps to source (restore) */ /* copy (without stretching) temporary bitmaps to source (restore) */
/* image */
SelectObject (hdcSrc, hbmTempImage);
SelectObject (hdcDst, himlSrc->hbmImage);
BitBlt (hdcDst, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
hdcSrc, 0, 0, SRCCOPY);
/* mask */ /* mask */
SelectObject (hdcSrc, hbmTempMask); BitBlt (himlSrc->hdcMask, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
SelectObject (hdcDst, himlSrc->hbmMask); hdcBmp, 0, 0, SRCCOPY);
BitBlt (hdcDst, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
hdcSrc, 0, 0, SRCCOPY);
/* image */
BitBlt (himlSrc->hdcImage, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
hdcBmp, 0, 0, SRCCOPY);
/* delete temporary bitmaps */ /* delete temporary bitmaps */
DeleteObject (hbmTempMask); DeleteObject (hbmTempMask);
DeleteObject (hbmTempImage); DeleteObject (hbmTempImage);
DeleteDC(hdcBmp);
} }
else { else {
/* copy image */ /* copy image */
SelectObject (hdcSrc, himlSrc->hbmImage); StretchBlt (himlDst->hdcImage, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
if (himlSrc == himlDst) himlSrc->hdcImage, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
hdcDst = hdcSrc;
else
SelectObject (hdcDst, himlDst->hbmImage);
StretchBlt (hdcDst, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
hdcSrc, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
SRCCOPY); SRCCOPY);
/* copy mask */ /* copy mask */
SelectObject (hdcSrc, himlSrc->hbmMask); StretchBlt (himlDst->hdcMask, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
if (himlSrc == himlDst) himlSrc->hdcMask, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
hdcDst = hdcSrc;
else
SelectObject (hdcDst, himlDst->hbmMask);
StretchBlt (hdcDst, iDst * himlDst->cx, 0, himlDst->cx, himlDst->cy,
hdcSrc, iSrc * himlSrc->cx, 0, himlSrc->cx, himlSrc->cy,
SRCCOPY); SRCCOPY);
} }
DeleteDC (hdcSrc);
if (himlSrc != himlDst)
DeleteDC (hdcDst);
return TRUE; return TRUE;
} }
@ -588,7 +535,6 @@ ImageList_Create (INT cx, INT cy, UINT flags,
INT cInitial, INT cGrow) INT cInitial, INT cGrow)
{ {
HIMAGELIST himl; HIMAGELIST himl;
HDC hdc;
INT nCount; INT nCount;
HBITMAP hbmTemp; HBITMAP hbmTemp;
static WORD aBitBlend25[] = static WORD aBitBlend25[] =
@ -603,6 +549,8 @@ ImageList_Create (INT cx, INT cy, UINT flags,
if (!himl) if (!himl)
return NULL; return NULL;
cGrow = (cGrow < 4) ? 4 : (cGrow + 3) & ~3;
himl->magic = IMAGELIST_MAGIC; himl->magic = IMAGELIST_MAGIC;
himl->cx = cx; himl->cx = cx;
himl->cy = cy; himl->cy = cy;
@ -610,21 +558,24 @@ ImageList_Create (INT cx, INT cy, UINT flags,
himl->cMaxImage = cInitial + cGrow; himl->cMaxImage = cInitial + cGrow;
himl->cInitial = cInitial; himl->cInitial = cInitial;
himl->cGrow = cGrow; himl->cGrow = cGrow;
himl->cCurImage = 0;
himl->clrFg = CLR_DEFAULT; himl->clrFg = CLR_DEFAULT;
himl->clrBk = CLR_NONE; himl->clrBk = CLR_NONE;
himl->hbmImage = 0;
himl->hbmMask = 0;
himl->hbrBlend25 = 0;
himl->hbrBlend50 = 0;
/* initialize overlay mask indices */ /* initialize overlay mask indices */
for (nCount = 0; nCount < MAX_OVERLAYIMAGE; nCount++) for (nCount = 0; nCount < MAX_OVERLAYIMAGE; nCount++)
himl->nOvlIdx[nCount] = -1; himl->nOvlIdx[nCount] = -1;
hdc = CreateCompatibleDC (0); /* Create Image & Mask DCs */
himl->uBitsPixel = (UINT)GetDeviceCaps (hdc, BITSPIXEL); himl->hdcImage = CreateCompatibleDC (0);
DeleteDC (hdc); if (!himl->hdcImage)
goto cleanup;
if (himl->flags & ILC_MASK){
himl->hdcMask = CreateCompatibleDC(0);
if (!himl->hdcMask)
goto cleanup;
}
himl->uBitsPixel = (UINT)GetDeviceCaps (himl->hdcImage, BITSPIXEL);
TRACE("Image: %d Bits per Pixel\n", himl->uBitsPixel); TRACE("Image: %d Bits per Pixel\n", himl->uBitsPixel);
@ -634,28 +585,21 @@ ImageList_Create (INT cx, INT cy, UINT flags,
1, himl->uBitsPixel, NULL); 1, himl->uBitsPixel, NULL);
if (himl->hbmImage == 0) { if (himl->hbmImage == 0) {
ERR("Error creating image bitmap!\n"); ERR("Error creating image bitmap!\n");
ImageList_Destroy(himl); goto cleanup;
return NULL;
} }
SelectObject(himl->hdcImage, himl->hbmImage);
} }
else
himl->hbmImage = 0;
if ( (himl->flags & ILC_MASK)) { if (himl->flags & ILC_MASK) {
int images = himl->cMaxImage; himl->hbmMask =
if (images <= 0) CreateBitmap (himl->cx * himl->cMaxImage, himl->cy,
images = 1; 1, 1, NULL);
himl->hbmMask = CreateBitmap (himl->cx * images, himl->cy,
1, 1, NULL);
if (himl->hbmMask == 0) { if (himl->hbmMask == 0) {
ERR("Error creating mask bitmap!\n"); ERR("Error creating mask bitmap!\n");
ImageList_Destroy(himl); goto cleanup;
return NULL;
} }
SelectObject(himl->hdcMask, himl->hbmMask);
} }
else
himl->hbmMask = 0;
/* create blending brushes */ /* create blending brushes */
hbmTemp = CreateBitmap (8, 8, 1, 1, &aBitBlend25); hbmTemp = CreateBitmap (8, 8, 1, 1, &aBitBlend25);
@ -668,6 +612,10 @@ ImageList_Create (INT cx, INT cy, UINT flags,
TRACE("created imagelist %p\n", himl); TRACE("created imagelist %p\n", himl);
return himl; return himl;
cleanup:
if (himl) ImageList_Destroy(himl);
return NULL;
} }
@ -696,6 +644,12 @@ ImageList_Destroy (HIMAGELIST himl)
if (himl->hbmMask) if (himl->hbmMask)
DeleteObject (himl->hbmMask); DeleteObject (himl->hbmMask);
/* delete image & mask DCs */
if (himl->hdcImage)
DeleteDC(himl->hdcImage);
if (himl->hdcMask)
DeleteDC(himl->hdcMask);
/* delete blending brushes */ /* delete blending brushes */
if (himl->hbrBlend25) if (himl->hbrBlend25)
DeleteObject (himl->hbrBlend25); DeleteObject (himl->hbrBlend25);
@ -1090,7 +1044,7 @@ ImageList_DrawIndirect (IMAGELISTDRAWPARAMS *pimldp)
UINT fStyle; UINT fStyle;
COLORREF clrBk, oldImageBk, oldImageFg; COLORREF clrBk, oldImageBk, oldImageFg;
HDC hImageDC, hImageListDC, hMaskListDC; HDC hImageDC, hImageListDC, hMaskListDC;
HBITMAP hImageBmp, hOldImageBmp, hOldImageListBmp, hOldMaskListBmp, hBlendMaskBmp; HBITMAP hImageBmp, hOldImageBmp, hBlendMaskBmp;
BOOL bIsTransparent, bBlend, bResult = FALSE; BOOL bIsTransparent, bBlend, bResult = FALSE;
HIMAGELIST himl; HIMAGELIST himl;
@ -1113,8 +1067,8 @@ ImageList_DrawIndirect (IMAGELISTDRAWPARAMS *pimldp)
himl->hbmMask, pimldp->i, pimldp->x, pimldp->y, cx, cy); himl->hbmMask, pimldp->i, pimldp->x, pimldp->y, cx, cy);
/* we will use these DCs to access the images and masks in the ImageList */ /* we will use these DCs to access the images and masks in the ImageList */
hImageListDC = CreateCompatibleDC(0); hImageListDC = himl->hdcImage;
hMaskListDC = himl->hbmMask ? CreateCompatibleDC(0) : 0; hMaskListDC = himl->hdcMask;
/* these will accumulate the image and mask for the image we're drawing */ /* these will accumulate the image and mask for the image we're drawing */
hImageDC = CreateCompatibleDC( pimldp->hdcDst ); hImageDC = CreateCompatibleDC( pimldp->hdcDst );
@ -1126,9 +1080,7 @@ ImageList_DrawIndirect (IMAGELISTDRAWPARAMS *pimldp)
(bBlend && !hBlendMaskBmp) || (himl->hbmMask && !hMaskListDC)) (bBlend && !hBlendMaskBmp) || (himl->hbmMask && !hMaskListDC))
goto cleanup; goto cleanup;
hOldImageListBmp = SelectObject(hImageListDC, himl->hbmImage);
hOldImageBmp = SelectObject(hImageDC, hImageBmp); hOldImageBmp = SelectObject(hImageDC, hImageBmp);
hOldMaskListBmp = hMaskListDC ? SelectObject(hMaskListDC, himl->hbmMask) : 0;
/* /*
* To obtain a transparent look, background color should be set * To obtain a transparent look, background color should be set
@ -1230,14 +1182,10 @@ ImageList_DrawIndirect (IMAGELISTDRAWPARAMS *pimldp)
SetBkColor(hImageDC, oldImageBk); SetBkColor(hImageDC, oldImageBk);
SetTextColor(hImageDC, oldImageFg); SetTextColor(hImageDC, oldImageFg);
SelectObject(hImageDC, hOldImageBmp); SelectObject(hImageDC, hOldImageBmp);
SelectObject(hImageListDC, hOldImageListBmp);
if (hMaskListDC) SelectObject(hMaskListDC, hOldMaskListBmp);
cleanup: cleanup:
DeleteObject(hBlendMaskBmp); DeleteObject(hBlendMaskBmp);
DeleteObject(hImageBmp); DeleteObject(hImageBmp);
DeleteDC(hImageDC); DeleteDC(hImageDC);
DeleteDC(hImageListDC);
DeleteDC(hMaskListDC);
return bResult; return bResult;
} }
@ -1258,7 +1206,6 @@ HIMAGELIST WINAPI
ImageList_Duplicate (HIMAGELIST himlSrc) ImageList_Duplicate (HIMAGELIST himlSrc)
{ {
HIMAGELIST himlDst; HIMAGELIST himlDst;
HDC hdcSrc, hdcDst;
if (!is_valid(himlSrc)) { if (!is_valid(himlSrc)) {
ERR("Invalid image list handle!\n"); ERR("Invalid image list handle!\n");
@ -1270,23 +1217,12 @@ ImageList_Duplicate (HIMAGELIST himlSrc)
if (himlDst) if (himlDst)
{ {
hdcSrc = CreateCompatibleDC (0); BitBlt (himlDst->hdcImage, 0, 0, himlSrc->cCurImage * himlSrc->cx, himlSrc->cy,
hdcDst = CreateCompatibleDC (0); himlSrc->hdcImage, 0, 0, SRCCOPY);
SelectObject (hdcSrc, himlSrc->hbmImage);
SelectObject (hdcDst, himlDst->hbmImage);
BitBlt (hdcDst, 0, 0, himlSrc->cCurImage * himlSrc->cx, himlSrc->cy,
hdcSrc, 0, 0, SRCCOPY);
if (himlDst->hbmMask) if (himlDst->hbmMask)
{ BitBlt (himlDst->hdcMask, 0, 0, himlSrc->cCurImage * himlSrc->cx, himlSrc->cy,
SelectObject (hdcSrc, himlSrc->hbmMask); himlSrc->hdcMask, 0, 0, SRCCOPY);
SelectObject (hdcDst, himlDst->hbmMask);
BitBlt (hdcDst, 0, 0, himlSrc->cCurImage * himlSrc->cx,
himlSrc->cy, hdcSrc, 0, 0, SRCCOPY);
}
DeleteDC (hdcDst);
DeleteDC (hdcSrc);
himlDst->cCurImage = himlSrc->cCurImage; himlDst->cCurImage = himlSrc->cCurImage;
himlDst->cMaxImage = himlSrc->cMaxImage; himlDst->cMaxImage = himlSrc->cMaxImage;
@ -1419,22 +1355,26 @@ ImageList_GetIcon (HIMAGELIST himl, INT i, UINT fStyle)
HBITMAP hOldDstBitmap; HBITMAP hOldDstBitmap;
HDC hdcDst; HDC hdcDst;
TRACE("%p %d %d\n", himl, i, fStyle);
if (!is_valid(himl) || (i < 0) || (i >= himl->cCurImage)) return NULL; if (!is_valid(himl) || (i < 0) || (i >= himl->cCurImage)) return NULL;
hdcDst = CreateCompatibleDC(0); hdcDst = CreateCompatibleDC(0);
ii.fIcon = TRUE; ii.fIcon = TRUE;
ii.xHotspot = 0;
ii.yHotspot = 0;
/* draw mask*/ /* draw mask*/
ii.hbmMask = CreateCompatibleBitmap (hdcDst, himl->cx, himl->cy); ii.hbmMask = CreateCompatibleBitmap (hdcDst, himl->cx, himl->cy);
hOldDstBitmap = (HBITMAP)SelectObject (hdcDst, ii.hbmMask); hOldDstBitmap = SelectObject (hdcDst, ii.hbmMask);
ImageList_Draw(himl, i, hdcDst, 0, 0, ILD_MASK); PatBlt (hdcDst, 0, 0, himl->cx, himl->cy, WHITENESS);
ImageList_Draw(himl, i, hdcDst, 0, 0, fStyle | ILD_MASK);
/* draw image*/ /* draw image*/
SelectObject (hdcDst, himl->hbmImage); ii.hbmColor = CreateCompatibleBitmap (himl->hdcImage, himl->cx, himl->cy);
ii.hbmColor = CreateCompatibleBitmap (hdcDst, himl->cx, himl->cy);
SelectObject (hdcDst, ii.hbmColor); SelectObject (hdcDst, ii.hbmColor);
ImageList_Draw(himl, i, hdcDst, 0, 0, fStyle); PatBlt (hdcDst, 0, 0, himl->cx, himl->cy, BLACKNESS);
ImageList_Draw(himl, i, hdcDst, 0, 0, fStyle | ILD_TRANSPARENT);
/* /*
* CreateIconIndirect requires us to deselect the bitmaps from * CreateIconIndirect requires us to deselect the bitmaps from
@ -1779,7 +1719,6 @@ ImageList_Merge (HIMAGELIST himl1, INT i1, HIMAGELIST himl2, INT i2,
INT dx, INT dy) INT dx, INT dy)
{ {
HIMAGELIST himlDst = NULL; HIMAGELIST himlDst = NULL;
HDC hdcSrcImage, hdcDstImage;
INT cxDst, cyDst; INT cxDst, cyDst;
INT xOff1, yOff1, xOff2, yOff2; INT xOff1, yOff1, xOff2, yOff2;
INT nX1, nX2; INT nX1, nX2;
@ -1838,41 +1777,20 @@ ImageList_Merge (HIMAGELIST himl1, INT i1, HIMAGELIST himl2, INT i2,
return NULL; return NULL;
if (himlDst) { if (himlDst) {
hdcSrcImage = CreateCompatibleDC (0);
hdcDstImage = CreateCompatibleDC (0);
nX1 = i1 * himl1->cx; nX1 = i1 * himl1->cx;
nX2 = i2 * himl2->cx; nX2 = i2 * himl2->cx;
/* copy image */ /* copy image */
SelectObject (hdcSrcImage, himl1->hbmImage); BitBlt (himlDst->hdcImage, 0, 0, cxDst, cyDst, himl1->hdcImage, 0, 0, BLACKNESS);
SelectObject (hdcDstImage, himlDst->hbmImage); BitBlt (himlDst->hdcImage, xOff1, yOff1, himl1->cx, himl1->cy, himl1->hdcImage, nX1, 0, SRCCOPY);
BitBlt (hdcDstImage, 0, 0, cxDst, cyDst, BitBlt (himlDst->hdcImage, xOff2, yOff2, himl2->cx, himl2->cy, himl2->hdcMask , nX2, 0, SRCAND);
hdcSrcImage, 0, 0, BLACKNESS); BitBlt (himlDst->hdcImage, xOff2, yOff2, himl2->cx, himl2->cy, himl2->hdcImage, nX2, 0, SRCPAINT);
BitBlt (hdcDstImage, xOff1, yOff1, himl1->cx, himl1->cy,
hdcSrcImage, nX1, 0, SRCCOPY);
SelectObject (hdcSrcImage, himl2->hbmMask);
BitBlt (hdcDstImage, xOff2, yOff2, himl2->cx, himl2->cy,
hdcSrcImage, nX2, 0, SRCAND);
SelectObject (hdcSrcImage, himl2->hbmImage);
BitBlt (hdcDstImage, xOff2, yOff2, himl2->cx, himl2->cy,
hdcSrcImage, nX2, 0, SRCPAINT);
/* copy mask */ /* copy mask */
SelectObject (hdcSrcImage, himl1->hbmMask); BitBlt (himlDst->hdcMask, 0, 0, cxDst, cyDst, himl1->hdcMask, 0, 0, WHITENESS);
SelectObject (hdcDstImage, himlDst->hbmMask); BitBlt (himlDst->hdcMask, xOff1, yOff1, himl1->cx, himl1->cy, himl1->hdcMask, nX1, 0, SRCCOPY);
BitBlt (hdcDstImage, 0, 0, cxDst, cyDst, BitBlt (himlDst->hdcMask, xOff2, yOff2, himl2->cx, himl2->cy, himl2->hdcMask, nX2, 0, SRCAND);
hdcSrcImage, 0, 0, WHITENESS);
BitBlt (hdcDstImage, xOff1, yOff1, himl1->cx, himl1->cy,
hdcSrcImage, nX1, 0, SRCCOPY);
SelectObject (hdcSrcImage, himl2->hbmMask);
BitBlt (hdcDstImage, xOff2, yOff2, himl2->cx, himl2->cy,
hdcSrcImage, nX2, 0, SRCAND);
DeleteDC (hdcSrcImage);
DeleteDC (hdcDstImage);
himlDst->cCurImage = 1; himlDst->cCurImage = 1;
} }
@ -2069,8 +1987,14 @@ HIMAGELIST WINAPI ImageList_Read (LPSTREAM pstm)
DeleteObject(hbmMask); DeleteObject(hbmMask);
return NULL; return NULL;
} }
SelectObject(himl->hdcImage, hbmColor);
DeleteObject(himl->hbmImage);
himl->hbmImage = hbmColor; himl->hbmImage = hbmColor;
himl->hbmMask = hbmMask; if (hbmMask){
SelectObject(himl->hdcMask, hbmMask);
DeleteObject(himl->hbmMask);
himl->hbmMask = hbmMask;
}
himl->cCurImage = ilHead.cCurImage; himl->cCurImage = ilHead.cCurImage;
himl->cMaxImage = ilHead.cMaxImage; himl->cMaxImage = ilHead.cMaxImage;
@ -2097,7 +2021,7 @@ BOOL WINAPI
ImageList_Remove (HIMAGELIST himl, INT i) ImageList_Remove (HIMAGELIST himl, INT i)
{ {
HBITMAP hbmNewImage, hbmNewMask; HBITMAP hbmNewImage, hbmNewMask;
HDC hdcSrc, hdcDst; HDC hdcBmp;
INT cxNew, nCount; INT cxNew, nCount;
TRACE("(himl=%p i=%d)\n", himl, i); TRACE("(himl=%p i=%d)\n", himl, i);
@ -2125,16 +2049,18 @@ ImageList_Remove (HIMAGELIST himl, INT i)
for (nCount = 0; nCount < MAX_OVERLAYIMAGE; nCount++) for (nCount = 0; nCount < MAX_OVERLAYIMAGE; nCount++)
himl->nOvlIdx[nCount] = -1; himl->nOvlIdx[nCount] = -1;
DeleteObject (himl->hbmImage); hbmNewImage = CreateBitmap (himl->cMaxImage * himl->cx, himl->cy,
himl->hbmImage =
CreateBitmap (himl->cMaxImage * himl->cx, himl->cy,
1, himl->uBitsPixel, NULL); 1, himl->uBitsPixel, NULL);
SelectObject (himl->hdcImage, hbmNewImage);
DeleteObject (himl->hbmImage);
himl->hbmImage = hbmNewImage;
if (himl->hbmMask) { if (himl->hbmMask) {
DeleteObject (himl->hbmMask); hbmNewMask = CreateBitmap (himl->cMaxImage * himl->cx, himl->cy,
himl->hbmMask =
CreateBitmap (himl->cMaxImage * himl->cx, himl->cy,
1, 1, NULL); 1, 1, NULL);
SelectObject (himl->hdcMask, hbmNewMask);
DeleteObject (himl->hbmMask);
himl->hbmMask = hbmNewMask;
} }
} }
else { else {
@ -2157,50 +2083,46 @@ ImageList_Remove (HIMAGELIST himl, INT i)
else else
hbmNewMask = 0; /* Just to keep compiler happy! */ hbmNewMask = 0; /* Just to keep compiler happy! */
hdcSrc = CreateCompatibleDC (0); hdcBmp = CreateCompatibleDC (0);
hdcDst = CreateCompatibleDC (0);
/* copy all images and masks prior to the "removed" image */ /* copy all images and masks prior to the "removed" image */
if (i > 0) { if (i > 0) {
TRACE("Pre image copy: Copy %d images\n", i); TRACE("Pre image copy: Copy %d images\n", i);
SelectObject (hdcSrc, himl->hbmImage); SelectObject (hdcBmp, hbmNewImage);
SelectObject (hdcDst, hbmNewImage); BitBlt (hdcBmp, 0, 0, i * himl->cx, himl->cy,
BitBlt (hdcDst, 0, 0, i * himl->cx, himl->cy, himl->hdcImage, 0, 0, SRCCOPY);
hdcSrc, 0, 0, SRCCOPY);
if (himl->hbmMask) { if (himl->hbmMask) {
SelectObject (hdcSrc, himl->hbmMask); SelectObject (hdcBmp, hbmNewMask);
SelectObject (hdcDst, hbmNewMask); BitBlt (hdcBmp, 0, 0, i * himl->cx, himl->cy,
BitBlt (hdcDst, 0, 0, i * himl->cx, himl->cy, himl->hdcMask, 0, 0, SRCCOPY);
hdcSrc, 0, 0, SRCCOPY);
} }
} }
/* copy all images and masks behind the removed image */ /* copy all images and masks behind the removed image */
if (i < himl->cCurImage - 1) { if (i < himl->cCurImage - 1) {
TRACE("Post image copy!\n"); TRACE("Post image copy!\n");
SelectObject (hdcSrc, himl->hbmImage); SelectObject (hdcBmp, hbmNewImage);
SelectObject (hdcDst, hbmNewImage); BitBlt (hdcBmp, i * himl->cx, 0, (himl->cCurImage - i - 1) * himl->cx,
BitBlt (hdcDst, i * himl->cx, 0, (himl->cCurImage - i - 1) * himl->cx, himl->cy, himl->hdcImage, (i + 1) * himl->cx, 0, SRCCOPY);
himl->cy, hdcSrc, (i + 1) * himl->cx, 0, SRCCOPY);
if (himl->hbmMask) { if (himl->hbmMask) {
SelectObject (hdcSrc, himl->hbmMask); SelectObject (hdcBmp, hbmNewMask);
SelectObject (hdcDst, hbmNewMask); BitBlt (hdcBmp, i * himl->cx, 0,
BitBlt (hdcDst, i * himl->cx, 0,
(himl->cCurImage - i - 1) * himl->cx, (himl->cCurImage - i - 1) * himl->cx,
himl->cy, hdcSrc, (i + 1) * himl->cx, 0, SRCCOPY); himl->cy, himl->hdcMask, (i + 1) * himl->cx, 0, SRCCOPY);
} }
} }
DeleteDC (hdcSrc); DeleteDC (hdcBmp);
DeleteDC (hdcDst);
/* delete old images and insert new ones */ /* delete old images and insert new ones */
SelectObject (himl->hdcImage, hbmNewImage);
DeleteObject (himl->hbmImage); DeleteObject (himl->hbmImage);
himl->hbmImage = hbmNewImage; himl->hbmImage = hbmNewImage;
if (himl->hbmMask) { if (himl->hbmMask) {
SelectObject (himl->hdcMask, hbmNewMask);
DeleteObject (himl->hbmMask); DeleteObject (himl->hbmMask);
himl->hbmMask = hbmNewMask; himl->hbmMask = hbmNewMask;
} }
@ -2233,7 +2155,7 @@ BOOL WINAPI
ImageList_Replace (HIMAGELIST himl, INT i, HBITMAP hbmImage, ImageList_Replace (HIMAGELIST himl, INT i, HBITMAP hbmImage,
HBITMAP hbmMask) HBITMAP hbmMask)
{ {
HDC hdcImageList, hdcImage; HDC hdcImage;
BITMAP bmp; BITMAP bmp;
TRACE("%p %d %p %p\n", himl, i, hbmImage, hbmMask); TRACE("%p %d %p %p\n", himl, i, hbmImage, hbmMask);
@ -2248,31 +2170,27 @@ ImageList_Replace (HIMAGELIST himl, INT i, HBITMAP hbmImage,
return FALSE; return FALSE;
} }
hdcImageList = CreateCompatibleDC (0);
hdcImage = CreateCompatibleDC (0); hdcImage = CreateCompatibleDC (0);
GetObjectA (hbmImage, sizeof(BITMAP), (LPVOID)&bmp); GetObjectA (hbmImage, sizeof(BITMAP), (LPVOID)&bmp);
/* Replace Image */ /* Replace Image */
SelectObject (hdcImageList, himl->hbmImage);
SelectObject (hdcImage, hbmImage); SelectObject (hdcImage, hbmImage);
StretchBlt (hdcImageList, i * himl->cx, 0, himl->cx, himl->cy, StretchBlt (himl->hdcImage, i * himl->cx, 0, himl->cx, himl->cy,
hdcImage, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY); hdcImage, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY);
if (himl->hbmMask) if (himl->hbmMask)
{ {
/* Replace Mask */ /* Replace Mask */
SelectObject (hdcImageList, himl->hbmMask);
SelectObject (hdcImage, hbmMask); SelectObject (hdcImage, hbmMask);
StretchBlt (hdcImageList, i * himl->cx, 0, himl->cx, himl->cy, StretchBlt (himl->hdcMask, i * himl->cx, 0, himl->cx, himl->cy,
hdcImage, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY); hdcImage, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY);
/* Remove the background from the image /* Remove the background from the image
*/ */
SelectObject (hdcImageList, himl->hbmImage); StretchBlt (himl->hdcImage,
StretchBlt (hdcImageList,
i*himl->cx, 0, himl->cx, himl->cy, i*himl->cx, 0, himl->cx, himl->cy,
hdcImage, hdcImage,
0, 0, bmp.bmWidth, bmp.bmHeight, 0, 0, bmp.bmWidth, bmp.bmHeight,
@ -2280,7 +2198,6 @@ ImageList_Replace (HIMAGELIST himl, INT i, HBITMAP hbmImage,
} }
DeleteDC (hdcImage); DeleteDC (hdcImage);
DeleteDC (hdcImageList);
return TRUE; return TRUE;
} }
@ -2304,10 +2221,10 @@ ImageList_Replace (HIMAGELIST himl, INT i, HBITMAP hbmImage,
INT WINAPI INT WINAPI
ImageList_ReplaceIcon (HIMAGELIST himl, INT i, HICON hIcon) ImageList_ReplaceIcon (HIMAGELIST himl, INT i, HICON hIcon)
{ {
HDC hdcImageList, hdcImage; HDC hdcImage;
INT nIndex; INT nIndex;
HICON hBestFitIcon; HICON hBestFitIcon;
HBITMAP hbmOldSrc, hbmOldDst; HBITMAP hbmOldSrc;
ICONINFO ii; ICONINFO ii;
BITMAP bmp; BITMAP bmp;
@ -2340,37 +2257,28 @@ ImageList_ReplaceIcon (HIMAGELIST himl, INT i, HICON hIcon)
else else
nIndex = i; nIndex = i;
hdcImageList = CreateCompatibleDC (0);
TRACE("hdcImageList=%p!\n", hdcImageList);
if (hdcImageList == 0)
ERR("invalid hdcImageList!\n");
hdcImage = CreateCompatibleDC (0); hdcImage = CreateCompatibleDC (0);
TRACE("hdcImage=%p!\n", hdcImage); TRACE("hdcImage=%p\n", hdcImage);
if (hdcImage == 0) if (hdcImage == 0)
ERR("invalid hdcImage!\n"); ERR("invalid hdcImage!\n");
hbmOldDst = SelectObject (hdcImageList, himl->hbmImage); SetTextColor(himl->hdcImage, RGB(0,0,0));
SetTextColor( hdcImageList, RGB(0,0,0)); SetBkColor (himl->hdcImage, RGB(255,255,255));
SetBkColor( hdcImageList, RGB(255,255,255));
hbmOldSrc = SelectObject (hdcImage, ii.hbmColor); hbmOldSrc = SelectObject (hdcImage, ii.hbmColor);
StretchBlt (hdcImageList, nIndex * himl->cx, 0, himl->cx, himl->cy,
StretchBlt (himl->hdcImage, nIndex * himl->cx, 0, himl->cx, himl->cy,
hdcImage, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY); hdcImage, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY);
if (himl->hbmMask) { if (himl->hbmMask) {
SelectObject (hdcImageList, himl->hbmMask);
SelectObject (hdcImage, ii.hbmMask); SelectObject (hdcImage, ii.hbmMask);
StretchBlt (hdcImageList, nIndex * himl->cx, 0, himl->cx, himl->cy, StretchBlt (himl->hdcMask, nIndex * himl->cx, 0, himl->cx, himl->cy,
hdcImage, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY); hdcImage, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY);
} }
SelectObject (hdcImage, hbmOldSrc); SelectObject (hdcImage, hbmOldSrc);
SelectObject (hdcImageList, hbmOldDst);
if(hBestFitIcon) if(hBestFitIcon)
DestroyIcon(hBestFitIcon); DestroyIcon(hBestFitIcon);
if (hdcImageList)
DeleteDC (hdcImageList);
if (hdcImage) if (hdcImage)
DeleteDC (hdcImage); DeleteDC (hdcImage);
if (ii.hbmColor) if (ii.hbmColor)
@ -2555,6 +2463,7 @@ BOOL WINAPI
ImageList_SetIconSize (HIMAGELIST himl, INT cx, INT cy) ImageList_SetIconSize (HIMAGELIST himl, INT cx, INT cy)
{ {
INT nCount; INT nCount;
HBITMAP hbmNew;
if (!is_valid(himl)) if (!is_valid(himl))
return FALSE; return FALSE;
@ -2569,16 +2478,18 @@ ImageList_SetIconSize (HIMAGELIST himl, INT cx, INT cy)
for (nCount = 0; nCount < MAX_OVERLAYIMAGE; nCount++) for (nCount = 0; nCount < MAX_OVERLAYIMAGE; nCount++)
himl->nOvlIdx[nCount] = -1; himl->nOvlIdx[nCount] = -1;
DeleteObject (himl->hbmImage); hbmNew = CreateBitmap (himl->cMaxImage * himl->cx, himl->cy,
himl->hbmImage =
CreateBitmap (himl->cMaxImage * himl->cx, himl->cy,
1, himl->uBitsPixel, NULL); 1, himl->uBitsPixel, NULL);
SelectObject (himl->hdcImage, hbmNew);
DeleteObject (himl->hbmImage);
himl->hbmImage = hbmNew;
if (himl->hbmMask) { if (himl->hbmMask) {
DeleteObject (himl->hbmMask); hbmNew = CreateBitmap (himl->cMaxImage * himl->cx, himl->cy,
himl->hbmMask =
CreateBitmap (himl->cMaxImage * himl->cx, himl->cy,
1, 1, NULL); 1, 1, NULL);
SelectObject (himl->hdcMask, hbmNew);
DeleteObject (himl->hbmMask);
himl->hbmMask = hbmNew;
} }
return TRUE; return TRUE;
@ -2602,7 +2513,7 @@ ImageList_SetIconSize (HIMAGELIST himl, INT cx, INT cy)
BOOL WINAPI BOOL WINAPI
ImageList_SetImageCount (HIMAGELIST himl, INT iImageCount) ImageList_SetImageCount (HIMAGELIST himl, INT iImageCount)
{ {
HDC hdcImageList, hdcBitmap; HDC hdcBitmap;
HBITMAP hbmNewBitmap; HBITMAP hbmNewBitmap;
INT nNewCount, nCopyCount; INT nNewCount, nCopyCount;
@ -2621,19 +2532,17 @@ ImageList_SetImageCount (HIMAGELIST himl, INT iImageCount)
nNewCount = iImageCount + himl->cGrow; nNewCount = iImageCount + himl->cGrow;
nCopyCount = min(himl->cCurImage, iImageCount); nCopyCount = min(himl->cCurImage, iImageCount);
hdcImageList = CreateCompatibleDC (0);
hdcBitmap = CreateCompatibleDC (0); hdcBitmap = CreateCompatibleDC (0);
hbmNewBitmap = CreateBitmap (nNewCount * himl->cx, himl->cy, hbmNewBitmap = CreateBitmap (nNewCount * himl->cx, himl->cy,
1, himl->uBitsPixel, NULL); 1, himl->uBitsPixel, NULL);
if (hbmNewBitmap != 0) if (hbmNewBitmap != 0)
{ {
SelectObject (hdcImageList, himl->hbmImage);
SelectObject (hdcBitmap, hbmNewBitmap); SelectObject (hdcBitmap, hbmNewBitmap);
/* copy images */ /* copy images */
BitBlt (hdcBitmap, 0, 0, nCopyCount * himl->cx, himl->cy, BitBlt (hdcBitmap, 0, 0, nCopyCount * himl->cx, himl->cy,
hdcImageList, 0, 0, SRCCOPY); himl->hdcImage, 0, 0, SRCCOPY);
#if 0 #if 0
/* delete 'empty' image space */ /* delete 'empty' image space */
SetBkColor (hdcBitmap, RGB(255, 255, 255)); SetBkColor (hdcBitmap, RGB(255, 255, 255));
@ -2641,6 +2550,7 @@ ImageList_SetImageCount (HIMAGELIST himl, INT iImageCount)
PatBlt (hdcBitmap, nCopyCount * himl->cx, 0, PatBlt (hdcBitmap, nCopyCount * himl->cx, 0,
(nNewCount - nCopyCount) * himl->cx, himl->cy, BLACKNESS); (nNewCount - nCopyCount) * himl->cx, himl->cy, BLACKNESS);
#endif #endif
SelectObject (himl->hdcImage, hbmNewBitmap);
DeleteObject (himl->hbmImage); DeleteObject (himl->hbmImage);
himl->hbmImage = hbmNewBitmap; himl->hbmImage = hbmNewBitmap;
} }
@ -2653,12 +2563,11 @@ ImageList_SetImageCount (HIMAGELIST himl, INT iImageCount)
1, 1, NULL); 1, 1, NULL);
if (hbmNewBitmap != 0) if (hbmNewBitmap != 0)
{ {
SelectObject (hdcImageList, himl->hbmMask);
SelectObject (hdcBitmap, hbmNewBitmap); SelectObject (hdcBitmap, hbmNewBitmap);
/* copy images */ /* copy images */
BitBlt (hdcBitmap, 0, 0, nCopyCount * himl->cx, himl->cy, BitBlt (hdcBitmap, 0, 0, nCopyCount * himl->cx, himl->cy,
hdcImageList, 0, 0, SRCCOPY); himl->hdcMask, 0, 0, SRCCOPY);
#if 0 #if 0
/* delete 'empty' image space */ /* delete 'empty' image space */
SetBkColor (hdcBitmap, RGB(255, 255, 255)); SetBkColor (hdcBitmap, RGB(255, 255, 255));
@ -2666,6 +2575,7 @@ ImageList_SetImageCount (HIMAGELIST himl, INT iImageCount)
PatBlt (hdcBitmap, nCopyCount * himl->cx, 0, PatBlt (hdcBitmap, nCopyCount * himl->cx, 0,
(nNewCount - nCopyCount) * himl->cx, himl->cy, BLACKNESS); (nNewCount - nCopyCount) * himl->cx, himl->cy, BLACKNESS);
#endif #endif
SelectObject (himl->hdcMask, hbmNewBitmap);
DeleteObject (himl->hbmMask); DeleteObject (himl->hbmMask);
himl->hbmMask = hbmNewBitmap; himl->hbmMask = hbmNewBitmap;
} }
@ -2673,7 +2583,6 @@ ImageList_SetImageCount (HIMAGELIST himl, INT iImageCount)
ERR("Could not create new mask bitmap!\n"); ERR("Could not create new mask bitmap!\n");
} }
DeleteDC (hdcImageList);
DeleteDC (hdcBitmap); DeleteDC (hdcBitmap);
/* Update max image count and current image count */ /* Update max image count and current image count */

View File

@ -29,28 +29,29 @@
/* the ones with offsets at the end are the same as in Windows */ /* the ones with offsets at the end are the same as in Windows */
struct _IMAGELIST struct _IMAGELIST
{ {
DWORD magic; /* 00: 'SAMX' */ DWORD magic; /* 00: 'SAMX' */
INT cCurImage; /* 04: ImageCount */ INT cCurImage; /* 04: ImageCount */
INT cMaxImage; /* 08: maximages */ INT cMaxImage; /* 08: maximages */
DWORD x3; INT cGrow; /* 0c: cGrow */
INT cx; /* 10: cx */ INT cx; /* 10: cx */
INT cy; /* 14: cy */ INT cy; /* 14: cy */
DWORD x4; DWORD x4;
UINT flags; /* 1c: flags */ UINT flags; /* 1c: flags */
DWORD x5; COLORREF clrFg; /* 20: foreground color */
COLORREF clrBk; /* 24: bkcolor */ COLORREF clrBk; /* 24: backgournd color */
HBITMAP hbmImage; /* 30: images Bitmap */
HBITMAP hbmMask; /* 34: masks Bitmap */
HDC hdcImage; /* 38: images MemDC */
HDC hdcMask; /* 3C: masks MemDC */
INT nOvlIdx[15]; /* 40: overlay images index */
/* not yet found out */ /* not yet found out */
HBITMAP hbmImage;
HBITMAP hbmMask;
HBRUSH hbrBlend25; HBRUSH hbrBlend25;
HBRUSH hbrBlend50; HBRUSH hbrBlend50;
COLORREF clrFg;
INT cInitial; INT cInitial;
INT cGrow;
UINT uBitsPixel; UINT uBitsPixel;
INT nOvlIdx[15];
}; };
#define IMAGELIST_MAGIC 0x53414D58 #define IMAGELIST_MAGIC 0x53414D58