65.9K
CodeProject 正在变化。 阅读更多。
Home

CDialogRegionT -为 WTL 对话框添加皮肤

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.83/5 (20投票s)

2006 年 9 月 8 日

CPOL

2分钟阅读

viewsIcon

64331

downloadIcon

2290

分 3 步为 WTL 对话框添加皮肤的最简单方法

CDialogRegionT - Sample Image

引言

在 WTL 对话框上添加皮肤或创建透明对话框遇到困难吗?从现在开始,你只需要编写三行代码!你可以创建与提供的位图形状相同的对话框,并具有透明功能。

背景

以前,如果你想为对话框添加皮肤,你必须处理 WM_ERASEBKGND 消息,然后自己编写绘制例程。

BEGIN_MSG_MAP(CMainDlg)
    MESSAGE_HANDLER(WM_ERASEBKGND, OnEraseBkGnd)

CDialogRegionT 模板承担了程序员的所有负担,并自行完成所有操作。 此模板类还处理其他一些消息,例如 WM_CTLCOLORSTATICWM_NCHITTEST。 在我们的例子中,处理 WM_NCHITTEST 消息允许我们通过单击对话框的任何位置来拖动对话框;这是通过在此例程中返回 HTCAPTION 来完成的。

LRESULT OnNCHitTest(UINT /*uMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, 
    BOOL& bHandled)
{
    // We handle this message only if we have set the region

    bHandled = m_bIsRgnSet;

    if(m_bDlgMove)    // check if we can move the dialog

    {
        return HTCAPTION;
    }
    else
    {
        return 0;
    }
}

使用代码

我尝试使代码的使用尽可能简单。 在将 DialogRegion.h 包含在你的 WTL 对话框类中后,你只需要遵循以下三个步骤

  1. CDialogRegionT 模板类继承 WTL 对话框。
    class CMainDlg : public CDialogImpl<CMainDlg>, public CUpdateUI<CMainDlg>,
        public CMessageFilter, public CIdleHandler, CDialogRegionT<CMainDlg>
    {
  2. 在消息映射中添加 CHAIN_MSG_MAP 条目,以将消息链接到此类。
  3.     BEGIN_MSG_MAP(CMainDlg)
            MESSAGE_HANDLER(WM_INITDIALOG, OnInitDialog)
            COMMAND_ID_HANDLER(ID_APP_ABOUT, OnAppAbout)
            COMMAND_ID_HANDLER(IDOK, OnOK)
            COMMAND_ID_HANDLER(IDCANCEL, OnCancel)
            CHAIN_MSG_MAP(CDialogRegionT<CMainDlg>)
        END_MSG_MAP()
  4. WM_INITDIALOG 例程中使用 SetBkBitmap 方法来指定皮肤文件。 SetBkBitmap 是一个重载函数,它接受要设置为透明的颜色(默认透明颜色为 RGB(255,0,255) )。

    • 如果你提供资源位图
      SetBKBitmap(IDB_BITMAP1);
      这里 IDB_BITMAP1 是位图资源标识符。

    • 如果你提供位图文件
      SetBKBitmap("MyBitmap.bmp");
      这里 MyBitmap.bmp 是生成的目标可执行文件目录中的位图文件名。

注意事项

在背景部分,我没有讨论 WM_CTLCOLORSTATIC 消息。 CDialogRegionT 模板类使用此消息来返回静态控件的颜色。 在我们的例子中,我们将使用任何颜色的位图,因此静态控件需要以透明方式绘制。 因此,当需要对静态控件进行着色时,我们将背景颜色设置为透明并返回空画笔。

LRESULT OnCtlColorStatic(UINT /*uMsg*/, WPARAM wParam, LPARAM lParam, 
    BOOL& bHandled)
{
    // We handle this message only if we have set the region

    bHandled = m_bIsRgnSet;

    if(m_bIsRgnSet)
    {
        ::SetBkMode((HDC)wParam, TRANSPARENT);
        return (LRESULT) GetStockObject (HOLLOW_BRUSH);
    }
    return 0;
}

我遇到一个问题:如果我添加了通用控件 6 的清单,静态控件将以黑色绘制。 因此,你必须**确保你没有在你的项目中使用的通用控件 6**。 你可以在使用 WTL 项目向导创建项目时选择不添加通用控件清单。 如果你已经有一个 WTL 项目,并且在添加 CDialogRegionT 类后使静态控件以黑色绘制,你可以从 .rc 文件中删除通用控件清单。

© . All rights reserved.