WEB开发网
开发学院软件开发VC MFC程序员WTL指南(5)对话框与控件 阅读

MFC程序员WTL指南(5)对话框与控件

 2008-01-18 20:24:13 来源:WEB开发网   
核心提示:该处理函数并未用到phdr参数,我将他强制转换成NMLISTVIEW*只是为了演示用法,MFC程序员WTL指南(5)对话框与控件(8),反射通知消息如果你是用CWindowImpl的派生类封装控件,比如前面使用的CEditImpl,和上面的代码一样处理TVN_ITEMEXPANDING消息,CMainDlg类的成员m_

该处理函数并未用到phdr参数,我将他强制转换成NMLISTVIEW*只是为了演示用法。

反射通知消息

如果你是用CWindowImpl的派生类封装控件,比如前面使用的CEditImpl,你可以在类的内部处理通知消息而不是在对话框中,这就是通知消息的反射,它和MFC的消息反射相似。不同的是在WTL中父窗口和控件都可以处理通知消息,而在MFC中只有控件能处理通知消息(译者加:除非你重载 WindowProc函数,在MFC反射这些消息之前截获它们)。

如果需要将通知消息反射给控件封装类,只需在对话框的消息映射链中添加REFLECT_NOTIFICATIONS()宏:

class CMainDlg : public ...
{
public:
   BEGIN_MSG_MAP_EX(CMainDlg)
     //...
     NOTIFY_HANDLER_EX(IDC_LIST, LVN_ITEMCHANGED, OnListItemchanged)
     REFLECT_NOTIFICATIONS()
   END_MSG_MAP()
};

这个宏向消息映射链添加了一些代码处理那些未被前面的宏处理的通知消息,它检查消息传递的HWND窗口句柄是否有效并将消息转发给这个窗口,当然,消息代码的数值被改变成OLE控件所使用的值,OLE控件有与之相似的消息反射系统。新的消息代码值用OCM_xxx代替了WM_xxx,但是消息的处理方式和未反射前一样。

有18中被反射的消息:

  • 控件通知消息: WM_COMMAND, WM_NOTIFY, WM_PARENTNOTIFY
  • 自画消息: WM_DRAWITEM, WM_MEASUREITEM, WM_COMPAREITEM, WM_DELETEITEM
  • List box 键盘消息: WM_VKEYTOITEM, WM_CHARTOITEM
  • 其它: WM_HSCROLL, WM_VSCROLL, WM_CTLCOLOR*

在你想添加反射消息处理的控件类内不要忘了使用DEFAULT_REFLECTION_HANDLER()宏,DEFAULT_REFLECTION_HANDLER()宏确保将未被处理的消息交给DefWindowProc()正确处理。 下面的例子是一个自画按钮类,它相应了从父窗口反射的WM_DRAWITEM消息。

class CODButtonImpl : public CWindowImpl<CODButtonImpl, CButton>
{
public:
   BEGIN_MSG_MAP_EX(CODButtonImpl)
     MSG_OCM_DRAWITEM(OnDrawItem)
     DEFAULT_REFLECTION_HANDLER()
   END_MSG_MAP()
   void OnDrawItem ( UINT idCtrl, LPDRAWITEMSTRUCT lpdis )
   {
     // do drawing here...
   }
};

用来处理反射消息的WTL宏

我们现在只看到了WTL的消息反射宏中的一个:MSG_OCM_DRAWITEM,还有17个这样的反射宏。由于WM_NOTIFY和WM_COMMAND消息带的参数需要展开,WTL提供了特殊的宏MSG_OCM_COMMAND和MSG_OCM_NOTIFY做这些事情。这些宏所作的工作与COMMAND_HANDLER_EX和NOTIFY_HANDLER_EX宏相同,只是前面加了“REFLECTED_”,例如,一个树控件类可能存在这样的消息映射链:

class CMyTreeCtrl : public CWindowImpl<CMyTreeCtrl, CTreeViewCtrl>
{
public:
  BEGIN_MSG_MAP_EX(CMyTreeCtrl)
   REFLECTED_NOTIFY_CODE_HANDLER_EX(TVN_ITEMEXPANDING, OnItemExpanding)
   DEFAULT_REFLECTION_HANDLER()
  END_MSG_MAP()
  LRESULT OnItemExpanding ( NMHDR* phdr );
};

在ControlMania1对话框中用了一个树控件,和上面的代码一样处理TVN_ITEMEXPANDING消息,CMainDlg类的成员m_wndTree使用DDX连接到控件上,CMainDlg反射通知消息,树控件的处理函数OnItemExpanding()是这样的:

LRESULT CBuffyTreeCtrl::OnItemExpanding ( NMHDR* phdr )
{
NMTREEVIEW* pnmtv = (NMTREEVIEW*) phdr;
   if ( pnmtv->action & TVE_COLLAPSE )
     return TRUE;  // don''t allow it
   else
     return FALSE;  // allow it
}

上一页  3 4 5 6 7 8 9  下一页

Tags:MFC 程序员 WTL

编辑录入:爽爽 [复制链接] [打 印]
赞助商链接