Use QWindow pointer on all platforms.

Signed-off-by: Yuhang Zhao <2546789017@qq.com>
This commit is contained in:
Yuhang Zhao 2020-11-17 15:08:39 +08:00
parent 4c65cba578
commit 137019f7e6
12 changed files with 888 additions and 1008 deletions

View File

@ -52,13 +52,10 @@ If you are using part of or all the code from this repository in your own projec
int main(int argc, char *argv[]) { int main(int argc, char *argv[]) {
QWidget widget; QWidget widget;
// Qt's internal function. Make sure it's a top level window.
widget.createWinId();
// Do this before the widget is shown. // Do this before the widget is shown.
#ifdef Q_OS_WIN FramelessWindowsManager::addWindow(widget.windowHandle());
const auto id = reinterpret_cast<FramelessWindowsManager::WindowId>(widget.winId());
#else
const auto id = static_cast<FramelessWindowsManager::WindowId>(&widget);
#endif
FramelessWindowsManager::addWindow(id);
widget.show(); widget.show();
} }
``` ```
@ -70,34 +67,32 @@ Please refer to [the QWidget example](/examples/QWidget/main.cpp) for more detai
```cpp ```cpp
// Only **TOP LEVEL** QWidgets and QWindows are supported. // Only **TOP LEVEL** QWidgets and QWindows are supported.
QMainWindow *mainWindow = new QMainWindow; QMainWindow *mainWindow = new QMainWindow;
#ifdef Q_OS_WIN // Qt's internal function. Make sure it's a top level window.
const auto id = reinterpret_cast<FramelessWindowsManager::WindowId>(mainWindow->winId()); mainWindow->createWinId();
#else const QWindow *win = mainWindow->windowHandle();
const auto id = static_cast<FramelessWindowsManager::WindowId>(mainWindow);
#endif
// Disable resizing of the given window. Resizing is enabled by default. // Disable resizing of the given window. Resizing is enabled by default.
FramelessWindowsManager::setResizable(id, false); FramelessWindowsManager::setResizable(win, false);
// All the following values should not be DPI-aware, just use the // All the following values should not be DPI-aware, just use the
// original numbers, assuming the scale factor is 1.0, don't scale // original numbers, assuming the scale factor is 1.0, don't scale
// them yourself, this code will do the scaling according to DPI // them yourself, this code will do the scaling according to DPI
// internally and automatically. // internally and automatically.
// Maximum window size // Maximum window size
FramelessWindowsManager::setMaximumSize(id, {1280, 720}); FramelessWindowsManager::setMaximumSize(win, {1280, 720});
// Minimum window size // Minimum window size
FramelessWindowsManager::setMinimumSize(id, {800, 540}); FramelessWindowsManager::setMinimumSize(win, {800, 540});
// How to set ignore areas: // How to set ignore areas:
// The geometry of something you already know, in window coordinates // The geometry of something you already know, in window coordinates
FramelessWindowsManager::addIgnoreArea(id, {100, 0, 30, 30}); FramelessWindowsManager::addIgnoreArea(win, {100, 0, 30, 30});
// The geometry of a widget, in window coordinates. // The geometry of a widget, in window coordinates.
// It won't update automatically when the geometry of that widget has // It won't update automatically when the geometry of that widget has
// changed, so if you want to add a widget, which is in a layout and // changed, so if you want to add a widget, which is in a layout and
// it's geometry will possibly change, to the ignore list, try the // it's geometry will possibly change, to the ignore list, try the
// next method (addIgnoreObject) instead. // next method (addIgnoreObject) instead.
FramelessWindowsManager::addIgnoreArea(id, pushButton_close.geometry()); FramelessWindowsManager::addIgnoreArea(win, pushButton_close.geometry());
// The **POINTER** of a QWidget or QQuickItem // The **POINTER** of a QWidget or QQuickItem
FramelessWindowsManager::addIgnoreObject(id, ui->pushButton_minimize); FramelessWindowsManager::addIgnoreObject(win, ui->pushButton_minimize);
// Move a QWidget or QWindow to the center of its current desktop. // Move a QWidget or QWindow to the center of its current desktop.
FramelessWindowsManager::moveWindowToDesktopCenter(id); FramelessWindowsManager::moveWindowToDesktopCenter(win);
``` ```
## Supported Platforms ## Supported Platforms

View File

@ -31,8 +31,10 @@
```cpp ```cpp
QWidget widget; QWidget widget;
// Qt's internal function. Make sure it's a top level window.
widget.createWinId();
// Do this before the widget is shown. // Do this before the widget is shown.
WinNativeEventFilter::addFramelessWindow(reinterpret_cast<void *>(widget.winId())); WinNativeEventFilter::addFramelessWindow(widget.windowHandle());
widget.show(); widget.show();
``` ```
@ -41,8 +43,7 @@ Please refer to [the QWidget example](/examples/QWidget/main.cpp) for more detai
### Ignore areas and etc ### Ignore areas and etc
```cpp ```cpp
// Get the window handle (HWND) first. const QWindow *win = widget.windowHandle();
const auto handle = reinterpret_cast<void *>(widget.winId());
WinNativeEventFilter::WINDOWDATA data = {}; WinNativeEventFilter::WINDOWDATA data = {};
// All the following values should not be DPI-aware, just use the // All the following values should not be DPI-aware, just use the
// original numbers, assuming the scale factor is 1.0, don't scale // original numbers, assuming the scale factor is 1.0, don't scale
@ -64,18 +65,18 @@ data.ignoreAreas.append(pushButton_close.geometry());
// The **POINTER** of a QWidget or QQuickItem // The **POINTER** of a QWidget or QQuickItem
data.ignoreObjects.append(ui->pushButton_minimize); data.ignoreObjects.append(ui->pushButton_minimize);
// Pass data as the second parameter // Pass data as the second parameter
WinNativeEventFilter::addFramelessWindow(handle, &data); WinNativeEventFilter::addFramelessWindow(win, &data);
// Or // Or
WinNativeEventFilter::setWindowData(handle, &data); WinNativeEventFilter::setWindowData(win, &data);
// Or modify the window data of a specific window directly: // Or modify the window data of a specific window directly:
const auto data = WinNativeEventFilter::getWindowData(handle); const auto data = WinNativeEventFilter::getWindowData(win);
if (data) { if (data) {
data->borderWidth = 5; data->borderWidth = 5;
data->borderHeight = 5; data->borderHeight = 5;
data->titleBarHeight = 30; data->titleBarHeight = 30;
} }
// The frameless window is resizable by default. // The frameless window is resizable by default.
WinNativeEventFilter::setWindowResizable(handle, false); WinNativeEventFilter::setWindowResizable(win, false);
``` ```
## Supported Platforms ## Supported Platforms

