使用Qt5(来自WId)在windows上获取HWND

我正试图将Qt4应用程序转换为Qt5。 唯一我无法弄清楚的是如何获得Widget的HWND 。 该程序使用EcWin7来显示任务栏图标上的胜利7 +的进展,但期望一个HWND 。 在将Q_WS_WIN更改为Q_OS_WIN之后,lib本身似乎编译正常)在Windows上的Qt4中,只是HWND的一个typedef,所以这没有问题。 在Qt5中,情况并非如此。 我发现了一些邮件列表发布 ,可能会提供一个线索,但似乎QPlatformNativeInterface不再Qt5的公共API的一部分。

该程序调用EcWin7.init(this-> winId()); 我需要一些方法来将此ID转换为HWND ID或其他方式来获得这个。

在Qt5中, winEventwinEvent所取代:

 bool winEvent(MSG* pMsg, long* result) 

就是现在

 bool nativeEvent(const QByteArray & eventType, void * message, long *result) 

而在EcWin7::winEvent你必须对MSG抛出void

 bool EcWin7::winEvent(void * message, long * result) { MSG* msg = reinterpret_cast<MSG*>(message); if (msg->message == mTaskbarMessageId) { ... 

我能够让应用程序工作! 只要更换:

  mWindowId = wid; 

  mWindowId = (HWND)wid; 
 #include <QtGui/5.0.0/QtGui/qpa/qplatformnativeinterface.h> static QWindow* windowForWidget(const QWidget* widget) { QWindow* window = widget->windowHandle(); if (window) return window; const QWidget* nativeParent = widget->nativeParentWidget(); if (nativeParent) return nativeParent->windowHandle(); return 0; } HWND getHWNDForWidget(const QWidget* widget) { QWindow* window = ::windowForWidget(widget); if (window && window->handle()) { QPlatformNativeInterface* interface = QGuiApplication::platformNativeInterface(); return static_cast<HWND>(interface->nativeResourceForWindow(QByteArrayLiteral("handle"), window)); } return 0; } 

你可以尝试:

 (HWND)QWidget::winId(); 

我花了整整一天的时间来找出这个问题。 基本上我找到三个建议的解决方案:

第一:

 static QWindow* windowForWidget(const QWidget* widget) { QWindow* window = widget->windowHandle(); if (window) return window; const QWidget* nativeParent = widget->nativeParentWidget(); if (nativeParent) return nativeParent->windowHandle(); return 0; } HWND getHWNDForWidget(const QWidget* widget) { QWindow* window = ::windowForWidget(widget); if (window) { QPlatformNativeInterface* interfacep = QGuiApplication::platformNativeInterface(); return static_cast<HWND>(interfacep->nativeResourceForWindow(QByteArrayLiteral("handle"), window)); } return 0; } 

第二:

 HWND getHWNDForWidget(const QWidget* widget) { QWindow* window = ::windowForWidget(widget); if (window) { QPlatformNativeInterface* interfacep = QGuiApplication::platformNativeInterface(); return static_cast<HWND>(interfacep->nativeResourceForWindow(QByteArrayLiteral("handle"), window)); } return 0; } 

第三:

  HWND hWnd = (HWND)this->winId(); 

在我的笔记本电脑与Win8 64x,VS2010,QT5.0.1,我已经尝试所有这些,但只有第三个可以得到正确的HWND。 我通过打印相关进程ID来验证返回的HWND,并使用以下代码将其与Windows任务管理器中显示的进行比较:

  GetWindowThreadProcessId(hWnd, &dwWndProcID); printf("WinID %d\n", dwWndProcID); 

但是,当我试图用这个HWND来发送来自其他函数的消息。 我无法收到任何消息

 bool winEvent(MSG* pMsg, long* result) 

它接缝,Windows消息从来没有工作。 有没有人有任何想法如何使其工作?

winId()在Qt 5.1上为我工作,至少它在我使用时具有相同的值

 bool Widget::nativeEvent(const QByteArray & eventType, void * message, long * result) { MSG* msg = reinterpret_cast<MSG*>(message); qDebug() << msg->hwnd; return false; } 

 qDebug() << winId(); 

试试这个函数: QWindowsNativeInterface::nativeResourceForWindow