diff options
author | Timothée Keller <timothee.keller@qt.io> | 2023-04-18 16:00:04 +0200 |
---|---|---|
committer | Timothée Keller <timothee.keller@qt.io> | 2023-04-25 22:57:43 +0200 |
commit | 21e411687428d05655b8db2634466384fa35cc03 (patch) | |
tree | d894a577af32f2fc5dfa848724b7db06611129d3 | |
parent | eec5a016d35197726ba34fc759ab2e24bdbd37f5 (diff) |
Windows QPA: Fix restore geometry after dragging from maximised
Start tracking the window geometry before a mouse drag, so that we can
revert back to that geometry when we restore from maximised. Previously,
when dragging from maximised to maximised, the restore geometry would
end up being the final drag place before snapping to maximised, instead
of where the window was before the first maximised.
Fixes: QTBUG-112814
Pick-to: 6.5 6.2
Change-Id: Ic2ddf29d6c4abdc9e8b0c5161b17aa6ee9474ea3
Reviewed-by: Oliver Wolff <oliver.wolff@qt.io>
-rw-r--r-- | src/plugins/platforms/windows/qwindowscontext.cpp | 4 | ||||
-rw-r--r-- | src/plugins/platforms/windows/qwindowswindow.cpp | 19 | ||||
-rw-r--r-- | src/plugins/platforms/windows/qwindowswindow.h | 3 |
3 files changed, 26 insertions, 0 deletions
diff --git a/src/plugins/platforms/windows/qwindowscontext.cpp b/src/plugins/platforms/windows/qwindowscontext.cpp index 501561115c..72a3ca15dc 100644 --- a/src/plugins/platforms/windows/qwindowscontext.cpp +++ b/src/plugins/platforms/windows/qwindowscontext.cpp @@ -1219,11 +1219,15 @@ bool QWindowsContext::windowsProc(HWND hwnd, UINT message, break; case QtWindows::EnterSizeMoveEvent: platformWindow->setFlag(QWindowsWindow::ResizeMoveActive); + if (!IsZoomed(hwnd)) + platformWindow->updateRestoreGeometry(); return true; case QtWindows::ExitSizeMoveEvent: platformWindow->clearFlag(QWindowsWindow::ResizeMoveActive); platformWindow->checkForScreenChanged(); handleExitSizeMove(platformWindow->window()); + if (!IsZoomed(hwnd)) + platformWindow->updateRestoreGeometry(); return true; case QtWindows::ScrollEvent: if (!(d->m_systemInfo & QWindowsContext::SI_SupportsPointer)) diff --git a/src/plugins/platforms/windows/qwindowswindow.cpp b/src/plugins/platforms/windows/qwindowswindow.cpp index 120c50249a..01f6f21354 100644 --- a/src/plugins/platforms/windows/qwindowswindow.cpp +++ b/src/plugins/platforms/windows/qwindowswindow.cpp @@ -932,6 +932,7 @@ QWindowsWindowData QRect obtainedGeometry(context->obtainedPos, context->obtainedSize); result.geometry = obtainedGeometry; + result.restoreGeometry = frameGeometry(result.hwnd, topLevel); result.fullFrameMargins = context->margins; result.embedded = embedded; result.hasFrame = hasFrame; @@ -1972,6 +1973,11 @@ void QWindowsWindow::handleDpiScaledSize(WPARAM wParam, LPARAM lParam, LRESULT * // are currently doing. m_data.customMargins *= scale; } + if (!m_data.restoreGeometry.isEmpty()) { + m_data.restoreGeometry.setWidth(m_data.restoreGeometry.width() * scale); + m_data.restoreGeometry.setHeight(m_data.restoreGeometry.height() * scale); + } + const QSize windowSize = (geometry().size() * scale).grownBy(margins + customMargins()); SIZE *size = reinterpret_cast<SIZE *>(lParam); size->cx = windowSize.width(); @@ -2435,6 +2441,14 @@ void QWindowsWindow::handleWindowStateChange(Qt::WindowStates state) handleHidden(); QWindowSystemInterface::flushWindowSystemEvents(QEventLoop::ExcludeUserInputEvents); // Tell QQuickWindow to stop rendering now. } else { + if (state & Qt::WindowMaximized) { + WINDOWPLACEMENT windowPlacement{}; + windowPlacement.length = sizeof(WINDOWPLACEMENT); + GetWindowPlacement(m_data.hwnd, &windowPlacement); + const RECT geometry = RECTfromQRect(m_data.restoreGeometry); + windowPlacement.rcNormalPosition = geometry; + SetWindowPlacement(m_data.hwnd, &windowPlacement); + } // QTBUG-17548: We send expose events when receiving WM_Paint, but for // layered windows and transient children, we won't receive any WM_Paint. QWindow *w = window(); @@ -2458,6 +2472,11 @@ void QWindowsWindow::handleWindowStateChange(Qt::WindowStates state) } } +void QWindowsWindow::updateRestoreGeometry() +{ + m_data.restoreGeometry = normalFrameGeometry(m_data.hwnd); +} + void QWindowsWindow::setWindowState(Qt::WindowStates state) { if (m_data.hwnd) { diff --git a/src/plugins/platforms/windows/qwindowswindow.h b/src/plugins/platforms/windows/qwindowswindow.h index 3404eebf22..0e47b31bf9 100644 --- a/src/plugins/platforms/windows/qwindowswindow.h +++ b/src/plugins/platforms/windows/qwindowswindow.h @@ -78,6 +78,7 @@ struct QWindowsWindowData { Qt::WindowFlags flags; QRect geometry; + QRect restoreGeometry; QMargins fullFrameMargins; // Do not use directly for windows, see FrameDirty. QMargins customMargins; // User-defined, additional frame for NCCALCSIZE HWND hwnd = nullptr; @@ -218,6 +219,8 @@ public: void setGeometry(const QRect &rect) override; QRect geometry() const override { return m_data.geometry; } QRect normalGeometry() const override; + QRect restoreGeometry() const { return m_data.restoreGeometry; } + void updateRestoreGeometry(); void setVisible(bool visible) override; bool isVisible() const; |