Simplify Windows native event filter
There's no need for a global event filter as it checks for the window hwnd anyway. And, moreover, that creates problems as Qt filters some events to global event filters.
This commit is contained in:
parent
a714fb0070
commit
ce35425670
6 changed files with 56 additions and 63 deletions
|
|
@ -70,6 +70,13 @@ rpl::producer<HitTestResult> BasicWindowHelper::systemButtonDown() const {
|
||||||
return rpl::never<HitTestResult>();
|
return rpl::never<HitTestResult>();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool BasicWindowHelper::nativeEvent(
|
||||||
|
const QByteArray &eventType,
|
||||||
|
void *message,
|
||||||
|
base::NativeEventResult *result) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
void BasicWindowHelper::setTitle(const QString &title) {
|
void BasicWindowHelper::setTitle(const QString &title) {
|
||||||
_window->setWindowTitle(title);
|
_window->setWindowTitle(title);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -8,6 +8,7 @@
|
||||||
|
|
||||||
#include "base/flags.h"
|
#include "base/flags.h"
|
||||||
#include "base/object_ptr.h"
|
#include "base/object_ptr.h"
|
||||||
|
#include "base/qt/qt_common_adapters.h"
|
||||||
#include "ui/round_rect.h"
|
#include "ui/round_rect.h"
|
||||||
|
|
||||||
namespace style {
|
namespace style {
|
||||||
|
|
@ -48,6 +49,10 @@ public:
|
||||||
-> rpl::producer<HitTestResult>;
|
-> rpl::producer<HitTestResult>;
|
||||||
[[nodiscard]] virtual auto systemButtonDown() const
|
[[nodiscard]] virtual auto systemButtonDown() const
|
||||||
-> rpl::producer<HitTestResult>;
|
-> rpl::producer<HitTestResult>;
|
||||||
|
[[nodiscard]] virtual bool nativeEvent(
|
||||||
|
const QByteArray &eventType,
|
||||||
|
void *message,
|
||||||
|
base::NativeEventResult *result);
|
||||||
virtual void setTitle(const QString &title);
|
virtual void setTitle(const QString &title);
|
||||||
virtual void setTitleStyle(const style::WindowTitle &st);
|
virtual void setTitleStyle(const style::WindowTitle &st);
|
||||||
virtual void setNativeFrame(bool enabled);
|
virtual void setNativeFrame(bool enabled);
|
||||||
|
|
|
||||||
|
|
@ -18,7 +18,6 @@
|
||||||
#include "styles/palette.h"
|
#include "styles/palette.h"
|
||||||
#include "styles/style_widgets.h"
|
#include "styles/style_widgets.h"
|
||||||
|
|
||||||
#include <QtCore/QAbstractNativeEventFilter>
|
|
||||||
#include <QtGui/QWindow>
|
#include <QtGui/QWindow>
|
||||||
#include <QtWidgets/QStyleFactory>
|
#include <QtWidgets/QStyleFactory>
|
||||||
#include <QtWidgets/QApplication>
|
#include <QtWidgets/QApplication>
|
||||||
|
|
@ -140,50 +139,6 @@ BOOL(__stdcall *AdjustWindowRectExForDpi)(
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
class WindowHelper::NativeFilter final : public QAbstractNativeEventFilter {
|
|
||||||
public:
|
|
||||||
void registerWindow(HWND handle, not_null<WindowHelper*> helper);
|
|
||||||
void unregisterWindow(HWND handle);
|
|
||||||
|
|
||||||
bool nativeEventFilter(
|
|
||||||
const QByteArray &eventType,
|
|
||||||
void *message,
|
|
||||||
long *result) override;
|
|
||||||
|
|
||||||
private:
|
|
||||||
base::flat_map<HWND, not_null<WindowHelper*>> _windowByHandle;
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
void WindowHelper::NativeFilter::registerWindow(
|
|
||||||
HWND handle,
|
|
||||||
not_null<WindowHelper*> helper) {
|
|
||||||
_windowByHandle.emplace(handle, helper);
|
|
||||||
}
|
|
||||||
|
|
||||||
void WindowHelper::NativeFilter::unregisterWindow(HWND handle) {
|
|
||||||
_windowByHandle.remove(handle);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool WindowHelper::NativeFilter::nativeEventFilter(
|
|
||||||
const QByteArray &eventType,
|
|
||||||
void *message,
|
|
||||||
long *result) {
|
|
||||||
auto filtered = false;
|
|
||||||
const auto msg = static_cast<MSG*>(message);
|
|
||||||
const auto i = _windowByHandle.find(msg->hwnd);
|
|
||||||
if (i != end(_windowByHandle)) {
|
|
||||||
base::Integration::Instance().enterFromEventLoop([&] {
|
|
||||||
filtered = i->second->handleNativeEvent(
|
|
||||||
msg->message,
|
|
||||||
msg->wParam,
|
|
||||||
msg->lParam,
|
|
||||||
reinterpret_cast<LRESULT*>(result));
|
|
||||||
});
|
|
||||||
}
|
|
||||||
return filtered;
|
|
||||||
}
|
|
||||||
|
|
||||||
WindowHelper::WindowHelper(not_null<RpWidget*> window)
|
WindowHelper::WindowHelper(not_null<RpWidget*> window)
|
||||||
: BasicWindowHelper(window)
|
: BasicWindowHelper(window)
|
||||||
, _handle(GetWindowHandle(window))
|
, _handle(GetWindowHandle(window))
|
||||||
|
|
@ -196,7 +151,6 @@ WindowHelper::WindowHelper(not_null<RpWidget*> window)
|
||||||
}
|
}
|
||||||
|
|
||||||
WindowHelper::~WindowHelper() {
|
WindowHelper::~WindowHelper() {
|
||||||
GetNativeFilter()->unregisterWindow(_handle);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void WindowHelper::initInWindow(not_null<RpWindow*> window) {
|
void WindowHelper::initInWindow(not_null<RpWindow*> window) {
|
||||||
|
|
@ -350,7 +304,6 @@ rpl::producer<HitTestResult> WindowHelper::systemButtonDown() const {
|
||||||
|
|
||||||
void WindowHelper::init() {
|
void WindowHelper::init() {
|
||||||
_title->show();
|
_title->show();
|
||||||
GetNativeFilter()->registerWindow(_handle, this);
|
|
||||||
|
|
||||||
style::PaletteChanged(
|
style::PaletteChanged(
|
||||||
) | rpl::start_with_next([=] {
|
) | rpl::start_with_next([=] {
|
||||||
|
|
@ -479,6 +432,22 @@ void WindowHelper::init() {
|
||||||
updateCornersRounding();
|
updateCornersRounding();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool WindowHelper::nativeEvent(
|
||||||
|
const QByteArray &eventType,
|
||||||
|
void *message,
|
||||||
|
base::NativeEventResult *result) {
|
||||||
|
const auto msg = static_cast<MSG*>(message);
|
||||||
|
auto lresult = LRESULT(*result);
|
||||||
|
const auto guard = gsl::finally([&] {
|
||||||
|
*result = base::NativeEventResult(lresult);
|
||||||
|
});
|
||||||
|
return handleNativeEvent(
|
||||||
|
msg->message,
|
||||||
|
msg->wParam,
|
||||||
|
msg->lParam,
|
||||||
|
&lresult);
|
||||||
|
}
|
||||||
|
|
||||||
bool WindowHelper::handleNativeEvent(
|
bool WindowHelper::handleNativeEvent(
|
||||||
UINT msg,
|
UINT msg,
|
||||||
WPARAM wParam,
|
WPARAM wParam,
|
||||||
|
|
@ -882,18 +851,6 @@ void WindowHelper::updateFrameMargins() {
|
||||||
_frameMargins = QMargins(0, -r.top, 0, 0) / window()->devicePixelRatioF();
|
_frameMargins = QMargins(0, -r.top, 0, 0) / window()->devicePixelRatioF();
|
||||||
}
|
}
|
||||||
|
|
||||||
not_null<WindowHelper::NativeFilter*> WindowHelper::GetNativeFilter() {
|
|
||||||
Expects(QCoreApplication::instance() != nullptr);
|
|
||||||
|
|
||||||
static const auto GlobalFilter = [&] {
|
|
||||||
const auto application = QCoreApplication::instance();
|
|
||||||
const auto filter = Ui::CreateChild<NativeFilter>(application);
|
|
||||||
application->installNativeEventFilter(filter);
|
|
||||||
return filter;
|
|
||||||
}();
|
|
||||||
return GlobalFilter;
|
|
||||||
}
|
|
||||||
|
|
||||||
HWND GetWindowHandle(not_null<QWidget*> widget) {
|
HWND GetWindowHandle(not_null<QWidget*> widget) {
|
||||||
const auto toplevel = widget->window();
|
const auto toplevel = widget->window();
|
||||||
toplevel->createWinId();
|
toplevel->createWinId();
|
||||||
|
|
|
||||||
|
|
@ -44,10 +44,12 @@ public:
|
||||||
[[nodiscard]] auto systemButtonDown() const
|
[[nodiscard]] auto systemButtonDown() const
|
||||||
-> rpl::producer<HitTestResult> override;
|
-> rpl::producer<HitTestResult> override;
|
||||||
|
|
||||||
private:
|
[[nodiscard]] bool nativeEvent(
|
||||||
class NativeFilter;
|
const QByteArray &eventType,
|
||||||
friend class NativeFilter;
|
void *message,
|
||||||
|
base::NativeEventResult *result) override;
|
||||||
|
|
||||||
|
private:
|
||||||
void init();
|
void init();
|
||||||
void updateFrameMargins();
|
void updateFrameMargins();
|
||||||
void updateWindowFrameColors();
|
void updateWindowFrameColors();
|
||||||
|
|
@ -70,7 +72,6 @@ private:
|
||||||
[[nodiscard]] HitTestResult systemButtonHitTest(int result) const;
|
[[nodiscard]] HitTestResult systemButtonHitTest(int result) const;
|
||||||
|
|
||||||
[[nodiscard]] int titleHeight() const;
|
[[nodiscard]] int titleHeight() const;
|
||||||
static not_null<NativeFilter*> GetNativeFilter();
|
|
||||||
|
|
||||||
const HWND _handle = nullptr;
|
const HWND _handle = nullptr;
|
||||||
const not_null<TitleWidget*> _title;
|
const not_null<TitleWidget*> _title;
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,8 @@ RpWindow::RpWindow(QWidget *parent)
|
||||||
|
|
||||||
_helper->initInWindow(this);
|
_helper->initInWindow(this);
|
||||||
hide();
|
hide();
|
||||||
|
|
||||||
|
_initialized = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
RpWindow::~RpWindow() = default;
|
RpWindow::~RpWindow() = default;
|
||||||
|
|
@ -99,4 +101,17 @@ void RpWindow::setBodyTitleArea(
|
||||||
_helper->setBodyTitleArea(std::move(testMethod));
|
_helper->setBodyTitleArea(std::move(testMethod));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool RpWindow::nativeEvent(
|
||||||
|
const QByteArray &eventType,
|
||||||
|
void *message,
|
||||||
|
base::NativeEventResult *result) {
|
||||||
|
if (_initialized && _helper->nativeEvent(
|
||||||
|
eventType,
|
||||||
|
message,
|
||||||
|
result)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return RpWidget::nativeEvent(eventType, message, result);
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace Ui
|
} // namespace Ui
|
||||||
|
|
|
||||||
|
|
@ -8,6 +8,7 @@
|
||||||
|
|
||||||
#include "ui/rp_widget.h"
|
#include "ui/rp_widget.h"
|
||||||
#include "base/flags.h"
|
#include "base/flags.h"
|
||||||
|
#include "base/qt/qt_common_adapters.h"
|
||||||
|
|
||||||
namespace style {
|
namespace style {
|
||||||
struct WindowTitle;
|
struct WindowTitle;
|
||||||
|
|
@ -67,7 +68,14 @@ public:
|
||||||
void close();
|
void close();
|
||||||
void setBodyTitleArea(Fn<WindowTitleHitTestFlags(QPoint)> testMethod);
|
void setBodyTitleArea(Fn<WindowTitleHitTestFlags(QPoint)> testMethod);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
bool nativeEvent(
|
||||||
|
const QByteArray &eventType,
|
||||||
|
void *message,
|
||||||
|
base::NativeEventResult *result) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
bool _initialized = false;
|
||||||
const std::unique_ptr<Platform::BasicWindowHelper> _helper;
|
const std::unique_ptr<Platform::BasicWindowHelper> _helper;
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue