From 90fb9eccd4f25266f9c77bc7c6ab473f643f32ab Mon Sep 17 00:00:00 2001 From: John Preston Date: Wed, 10 Jul 2019 17:03:15 +0200 Subject: [PATCH] Optimize InvokeQueued(). --- Telegram/SourceFiles/base/algorithm.h | 2 ++ Telegram/SourceFiles/base/invoke_queued.h | 42 +++++++++++++++++++++++ Telegram/SourceFiles/core/sandbox.cpp | 16 ++++++--- Telegram/SourceFiles/core/sandbox.h | 2 ++ Telegram/SourceFiles/core/utils.h | 8 +---- Telegram/SourceFiles/stdafx.h | 1 + 6 files changed, 60 insertions(+), 11 deletions(-) create mode 100644 Telegram/SourceFiles/base/invoke_queued.h diff --git a/Telegram/SourceFiles/base/algorithm.h b/Telegram/SourceFiles/base/algorithm.h index 9038d24def..a971e97042 100644 --- a/Telegram/SourceFiles/base/algorithm.h +++ b/Telegram/SourceFiles/base/algorithm.h @@ -7,6 +7,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL */ #pragma once +#include + namespace base { template diff --git a/Telegram/SourceFiles/base/invoke_queued.h b/Telegram/SourceFiles/base/invoke_queued.h new file mode 100644 index 0000000000..e7a91b1b9b --- /dev/null +++ b/Telegram/SourceFiles/base/invoke_queued.h @@ -0,0 +1,42 @@ +/* +This file is part of Telegram Desktop, +the official desktop application for the Telegram messaging service. + +For license and copyright information please follow this link: +https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL +*/ +#pragma once + +#include +#include + +#include "base/basic_types.h" + +namespace base { + +class InvokeQueuedEvent : public QEvent { +public: + static constexpr auto kType = QEvent::Type(60666); + + explicit InvokeQueuedEvent(FnMut &&method) + : QEvent(kType) + , _method(std::move(method)) { + } + + void invoke() { + _method(); + } + +private: + FnMut _method; + +}; + +} // namespace base + +template +inline void InvokeQueued(const QObject *context, Lambda &&lambda) { + QCoreApplication::postEvent( + const_cast(context), + new base::InvokeQueuedEvent(std::forward(lambda))); +} diff --git a/Telegram/SourceFiles/core/sandbox.cpp b/Telegram/SourceFiles/core/sandbox.cpp index 2f4e3b8203..7c1fd159e7 100644 --- a/Telegram/SourceFiles/core/sandbox.cpp +++ b/Telegram/SourceFiles/core/sandbox.cpp @@ -20,6 +20,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL #include "core/update_checker.h" #include "base/timer.h" #include "base/concurrent_timer.h" +#include "base/invoke_queued.h" #include "base/qthelp_url.h" #include "base/qthelp_regex.h" #include "ui/effects/animations.h" @@ -494,21 +495,28 @@ void Sandbox::registerEnterFromEventLoop() { } } +bool Sandbox::notifyOrInvoke(QObject *receiver, QEvent *e) { + if (e->type() == base::InvokeQueuedEvent::kType) { + static_cast(e)->invoke(); + return true; + } + return QApplication::notify(receiver, e); +} + bool Sandbox::notify(QObject *receiver, QEvent *e) { if (QThread::currentThreadId() != _mainThreadId) { - return QApplication::notify(receiver, e); + return notifyOrInvoke(receiver, e); } const auto wrap = createEventNestingLevel(); - const auto type = e->type(); - if (type == QEvent::UpdateRequest) { + if (e->type() == QEvent::UpdateRequest) { const auto weak = make_weak(receiver); _widgetUpdateRequests.fire({}); if (!weak) { return true; } } - return QApplication::notify(receiver, e); + return notifyOrInvoke(receiver, e); } void Sandbox::processPostponedCalls(int level) { diff --git a/Telegram/SourceFiles/core/sandbox.h b/Telegram/SourceFiles/core/sandbox.h index 5d8d8b208c..14194dd64a 100644 --- a/Telegram/SourceFiles/core/sandbox.h +++ b/Telegram/SourceFiles/core/sandbox.h @@ -71,6 +71,8 @@ private: FnMut callable; }; + bool notifyOrInvoke(QObject *receiver, QEvent *e); + void closeApplication(); // will be done in aboutToQuit() void checkForQuit(); // will be done in exec() void registerEnterFromEventLoop(); diff --git a/Telegram/SourceFiles/core/utils.h b/Telegram/SourceFiles/core/utils.h index 3f721a06dd..e74ab39ced 100644 --- a/Telegram/SourceFiles/core/utils.h +++ b/Telegram/SourceFiles/core/utils.h @@ -14,10 +14,10 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL #include "base/assertion.h" #include "base/bytes.h" +#include #include #include #include - #include #include @@ -55,12 +55,6 @@ inline bool in_range(Value &&value, From &&from, Till &&till) { // while "for_const (T *p, v)" won't and "for_const (T *&p, v)" won't compile #define for_const(range_declaration, range_expression) for (range_declaration : std::as_const(range_expression)) -template -inline void InvokeQueued(const QObject *context, Lambda &&lambda) { - QObject proxy; - QObject::connect(&proxy, &QObject::destroyed, context, std::forward(lambda), Qt::QueuedConnection); -} - static const int32 ScrollMax = INT_MAX; extern uint64 _SharedMemoryLocation[]; diff --git a/Telegram/SourceFiles/stdafx.h b/Telegram/SourceFiles/stdafx.h index c5735ee160..4a0c137658 100644 --- a/Telegram/SourceFiles/stdafx.h +++ b/Telegram/SourceFiles/stdafx.h @@ -68,6 +68,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL #include "base/variant.h" #include "base/optional.h" #include "base/algorithm.h" +#include "base/invoke_queued.h" #include "base/flat_set.h" #include "base/flat_map.h" #include "base/weak_ptr.h"