From f585b127300383fe321b5ff1a08ba09dce403890 Mon Sep 17 00:00:00 2001 From: Florent Revest Date: Tue, 11 Jan 2022 23:44:15 +0100 Subject: [PATCH 2/4] Add heart rate monitor sensor with hybris adaptor --- adaptors/adaptors.pro | 1 + .../hybrishrmadaptor/hybrishrmadaptor.cpp | 101 +++++++++++++ adaptors/hybrishrmadaptor/hybrishrmadaptor.h | 67 +++++++++ .../hybrishrmadaptor/hybrishrmadaptor.pro | 13 ++ .../hybrishrmadaptorplugin.cpp | 35 +++++ .../hybrishrmadaptor/hybrishrmadaptorplugin.h | 38 +++++ config/20-sensors-default.conf | 1 + config/sensord-hybris.conf | 1 + datatypes/datatypes.pro | 7 +- datatypes/heartrate.cpp | 37 +++++ datatypes/heartrate.h | 133 ++++++++++++++++++ datatypes/heartratedata.h | 91 ++++++++++++ datatypes/utils.cpp | 3 + qt-api/hrmsensor_i.cpp | 80 +++++++++++ qt-api/hrmsensor_i.h | 121 ++++++++++++++++ qt-api/qt-api.pro | 6 +- sensors/hrmsensor/hrmplugin.cpp | 49 +++++++ sensors/hrmsensor/hrmplugin.h | 43 ++++++ sensors/hrmsensor/hrmsensor.cpp | 123 ++++++++++++++++ sensors/hrmsensor/hrmsensor.h | 101 +++++++++++++ sensors/hrmsensor/hrmsensor.pro | 19 +++ sensors/hrmsensor/hrmsensor_a.cpp | 38 +++++ sensors/hrmsensor/hrmsensor_a.h | 55 ++++++++ sensors/sensors.pro | 3 +- 24 files changed, 1161 insertions(+), 5 deletions(-) create mode 100644 adaptors/hybrishrmadaptor/hybrishrmadaptor.cpp create mode 100644 adaptors/hybrishrmadaptor/hybrishrmadaptor.h create mode 100644 adaptors/hybrishrmadaptor/hybrishrmadaptor.pro create mode 100644 adaptors/hybrishrmadaptor/hybrishrmadaptorplugin.cpp create mode 100644 adaptors/hybrishrmadaptor/hybrishrmadaptorplugin.h create mode 100644 datatypes/heartrate.cpp create mode 100644 datatypes/heartrate.h create mode 100644 datatypes/heartratedata.h create mode 100644 qt-api/hrmsensor_i.cpp create mode 100644 qt-api/hrmsensor_i.h create mode 100644 sensors/hrmsensor/hrmplugin.cpp create mode 100644 sensors/hrmsensor/hrmplugin.h create mode 100644 sensors/hrmsensor/hrmsensor.cpp create mode 100644 sensors/hrmsensor/hrmsensor.h create mode 100644 sensors/hrmsensor/hrmsensor.pro create mode 100644 sensors/hrmsensor/hrmsensor_a.cpp create mode 100644 sensors/hrmsensor/hrmsensor_a.h diff --git a/adaptors/adaptors.pro b/adaptors/adaptors.pro index 70ffb6f..ce558a4 100644 --- a/adaptors/adaptors.pro +++ b/adaptors/adaptors.pro @@ -11,7 +11,8 @@ HYBRIS_SUBDIRS = hybrisaccelerometer \ hybrisorientationadaptor \ hybrisrotationadaptor \ hybrisgeorotationadaptor \ - hybrisstepcounteradaptor + hybrisstepcounteradaptor \ + hybrishrmadaptor # split like this as Sailfish only installs hybris plugins contains(CONFIG,hybris) { diff --git a/adaptors/hybrishrmadaptor/hybrishrmadaptor.cpp b/adaptors/hybrishrmadaptor/hybrishrmadaptor.cpp new file mode 100644 index 0000000..0b92efa --- /dev/null +++ b/adaptors/hybrishrmadaptor/hybrishrmadaptor.cpp @@ -0,0 +1,101 @@ +/**************************************************************************** +** +** Copyright (C) 2013 Jolla Ltd +** Contact: lorn.potter@jollamobile.com +** +** Copyright (C) 2019 Florent Revest +** Contact: revestflo@gmail.com +** +** +** $QT_BEGIN_LICENSE:LGPL$ +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#include "hybrishrmadaptor.h" +#include "logging.h" +#include "datatypes/utils.h" +#include +#include "config.h" + +#ifndef SENSOR_TYPE_HEART_RATE +#define SENSOR_TYPE_HEART_RATE (21) +#endif + +HybrisHrmAdaptor::HybrisHrmAdaptor(const QString& id) : + HybrisAdaptor(id, SENSOR_TYPE_HEART_RATE) +{ + buffer = new DeviceAdaptorRingBuffer(1); + setAdaptedSensor("hrm", "Heart rate monitor", buffer); + setDescription("Hybris heart rate monitor"); + powerStatePath = SensorFrameworkConfig::configuration()->value("heartrate/powerstate_path").toByteArray(); + if (!powerStatePath.isEmpty() && !QFile::exists(powerStatePath)) + { + sensordLogW() << "Path does not exists: " << powerStatePath; + powerStatePath.clear(); + } + // Set default delay. + setInterval(200, 0); +} + +HybrisHrmAdaptor::~HybrisHrmAdaptor() +{ + delete buffer; +} + +bool HybrisHrmAdaptor::startSensor() +{ + if (!(HybrisAdaptor::startSensor())) + return false; + if (isRunning() && !powerStatePath.isEmpty()) + writeToFile(powerStatePath, "1"); + sensordLogD() << "Hybris HybrisHrmAdaptor start\n"; + return true; +} + +void HybrisHrmAdaptor::sendInitialData() +{ + sensordLogW() << "No initial data for heart rate monitor"; +} + +void HybrisHrmAdaptor::stopSensor() +{ + HybrisAdaptor::stopSensor(); + if (!isRunning() && !powerStatePath.isEmpty()) + writeToFile(powerStatePath, "0"); + sensordLogD() << "Hybris HybrisHrmAdaptor stop\n"; +} + +void HybrisHrmAdaptor::processSample(const sensors_event_t& data) +{ + HeartRateData *d = buffer->nextSlot(); + d->timestamp_ = quint64(data.timestamp * .001); + d->bpm_ = data.heart_rate.bpm; + switch(data.heart_rate.status) { + case SENSOR_STATUS_UNRELIABLE: + d->status_ = HrmUnreliable; + break; + case SENSOR_STATUS_ACCURACY_LOW: + d->status_ = HrmAccuracyLow; + break; + case SENSOR_STATUS_ACCURACY_MEDIUM: + d->status_ = HrmAccuracyMedium; + break; + case SENSOR_STATUS_ACCURACY_HIGH: + d->status_ = HrmAccuracyHigh; + break; + default: + d->status_ = HrmNoContact; + } + buffer->commit(); + buffer->wakeUpReaders(); +} diff --git a/adaptors/hybrishrmadaptor/hybrishrmadaptor.h b/adaptors/hybrishrmadaptor/hybrishrmadaptor.h new file mode 100644 index 0000000..2426871 --- /dev/null +++ b/adaptors/hybrishrmadaptor/hybrishrmadaptor.h @@ -0,0 +1,67 @@ +/**************************************************************************** +** +** Copyright (C) 2013 Jolla Ltd +** Contact: lorn.potter@jollamobile.com +** +** Copyright (C) 2019 Florent Revest +** Contact: revestflo@gmail.com +** +** +** $QT_BEGIN_LICENSE:LGPL$ +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#ifndef HYBRISHRMADAPTOR_H +#define HYBRISHRMADAPTOR_H +#include "hybrisadaptor.h" + +#include +#include +#include +#include "deviceadaptorringbuffer.h" +#include "datatypes/heartratedata.h" +#include + +/** + * @brief Adaptor for hybris hrm sensor. + * + * Adaptor for heart rate monitor sensor. + * + * Returns the beat per minute of the user's heart. + * + */ +class HybrisHrmAdaptor : public HybrisAdaptor +{ + Q_OBJECT + +public: + static DeviceAdaptor* factoryMethod(const QString& id) { + return new HybrisHrmAdaptor(id); + } + HybrisHrmAdaptor(const QString& id); + ~HybrisHrmAdaptor(); + + bool startSensor(); + void stopSensor(); + + void sendInitialData(); + +protected: + void processSample(const sensors_event_t& data); + +private: + DeviceAdaptorRingBuffer* buffer; + QByteArray powerStatePath; + +}; +#endif diff --git a/adaptors/hybrishrmadaptor/hybrishrmadaptor.pro b/adaptors/hybrishrmadaptor/hybrishrmadaptor.pro new file mode 100644 index 0000000..f7b7d6c --- /dev/null +++ b/adaptors/hybrishrmadaptor/hybrishrmadaptor.pro @@ -0,0 +1,13 @@ +TARGET = hybrishrmadaptor + +HEADERS += hybrishrmadaptor.h \ + hybrishrmadaptorplugin.h + +SOURCES += hybrishrmadaptor.cpp \ + hybrishrmadaptorplugin.cpp +LIBS+= -L../../core -lhybrissensorfw-qt5 + +include( ../adaptor-config.pri ) +config_hybris { + PKGCONFIG += android-headers +} diff --git a/adaptors/hybrishrmadaptor/hybrishrmadaptorplugin.cpp b/adaptors/hybrishrmadaptor/hybrishrmadaptorplugin.cpp new file mode 100644 index 0000000..8819af7 --- /dev/null +++ b/adaptors/hybrishrmadaptor/hybrishrmadaptorplugin.cpp @@ -0,0 +1,35 @@ +/**************************************************************************** +** +** Copyright (C) 2013 Jolla Ltd +** Contact: lorn.potter@jollamobile.com +** +** Copyright (C) 2019 Florent Revest +** Contact: revestflo@gmail.com +** +** +** $QT_BEGIN_LICENSE:LGPL$ +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#include "hybrishrmadaptorplugin.h" +#include "hybrishrmadaptor.h" +#include "sensormanager.h" +#include "logging.h" + +void HybrisHrmAdaptorPlugin::Register(class Loader&) +{ + sensordLogD() << "registering hybrishrmadaptor"; + SensorManager& sm = SensorManager::instance(); + sm.registerDeviceAdaptor("hrmadaptor"); +} + diff --git a/adaptors/hybrishrmadaptor/hybrishrmadaptorplugin.h b/adaptors/hybrishrmadaptor/hybrishrmadaptorplugin.h new file mode 100644 index 0000000..b0a19f6 --- /dev/null +++ b/adaptors/hybrishrmadaptor/hybrishrmadaptorplugin.h @@ -0,0 +1,38 @@ +/**************************************************************************** +** +** Copyright (C) 2013 Jolla Ltd +** Contact: lorn.potter@jollamobile.com +** +** Copyright (C) 2019 Florent Revest +** Contact: revestflo@gmail.com +** +** +** $QT_BEGIN_LICENSE:LGPL$ +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#ifndef HYBRISHRMADAPTORPLUGIN_H +#define HYBRISHRMADAPTORPLUGIN_H + +#include "plugin.h" + +class HybrisHrmAdaptorPlugin : public Plugin +{ + Q_OBJECT + Q_PLUGIN_METADATA(IID "com.nokia.SensorService.Plugin/1.0") + +private: + void Register(class Loader& l); +}; + +#endif diff --git a/config/20-sensors-default.conf b/config/20-sensors-default.conf index 079bcde..5bccd68 100644 --- a/config/20-sensors-default.conf +++ b/config/20-sensors-default.conf @@ -42,6 +42,7 @@ magnetometersensor=True pressuresensor=True rotationsensor=True stepcountersensor=True +hrmsensor=True ; To avoid revisiting config files for all old ports in the future, the ; defaults for added sensors should be set "False" by default here, and diff --git a/config/sensord-hybris.conf b/config/sensord-hybris.conf index 5c5edf9..8d5cdfb 100644 --- a/config/sensord-hybris.conf +++ b/config/sensord-hybris.conf @@ -7,6 +7,7 @@ gyroscopeadaptor = hybrisgyroscopeadaptor orientationadaptor = hybrisorientationadaptor stepcounteradaptor = hybrisstepcounteradaptor pressureadaptor = hybrispressureadaptor +hrmadaptor = hybrishrmadaptor [magnetometer] scale_coefficient = 1 diff --git a/datatypes/datatypes.pro b/datatypes/datatypes.pro index c90be16..23d7b89 100644 --- a/datatypes/datatypes.pro +++ b/datatypes/datatypes.pro @@ -25,7 +25,9 @@ HEADERS += xyz.h \ touchdata.h \ proximity.h \ lid.h \ - liddata.h + liddata.h \ + heartratedata.h \ + heartrate.h SOURCES += xyz.cpp \ orientation.cpp \ @@ -33,7 +35,8 @@ SOURCES += xyz.cpp \ compass.cpp \ utils.cpp \ tap.cpp \ - lid.cpp + lid.cpp \ + heartrate.cpp include(../common-install.pri) publicheaders.path = $${publicheaders.path}/datatypes diff --git a/datatypes/heartrate.cpp b/datatypes/heartrate.cpp new file mode 100644 index 0000000..66d816a --- /dev/null +++ b/datatypes/heartrate.cpp @@ -0,0 +1,37 @@ +/** + @file heartrate.cpp + @brief QObject based datatype for HeartRateData + +

