Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: PulseSensor GSM Thermometer KalmanFilter
Revision 25:8621ebb6ea0c, committed 2018-06-23
- Comitter:
- DuyLionTran
- Date:
- Sat Jun 23 18:12:35 2018 +0000
- Parent:
- 24:bee84b48322a
- Commit message:
- * version 1.4.4 23-06-2018 Added max30100 still developing
Changed in this revision
--- a/Application/ble_healthcare_service.h Mon Jun 18 07:38:54 2018 +0000
+++ b/Application/ble_healthcare_service.h Sat Jun 23 18:12:35 2018 +0000
@@ -265,11 +265,9 @@
HeartRateValueBytes hrmValueByte;
ReadOnlyGattCharacteristic<TemperatureValueBytes> tempMeasurement;
-// ReadOnlyGattCharacteristic<uint8_t> tempLocation;
ReadWriteGattCharacteristic<uint8_t> tempLocation;
GattCharacteristic hrmRate;
-// ReadOnlyGattCharacteristic<uint8_t> hrmLocation;
ReadWriteGattCharacteristic<uint8_t> hrmLocation;
ReadWriteGattCharacteristic<uint8_t> controlState;
--- a/Application/main.cpp Mon Jun 18 07:38:54 2018 +0000
+++ b/Application/main.cpp Sat Jun 23 18:12:35 2018 +0000
@@ -12,15 +12,16 @@
* version 1.0 03-09-2018 Some minor bugs fixed
* version 1.0.5 03-09-2018 Some minor bugs fixed
* version 1.3.7 04-06-2018 Some minor bugs fixed
+ * version 1.4.4 23-06-2018 Added max30100 still developing
/* ======================== INCLUDES ========================= */
#include <events/mbed_events.h>
#include <mbed.h>
#include "ble/BLE.h"
#include "ble_healthcare_service.h"
-#include "GSM.h"
#include "LM35.h"
#include "PulseSensor.h"
+#include "MAX30100_PulseOximeter.h"
#include "KalmanFilterPulse.h"
/* ======================== DEFINES ========================== */
@@ -30,12 +31,26 @@
#define START_SEND_INT_TEMP 13
#define START_SEND_FLOAT_TEMP 10
#define STOP_SEND_TEMP 20
+
+#define SAMPLE_HEARTRATE 16
+#define AVERAGE_HEARTRATE 8
+#define REPORTING_PERIOS 3125 /* 1/16 s */
+
/* ======================= VARIABLES ========================= */
/* GLOBAL VARIABLES */
-static float currentTemperature = 36.9;
-static uint16_t currentHRMCounter;
+static float processedTemperature = 36.9;
+static uint16_t processedHRMCounter;
static float sendCombinedTempAndHR;
static uint16_t sendCombinedHRAndTemp;
+
+bool isEmptyavgHR = true;
+bool startCalculatingStandardDeviation = true;
+std::vector<float> valuesHeartRate;
+std::vector<uint8_t> valuesSpO2;
+
+uint8_t avgHRIndex = 0;
+float avgHR[AVERAGE_HEARTRATE] = {0};
+uint16_t avgHeartRate;
/* PRIVATE VARIABLES */
uint8_t cnt;
@@ -57,9 +72,20 @@
uint8_t hrmPosition = HealthCareService::HealthCareService::HRM_LOCATION_FINGER;
/* STRUCTS/CLASSESS */
+typedef struct {
+ float heartRate;
+ float SpO2;
+} message_t;
+
HealthCareService *HealthCareServicePtr;
+
+MemoryPool<message_t, 32> mpool;
+Queue<message_t, 32> queue;
+
+Thread thread;
+PulseOximeter pox;
-static EventQueue eventQueue(EVENTS_EVENT_SIZE * 20);
+static EventQueue eventQueue(EVENTS_EVENT_SIZE * 32);
Serial serial(USBTX, USBRX);
KalmanFilterPulse kalman(0.5, 10, 1);
KalmanFilterPulse kalman1(2, 10, 0.1);
@@ -72,12 +98,14 @@
void scheduleBleEventsProcessing(BLE::OnEventsToProcessCallbackContext* context);
void sendDataToProcessing(char symbol, int data);
+void onBeatDetected();
+void beatEvent();
void updatePayload(void);
void main_event(void);
void periodicCallback(void);
-PulseSensor sensor(PULSE_SENSOR_PIN, sendDataToProcessing, 10);
-LM35Therm lm35(THERM_SENSOR_PIN, 7.15);
+PulseSensor sensor(PULSE_SENSOR_PIN, sendDataToProcessing, 20);
+LM35Therm lm35(THERM_SENSOR_PIN, 4.56);
/* ==================== FUNCTION DETAILS ===================== */
/* Restart Advertising on disconnection */
@@ -95,7 +123,7 @@
{
filtedData = kalman.kalmanUpdate(data);
filtedData = kalman.kalmanUpdate(filtedData);
- currentHRMCounter = filtedData/1;
+ processedHRMCounter = filtedData/1;
printf("%c%d %d\r\n", symbol, data,(uint8_t)(filtedData/1));
}
}
@@ -134,17 +162,15 @@
/* Do blocking calls or whatever is necessary for sensor polling.
In our case, we simply update the Temperature measurement. */
/* TODO Read temperature */
-// currentTemperature = (currentTemperature + 0.16 > 42.79) ? 35.69 : currentTemperature + 1.18;
lm35.getAverageValue();
- currentTemperature = kalman1.kalmanUpdate(lm35.getTempInC());
- currentTemperature = kalman1.kalmanUpdate(currentTemperature);
+ processedTemperature = kalman1.kalmanUpdate(lm35.getTempInC());
+ processedTemperature = kalman1.kalmanUpdate(processedTemperature);
/* TODO Read Heart Rate */
-// currentHRMCounter = (currentHRMCounter + 1 > 120) ? 75 : (currentHRMCounter + HRM_increasement);
/* Updated in callback function */
/* Some little tricks here to make the temperature decimal and fractional parts different from the send codes */
- intTemperatureValuex100 = currentTemperature * 100;
+ intTemperatureValuex100 = processedTemperature * 100;
fractionalTemperature = intTemperatureValuex100 % 100;
decimalTemperature = intTemperatureValuex100 / 100;
if ((fractionalTemperature == START_SEND_INT_TEMP) ||
@@ -159,28 +185,26 @@
/* TODO Update Service data */
updatePayload();
- /* sendCombinedTempAndHR = (currentTemperature * 100)* 1000 + currentHRMCounter */
- sendCombinedTempAndHR = currentTemperature * 1000; /* Temperature float to int conversion */
- sendCombinedTempAndHR = sendCombinedTempAndHR + (float)(currentHRMCounter/100.0);
-
-
+ /* sendCombinedTempAndHR = (processedTemperature * 100)* 1000 + processedHRMCounter */
+ sendCombinedTempAndHR = intTemperatureValuex100 * 10.0; /* Temperature float to int conversion */
+ sendCombinedTempAndHR = sendCombinedTempAndHR + (float)(processedHRMCounter/100.0);
switch (startSendFloat) {
- case 0: sendCombinedHRAndTemp = currentHRMCounter * 100;
+ case 0: sendCombinedHRAndTemp = processedHRMCounter * 100;
sendCombinedHRAndTemp = sendCombinedHRAndTemp + (uint8_t)START_SEND_INT_TEMP;
break;
- case 1: /* sendCombinedHRAndTemp = (currentHRMCounter * 100) + decimalTemperature */
+ case 1: /* sendCombinedHRAndTemp = (processedHRMCounter * 100) + decimalTemperature */
/* Because the maximum size of HRM Value is 2 bytes */
- sendCombinedHRAndTemp = currentHRMCounter * 100;
+ sendCombinedHRAndTemp = processedHRMCounter * 100;
sendCombinedHRAndTemp = sendCombinedHRAndTemp + (uint8_t)decimalTemperature;
break;
- case 2: sendCombinedHRAndTemp = currentHRMCounter * 100;
+ case 2: sendCombinedHRAndTemp = processedHRMCounter * 100;
sendCombinedHRAndTemp = sendCombinedHRAndTemp + (uint8_t)START_SEND_FLOAT_TEMP;
break;
- case 3: sendCombinedHRAndTemp = currentHRMCounter * 100;
+ case 3: sendCombinedHRAndTemp = processedHRMCounter * 100;
sendCombinedHRAndTemp = sendCombinedHRAndTemp + (uint8_t)fractionalTemperature;
break;
@@ -188,8 +212,8 @@
}
// printf("sendCombinedTempAndHR %d\r\n", sendCombinedTempAndHR);
// printf("sendCombinedTempAndHR %.2f\r\n\r\n", (float)sendCombinedTempAndHR);
-// printf("currentHRMCounter %d\r\n", currentHRMCounter);
-// printf("currentTemperature %d\r\n", (uint8_t)currentTemperature);
+// printf("processedHRMCounter %d\r\n", processedHRMCounter);
+// printf("processedTemperature %d\r\n", (uint8_t)processedTemperature);
// printf("sendCombinedHRAndTemp %d\r\n", sendCombinedHRAndTemp);
if (isConnectedToDevice)
@@ -203,6 +227,68 @@
startSendFloat = 0;
}
}
+
+void beatEvent()
+{
+ float heartRate;
+ float rawHeartRate;
+ uint8_t spO2;
+ uint16_t rawSpO2;
+ uint8_t counterMAX30100 = 0;
+ bool newValueMAX30100 = false;
+ uint32_t loopCount = 0;
+ printf("Thread\r\n");
+ while (1)
+ {
+ pox.update();
+ if (loopCount >= REPORTING_PERIOS)
+ {
+ heartRate = pox.getHeartRate();
+ spO2 = pox.getSpO2();
+
+ if(heartRate != 0 && spO2 != 0)
+ {
+ printf("Heart rate: %f",heartRate);
+ printf(" bpm / SpO2: %d%\r\n", spO2);
+ valuesHeartRate.push_back(heartRate);
+ valuesSpO2.push_back(spO2);
+ counterMAX30100++;
+ }
+ else
+ {
+ printf("No finger\r\n");
+ }
+
+ if(counterMAX30100 == SAMPLE_HEARTRATE) {
+ rawHeartRate = 0;
+ rawSpO2 = 0;
+ for(int i = 0; i < SAMPLE_HEARTRATE; i++){
+ rawHeartRate += valuesHeartRate[i];
+ rawSpO2 += valuesSpO2[i];
+ }
+
+ rawHeartRate /= SAMPLE_HEARTRATE;
+ rawSpO2 /= SAMPLE_HEARTRATE;
+
+ counterMAX30100 = 0;
+ valuesHeartRate.clear();
+ valuesSpO2.clear();
+ newValueMAX30100 = true;
+ }
+ loopCount = 0;
+ }
+ if (newValueMAX30100)
+ {
+ message_t *message = mpool.alloc();
+ message->heartRate = rawHeartRate;
+ message->SpO2 = rawSpO2;
+ printf("Send vales %.2f %.2f \r\n", rawHeartRate, rawSpO2);
+ queue.put(message);
+ newValueMAX30100 = false;
+ }
+ loopCount++;
+ }
+}
void periodicCallback(void)
{
@@ -277,8 +363,8 @@
ble.gap().onDisconnection(&disconnectionCallback);
ble.gattServer().onDataWritten(onDataWrittenCallback);
- HealthCareServicePtr = new HealthCareService(ble, currentTemperature, htsPosition,
- currentHRMCounter, hrmPosition,
+ HealthCareServicePtr = new HealthCareService(ble, processedTemperature, htsPosition,
+ processedHRMCounter, hrmPosition,
initial_HRMIncreasement);
/* setup advertising */
@@ -323,6 +409,17 @@
{
serial.baud(115200);
printf("\r\n BODY WIRELESS SENSOR NETWORK\r\n");
+
+// if(!pox.begin())
+// {
+// printf("No sensor detected\r\n");
+// }
+// else
+// {
+// printf("Sensor found\r\n");
+// }
+// thread.start(callback(beatEvent));
+
/* call periodicCallback every 500ms */
eventQueue.call_every(1000, periodicCallback);
--- a/GSM.lib Mon Jun 18 07:38:54 2018 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1 +0,0 @@ -http://os.mbed.com/teams/components/code/GSM/#24671d8aa0c9
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/MAX30100.lib Sat Jun 23 18:12:35 2018 +0000 @@ -0,0 +1,1 @@ +https://developer.mbed.org/users/AVELARDEV/code/MAX30100/#010b908e2187