forked from CoolDude937/ECG
-
Notifications
You must be signed in to change notification settings - Fork 0
/
heartbeat.ino
103 lines (82 loc) · 2.23 KB
/
heartbeat.ino
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
#include "Arduino.h"
#include "stdlib.h"
#include "stdio.h"
//Using built in LED pin for demo
#define ledPin 13
// Pulse meter connected to any Analog pin
#define sensorPin A0
int arr_bpm[10];
float alpha = 0.75;
int period = 50;
float max = 0.0;
void setup() {
// Inbuilt LED
pinMode(ledPin, OUTPUT);
for (int j = 0; j < 10; j++)
{
arr_bpm[j] = 0;
}
Serial.begin(9600);
}
void loop() {
// to find value between current and old
static float oldValue = 400;
//trying to average the bpm each iteration
float averager = 1;
int index;
// Time recording for BPM (beats per minute)
static unsigned long bpmMills = millis();
static int bpm = 0;
static float avg_bpm = 0;
// to minimize bad input
static unsigned long timeBetweenBeats = millis();
int minDelayBetweenBeats = 700;
// Read the sensor value (0 - 1023)
int rawValue = analogRead((unsigned char)sensorPin);
// Some maths (USA: math) to determine whether we are detected a peak (pulse)
float value = alpha * oldValue + (1 - alpha) * rawValue;
float change = value - oldValue;
oldValue = value;
// if we find a new maximum value AND we haven't had a pulse lately
if ((change >= max) && (millis() > timeBetweenBeats + minDelayBetweenBeats)) {
// Flash LED
digitalWrite(ledPin, 1);
tone(3, 2500, 50);
// Reset max every time we find a new peak
max = change;
// Reset the heart beat time values
timeBetweenBeats = millis();
bpm++;
} else {
// No pulse detected, ensure LED is off (may be off already)
digitalWrite(ledPin, 0);
}
// Slowly decay max for when sensor is moved around
// but decay must be slower than time needed to hit
// next pulse peak. Originally: 0.98
max = max * 0.97;
if(bpm != 0)
{
if (index == 10)
index = 0;
if (averager >= 10)
averager = 10;
arr_bpm[index] = bpm;
for (int i = 0; i < 10; i++)
{
avg_bpm += arr_bpm[i];
}
avg_bpm = avg_bpm / averager;
averager++;
index++;
}
// Every 4 seconds extrapolate the pulse rate.
if (millis() >= bpmMills + 4000) {
Serial.println(avg_bpm * 15);
bpm = 0;
bpmMills = millis();
}
avg_bpm = 0;
// Must delay here to give the value a chance to decay
delay(period);
}