mfc 消息传递

来源:互联网 发布:金蝶数据库置疑 编辑:程序博客网 时间:2024/04/29 11:17
消息分类
 Windows的消息都是以WM_xxx为名,WM_的意思是Windows Message.
MFC把消息分为三大类:
# 命令消息(WM_COMMAND):命令消息意味着使用者命令程序做某些操作.凡是UI对象产生的消息都是这种命令消息,可能来自菜单或加速键或工具栏按钮,并且都以WM_COMMAND呈现.如何分辨来自各处的命令消息?SDK程序主要靠消息的wParam识别之,MFC程序则主要靠菜单项的识别码(menu ID)识别之,其实两者是相同的.
 什么样的类有资格接受命令消息?凡派生自CCmdTarget的类皆有资格.从command target的字面意思可知,这是命令消息的目的地.也就是说,凡派生自CCmdTarget的类,就有一种特殊的机制.
# 标准消息:除WM_COMMAND之外,任何以WM_开头的都酸这一类.任何派生在CWnd的类,均可接受此消息.
# Control Notification:这种消息由控件产生,为的是其父窗口(通常是对话框)通知某种情况.例如当字ListBox上选择其中一个项目,ListBox就会产生LBN_SEDCHANGE传送给父窗口,这类消息也是以WM_COMMAND形式呈现.
 
Command Target( CCmdTarget )
 程序中的许多类都可以接受并处理消息.只要是CWnd的派生类,就可以拦下任何Windows消息.与窗口无关的MFC类,如果也想处理消息,必须派生自CCmdTarget,并且只可能接受到WM_COMMAND命令消息.
 会产生命令消息的,不外就是UI对象:菜单项和工具栏都是.命令消息必须有一个对应的处理函数.把消息和其处理函数在一起,这种操作称为:CommandBinding,这个操作将由一堆宏完成.
一个Command Target对象根据自己的消息映射表知道它可以处理某个消息.消息映射表使得消息和函数的对应关系形成一份表格,进而全体形成一张网.
 
三个奇怪的宏
 消息映射是MFC内建的一个消息分派机制,只要利用数个宏以及固定形式的写法,类似填表格,就可以让Framewok知道,一旦消息发生,该走哪一条路.
 每个类只能拥有一个消息映射表格,但也可以没有.
 第一个宏BEGIN_MESSAGE_MAP有两个参数,分别是拥有此消息映射表之类,及其父类.第二个宏是ON_COMMAND,指定命令消息的处理函数名称.第三个宏END_MESSAGE_MAP作为结尾记号.
 
DECLARE_MESSAGE_MAP
 消息映射的本质其实是一个巨大的数据结构,用来为诸如WM_PAINT这样的标准消息决定流动路线,使它得以流到父类去:也用来为WM_COMMAND这个特殊消息决定流动路线,使它能够七怪八弯地流到类层次结构的旁支去.
#define DECLARE_MESSAGE_MAP() /
Private:
    Static const AFX_MESSAGE_ENTRY _messageEntries[];/
Protected:
    Static AFX_DATA const AFX_MSGMAP messageMap;/
    Virtual const AFX_MSGMAP * GetMessageMap() const; /
其中, AFX_MESSAGE_ENTRY是一个结构体,主要作用是让消息对应于其函数.
AFX_MSGMAP也是一个结构体,它里面有个参数pBaseMap是一个指向基类之映射表的指针,它提供了一个走访整个继承链表的方法,有效地实现消息映射的继承性.派生类将自动地继承其基类中所处理的消息,意思是,若基类处理过A消息,其派生类即使未设计A消息之消息映射表项目,也具有对A消息的处理能力.

 消息的传递

消息的流动路线已隐隐有脉络可寻,此脉络是指由BEGIN_MESSAGE_MAPEND_MESSAGE_END以及许多ON_WM_XXX宏所构成的消息映射网。
整个MFC,拥有虚函数WindowProc者包括CWnd, CcontrolBar, ColeControl, ColePropertyPage,Cdialog,CreflectorWnd,CparkingWind.一般窗口都派生自CWnd
 
一般Windows消息
 CWnd::windowProc调用的OnWndMsg是用来分辨并处理消息的专职函数:如果是命令消息,就交给OnCommand处理;若是通知消息(Notification),就交给OnNotify处理 
原创粉丝点击