如何使用SendMessage从父窗口获取CString值?
用消息机制从父窗口获取私有CString值的实现方法
我们知道用SendMessage可以轻松把CString传递给父窗口,简化示例如下:
CString strText = L"The text"; GetParent()->SendMessage(theApp.UWM_LOADED_SRR_FILE_MSG, reinterpret_cast<WPARAM>(strText.GetString()));
父窗口对应的消息处理函数:
afx_msg LRESULT CMyDialog::OnSetSRRFilename(WPARAM wParam, LPARAM lParam) { LPCTSTR szFilename = reinterpret_cast<LPCTSTR>(wParam); // 执行相关业务操作 return 0; }
但反过来,怎么通过消息机制从父窗口获取它的私有CString值?我知道可以把父对象强制类型转换后调用其公共方法,但希望用消息机制实现。我理解SendMessage是向接收方传递文本,那是不是需要先给父窗口发一条“请求获取字符串”的消息,同时传入自身窗口句柄,再让父窗口的处理函数给这个句柄发送包含字符串值的消息?这样是不是把问题复杂化了?(注:目标字符串是父窗口的私有变量,不是控件内容)
其实不用这么复杂,直接利用SendMessage的同步特性和返回值就能实现,不需要额外的反向消息传递,具体实现步骤如下:
1. 定义自定义请求消息
先定义一个用于子窗口请求父窗口私有字符串的自定义消息,比如:
#define UWM_REQUEST_SRR_FILE_MSG (WM_USER + 101)
2. 父窗口实现消息处理函数
在父窗口类中添加消息映射和处理函数,直接将私有CString的内部字符串指针通过返回值返回:
// 消息映射(在父窗口类的消息映射表中添加) ON_MESSAGE(UWM_REQUEST_SRR_FILE_MSG, &CMyDialog::OnRequestSRRFilename) // 处理函数实现 afx_msg LRESULT CMyDialog::OnRequestSRRFilename(WPARAM wParam, LPARAM lParam) { // m_strPrivateFilename是父窗口的私有CString成员变量 return reinterpret_cast<LRESULT>(m_strPrivateFilename.GetString()); }
3. 子窗口发送请求并获取字符串
子窗口通过SendMessage发送请求,直接接收返回值并转换为字符串即可:
// 发送请求消息,同步获取父窗口返回的字符串指针 LPCTSTR szReceived = reinterpret_cast<LPCTSTR>( GetParent()->SendMessage(UWM_REQUEST_SRR_FILE_MSG) ); if (szReceived != nullptr) { CString strResult(szReceived); // 对获取到的字符串进行后续处理 }
关键说明
SendMessage是同步调用,子窗口在调用过程中父窗口的私有CString不会被销毁,所以直接返回内部指针是安全的,不会出现野指针问题- 如果使用异步的
PostMessage则不能这么做,因为异步调用时父窗口的字符串可能已经被释放,但本场景是子窗口主动请求,用同步的SendMessage完全适配 - 这种方式比“双向消息传递”简洁得多,不需要额外传递窗口句柄,也避免了复杂的回调逻辑
内容的提问来源于stack exchange,提问作者Andrew Truckle
相关产品推荐
相关产品推荐

