bluetooth: fix defaultAdapter reactivity

Fixes #100
This commit is contained in:
outfoxxed 2025-07-07 02:21:50 -07:00
parent 87d99b866f
commit 5d7e07508a
Signed by untrusted user: outfoxxed
GPG key ID: 4C88A185FB89301E
2 changed files with 24 additions and 8 deletions

View file

@ -26,6 +26,11 @@ Bluez* Bluez::instance() {
Bluez::Bluez() { this->init(); } Bluez::Bluez() { this->init(); }
void Bluez::updateDefaultAdapter() {
const auto& adapters = this->mAdapters.valueList();
this->bDefaultAdapter = adapters.empty() ? nullptr : adapters.first();
}
void Bluez::init() { void Bluez::init() {
qCDebug(logBluetooth) << "Connecting to BlueZ"; qCDebug(logBluetooth) << "Connecting to BlueZ";
@ -95,6 +100,7 @@ void Bluez::onInterfacesAdded(
this->mAdapterMap.insert(path.path(), adapter); this->mAdapterMap.insert(path.path(), adapter);
this->mAdapters.insertObject(adapter); this->mAdapters.insertObject(adapter);
this->updateDefaultAdapter();
} else if (interfaces.contains("org.bluez.Device1")) { } else if (interfaces.contains("org.bluez.Device1")) {
auto* device = new BluetoothDevice(path.path(), this); auto* device = new BluetoothDevice(path.path(), this);
@ -127,6 +133,7 @@ void Bluez::onInterfacesRemoved(const QDBusObjectPath& path, const QStringList&
this->mAdapterMap.remove(path.path()); this->mAdapterMap.remove(path.path());
this->mAdapters.removeObject(adapter); this->mAdapters.removeObject(adapter);
this->updateDefaultAdapter();
delete adapter; delete adapter;
} }
} else if (auto* device = this->mDeviceMap.value(path.path())) { } else if (auto* device = this->mDeviceMap.value(path.path())) {
@ -148,9 +155,8 @@ void Bluez::onInterfacesRemoved(const QDBusObjectPath& path, const QStringList&
} }
} }
BluetoothAdapter* Bluez::defaultAdapter() const { BluezQml::BluezQml() {
const auto& adapters = this->mAdapters.valueList(); QObject::connect(Bluez::instance(), &Bluez::defaultAdapterChanged, this, &BluezQml::defaultAdapterChanged);
return adapters.isEmpty() ? nullptr : adapters.first();
} }
} // namespace qs::bluetooth } // namespace qs::bluetooth

View file

@ -3,6 +3,7 @@
#include <qcontainerfwd.h> #include <qcontainerfwd.h>
#include <qhash.h> #include <qhash.h>
#include <qobject.h> #include <qobject.h>
#include <qproperty.h>
#include <qqmlintegration.h> #include <qqmlintegration.h>
#include <qtmetamacros.h> #include <qtmetamacros.h>
@ -22,7 +23,6 @@ class Bluez: public QObject {
public: public:
[[nodiscard]] ObjectModel<BluetoothAdapter>* adapters() { return &this->mAdapters; } [[nodiscard]] ObjectModel<BluetoothAdapter>* adapters() { return &this->mAdapters; }
[[nodiscard]] ObjectModel<BluetoothDevice>* devices() { return &this->mDevices; } [[nodiscard]] ObjectModel<BluetoothDevice>* devices() { return &this->mDevices; }
[[nodiscard]] BluetoothAdapter* defaultAdapter() const;
[[nodiscard]] BluetoothAdapter* adapter(const QString& path) { [[nodiscard]] BluetoothAdapter* adapter(const QString& path) {
return this->mAdapterMap.value(path); return this->mAdapterMap.value(path);
@ -30,10 +30,14 @@ public:
static Bluez* instance(); static Bluez* instance();
signals:
void defaultAdapterChanged();
private slots: private slots:
void void
onInterfacesAdded(const QDBusObjectPath& path, const DBusObjectManagerInterfaces& interfaces); onInterfacesAdded(const QDBusObjectPath& path, const DBusObjectManagerInterfaces& interfaces);
void onInterfacesRemoved(const QDBusObjectPath& path, const QStringList& interfaces); void onInterfacesRemoved(const QDBusObjectPath& path, const QStringList& interfaces);
void updateDefaultAdapter();
private: private:
explicit Bluez(); explicit Bluez();
@ -44,6 +48,9 @@ private:
QHash<QString, BluetoothDevice*> mDeviceMap; QHash<QString, BluetoothDevice*> mDeviceMap;
ObjectModel<BluetoothAdapter> mAdapters {this}; ObjectModel<BluetoothAdapter> mAdapters {this};
ObjectModel<BluetoothDevice> mDevices {this}; ObjectModel<BluetoothDevice> mDevices {this};
public:
Q_OBJECT_BINDABLE_PROPERTY(Bluez, BluetoothAdapter*, bDefaultAdapter, &Bluez::defaultAdapterChanged);
}; };
///! Bluetooth manager ///! Bluetooth manager
@ -51,7 +58,7 @@ private:
class BluezQml: public QObject { class BluezQml: public QObject {
Q_OBJECT; Q_OBJECT;
/// The default bluetooth adapter. Usually there is only one. /// The default bluetooth adapter. Usually there is only one.
Q_PROPERTY(BluetoothAdapter* defaultAdapter READ defaultAdapter CONSTANT); Q_PROPERTY(BluetoothAdapter* defaultAdapter READ default NOTIFY defaultAdapterChanged BINDABLE bindableDefaultAdapter);
QSDOC_TYPE_OVERRIDE(ObjectModel<qs::bluetooth::BluetoothAdapter>*); QSDOC_TYPE_OVERRIDE(ObjectModel<qs::bluetooth::BluetoothAdapter>*);
/// A list of all bluetooth adapters. See @@defaultAdapter for the default. /// A list of all bluetooth adapters. See @@defaultAdapter for the default.
Q_PROPERTY(UntypedObjectModel* adapters READ adapters CONSTANT); Q_PROPERTY(UntypedObjectModel* adapters READ adapters CONSTANT);
@ -62,8 +69,11 @@ class BluezQml: public QObject {
QML_NAMED_ELEMENT(Bluetooth); QML_NAMED_ELEMENT(Bluetooth);
QML_SINGLETON; QML_SINGLETON;
signals:
void defaultAdapterChanged();
public: public:
explicit BluezQml(QObject* parent = nullptr): QObject(parent) {} explicit BluezQml();
[[nodiscard]] static ObjectModel<BluetoothAdapter>* adapters() { [[nodiscard]] static ObjectModel<BluetoothAdapter>* adapters() {
return Bluez::instance()->adapters(); return Bluez::instance()->adapters();
@ -73,8 +83,8 @@ public:
return Bluez::instance()->devices(); return Bluez::instance()->devices();
} }
[[nodiscard]] static BluetoothAdapter* defaultAdapter() { [[nodiscard]] static QBindable<BluetoothAdapter*> bindableDefaultAdapter() {
return Bluez::instance()->defaultAdapter(); return &Bluez::instance()->bDefaultAdapter;
} }
}; };