创建不规则窗口的三种方式
1. 通过区域相关 API 设置窗口的区域 SetWindowRgn;;
2. 通过 SetLayeredWindowAttributes 来指定特殊的透明颜色,让背景图的部分位置全透从而实现窗口的 "不规则";
3. 通过 UpdateLayeredWindow 来指定特殊颜色透明或者根据图片的 ALPHA 值来设置窗口全透。
我们的不规则形状由此而来。这个函数和它的朋友们十分强大,不仅可以定义独立的基本形状的区 域,还可以通过运算(CombineRgn:可对两个区域进行交集、拷贝、相减、异或运算)来组合已有区域从而产生新的区域。
- if( *(DWORD*)(&pDest[i*4]) == mask ) {
- pDest[i*4] = (BYTE)0;
- pDest[i*4 + 1] = (BYTE)0;
- pDest[i*4 + 2] = (BYTE)0;
- pDest[i*4 + 3] = (BYTE)0;
- bAlphaChannel = true;
- }
- // data : 加载的图片资源
- if( !data ) return NULL;
- if( type != NULL ) data->sResType = type;
- data->dwMask = mask;
- if( !m_mImageHash.Insert(bitmap, data) ) {// 缓存提速
- ::DeleteObject(data->hBitmap);
- delete data;
- data = NULL;
- }
- static LPALPHABLEND lpAlphaBlend = (LPALPHABLEND) : :GetProcAddress(: :GetModuleHandle(_T("msimg32.dll")), "AlphaBlend");........
- if (lpAlphaBlend && (alphaChannel || uFade < 255)) {
- // uFade:设置背景图片透明度; alphaChannel:启用指定颜色(Mask)透明
- BLENDFUNCTION bf = {
- AC_SRC_OVER,
- 0,
- uFade,
- AC_SRC_ALPHA
- };
- if (lpAlphaBlend == NULL) lpAlphaBlend = AlphaBitBlt;
- ........
- // Alpha混合贴图
- lpAlphaBlend(hDC, lDestLeft, rcDest.top, lDestRight - lDestLeft, rcDest.bottom, hCloneDC, rcBmpPart.left + rcCorners.left, rcBmpPart.top + rcCorners.top, lDrawWidth, rcBmpPart.bottom - rcBmpPart.top - rcCorners.top - rcCorners.bottom, bf);
- void CControlUI::DoPaint(HDC hDC, const RECT& rcPaint)
- {
- if( !::IntersectRect(&m_rcPaint, &rcPaint, &m_rcItem) ) return;
- // 绘制循序:背景颜色->背景图->状态图->文本->边框
- if( m_cxyBorderRound.cx > 0 || m_cxyBorderRound.cy > 0 ) {
- CRenderClip roundClip;
- // CRenderClip内部以SetWindowRgn()函数对绘制区域进行控制
- CRenderClip::GenerateRoundClip(hDC, m_rcPaint, m_rcItem, m_cxyBorderRound.cx, m_cxyBorderRound.cy, roundClip);
- PaintBkColor(hDC);
- PaintBkImage(hDC);// 调用渲染引擎绘制背景图片
- PaintStatusImage(hDC);
- PaintText(hDC);
- PaintBorder(hDC);
- }
- else {
- PaintBkColor(hDC);
- PaintBkImage(hDC);
- PaintStatusImage(hDC);
- PaintText(hDC);
- PaintBorder(hDC);
- }
- }
- BLENDFUNCTION blendPixelFunction = {
- AC_SRC_OVER,
- 0,
- m_nOpacity,
- AC_SRC_ALPHA
- };
- BOOL bRet = ::UpdateLayeredWindow(m_hWndPaint, NULL, &pt, &szWindow, m_hDcOffscreen, &ptSrc, 0, &blendPixelFunction, ULW_ALPHA);
来源: http://www.bubuko.com/infodetail-1978910.html