MFC中WM_COPYDATA消息

进程间通信最简单的方式就是发送WM_COPYDATA消息。

发送WM_COPYDATA消息:

SendMessage(接收窗口句柄, WM_COPYDATA, (WPARAM)发送窗口句柄, (LPARAM)&CopyData);

其中的CopyData为COPYDATASTRUCT结构类型,该结构定义如下:

typedef struct tagCOPYDATASTRUCT {
DWORD dwData;  // Specifies data to be passed to the receiving application.
DWORD cbData;  //Specifies the size, in bytes, of the data pointed to by the lpData member.
 PVOID lpData;    // Pointer to data to be passed to the receiving application. can be NULL.
} COPYDATASTRUCT, *PCOPYDATASTRUCT;

注意:该消息只能由SendMessage()来发送,而不能使用PostMessage()。因为系统必须管理用以传递数据的缓冲区的生命期,如果使用了PostMessage(),数据缓冲区会在接收方(线程)有机会处理该数据之前,就被系统清除和回收。此外如果lpData指向一个带有指针或某一拥有虚函数的对象时,也要小心处理。

如果传入的句柄不是一个有效的窗口或当接收方进程意外终止时,SendMessage()会立即返回,因此发送方在这种情况下不会陷入一个无穷的等待状态中。

返回值问题,MSDN上说如果接收方处理了,返回TRUE,否则返回FALSE,但是本人在实验时,都是返回0(接收方已经处理)。

例子:新建两个MFC Application,一个“CopyDataReceiver”,另一个“CopyDataSender”。

void CCopyDataSenderDlg::OnBnClickedOk()//发送按钮
{
    // TODO:  在此添加控件通知处理程序代码
//    CDialogEx::OnOK();
    HWND receiveWindow = ::FindWindow(NULL, L"CopyDataReceiver");
    if (receiveWindow == NULL)
        return;

    CString sendData;
    GetDlgItemText(IDC_EDIT_SEND, sendData);

    COPYDATASTRUCT copyData = { 0 };
    copyData.lpData = sendData.GetBuffer();
    copyData.cbData = sendData.GetLength() * sizeof(sendData[0]);

    LRESULT ret = ::SendMessage(receiveWindow, WM_COPYDATA, (WPARAM)GetSafeHwnd(), (LPARAM)&copyData);

    sendData.ReleaseBuffer();
}

-------------------------------------

#pragma warning(disable:4996)
//类向导添加的WM_COPYDATA消息的响应函数
BOOL CCopyDataReceiverDlg::OnCopyData(CWnd* pWnd, COPYDATASTRUCT* pCopyDataStruct)
{
    // TODO:  在此添加消息处理程序代码和/或调用默认值
    if (pCopyDataStruct->cbData > 0)
    {
        //char recvData[256] = { 0 };
        //strncpy(recvData, (char *)pCopyDataStruct->lpData, pCopyDataStruct->cbData);//这是针对char*字符串
        unsigned char recvData[256] = { 0 };
        memcpy(recvData, pCopyDataStruct->lpData, pCopyDataStruct->cbData);//这是针对所有的,char*,wchar_t*
        TRACE1("%s\n",(LPCTSTR)recvData);
        SetDlgItemText(IDC_EDIT_RECEIVE, (LPCTSTR)(recvData));//在这里做相应的转换,是char*或wchar_t*

        //Feedback(pWnd);
    }

    return CDialogEx::OnCopyData(pWnd, pCopyDataStruct);
}
View Code

 

-----------------------------------------------------------------

参考:
https://www.cnblogs.com/zhuyf87/archive/2013/03/03/2941620.html
https://www.cnblogs.com/morewindows/archive/2011/09/23/2186294.html

posted @ 2019-11-16 11:24  htj10  阅读(436)  评论(0编辑  收藏  举报
TOP