+ Copyright (C) 2009-2010 Nokia Corporation + + @author Joep van Gassel + @author Timo Rongas + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#include "heartrate.h" + +HeartRate::HeartRate(const HeartRateData& heartRateData) + : QObject(), data_(heartRateData.timestamp_, heartRateData.status_, heartRateData.bpm_) +{ +} + +HeartRate::HeartRate(const HeartRate& heartRate) + : QObject(), data_(heartRate.heartRateData().timestamp_, heartRate.heartRateData().status_, heartRate.heartRateData().bpm_) +{ +} diff --git a/datatypes/heartrate.h b/datatypes/heartrate.h new file mode 100644 index 0000000..d6b9e7e --- /dev/null +++ b/datatypes/heartrate.h @@ -0,0 +1,133 @@ +/** + @file heartrate.h + @brief QObject based datatype for HeartRateData + +

+ Copyright (C) 2009-2010 Nokia Corporation + + @author Joep van Gassel + @author Timo Rongas + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#ifndef HEARTRATE_H +#define HEARTRATE_H + +#include +#include + +/** + * QObject facade for #HeartRateData. + */ +class HeartRate : public QObject +{ + Q_OBJECT + + Q_PROPERTY(HrmStatus hrmStatus READ status) + Q_PROPERTY(int bpm READ bpm) + +public: + /** + * Default constructor. + */ + HeartRate() {} + + /** + * Constructor. + * + * @param HeartRateData Source object. + */ + HeartRate(const HeartRateData& heartRateData); + + /** + * Copy constructor. + * + * @param HeartRate Source object. + */ + HeartRate(const HeartRate& heartRate); + + /** + * Accessor for contained #HeartRateData. + * + * @return contained #HeartRateData. + */ + const HeartRateData& heartRateData() const { return data_; } + + /** + * Accessor for hrm status. + * + * @return heart rate monitor status. + */ + HrmStatus status() const { return data_.status_; } + + /** + * Accessor for bpm. + * + * @return beat per minutes. + */ + int bpm() const { return data_.bpm_; } + + /** + * Assignment operator. + * + * @param origin Source object for assigment. + */ + HeartRate& operator=(const HeartRate& origin) + { + data_ = origin.heartRateData(); + return *this; + } + +private: + HeartRateData data_; /**< Contained data */ + + friend const QDBusArgument &operator>>(const QDBusArgument &argument, HeartRate& heartRate); +}; + +Q_DECLARE_METATYPE( HeartRate ) + +/** + * Marshall the HeartRate data into a D-Bus argument + * + * @param argument dbus argument. + * @param heartRate data to marshall. + * @return dbus argument. + */ +inline QDBusArgument &operator<<(QDBusArgument &argument, const HeartRate &heartRate) +{ + argument.beginStructure(); + argument << heartRate.heartRateData().status_ << heartRate.heartRateData().bpm_; + argument.endStructure(); + return argument; +} + +/** + * Unmarshall HeartRate data from the D-Bus argument + * + * @param argument dbus argument. + * @param heartRate unmarshalled data. + * @return dbus argument. + */ +inline const QDBusArgument &operator>>(const QDBusArgument &argument, HeartRate &heartRate) +{ + argument.beginStructure(); + argument >> heartRate.data_.status_ >> heartRate.data_.bpm_; + argument.endStructure(); + return argument; +} + +#endif // HEARTRATE_H diff --git a/datatypes/heartratedata.h b/datatypes/heartratedata.h new file mode 100644 index 0000000..e4ec7a4 --- /dev/null +++ b/datatypes/heartratedata.h @@ -0,0 +1,91 @@ +/** + @file heartratedata.h + @brief Datatypes for different filters + +

