mirror of
https://github.com/nymea/nymea-plugins.git
synced 2026-07-18 00:43:48 +02:00
Add first version of new sensor tag
This commit is contained in:
parent
be1bc16479
commit
0479ecb0bb
@ -1,6 +1,6 @@
|
||||
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
||||
* *
|
||||
* Copyright (C) 2015 Simon Stuerz <simon.stuerz@guh.io> *
|
||||
* Copyright (C) 2015-2018 Simon Stuerz <simon.stuerz@guh.io> *
|
||||
* Copyright (C) 2016 nicc *
|
||||
* *
|
||||
* This file is part of nymea. *
|
||||
@ -52,10 +52,15 @@ DevicePluginMultiSensor::DevicePluginMultiSensor()
|
||||
|
||||
}
|
||||
|
||||
DevicePluginMultiSensor::~DevicePluginMultiSensor()
|
||||
{
|
||||
hardwareManager()->pluginTimerManager()->unregisterTimer(m_reconnectTimer);
|
||||
}
|
||||
|
||||
void DevicePluginMultiSensor::init()
|
||||
{
|
||||
m_measureTimer = hardwareManager()->pluginTimerManager()->registerTimer(60);
|
||||
connect(m_measureTimer, &PluginTimer::timeout, this, &DevicePluginMultiSensor::onPluginTimer);
|
||||
m_reconnectTimer = hardwareManager()->pluginTimerManager()->registerTimer(10);
|
||||
connect(m_reconnectTimer, &PluginTimer::timeout, this, &DevicePluginMultiSensor::onPluginTimer);
|
||||
}
|
||||
|
||||
DeviceManager::DeviceError DevicePluginMultiSensor::discoverDevices(const DeviceClassId &deviceClassId, const ParamList ¶ms)
|
||||
@ -89,8 +94,6 @@ DeviceManager::DeviceSetupStatus DevicePluginMultiSensor::setupDevice(Device *de
|
||||
BluetoothLowEnergyDevice *bluetoothDevice = hardwareManager()->bluetoothLowEnergyManager()->registerDevice(deviceInfo, QLowEnergyController::PublicAddress);
|
||||
|
||||
SensorTag *sensor = new SensorTag(device, bluetoothDevice, this);
|
||||
connect(sensor, &SensorTag::leftKeyPressed, this, &DevicePluginMultiSensor::onSensorLeftButtonPressed);
|
||||
connect(sensor, &SensorTag::rightKeyPressed, this, &DevicePluginMultiSensor::onSensorRightButtonPressed);
|
||||
|
||||
m_sensors.insert(device, sensor);
|
||||
sensor->bluetoothDevice()->connectDevice();
|
||||
@ -124,23 +127,13 @@ bool DevicePluginMultiSensor::verifyExistingDevices(const QBluetoothDeviceInfo &
|
||||
|
||||
void DevicePluginMultiSensor::onPluginTimer()
|
||||
{
|
||||
foreach (SensorTag *sensor, m_sensors) {
|
||||
sensor->measure();
|
||||
foreach (SensorTag *sensor, m_sensors.values()) {
|
||||
if (!sensor->bluetoothDevice()->connected()) {
|
||||
sensor->bluetoothDevice()->connectDevice();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void DevicePluginMultiSensor::onSensorLeftButtonPressed()
|
||||
{
|
||||
SensorTag *sensor = static_cast<SensorTag *>(sender());
|
||||
emit emitEvent(Event(sensortagLeftKeyEventTypeId, sensor->device()->id()));
|
||||
}
|
||||
|
||||
void DevicePluginMultiSensor::onSensorRightButtonPressed()
|
||||
{
|
||||
SensorTag *sensor = static_cast<SensorTag *>(sender());
|
||||
emit emitEvent(Event(sensortagRightKeyEventTypeId, sensor->device()->id()));
|
||||
}
|
||||
|
||||
void DevicePluginMultiSensor::onBluetoothDiscoveryFinished()
|
||||
{
|
||||
BluetoothDiscoveryReply *reply = static_cast<BluetoothDiscoveryReply *>(sender());
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
||||
* *
|
||||
* Copyright (C) 2015 Simon Stuerz <simon.stuerz@guh.io> *
|
||||
* Copyright (C) 2015-2018 Simon Stuerz <simon.stuerz@guh.io> *
|
||||
* Copyright (C) 2016 nicc *
|
||||
* *
|
||||
* This file is part of nymea. *
|
||||
@ -41,6 +41,7 @@ class DevicePluginMultiSensor : public DevicePlugin
|
||||
|
||||
public:
|
||||
explicit DevicePluginMultiSensor();
|
||||
~DevicePluginMultiSensor();
|
||||
|
||||
void init() override;
|
||||
DeviceManager::DeviceError discoverDevices(const DeviceClassId &deviceClassId, const ParamList ¶ms) override;
|
||||
@ -48,17 +49,13 @@ public:
|
||||
void deviceRemoved(Device *device) override;
|
||||
|
||||
private:
|
||||
PluginTimer *m_measureTimer = nullptr;
|
||||
PluginTimer *m_reconnectTimer = nullptr;
|
||||
QHash<Device *, SensorTag *> m_sensors;
|
||||
|
||||
bool verifyExistingDevices(const QBluetoothDeviceInfo &deviceInfo);
|
||||
|
||||
private slots:
|
||||
void onPluginTimer();
|
||||
|
||||
void onSensorLeftButtonPressed();
|
||||
void onSensorRightButtonPressed();
|
||||
|
||||
void onBluetoothDiscoveryFinished();
|
||||
};
|
||||
|
||||
|
||||
@ -2,6 +2,47 @@
|
||||
"displayName": "MultiSensor",
|
||||
"name": "MultiSensor",
|
||||
"id": "23bf0d8d-df7d-4bee-80ee-f015c5a7f52e",
|
||||
"paramTypes": [
|
||||
{
|
||||
"id": "5786c91a-d94d-461a-8d22-f978dd1438ab",
|
||||
"name": "accelerometerEnabled",
|
||||
"displayName": "Accelerometer enabled",
|
||||
"type": "bool",
|
||||
"defaultValue": true
|
||||
},
|
||||
{
|
||||
"id": "94517544-cb97-4816-8993-cb4cf2651a1e",
|
||||
"name": "gyroscopeEnabled",
|
||||
"displayName": "Gyroscope enabled",
|
||||
"type": "bool",
|
||||
"defaultValue": false
|
||||
},
|
||||
{
|
||||
"id": "96aae111-b1c1-48a1-9b1f-b56efa546d0d",
|
||||
"name": "magnetometerEnabled",
|
||||
"displayName": "Magnetometer enabled",
|
||||
"type": "bool",
|
||||
"defaultValue": false
|
||||
},
|
||||
{
|
||||
"id": "5237c89c-c21d-4d78-ac99-8be661b40da7",
|
||||
"name": "measurementPeriodMovement",
|
||||
"displayName": "Measurement period movement sensor",
|
||||
"type": "int",
|
||||
"minValue": 10,
|
||||
"maxValue": 2500,
|
||||
"defaultValue": 2000
|
||||
},
|
||||
{
|
||||
"id": "c5308565-5dc9-409e-ae99-577c212c7a92",
|
||||
"name": "measurementPeriod",
|
||||
"displayName": "Measurement period for enviromental sensors",
|
||||
"type": "int",
|
||||
"minValue": 10,
|
||||
"maxValue": 2500,
|
||||
"defaultValue": 500
|
||||
}
|
||||
],
|
||||
"vendors": [
|
||||
{
|
||||
"id": "2edf543e-dc2c-4693-bb0c-e76c0d305fad",
|
||||
@ -9,12 +50,12 @@
|
||||
"displayName": "Texas Instruments",
|
||||
"deviceClasses": [
|
||||
{
|
||||
"displayName": "Sensor Tag",
|
||||
"name": "sensortag",
|
||||
"id": "158a06b6-b27f-4951-957e-6f1e3b44f604",
|
||||
"name": "sensortag",
|
||||
"displayName": "Sensor Tag (CC2650)",
|
||||
"createMethods": ["discovery"],
|
||||
"deviceIcon": "Thermometer",
|
||||
"criticalStateTypeId": "a9629b11-0f34-47f0-a0f0-f758a6aec2b4",
|
||||
"interfaces": ["connectable", "humiditysensor", "temperaturesensor"],
|
||||
"basicTags": [
|
||||
"Device",
|
||||
"Sensor"
|
||||
@ -23,14 +64,14 @@
|
||||
{
|
||||
"id": "bdb9d684-2f98-45f5-889c-f184c1e73dc7",
|
||||
"name": "name",
|
||||
"displayName": "name",
|
||||
"displayName": "Name",
|
||||
"type": "QString",
|
||||
"inputType": "TextLine"
|
||||
},
|
||||
{
|
||||
"id": "d51ed68e-c84a-4136-a5b5-be2f95fd5a0f",
|
||||
"name": "mac",
|
||||
"displayName": "mac address",
|
||||
"displayName": "MAC address",
|
||||
"type": "QString",
|
||||
"inputType": "MacAddress"
|
||||
}
|
||||
@ -39,29 +80,12 @@
|
||||
{
|
||||
"id": "a9629b11-0f34-47f0-a0f0-f758a6aec2b4",
|
||||
"name": "connected",
|
||||
"displayName": "connected",
|
||||
"displayNameEvent": "connected changed",
|
||||
"displayName": "Connected",
|
||||
"displayNameEvent": "Connected changed",
|
||||
"type": "bool",
|
||||
"cached": false,
|
||||
"defaultValue": false
|
||||
},
|
||||
{
|
||||
"id": "c664e9ec-a045-49ba-add1-1642ceba7c4f",
|
||||
"name": "IRtemperature",
|
||||
"displayName": "IR temperature",
|
||||
"displayNameEvent": "IR temperature changed",
|
||||
"type": "double",
|
||||
"unit": "DegreeCelsius",
|
||||
"defaultValue": 0
|
||||
},
|
||||
{
|
||||
"id": "e83a50ff-96c9-4b6d-889f-f4238353e794",
|
||||
"name": "humidity",
|
||||
"displayName": "humidity",
|
||||
"displayNameEvent": "humidity changed",
|
||||
"type": "double",
|
||||
"unit": "Percentage",
|
||||
"defaultValue": 0
|
||||
},
|
||||
{
|
||||
"id": "8359ada9-df1c-4e60-bb87-9e21d05ee2e2",
|
||||
"name": "temperature",
|
||||
@ -71,34 +95,79 @@
|
||||
"unit": "DegreeCelsius",
|
||||
"defaultValue": 0
|
||||
},
|
||||
{
|
||||
"id": "c664e9ec-a045-49ba-add1-1642ceba7c4f",
|
||||
"name": "objectTemperature",
|
||||
"displayName": "Object temperature",
|
||||
"displayNameEvent": "Object temperature changed",
|
||||
"type": "double",
|
||||
"unit": "DegreeCelsius",
|
||||
"defaultValue": 0
|
||||
},
|
||||
{
|
||||
"id": "e83a50ff-96c9-4b6d-889f-f4238353e794",
|
||||
"name": "humidity",
|
||||
"displayName": "Humidity",
|
||||
"displayNameEvent": "Humidity changed",
|
||||
"type": "double",
|
||||
"minValue": 0,
|
||||
"maxValue": 100,
|
||||
"unit": "Percentage",
|
||||
"defaultValue": 0
|
||||
},
|
||||
{
|
||||
"id": "645633ad-77d4-45b2-8be8-d6ca7a12eb7a",
|
||||
"name": "pressure",
|
||||
"displayName": "pressure",
|
||||
"displayNameEvent": "pressure changed",
|
||||
"displayName": "Barometric pressure",
|
||||
"displayNameEvent": "Barometric pressure changed",
|
||||
"type": "double",
|
||||
"unit": "HectoPascal",
|
||||
"defaultValue": 0
|
||||
},
|
||||
{
|
||||
"id": "4be5ca26-0565-419d-b18b-2a5a385d2a3d",
|
||||
"name": "moving",
|
||||
"displayName": "moving",
|
||||
"displayNameEvent": "moving changed",
|
||||
"type": "bool",
|
||||
"defaultValue": false
|
||||
}
|
||||
],
|
||||
"eventTypes": [
|
||||
{
|
||||
"id": "61478490-bed0-4fed-9d58-f13c35b4f220",
|
||||
"name": "leftKey",
|
||||
"displayName": "left key pressed"
|
||||
"id": "6635dce4-2d8d-4608-a836-768c3014f356",
|
||||
"name": "lightIntensity",
|
||||
"displayName": "Light intensity",
|
||||
"displayNameEvent": "Light intensity changed",
|
||||
"type": "double",
|
||||
"unit": "Lux",
|
||||
"defaultValue": 0
|
||||
},
|
||||
{
|
||||
"id": "b7e927db-af28-4fdc-8eb7-edb02258ff5a",
|
||||
"name": "rightKey",
|
||||
"displayName": "right key pressed"
|
||||
"id": "4be5ca26-0565-419d-b18b-2a5a385d2a3d",
|
||||
"name": "moving",
|
||||
"displayName": "Moving",
|
||||
"displayNameEvent": "Moving changed",
|
||||
"type": "bool",
|
||||
"cached": false,
|
||||
"defaultValue": false
|
||||
},
|
||||
{
|
||||
"id": "758d9b39-7390-40f5-8e19-d8b0f4a0a0c6",
|
||||
"name": "magnetDetected",
|
||||
"displayName": "Magnet detected",
|
||||
"displayNameEvent": "Magnet detected changed",
|
||||
"type": "bool",
|
||||
"cached": false,
|
||||
"defaultValue": false
|
||||
},
|
||||
{
|
||||
"id": "8995e49e-ca2d-4dd9-a22f-de6c566c2115",
|
||||
"name": "leftButtonPressed",
|
||||
"displayName": "Left button pressed",
|
||||
"displayNameEvent": "Left button pressed changed",
|
||||
"type": "bool",
|
||||
"cached": false,
|
||||
"defaultValue": false
|
||||
},
|
||||
{
|
||||
"id": "ef8eedc5-6a45-4dfb-bb55-ada1a931b20b",
|
||||
"name": "rightButtonPressed",
|
||||
"displayName": "Right button pressed",
|
||||
"displayNameEvent": "Right button pressed changed",
|
||||
"type": "bool",
|
||||
"cached": false,
|
||||
"defaultValue": false
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@ -1,6 +1,30 @@
|
||||
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
||||
* *
|
||||
* Copyright (C) 2015-2018 Simon Stuerz <simon.stuerz@guh.io> *
|
||||
* *
|
||||
* This file is part of guh. *
|
||||
* *
|
||||
* This library is free software; you can redistribute it and/or *
|
||||
* modify it under the terms of the GNU Lesser General Public *
|
||||
* License as published by the Free Software Foundation; either *
|
||||
* version 2.1 of the License, or (at your option) any later version. *
|
||||
* *
|
||||
* This library is distributed in the hope that it will be useful, *
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
|
||||
* Lesser General Public License for more details. *
|
||||
* *
|
||||
* You should have received a copy of the GNU Lesser General Public *
|
||||
* License along with this library; If not, see *
|
||||
* <http://www.gnu.org/licenses/>. *
|
||||
* *
|
||||
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||
|
||||
#include "sensortag.h"
|
||||
#include "extern-plugininfo.h"
|
||||
|
||||
#include <QDataStream>
|
||||
|
||||
SensorTag::SensorTag(Device *device, BluetoothLowEnergyDevice *bluetoothDevice, QObject *parent) :
|
||||
QObject(parent),
|
||||
m_device(device),
|
||||
@ -20,28 +44,212 @@ BluetoothLowEnergyDevice *SensorTag::bluetoothDevice()
|
||||
return m_bluetoothDevice;
|
||||
}
|
||||
|
||||
void SensorTag::updateInfraredValue(const QByteArray &value)
|
||||
void SensorTag::setAccelerometerEnabled(bool enabled)
|
||||
{
|
||||
qCDebug(dcMultiSensor()) << "Infrared value" << value;
|
||||
m_accelerometerEnabled = enabled;
|
||||
}
|
||||
|
||||
void SensorTag::updateButtonValue(const QByteArray &value)
|
||||
void SensorTag::configurePeriod(QLowEnergyService *serice, const QLowEnergyCharacteristic &characteristic, int measurementPeriod)
|
||||
{
|
||||
const quint8 *data = reinterpret_cast<const quint8 *>(value.constData());
|
||||
if (*data & 1)
|
||||
emit leftKeyPressed();
|
||||
if (*data & 2)
|
||||
emit rightKeyPressed();
|
||||
Q_ASSERT(measurementPeriod % 10 == 0);
|
||||
QByteArray payload;
|
||||
QDataStream stream(&payload, QIODevice::WriteOnly);
|
||||
stream << static_cast<quint8>(measurementPeriod / 10);
|
||||
|
||||
qCDebug(dcMultiSensor()) << "Configure period to" << measurementPeriod << payload.toHex();
|
||||
serice->writeCharacteristic(characteristic, payload);
|
||||
}
|
||||
|
||||
void SensorTag::updateHumidityValue(const QByteArray &value)
|
||||
void SensorTag::configureMovement(bool gyroscopeEnabled, bool accelerometerEnabled, bool magnetometerEnabled, bool wakeOnMotion)
|
||||
{
|
||||
qCDebug(dcMultiSensor()) << "Humidity value" << value;
|
||||
if (!m_movementService || !m_movementConfigurationCharacteristic.isValid())
|
||||
return;
|
||||
|
||||
quint16 configuration = 0;
|
||||
if (gyroscopeEnabled) {
|
||||
configuration |= (1 << 0); // enable x-axis
|
||||
configuration |= (1 << 1); // enable y-axis
|
||||
configuration |= (1 << 2); // enable z-axis
|
||||
}
|
||||
|
||||
if (accelerometerEnabled) {
|
||||
configuration |= (1 << 3); // enable x-axis
|
||||
configuration |= (1 << 4); // enable y-axis
|
||||
configuration |= (1 << 5); // enable z-axis
|
||||
}
|
||||
|
||||
if (magnetometerEnabled) {
|
||||
configuration |= (1 << 6); // enable all axis
|
||||
}
|
||||
|
||||
if (wakeOnMotion) {
|
||||
configuration |= (1 << 8); // enable
|
||||
}
|
||||
|
||||
// Accelerometer 2 Bit ( 0 = 2G, 1 = 4G, 2 = 8G, 3 = 16G)
|
||||
// Default 0
|
||||
|
||||
QByteArray data;
|
||||
QDataStream stream(&data, QIODevice::WriteOnly);
|
||||
stream.setByteOrder(QDataStream::BigEndian);
|
||||
stream << configuration;
|
||||
|
||||
qCDebug(dcMultiSensor()) << "Configure movement sensor" << data.toHex();
|
||||
m_movementService->writeCharacteristic(m_movementConfigurationCharacteristic, data);
|
||||
}
|
||||
|
||||
void SensorTag::updatePressureValue(const QByteArray &value)
|
||||
void SensorTag::processTemperatureData(const QByteArray &data)
|
||||
{
|
||||
qCDebug(dcMultiSensor()) << "Pressure value" << value;
|
||||
Q_ASSERT(data.count() == 4);
|
||||
|
||||
quint16 rawObjectTemperature = 0;
|
||||
quint16 rawAmbientTemperature = 0;
|
||||
|
||||
QByteArray payload(data);
|
||||
QDataStream stream(&payload, QIODevice::ReadOnly);
|
||||
stream.setByteOrder(QDataStream::LittleEndian);
|
||||
stream >> rawObjectTemperature >> rawAmbientTemperature ;
|
||||
|
||||
float scaleFactor = 0.03125;
|
||||
float objectTemperature = static_cast<float>(rawObjectTemperature) / 4 * scaleFactor;
|
||||
float ambientTemperature = static_cast<float>(rawAmbientTemperature) / 4 * scaleFactor;
|
||||
|
||||
//qCDebug(dcMultiSensor()) << "Temperature value" << data.toHex();
|
||||
//qCDebug(dcMultiSensor()) << "Object temperature" << roundValue(objectTemperature) << "°C";
|
||||
//qCDebug(dcMultiSensor()) << "Ambient temperature" << roundValue(ambientTemperature) << "°C";
|
||||
|
||||
m_device->setStateValue(sensortagObjectTemperatureStateTypeId, roundValue(objectTemperature));
|
||||
m_device->setStateValue(sensortagTemperatureStateTypeId, roundValue(ambientTemperature));
|
||||
}
|
||||
|
||||
void SensorTag::processKeyData(const QByteArray &data)
|
||||
{
|
||||
Q_ASSERT(data.count() == 1);
|
||||
quint8 flags = static_cast<quint8>(data.at(0));
|
||||
setLeftButtonPressed(testBitUint8(flags, 0));
|
||||
setRightButtonPressed(testBitUint8(flags, 1));
|
||||
setMagnetDetected(!testBitUint8(flags, 2));
|
||||
}
|
||||
|
||||
void SensorTag::processHumidityData(const QByteArray &data)
|
||||
{
|
||||
Q_ASSERT(data.count() == 4);
|
||||
quint16 rawHumidityTemperature = 0;
|
||||
quint16 rawHumidity = 0;
|
||||
|
||||
QByteArray payload(data);
|
||||
QDataStream stream(&payload, QIODevice::ReadOnly);
|
||||
stream.setByteOrder(QDataStream::LittleEndian);
|
||||
stream >> rawHumidityTemperature >> rawHumidity ;
|
||||
|
||||
//double humidityTemperature = (rawHumidityTemperature / 65536.0 * 165.0) - 40;
|
||||
double humidity = rawHumidity / 65536.0 * 100.0;
|
||||
|
||||
//qCDebug(dcMultiSensor()) << "Humidity" << humidity << "%" << humidityTemperature << "°C";
|
||||
m_device->setStateValue(sensortagHumidityStateTypeId, roundValue(humidity));
|
||||
}
|
||||
|
||||
void SensorTag::processPressureData(const QByteArray &data)
|
||||
{
|
||||
Q_ASSERT(data.count() == 6);
|
||||
|
||||
QByteArray pressureData(data.right(3));
|
||||
quint32 rawPressure = static_cast<quint8>(pressureData.at(2));
|
||||
rawPressure <<= 8;
|
||||
rawPressure |= static_cast<quint8>(pressureData.at(1));
|
||||
rawPressure <<= 8;
|
||||
rawPressure |= static_cast<quint8>(pressureData.at(0));
|
||||
|
||||
//qCDebug(dcMultiSensor()) << "Pressure:" << roundValue(rawPressure / 100.0) << "mBar";
|
||||
m_device->setStateValue(sensortagPressureStateTypeId, roundValue(rawPressure / 100.0));
|
||||
}
|
||||
|
||||
void SensorTag::processOpticalData(const QByteArray &data)
|
||||
{
|
||||
Q_ASSERT(data.count() == 2);
|
||||
|
||||
quint16 rawOptical = 0;
|
||||
QByteArray payload(data);
|
||||
QDataStream stream(&payload, QIODevice::ReadOnly);
|
||||
stream.setByteOrder(QDataStream::LittleEndian);
|
||||
stream >> rawOptical;
|
||||
|
||||
quint16 lumm = rawOptical & 0x0FFF;
|
||||
quint16 lume = (rawOptical & 0xF000) >> 12;
|
||||
|
||||
double lux = lumm * (0.01 * pow(2,lume));
|
||||
|
||||
//qCDebug(dcMultiSensor()) << "Lux:" << lux;
|
||||
device()->setStateValue(sensortagLightIntensityStateTypeId, roundValue(lux));
|
||||
}
|
||||
|
||||
void SensorTag::processMovementData(const QByteArray &data)
|
||||
{
|
||||
qCDebug(dcMultiSensor()) << "Movement value" << data.toHex();
|
||||
|
||||
QByteArray payload(data);
|
||||
QDataStream stream(&payload, QIODevice::ReadOnly);
|
||||
|
||||
qint16 gyroXRaw = 0; qint16 gyroYRaw = 0; qint16 gyroZRaw = 0;
|
||||
stream >> gyroXRaw >> gyroYRaw >> gyroZRaw;
|
||||
|
||||
qint16 accXRaw = 0; qint16 accYRaw = 0; qint16 accZRaw = 0;
|
||||
stream >> accXRaw >> accYRaw >> accZRaw;
|
||||
|
||||
qint16 magXRaw = 0; qint16 magYRaw = 0; qint16 magZRaw = 0;
|
||||
stream >> magXRaw >> magYRaw >> magZRaw;
|
||||
|
||||
|
||||
// Calculate rotation, unit deg/s, range -250, +250
|
||||
double gyroX = static_cast<double>(gyroXRaw) / (65536 / 500);
|
||||
double gyroY = static_cast<double>(gyroYRaw) / (65536 / 500);
|
||||
double gyroZ = static_cast<double>(gyroZRaw) / (65536 / 500);
|
||||
qCDebug(dcMultiSensor()) << "Gyroscope x:" << gyroX << " y:" << gyroY << " z:" << gyroZ;
|
||||
|
||||
}
|
||||
|
||||
void SensorTag::setLeftButtonPressed(bool pressed)
|
||||
{
|
||||
if (m_leftButtonPressed == pressed)
|
||||
return;
|
||||
|
||||
qCDebug(dcMultiSensor()) << "Left button" << (pressed ? "pressed" : "released");
|
||||
m_leftButtonPressed = pressed;
|
||||
emit leftButtonPressedChainged(m_leftButtonPressed);
|
||||
m_device->setStateValue(sensortagLeftButtonPressedStateTypeId, m_leftButtonPressed);
|
||||
}
|
||||
|
||||
void SensorTag::setRightButtonPressed(bool pressed)
|
||||
{
|
||||
if (m_rightButtonPressed == pressed)
|
||||
return;
|
||||
|
||||
qCDebug(dcMultiSensor()) << "Right button" << (pressed ? "pressed" : "released");
|
||||
m_rightButtonPressed = pressed;
|
||||
emit rightButtonPressedChainged(m_rightButtonPressed);
|
||||
m_device->setStateValue(sensortagRightButtonPressedStateTypeId, m_rightButtonPressed);
|
||||
}
|
||||
|
||||
void SensorTag::setMagnetDetected(bool detected)
|
||||
{
|
||||
if (m_magnetDetected == detected)
|
||||
return;
|
||||
|
||||
qCDebug(dcMultiSensor()) << "Magnet detector" << (detected ? "active" : "inactive");
|
||||
m_magnetDetected = detected;
|
||||
emit magnetDetectedChainged(m_magnetDetected);
|
||||
m_device->setStateValue(sensortagMagnetDetectedStateTypeId, m_magnetDetected);
|
||||
}
|
||||
|
||||
bool SensorTag::testBitUint8(quint8 value, int bitPosition)
|
||||
{
|
||||
return (((value)>> (bitPosition)) & 1);
|
||||
}
|
||||
|
||||
double SensorTag::roundValue(float value)
|
||||
{
|
||||
int tmpValue = static_cast<int>(value * 10);
|
||||
return static_cast<double>(tmpValue) / 10.0;
|
||||
}
|
||||
|
||||
void SensorTag::onConnectedChanged(const bool &connected)
|
||||
@ -51,80 +259,79 @@ void SensorTag::onConnectedChanged(const bool &connected)
|
||||
|
||||
if (!connected) {
|
||||
// Clean up services
|
||||
m_infraredService->deleteLater();
|
||||
m_buttonService->deleteLater();
|
||||
m_temperatureService->deleteLater();
|
||||
m_humidityService->deleteLater();
|
||||
m_pressureService->deleteLater();
|
||||
m_opticalService->deleteLater();
|
||||
m_keyService->deleteLater();
|
||||
m_movementService->deleteLater();
|
||||
|
||||
m_infraredService = nullptr;
|
||||
m_buttonService = nullptr;
|
||||
m_temperatureService = nullptr;
|
||||
m_humidityService = nullptr;
|
||||
m_pressureService = nullptr;
|
||||
m_opticalService = nullptr;
|
||||
m_keyService = nullptr;
|
||||
m_movementService = nullptr;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void SensorTag::onServiceDiscoveryFinished()
|
||||
{
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(infraredServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find infrared service";
|
||||
return;
|
||||
foreach (const QBluetoothUuid serviceUuid, m_bluetoothDevice->serviceUuids()) {
|
||||
qCDebug(dcMultiSensor()) << "-->" << serviceUuid;
|
||||
}
|
||||
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(accelerometerServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find accelereometer service";
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(temperatureServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find temperature service";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(humidityServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find humidity service";
|
||||
return;
|
||||
}
|
||||
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(magnetometerServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find magnetometer service";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(pressureServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find pressure service";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(gyroscopeServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find magnetometer service";
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(opticalServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find optical service";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(keyServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find key service";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!m_bluetoothDevice->serviceUuids().contains(movementServiceUuid)) {
|
||||
qCWarning(dcMultiSensor()) << "Could not find movement service";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
// IR Temperature
|
||||
if (!m_infraredService) {
|
||||
m_infraredService = m_bluetoothDevice->controller()->createServiceObject(infraredServiceUuid, this);
|
||||
if (!m_infraredService) {
|
||||
qCWarning(dcMultiSensor()) << "Could not create infrared service.";
|
||||
if (!m_temperatureService) {
|
||||
m_temperatureService = m_bluetoothDevice->controller()->createServiceObject(temperatureServiceUuid, this);
|
||||
if (!m_temperatureService) {
|
||||
qCWarning(dcMultiSensor()) << "Could not create temperature service.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
connect(m_infraredService, &QLowEnergyService::stateChanged, this, &SensorTag::onInfraredServiceStateChanged);
|
||||
connect(m_infraredService, &QLowEnergyService::characteristicChanged, this, &SensorTag::onInfraredServiceCharacteristicChanged);
|
||||
connect(m_temperatureService, &QLowEnergyService::stateChanged, this, &SensorTag::onTemperatureServiceStateChanged);
|
||||
connect(m_temperatureService, &QLowEnergyService::characteristicChanged, this, &SensorTag::onTemperatureServiceCharacteristicChanged);
|
||||
|
||||
if (m_infraredService->state() == QLowEnergyService::DiscoveryRequired) {
|
||||
m_infraredService->discoverDetails();
|
||||
}
|
||||
}
|
||||
|
||||
// Buttons
|
||||
if (!m_buttonService) {
|
||||
m_buttonService = m_bluetoothDevice->controller()->createServiceObject(buttonServiceUuid, this);
|
||||
if (!m_buttonService) {
|
||||
qCWarning(dcMultiSensor()) << "Could not create button service.";
|
||||
return;
|
||||
}
|
||||
|
||||
connect(m_buttonService, &QLowEnergyService::stateChanged, this, &SensorTag::onButtonServiceStateChanged);
|
||||
connect(m_buttonService, &QLowEnergyService::characteristicChanged, this, &SensorTag::onButtonServiceCharacteristicChanged);
|
||||
|
||||
if (m_buttonService->state() == QLowEnergyService::DiscoveryRequired) {
|
||||
m_buttonService->discoverDetails();
|
||||
if (m_temperatureService->state() == QLowEnergyService::DiscoveryRequired) {
|
||||
m_temperatureService->discoverDetails();
|
||||
}
|
||||
}
|
||||
|
||||
@ -133,6 +340,7 @@ void SensorTag::onServiceDiscoveryFinished()
|
||||
m_humidityService = m_bluetoothDevice->controller()->createServiceObject(humidityServiceUuid, this);
|
||||
if (!m_humidityService) {
|
||||
qCWarning(dcMultiSensor()) << "Could not create humidity service.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
@ -148,6 +356,7 @@ void SensorTag::onServiceDiscoveryFinished()
|
||||
m_pressureService = m_bluetoothDevice->controller()->createServiceObject(pressureServiceUuid, this);
|
||||
if (!m_pressureService) {
|
||||
qCWarning(dcMultiSensor()) << "Could not create pressure service.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
@ -157,17 +366,69 @@ void SensorTag::onServiceDiscoveryFinished()
|
||||
m_pressureService->discoverDetails();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Optical
|
||||
if (!m_opticalService) {
|
||||
m_opticalService = m_bluetoothDevice->controller()->createServiceObject(opticalServiceUuid, this);
|
||||
if (!m_opticalService) {
|
||||
qCWarning(dcMultiSensor()) << "Could not create optical service.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
connect(m_opticalService, &QLowEnergyService::stateChanged, this, &SensorTag::onOpticalServiceStateChanged);
|
||||
connect(m_opticalService, &QLowEnergyService::characteristicChanged, this, &SensorTag::onOpticalServiceCharacteristicChanged);
|
||||
|
||||
if (m_opticalService->state() == QLowEnergyService::DiscoveryRequired) {
|
||||
m_opticalService->discoverDetails();
|
||||
}
|
||||
}
|
||||
|
||||
// Key
|
||||
if (!m_keyService) {
|
||||
m_keyService = m_bluetoothDevice->controller()->createServiceObject(keyServiceUuid, this);
|
||||
if (!m_keyService) {
|
||||
qCWarning(dcMultiSensor()) << "Could not create key service.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
connect(m_keyService, &QLowEnergyService::stateChanged, this, &SensorTag::onKeyServiceStateChanged);
|
||||
connect(m_keyService, &QLowEnergyService::characteristicChanged, this, &SensorTag::onKeyServiceCharacteristicChanged);
|
||||
|
||||
if (m_keyService->state() == QLowEnergyService::DiscoveryRequired) {
|
||||
m_keyService->discoverDetails();
|
||||
}
|
||||
}
|
||||
|
||||
// Movement
|
||||
if (!m_movementService) {
|
||||
m_movementService = m_bluetoothDevice->controller()->createServiceObject(movementServiceUuid, this);
|
||||
if (!m_movementService) {
|
||||
qCWarning(dcMultiSensor()) << "Could not create movement service.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
connect(m_movementService, &QLowEnergyService::stateChanged, this, &SensorTag::onMovementServiceStateChanged);
|
||||
connect(m_movementService, &QLowEnergyService::characteristicChanged, this, &SensorTag::onMovementServiceCharacteristicChanged);
|
||||
|
||||
if (m_movementService->state() == QLowEnergyService::DiscoveryRequired) {
|
||||
m_movementService->discoverDetails();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void SensorTag::onInfraredServiceStateChanged(const QLowEnergyService::ServiceState &state)
|
||||
void SensorTag::onTemperatureServiceStateChanged(const QLowEnergyService::ServiceState &state)
|
||||
{
|
||||
// Only continue if discovered
|
||||
if (state != QLowEnergyService::ServiceDiscovered)
|
||||
return;
|
||||
|
||||
qCDebug(dcMultiSensor()) << "Infrared sensor service discovered.";
|
||||
qCDebug(dcMultiSensor()) << "Temperature sensor service discovered.";
|
||||
|
||||
foreach (const QLowEnergyCharacteristic &characteristic, m_infraredService->characteristics()) {
|
||||
foreach (const QLowEnergyCharacteristic &characteristic, m_temperatureService->characteristics()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << characteristic.name() << characteristic.uuid().toString() << characteristic.value();
|
||||
foreach (const QLowEnergyDescriptor &desciptor, characteristic.descriptors()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << desciptor.name() << desciptor.uuid().toString() << desciptor.value();
|
||||
@ -175,66 +436,47 @@ void SensorTag::onInfraredServiceStateChanged(const QLowEnergyService::ServiceSt
|
||||
}
|
||||
|
||||
// Data characteristic
|
||||
m_infraredDataCharacteristic = m_infraredService->characteristic(QBluetoothUuid(QUuid("f000aa01-0451-4000-b000-000000000000")));
|
||||
if (!m_infraredDataCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid infrared data characteristic.";
|
||||
m_temperatureDataCharacteristic = m_temperatureService->characteristic(QBluetoothUuid(QUuid("f000aa01-0451-4000-b000-000000000000")));
|
||||
if (!m_temperatureDataCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid temperature data characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
// Enable notifications
|
||||
QLowEnergyDescriptor notificationDescriptor = m_infraredDataCharacteristic.descriptor(QBluetoothUuid::ClientCharacteristicConfiguration);
|
||||
m_infraredService->writeDescriptor(notificationDescriptor, QByteArray::fromHex("0100"));
|
||||
QLowEnergyDescriptor notificationDescriptor = m_temperatureDataCharacteristic.descriptor(QBluetoothUuid::ClientCharacteristicConfiguration);
|
||||
m_temperatureService->writeDescriptor(notificationDescriptor, QByteArray::fromHex("0100"));
|
||||
|
||||
|
||||
// Config characteristic
|
||||
m_infraredConfigCharacteristic = m_infraredService->characteristic(QBluetoothUuid(QUuid("f000aa02-0451-4000-b000-000000000000")));
|
||||
if (!m_infraredConfigCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid infrared configuration characteristic.";
|
||||
m_temperatureConfigurationCharacteristic = m_temperatureService->characteristic(temperatureConfigurationCharacteristicUuid);
|
||||
if (!m_temperatureConfigurationCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid temperature configuration characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
// Period characteristic
|
||||
m_temperaturePeriodCharacteristic = m_temperatureService->characteristic(temperaturePeriodCharacteristicUuid);
|
||||
if (!m_temperaturePeriodCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid temperature period characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
configurePeriod(m_temperatureService, m_temperaturePeriodCharacteristic, m_temperaturePeriod);
|
||||
|
||||
// Enable measuring
|
||||
m_infraredService->writeCharacteristic(m_infraredConfigCharacteristic, QByteArray::fromHex("01"));
|
||||
m_temperatureService->writeCharacteristic(m_temperatureConfigurationCharacteristic, QByteArray::fromHex("01"));
|
||||
}
|
||||
|
||||
void SensorTag::onInfraredServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value)
|
||||
void SensorTag::onTemperatureServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value)
|
||||
{
|
||||
if (characteristic == m_infraredDataCharacteristic) {
|
||||
updateInfraredValue(value);
|
||||
if (characteristic == m_temperatureDataCharacteristic) {
|
||||
processTemperatureData(value);
|
||||
|
||||
// FIXME: Disable measuring
|
||||
// m_infraredService->writeCharacteristic(m_infraredConfigCharacteristic, QByteArray::fromHex("00"));
|
||||
}
|
||||
}
|
||||
|
||||
void SensorTag::onButtonServiceStateChanged(const QLowEnergyService::ServiceState &state)
|
||||
{
|
||||
// Only continue if discovered
|
||||
if (state != QLowEnergyService::ServiceDiscovered)
|
||||
return;
|
||||
|
||||
qCDebug(dcMultiSensor()) << "Button sensor service discovered.";
|
||||
|
||||
foreach (const QLowEnergyCharacteristic &characteristic, m_buttonService->characteristics()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << characteristic.name() << characteristic.uuid().toString() << characteristic.value();
|
||||
foreach (const QLowEnergyDescriptor &desciptor, characteristic.descriptors()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << desciptor.name() << desciptor.uuid().toString() << desciptor.value();
|
||||
}
|
||||
}
|
||||
|
||||
// Data characteristic
|
||||
m_buttonCharacteristic = m_buttonService->characteristic(QBluetoothUuid(QUuid("0000ffe1-0000-1000-8000-00805f9b34fb")));
|
||||
if (!m_buttonCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid button data characteristic.";
|
||||
}
|
||||
|
||||
// Enable notifications
|
||||
QLowEnergyDescriptor notificationDescriptor = m_buttonCharacteristic.descriptor(QBluetoothUuid::ClientCharacteristicConfiguration);
|
||||
m_buttonService->writeDescriptor(notificationDescriptor, QByteArray::fromHex("0100"));
|
||||
}
|
||||
|
||||
void SensorTag::onButtonServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value)
|
||||
{
|
||||
if (characteristic == m_buttonCharacteristic) {
|
||||
updateButtonValue(value);
|
||||
// m_temperatureService->writeCharacteristic(m_temperatureConfigCharacteristic, QByteArray::fromHex("00"));
|
||||
}
|
||||
}
|
||||
|
||||
@ -254,9 +496,11 @@ void SensorTag::onHumidityServiceStateChanged(const QLowEnergyService::ServiceSt
|
||||
}
|
||||
|
||||
// Data characteristic
|
||||
m_humidityDataCharacteristic = m_humidityService->characteristic(QBluetoothUuid(QUuid("f000aa21-0451-4000-b000-000000000000")));
|
||||
m_humidityDataCharacteristic = m_humidityService->characteristic(humidityDataCharacteristicUuid);
|
||||
if (!m_humidityDataCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid humidity data characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
// Enable notifications
|
||||
@ -264,19 +508,31 @@ void SensorTag::onHumidityServiceStateChanged(const QLowEnergyService::ServiceSt
|
||||
m_humidityService->writeDescriptor(notificationDescriptor, QByteArray::fromHex("0100"));
|
||||
|
||||
// Config characteristic
|
||||
m_humidityConfigCharacteristic = m_humidityService->characteristic(QBluetoothUuid(QUuid("f000aa22-0451-4000-b000-000000000000")));
|
||||
if (!m_humidityConfigCharacteristic.isValid()) {
|
||||
m_humidityConfigurationCharacteristic = m_humidityService->characteristic(humidityConfigurationCharacteristicUuid);
|
||||
if (!m_humidityConfigurationCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid humidity configuration characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
// Period characteristic
|
||||
m_humidityPeriodCharacteristic = m_humidityService->characteristic(humidityPeriodCharacteristicUuid);
|
||||
if (!m_humidityPeriodCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid humidity period characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
configurePeriod(m_humidityService, m_humidityPeriodCharacteristic, m_humidityPeriod);
|
||||
|
||||
// Enable measuring
|
||||
m_humidityService->writeCharacteristic(m_humidityConfigCharacteristic, QByteArray::fromHex("01"));
|
||||
m_humidityService->writeCharacteristic(m_humidityConfigurationCharacteristic, QByteArray::fromHex("01"));
|
||||
}
|
||||
|
||||
void SensorTag::onHumidityServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value)
|
||||
{
|
||||
if (characteristic == m_humidityDataCharacteristic) {
|
||||
updateHumidityValue(value);
|
||||
processHumidityData(value);
|
||||
// FIXME: Disable measuring
|
||||
// m_humidityService->writeCharacteristic(m_humidityConfigCharacteristic, QByteArray::fromHex("00"));
|
||||
}
|
||||
@ -298,9 +554,11 @@ void SensorTag::onPressureServiceStateChanged(const QLowEnergyService::ServiceSt
|
||||
}
|
||||
|
||||
// Data characteristic
|
||||
m_pressureDataCharacteristic = m_pressureService->characteristic(QBluetoothUuid(QUuid("f000aa41-0451-4000-b000-000000000000")));
|
||||
m_pressureDataCharacteristic = m_pressureService->characteristic(pressureDataCharacteristicUuid);
|
||||
if (!m_pressureDataCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid pressure data characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
// Enable notifications
|
||||
@ -308,36 +566,179 @@ void SensorTag::onPressureServiceStateChanged(const QLowEnergyService::ServiceSt
|
||||
m_pressureService->writeDescriptor(notificationDescriptor, QByteArray::fromHex("0100"));
|
||||
|
||||
// Config characteristic
|
||||
m_pressureConfigCharacteristic = m_pressureService->characteristic(QBluetoothUuid(QUuid("f000aa42-0451-4000-b000-000000000000")));
|
||||
if (!m_pressureConfigCharacteristic.isValid()) {
|
||||
m_pressureConfigurationCharacteristic = m_pressureService->characteristic(pressureConfigurationCharacteristicUuid);
|
||||
if (!m_pressureConfigurationCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid pressure configuration characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
// Period characteristic
|
||||
m_pressurePeriodCharacteristic = m_pressureService->characteristic(pressurePeriodCharacteristicUuid);
|
||||
if (!m_pressurePeriodCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid pressure period characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
configurePeriod(m_pressureService, m_pressurePeriodCharacteristic, m_pressurePeriod);
|
||||
|
||||
// Enable measuring
|
||||
m_pressureService->writeCharacteristic(m_pressureConfigCharacteristic, QByteArray::fromHex("01"));
|
||||
m_pressureService->writeCharacteristic(m_pressureConfigurationCharacteristic, QByteArray::fromHex("01"));
|
||||
}
|
||||
|
||||
void SensorTag::onPressureServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value)
|
||||
{
|
||||
if (characteristic == m_pressureDataCharacteristic) {
|
||||
updatePressureValue(value);
|
||||
processPressureData(value);
|
||||
// FIXME: Disable measuring
|
||||
// m_pressureService->writeCharacteristic(m_pressureConfigCharacteristic, QByteArray::fromHex("00"));
|
||||
}
|
||||
}
|
||||
|
||||
void SensorTag::measure()
|
||||
void SensorTag::onOpticalServiceStateChanged(const QLowEnergyService::ServiceState &state)
|
||||
{
|
||||
if (!m_bluetoothDevice->connected())
|
||||
// Only continue if discovered
|
||||
if (state != QLowEnergyService::ServiceDiscovered)
|
||||
return;
|
||||
|
||||
// TODO: measure using plugintimer to save energy
|
||||
qCDebug(dcMultiSensor()) << "Optical sensor service discovered.";
|
||||
|
||||
// qCDebug(dcMultiSensor()) << "Measure data" << m_bluetoothDevice->name() << m_bluetoothDevice->address().toString();
|
||||
foreach (const QLowEnergyCharacteristic &characteristic, m_pressureService->characteristics()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << characteristic.name() << characteristic.uuid().toString() << characteristic.value();
|
||||
foreach (const QLowEnergyDescriptor &desciptor, characteristic.descriptors()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << desciptor.name() << desciptor.uuid().toString() << desciptor.value();
|
||||
}
|
||||
}
|
||||
|
||||
// m_infraredService->writeCharacteristic(m_infraredConfigCharacteristic, QByteArray::fromHex("01"));
|
||||
// m_humidityService->writeCharacteristic(m_humidityConfigCharacteristic, QByteArray::fromHex("01"));
|
||||
// m_pressureService->writeCharacteristic(m_pressureConfigCharacteristic, QByteArray::fromHex("01"));
|
||||
// Data characteristic
|
||||
m_opticalDataCharacteristic = m_opticalService->characteristic(opticalDataCharacteristicUuid);
|
||||
if (!m_opticalDataCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid optical data characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
return;
|
||||
}
|
||||
|
||||
// Enable notifications
|
||||
QLowEnergyDescriptor notificationDescriptor = m_opticalDataCharacteristic.descriptor(QBluetoothUuid::ClientCharacteristicConfiguration);
|
||||
m_opticalService->writeDescriptor(notificationDescriptor, QByteArray::fromHex("0100"));
|
||||
|
||||
// Config characteristic
|
||||
m_opticalConfigurationCharacteristic = m_opticalService->characteristic(opticalConfigurationCharacteristicUuid);
|
||||
if (!m_opticalConfigurationCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid optical configuration characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
}
|
||||
|
||||
// Period characteristic
|
||||
m_opticalPeriodCharacteristic = m_opticalService->characteristic(opticalPeriodCharacteristicUuid);
|
||||
if (!m_opticalPeriodCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid optical period characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
}
|
||||
|
||||
// Set measurement period
|
||||
configurePeriod(m_opticalService, m_opticalPeriodCharacteristic, m_opticalPeriod);
|
||||
|
||||
// Enable measuring
|
||||
m_opticalService->writeCharacteristic(m_opticalConfigurationCharacteristic, QByteArray::fromHex("01"));
|
||||
}
|
||||
|
||||
void SensorTag::onOpticalServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value)
|
||||
{
|
||||
if (characteristic == m_opticalDataCharacteristic) {
|
||||
processOpticalData(value);
|
||||
// FIXME: Disable measuring
|
||||
// m_opticalService->writeCharacteristic(m_pressureopticalCharacteristic, QByteArray::fromHex("00"));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void SensorTag::onKeyServiceStateChanged(const QLowEnergyService::ServiceState &state)
|
||||
{
|
||||
// Only continue if discovered
|
||||
if (state != QLowEnergyService::ServiceDiscovered)
|
||||
return;
|
||||
|
||||
qCDebug(dcMultiSensor()) << "Key service discovered.";
|
||||
foreach (const QLowEnergyCharacteristic &characteristic, m_keyService->characteristics()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << characteristic.name() << characteristic.uuid().toString() << characteristic.value();
|
||||
foreach (const QLowEnergyDescriptor &desciptor, characteristic.descriptors()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << desciptor.name() << desciptor.uuid().toString() << desciptor.value();
|
||||
}
|
||||
}
|
||||
|
||||
// Data characteristic
|
||||
m_keyDataCharacteristic = m_keyService->characteristic(keyDataCharacteristicUuid);
|
||||
if (!m_keyDataCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid button data characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
}
|
||||
|
||||
// Enable notifications
|
||||
QLowEnergyDescriptor notificationDescriptor = m_keyDataCharacteristic.descriptor(QBluetoothUuid::ClientCharacteristicConfiguration);
|
||||
m_keyService->writeDescriptor(notificationDescriptor, QByteArray::fromHex("0100"));
|
||||
}
|
||||
|
||||
void SensorTag::onKeyServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value)
|
||||
{
|
||||
if (characteristic == m_keyDataCharacteristic) {
|
||||
processKeyData(value);
|
||||
}
|
||||
}
|
||||
|
||||
void SensorTag::onMovementServiceStateChanged(const QLowEnergyService::ServiceState &state)
|
||||
{
|
||||
// Only continue if discovered
|
||||
if (state != QLowEnergyService::ServiceDiscovered)
|
||||
return;
|
||||
|
||||
qCDebug(dcMultiSensor()) << "Movement sensor service discovered.";
|
||||
|
||||
foreach (const QLowEnergyCharacteristic &characteristic, m_pressureService->characteristics()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << characteristic.name() << characteristic.uuid().toString() << characteristic.value();
|
||||
foreach (const QLowEnergyDescriptor &desciptor, characteristic.descriptors()) {
|
||||
qCDebug(dcMultiSensor()) << " -->" << desciptor.name() << desciptor.uuid().toString() << desciptor.value();
|
||||
}
|
||||
}
|
||||
|
||||
// Data characteristic
|
||||
m_movementDataCharacteristic = m_movementService->characteristic(movementDataCharacteristicUuid);
|
||||
if (!m_movementDataCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid movement data characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
}
|
||||
|
||||
// Enable notifications
|
||||
QLowEnergyDescriptor notificationDescriptor = m_movementDataCharacteristic.descriptor(QBluetoothUuid::ClientCharacteristicConfiguration);
|
||||
m_movementService->writeDescriptor(notificationDescriptor, QByteArray::fromHex("0100"));
|
||||
|
||||
// Config characteristic
|
||||
m_movementConfigurationCharacteristic = m_movementService->characteristic(movementConfigurationCharacteristicUuid);
|
||||
if (!m_movementConfigurationCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid movement configuration characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
}
|
||||
|
||||
// Period characteristic
|
||||
m_movementPeriodCharacteristic = m_movementService->characteristic(movementPeriodCharacteristicUuid);
|
||||
if (!m_movementPeriodCharacteristic.isValid()) {
|
||||
qCWarning(dcMultiSensor()) << "Invalid movement period characteristic.";
|
||||
m_bluetoothDevice->disconnectDevice();
|
||||
}
|
||||
|
||||
// Set measurement period
|
||||
configurePeriod(m_movementService, m_movementPeriodCharacteristic, m_movementPeriod);
|
||||
|
||||
configureMovement();
|
||||
|
||||
// Enable measuring
|
||||
m_movementService->writeCharacteristic(m_movementConfigurationCharacteristic, QByteArray::fromHex("01"));
|
||||
}
|
||||
|
||||
void SensorTag::onMovementServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value)
|
||||
{
|
||||
if (characteristic == m_movementDataCharacteristic) {
|
||||
processMovementData(value);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1,3 +1,25 @@
|
||||
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
||||
* *
|
||||
* Copyright (C) 2015-2018 Simon Stuerz <simon.stuerz@guh.io> *
|
||||
* *
|
||||
* This file is part of guh. *
|
||||
* *
|
||||
* This library is free software; you can redistribute it and/or *
|
||||
* modify it under the terms of the GNU Lesser General Public *
|
||||
* License as published by the Free Software Foundation; either *
|
||||
* version 2.1 of the License, or (at your option) any later version. *
|
||||
* *
|
||||
* This library is distributed in the hope that it will be useful, *
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
|
||||
* Lesser General Public License for more details. *
|
||||
* *
|
||||
* You should have received a copy of the GNU Lesser General Public *
|
||||
* License along with this library; If not, see *
|
||||
* <http://www.gnu.org/licenses/>. *
|
||||
* *
|
||||
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||
|
||||
#ifndef SENSORTAG_H
|
||||
#define SENSORTAG_H
|
||||
|
||||
@ -7,17 +29,40 @@
|
||||
#include "extern-plugininfo.h"
|
||||
#include "hardware/bluetoothlowenergy/bluetoothlowenergydevice.h"
|
||||
|
||||
static QBluetoothUuid infraredServiceUuid = QBluetoothUuid(QUuid("f000aa00-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid accelerometerServiceUuid = QBluetoothUuid(QUuid("f000aa10-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid humidityServiceUuid = QBluetoothUuid(QUuid("f000aa20-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid magnetometerServiceUuid = QBluetoothUuid(QUuid("f000aa30-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid pressureServiceUuid = QBluetoothUuid(QUuid("f000aa40-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid gyroscopeServiceUuid = QBluetoothUuid(QUuid("f000aa50-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid testServiceUuid = QBluetoothUuid(QUuid("f000aa60-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid otaServiceUuid = QBluetoothUuid(QUuid("f000aac0-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid buttonServiceUuid = QBluetoothUuid(QUuid("0000ffe0-0000-1000-8000-00805f9b34fb"));
|
||||
// http://processors.wiki.ti.com/index.php/CC2650_SensorTag_User's_Guide
|
||||
|
||||
static QBluetoothUuid temperatureServiceUuid = QBluetoothUuid(QUuid("f000aa00-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid temperatureDataCharacteristicUuid = QBluetoothUuid(QUuid("f000aa01-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid temperatureConfigurationCharacteristicUuid = QBluetoothUuid(QUuid("f000aa02-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid temperaturePeriodCharacteristicUuid = QBluetoothUuid(QUuid("f000aa03-0451-4000-b000-000000000000"));
|
||||
|
||||
static QBluetoothUuid humidityServiceUuid = QBluetoothUuid(QUuid("f000aa20-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid humidityDataCharacteristicUuid = QBluetoothUuid(QUuid("f000aa21-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid humidityConfigurationCharacteristicUuid = QBluetoothUuid(QUuid("f000aa22-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid humidityPeriodCharacteristicUuid = QBluetoothUuid(QUuid("f000aa23-0451-4000-b000-000000000000"));
|
||||
|
||||
static QBluetoothUuid pressureServiceUuid = QBluetoothUuid(QUuid("f000aa40-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid pressureDataCharacteristicUuid = QBluetoothUuid(QUuid("f000aa41-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid pressureConfigurationCharacteristicUuid = QBluetoothUuid(QUuid("f000aa42-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid pressurePeriodCharacteristicUuid = QBluetoothUuid(QUuid("f000aa44-0451-4000-b000-000000000000"));
|
||||
|
||||
static QBluetoothUuid opticalServiceUuid = QBluetoothUuid(QUuid("f000aa70-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid opticalDataCharacteristicUuid = QBluetoothUuid(QUuid("f000aa71-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid opticalConfigurationCharacteristicUuid = QBluetoothUuid(QUuid("f000aa72-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid opticalPeriodCharacteristicUuid = QBluetoothUuid(QUuid("f000aa73-0451-4000-b000-000000000000"));
|
||||
|
||||
static QBluetoothUuid keyServiceUuid = QBluetoothUuid(QUuid("0000ffe0-0000-1000-8000-00805f9b34fb"));
|
||||
static QBluetoothUuid keyDataCharacteristicUuid = QBluetoothUuid(QUuid("0000ffe1-0000-1000-8000-00805f9b34fb"));
|
||||
|
||||
static QBluetoothUuid ioServiceUuid = QBluetoothUuid(QUuid("f000aa64-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid ioDataCharacteristicUuid = QBluetoothUuid(QUuid("f000aa65-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid ioConfigurationCharacteristicUuid = QBluetoothUuid(QUuid("f000aa66-0451-4000-b000-000000000000"));
|
||||
|
||||
static QBluetoothUuid movementServiceUuid = QBluetoothUuid(QUuid("f000aa80-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid movementDataCharacteristicUuid = QBluetoothUuid(QUuid("f000aa81-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid movementConfigurationCharacteristicUuid = QBluetoothUuid(QUuid("f000aa82-0451-4000-b000-000000000000"));
|
||||
static QBluetoothUuid movementPeriodCharacteristicUuid = QBluetoothUuid(QUuid("f000aa83-0451-4000-b000-000000000000"));
|
||||
|
||||
// Currently unused services
|
||||
|
||||
class SensorTag : public QObject
|
||||
{
|
||||
@ -28,49 +73,93 @@ public:
|
||||
Device *device();
|
||||
BluetoothLowEnergyDevice *bluetoothDevice();
|
||||
|
||||
void setAccelerometerEnabled(bool enabled);
|
||||
void setGyroscopeEnabled(bool enabled);
|
||||
void setMagnetometerEnabled(bool enabled);
|
||||
void setMeasurementPeriod(int period);
|
||||
|
||||
private:
|
||||
Device *m_device;
|
||||
BluetoothLowEnergyDevice *m_bluetoothDevice;
|
||||
|
||||
// Services
|
||||
QLowEnergyService *m_infraredService = nullptr;
|
||||
QLowEnergyService *m_buttonService = nullptr;
|
||||
QLowEnergyService *m_temperatureService = nullptr;
|
||||
QLowEnergyService *m_humidityService = nullptr;
|
||||
QLowEnergyService *m_pressureService = nullptr;
|
||||
QLowEnergyService *m_accelerometerService = nullptr;
|
||||
QLowEnergyService *m_magnetometerService = nullptr;
|
||||
QLowEnergyService *m_gyroscopeService = nullptr;
|
||||
QLowEnergyService *m_opticalService = nullptr;
|
||||
QLowEnergyService *m_keyService = nullptr;
|
||||
QLowEnergyService *m_movementService = nullptr;
|
||||
|
||||
// Characteristics
|
||||
QLowEnergyCharacteristic m_infraredDataCharacteristic;
|
||||
QLowEnergyCharacteristic m_infraredConfigCharacteristic;
|
||||
QLowEnergyCharacteristic m_buttonCharacteristic;
|
||||
QLowEnergyCharacteristic m_temperatureDataCharacteristic;
|
||||
QLowEnergyCharacteristic m_temperatureConfigurationCharacteristic;
|
||||
QLowEnergyCharacteristic m_temperaturePeriodCharacteristic;
|
||||
|
||||
QLowEnergyCharacteristic m_humidityDataCharacteristic;
|
||||
QLowEnergyCharacteristic m_humidityConfigCharacteristic;
|
||||
QLowEnergyCharacteristic m_humidityConfigurationCharacteristic;
|
||||
QLowEnergyCharacteristic m_humidityPeriodCharacteristic;
|
||||
|
||||
QLowEnergyCharacteristic m_pressureDataCharacteristic;
|
||||
QLowEnergyCharacteristic m_pressureConfigCharacteristic;
|
||||
QLowEnergyCharacteristic m_pressureConfigurationCharacteristic;
|
||||
QLowEnergyCharacteristic m_pressurePeriodCharacteristic;
|
||||
|
||||
QLowEnergyCharacteristic m_opticalDataCharacteristic;
|
||||
QLowEnergyCharacteristic m_opticalConfigurationCharacteristic;
|
||||
QLowEnergyCharacteristic m_opticalPeriodCharacteristic;
|
||||
|
||||
void updateInfraredValue(const QByteArray &value);
|
||||
void updateButtonValue(const QByteArray &value);
|
||||
void updateHumidityValue(const QByteArray &value);
|
||||
void updatePressureValue(const QByteArray &value);
|
||||
QLowEnergyCharacteristic m_keyDataCharacteristic;
|
||||
|
||||
QLowEnergyCharacteristic m_movementDataCharacteristic;
|
||||
QLowEnergyCharacteristic m_movementConfigurationCharacteristic;
|
||||
QLowEnergyCharacteristic m_movementPeriodCharacteristic;
|
||||
|
||||
// Measure periods
|
||||
int m_temperaturePeriod = 2500;
|
||||
int m_humidityPeriod = 2500;
|
||||
int m_pressurePeriod = 2500;
|
||||
int m_opticalPeriod = 2500;
|
||||
int m_movementPeriod = 500;
|
||||
|
||||
bool m_leftButtonPressed = false;
|
||||
bool m_rightButtonPressed = false;
|
||||
bool m_magnetDetected = false;
|
||||
|
||||
// Plugin configs
|
||||
bool m_accelerometerEnabled = true;
|
||||
bool m_gyroscopeEnabled = false;
|
||||
bool m_magnetometerEnabled = false;
|
||||
|
||||
void configurePeriod(QLowEnergyService *serice, const QLowEnergyCharacteristic &characteristic, int measurementPeriod);
|
||||
void configureMovement(bool gyroscopeEnabled = false, bool accelerometerEnabled = true, bool magnetometerEnabled = true, bool wakeOnMotion = true);
|
||||
|
||||
void processTemperatureData(const QByteArray &data);
|
||||
void processKeyData(const QByteArray &data);
|
||||
void processHumidityData(const QByteArray &data);
|
||||
void processPressureData(const QByteArray &data);
|
||||
void processOpticalData(const QByteArray &data);
|
||||
void processMovementData(const QByteArray &data);
|
||||
|
||||
// Set methods
|
||||
void setLeftButtonPressed(bool pressed);
|
||||
void setRightButtonPressed(bool pressed);
|
||||
void setMagnetDetected(bool detected);
|
||||
|
||||
// Helper
|
||||
bool testBitUint8(quint8 value, int bitPosition);
|
||||
double roundValue(float value);
|
||||
|
||||
signals:
|
||||
void leftKeyPressed();
|
||||
void rightKeyPressed();
|
||||
void leftButtonPressedChainged(bool pressed);
|
||||
void rightButtonPressedChainged(bool pressed);
|
||||
void magnetDetectedChainged(bool detected);
|
||||
|
||||
private slots:
|
||||
void onConnectedChanged(const bool &connected);
|
||||
void onServiceDiscoveryFinished();
|
||||
|
||||
// Infrared sensor service
|
||||
void onInfraredServiceStateChanged(const QLowEnergyService::ServiceState &state);
|
||||
void onInfraredServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value);
|
||||
|
||||
// Button service
|
||||
void onButtonServiceStateChanged(const QLowEnergyService::ServiceState &state);
|
||||
void onButtonServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value);
|
||||
// Temperature sensor service
|
||||
void onTemperatureServiceStateChanged(const QLowEnergyService::ServiceState &state);
|
||||
void onTemperatureServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value);
|
||||
|
||||
// Humidity sensor service
|
||||
void onHumidityServiceStateChanged(const QLowEnergyService::ServiceState &state);
|
||||
@ -80,9 +169,17 @@ private slots:
|
||||
void onPressureServiceStateChanged(const QLowEnergyService::ServiceState &state);
|
||||
void onPressureServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value);
|
||||
|
||||
// Optical sensor service
|
||||
void onOpticalServiceStateChanged(const QLowEnergyService::ServiceState &state);
|
||||
void onOpticalServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value);
|
||||
|
||||
public slots:
|
||||
void measure();
|
||||
// Button service
|
||||
void onKeyServiceStateChanged(const QLowEnergyService::ServiceState &state);
|
||||
void onKeyServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value);
|
||||
|
||||
// Movement service
|
||||
void onMovementServiceStateChanged(const QLowEnergyService::ServiceState &state);
|
||||
void onMovementServiceCharacteristicChanged(const QLowEnergyCharacteristic &characteristic, const QByteArray &value);
|
||||
|
||||
};
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user