View File

@ -103,18 +103,13 @@ int main(int argc, char *argv[])
mainWindow->setWindowIcon(icon); mainWindow->setWindowIcon(icon);
mainWindow->setWindowTitle(QObject::tr("Hello, World!")); mainWindow->setWindowTitle(QObject::tr("Hello, World!"));
#ifdef Q_OS_WIN mainWindow->createWinId(); // Qt's internal function, make sure it's a top level window.
const auto id = reinterpret_cast<FramelessWindowsManager::WindowId>(mainWindow->winId()); const QWindow *win = mainWindow->windowHandle();
#else FramelessWindowsManager::addWindow(win);
const auto id = static_cast<FramelessWindowsManager::WindowId>(mainWindow); FramelessWindowsManager::addIgnoreObject(win, titleBarWidget.minimizeButton);
#endif FramelessWindowsManager::addIgnoreObject(win, titleBarWidget.maximizeButton);
FramelessWindowsManager::addIgnoreObject(win, titleBarWidget.closeButton);
FramelessWindowsManager::addWindow(id); FramelessWindowsManager::addIgnoreObject(win, appMainWindow.menubar);
FramelessWindowsManager::addIgnoreObject(id, titleBarWidget.minimizeButton);
FramelessWindowsManager::addIgnoreObject(id, titleBarWidget.maximizeButton);
FramelessWindowsManager::addIgnoreObject(id, titleBarWidget.closeButton);
FramelessWindowsManager::addIgnoreObject(id, appMainWindow.menubar);
mainWindow->resize(800, 600); mainWindow->resize(800, 600);

View File

@ -94,17 +94,12 @@ int main(int argc, char *argv[])
widget.setLayout(mainLayout); widget.setLayout(mainLayout);
widget.setWindowTitle(QObject::tr("Hello, World!")); widget.setWindowTitle(QObject::tr("Hello, World!"));
#ifdef Q_OS_WIN widget.createWinId(); // Qt's internal function, make sure it's a top level window.
const auto id = reinterpret_cast<FramelessWindowsManager::WindowId>(widget.winId()); const QWindow *win = widget.windowHandle();
#else FramelessWindowsManager::addWindow(win);
const auto id = static_cast<FramelessWindowsManager::WindowId>(&widget); FramelessWindowsManager::addIgnoreObject(win, minimizeButton);
#endif FramelessWindowsManager::addIgnoreObject(win, maximizeButton);
FramelessWindowsManager::addIgnoreObject(win, closeButton);
FramelessWindowsManager::addWindow(id);
FramelessWindowsManager::addIgnoreObject(id, minimizeButton);
FramelessWindowsManager::addIgnoreObject(id, maximizeButton);
FramelessWindowsManager::addIgnoreObject(id, closeButton);
widget.resize(800, 600); widget.resize(800, 600);

View File

