From 3a8e67e8abe3b09d4099cebe91ad5af02a4d8939 Mon Sep 17 00:00:00 2001 From: outfoxxed Date: Tue, 30 Jul 2024 12:19:59 -0700 Subject: [PATCH 1/2] core/util: move DropEmitter to utils and add generic accessor macros --- src/core/types.cpp | 19 ----------- src/core/types.hpp | 25 -------------- src/core/util.hpp | 81 ++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 81 insertions(+), 44 deletions(-) create mode 100644 src/core/util.hpp diff --git a/src/core/types.cpp b/src/core/types.cpp index d9c025f..5ed63a0 100644 --- a/src/core/types.cpp +++ b/src/core/types.cpp @@ -21,22 +21,3 @@ Qt::Edges Edges::toQt(Edges::Flags edges) { return Qt::Edges(edges.toInt()); } bool Edges::isOpposing(Edges::Flags edges) { return edges.testFlags(Edges::Top | Edges::Bottom) || edges.testFlags(Edges::Left | Edges::Right); } - -DropEmitter::DropEmitter(DropEmitter&& other) noexcept: object(other.object), signal(other.signal) { - other.object = nullptr; -} - -DropEmitter& DropEmitter::operator=(DropEmitter&& other) noexcept { - this->object = other.object; - this->signal = other.signal; - other.object = nullptr; - return *this; -} - -DropEmitter::~DropEmitter() { this->call(); } - -void DropEmitter::call() { - if (!this->object) return; - this->signal(this->object); - this->object = nullptr; -} diff --git a/src/core/types.hpp b/src/core/types.hpp index a23ff08..13fce82 100644 --- a/src/core/types.hpp +++ b/src/core/types.hpp @@ -69,28 +69,3 @@ bool isOpposing(Flags edges); }; // namespace Edges Q_DECLARE_OPERATORS_FOR_FLAGS(Edges::Flags); - -// NOLINTBEGIN -#define DROP_EMIT(object, func) \ - DropEmitter(object, static_cast([](typeof(object) o) { o->func(); })) -// NOLINTEND - -class DropEmitter { -public: - template - DropEmitter(O* object, void (*signal)(O*)) - : object(object) - , signal(*reinterpret_cast(signal)) {} // NOLINT - - DropEmitter() = default; - DropEmitter(DropEmitter&& other) noexcept; - DropEmitter& operator=(DropEmitter&& other) noexcept; - ~DropEmitter(); - Q_DISABLE_COPY(DropEmitter); - - void call(); - -private: - void* object = nullptr; - void (*signal)(void*) = nullptr; -}; diff --git a/src/core/util.hpp b/src/core/util.hpp new file mode 100644 index 0000000..249ab49 --- /dev/null +++ b/src/core/util.hpp @@ -0,0 +1,81 @@ +#pragma once + +// NOLINTBEGIN +#define DROP_EMIT(object, func) \ + DropEmitter(object, static_cast([](typeof(object) o) { o->func(); })) + +#define DROP_EMIT_IF(cond, object, func) (cond) ? DROP_EMIT(object, func) : DropEmitter() + +#define DEFINE_DROP_EMIT_IF(cond, object, func) DropEmitter func = DROP_EMIT_IF(cond, object, func) + +#define DROP_EMIT_SET(object, local, member, signal) \ + auto signal = DropEmitter(); \ + if (local == object->member) { \ + object->member = local; \ + signal = DROP_EMIT(object, signal); \ + } + +// generic accessor declarations + +#define GDECL_GETTER(type, name) [[nodiscard]] type name() const + +#define GDEF_GETTER(class, type, member, name) \ + type class::name() const { return this->member; } + +#define GDECL_SETTER(type, name) DropEmitter name(type value) + +#define GDEF_SETTER(class, type, member, name, signal) \ + DropEmitter class ::name(type value) { \ + if (value == this->member) return DropEmitter(); \ + this->member = value; \ + return DROP_EMIT(this, signal); \ + } + +#define GDECL_MEMBER(type, getter, setter) \ + GDECL_GETTER(type, getter) \ + GDECL_SETTER(type, setter) + +#define GDEF_MEMBER(class, type, member, getter, setter, signal) \ + GDEF_GETTER(class, type, member, getter) \ + GDEF_SETTER(class, type, member, setter, signal) + +#define GDEF_MEMBER_S(class, type, lower, upper) \ + GDEF_MEMBER(class, type, m##upper, lower, set##upper, lower##Changed) + +// NOLINTEND + +class DropEmitter { +public: + Q_DISABLE_COPY(DropEmitter); + template + DropEmitter(O* object, void (*signal)(O*)) + : object(object) + , signal(*reinterpret_cast(signal)) {} // NOLINT + + DropEmitter() = default; + + DropEmitter(DropEmitter&& other) noexcept: object(other.object), signal(other.signal) { + other.object = nullptr; + } + + ~DropEmitter() { this->call(); } + + DropEmitter& operator=(DropEmitter&& other) noexcept { + this->object = other.object; + this->signal = other.signal; + other.object = nullptr; + return *this; + } + + explicit operator bool() const noexcept { return this->object; } + + void call() { + if (!this->object) return; + this->signal(this->object); + this->object = nullptr; + } + +private: + void* object = nullptr; + void (*signal)(void*) = nullptr; +}; From 8873a06962e7bf09bca9a2b68254c878278e3390 Mon Sep 17 00:00:00 2001 From: outfoxxed Date: Tue, 30 Jul 2024 12:20:39 -0700 Subject: [PATCH 2/2] service/notifications: use DROP_EMIT_SET for notification properties --- src/services/notifications/notification.cpp | 46 ++++++--------------- 1 file changed, 13 insertions(+), 33 deletions(-) diff --git a/src/services/notifications/notification.cpp b/src/services/notifications/notification.cpp index 46a337a..b708091 100644 --- a/src/services/notifications/notification.cpp +++ b/src/services/notifications/notification.cpp @@ -8,6 +8,7 @@ #include #include +#include "../../core/util.hpp" #include "../../core/desktopentry.hpp" #include "../../core/iconimageprovider.hpp" #include "dbusimage.hpp" @@ -130,29 +131,20 @@ void Notification::updateProperties( } } - auto appNameChanged = appName != this->mAppName; - auto appIconChanged = appIcon != this->mAppIcon; - auto summaryChanged = summary != this->mSummary; - auto bodyChanged = body != this->mBody; - auto expireTimeoutChanged = expireTimeout != this->mExpireTimeout; - auto urgencyChanged = urgency != this->mUrgency; - auto hasActionIconsChanged = hasActionIcons != this->mHasActionIcons; - auto isResidentChanged = isResident != this->mIsResident; - auto isTransientChanged = isTransient != this->mIsTransient; - auto desktopEntryChanged = desktopEntry != this->mDesktopEntry; - auto imageChanged = imagePixmap || imagePath != this->mImagePath; - auto hintsChanged = hints != this->mHints; + DROP_EMIT_SET(this, appName, mAppName, appNameChanged); + DROP_EMIT_SET(this, appIcon, mAppIcon, appIconChanged); + DROP_EMIT_SET(this, summary, mSummary, summaryChanged); + DROP_EMIT_SET(this, body, mBody, bodyChanged); + DROP_EMIT_SET(this, expireTimeout, mExpireTimeout, expireTimeoutChanged); + DEFINE_DROP_EMIT_IF(urgency != this->mUrgency, this, urgencyChanged); + DROP_EMIT_SET(this, hasActionIcons, mHasActionIcons, hasActionIconsChanged); + DROP_EMIT_SET(this, isResident, mIsResident, isResidentChanged); + DROP_EMIT_SET(this, isTransient, mIsTransient, isTransientChanged); + DROP_EMIT_SET(this, desktopEntry, mDesktopEntry, desktopEntryChanged); + DEFINE_DROP_EMIT_IF(imagePixmap || imagePath != this->mImagePath, this, imageChanged); + DROP_EMIT_SET(this, hints, mHints, hintsChanged); - if (appNameChanged) this->mAppName = appName; - if (appIconChanged) this->mAppIcon = appIcon; - if (summaryChanged) this->mSummary = summary; - if (bodyChanged) this->mBody = body; - if (expireTimeoutChanged) this->mExpireTimeout = expireTimeout; if (urgencyChanged) this->mUrgency = static_cast(urgency); - if (hasActionIcons) this->mHasActionIcons = hasActionIcons; - if (isResidentChanged) this->mIsResident = isResident; - if (isTransientChanged) this->mIsTransient = isTransient; - if (desktopEntryChanged) this->mDesktopEntry = desktopEntry; NotificationImage* oldImage = nullptr; @@ -203,19 +195,7 @@ void Notification::updateProperties( << "sent an action set of an invalid length."; } - if (appNameChanged) emit this->appNameChanged(); - if (appIconChanged) emit this->appIconChanged(); - if (summaryChanged) emit this->summaryChanged(); - if (bodyChanged) emit this->bodyChanged(); - if (expireTimeoutChanged) emit this->expireTimeoutChanged(); - if (urgencyChanged) emit this->urgencyChanged(); if (actionsChanged) emit this->actionsChanged(); - if (hasActionIconsChanged) emit this->hasActionIconsChanged(); - if (isResidentChanged) emit this->isResidentChanged(); - if (isTransientChanged) emit this->isTransientChanged(); - if (desktopEntryChanged) emit this->desktopEntryChanged(); - if (imageChanged) emit this->imageChanged(); - if (hintsChanged) emit this->hintsChanged(); for (auto* action: deletedActions) { delete action;