-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Initial commit – basic ECG visualisation
- Loading branch information
0 parents
commit 00c8191
Showing
8 changed files
with
711 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
/venv | ||
/__pycache__ | ||
.DS_Store |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
|
||
import os | ||
os.environ['QT_API'] = 'PySide6' # For qasync to know which binding is being used | ||
os.environ['QT_LOGGING_RULES'] = 'qt.pointer.dispatch=false' # Disable pointer logging | ||
|
||
import sys | ||
import asyncio | ||
from PySide6.QtWidgets import QApplication | ||
from qasync import QEventLoop | ||
from View import View | ||
|
||
if __name__ == "__main__": | ||
|
||
app = QApplication(sys.argv) | ||
loop = QEventLoop(app) | ||
asyncio.set_event_loop(loop) | ||
|
||
plot = View() | ||
plot.setWindowTitle("Rolling Plot") | ||
plot.resize(1200, 600) | ||
plot.show() | ||
|
||
loop.run_until_complete(plot.main()) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
MIT License | ||
|
||
Copyright (c) 2023 Kieran Brennan | ||
|
||
Permission is hereby granted, free of charge, to any person obtaining a copy | ||
of this software and associated documentation files (the "Software"), to deal | ||
in the Software without restriction, including without limitation the rights | ||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||
copies of the Software, and to permit persons to whom the Software is | ||
furnished to do so, subject to the following conditions: | ||
|
||
The above copyright notice and this permission notice shall be included in all | ||
copies or substantial portions of the Software. | ||
|
||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||
SOFTWARE. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,61 @@ | ||
import numpy as np | ||
import asyncio | ||
from PolarH10 import PolarH10 | ||
import time | ||
|
||
class Model: | ||
|
||
def __init__(self): | ||
|
||
self.polar_sensor = None | ||
|
||
# Sample rates | ||
self.ACC_UPDATE_LOOP_PERIOD = 0.001 # s, time to sleep between accelerometer updates | ||
self.ACC_HIST_SAMPLE_RATE = 1000 # Hz, rate to subsample acceleration (raw data @ 200 Hz) | ||
|
||
# History sizes | ||
self.BR_ACC_HIST_SIZE = 1200 # | ||
self.BR_HIST_SIZE = 500 # Fast breathing 20 breaths per minute, sampled once every breathing cycle, over 10 minutes this is 200 values | ||
|
||
# Initialisation | ||
self.t_last_breath_acc_update = 0 | ||
|
||
# History array initialisation | ||
self.breath_acc_hist = np.full(self.BR_ACC_HIST_SIZE, np.nan) | ||
self.breath_acc_times = np.full(self.BR_ACC_HIST_SIZE, np.nan) | ||
self.breath_acc_times_rel_s = np.full(self.BR_ACC_HIST_SIZE, np.nan) | ||
|
||
def set_polar_sensor(self, device): | ||
self.polar_sensor = PolarH10(device) | ||
|
||
async def connect_sensor(self): | ||
await self.polar_sensor.connect() | ||
await self.polar_sensor.get_device_info() | ||
await self.polar_sensor.print_device_info() | ||
|
||
async def disconnect_sensor(self): | ||
await self.polar_sensor.disconnect() | ||
|
||
async def update_acc(self): # pmd: polar measurement data | ||
|
||
await self.polar_sensor.start_ecg_stream() | ||
|
||
while True: | ||
await asyncio.sleep(self.ACC_UPDATE_LOOP_PERIOD) | ||
|
||
# Updating the acceleration history | ||
while not self.polar_sensor.ecg_queue_is_empty(): | ||
# Get the latest sensor data | ||
t, ecg = self.polar_sensor.dequeue_ecg() | ||
|
||
if t - self.t_last_breath_acc_update > 1/self.ACC_HIST_SAMPLE_RATE: | ||
self.breath_acc_hist = np.roll(self.breath_acc_hist, -1) | ||
self.breath_acc_hist[-1] = ecg | ||
self.breath_acc_times = np.roll(self.breath_acc_times, -1) | ||
self.breath_acc_times[-1] = t | ||
self.t_last_breath_acc_update = t | ||
|
||
|
||
|
||
|
||
|
Oops, something went wrong.