使用BM_SETIMAGE和SetWindowRgn的循环按钮

时间:2013-10-17 16:25:47

标签: visual-studio winapi visual-c++

我正在尝试创建一个圆形按钮。到目前为止,这是我的流程:

创建BS_BITMAP样式按钮:

hButton = CreateWindow(L"button",L"Label",WS_CHILD|WS_VISIBLE|BS_BITMAP,
               122,363,65,65,hWnd,(HMENU)BUTTON_ID,NULL,NULL);

使用LoadImage加载位图。位图是一个正方形,但我只想在中心显示圆圈(稍后会详细介绍):

buttonImage = (HBITMAP)LoadImage(hInstance,L"button.bmp",IMAGE_BITMAP,65,65, 
               LR_LOADFROMFILE|LR_CREATEDIBSECTION);

设置按钮的图像:

SendMessage(hButton,BM_SETIMAGE,IMAGE_BITMAP,(LPARAM)buttonImage);

为了只显示圆圈,我使用以下内容:

hButtonRgn = CreateEllipticRgn(0,0,65,65);
SetWindowRgn(hButton,hButtonRgn,TRUE);

请注意,我全局定义hButtonRgn并且不再使用它,因为SetWindowRgn的MSDN文档声明“系统拥有区域句柄hRgn指定的区域”。

问题在于:

按钮最初只显示为一个圆圈。但是,在单击并按住时,会出现完整的方形位图,圆圈周围有空白区域。但是,在发布时,只会再次显示圆圈。

以下是我尝试的解决方案:

单击该按钮后,立即重新显示按钮周围的主窗口。在主窗口的WndProc中,我执行以下操作:

case WM_PARENTNOTIFY:
    if ((int)wParam == WM_LBUTTONDOWN)
    {
        PAINTSTRUCT ps;
        BeginPaint(hWnd, &ps);
        pRenderTarget->BeginDraw();
        // paint the background surrounding the button in another function
        pRenderTarget->EndDraw();
        EndPaint(hWnd, &ps);
    }

但是,这没有明显的效果。释放鼠标后按钮显示为圆形,但在按住鼠标时显示为方形。

关于我哪里出错的任何想法?

1 个答案:

答案 0 :(得分:0)

您的重绘例程不正确。 BeginPaint()只应用于回复WM_PAINT消息 - 它会告诉您某些内容很脏并且需要重新绘制。你想要做的是触发这种机制,你这样做的方法是使用InvalidateRect()标记父窗口的适当区域进行重绘。

即使这确实改善了你的想法,我认为你最终会出现闪烁,这可能是不可接受的。您可以调查的另一个机制是使按钮所有者绘制,因为这样您就可以在同一步骤中将其绘制为圆形(并使父窗口无效)。