Version 3.1.0

Tepovka: Heart activity analysis using photoplethysmography

Research project from BUT in Brno. App for measuring HR and HRV by extracting the optical signal from a phone camera. Processing happens 100% locally without sending data to the cloud. Current version: 3.1.0.

About the project

Tepovka started in autumn 2024 in the FEKTeams competition at FEKT BUT. The goal is practical measurement of HR and HRV using PPG on standard phones, openly and clearly.

We involve students in development, share procedures, and design algorithms that can be further verified in the lab and in the field. The project is supported by the Department of Biomedical Engineering (DBME).

Context

The project is developed and tested at UBMI, FEKT BUT. It serves as a training and research framework for rPPG/HRV with links to academic resources, labs, and internal methodologies.

How Tepovka works

Adaptive photoplethysmography

We use a noninvasive method for measuring blood volume changes. The algorithm primarily analyzes the green channel from the phone camera but switches to red when the signal is weak for reliability.

Hybrid computation and HRV

The system combines time-domain analysis and FFT. In real time it calculates selected parameters of heart rate variability (HRV): SDNN, RMSSD, pNN50, SD1, and SD2. The metrics provide insight into the autonomic nervous system.

Breathing and heart rate recovery

From the signal envelope the algorithm extracts breathing frequency. It also analyzes heart rate recovery (HR Recovery Rate) to estimate how the cardiovascular system settles after exertion.

Direction

We build on current HR/HRV measurement and gradually add metrics and ways to share them.

  • New parameters: blood oxygen saturation (SpO2) — currently being calibrated against a pulse oximeter — and deeper analysis of the PPG waveform.
  • Secure data sharing: Preparation for remote consultations with specialists.
  • Accessibility: High-contrast mode, larger type, and voice guidance.

AI plan

Collected data will feed machine learning models: early detection of arrhythmias, atypical HRV trends, and anomalies in PPG waveform shape. We are building training data for artifact rejection and load profiles so we can flag risks even in suboptimal measurement conditions.

Goal: timely, plain-language alerts about possible deviations without overpromising.

Validated by measurement

We validated the accuracy against ECG

Most apps that measure heart rate from a camera have no validation — or do not show it. In August 2026 we measured 15 volunteers with a Bittium Faros 180 ECG holter and a Nonin pulse oximeter running at the same time as the phone. That produced 61 simultaneous recordings, so the accuracy can be backed by a number rather than a claim.

1.25 bpm

Mean deviation from ECG
Across 57 recordings with a good reference.

93%

Recordings within 5 bpm
Difference from ECG below five beats per minute.

0.98

Agreement (ICC)
Pearson r = 0.985.

How the measurement was run

Every participant wore the ECG holter on the chest and the pulse oximeter on one hand, and measured with the phone using the other. The protocol was identical for everyone: three thirty-second recordings at rest and one ninety-second recording after exertion, so the data would also cover elevated heart rates. The measured range is 51–112 bpm and participants were 20 to 47 years old.

Chart: heart rate from the phone, the ECG holter and the pulse oximeter during one session
One full session. The phone (blue dots) tracks both the ECG and the oximeter at rest and during the post-exertion phase, where the heart rate rises and falls quickly.

Beat by beat

Accuracy is not about the average over a whole recording but about whether the app finds every single beat. The excerpt below shows the ECG with detected R waves on top and the phone camera signal with detected pulses underneath — one to one. Across the whole data set the detector finds 99% of real beats.

Chart: eight-second excerpt of ECG with R waves and phone PPG with detected pulses
Eight seconds of a simultaneous measurement. The excerpt is picked automatically by signal quality, not by hand.

How large the deviations are

The chart below shows the difference between the phone and the ECG for each recording. The mean deviation is +0.2 bpm and the vast majority of recordings fall inside the ±5 bpm band. For context: on the same data the ECG holter and the pulse oximeter agreed with each other to within 2.0 bpm — the app therefore sits inside the spread of two certified devices.

Bland-Altman chart: difference between phone and ECG heart rate across 57 recordings
Each dot is one recording. The horizontal axis is the mean of both methods, the vertical one their difference.

What the measurement also revealed

The simultaneous data exposed two processing bugs we would not have spotted otherwise: the exported time base ran a quarter too fast and the detector missed every fifth beat. Both are fixed and new measurements confirmed it. We mention it deliberately — validation earns its keep precisely by finding errors, and the figures above apply to the fixed version.

Limitations we are aware of: the cohort is small and consists of healthy adults, accuracy depends on signal quality (which is why a quality rating is stored with every recording), and heart rate variability parameters should be treated as indicative only. The app is not a medical device.

Methodology and signal processing

Technology stack

  • User interface: Flutter / Dart (voice feedback via flutter_tts)
  • Signal processing: custom Dart implementation (~12,700 lines); analysis runs in a separate isolate, off the UI thread
  • Filtering: Butterworth biquads, zero-phase filtering for retrospective analysis, adaptive motion suppression using the accelerometer
  • Frequency analysis: FFT (library fftea) and autocorrelation
  • Time base: the camera frame rate is measured and stored with every recording instead of being assumed

Extracted metrics

  • Basic vital signs: Heart rate (40–200 BPM), breathing rate (6–30 breaths/min)
  • HRV time domain: SDNN, RMSSD, pNN50
  • HRV nonlinear domain: SD1, SD2 (Poincare plot)
  • Signal quality: an index based on spectral purity and periodicity, for each recording and each segment

Treat HRV parameters as indicative: at smartphone frame rates the interbeat interval is quantised more coarsely than with ECG, which shows up mainly in RMSSD and pNN50.

In research mode you fill in the recording details before measuring (subject ID, protocol, note — the fields are configurable) and can export to TXT, CSV or JSON. The file carries the processed signal plus the unfiltered colour channels from the camera, the measured frame rate, the quality rating and the positions of pulse peaks and onsets. Measurements can also be synced via Apple HealthKit. All processing stays on device.

Development plan (Roadmap)

v3.1.0 (Current version)

Research mode with metadata and TXT/CSV/JSON export, measured instead of assumed frame rate, unified pulse detection timed from pulse onsets, signal quality rating, HealthKit integration, senior mode, 33 automated tests.

v3.2.0 (Planned Q2 2026)

Extended validation on a larger cohort, advanced trend analysis and Wear OS integration.

v4.0.0 (Planned Q4 2026)

Machine learning to optimize peak detection, optional web dashboard for batch analysis.

Live demo

Tepovka right in your browser

What you see on the right is the real app, not a screenshot. A browser cannot see a finger on the lens, so a prerecorded video stands in for the camera — the signal then goes through exactly the same processing as on the phone.

The app is available for iPhone — download it on the App Store.

Development team

We are biomedical engineering students working together to advance mobile health and share experience with other science enthusiasts. The project is led by mentors Ing. Jan Šíma and Ing. Andrea Němcová, PhD. and we are gradually adding new members.