@ -138,7 +138,7 @@ const QLatin1String g_sCloseButtonImageLight(":/images/button_close_white.svg");
Widget::Widget(QWidget *parent) : QWidget(parent) Widget::Widget(QWidget *parent) : QWidget(parent)
{ {
createWinId(); // Internal function createWinId(); // Qt's internal function, make sure it's a top level window.
initializeWindow(); initializeWindow();
} }
@ -171,7 +171,7 @@ void Widget::setupUi()
sizePolicy.setHeightForWidth(titleBarWidget->sizePolicy().hasHeightForWidth()); sizePolicy.setHeightForWidth(titleBarWidget->sizePolicy().hasHeightForWidth());
titleBarWidget->setSizePolicy(sizePolicy); titleBarWidget->setSizePolicy(sizePolicy);
const int titleBarHeight const int titleBarHeight
= WinNativeEventFilter::getSystemMetric(rawHandle(), = WinNativeEventFilter::getSystemMetric(windowHandle(),
WinNativeEventFilter::SystemMetric::TitleBarHeight); WinNativeEventFilter::SystemMetric::TitleBarHeight);
titleBarWidget->setMinimumSize(QSize(0, titleBarHeight)); titleBarWidget->setMinimumSize(QSize(0, titleBarHeight));
titleBarWidget->setMaximumSize(QSize(16777215, titleBarHeight)); titleBarWidget->setMaximumSize(QSize(16777215, titleBarHeight));
@ -349,11 +349,6 @@ bool Widget::isWin10OrGreater(const Win10Version subVer)
static_cast<int>(subVer)))); static_cast<int>(subVer))));
} }
void *Widget::rawHandle() const
{
return reinterpret_cast<void *>(winId());
}
bool Widget::eventFilter(QObject *object, QEvent *event) bool Widget::eventFilter(QObject *object, QEvent *event)
{ {
Q_ASSERT(object); Q_ASSERT(object);
@ -374,7 +369,7 @@ bool Widget::eventFilter(QObject *object, QEvent *event)
break; break;
} }
case QEvent::WinIdChange: case QEvent::WinIdChange:
WinNativeEventFilter::addFramelessWindow(rawHandle()); WinNativeEventFilter::addFramelessWindow(windowHandle());
break; break;
case QEvent::WindowActivate: case QEvent::WindowActivate:
case QEvent::WindowDeactivate: case QEvent::WindowDeactivate:
@ -401,7 +396,7 @@ bool Widget::nativeEvent(const QByteArray &eventType, void *message, long *resul
switch (msg->message) { switch (msg->message) {
case WM_NCRBUTTONUP: { case WM_NCRBUTTONUP: {
if (msg->wParam == HTCAPTION) { if (msg->wParam == HTCAPTION) {
if (WinNativeEventFilter::displaySystemMenu(msg->hwnd)) { if (WinNativeEventFilter::displaySystemMenu(windowHandle())) {
*result = 0; *result = 0;
return true; return true;
} }
@ -445,8 +440,8 @@ void Widget::paintEvent(QPaintEvent *event)
void Widget::updateWindow() void Widget::updateWindow()
{ {
WinNativeEventFilter::updateFrameMargins(rawHandle()); WinNativeEventFilter::updateFrameMargins(windowHandle());
WinNativeEventFilter::updateWindow(rawHandle(), true, true); WinNativeEventFilter::updateWindow(windowHandle(), true, true);
update(); update();
} }
@ -503,7 +498,7 @@ void Widget::initializeOptions()
if (m_bIsWin10OrGreater) { if (m_bIsWin10OrGreater) {
//preserveWindowFrameCB->click(); //preserveWindowFrameCB->click();
if (m_bCanAcrylicBeEnabled) { if (m_bCanAcrylicBeEnabled) {
forceAcrylicCB->click(); //forceAcrylicCB->click();
} }
} }
customizeTitleBarCB->click(); customizeTitleBarCB->click();
@ -515,12 +510,6 @@ void Widget::initializeOptions()
void Widget::setupConnections() void Widget::setupConnections()
{ {
connect(iconButton, &QPushButton::clicked, this, [this]() {
POINT pos = {};
GetCursorPos(&pos);
const auto hwnd = reinterpret_cast<HWND>(rawHandle());
SendMessageW(hwnd, WM_CONTEXTMENU, reinterpret_cast<WPARAM>(hwnd), MAKELPARAM(pos.x, pos.y));
});
connect(minimizeButton, &QPushButton::clicked, this, &Widget::showMinimized); connect(minimizeButton, &QPushButton::clicked, this, &Widget::showMinimized);
connect(maximizeButton, &QPushButton::clicked, this, [this]() { connect(maximizeButton, &QPushButton::clicked, this, [this]() {
if (isMaximized()) { if (isMaximized()) {
@ -531,7 +520,7 @@ void Widget::setupConnections()
}); });
connect(closeButton, &QPushButton::clicked, this, &Widget::close); connect(closeButton, &QPushButton::clicked, this, &Widget::close);
connect(moveCenterButton, &QPushButton::clicked, this, [this]() { connect(moveCenterButton, &QPushButton::clicked, this, [this]() {
WinNativeEventFilter::moveWindowToDesktopCenter(rawHandle()); WinNativeEventFilter::moveWindowToDesktopCenter(windowHandle());
}); });
connect(this, &Widget::windowTitleChanged, titleLabel, &QLabel::setText); connect(this, &Widget::windowTitleChanged, titleLabel, &QLabel::setText);
connect(this, &Widget::windowIconChanged, iconButton, &QPushButton::setIcon); connect(this, &Widget::windowIconChanged, iconButton, &QPushButton::setIcon);
@ -540,7 +529,7 @@ void Widget::setupConnections()
preserveWindowFrameCB->setEnabled(enable); preserveWindowFrameCB->setEnabled(enable);
WinNativeEventFilter::updateQtFrame(windowHandle(), WinNativeEventFilter::updateQtFrame(windowHandle(),
enable ? WinNativeEventFilter::getSystemMetric( enable ? WinNativeEventFilter::getSystemMetric(
rawHandle(), windowHandle(),
WinNativeEventFilter::SystemMetric::TitleBarHeight) WinNativeEventFilter::SystemMetric::TitleBarHeight)
: 0); : 0);
titleBarWidget->setVisible(enable); titleBarWidget->setVisible(enable);
@ -589,7 +578,7 @@ void Widget::setupConnections()
palette.setColor(QPalette::Window, Qt::transparent); palette.setColor(QPalette::Window, Qt::transparent);
} }
setPalette(palette); setPalette(palette);
WinNativeEventFilter::setBlurEffectEnabled(rawHandle(), enable, color); WinNativeEventFilter::setBlurEffectEnabled(windowHandle(), enable, color);
updateWindow(); updateWindow();
if (useAcrylicEffect && enable && WinNativeEventFilter::isTransparencyEffectEnabled()) { if (useAcrylicEffect && enable && WinNativeEventFilter::isTransparencyEffectEnabled()) {
QMessageBox::warning(this, QMessageBox::warning(this,
@ -621,7 +610,7 @@ void Widget::setupConnections()
connect(resizableCB, &QCheckBox::stateChanged, this, [this](int state) { connect(resizableCB, &QCheckBox::stateChanged, this, [this](int state) {
const bool enable = state == Qt::Checked; const bool enable = state == Qt::Checked;
maximizeButton->setEnabled(enable); maximizeButton->setEnabled(enable);
WinNativeEventFilter::setWindowResizable(rawHandle(), enable); WinNativeEventFilter::setWindowResizable(windowHandle(), enable);
}); });
} }
@ -629,7 +618,7 @@ void Widget::initializeFramelessFunctions()
{ {
WinNativeEventFilter::WINDOWDATA data = {}; WinNativeEventFilter::WINDOWDATA data = {};
data.ignoreObjects << iconButton << minimizeButton << maximizeButton << closeButton; data.ignoreObjects << iconButton << minimizeButton << maximizeButton << closeButton;
WinNativeEventFilter::addFramelessWindow(rawHandle(), &data); WinNativeEventFilter::addFramelessWindow(windowHandle(), &data);
installEventFilter(this); installEventFilter(this);
} }

View File

@ -68,8 +68,6 @@ public:
explicit Widget(QWidget *parent = nullptr); explicit Widget(QWidget *parent = nullptr);
~Widget() override = default; ~Widget() override = default;
void *rawHandle() const;
bool isNormaled() const; bool isNormaled() const;
bool shouldDrawBorder(const bool ignoreWindowState = false) const; bool shouldDrawBorder(const bool ignoreWindowState = false) const;

View File

@ -31,34 +31,15 @@
#include <QOperatingSystemVersion> #include <QOperatingSystemVersion>
#endif #endif
#ifdef Q_OS_WINDOWS
namespace { namespace {
#ifdef Q_OS_WINDOWS
const char g_sPreserveWindowFrame[] = "WNEF_FORCE_PRESERVE_WINDOW_FRAME"; const char g_sPreserveWindowFrame[] = "WNEF_FORCE_PRESERVE_WINDOW_FRAME";
const char g_sDontExtendFrame[] = "WNEF_DO_NOT_EXTEND_FRAME"; const char g_sDontExtendFrame[] = "WNEF_DO_NOT_EXTEND_FRAME";
const char g_sForceUseAcrylicEffect[] = "WNEF_FORCE_ACRYLIC_ON_WIN10"; const char g_sForceUseAcrylicEffect[] = "WNEF_FORCE_ACRYLIC_ON_WIN10";
#endif
FramelessWindowsManager::WindowId getWindowId(QObject *object)
{
Q_ASSERT(object);
if (!object->isWindowType()) {
qWarning() << object << "is not a window!";
return nullptr;
}
const auto window = qobject_cast<QWindow *>(object);
if (!window) {
qWarning() << "Failed to convert" << object << "to QWindow!";
return nullptr;
}
#ifdef Q_OS_WINDOWS
return reinterpret_cast<FramelessWindowsManager::WindowId>(window->winId());
#else
return static_cast<FramelessWindowsManager::WindowId>(window);
#endif
}
} // namespace } // namespace
#endif
FramelessQuickHelper::FramelessQuickHelper(QQuickItem *parent) : QQuickItem(parent) FramelessQuickHelper::FramelessQuickHelper(QQuickItem *parent) : QQuickItem(parent)
{ {
@ -69,56 +50,56 @@ FramelessQuickHelper::FramelessQuickHelper(QQuickItem *parent) : QQuickItem(pare
int FramelessQuickHelper::borderWidth() const int FramelessQuickHelper::borderWidth() const
{ {
return FramelessWindowsManager::getBorderWidth(getWindowId(window())); return FramelessWindowsManager::getBorderWidth(window());
} }
void FramelessQuickHelper::setBorderWidth(const int val) void FramelessQuickHelper::setBorderWidth(const int val)
{ {
FramelessWindowsManager::setBorderWidth(getWindowId(window()), val); FramelessWindowsManager::setBorderWidth(window(), val);
Q_EMIT borderWidthChanged(val); Q_EMIT borderWidthChanged(val);
} }
int FramelessQuickHelper::borderHeight() const int FramelessQuickHelper::borderHeight() const
{ {
return FramelessWindowsManager::getBorderHeight(getWindowId(window())); return FramelessWindowsManager::getBorderHeight(window());
} }
void FramelessQuickHelper::setBorderHeight(const int val) void FramelessQuickHelper::setBorderHeight(const int val)
{ {
FramelessWindowsManager::setBorderHeight(getWindowId(window()), val); FramelessWindowsManager::setBorderHeight(window(), val);
Q_EMIT borderHeightChanged(val); Q_EMIT borderHeightChanged(val);
} }
int FramelessQuickHelper::titleBarHeight() const int FramelessQuickHelper::titleBarHeight() const
{ {
return FramelessWindowsManager::getTitleBarHeight(getWindowId(window())); return FramelessWindowsManager::getTitleBarHeight(window());
} }
void FramelessQuickHelper::setTitleBarHeight(const int val) void FramelessQuickHelper::setTitleBarHeight(const int val)
{ {
FramelessWindowsManager::setTitleBarHeight(getWindowId(window()), val); FramelessWindowsManager::setTitleBarHeight(window(), val);
Q_EMIT titleBarHeightChanged(val); Q_EMIT titleBarHeightChanged(val);
} }
bool FramelessQuickHelper::resizable() const bool FramelessQuickHelper::resizable() const
{ {
return FramelessWindowsManager::getResizable(getWindowId(window())); return FramelessWindowsManager::getResizable(window());
} }
void FramelessQuickHelper::setResizable(const bool val) void FramelessQuickHelper::setResizable(const bool val)
{ {
FramelessWindowsManager::setResizable(getWindowId(window()), val); FramelessWindowsManager::setResizable(window(), val);
Q_EMIT resizableChanged(val); Q_EMIT resizableChanged(val);
} }
bool FramelessQuickHelper::titleBarEnabled() const bool FramelessQuickHelper::titleBarEnabled() const
{ {
return FramelessWindowsManager::getTitleBarEnabled(getWindowId(window())); return FramelessWindowsManager::getTitleBarEnabled(window());
} }
void FramelessQuickHelper::setTitleBarEnabled(const bool val) void FramelessQuickHelper::setTitleBarEnabled(const bool val)
{ {
FramelessWindowsManager::setTitleBarEnabled(getWindowId(window()), val); FramelessWindowsManager::setTitleBarEnabled(window(), val);
Q_EMIT titleBarEnabledChanged(val); Q_EMIT titleBarEnabledChanged(val);
} }
@ -155,7 +136,7 @@ bool FramelessQuickHelper::highContrastModeEnabled() const
bool FramelessQuickHelper::darkFrameEnabled() const bool FramelessQuickHelper::darkFrameEnabled() const
{ {
return WinNativeEventFilter::isDarkFrameEnabled(rawWindowHandle()); return WinNativeEventFilter::isDarkFrameEnabled(window());
} }
bool FramelessQuickHelper::transparencyEffectEnabled() const bool FramelessQuickHelper::transparencyEffectEnabled() const
@ -166,56 +147,56 @@ bool FramelessQuickHelper::transparencyEffectEnabled() const
QSize FramelessQuickHelper::minimumSize() const QSize FramelessQuickHelper::minimumSize() const
{ {
return FramelessWindowsManager::getMinimumSize(getWindowId(window())); return FramelessWindowsManager::getMinimumSize(window());
} }
void FramelessQuickHelper::setMinimumSize(const QSize &val) void FramelessQuickHelper::setMinimumSize(const QSize &val)
{ {
FramelessWindowsManager::setMinimumSize(getWindowId(window()), val); FramelessWindowsManager::setMinimumSize(window(), val);
Q_EMIT minimumSizeChanged(val); Q_EMIT minimumSizeChanged(val);
} }
QSize FramelessQuickHelper::maximumSize() const QSize FramelessQuickHelper::maximumSize() const
{ {
return FramelessWindowsManager::getMaximumSize(getWindowId(window())); return FramelessWindowsManager::getMaximumSize(window());
} }
void FramelessQuickHelper::setMaximumSize(const QSize &val) void FramelessQuickHelper::setMaximumSize(const QSize &val)
{ {
FramelessWindowsManager::setMaximumSize(getWindowId(window()), val); FramelessWindowsManager::setMaximumSize(window(), val);
Q_EMIT maximumSizeChanged(val); Q_EMIT maximumSizeChanged(val);
} }
void FramelessQuickHelper::removeWindowFrame(const bool center) void FramelessQuickHelper::removeWindowFrame(const bool center)
{ {
FramelessWindowsManager::addWindow(getWindowId(window()), center); FramelessWindowsManager::addWindow(window(), center);
} }
void FramelessQuickHelper::moveWindowToDesktopCenter() void FramelessQuickHelper::moveWindowToDesktopCenter()
{ {
FramelessWindowsManager::moveWindowToDesktopCenter(getWindowId(window())); FramelessWindowsManager::moveWindowToDesktopCenter(window());
} }
void FramelessQuickHelper::addIgnoreArea(const QRect &val) void FramelessQuickHelper::addIgnoreArea(const QRect &val)
{ {
FramelessWindowsManager::addIgnoreArea(getWindowId(window()), val); FramelessWindowsManager::addIgnoreArea(window(), val);
} }
void FramelessQuickHelper::addDraggableArea(const QRect &val) void FramelessQuickHelper::addDraggableArea(const QRect &val)
{ {
FramelessWindowsManager::addDraggableArea(getWindowId(window()), val); FramelessWindowsManager::addDraggableArea(window(), val);
} }
void FramelessQuickHelper::addIgnoreObject(QQuickItem *val) void FramelessQuickHelper::addIgnoreObject(QQuickItem *val)
{ {
Q_ASSERT(val); Q_ASSERT(val);
FramelessWindowsManager::addIgnoreObject(getWindowId(window()), val); FramelessWindowsManager::addIgnoreObject(window(), val);
} }
void FramelessQuickHelper::addDraggableObject(QQuickItem *val) void FramelessQuickHelper::addDraggableObject(QQuickItem *val)
{ {
Q_ASSERT(val); Q_ASSERT(val);
FramelessWindowsManager::addDraggableObject(getWindowId(window()), val); FramelessWindowsManager::addDraggableObject(window(), val);
} }
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -231,15 +212,6 @@ void FramelessQuickHelper::timerEvent(QTimerEvent *event)
Q_EMIT transparencyEffectEnabledChanged(transparencyEffectEnabled()); Q_EMIT transparencyEffectEnabledChanged(transparencyEffectEnabled());
} }
void *FramelessQuickHelper::rawWindowHandle() const
{
const QWindow *win = window();
if (win) {
return reinterpret_cast<void *>(win->winId());
}
return nullptr;
}
void FramelessQuickHelper::setWindowFrameVisible(const bool value) void FramelessQuickHelper::setWindowFrameVisible(const bool value)
{ {
if (value) { if (value) {
@ -253,7 +225,7 @@ void FramelessQuickHelper::setWindowFrameVisible(const bool value)
void FramelessQuickHelper::displaySystemMenu(const QPointF &pos) void FramelessQuickHelper::displaySystemMenu(const QPointF &pos)
{ {
WinNativeEventFilter::displaySystemMenu(rawWindowHandle(), pos); WinNativeEventFilter::displaySystemMenu(window(), pos);
} }
void FramelessQuickHelper::setBlurEffectEnabled(const bool enabled, void FramelessQuickHelper::setBlurEffectEnabled(const bool enabled,
@ -265,6 +237,6 @@ void FramelessQuickHelper::setBlurEffectEnabled(const bool enabled,
} else { } else {
qunsetenv(g_sForceUseAcrylicEffect); qunsetenv(g_sForceUseAcrylicEffect);
} }
WinNativeEventFilter::setBlurEffectEnabled(rawWindowHandle(), enabled, gradientColor); WinNativeEventFilter::setBlurEffectEnabled(window(), enabled, gradientColor);
} }
#endif #endif

View File

@ -128,9 +128,6 @@ public Q_SLOTS:
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
protected: protected:
void timerEvent(QTimerEvent *event) override; void timerEvent(QTimerEvent *event) override;
private:
void *rawWindowHandle() const;
#endif #endif
Q_SIGNALS: Q_SIGNALS:

View File

@ -24,10 +24,7 @@
#include "framelesswindowsmanager.h" #include "framelesswindowsmanager.h"
#ifndef Q_OS_WINDOWS
#include <QGuiApplication>
#include <QWindow> #include <QWindow>
#endif
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
#include "winnativeeventfilter.h" #include "winnativeeventfilter.h"
@ -38,12 +35,6 @@
#ifndef Q_OS_WINDOWS #ifndef Q_OS_WINDOWS
namespace { namespace {
QWindow *toWindow(QObject *object)
{
Q_ASSERT(object);
return object->isWindowType() ? qobject_cast<QWindow *>(object) : nullptr;
}
using FLWM_CORE_DATA = struct _FLWM_CORE_DATA using FLWM_CORE_DATA = struct _FLWM_CORE_DATA
{ {
FramelessHelper framelessHelper; FramelessHelper framelessHelper;
@ -58,7 +49,7 @@ Q_GLOBAL_STATIC(FLWM_CORE_DATA, coreData)
FramelessWindowsManager::FramelessWindowsManager() = default; FramelessWindowsManager::FramelessWindowsManager() = default;
void FramelessWindowsManager::addWindow(WindowId window, const bool center) void FramelessWindowsManager::addWindow(const QWindow *window, const bool center)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -71,7 +62,7 @@ void FramelessWindowsManager::addWindow(WindowId window, const bool center)
} }
} }
void FramelessWindowsManager::moveWindowToDesktopCenter(WindowId window) void FramelessWindowsManager::moveWindowToDesktopCenter(const QWindow *window)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -81,7 +72,7 @@ void FramelessWindowsManager::moveWindowToDesktopCenter(WindowId window)
#endif #endif
} }
void FramelessWindowsManager::addIgnoreArea(WindowId window, const QRect &area) void FramelessWindowsManager::addIgnoreArea(const QWindow *window, const QRect &area)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -94,7 +85,7 @@ void FramelessWindowsManager::addIgnoreArea(WindowId window, const QRect &area)
#endif #endif
} }
void FramelessWindowsManager::addDraggableArea(WindowId window, const QRect &area) void FramelessWindowsManager::addDraggableArea(const QWindow *window, const QRect &area)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -107,7 +98,7 @@ void FramelessWindowsManager::addDraggableArea(WindowId window, const QRect &are
#endif #endif
} }
void FramelessWindowsManager::addIgnoreObject(WindowId window, QObject *object) void FramelessWindowsManager::addIgnoreObject(const QWindow *window, QObject *object)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -120,7 +111,7 @@ void FramelessWindowsManager::addIgnoreObject(WindowId window, QObject *object)
#endif #endif
} }
void FramelessWindowsManager::addDraggableObject(WindowId window, QObject *object) void FramelessWindowsManager::addDraggableObject(const QWindow *window, QObject *object)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -133,7 +124,7 @@ void FramelessWindowsManager::addDraggableObject(WindowId window, QObject *objec
#endif #endif
} }
int FramelessWindowsManager::getBorderWidth(WindowId window) int FramelessWindowsManager::getBorderWidth(const QWindow *window)
{ {
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
Q_ASSERT(window); Q_ASSERT(window);
@ -145,7 +136,7 @@ int FramelessWindowsManager::getBorderWidth(WindowId window)
#endif #endif
} }
void FramelessWindowsManager::setBorderWidth(WindowId window, const int value) void FramelessWindowsManager::setBorderWidth(const QWindow *window, const int value)
{ {
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
Q_ASSERT(window); Q_ASSERT(window);
@ -159,7 +150,7 @@ void FramelessWindowsManager::setBorderWidth(WindowId window, const int value)
#endif #endif
} }
int FramelessWindowsManager::getBorderHeight(WindowId window) int FramelessWindowsManager::getBorderHeight(const QWindow *window)
{ {
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
Q_ASSERT(window); Q_ASSERT(window);
@ -171,7 +162,7 @@ int FramelessWindowsManager::getBorderHeight(WindowId window)
#endif #endif
} }
void FramelessWindowsManager::setBorderHeight(WindowId window, const int value) void FramelessWindowsManager::setBorderHeight(const QWindow *window, const int value)
{ {
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
Q_ASSERT(window); Q_ASSERT(window);
@ -185,7 +176,7 @@ void FramelessWindowsManager::setBorderHeight(WindowId window, const int value)
#endif #endif
} }
int FramelessWindowsManager::getTitleBarHeight(WindowId window) int FramelessWindowsManager::getTitleBarHeight(const QWindow *window)
{ {
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
Q_ASSERT(window); Q_ASSERT(window);
@ -197,7 +188,7 @@ int FramelessWindowsManager::getTitleBarHeight(WindowId window)
#endif #endif
} }
void FramelessWindowsManager::setTitleBarHeight(WindowId window, const int value) void FramelessWindowsManager::setTitleBarHeight(const QWindow *window, const int value)
{ {
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
Q_ASSERT(window); Q_ASSERT(window);
@ -211,7 +202,7 @@ void FramelessWindowsManager::setTitleBarHeight(WindowId window, const int value
#endif #endif
} }
bool FramelessWindowsManager::getResizable(WindowId window) bool FramelessWindowsManager::getResizable(const QWindow *window)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -222,7 +213,7 @@ bool FramelessWindowsManager::getResizable(WindowId window)
#endif #endif
} }
void FramelessWindowsManager::setResizable(WindowId window, const bool value) void FramelessWindowsManager::setResizable(const QWindow *window, const bool value)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -232,19 +223,18 @@ void FramelessWindowsManager::setResizable(WindowId window, const bool value)
#endif #endif
} }
QSize FramelessWindowsManager::getMinimumSize(WindowId window) QSize FramelessWindowsManager::getMinimumSize(const QWindow *window)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
const auto data = WinNativeEventFilter::getWindowData(window); const auto data = WinNativeEventFilter::getWindowData(window);
return data ? data->minimumSize : QSize(); return data ? data->minimumSize : QSize();
#else #else
const auto win = toWindow(window); return window->minimumSize();
return win ? win->minimumSize() : QSize();
#endif #endif
} }
void FramelessWindowsManager::setMinimumSize(WindowId window, const QSize &value) void FramelessWindowsManager::setMinimumSize(const QWindow *window, const QSize &value)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -253,26 +243,22 @@ void FramelessWindowsManager::setMinimumSize(WindowId window, const QSize &value
data->minimumSize = value; data->minimumSize = value;
} }
#else #else
const auto win = toWindow(window); window->setMinimumSize(value);
if (win) {
win->setMinimumSize(value);
}
#endif #endif
} }
QSize FramelessWindowsManager::getMaximumSize(WindowId window) QSize FramelessWindowsManager::getMaximumSize(const QWindow *window)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
const auto data = WinNativeEventFilter::getWindowData(window); const auto data = WinNativeEventFilter::getWindowData(window);
return data ? data->maximumSize : QSize(); return data ? data->maximumSize : QSize();
#else #else
const auto win = toWindow(window); return window->maximumSize();
return win ? win->maximumSize() : QSize();
#endif #endif
} }
void FramelessWindowsManager::setMaximumSize(WindowId window, const QSize &value) void FramelessWindowsManager::setMaximumSize(const QWindow *window, const QSize &value)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -281,14 +267,11 @@ void FramelessWindowsManager::setMaximumSize(WindowId window, const QSize &value
data->maximumSize = value; data->maximumSize = value;
} }
#else #else
const auto win = toWindow(window); window->setMaximumSize(value);
if (win) {
win->setMaximumSize(value);
}
#endif #endif
} }
bool FramelessWindowsManager::getTitleBarEnabled(WindowId window) bool FramelessWindowsManager::getTitleBarEnabled(const QWindow *window)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS
@ -299,7 +282,7 @@ bool FramelessWindowsManager::getTitleBarEnabled(WindowId window)
#endif #endif
} }
void FramelessWindowsManager::setTitleBarEnabled(WindowId window, const bool value) void FramelessWindowsManager::setTitleBarEnabled(const QWindow *window, const bool value)
{ {
Q_ASSERT(window); Q_ASSERT(window);
#ifdef Q_OS_WINDOWS #ifdef Q_OS_WINDOWS

View File

@ -34,6 +34,7 @@
QT_BEGIN_NAMESPACE QT_BEGIN_NAMESPACE
QT_FORWARD_DECLARE_CLASS(QObject) QT_FORWARD_DECLARE_CLASS(QObject)
QT_FORWARD_DECLARE_CLASS(QWindow)
QT_END_NAMESPACE QT_END_NAMESPACE
#if (QT_VERSION < QT_VERSION_CHECK(5, 13, 0)) #if (QT_VERSION < QT_VERSION_CHECK(5, 13, 0))
@ -51,45 +52,37 @@ class FRAMELESSHELPER_EXPORT FramelessWindowsManager
Q_DISABLE_COPY_MOVE(FramelessWindowsManager) Q_DISABLE_COPY_MOVE(FramelessWindowsManager)
public: public:
using WindowId =
#ifdef Q_OS_WINDOWS
void *
#else
QObject *
#endif
;
explicit FramelessWindowsManager(); explicit FramelessWindowsManager();
~FramelessWindowsManager() = default; ~FramelessWindowsManager() = default;
static void addWindow(WindowId window, const bool center = false); static void addWindow(const QWindow *window, const bool center = false);
static void moveWindowToDesktopCenter(WindowId window); static void moveWindowToDesktopCenter(const QWindow *window);
static void addIgnoreArea(WindowId window, const QRect &area); static void addIgnoreArea(const QWindow *window, const QRect &area);
static void addDraggableArea(WindowId window, const QRect &area); static void addDraggableArea(const QWindow *window, const QRect &area);
static void addIgnoreObject(WindowId window, QObject *object); static void addIgnoreObject(const QWindow *window, QObject *object);
static void addDraggableObject(WindowId window, QObject *object); static void addDraggableObject(const QWindow *window, QObject *object);
static int getBorderWidth(WindowId window); static int getBorderWidth(const QWindow *window);
static void setBorderWidth(WindowId window, const int value); static void setBorderWidth(const QWindow *window, const int value);
static int getBorderHeight(WindowId window); static int getBorderHeight(const QWindow *window);
static void setBorderHeight(WindowId window, const int value); static void setBorderHeight(const QWindow *window, const int value);
static int getTitleBarHeight(WindowId window); static int getTitleBarHeight(const QWindow *window);
static void setTitleBarHeight(WindowId window, const int value); static void setTitleBarHeight(const QWindow *window, const int value);
static bool getResizable(WindowId window); static bool getResizable(const QWindow *window);
static void setResizable(WindowId window, const bool value = true); static void setResizable(const QWindow *window, const bool value = true);
static QSize getMinimumSize(WindowId window); static QSize getMinimumSize(const QWindow *window);
static void setMinimumSize(WindowId window, const QSize &value); static void setMinimumSize(const QWindow *window, const QSize &value);
static QSize getMaximumSize(WindowId window); static QSize getMaximumSize(const QWindow *window);
static void setMaximumSize(WindowId window, const QSize &value); static void setMaximumSize(const QWindow *window, const QSize &value);
static bool getTitleBarEnabled(WindowId window); static bool getTitleBarEnabled(const QWindow *window);
static void setTitleBarEnabled(WindowId window, const bool value = true); static void setTitleBarEnabled(const QWindow *window, const bool value = true);
}; };