+ Copyright (C) 2009-2010 Nokia Corporation + + @author Joep van Gassel + @author Timo Rongas + @author Ustun Ergenoglu + @author Antti Virtanen + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#ifndef HEARTRATEDATA_H +#define HEARTRATEDATA_H + +#include + +/** + * Status + */ +enum HrmStatus +{ + HrmNoContact, + HrmUnreliable, + HrmAccuracyLow, + HrmAccuracyMedium, + HrmAccuracyHigh +}; +Q_DECLARE_METATYPE ( HrmStatus ) + +inline QDBusArgument &operator<<(QDBusArgument &argument, HrmStatus value) +{ + argument.beginStructure(); + qlonglong newVal = (qlonglong)value; + argument << newVal; + argument.endStructure(); + return argument; +} + +inline const QDBusArgument &operator>>(const QDBusArgument &argument, HrmStatus &val) +{ + argument.beginStructure(); + qlonglong result = 0; + argument >> result; + val = (HrmStatus)result; + argument.endStructure(); + return argument; +} + +/** + * Class for vector type measurement data (timestamp, x, y, z). + */ +class HeartRateData : public TimedData +{ +public: + /** + * Constructor. + */ + HeartRateData() : TimedData(0), status_(HrmNoContact), bpm_(0) {} + + /** + * Constructor. + * + * @param timestamp monotonic time (microsec) + * @param bpm Beats per minute. + * @param status Heart Rate Monitor status. + */ + HeartRateData(const quint64& timestamp, HrmStatus status, int bpm) : TimedData(timestamp), status_(status), bpm_(bpm) {} + + HrmStatus status_; /**< hrm status */ + int bpm_; /**< beat per minute */ +}; +Q_DECLARE_METATYPE ( HeartRateData ) + +#endif // HEARTRATEDATA_H diff --git a/datatypes/utils.cpp b/datatypes/utils.cpp index b6464fd..6a64346 100644 --- a/datatypes/utils.cpp +++ b/datatypes/utils.cpp @@ -39,6 +39,7 @@ #include "tap.h" #include "posedata.h" #include "proximity.h" +#include "heartrate.h" void __attribute__ ((constructor)) datatypes_init(void) { @@ -55,6 +56,8 @@ void __attribute__ ((constructor)) datatypes_init(void) qRegisterMetaType(); qRegisterMetaType(); qRegisterMetaType(); + qRegisterMetaType(); + qDBusRegisterMetaType(); } void __attribute__ ((destructor)) datatypes_fini(void) diff --git a/qt-api/hrmsensor_i.cpp b/qt-api/hrmsensor_i.cpp new file mode 100644 index 0000000..6ecfa29 --- /dev/null +++ b/qt-api/hrmsensor_i.cpp @@ -0,0 +1,80 @@ +/** + @file hrmsensor_i.cpp + @brief Interface for heart rate monitor sensor + +

