📄 imagelist.c
字号:
hdcOffScreen, origNewX - origRegX, origNewY - origRegY, SRCCOPY);
/* draw the image */
ImageList_InternalDragDraw(hdcOffScreen, origNewX - origRegX,
origNewY - origRegY);
/* draw the update region to the screen */
BitBlt(hdcDrag, origRegX, origRegY, sizeRegX, sizeRegY,
hdcOffScreen, 0, 0, SRCCOPY);
DeleteDC(hdcBg);
DeleteDC(hdcOffScreen);
DeleteObject(hbmOffScreen);
ReleaseDC(InternalDrag.hwnd, hdcDrag);
}
/* update the image position */
InternalDrag.x = x;
InternalDrag.y = y;
return TRUE;
}
/*************************************************************************
* ImageList_DragShowNolock [COMCTL32.@]
*
* Shows or hides the drag image.
*
* PARAMS
* bShow [I] TRUE shows the drag image, FALSE hides it.
*
* RETURNS
* Success: TRUE
* Failure: FALSE
*
* BUGS
* The drag image should be drawn semitransparent.
*/
BOOL WINAPI
ImageList_DragShowNolock (BOOL bShow)
{
HDC hdcDrag;
HDC hdcBg;
INT x, y;
if (!is_valid(InternalDrag.himl))
return FALSE;
TRACE("bShow=0x%X!\n", bShow);
/* DragImage is already visible/hidden */
if ((InternalDrag.bShow && bShow) || (!InternalDrag.bShow && !bShow)) {
return FALSE;
}
/* position of the origin of the DragImage */
x = InternalDrag.x - InternalDrag.dxHotspot;
y = InternalDrag.y - InternalDrag.dyHotspot;
hdcDrag = GetDCEx (InternalDrag.hwnd, 0,
DCX_WINDOW | DCX_CACHE | DCX_LOCKWINDOWUPDATE);
if (!hdcDrag) {
return FALSE;
}
hdcBg = CreateCompatibleDC(hdcDrag);
if (!InternalDrag.hbmBg) {
InternalDrag.hbmBg = CreateCompatibleBitmap(hdcDrag,
InternalDrag.himl->cx, InternalDrag.himl->cy);
}
SelectObject(hdcBg, InternalDrag.hbmBg);
if (bShow) {
/* save the background */
BitBlt(hdcBg, 0, 0, InternalDrag.himl->cx, InternalDrag.himl->cy,
hdcDrag, x, y, SRCCOPY);
/* show the image */
ImageList_InternalDragDraw(hdcDrag, x, y);
} else {
/* hide the image */
BitBlt(hdcDrag, x, y, InternalDrag.himl->cx, InternalDrag.himl->cy,
hdcBg, 0, 0, SRCCOPY);
}
InternalDrag.bShow = !InternalDrag.bShow;
DeleteDC(hdcBg);
ReleaseDC (InternalDrag.hwnd, hdcDrag);
return TRUE;
}
/*************************************************************************
* ImageList_Draw [COMCTL32.@]
*
* Draws an image.
*
* PARAMS
* himl [I] handle to image list
* i [I] image index
* hdc [I] handle to device context
* x [I] x position
* y [I] y position
* fStyle [I] drawing flags
*
* RETURNS
* Success: TRUE
* Failure: FALSE
*
* SEE
* ImageList_DrawEx.
*/
BOOL WINAPI
ImageList_Draw (HIMAGELIST himl, INT i, HDC hdc, INT x, INT y, UINT fStyle)
{
return ImageList_DrawEx (himl, i, hdc, x, y, 0, 0,
CLR_DEFAULT, CLR_DEFAULT, fStyle);
}
/*************************************************************************
* ImageList_DrawEx [COMCTL32.@]
*
* Draws an image and allows to use extended drawing features.
*
* PARAMS
* himl [I] handle to image list
* i [I] image index
* hdc [I] handle to device context
* x [I] X position
* y [I] Y position
* dx [I] X offset
* dy [I] Y offset
* rgbBk [I] background color
* rgbFg [I] foreground color
* fStyle [I] drawing flags
*
* RETURNS
* Success: TRUE
* Failure: FALSE
*
* NOTES
* Calls ImageList_DrawIndirect.
*
* SEE
* ImageList_DrawIndirect.
*/
BOOL WINAPI
ImageList_DrawEx (HIMAGELIST himl, INT i, HDC hdc, INT x, INT y,
INT dx, INT dy, COLORREF rgbBk, COLORREF rgbFg,
UINT fStyle)
{
IMAGELISTDRAWPARAMS imldp;
ZeroMemory (&imldp, sizeof(imldp));
imldp.cbSize = sizeof(imldp);
imldp.himl = himl;
imldp.i = i;
imldp.hdcDst = hdc,
imldp.x = x;
imldp.y = y;
imldp.cx = dx;
imldp.cy = dy;
imldp.rgbBk = rgbBk;
imldp.rgbFg = rgbFg;
imldp.fStyle = fStyle;
return ImageList_DrawIndirect (&imldp);
}
/*************************************************************************
* ImageList_DrawIndirect [COMCTL32.@]
*
* Draws an image using various parameters specified in pimldp.
*
* PARAMS
* pimldp [I] pointer to IMAGELISTDRAWPARAMS structure.
*
* RETURNS
* Success: TRUE
* Failure: FALSE
*/
BOOL WINAPI
ImageList_DrawIndirect (IMAGELISTDRAWPARAMS *pimldp)
{
INT cx, cy, nOvlIdx;
DWORD fState, dwRop;
UINT fStyle;
COLORREF oldImageBk, oldImageFg;
HDC hImageDC, hImageListDC, hMaskListDC;
HBITMAP hImageBmp, hOldImageBmp, hBlendMaskBmp;
BOOL bIsTransparent, bBlend, bResult = FALSE, bMask;
HIMAGELIST himl;
POINT pt;
if (!pimldp || !(himl = pimldp->himl)) return FALSE;
if (!is_valid(himl)) return FALSE;
if ((pimldp->i < 0) || (pimldp->i >= himl->cCurImage)) return FALSE;
imagelist_point_from_index( himl, pimldp->i, &pt );
pt.x += pimldp->xBitmap;
pt.y += pimldp->yBitmap;
fState = pimldp->cbSize < sizeof(IMAGELISTDRAWPARAMS) ? ILS_NORMAL : pimldp->fState;
fStyle = pimldp->fStyle & ~ILD_OVERLAYMASK;
cx = (pimldp->cx == 0) ? himl->cx : pimldp->cx;
cy = (pimldp->cy == 0) ? himl->cy : pimldp->cy;
bIsTransparent = (fStyle & ILD_TRANSPARENT);
if( pimldp->rgbBk == CLR_NONE )
bIsTransparent = TRUE;
if( ( pimldp->rgbBk == CLR_DEFAULT ) && ( himl->clrBk == CLR_NONE ) )
bIsTransparent = TRUE;
bMask = (himl->flags & ILC_MASK) && (fStyle & ILD_MASK) ;
bBlend = (fStyle & (ILD_BLEND25 | ILD_BLEND50) ) && !bMask;
TRACE("himl(%p) hbmMask(%p) iImage(%d) x(%d) y(%d) cx(%d) cy(%d)\n",
himl, himl->hbmMask, pimldp->i, pimldp->x, pimldp->y, cx, cy);
/* we will use these DCs to access the images and masks in the ImageList */
hImageListDC = himl->hdcImage;
hMaskListDC = himl->hdcMask;
/* these will accumulate the image and mask for the image we're drawing */
hImageDC = CreateCompatibleDC( pimldp->hdcDst );
hImageBmp = CreateCompatibleBitmap( pimldp->hdcDst, cx, cy );
hBlendMaskBmp = bBlend ? CreateBitmap(cx, cy, 1, 1, NULL) : 0;
/* Create a compatible DC. */
if (!hImageListDC || !hImageDC || !hImageBmp ||
(bBlend && !hBlendMaskBmp) || (himl->hbmMask && !hMaskListDC))
goto cleanup;
hOldImageBmp = SelectObject(hImageDC, hImageBmp);
/*
* To obtain a transparent look, background color should be set
* to white and foreground color to black when blting the
* monochrome mask.
*/
oldImageFg = SetTextColor( hImageDC, RGB( 0, 0, 0 ) );
oldImageBk = SetBkColor( hImageDC, RGB( 0xff, 0xff, 0xff ) );
/*
* Draw the initial image
*/
if( bMask ) {
if (himl->hbmMask) {
HBRUSH hOldBrush;
hOldBrush = SelectObject (hImageDC, CreateSolidBrush (GetTextColor(pimldp->hdcDst)));
PatBlt( hImageDC, 0, 0, cx, cy, PATCOPY );
BitBlt(hImageDC, 0, 0, cx, cy, hMaskListDC, pt.x, pt.y, SRCPAINT);
DeleteObject (SelectObject (hImageDC, hOldBrush));
if( bIsTransparent )
{
BitBlt ( pimldp->hdcDst, pimldp->x, pimldp->y, cx, cy, hImageDC, 0, 0, SRCAND);
bResult = TRUE;
goto end;
}
} else {
HBRUSH hOldBrush = SelectObject (hImageDC, GetStockObject(BLACK_BRUSH));
PatBlt( hImageDC, 0, 0, cx, cy, PATCOPY);
SelectObject(hImageDC, hOldBrush);
}
} else {
/* blend the image with the needed solid background */
COLORREF colour = RGB(0,0,0);
HBRUSH hOldBrush;
if( !bIsTransparent )
{
colour = pimldp->rgbBk;
if( colour == CLR_DEFAULT )
colour = himl->clrBk;
if( colour == CLR_NONE )
colour = GetBkColor(pimldp->hdcDst);
}
hOldBrush = SelectObject (hImageDC, CreateSolidBrush (colour));
PatBlt( hImageDC, 0, 0, cx, cy, PATCOPY );
BitBlt( hImageDC, 0, 0, cx, cy, hMaskListDC, pt.x, pt.y, SRCAND );
BitBlt( hImageDC, 0, 0, cx, cy, hImageListDC, pt.x, pt.y, SRCPAINT );
DeleteObject (SelectObject (hImageDC, hOldBrush));
}
/* Time for blending, if required */
if (bBlend) {
HBRUSH hBlendBrush, hOldBrush;
COLORREF clrBlend = pimldp->rgbFg;
HDC hBlendMaskDC = hImageListDC;
HBITMAP hOldBitmap;
/* Create the blend Mask */
hOldBitmap = SelectObject(hBlendMaskDC, hBlendMaskBmp);
hBlendBrush = fStyle & ILD_BLEND50 ? himl->hbrBlend50 : himl->hbrBlend25;
hOldBrush = (HBRUSH) SelectObject(hBlendMaskDC, hBlendBrush);
PatBlt(hBlendMaskDC, 0, 0, cx, cy, PATCOPY);
SelectObject(hBlendMaskDC, hOldBrush);
/* Modify the blend mask if an Image Mask exist */
if(himl->hbmMask) {
BitBlt(hBlendMaskDC, 0, 0, cx, cy, hMaskListDC, pt.x, pt.y, 0x220326); /* NOTSRCAND */
BitBlt(hBlendMaskDC, 0, 0, cx, cy, hBlendMaskDC, 0, 0, NOTSRCCOPY);
}
/* now apply blend to the current image given the BlendMask */
if (clrBlend == CLR_DEFAULT) clrBlend = GetSysColor (COLOR_HIGHLIGHT);
else if (clrBlend == CLR_NONE) clrBlend = GetTextColor (pimldp->hdcDst);
hOldBrush = (HBRUSH) SelectObject (hImageDC, CreateSolidBrush(clrBlend));
BitBlt (hImageDC, 0, 0, cx, cy, hBlendMaskDC, 0, 0, 0xB8074A); /* PSDPxax */
DeleteObject(SelectObject(hImageDC, hOldBrush));
SelectObject(hBlendMaskDC, hOldBitmap);
}
/* Now do the overlay image, if any */
nOvlIdx = (pimldp->fStyle & ILD_OVERLAYMASK) >> 8;
if ( (nOvlIdx >= 1) && (nOvlIdx <= MAX_OVERLAYIMAGE)) {
nOvlIdx = himl->nOvlIdx[nOvlIdx - 1];
if ((nOvlIdx >= 0) && (nOvlIdx < himl->cCurImage)) {
POINT ptOvl;
imagelist_point_from_index( himl, nOvlIdx, &ptOvl );
ptOvl.x += pimldp->xBitmap;
if (himl->hbmMask && !(fStyle & ILD_IMAGE))
BitBlt (hImageDC, 0, 0, cx, cy, hMaskListDC, ptOvl.x, ptOvl.y, SRCAND);
BitBlt (hImageDC, 0, 0, cx, cy, hImageListDC, ptOvl.x, ptOvl.y, SRCPAINT);
}
}
if (fState & ILS_SATURATE) FIXME("ILS_SATURATE: unimplemented!\n");
if (fState & ILS_GLOW) FIXME("ILS_GLOW: unimplemented!\n");
if (fState & ILS_SHADOW) FIXME("ILS_SHADOW: unimplemented!\n");
if (fState & ILS_ALPHA) FIXME("ILS_ALPHA: unimplemented!\n");
if (fStyle & ILD_PRESERVEALPHA) FIXME("ILD_PRESERVEALPHA: unimplemented!\n");
if (fStyle & ILD_SCALE) FIXME("ILD_SCALE: unimplemented!\n");
if (fStyle & ILD_DPISCALE) FIXME("ILD_DPISCALE: unimplemented!\n");
/* now copy the image to the screen */
dwRop = SRCCOPY;
if (himl->hbmMask && bIsTransparent ) {
COLORREF oldDstFg = SetTextColor(pimldp->hdcDst, RGB( 0, 0, 0 ) );
COLORREF oldDstBk = SetBkColor(pimldp->hdcDst, RGB( 0xff, 0xff, 0xff ));
BitBlt (pimldp->hdcDst, pimldp->x, pimldp->y, cx, cy, hMaskListDC, pt.x, pt.y, SRCAND);
SetBkColor(pimldp->hdcDst, oldDstBk);
SetTextColor(pimldp->hdcDst, oldDstFg);
dwRop = SRCPAINT;
}
if (fStyle & ILD_ROP) dwRop = pimldp->dwRop;
BitBlt (pimldp->hdcDst, pimldp->x, pimldp->y, cx, cy, hImageDC, 0, 0, dwRop);
bResult = TRUE;
end:
/* cleanup the mess */
SetBkColor(hImageDC, oldImageBk);
SetTextColor(hImageDC, oldImageFg);
SelectObject(hImageDC, hOldImageBmp);
cleanup:
DeleteObject(hBlendMaskBmp);
DeleteObject(hImageBmp);
DeleteDC(hImageDC);
return bResult;
}
/*************************************************************************
* ImageList_Duplicate [COMCTL32.@]
*
* Duplicates an image list.
*
* PARAMS
* himlSrc [I] source image list handle
*
* RETURNS
* Success: Handle of duplicated image list.
* Failure: NULL
*/
HIMAGELIST WINAPI
ImageList_Duplicate (HIMAGELIST himlSrc)
{
HIMAGELIST himlDst;
if (!is_valid(himlSrc)) {
ERR("Invalid image list handle!\n");
return NULL;
}
himlDst = ImageList_Create (himlSrc->cx, himlSrc->cy, himlSrc->flags,
himlSrc->cInitial, himlSrc->cGrow);
if (himlDst)
{
SIZE sz;
imagelist_get_bitmap_size(himlSrc, himlSrc->cCurImage, himlSrc->cy, &sz);
BitBlt (himlDst->hdcImage, 0, 0, sz.cx, sz.cy,
himlSrc->hdcImage, 0, 0, SRCCOPY);
if (himlDst->hbmMask)
BitBlt (himlDst->hdcMask, 0, 0, sz.cx, sz.cy,
himlSrc->hdcMask, 0, 0, SRCCOPY);
himlDst->cCurImage = himlSrc->cCurImage;
himlDst->cMaxImage = himlSrc->cMaxImage;
}
return himlDst;
}
/*************************************************************************
* ImageList_EndDrag [COMCTL32.@]
*
* Finishes a drag operation.
*
* PARAMS
* no Parameters
*
* RETURNS
* Success: TRUE
* Failure: FALSE
*/
VOID WINAPI
ImageList_EndDrag (void)
{
/* cleanup the InternalDrag struct */
InternalDrag.hwnd = 0;
ImageList_Destroy (InternalDrag.himl);
InternalDrag.himl = 0;
InternalDrag.x= 0;
InternalDrag.y= 0;
InternalDrag.dxHotspot = 0;
InternalDrag.dyHotspot = 0;
InternalDrag.bShow = FALSE;
DeleteObject(InternalDrag.hbmBg);
InternalDrag.hbmBg = 0;
}
/*************************************************************************
* ImageList_GetBkColor [COMCTL32.@]
*
* Returns the background color of an image list.
*
* PARAMS
* himl [I] Image list handle.
*
* RETURNS
* Success: background color
* Failure: CLR_NONE
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -