From c1a115216927bb97b9defee94cc4db93a4be28db Mon Sep 17 00:00:00 2001 From: Sebastian Palencsar Date: Thu, 28 May 2026 08:28:57 +0200 Subject: [PATCH] Implement single instance check using DBus --- CHANGELOG.md | 1 + src/main.cpp | 15 ++++++++++++++- src/mprisadaptor.cpp | 3 ++- src/qml/Main.qml | 9 +++++++++ src/radiobackend.h | 1 + 5 files changed, 27 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 977fd41..916fe80 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,6 +10,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Added - SPDX license identifiers (GPL-3.0-or-later) to all source files. +- Single instance application check via DBus to prevent multiple concurrent instances. ### Changed diff --git a/src/main.cpp b/src/main.cpp index bfeff6d..ccd3ad0 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -3,6 +3,8 @@ #include #include +#include +#include #include #include #include @@ -23,6 +25,18 @@ int main(int argc, char *argv[]) QApplication::setApplicationVersion(QStringLiteral("1.0.1")); QApplication app(argc, argv); + + QDBusConnection sessionBus = QDBusConnection::sessionBus(); + if (sessionBus.isConnected() && sessionBus.interface() && sessionBus.interface()->isServiceRegistered(QStringLiteral("org.mpris.MediaPlayer2.bearwave"))) { + QDBusMessage call = QDBusMessage::createMethodCall( + QStringLiteral("org.mpris.MediaPlayer2.bearwave"), + QStringLiteral("/org/mpris/MediaPlayer2"), + QStringLiteral("org.mpris.MediaPlayer2"), + QStringLiteral("Raise") + ); + sessionBus.call(call); + return 0; + } app.setWindowIcon(QIcon::fromTheme(QStringLiteral("de.nerdbear.bearwave"))); app.setQuitOnLastWindowClosed(false); @@ -45,7 +59,6 @@ int main(int argc, char *argv[]) Q_UNUSED(controlAdaptor) Q_UNUSED(notificationManager) - QDBusConnection sessionBus = QDBusConnection::sessionBus(); sessionBus.registerObject(QStringLiteral("/org/mpris/MediaPlayer2"), &backend, QDBusConnection::ExportAdaptors); sessionBus.registerService(QStringLiteral("org.mpris.MediaPlayer2.bearwave")); diff --git a/src/mprisadaptor.cpp b/src/mprisadaptor.cpp index 8bc7dcf..ac85bd8 100644 --- a/src/mprisadaptor.cpp +++ b/src/mprisadaptor.cpp @@ -58,7 +58,7 @@ bool MprisRootAdaptor::canSetFullscreen() const bool MprisRootAdaptor::canRaise() const { - return false; + return true; } bool MprisRootAdaptor::hasTrackList() const @@ -94,6 +94,7 @@ QStringList MprisRootAdaptor::supportedMimeTypes() const void MprisRootAdaptor::Raise() { + emit m_backend->raiseRequested(); } void MprisRootAdaptor::Quit() diff --git a/src/qml/Main.qml b/src/qml/Main.qml index f76e447..326b0c4 100644 --- a/src/qml/Main.qml +++ b/src/qml/Main.qml @@ -20,6 +20,15 @@ ApplicationWindow { root.hide() } + Connections { + target: backend + function onRaiseRequested() { + root.show() + root.raise() + root.requestActivate() + } + } + Platform.SystemTrayIcon { id: systray visible: true diff --git a/src/radiobackend.h b/src/radiobackend.h index d172f5a..12b01f1 100644 --- a/src/radiobackend.h +++ b/src/radiobackend.h @@ -83,6 +83,7 @@ signals: void resumeStateChanged(); void filterQueryChanged(); void currentStationChanged(); + void raiseRequested(); private slots: void onStationsLoaded(const QList &stations);