+ Copyright (C) 2009-2010 Nokia Corporation + Copyright (C) 2019 Florent Revest + + @author Kimmo Lindholm + @author Timo Rongas + @author Antti Virtanen + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#include "sensormanagerinterface.h" +#include "hrmsensor_i.h" +#include "socketreader.h" + +const char* HrmSensorChannelInterface::staticInterfaceName = "local.HrmSensor"; + +AbstractSensorChannelInterface* HrmSensorChannelInterface::factoryMethod(const QString& id, int sessionId) +{ + return new HrmSensorChannelInterface(OBJECT_PATH + "/" + id, sessionId); +} + +HrmSensorChannelInterface::HrmSensorChannelInterface(const QString& path, int sessionId) + : AbstractSensorChannelInterface(path, HrmSensorChannelInterface::staticInterfaceName, sessionId) +{ +} + +const HrmSensorChannelInterface* HrmSensorChannelInterface::listenInterface(const QString& id) +{ + return dynamic_cast (interface(id)); +} + +HrmSensorChannelInterface* HrmSensorChannelInterface::controlInterface(const QString& id) +{ + return interface(id); +} + + +HrmSensorChannelInterface* HrmSensorChannelInterface::interface(const QString& id) +{ + SensorManagerInterface& sm = SensorManagerInterface::instance(); + if ( !sm.registeredAndCorrectClassName( id, HrmSensorChannelInterface::staticMetaObject.className() ) ) + { + return 0; + } + + return dynamic_cast(sm.interface(id)); +} + +bool HrmSensorChannelInterface::dataReceivedImpl() +{ + QVector values; + if(!read(values)) + return false; + foreach(const HeartRateData& data, values) + emit HeartRateChanged(data); + return true; +} + +HeartRate HrmSensorChannelInterface::heartRate() +{ + return getAccessor("heartRate"); +} diff --git a/qt-api/hrmsensor_i.h b/qt-api/hrmsensor_i.h new file mode 100644 index 0000000..e7fd3a0 --- /dev/null +++ b/qt-api/hrmsensor_i.h @@ -0,0 +1,121 @@ +/** + @file hrmsensor_i.h + @brief Interface for heart rate monitor sensor + +

