我是靠谱客的博主 坚定自行车,这篇文章主要介绍MFC线程间通信一、主线程与子线程通信二、线程间通信的三种方法,现在分享给大家,希望可以做个参考。

一、主线程与子线程通信

方法一:

第一步:#define WM_RECVDATA WM_USER+100
WM_USER不一定+100,只要大于WM_USER即可,但要注意不可与其他的自定义消息冲突

1、子线程(要发送消息的线程)

复制代码
1
2
3
4
5
6
7
8
9
10
11
CString str; //将传输的数据转化 成char* char *ch = new char[10]; WideCharToMultiByte(CP_ACP,0,str,-1,ch,10,NULL,NULL); //不断调用PostThreadMessage函数,直到函数成功。 这是因为当线程收到这样的函数以后, //会自动创建消息队列。 while(!::PostThreadMessage(WM_RECVDATA,(WPARAM)ch,0)) { Sleep(10); delete[] ch; } //此处也可设置全局变量传值,只利用此函数触发主线程函数进行消息处理

2、主线程(接收消息的线程)
重写BOOL VeinDemoDlg::PreTranslateMessage(MSG* pMsg)

复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
BOOL VeinDemoDlg::PreTranslateMessage(MSG* pMsg) { //目标线程通过调用PeekMessage强制系统创建一个消息队列 PeekMessage(pMsg,NULL,WM_USER+100,WM_USER+100,PM_NOREMOVE); //如果是有条件发送,则采用判断语言if进行接收 if(pMsg->message == WM_RECVDATA) { //此处添加消息处理函数 } //如果发送的消息是不间断的,则用while进行接收 while(true) { if (GetMessage(&msg,0,0,0)) { switch (msg.message) { case UM_MESSAGE: char *pch = (char*)msg.wParam; m_offset_v = atof(pch);//添加消息处理函数 delete[] pch; break; } } } return CDialog::PreTranslateMessage(pMsg); }
复制代码
1
2
BOOL PeekMessage(LPMSG lpMsg, HWND hWnd, UINT wMsgFilterMin, UINT wMsgFilterMax, UINT wRemoveMsg);

LPMSG lpMsg:消息的地址
HWND hWnd:视窗的句柄
UINT wMsgFilterMin, UINT wMsgFilterMax:两个值指示消息范围(都为0或NULL表示传回所有消息
UINT wRemoveMsg:PM_REMOVE将消息从消息队列中删除,PM_NOREMOVE保留消息从在消息队列中

参考:https://blog.csdn.net/m0_37884601/article/details/84639830

方法二(推荐):

在MFC中测试通过
在同一个.cpp中

复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
#define WM_CAPTURE_HINT WM_USER + 14 BEGIN_MESSAGE_MAP(VeinDemoDlg, CDialog) //{{AFX_MSG_MAP(VeinDemoDlg) ON_WM_SYSCOMMAND() ON_WM_PAINT() ON_WM_QUERYDRAGICON() ON_BN_CLICKED(IDC_CLOSE, OnClose) //}}AFX_MSG_MAP ON_MESSAGE(WM_CAPTURE_HINT, OnCaptureHint)//注意这一条,用于传递消息 END_MESSAGE_MAP() LRESULT VeinDemoDlg::OnCaptureHint(WPARAM wParam, LPARAM lParam) { char * strMessage = (char*)wParam; //在此可以添加消息处理程序,和主线程中的函数使用相同 LogMessage(strMessage); delete [] strMessage; return 0; } DWORD WINAPI VeinDemoDlg::MatchProc(LPVOID param) { VeinDemoDlg * mainWindow = (VeinDemoDlg *)param; mainWindow->LogMessageInThread("HelloWorld!"); } void VeinDemoDlg::LogMessageInThread(char * strFmt, ...) { char tempMsg[1024]; CString outMsg = ""; /*---获取参数列表---*/ va_list argp; va_start(argp, strFmt); /*---格式化的数据输出到指定的数据流中---*/ _vsnprintf_s(tempMsg, 1024,strFmt, argp); a_end(argp); outMsg += tempMsg; char * strMessage = new char[outMsg.GetLength() + 1]; strcpy(strMessage , (const char*)outMsg.GetBuffer(0)); ::PostMessage(GetSafeHwnd(),WM_CAPTURE_HINT,(WPARAM)strMessage,(LPARAM)0); } void VeinDemoDlg::LogMessage(char * strFmt, ...) { SYSTEMTIME st; GetLocalTime(&st); char CurTime[64] = { '' }; char tempMsg[1024]; CString outMsg; sprintf_s(CurTime, "%02d:%02d:%02d.%03d ",st.wHour,st.wMinute,st.wSecond,st.wMilliseconds); outMsg = CurTime; /*---获取参数列表---*/ va_list argp; va_start(argp, strFmt); /*---格式化的数据输出到指定的数据流中---*/ _vsnprintf_s(tempMsg, 1024,strFmt, argp); va_end(argp); outMsg += tempMsg; m_msgList.InsertString(0,outMsg); }

二、线程间通信的三种方法

可参考该博文:https://blog.csdn.net/cbnotes/article/details/8516703

最后

以上就是坚定自行车最近收集整理的关于MFC线程间通信一、主线程与子线程通信二、线程间通信的三种方法的全部内容,更多相关MFC线程间通信一、主线程与子线程通信二、线程间通信内容请搜索靠谱客的其他文章。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(82)

评论列表共有 0 条评论

立即
投稿
返回
顶部