CWnd with transparent background

心已入冬 提交于 2019-12-11 10:45:37

问题


I'd like to create a CWnd based class that will introduce a control with transparent background.

There is no big deal for me to create a control and draw its content with transparent background as long as the content is static.

The problem is when I want to create a control with changing content. It's becaue I don't know how to erase content of control with parent's background (which in general case may not be just a solid color).

So the goal I want to achieve is to erase control before painting its conent as the control was never there (parent, and maybe other controls may appear), and than paint control in this place.


回答1:


Roel answer is fine if you want to create a top-level window. If you need to crate a child window (which must be the case if you are creating a control) you cannot use WS_EX_LAYERED (I think this has changed from Windows 8 on).

The easy trick is to draw parent as the control backgroud. So in the OnEraseBkgnd you can add this code:

BOOL uiBarcodeButton::OnEraseBkgnd(CDC* pDC)
{
    CRect rect;
    GetClientRect(rect);

    return afxGlobalData.DrawParentBackground( this, pDC, rect);
}

Not sure if afxGlobalData global variable is just for MFC 2008 Feature Pack. If you are using a previous version of MFCs then you can use the code from DrawParentBackground:

ASSERT_VALID(pDC);
ASSERT_VALID(pWnd);

BOOL bRes = FALSE;

CRgn rgn;
if (rectClip != NULL)
{
    rgn.CreateRectRgnIndirect(rectClip);
    pDC->SelectClipRgn(&rgn);
}

CWnd* pParent = pWnd->GetParent();
ASSERT_VALID(pParent);

// In Windows XP, we need to call DrawThemeParentBackground function to implement
// transparent controls
if (m_pfDrawThemeBackground != NULL)
{
    bRes = (*m_pfDrawThemeBackground)(pWnd->GetSafeHwnd(), pDC->GetSafeHdc(), rectClip) == S_OK;
}

if (!bRes)
{
    CPoint pt(0, 0);
    pWnd->MapWindowPoints(pParent, &pt, 1);
    pt = pDC->OffsetWindowOrg(pt.x, pt.y);

    bRes = (BOOL) pParent->SendMessage(WM_ERASEBKGND, (WPARAM)pDC->m_hDC);

    pDC->SetWindowOrg(pt.x, pt.y);
}

pDC->SelectClipRgn(NULL);

return bRes;



回答2:


You use WS_EX_LAYERED and the UpdateLayeredWindow() API to draw your window. See http://msdn.microsoft.com/en-us/library/ms997507.aspx .




回答3:


I used below code for my custom Static control:

BOOL MyStaticText::OnEraseBkgnd(CDC* pDC)
{
    CRect rect;
    GetClientRect(&rect);
    pDC->SelectObject((HBRUSH)GetStockObject(NULL_BRUSH));
    return pDC->PatBlt(0, 0, rect.Width(), rect.Height(), PATCOPY); 
}


来源:https://stackoverflow.com/questions/13684437/cwnd-with-transparent-background

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!