+ Copyright (C) 2009-2010 Nokia Corporation + Copyright (C) 2019 Florent Revest + + @author Kimmo Lindholm + @author Timo Rongas + @author Antti Virtanen + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#ifndef HRMSENSOR_I_H +#define HRMSENSOR_I_H + +#include + +#include "datatypes/heartrate.h" +#include "abstractsensor_i.h" + +/** + * Client interface for accessing heart rate monitor sensor. + * Provides signal on change of bpm of hrm status. + * Previous measured heart rate can be queried any time. Provided + * values are in \e heartRate. + */ +class HrmSensorChannelInterface : public AbstractSensorChannelInterface +{ + Q_OBJECT + Q_DISABLE_COPY(HrmSensorChannelInterface) + Q_PROPERTY(HeartRate heartRate READ heartRate) + +public: + /** + * Name of the D-Bus interface for this class. + */ + static const char* staticInterfaceName; + + /** + * Create new instance of the class. + * + * @param id Sensor ID. + * @param sessionId Session ID. + * @return Pointer to new instance of the class. + */ + static AbstractSensorChannelInterface* factoryMethod(const QString& id, int sessionId); + + /** + * Get latest heart rate measurements from sensor daemon. + * + * @return current bpm and hrm status. + */ + HeartRate heartRate(); + + /** + * Constructor. + * + * @param path path. + * @param sessionId session ID. + */ + HrmSensorChannelInterface(const QString& path, int sessionId); + + /** + * Request a listening interface to the sensor. + * + * @param id sensor ID. + * @return Pointer to interface, or NULL on failure. + * @deprecated use interface(const QString&) instead. + */ + static const HrmSensorChannelInterface* listenInterface(const QString& id); + + /** + * Request a control interface to the sensor. + * + * @param id sensor ID. + * @return Pointer to interface, or NULL on failure. + * @deprecated use interface(const QString&) instead. + */ + static HrmSensorChannelInterface* controlInterface(const QString& id); + + /** + * Request an interface to the sensor. + * + * @param id sensor ID. + * @return Pointer to interface, or NULL on failure. + */ + static HrmSensorChannelInterface* interface(const QString& id); + +protected: + virtual bool dataReceivedImpl(); + +Q_SIGNALS: + /** + * Sent when measured bpm has changed. + * + * @param value bpm reading. + */ + void HeartRateChanged(const HeartRate& value); +}; + +namespace local { + typedef ::HrmSensorChannelInterface HrmSensor; +} + +#endif diff --git a/qt-api/qt-api.pro b/qt-api/qt-api.pro index 1fa3d7d..be248ae 100644 --- a/qt-api/qt-api.pro +++ b/qt-api/qt-api.pro @@ -22,7 +22,8 @@ SOURCES += sensormanagerinterface.cpp \ humiditysensor_i.cpp \ pressuresensor_i.cpp \ temperaturesensor_i.cpp \ - stepcountersensor_i.cpp + stepcountersensor_i.cpp \ + hrmsensor_i.cpp HEADERS += sensormanagerinterface.h \ sensormanager_i.h \ @@ -41,7 +42,8 @@ HEADERS += sensormanagerinterface.h \ humiditysensor_i.h \ pressuresensor_i.h \ temperaturesensor_i.h \ - stepcountersensor_i.h + stepcountersensor_i.h \ + hrmsensor_i.h SENSORFW_INCLUDEPATHS = .. \ ../include \ diff --git a/sensors/hrmsensor/hrmplugin.cpp b/sensors/hrmsensor/hrmplugin.cpp new file mode 100644 index 0000000..595c739 --- /dev/null +++ b/sensors/hrmsensor/hrmplugin.cpp @@ -0,0 +1,49 @@ +/** + @file hrmplugin.cpp + @brief Plugin for heart rate monitor sensor + +

