Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Are there plans to add millisecond timestamps to the ecg waveform acquisition? This would be of great value in achieving data synchronisation for multi-sensor data. #2

Open
fixernhc opened this issue Nov 22, 2022 · 21 comments

Comments

@fixernhc
Copy link

No description provided.

@stuartlynne
Copy link
Owner

stuartlynne commented Nov 22, 2022 via email

@MedTechCD
Copy link

Stuart, I don't know if or how you will implement breathing frequency but I'm also closely following the work of Inigo Tolosa on the Garmin IQ app AlphaHRV. They have breathing frequency derived from RR intervals. Underneath is a screenshot from my findings using Fitness-ECG alongside the Garmin IQ app. As you say above, the 130hz sampling rate for the Polar is quite accurate and when I plot the ECG in Excel with a time base based on that sampling rate I see something interesting. The screenshot has the ECG from the first and last 60sec of a AeT ramp test. A side-effect of chest strap ECG seems to be that the QRS amplitude changes with chest expansion/breathing. How feasible would it be to implement that?
image

@stuartlynne
Copy link
Owner

stuartlynne commented Dec 15, 2022 via email

@MedTechCD
Copy link

Extracting RespRate from the ECG is surprisingly easy. Here's an example with on top 20sec ECG recorded with your app. At the bottom 1 min with the extracted R-peaks (orange) and in green the chest movement = respiratory trace.
image

Some simple Excel manipulations.

@stuartlynne
Copy link
Owner

stuartlynne commented Jan 25, 2023 via email

@stuartlynne
Copy link
Owner

stuartlynne commented Jan 25, 2023 via email

@MedTechCD
Copy link

MedTechCD commented Jan 25, 2023

map some other data from the same sensor, for example, RR times

I've used the HR stream to sync data from multiple devices with resonable accuracy. And for resprate, a few seconds will not make a difference. But I understand the problems you're facing.
Some thoughts:
An artefact like a premature beat should show in both ECG and RR time. That would be pretty accurate but can't be invoked...
I'm thinking of trying to hook up an ecg simulator and during recording, at specific time points, shortcircuit the signal. If that turns out to be consistent in timing difference, it could be part of a solution. But still, nothing guarantees that all H10 sensors have the same lag.

@stuartlynne
Copy link
Owner

stuartlynne commented Jan 25, 2023 via email

@MedTechCD
Copy link

MedTechCD commented Jan 25, 2023

Garmin announcing ECG support real soon now

It's released for the Venu 2 Plus in the US
https://www.dcrainmaker.com/2023/01/garmin-ecg-app-devices-fully-explained.html

We do have RR from the same H10 via the ANT+ channel in Dashboard, don't we?
To get as close as possible now (close enough for what I'm doing), I start both apps and if the ECG shows a stable trace, I hit the Start Record button when dasboard is exactly at 4 or 5 min. That gives me an ECG file with a creation time 4 or 5 min later then the dashboard files. I hit the button again at an exact minute when stopping. For a recording of 80-90 min, the number of samples in the ECG is very close (within 200-250 samples) to the number of seconds * 130. This off course does not take into account that the data coming from the sensor may be delayed.

@stuartlynne
Copy link
Owner

stuartlynne commented Jan 26, 2023 via email

@MedTechCD
Copy link

separate stream of HRV Messages and they DO NOT
have a timestamp

The way RR data is saved is pretty good.
From the start of the recording, you look for the first R-peak. If it falls before one second has elapsed, the exact ms is stored with the first second by second data point. If not, it goes to the next data point. The following R-peaks are stored with a reference to the former R-peak in ms. If more then one R-peak occurs within the same second, all ms values are stored in that datapoint.
The timeline for the R peaks can be reconstructed from this by adding up all inter-peak intervals.
As an example, A, B, C are the usual metrics measured every second (HR, Power, Cadence, ...) and then comes the RR values in this simple representation:
1 A B C 800
2 A B C 820
3 A B C 652
4 A B C 480;430
5 A B C 330;295,280

And so on. Every R peak can be exactly positioned by adding up all inter-beat values.

@MedTechCD
Copy link

For timing consistency, I did the following test:
Installed 2 little wires on the clips of the H10 sensor leading to a pushbutton to shortcircuit.
With the desktop clock displayed, started the ECG recording at 16:26:00. After 30 sec and then 7 consecutive times with a 10 sec interval, pushed the button to shortcircuit the strap. Stopped the recording after another 30 sec, for a total recording time of 2 minutes. File creation time = 16:26:00, modified time = 16:28:00.
Plotted in Excel:
image

I think you're worrying to much about timing. From what I see, the ECG is recorded with negligible time errors. The display on the other hand is lagging somewhere in between 3 and 3.5 seconds. That's probably caused by extra filtering and video lag.

@stuartlynne
Copy link
Owner

stuartlynne commented Jan 27, 2023 via email

@MedTechCD
Copy link

We just don't have the exact offset to match to the other data

The ECG file creation time gives you a date-time stamp (which is already used in the filename). Every 130 samples make up a second. Then it is just a question to reference that to the date-time stamp of the regular datastream or am I overlooking something?
One thing I'm absolutely missing in the actual dashboard app, is a Start button. You have to wait for the 2min data collection window for a1, but then you have no way to control when the Ra calculation starts because it starts immediately... I'm usualy doing other prep stuff (Power meter calibration, trainer control app setup, ...) while dashboard is already running. I would like a start button to control when data logging starts, and that button could start ECG collection at the same time.

@stuartlynne
Copy link
Owner

stuartlynne commented Jan 27, 2023 via email

@MedTechCD
Copy link

Do you want to play with an early beta of the new release?

I would be glad to give you my opinion and eventual remarks ;-)

