diff --git a/framelesshelper_win32.cpp b/framelesshelper_win32.cpp index 6629e26..fc13efb 100644 --- a/framelesshelper_win32.cpp +++ b/framelesshelper_win32.cpp @@ -247,7 +247,7 @@ bool FramelessHelperWin::nativeEventFilter(const QByteArray &eventType, void *me ? reinterpret_cast(msg->lParam) : &(reinterpret_cast(msg->lParam))->rgrc[0]); const bool max = IsMaximized(msg->hwnd); - const bool full = window->windowState() == Qt::WindowFullScreen; + const bool full = Utilities::isFullScreen(reinterpret_cast(msg->hwnd)); // We don't need this correction when we're fullscreen. We will // have the WS_POPUP size, so we don't have to worry about // borders, and the default frame will be fine. @@ -574,12 +574,12 @@ bool FramelessHelperWin::nativeEventFilter(const QByteArray &eventType, void *me const int titleBarHeight = Utilities::getSystemMetric(window, SystemMetric::TitleBarHeight, true); bool isTitleBar = false; const bool max = IsMaximized(msg->hwnd); - if (max || (window->windowState() == Qt::WindowFullScreen)) { + if (max || Utilities::isFullScreen(reinterpret_cast(msg->hwnd))) { isTitleBar = (localMouse.y() >= 0) && (localMouse.y() <= titleBarHeight) && (localMouse.x() >= 0) && (localMouse.x() <= windowWidth) && !Utilities::isHitTestVisible(window); } - if (window->windowState() == Qt::WindowNoState) { + if (Utilities::isWindowNoState(reinterpret_cast(msg->hwnd))) { isTitleBar = (localMouse.y() > resizeBorderThickness) && (localMouse.y() <= titleBarHeight) && (localMouse.x() > resizeBorderThickness) && (localMouse.x() < (windowWidth - resizeBorderThickness)) && !Utilities::isHitTestVisible(window); diff --git a/utilities.h b/utilities.h index 82e2326..5cf4ed8 100644 --- a/utilities.h +++ b/utilities.h @@ -55,6 +55,8 @@ FRAMELESSHELPER_API void triggerFrameChange(const WId winId); FRAMELESSHELPER_API void updateFrameMargins(const WId winId, const bool reset); FRAMELESSHELPER_API void updateQtFrameMargins(QWindow *window, const bool enable); [[nodiscard]] FRAMELESSHELPER_API QString getSystemErrorMessage(const QString &function); +[[nodiscard]] FRAMELESSHELPER_API bool isFullScreen(const WId winId); +[[nodiscard]] FRAMELESSHELPER_API bool isWindowNoState(const WId winId); #endif } diff --git a/utilities_win32.cpp b/utilities_win32.cpp index 0076a6b..502443b 100644 --- a/utilities_win32.cpp +++ b/utilities_win32.cpp @@ -547,4 +547,53 @@ bool Utilities::showSystemMenu(const WId winId, const QPointF &pos) return true; } +bool Utilities::isFullScreen(const WId winId) +{ + Q_ASSERT(winId); + if (!winId) { + return false; + } + const auto hwnd = reinterpret_cast(winId); + RECT wndRect = {}; + if (GetWindowRect(hwnd, &wndRect) == FALSE) { + qWarning() << getSystemErrorMessage(QStringLiteral("GetWindowRect")); + return false; + } + // According to Microsoft Docs, we should compare to primary + // screen's geometry. + const HMONITOR mon = MonitorFromWindow(hwnd, MONITOR_DEFAULTTOPRIMARY); + if (!mon) { + qWarning() << getSystemErrorMessage(QStringLiteral("MonitorFromWindow")); + return false; + } + MONITORINFO mi; + SecureZeroMemory(&mi, sizeof(mi)); + mi.cbSize = sizeof(mi); + if (GetMonitorInfoW(mon, &mi) == FALSE) { + qWarning() << getSystemErrorMessage(QStringLiteral("GetMonitorInfoW")); + return false; + } + // Compare to the full area of the screen, not the work area. + const RECT scrRect = mi.rcMonitor; + return ((wndRect.left == scrRect.left) && (wndRect.top == scrRect.top) + && (wndRect.right == scrRect.right) && (wndRect.bottom == scrRect.bottom)); +} + +bool Utilities::isWindowNoState(const WId winId) +{ + Q_ASSERT(winId); + if (!winId) { + return false; + } + const auto hwnd = reinterpret_cast(winId); + WINDOWPLACEMENT wp; + SecureZeroMemory(&wp, sizeof(wp)); + wp.length = sizeof(wp); + if (GetWindowPlacement(hwnd, &wp) == FALSE) { + qWarning() << getSystemErrorMessage(QStringLiteral("GetWindowPlacement")); + return false; + } + return ((wp.showCmd == SW_NORMAL) || (wp.showCmd == SW_RESTORE)); +} + FRAMELESSHELPER_END_NAMESPACE