+ Copyright (C) 2009-2010 Nokia Corporation + Copyright (C) 2019 Florent Revest + + @author Kimmo Lindholm + @author Timo Rongas + @author Ustun Ergenoglu + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#include "hrmplugin.h" +#include "hrmsensor.h" +#include "sensormanager.h" +#include "logging.h" + +void HrmPlugin::Register(class Loader&) +{ + sensordLogD() << "registering hrmsensor"; + SensorManager& sm = SensorManager::instance(); + sm.registerSensor("hrmsensor"); +} + +void HrmPlugin::Init(class Loader& l) +{ + Q_UNUSED(l); + SensorManager::instance().requestSensor("hrmsensor"); +} + +QStringList HrmPlugin::Dependencies() { + return QString("hrmadaptor").split(":", QString::SkipEmptyParts); +} diff --git a/sensors/hrmsensor/hrmplugin.h b/sensors/hrmsensor/hrmplugin.h new file mode 100644 index 0000000..f7fe9d8 --- /dev/null +++ b/sensors/hrmsensor/hrmplugin.h @@ -0,0 +1,43 @@ +/** + @file hrmplugin.h + @brief Plugin for heart rate monitor sensor + +

+ Copyright (C) 2009-2010 Nokia Corporation + Copyright (C) 2019 Florent Revest + + @author Kimmo Lindholm + @author Timo Rongas + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#ifndef HRMPLUGIN_H +#define HRMPLUGIN_H + +#include "plugin.h" + +class HrmPlugin : public Plugin +{ + Q_OBJECT + Q_PLUGIN_METADATA(IID "com.nokia.SensorService.Plugin/1.0") +private: + void Register(class Loader& l); + void Init(class Loader& l); + QStringList Dependencies(); +}; + +#endif diff --git a/sensors/hrmsensor/hrmsensor.cpp b/sensors/hrmsensor/hrmsensor.cpp new file mode 100644 index 0000000..3c10db9 --- /dev/null +++ b/sensors/hrmsensor/hrmsensor.cpp @@ -0,0 +1,123 @@ +/** + @file hrmsensor.cpp + @brief heart rate monitor sensor + +

