diff options
-rw-r--r-- | src/bluetooth/qbluetoothdevicediscoveryagent.cpp | 20 | ||||
-rw-r--r-- | src/bluetooth/qbluetoothdevicediscoveryagent.h | 1 | ||||
-rw-r--r-- | src/bluetooth/qbluetoothdevicediscoveryagent_android.cpp | 23 | ||||
-rw-r--r-- | src/bluetooth/qbluetoothdevicediscoveryagent_bluez.cpp | 14 | ||||
-rw-r--r-- | src/bluetooth/qbluetoothdeviceinfo.cpp | 34 | ||||
-rw-r--r-- | src/bluetooth/qbluetoothdeviceinfo.h | 11 |
6 files changed, 93 insertions, 10 deletions
diff --git a/src/bluetooth/qbluetoothdevicediscoveryagent.cpp b/src/bluetooth/qbluetoothdevicediscoveryagent.cpp index a9e35960..ac978349 100644 --- a/src/bluetooth/qbluetoothdevicediscoveryagent.cpp +++ b/src/bluetooth/qbluetoothdevicediscoveryagent.cpp @@ -155,6 +155,26 @@ Q_DECLARE_LOGGING_CATEGORY(QT_BT) */ /*! + \fn void QBluetoothDeviceDiscoveryAgent::deviceUpdated(const QBluetoothDeviceInfo &info, QBluetoothDeviceInfo::Fields updatedFields) + + This signal is emitted when the agent receives additional information about + the Bluetooth device described by \a info. The \l updatedFields flags tell + which information has been updated. + + During discovery, some information can change dynamically, such as + \l {signal strength}{QBluetoothDeviceInfo::rssi()} and + \l {manufacturerData}{QBluetoothDeviceInfo::manufacturerData()}. + This signal informs you that if your application is displaying this data, it + can be updated, rather than waiting until the discovery has finished. + + \note This signal is only emitted on Android and BlueZ 5.x. + + \sa QBluetoothDeviceInfo::rssi(), lowEnergyDiscoveryTimeout() +*/ + +// TODO deviceUpdated() signal not implemented on WinRT and Apple platforms + +/*! \fn void QBluetoothDeviceDiscoveryAgent::finished() This signal is emitted when Bluetooth device discovery completes. diff --git a/src/bluetooth/qbluetoothdevicediscoveryagent.h b/src/bluetooth/qbluetoothdevicediscoveryagent.h index d3e41265..f24478bf 100644 --- a/src/bluetooth/qbluetoothdevicediscoveryagent.h +++ b/src/bluetooth/qbluetoothdevicediscoveryagent.h @@ -112,6 +112,7 @@ public Q_SLOTS: Q_SIGNALS: void deviceDiscovered(const QBluetoothDeviceInfo &info); + void deviceUpdated(const QBluetoothDeviceInfo &info, QBluetoothDeviceInfo::Fields updatedFields); void finished(); void error(QBluetoothDeviceDiscoveryAgent::Error error); void canceled(); diff --git a/src/bluetooth/qbluetoothdevicediscoveryagent_android.cpp b/src/bluetooth/qbluetoothdevicediscoveryagent_android.cpp index c7afd578..50f3aef9 100644 --- a/src/bluetooth/qbluetoothdevicediscoveryagent_android.cpp +++ b/src/bluetooth/qbluetoothdevicediscoveryagent_android.cpp @@ -317,12 +317,29 @@ void QBluetoothDeviceDiscoveryAgentPrivate::processDiscoveredDevices( for (int i = 0; i < discoveredDevices.size(); i++) { if (discoveredDevices[i].address() == info.address()) { - if (discoveredDevices[i] == info && lowEnergySearchTimeout > 0) { - qCDebug(QT_BT_ANDROID) << "Duplicate: " << info.address() - << "isLeScanResult:" << isLeResult; + QBluetoothDeviceInfo::Fields updatedFields = QBluetoothDeviceInfo::Field::None; + if (discoveredDevices[i].rssi() != info.rssi()) { + qCDebug(QT_BT_ANDROID) << "Updating RSSI for" << info.address() + << info.rssi(); + discoveredDevices[i].setRssi(info.rssi()); + updatedFields.setFlag(QBluetoothDeviceInfo::Field::RSSI); + } + if (discoveredDevices[i].manufacturerData() != info.manufacturerData()) { + qCDebug(QT_BT_ANDROID) << "Updating manufacturer data for" << info.address(); + const QVector<quint16> keys = info.manufacturerIds(); + for (auto key: keys) + discoveredDevices[i].setManufacturerData(key, info.manufacturerData(key)); + updatedFields.setFlag(QBluetoothDeviceInfo::Field::ManufacturerData); + } + + if (!updatedFields.testFlag(QBluetoothDeviceInfo::Field::None)) { + emit q->deviceUpdated(discoveredDevices[i], updatedFields); return; } + if (discoveredDevices[i] == info) + return; + if (discoveredDevices.at(i).name() == info.name()) { qCDebug(QT_BT_ANDROID) << "Almost Duplicate "<< info.address() << info.name() << "- replacing in place"; diff --git a/src/bluetooth/qbluetoothdevicediscoveryagent_bluez.cpp b/src/bluetooth/qbluetoothdevicediscoveryagent_bluez.cpp index a5fdb323..a039c916 100644 --- a/src/bluetooth/qbluetoothdevicediscoveryagent_bluez.cpp +++ b/src/bluetooth/qbluetoothdevicediscoveryagent_bluez.cpp @@ -633,23 +633,27 @@ void QBluetoothDeviceDiscoveryAgentPrivate::_q_PropertiesChanged(const QString & QDBusConnection::systemBus()); for (int i = 0; i < discoveredDevices.size(); i++) { if (discoveredDevices[i].address().toString() == device.address()) { + QBluetoothDeviceInfo::Fields updatedFields = QBluetoothDeviceInfo::Field::None; if (changed_properties.contains(QStringLiteral("RSSI"))) { qCDebug(QT_BT_BLUEZ) << "Updating RSSI for" << device.address() << changed_properties.value(QStringLiteral("RSSI")); discoveredDevices[i].setRssi( changed_properties.value(QStringLiteral("RSSI")).toInt()); + updatedFields.setFlag(QBluetoothDeviceInfo::Field::RSSI); } if (changed_properties.contains(QStringLiteral("ManufacturerData"))) { qCDebug(QT_BT_BLUEZ) << "Updating ManufacturerData for" << device.address(); - - QVector<QPair<quint16,QByteArray>> manufacturerData; ManufacturerDataList changedManufacturerData = - qvariant_cast< ManufacturerDataList >(changed_properties.value(QStringLiteral("ManufacturerData"))); + qdbus_cast< ManufacturerDataList >(changed_properties.value(QStringLiteral("ManufacturerData"))); const QList<quint16> keys = changedManufacturerData.keys(); - for (quint16 key : keys) - discoveredDevices[i].setManufacturerData(key, changedManufacturerData.value(key).variant().toByteArray()); + for (quint16 key : keys) { + if (discoveredDevices[i].setManufacturerData(key, changedManufacturerData.value(key).variant().toByteArray())) + updatedFields.setFlag(QBluetoothDeviceInfo::Field::ManufacturerData); + } } + if (!updatedFields.testFlag(QBluetoothDeviceInfo::Field::None)) + emit q->deviceUpdated(discoveredDevices[i], updatedFields); return; } } diff --git a/src/bluetooth/qbluetoothdeviceinfo.cpp b/src/bluetooth/qbluetoothdeviceinfo.cpp index 11a60565..bd3b9c00 100644 --- a/src/bluetooth/qbluetoothdeviceinfo.cpp +++ b/src/bluetooth/qbluetoothdeviceinfo.cpp @@ -72,6 +72,20 @@ QT_BEGIN_NAMESPACE */ /*! + \enum QBluetoothDeviceInfo::Field + + This enum is used in conjuntion with the \l deviceUpdated() signal and indicates the field + that changed. + + \value None None of the values changed. + \value RSSI The \l rssi() value of the device changed. + \value ManufacturerData The \l manufacturerData() field changed + \value All Matches every possible field. + + \since 5.12 +*/ + +/*! \enum QBluetoothDeviceInfo::MinorMiscellaneousClass This enum describes the minor device classes for miscellaneous Bluetooth devices. @@ -598,20 +612,38 @@ QVector<quint16> QBluetoothDeviceInfo::manufacturerIds() const */ QByteArray QBluetoothDeviceInfo::manufacturerData(quint16 manufacturerId) const { + // TODO Currently not implemented on WinRT Q_D(const QBluetoothDeviceInfo); return d->manufacturerData.value(manufacturerId); } /*! Sets the advertised manufacturer \a data for the given \a manufacturerId. + Returns true if it was inserted or changed, false if it was already known. \sa manufacturerData, \since 5.12 */ -void QBluetoothDeviceInfo::setManufacturerData(quint16 manufacturerId, const QByteArray &data) +bool QBluetoothDeviceInfo::setManufacturerData(quint16 manufacturerId, const QByteArray &data) { Q_D(QBluetoothDeviceInfo); + const auto it = d->manufacturerData.find(manufacturerId); + if (it != d->manufacturerData.end() && *it == data) + return false; d->manufacturerData.insert(manufacturerId, data); + return true; +} + +/*! + Returns the complete set of all manufacturer data. + + \sa setManufacturerData + \since 5.12 +*/ +QHash<quint16, QByteArray> QBluetoothDeviceInfo::manufacturerData() const +{ + Q_D(const QBluetoothDeviceInfo); + return d->manufacturerData; } /*! diff --git a/src/bluetooth/qbluetoothdeviceinfo.h b/src/bluetooth/qbluetoothdeviceinfo.h index 88b477d8..d59eb27d 100644 --- a/src/bluetooth/qbluetoothdeviceinfo.h +++ b/src/bluetooth/qbluetoothdeviceinfo.h @@ -198,6 +198,14 @@ public: DataUnavailable }; + enum class Field { + None = 0x0000, + RSSI = 0x0001, + ManufacturerData = 0x0002, + All = 0x7fff + }; + Q_DECLARE_FLAGS(Fields, Field) + enum CoreConfiguration { UnknownCoreConfiguration = 0x0, LowEnergyCoreConfiguration = 0x01, @@ -239,7 +247,8 @@ public: QVector<quint16> manufacturerIds() const; QByteArray manufacturerData(quint16 manufacturerId) const; - void setManufacturerData(quint16 manufacturerId, const QByteArray &data); + bool setManufacturerData(quint16 manufacturerId, const QByteArray &data); + QHash<quint16, QByteArray> manufacturerData() const; void setCoreConfigurations(QBluetoothDeviceInfo::CoreConfigurations coreConfigs); QBluetoothDeviceInfo::CoreConfigurations coreConfigurations() const; |