File diff suppressed because it is too large Load Diff

View File

@ -72,23 +72,23 @@ public:
// The width and height will be scaled automatically according to DPI. Don't // The width and height will be scaled automatically according to DPI. Don't
// scale them yourself. Just pass the original value. If you don't want to // scale them yourself. Just pass the original value. If you don't want to
// change them, pass negative values to the parameters. // change them, pass negative values to the parameters.
static void addFramelessWindow(void *window /* HWND */, static void addFramelessWindow(const QWindow *window,
const WINDOWDATA *data = nullptr, const WINDOWDATA *data = nullptr,
const bool center = false, const bool center = false,
const int x = -1, const int x = -1,
const int y = -1, const int y = -1,
const int width = -1, const int width = -1,
const int height = -1); const int height = -1);
static void removeFramelessWindow(void *window /* HWND */); static void removeFramelessWindow(const QWindow *window);
// Set borderWidth, borderHeight or titleBarHeight to a negative value to // Set borderWidth, borderHeight or titleBarHeight to a negative value to
// restore default behavior. // restore default behavior.
// Note that it can only affect one specific window. // Note that it can only affect one specific window.
// If you want to change these values globally, use setBorderWidth instead. // If you want to change these values globally, use setBorderWidth instead.
static void setWindowData(void *window /* HWND */, const WINDOWDATA *data); static void setWindowData(const QWindow *window, const WINDOWDATA *data);
// You can modify the given window's data directly, it's the same with using // You can modify the given window's data directly, it's the same with using
// setWindowData. // setWindowData.
static WINDOWDATA *getWindowData(void *window /* HWND */); static WINDOWDATA *getWindowData(const QWindow *window);
// Change settings globally, not a specific window. // Change settings globally, not a specific window.
// These values will be scaled automatically according to DPI, don't scale // These values will be scaled automatically according to DPI, don't scale
@ -99,14 +99,14 @@ public:
// System metric value of the given window (if the pointer is null, // System metric value of the given window (if the pointer is null,
// return the system's standard value). // return the system's standard value).
static int getSystemMetric(void *handle /* HWND */, static int getSystemMetric(const QWindow *window,
const SystemMetric metric, const SystemMetric metric,
const bool dpiAware = false); const bool dpiAware = false);
// Use this function to trigger a frame change event or redraw a // Use this function to trigger a frame change event or redraw a
// specific window. Useful when you want to let some changes // specific window. Useful when you want to let some changes
// in effect immediately. // in effect immediately.
static void updateWindow(void *handle /* HWND */, static void updateWindow(const QWindow *window,
const bool triggerFrameChange = true, const bool triggerFrameChange = true,
const bool redraw = true); const bool redraw = true);
@ -114,10 +114,10 @@ public:
// The width and height will be scaled automatically according to DPI. So // The width and height will be scaled automatically according to DPI. So
// just pass the original value. // just pass the original value.
static void setWindowGeometry( static void setWindowGeometry(
void *handle /* HWND */, const int x, const int y, const int width, const int height); const QWindow *window, const int x, const int y, const int width, const int height);
// Move the window to the center of the desktop. // Move the window to the center of the desktop.
static void moveWindowToDesktopCenter(void *handle /* HWND */); static void moveWindowToDesktopCenter(const QWindow *window);
// Update Qt's internal data about the window frame, otherwise Qt will // Update Qt's internal data about the window frame, otherwise Qt will
// take the size of the window frame into account when anyone is trying to // take the size of the window frame into account when anyone is trying to
@ -125,20 +125,20 @@ public:
static void updateQtFrame(QWindow *window, const int titleBarHeight); static void updateQtFrame(QWindow *window, const int titleBarHeight);
// Display the system context menu. // Display the system context menu.
static bool displaySystemMenu(void *handle /* HWND */, const QPointF &pos = {}); static bool displaySystemMenu(const QWindow *window, const QPointF &pos = {});
// Enable or disable the blur effect for a specific window. // Enable or disable the blur effect for a specific window.
// On Win10 it's the Acrylic effect. // On Win10 it's the Acrylic effect.
static bool setBlurEffectEnabled(void *handle /* HWND */, static bool setBlurEffectEnabled(const QWindow *window,
const bool enabled = true, const bool enabled = true,
const QColor &gradientColor = Qt::white); const QColor &gradientColor = Qt::white);
// Thin wrapper of DwmExtendFrameIntoClientArea(). // Thin wrapper of DwmExtendFrameIntoClientArea().
static void updateFrameMargins(void *handle /* HWND */); static void updateFrameMargins(const QWindow *window);
// A resizable window can be resized and maximized, however, a fixed size // A resizable window can be resized and maximized, however, a fixed size
// window can only be moved and minimized, it can't be resized and maximized. // window can only be moved and minimized, it can't be resized and maximized.
static void setWindowResizable(void *handle /* HWND */, const bool resizable = true); static void setWindowResizable(const QWindow *window, const bool resizable = true);
// Query whether colorization is enabled or not. // Query whether colorization is enabled or not.
static bool isColorizationEnabled(); static bool isColorizationEnabled();
@ -156,7 +156,7 @@ public:
static bool isHighContrastModeEnabled(); static bool isHighContrastModeEnabled();
// Query whether the given window is using dark frame or not. // Query whether the given window is using dark frame or not.
static bool isDarkFrameEnabled(void *handle /* HWND */); static bool isDarkFrameEnabled(const QWindow *window);
// Query whether the transparency effect is enabled or not. // Query whether the transparency effect is enabled or not.
static bool isTransparencyEffectEnabled(); static bool isTransparencyEffectEnabled();