+ Copyright (C) 2009-2010 Nokia Corporation + Copyright (C) 2019 Florent Revest + + @author Kimmo Lindholm + @author Timo Rongas + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#include "hrmsensor.h" + +#include "sensormanager.h" +#include "bin.h" +#include "bufferreader.h" +#include "datatypes/orientation.h" + +HrmSensorChannel::HrmSensorChannel(const QString& id) : + AbstractSensorChannel(id), + DataEmitter(1) +{ + SensorManager& sm = SensorManager::instance(); + + hrmAdaptor_ = sm.requestDeviceAdaptor("hrmadaptor"); + if (!hrmAdaptor_) { + setValid(false); + return; + } + + hrmReader_ = new BufferReader(1); + + outputBuffer_ = new RingBuffer(1); + + // Create buffers for filter chain + filterBin_ = new Bin; + + filterBin_->add(hrmReader_, "hrm"); + filterBin_->add(outputBuffer_, "buffer"); + + filterBin_->join("hrm", "source", "buffer", "sink"); + + // Join datasources to the chain + connectToSource(hrmAdaptor_, "hrm", hrmReader_); + + marshallingBin_ = new Bin; + marshallingBin_->add(this, "sensorchannel"); + + outputBuffer_->join(this); + + setDescription("beats per minute"); + setRangeSource(hrmAdaptor_); + addStandbyOverrideSource(hrmAdaptor_); + setIntervalSource(hrmAdaptor_); + + setValid(true); +} + +HrmSensorChannel::~HrmSensorChannel() +{ + if (isValid()) { + SensorManager& sm = SensorManager::instance(); + + disconnectFromSource(hrmAdaptor_, "hrm", hrmReader_); + + sm.releaseDeviceAdaptor("hrmadaptor"); + + delete hrmReader_; + delete outputBuffer_; + delete marshallingBin_; + delete filterBin_; + } +} + +bool HrmSensorChannel::start() +{ + sensordLogD() << "Starting HrmSensorChannel"; + + if (AbstractSensorChannel::start()) { + marshallingBin_->start(); + filterBin_->start(); + hrmAdaptor_->startSensor(); + } + return true; +} + +bool HrmSensorChannel::stop() +{ + sensordLogD() << "Stopping HrmSensorChannel"; + + if (AbstractSensorChannel::stop()) { + hrmAdaptor_->stopSensor(); + filterBin_->stop(); + marshallingBin_->stop(); + } + return true; +} + +void HrmSensorChannel::emitData(const HeartRateData& value) +{ + if (value.bpm_ != previousValue_.bpm_ || value.status_ != previousValue_.status_) { + previousValue_.bpm_ = value.bpm_; + previousValue_.status_ = value.status_; + + writeToClients((const void*)(&value), sizeof(value)); + } +} diff --git a/sensors/hrmsensor/hrmsensor.h b/sensors/hrmsensor/hrmsensor.h new file mode 100644 index 0000000..e2c7c30 --- /dev/null +++ b/sensors/hrmsensor/hrmsensor.h @@ -0,0 +1,101 @@ +/** + @file hrmsensor.h + @brief heart rate monitor sensor + +

