void TransparentCDC(CDC *pDstDC, CRect rtTran, COLORREF clrSrc)
{
int nSavedDC = pDstDC->SaveDC();
int nWidth = rtTran.Width();
int nHeight = rtTran.Height();
CDC bmpDC;
bmpDC.CreateCompatibleDC(pDstDC);
CBitmap bmp ;
bmp.CreateCompatibleBitmap(pDstDC , nWidth , nHeight);
CBitmap* pOldBmp = (CBitmap*)bmpDC.SelectObject(&bmp);
bmpDC.BitBlt(0 , 0 , nWidth , nHeight , pDstDC , rtTran.left , rtTran.top , SRCCOPY);
//获取bmpDC中的图形数据到BYTE数组
HDC hDIBDC = CreateCompatibleDC(NULL);
BITMAPINFO hdr;
ZeroMemory(&hdr , sizeof(BITMAPINFO));
hdr.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
hdr.bmiHeader.biWidth = nWidth;
hdr.bmiHeader.biHeight = nHeight;
hdr.bmiHeader.biPlanes = 1;
hdr.bmiHeader.biBitCount = 32;
BYTE * pbtPixels = NULL ;
HBITMAP hDIBitmap = CreateDIBSection(hDIBDC,
(BITMAPINFO *)&hdr,
DIB_RGB_COLORS,
(void **)&pbtPixels,
NULL,
0);
HBITMAP hOldBmp = (HBITMAP)SelectObject(hDIBDC, hDIBitmap);
BitBlt(hDIBDC,0,0,nWidth,nHeight,bmpDC,0,0,SRCCOPY);
SelectObject(hDIBDC, hOldBmp);
BYTE btSR = GetRValue(clrSrc);
BYTE btSG = GetGValue(clrSrc);
BYTE btSB = GetBValue(clrSrc);
//对BYTE数组进行Alpha混和
const int nPixelSize = 4 ;
int iPos = 0;
for(int i = 0 ; i < nHeight ; i ++)
{
for(int j = 0 ; j < nWidth ; j ++)
{
iPos += nPixelSize;
BYTE btB = pbtPixels[iPos];
BYTE btG = pbtPixels[iPos+1];
BYTE btR = pbtPixels[iPos+2];
btB = (btSB + btB ) >> 1;
btG = (btSG + btG ) >> 1;
btR = (btSR + btR ) >> 1;
pbtPixels[iPos] = btB;
pbtPixels[iPos+1] = btG;
pbtPixels[iPos+2] = btR;
}
}
//绘制最终半透明图形到目标区域
SetDIBitsToDevice(pDstDC->GetSafeHdc(),
rtTran.left,
rtTran.top,
nWidth,nHeight,
0,0,0,nHeight,
(void*)pbtPixels,
(BITMAPINFO*)&hdr,
DIB_RGB_COLORS);
bmpDC.SelectObject(pOldBmp);
bmp.Detach();
delete [] pbtPixels ;
DeleteObject(hDIBDC);
pDstDC->RestoreDC(nSavedDC);
}
void MFC_2D::drawTransparentBmp(CDC* io_pdcDest, CBitmap& i_bmpSrc, const CRect& i_rtDest,
const CRect& i_rtSrc,LPCOLORREF i_pTransparentColor)
{
CDC dcSrc;
dcSrc.CreateCompatibleDC(io_pdcDest);
CBitmap* pOldBitmap = dcSrc.SelectObject(&i_bmpSrc);
int nWidthDest = i_rtDest.Width();
int nHeightDest = i_rtDest.Height();
int nWidthSrc = i_rtSrc.Width();
int nHeightSrc = i_rtDest.Height();
HBITMAP hOldImageBMP, hImageBMP = CreateCompatibleBitmap(*io_pdcDest, nWidthDest, nHeightDest); // 创建兼容位图
HBITMAP hOldMaskBMP, hMaskBMP = CreateBitmap(nWidthDest, nHeightDest, 1, 1, NULL); // 创建单色掩码位图
HDC hImageDC = CreateCompatibleDC(*io_pdcDest);
HDC hMaskDC = CreateCompatibleDC(*io_pdcDest);
hOldImageBMP = (HBITMAP)SelectObject(hImageDC, hImageBMP);
hOldMaskBMP = (HBITMAP)SelectObject(hMaskDC, hMaskBMP);
将源DC中的位图拷贝到临时DC中
if (nWidthDest == nWidthSrc && nHeightDest == nHeightSrc)
BitBlt(hImageDC, 0, 0, nWidthDest, nHeightDest, dcSrc, i_rtSrc.left,i_rtSrc.top, SRCCOPY);
else
StretchBlt(hImageDC, 0, 0, nWidthDest, nHeightDest,
dcSrc, i_rtSrc.left,i_rtSrc.top, nWidthSrc, nHeightSrc, SRCCOPY);
// 设置透明色
if( NULL != i_pTransparentColor)
SetBkColor(hImageDC, *i_pTransparentColor);
else
{
COLORREF col = dcSrc.GetPixel(0,0);
SetBkColor(hImageDC, col);
}
// 生成透明区域为白色,其它区域为黑色的掩码位图
BitBlt(hMaskDC, 0, 0, nWidthDest, nHeightDest, hImageDC, 0, 0, SRCCOPY);
// 生成透明区域为黑色,其它区域保持不变的位图
SetBkColor(hImageDC, RGB(0,0,0));
SetTextColor(hImageDC, RGB(255,255,255));
BitBlt(hImageDC, 0, 0, nWidthDest, nHeightDest, hMaskDC, 0, 0, SRCAND);
// 透明部分保持屏幕不变,其它部分变成黑色
SetBkColor(*io_pdcDest,RGB(255,255,255));
SetTextColor(*io_pdcDest,RGB(0,0,0));
BitBlt(*io_pdcDest, i_rtDest.left,i_rtDest.top, nWidthDest, nHeightDest, hMaskDC, 0, 0, SRCAND);
// "或"运算,生成最终效果
BitBlt(*io_pdcDest, i_rtDest.left,i_rtDest.top, nWidthDest, nHeightDest, hImageDC, 0, 0, SRCPAINT);
//清空
dcSrc.SelectObject(pOldBitmap);
SelectObject(hImageDC, hOldImageBMP);
DeleteDC(hImageDC);
SelectObject(hMaskDC, hOldMaskBMP);
DeleteDC(hMaskDC);
DeleteObject(hImageBMP);
DeleteObject(hMaskBMP);
}