Подтвердить что ты не робот

Получить HWND на окнах с Qt5 (из WId)

Я пытаюсь преобразовать приложение Qt4 в Qt5. Единственное, что я не мог понять, - это получить HWND виджета. Программа использует EcWin7, чтобы показать прогресс на значке панели задач на выигрыше 7+, но ожидает HWND. Сам lib, похоже, компилируется после изменения Q_WS_WIN на Q_OS_WIN) В Qt4 на Windows WId был всего лишь typedef для HWND, поэтому это не проблема. В Qt5 это уже не так. Я нашел рассылку рассылки, которая могла бы дать ключ, но похоже, что QPlatformNativeInterface больше не является частью публичного API Qt5.

Программа вызывает EcWin7.init(this- > winId()); и мне нужно каким-то образом преобразовать этот идентификатор в идентификатор HWND или каким-либо другим способом, чтобы получить это.

4b9b3361

Ответ 1

В Qt5 winEvent был заменен на nativeEvent:

bool winEvent(MSG* pMsg, long* result)

теперь

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

И в EcWin7::winEvent вам нужно отбрасывать void в MSG:

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

Мне удалось заставить приложение работать! Просто замените:

 mWindowId = wid;

с

 mWindowId = (HWND)wid;

Ответ 2

#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; 
}

Ответ 3

Вы можете попробовать:

(HWND)QWidget::winId();

Ответ 4

Я искал целый день для выяснения этой проблемы. В основном я нахожу три предложенных решения:

Во-первых:

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. Я проверил возвращенный HWND, распечатав связанный идентификатор процесса и сравнил его с показанным в диспетчере задач Windows, используя следующий код:

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

Однако, когда я пытался использовать этот HWND для отправки для отправки сообщений Windows из других функций. Я не могу получать сообщения в

bool winEvent(MSG* pMsg, long* result)

Это означает, что сообщение Windows никогда не работает. Есть ли у кого-нибудь представление о том, как заставить его работать?

Ответ 5

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();

Ответ 6

Попробуйте эту функцию: QWindowsNativeInterface::nativeResourceForWindow