+ Copyright (C) 2009-2010 Nokia Corporation + Copyright (C) 2019 Florent Revest + + @author Kimmo Lindholm + @author Timo Rongas + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#ifndef HRM_SENSOR_CHANNEL_H +#define HRM_SENSOR_CHANNEL_H + +#include + +#include "deviceadaptor.h" +#include "abstractsensor.h" +#include "hrmsensor_a.h" +#include "dataemitter.h" +#include "datatypes/heartratedata.h" +#include "datatypes/heartrate.h" + +class Bin; +template class BufferReader; +class FilterBase; + +/** + * @brief Sensor for accessing the internal heart rate monitor sensor measurements. + * + * Signals listeners whenever observed bpm changed. + */ +class HrmSensorChannel : + public AbstractSensorChannel, + public DataEmitter +{ + Q_OBJECT; + Q_PROPERTY(HeartRate heartRate READ heartRate); + +public: + /** + * Factory method for HrmSensorChannel. + * @return New HrmSensorChannel as AbstractSensorChannel* + */ + static AbstractSensorChannel* factoryMethod(const QString& id) + { + HrmSensorChannel* sc = new HrmSensorChannel(id); + new HrmSensorChannelAdaptor(sc); + + return sc; + } + + /** + * Property for accessing the measured value. + * @return Last measured value. + */ + HeartRate heartRate() const { return previousValue_; } + +public Q_SLOTS: + bool start(); + bool stop(); + +signals: + /** + * Sent when a change in measured data is observed. + * @param value Measured value. + */ + void HeartRateChanged(const HeartRate& value); + +protected: + HrmSensorChannel(const QString& id); + virtual ~HrmSensorChannel(); + +private: + HeartRateData previousValue_; + Bin* filterBin_; + Bin* marshallingBin_; + DeviceAdaptor* hrmAdaptor_; + BufferReader* hrmReader_; + RingBuffer* outputBuffer_; + + void emitData(const HeartRateData& value); +}; + +#endif // HRM_SENSOR_CHANNEL_H diff --git a/sensors/hrmsensor/hrmsensor.pro b/sensors/hrmsensor/hrmsensor.pro new file mode 100644 index 0000000..6becd8f --- /dev/null +++ b/sensors/hrmsensor/hrmsensor.pro @@ -0,0 +1,19 @@ +CONFIG += link_pkgconfig + +TARGET = hrmsensor + +HEADERS += hrmsensor.h \ + hrmsensor_a.h \ + hrmplugin.h + +SOURCES += hrmsensor.cpp \ + hrmsensor_a.cpp \ + hrmplugin.cpp + +include( ../sensor-config.pri ) + +contextprovider { + DEFINES += PROVIDE_CONTEXT_INFO + PKGCONFIG += contextprovider-1.0 +} + diff --git a/sensors/hrmsensor/hrmsensor_a.cpp b/sensors/hrmsensor/hrmsensor_a.cpp new file mode 100644 index 0000000..3776fcb --- /dev/null +++ b/sensors/hrmsensor/hrmsensor_a.cpp @@ -0,0 +1,38 @@ +/** + @file hrmsensor_a.cpp + @brief D-Bus adaptor for heart rate monitor sensor + +

+ Copyright (C) 2009-2010 Nokia Corporation + Copyright (C) 2019 Florent Revest + + @author Kimmo Lindholm + @author Timo Rongas + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#include "hrmsensor_a.h" + +HrmSensorChannelAdaptor::HrmSensorChannelAdaptor(QObject* parent) : + AbstractSensorChannelAdaptor(parent) +{ +} + +HeartRate HrmSensorChannelAdaptor::heartRate() const +{ + return qvariant_cast(parent()->property("heartRate")); +} diff --git a/sensors/hrmsensor/hrmsensor_a.h b/sensors/hrmsensor/hrmsensor_a.h new file mode 100644 index 0000000..598c4f0 --- /dev/null +++ b/sensors/hrmsensor/hrmsensor_a.h @@ -0,0 +1,55 @@ +/** + @file hrmsensor_a.h + @brief D-Bus adaptor for heart rate monitor sensor + +

+ Copyright (C) 2009-2010 Nokia Corporation + Copyright (C) 2019 Florent Revest + + @author Kimmo Lindholm + @author Timo Rongas + @author Antti Virtanen + + This file is part of Sensord. + + Sensord is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License + version 2.1 as published by the Free Software Foundation. + + Sensord 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 Sensord. If not, see . +

+ */ + +#ifndef HRM_SENSOR_H +#define HRM_SENSOR_H + +#include +#include + +#include "datatypes/heartrate.h" +#include "abstractsensor_a.h" + +class HrmSensorChannelAdaptor : public AbstractSensorChannelAdaptor +{ + Q_OBJECT + Q_DISABLE_COPY(HrmSensorChannelAdaptor) + Q_CLASSINFO("D-Bus Interface", "local.HrmSensor") + Q_PROPERTY(HeartRate heartRate READ heartRate) + +public: + HrmSensorChannelAdaptor(QObject* parent); + +public Q_SLOTS: + HeartRate heartRate() const; + +Q_SIGNALS: + void HeartRateChanged(const HeartRate& value); +}; + +#endif diff --git a/sensors/sensors.pro b/sensors/sensors.pro index 6afdb7d..286fecf 100644 --- a/sensors/sensors.pro +++ b/sensors/sensors.pro @@ -16,6 +16,7 @@ SUBDIRS = accelerometersensor \ humiditysensor \ pressuresensor \ temperaturesensor \ - stepcountersensor + stepcountersensor \ + hrmsensor contextprovider:SUBDIRS += contextplugin -- 2.34.1