gpt4 book ai didi

c++ - 在 Windows 和 Qt5 上使用 SendMessage 进行进程间通信

转载 作者:行者123 更新时间:2023-11-28 05:42:52 26 4
gpt4 key购买 nike

我想我的问题相当普遍:当第二个实例运行时在我的应用程序的第一个实例中打开一个文件(例如,通过在资源管理器中打开一个关联的文件)。

我在 Windows 上实现它的方法是使用 SendMessage Win API 并通过在 Qt 窗口中重新实现 winEvent 来接收消息。这在 Qt4 上运行良好。但出于某种原因,在我将我的应用程序更新到 Qt 5 后它完全停止工作。

我已经编写了一个重现该行为的最小测试(见下文):在 Qt 4 上也很好,但在 Qt 5 上不起作用(未收到消息)。我正在使用 mingw32 (gcc) 以防它有什么不同。我对 Windows API 非常不熟悉,所以如果有人能解释这种奇怪的行为,我会很高兴。

非常感谢!

服务器.c:

#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <winuser.h>
#include <windef.h>

#include <QApplication>
#include <QLabel>
#include <QDialog>

#include "winmessagelistener.h"

bool WinMessageListener::winEvent( MSG* message, long* result ) {
if( message->message == WM_COPYDATA ) {
label->setText( "Message!" );
// We process the event here
*result = 0;
return true;
}
else {
// Give the event to qt
return false;
}
}

WinMessageListener::WinMessageListener() : QDialog() {
setWindowTitle( "blah" );
label = new QLabel( this );
label->setText("no message");
}

int main(int argc, char **argv) {
QApplication app (argc, argv);
WinMessageListener listener;

listener.show();

return app.exec();
}

winmessagelistener.h:

#include <QDialog>
#include <QLabel>

class WinMessageListener : public QDialog {
Q_OBJECT

public:
WinMessageListener();

private:
// Override the default event message
bool winEvent( MSG* message, long* result );
QLabel* label;
};

客户端.c:

#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <winuser.h>
#include <windef.h>

#include <iostream>
#include <QString>

const QString WINDOW_TITLE = "blah";

int main(int argc, char **argv) {
LPCWSTR window_title = (LPCWSTR) WINDOW_TITLE.utf16();
HWND window_handle_ = FindWindow( NULL, window_title );

std::cerr << "Window handle = " << window_handle_ << std::endl;

COPYDATASTRUCT data = { 0, 0, 0 };

SendMessage( window_handle_, WM_COPYDATA, 0, (LPARAM) &data );
}

最佳答案

由于答案比评论更能帮助他人,所以在这里。问题是在 Qt5 中,函数 bool QWidget::winEvent(MSG * message, long * result) 不再可用。它已被函数 bool QWidget::nativeEvent(const QByteArray &eventType, void *message, long *result) 取代,如 documentation 中所述:

Note: This function superseedes the event filter functions x11Event(), winEvent() and macEvent() of Qt 4.

请注意,以更一般的方式,正如@Paul R. 在评论中所说,不要忘记使用宏 Q_DECL_OVERRIDE为了让编译器在你重写虚函数什么都不做的情况下产生错误。在那种情况下,它可以像这样使用:

bool WinMessageListener::winEvent(MSG * message, long * result) Q_DECL_OVERRIDE;

注意:这是一个 C++11 上下文关键字,因此如果您想使用它,您的编译器需要支持 C++11。如果您没有使用支持 C++11 的编译器,您将得不到任何诊断。

关于c++ - 在 Windows 和 Qt5 上使用 SendMessage 进行进程间通信,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36796216/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com