@stuartlynne
Copy link
Owner

stuartlynne commented Feb 6, 2023 via email

@MedTechCD
Copy link

Also, on reviewing the Polar H10 data and comparing it to Movesense, I
think the Polar is giving us millivolt samples, not microvolts.

The values in the recorded csv file from Fitness ECG app are definitely µV. Common p2p amplitudes for ECG are around 1-2,5mV. The csv, for my recordings, has max values around 2500. That can only be µV. But I don't know if they are already manipulated by your app.

Effectively I am getting a BLE message containing a microsecond timestamp
and 73 data points every 560 mS.

Guess you mean a millisecond timestamp?
That would be slightly higher then 130Hz resulting in 1286 samples extra per hour compared to the 130 Hz I used now. Or about 10 sec. Not entirely convinced here...

Or just put the timestamp in once every 73 samples?

I think just putting in what you actually get from the Polar SDK is the safest thing to do. Interpolating isn't difficult to do afterwards.

@MedTechCD
Copy link

MedTechCD commented Feb 7, 2023

This could be valuable information to understand the H10 Timestamps!

https://github.com/polarofficial/polar-ble-sdk/blob/master/technical_documentation/TimeSystemExplained.md

@stuartlynne
Copy link
Owner

stuartlynne commented Feb 8, 2023 via email

@MedTechCD
Copy link

MedTechCD commented Feb 9, 2023

The timestamp provided has a lot more precision (about nanoseconds), I
don't know how accurate it is. I can push as much of that across as is
needed.

There is absolutely no need to have that kind of precision. But this info allows correct interpretation of the timestamp. Rounding to milliseconds (eventally µsec) should be more the enough. Plotting ECG is in my opinion best done with the sample index and not with a timeline. Then visualy display a line every second or 10 seconds which aligns with 130 or 1300 samples. Calculating interbeat intervals is the number of samples divided by the sampling rate and multiplied by 1000 to have those in milliseconds. If my interpretation is correct, for the Polar H10 you would get a very large number as a date timestamp, because it is the number of nanoseconds counted from the default date 2019-01-01 - 00:00:00. Your local system date/time minus the default date/time is an offset to display with time-of day. Once you have the precise start-time to sync with other sensor sources, things can be displayed with elapsed time.
Or, at start of a recording, you send the system time to the H10 with the setlocaltime command and then the timestamps should be elapsed time in nanosecs.

The first time-stamp is the most important one to make syncing with other sources possible. After that, it's just a matter of checking that no samples were lost every x msec (560?). But the timing should be very consistent by simply using the sample index.

Regarding the amplitudes of the ECG signal: if you get any number in the stream that is higher then ~500, it must be µV because the electrical signals from the heart simply don't have amplitudes of 0.5V and higher.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants