forked from github_mirror/framelesshelper
win: add a little delay to some operations
Signed-off-by: Yuhang Zhao <2546789017@qq.com>
This commit is contained in:
parent
04f254556d
commit
648876b6b0
|
@ -27,6 +27,7 @@
|
||||||
#include <QtCore/qmutex.h>
|
#include <QtCore/qmutex.h>
|
||||||
#include <QtCore/qvariant.h>
|
#include <QtCore/qvariant.h>
|
||||||
#include <QtCore/qcoreapplication.h>
|
#include <QtCore/qcoreapplication.h>
|
||||||
|
#include <QtCore/qtimer.h>
|
||||||
#include <QtGui/qwindow.h>
|
#include <QtGui/qwindow.h>
|
||||||
#include "framelessmanager.h"
|
#include "framelessmanager.h"
|
||||||
#include "framelessmanager_p.h"
|
#include "framelessmanager_p.h"
|
||||||
|
@ -639,7 +640,7 @@ bool FramelessHelperWin::nativeEventFilter(const QByteArray &eventType, void *me
|
||||||
const WPARAM wParam = msg->wParam;
|
const WPARAM wParam = msg->wParam;
|
||||||
const LPARAM lParam = msg->lParam;
|
const LPARAM lParam = msg->lParam;
|
||||||
switch (uMsg) {
|
switch (uMsg) {
|
||||||
#if (QT_VERSION < QT_VERSION_CHECK(5, 9, 0))
|
#if (QT_VERSION < QT_VERSION_CHECK(5, 9, 0)) // Qt has done this for us since 5.9.0
|
||||||
case WM_NCCREATE: {
|
case WM_NCCREATE: {
|
||||||
// Enable automatic DPI scaling for the non-client area of the window,
|
// Enable automatic DPI scaling for the non-client area of the window,
|
||||||
// such as the caption bar, the scrollbars, and the menu bar. We need
|
// such as the caption bar, the scrollbars, and the menu bar. We need
|
||||||
|
@ -1112,7 +1113,7 @@ bool FramelessHelperWin::nativeEventFilter(const QByteArray &eventType, void *me
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#if (QT_VERSION < QT_VERSION_CHECK(6, 2, 2))
|
#if (QT_VERSION < QT_VERSION_CHECK(6, 2, 2)) // I contributed this to Qt since 6.2.2
|
||||||
case WM_WINDOWPOSCHANGING: {
|
case WM_WINDOWPOSCHANGING: {
|
||||||
// Tell Windows to discard the entire contents of the client area, as re-using
|
// Tell Windows to discard the entire contents of the client area, as re-using
|
||||||
// parts of the client area would lead to jitter during resize.
|
// parts of the client area would lead to jitter during resize.
|
||||||
|
@ -1127,13 +1128,17 @@ bool FramelessHelperWin::nativeEventFilter(const QByteArray &eventType, void *me
|
||||||
<< hwnd2str(hWnd) << ": QDpi(" << dpiX << ", " << dpiY << ").";
|
<< hwnd2str(hWnd) << ": QDpi(" << dpiX << ", " << dpiY << ").";
|
||||||
// Sync the internal window frame margins with the latest DPI.
|
// Sync the internal window frame margins with the latest DPI.
|
||||||
Utils::updateInternalWindowFrameMargins(data.params.getWindowHandle(), true);
|
Utils::updateInternalWindowFrameMargins(data.params.getWindowHandle(), true);
|
||||||
// For some unknown reason, Qt sometimes won't re-paint the window contents after
|
// Here we need a little delay because event filters are processed before
|
||||||
// the DPI changes, and in my experiments the controls should be moved to our
|
// Qt's own window message handlers.
|
||||||
// desired geometry already, the only issue is we don't get the updated appearance
|
QTimer::singleShot(50, [data](){ // Copy "data" intentionally, otherwise it'll go out of scope when Qt finally use it.
|
||||||
// of our window. And we can workaround this issue by simply triggering a resize
|
// For some unknown reason, Qt sometimes won't re-paint the window contents after
|
||||||
// event manually. There's no need to increase/decrease the window size and then
|
// the DPI changes, and in my experiments the controls should be moved to our
|
||||||
// change it back, just give Qt our current window size is sufficient enough.
|
// desired geometry already, the only issue is we don't get the updated appearance
|
||||||
data.params.setWindowSize(data.params.getWindowSize());
|
// of our window. And we can workaround this issue by simply triggering a resize
|
||||||
|
// event manually. There's no need to increase/decrease the window size and then
|
||||||
|
// change it back, just give Qt our current window size is sufficient enough.
|
||||||
|
data.params.setWindowSize(data.params.getWindowSize());
|
||||||
|
});
|
||||||
} break;
|
} break;
|
||||||
case WM_DWMCOMPOSITIONCHANGED: {
|
case WM_DWMCOMPOSITIONCHANGED: {
|
||||||
// Re-apply the custom window frame if recovered from the basic theme.
|
// Re-apply the custom window frame if recovered from the basic theme.
|
||||||
|
|
|
@ -25,6 +25,7 @@
|
||||||
#include "framelessmanager_p.h"
|
#include "framelessmanager_p.h"
|
||||||
#include <QtCore/qmutex.h>
|
#include <QtCore/qmutex.h>
|
||||||
#include <QtCore/qcoreapplication.h>
|
#include <QtCore/qcoreapplication.h>
|
||||||
|
#include <QtCore/qtimer.h>
|
||||||
#include <QtGui/qscreen.h>
|
#include <QtGui/qscreen.h>
|
||||||
#include <QtGui/qwindow.h>
|
#include <QtGui/qwindow.h>
|
||||||
#include <QtGui/qfontdatabase.h>
|
#include <QtGui/qfontdatabase.h>
|
||||||
|
@ -217,14 +218,18 @@ void FramelessManagerPrivate::addWindow(const SystemParameters ¶ms)
|
||||||
g_helper()->data[windowId].screenChangeConnection =
|
g_helper()->data[windowId].screenChangeConnection =
|
||||||
connect(window, &QWindow::screenChanged, window, [windowId, window](QScreen *screen){
|
connect(window, &QWindow::screenChanged, window, [windowId, window](QScreen *screen){
|
||||||
Q_UNUSED(screen);
|
Q_UNUSED(screen);
|
||||||
// Force a WM_NCCALCSIZE event to inform Windows about our custom window frame,
|
// Add a little delay here, make sure it happens after Qt has processed the window
|
||||||
// this is only necessary when the window is being moved cross monitors.
|
// messages.
|
||||||
Utils::triggerFrameChange(windowId);
|
QTimer::singleShot(50, window, [windowId, window](){
|
||||||
// For some reason the window is not repainted correctly when moving cross monitors,
|
// Force a WM_NCCALCSIZE event to inform Windows about our custom window frame,
|
||||||
// we workaround this issue by force a re-paint and re-layout of the window by triggering
|
// this is only necessary when the window is being moved cross monitors.
|
||||||
// a resize event manually. Although the actual size does not change, the issue we
|
Utils::triggerFrameChange(windowId);
|
||||||
// observed disappeared indeed, amazingly.
|
// For some reason the window is not repainted correctly when moving cross monitors,
|
||||||
window->resize(window->size());
|
// we workaround this issue by force a re-paint and re-layout of the window by triggering
|
||||||
|
// a resize event manually. Although the actual size does not change, the issue we
|
||||||
|
// observed disappeared indeed, amazingly.
|
||||||
|
window->resize(window->size());
|
||||||
|
});
|
||||||
});
|
});
|
||||||
g_helper()->mutex.unlock();
|
g_helper()->mutex.unlock();
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue