MFC—PostMessage与OnCommand

MFC—PostMessage与OnCommand

首先放一个关于PostMessage的链接,清楚说明了PostMessage发送消息(自定义消息)的实例。

https://blog.csdn.net/alzzw/article/details/103070568

别处感觉好的解释: Windows程序都维护有自己的消息队列,保存了队列消息(当然也有非队列消息,它们直接发给窗口),并用过消息循环对消息进行处理。
  MFC使用一种消息映射机制来处理消息,在应用程序框架中的表现就是一个消息与消息处理函数一一对应的消息映射表,以及消息处理函数的声明和实现等代码。当窗口接收到消息时,会到消息映射表中查找该消息对应的消息处理函数,然后由消息处理函数进行相应的处理。
  
实现过程:
 首先,我们先对MFC的消息映射做一个简单介绍。MFC为了实现消息映射在响应消息的类内部自动做了如下方面的处理:
 1.定义消息和声明消息处理函数,对应上文链接中的一。
 		#define WM_MY_MESSAGE (WM_USER+100) 
 		afx_msg LRESULT OnMyMessage(WPARAM wParam, LPARAM lParam);
 2.添加消息映射
 	ON_MESSAGE(WM_MY_MESSAGE, OnMyMessage)
 3.写消息函数

LRESULT 你的类名::OnMyMessage(WPARAM wParam, LPARAM lParam)

{
// TODO: 处理用户自定义消息
//…
CString str = (LPCTSTR)lParam;
SetWindowText(IDC_ShowStr,str);
delete str;
return 0; }

讲下Windows消息的分类。Windows消息分为系统消息和用户自定义消息。Windows系统消息有三种:

   1.标准Windows消息。除WM_COMMAND外以WM_开头的消息是标准消息。例如,WM_CREATE、WM_CLOSE。

   2.命令消息。消息名为WM_COMMAND,消息中附带了标识符ID来区分是来自哪个菜单、工具栏按钮或加速键的消息。

   3.通知消息。通知消息一般由列表框等子窗口发送给父窗口,消息名也是WM_COMMAND,其中附带了控件通知码来区分控件。

关于OnCommand和OnMessage的区别,看了很多博客,感觉最简单易懂的是这个
https://blog.csdn.net/hk121/article/details/80969964?ops_request_misc=&request_id=&biz_id=102&utm_term=%E6%B6%88%E6%81%AF%E6%98%A0%E5%B0%84%E6%9C%BA%E5%88%B6&utm_medium=distribute.pc_search_result.none-task-blog-2allsobaiduweb~default-1-80969964
即只是
ON_COMMAND是菜单和工具栏项处理消息的宏
ON_MESSAGE是处理自定义消息的宏

ON_MESSAGE是处理所有的Windows的消息的,因为所有的消息都以相同的格式传送,也就是ID, WPARAM, LPARAM.
 ON_COMMAND是专门处理WM_COMMAND消息的,这样我们就不用自己解开WM_COMMAND中wParam和lParam中传送的控件ID,事件种类…(所有的都在MFC内部解决了:),当然方便了。

几点说明:
1、ON_COMMAND(id,memberFxn)
此宏通过ClassWizard或手工插入一个消息映射。它表明那个函数将从一个命令用户接口(例如一个菜单项或toolbar按钮)处理一个命令消息(自己写函数)。当一个命令对象通过指定的ID接受到一个Windows WM_COMMAND消息时,ON_COMMAND将调用成员函数memberFxn处理此消息。在用户的消息映射中,对于每个菜单或加速器命令(必须被映射到一个消息处理函数)应该确实有一个ON_COMMAND宏语句。
2、ON_MESSAGE(message,memberFxn)
指明哪个函数将处理一用户定义消息。用户定义消息通常定义在WM_USER到0x7FF范围内。用户定义消息是那些不是标准 Windows WM_MESSAGE消息的任何消息。在用户的消息映射中,每个必须被映射到一个消息处理函数。用户定义消息应该有一个 ON_MESSAGE宏语句。
3、ON_Update_COMMAND_UI(id,memberFxn)
此宏通常通过ClassWizard被插入一个消息映射,以指明哪个函数将处理一个用户接口更改命令消息。在用户的消息映射中,每个用户接口更改命令(比讯被映射到一个消息处理函数)应该有一个ON_Update_COMMAND_UI宏语句。

注意,OnCommand是一个函数,是响应WM_COMMAND消息的,一般是响应控件和菜单的命令消息时使用。
BOOL CDlgTest::OnCommand(WPARAM wParam, LPARAM lParam)
{
switch(LOWORD(wParam))//wParam的低字是控件ID,lParam是发送这个WM_COMMAND消息的控件的句柄。
{
case IDC_BTN_BEGIN:
{
AfxMessageBox(_T(“开始”));
break;
}
case IDC_BTN_END:
{
AfxMessageBox(_T(“结束”));
break;
}
}
return CDialog::OnCommand(wParam, lParam);
}
当然,我们也可以自己定义对应函数但是这样可能无法使用WPARAM,LPARAM
使用ON_Message可用

补充:因为ON_Command是调用菜单和工具栏等系统资源的,所以不用自定义消息消息,而是使用对应的资源ID,如
ON_COMMAND(ID_COMRESTART, &CDisplayApp::OnComrestart)
参数分别对应空间ID和处理函数
但是ON_Message则要多一步自定义消息
ON_MESSAGE(WM_MY_MESSAGE, OnMyMessage)
实际调用时,使用PostMessage等函数,标明句柄调用
::PostMessage(MyList, WM_MY_MESSAGE, 0, (LPARAM)(LPCTSTR)str4);//(LPARAM)(LPCTSTR)str4);

另附PostMessage粗略解释
PostMessage函数放置(投递)消息到创建指定窗口的线程所关联的消息队列中,并且不会等待相应线程处理消息,而直接返回。
BOOL PostMessage(
HWND hWnd,
UINT Msg,
WPARAMwParam,
LPARAMlParam
);

参数说明:
hWnd:指定将要接收消息的窗口过程的窗口句柄。下面的值有其特殊含义:

HWND_BROADCAST:
消息将被发送到系统中所有顶层窗口,包括无效或不可见的非自身拥有的窗口、被覆盖的窗口和弹出式窗口,但消息不被发送到子窗口。
NULL:
该函数的行为和调用PostThreadMessage函数时将dwThreadId参数设置为当前线程id一致。

Msg:指定将要被发送的消息。

wParam:指定附加的消息特定信息。

lParam:指定附加的消息特定信息。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值