Arduino Based Pulse Oximeter Health Monitoring

Hello guys, today in this tutorial we have MAX30100 pulse oximeter sensor. We will pair this sensor with our Arduino and check the operation. This will be a simple project and you will get the circuit diagram and code here below.

In these types of sketches most of the work is done by libraries itself, we just have to initialize the code, libraries and functions. You can make your own PCB as a watch or something like commercially available in market. Through this we can measure BPM and SPO2 levels. Then we will design a PCB and order it from JLCPCB ( just $2 for 5 pcs).

Pulse oximeter:

A non-invasive medical device that utilizes spectrophotometry to measure the oxygen saturation of circulating arterial blood in an individual by determining the percentage of oxygenated haemoglobin pulsating through a network of blood capillaries by way of a sensor attached typically to a finger. This sensor used to measure BPM( Heart beat per minute) and Spo2(Oxygen level in blood).

A normal level of oxygen is usually 95% or higher. Some people with chronic lung disease or sleep apnoea can have normal levels around 90%. The “SpO2” reading on a pulse oximeter shows the percentage of oxygen in someone’s blood. If your home SpO2 reading is lower than 95%, call your health care provider.

Difference Between BP and BPM:

The heart rate records the number of times that your heart beats per minute (BPM) , while your blood pressure quantifies how strong your blood moves through the blood vessels (BP).

Pulse Oximeter sensor:

MAX30100 is an integrated pulse oximeter and heart-rate monitor sensor solution. It’s an optical sensor that derives its readings from emitting two wavelengths of light from two LEDs – a red and an infrared one – then measuring the absorbance of pulsing blood through a photodetector.

This particular LED color combination is optimized for reading the data through the tip of one’s finger. It is fully configurable through software registers and the digital output data is stored in a 16-deep FIFO within the device. It has an I2C digital interface to communicate with a host microcontroller.Features:

  • Measures absorbance of pulsing blood
  • I2C interface plus INT pin
  • Tiny 5.6mm x 2.8mm x 1.2mm 14-Pin Optically Enhanced System-in-Package
  • Ultra-Low-Power Operation Increases Battery Life for Wearable Devices
  • Programmable Sample Rate and LED Current for Power Savings
  • Ultra-Low Shutdown Current (0.7µA, typically)
  • Advanced Functionality Improves Measurement Performance
  • High SNR Provides Robust Motion Artifact Resilience
  • Integrated Ambient Light Cancellation
  • High Sample Rate Capability
  • Fast Data Output Capability

Components required:

1) Arduino UNO2) 16X2 LCD (With I2C adapter)3) MAX30100 sensor4) Wires and breadboard5) Custom PCB

Circuit diagram:

Both the LCD and sensor use I2C communications, so we can connect both of them to same A5 (SCL) and A4 (SDA) pin. Arduino uno i2c have 7 bit addresses so we can use 127 devices in parallel. To power up the sensor and lcd we can give +5v. And rest of the work is done by the microcontroller itself. Download Circuit diagram, code and Gerber files from here.

PCB designs:

I want to minimize this DIY design, so here in the PCB I am using Arduino Nano MCU, 16*2 LCD, MAX30100 with charging circuit.

This is tested schematics, but the LCD only work on I2C port. Pins are just for understanding purpose. If you want to use same design as mine then Download the Gerber files from here. JLCPCB offering a very good service (just $2 for 5 Pcs).

And if you Sign-up using my link, you will get reward coupons of worth $27 and some SMT assembly/ PCB prototype coupons on each successful order.

Code:

Download Libraries used in this code from here.


#include <LiquidCrystal_I2C.h>
#include <Wire.h>
#include "MAX30100_PulseOximeter.h"

#define REPORTING_PERIOD_MS     1000

LiquidCrystal_I2C lcd(0x27, 16, 2);

byte smile[] = {
  B00000,
  B00000,
  B01010,
  B00000,
  B10001,
  B01110,
  B00000,
  B00000
};
byte mod[] = {
  B00000,
  B00000,
  B01010,
  B00000,
  B11111,
  B00000,
  B00000,
  B00000
};
byte sad[] = {
  B00000,
  B00000,
  B01010,
  B00000,
  B01110,
  B10001,
  B00000,
  B00000
};

PulseOximeter pox;
uint32_t tsLastReport = 0;

void onBeatDetected()
{

  Serial.println("Beat!!!");

}

void setup()
{
  Serial.begin(115200);
  lcd.begin();
  lcd.backlight();
  lcd.createChar(1 , smile);
  lcd.createChar(2 , mod);
  lcd.createChar(3 , sad);
  lcd.setCursor(0, 0);
  lcd.print("      Pluse");
  lcd.setCursor(0, 1);
  lcd.print("    Oximeter");
  delay(2000);

  if (!pox.begin()) {
    Serial.println("FAILED");
    for (;;);
  } else {
    Serial.println("SUCCESS");
  }
  pox.setIRLedCurrent(MAX30100_LED_CURR_7_6MA);

  pox.setOnBeatDetectedCallback(onBeatDetected);
}

void loop()
{
  pox.update();
  if (millis() - tsLastReport > REPORTING_PERIOD_MS) {

    lcd.clear();
    lcd.setCursor(0 , 0);
    lcd.print("BPM : ");
    lcd.print(pox.getHeartRate());
    lcd.setCursor(0 , 1);
    lcd.print("Sp02: ");
    lcd.print(pox.getSpO2());
    lcd.print("%");
    tsLastReport = millis();

    if (pox.getSpO2() >= 96) {
      lcd.setCursor(15 , 1);
      lcd.write(1);                 
    }
    else if (pox.getSpO2() <= 95 && pox.getSpO2() >= 91) {
      lcd.setCursor(15 , 1);
      lcd.write(2);                 
    }
    else if (pox.getSpO2() <= 90) {
      lcd.setCursor(15 , 1);
      lcd.write(3);
    }
  }
} 

Measurements:

With health monitoring this code also have some symbolic representation on screen which is with smile face, rough and normal face (emoji).

Measuring BPM and oxygen level is too simple, just place your finder gently on the Max30100 sensor. It will automatically start the system.

You will get a full accurate reading after 10 seconds and its done.

You can also use prototype PCB Gerber file to make this project more practical, with inbuild power supply and a compact size. By the way, A big thanks to JLCPCB to sponsor this project.

Similar Posts

Leave a Reply

Your email address will not be published. Required fields are marked *