Back to All Blog Posts
Tutorial EltroNerd Engineering

Blood Pressure and Heart Monitoring

A portable system to measure Blood Pressure (BP) and Heart Rate (HR).

Blood Pressure + Heart Monitoring Kit

Overview

This project builds a Blood Pressure (BP) + Heart Rate (HR) monitoring kit using:

  • Oscillometric cuff-based BP measurement with a pressure sensor.
  • PPG/ECG sensor (MAX30102 or AD8232) for heart rate.
  • ESP32 for control, display, and IoT.

⚠️ Disclaimer: This is a prototype for learning. Not medical-grade. Validate against a certified BP monitor.


Components

  • ESP32 dev board
  • Inflatable cuff + air pump + solenoid valve
  • Pressure sensor (0–300 mmHg, e.g., MPX series)
  • MAX30102 (PPG) or AD8232 (ECG)
  • OLED (SSD1306, I²C)
  • MOSFETs, diodes, wires, battery

Wiring (High-level)

  • Pressure sensor → ESP32 ADC (e.g., GPIO34)
  • Pump → MOSFET driver (GPIO26)
  • Valve → MOSFET driver (GPIO25)
  • MAX30102 → I²C (SDA GPIO21, SCL GPIO22)
  • OLED → I²C (shared bus)
  • All grounds connected

System Flow

  1. Inflate cuff to ~160 mmHg
  2. Deflate slowly (~2–3 mmHg/sec)
  3. Measure oscillations in cuff pressure
  4. Extract envelope → MAP → estimate systolic/diastolic
  5. Measure HR from MAX30102/ECG
  6. Display values on OLED + send via MQTT

Example Firmware (ESP32 + OLED + Pressure Sensor)

c
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>

#define SCREEN_WIDTH 128
#define SCREEN_HEIGHT 64
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, -1);

// Pins
const int PRESSURE_PIN = 34;   // ADC pin for pressure sensor
const int VALVE_PIN = 25;      // Solenoid valve control
const int PUMP_PIN = 26;       // Pump control

// Variables
float pressure_mmHg = 0;
int bpm = 0;  // placeholder for HR (replace with MAX30102/ECG code)

// Convert raw ADC to mmHg (example calibration, adjust for your sensor)
float readPressure_mmHg() {
  int raw = analogRead(PRESSURE_PIN);
  float voltage = (raw / 4095.0) * 3.3;
  float mmHg = (voltage / 3.0) * 300.0; // scale depends on sensor
  return mmHg;
}

void setup() {
  Serial.begin(115200);
  pinMode(PUMP_PIN, OUTPUT);
  pinMode(VALVE_PIN, OUTPUT);

  if(!display.begin(SSD1306_SWITCHCAPVCC, 0x3C)) {
    Serial.println("OLED init failed");
    while(1);
  }
  display.clearDisplay();
  display.setTextSize(1);
  display.setTextColor(SSD1306_WHITE);
  display.setCursor(0,0);
  display.println("BP Monitor Init...");
  display.display();
}

void loop() {
  // Step 1: Inflate cuff
  digitalWrite(PUMP_PIN, HIGH);
  while (pressure_mmHg < 160) {
    pressure_mmHg = readPressure_mmHg();
    Serial.print("Inflating: "); Serial.println(pressure_mmHg);
  }
  digitalWrite(PUMP_PIN, LOW);

  // Step 2: Controlled deflation
  while (pressure_mmHg > 40) {
    pressure_mmHg = readPressure_mmHg();
    Serial.print("Deflating: "); Serial.println(pressure_mmHg);

    // Fake BPM (replace with MAX30102/ECG code)
    bpm = 72;

    // Display on OLED
    display.clearDisplay();
    display.setCursor(0,0);
    display.println("Blood Pressure Kit");
    display.print("Pressure: ");
    display.println(pressure_mmHg, 1);
    display.print("BPM: ");
    display.println(bpm);
    display.display();

    delay(200);
  }

  // Step 3: Vent cuff fully
  digitalWrite(VALVE_PIN, HIGH);
  delay(1000);
  digitalWrite(VALVE_PIN, LOW);

  delay(5000); // Pause before next cycle
}

Try this project in your browser

Compile code and simulate hardware output with EltroNerd Cloud IDE.

Launch Cloud IDE