This project is an attempt to create a 'health kit' which can diagnose medical conditions and be portable enough to fit in a small box. With the proliferation of IoMT (Internet of Medical Things), its possible to get sensors that can measure pulse, ECG (Electrocardiography), EMG (Electromyography), body temperature, blood alcohol concentration among other variables. I also explore the possibility of using thermal imaging to view under skin bruises. Before proceeding, I'd like to say that this device is no substitute for professional medical diagnostics. A device needs to undergo a long period of extensive testing before being cleared for medical use. This is just a proof of concept (POC) of exploring the idea of building such a kit.
The project is a work in progress - While a working hardware prototype and app exists, newer features are constantly being added, newer sensors are being tested and machine learning models are being tried out. Due to the current COVID-19 situation, I am unable to move forward with this at the pace i'd like to. I did try rebuilding this with the new Arduino BLE 33, but I ran into issues along the way which I've described in this post. That being said, lets begin.
All too often diagnostic tools at home are limited to a sphygmomanometer (to measure blood pressure) or a blood sugar monitor. In my country (India), a staggering 60% of ambulances are not equipped with basic diagnostic tools. Adding to the problem, the arrival time can be close to half an hour, with several places running into several hours. Motorcycle ambulances are also becoming increasingly popular, as they offer a quicker, cheaper way to reach the patient. The downside is that they have very limited space for carrying any diagnostic tools. Its generally accepted that pre-hospital care is useful in helping patients where the cause isn't immediately apparent - the patient could be comatose or may have an abnormal heart beat. The system consists of a hardware health kit and a companion mobile application (built in React Native, so it has Android and iOS support).
The envisaged use cases of this include - In old age homes to do a more comprehensive health check of patients, In ambulances that are under equipped so that paramedics can get a more comprehensive view of the patients health and so that data can be sent to a doctor before the ambulance reaches the hospital, so that the doctor can better prepared and save time which would have been otherwise wasted on diagnosing the patient.
Open Source Hardware
- Arduino UNO - To interface with the sensors.
- Arduino Nano - To measure the environment variables and the drive the ILI9341 display.
- AD8232 - To measure ECG.
- Advancer Myoware V3 - To measure EMG.
- BMP180 - Measure barometric pressure and temperature.
- Neo 6M - GPS.
- DS18B20 - To measure body temperature.
- Raspberry Pi Model 4B - To interface with both the arduinos and the drive the 5" LCD Display.
- KY039 - To measure pulse.
- Bidirectional Logic Level Converter - Since ILI9341 display operates on a 3.3 V logic level, this is essential.
- 5 inch HDMI Display - To show the ECG and EMG.
- 2.8 Inch ILI9341 display - To show other variables such as body temperature, blood alcohol concentration etc.
- MQ3 - Makeshift breathalyzer.
Other Hardware: A thermal camera manufactured by Tonbo Imaging.
Open Source Software
- React Native - Build cross-platform mobile application.
- Raspbian - Open Source Linux Distro on Raspberry Pi.
- PuTTy - Open Source Terminal Emulator.
- Arduino/C++ - Programming Language.
Relevant files can be found on: https://github.com/AshutoshPandey123456/HealthHack .
Detailed Project Description:
The hardware consists of 2 Arduino's - one Uno and one Nano. The Uno drives the ECG and EMG Sensor. Since the ECG sensor needs a +18V and -18V potential difference to work, two 9V batteries are used (450 mAh). I left the battery circuit connected connected for a good 20 hours with barely any voltage drop across the battery, so the current drain is minimal. The ECG sensor has 3 electrodes that must be stuck to the body in an Einthoven triangle to work - one electrode on the heart and two on the side.
The above image depicts two possible electrode placements. I tried them both, and the electrode placement in image 2 was what gave me a cleaner PQRS graph - the readings were a lot more clear, So I went with that. ECG has a lot of applications in detecting abnormal heart beat patterns, and can go a long way in diagnosing conditions like atrial fibrillation. I looked online for datasets on heart beat, and there were quite a few on Kaggle. The issue is that medical ECG equipment usually has 6 'leads' or channels through which signals are received, whereas the sensor I am using has only 1 channel, so its not possible to use online datasets to detect fibrillation directly. I am working on combining data from multiple ECG sensors (the blue board on the left is an ECG shield mounted on top of the Uno). But at the moment we are displaying live ECG data. The ECG data is sent via HTTP Post requests to the web server, but the person administering care (paramedic or first responder) needs to know what's going on too. I went the easy route and decided to just use the Arduino Serial Plotter built into the Arduino IDE which can plot values and automatically adjust the graph axes based on incoming data and it worked like a charm. The Blue Line is ECG data.
The Red Line represents EMG data, Electromyography is used to measure activity of muscles. The peak on the right side of the graph represents me flexing my bicep muscles. Why have EMG at all? It can pick up abnormalities in muscle contractions. There are several diseases that are characterized by abnormal muscular contractions like tetanus, so I felt it was a useful metric to include. Because the values returned by the EMG sensor are so much smaller than ECG, I had to scale up the EMG readings so that they would be visible side by side with the ECG. However when the data is sent to the mobile app, only true readings are sent.
Adding any more sensors to the Arduino Uno would result in not being able to draw the graph on the serial plotter properly, so the rest of the components were connected to an Arduino Nano.
Having figured out the most obvious sensors to use apart from ECG and EMG (Temperature, Blood Alcohol concentration, Outside temperature, GPS etc). I turned my attention towards detecting injuries under the skin. Under the skin concussions are known to kill people, and even some limited form of imaging could be a potential game changer. I examined my options - making a portable MRI or CAT scanner was out of question. I briefly toyed with the idea of building a DIY X-ray machine (which had instructables on the web), but decided to not go with it because it still involved high voltages which were dangerous, and because it was hard to make the system truly 'portable'. Then I turned my attention to thermal imaging, I knew portable thermal cameras existed, and they could be used to check for conditions such as hypothermia. I was curious to see if thermography could help in diagnosing other injuries. After doing some research (links given at the bottom) , I came across quite a few papers. Where thermal imaging was used for:
- Detecting delayed onset muscle soreness (DOMS).
- Detecting vascular disorders.
- Detecting sports injuries.
However, thermal cameras are known to be expensive. Where was I going to get one? Being a college student, I decided to ask them. And the college did have a camera. It had been used by my seniors for a project for college some 8-10 years prior, and had been sitting in the college ever since.
The college provided one thermal camera (the one labelled Serial Innovations above). However, when I set out to actually use it, I ran into a lot of problems. The serial port cable was missing, and when I finally found a Serial to USB cable, plugging it in wouldn't do anything! The camera obviously needed some kind of drivers to work. Since the original company that manufactured these cameras had shut down, I had no option but to directly walk into the office of the company that had brought them out (which was fortunately in the same city I was in). They said they didn't have drivers, and couldn't give me some chip they used with the long green connector of the camera, but they did suggest a USB video capture device as a means of input. I got a cheap video grabber, which came with a CD for installation. I dug out an old laptop I had, converted the file to ISO, and finally got it to run on my laptop. Unfortunately the video grabber was only for windows, so I couldn't get it to run on the Pi of the kit, but at least I could connect my setup and get some thermal images. Here was the camera output:
The camera was positively ancient compared to modern FLIRs, and the image quality was real bad. Without the thermogram data that was not being transmitted over serial, I was limited to dealing with greyscale images. If I had the thermogram data, getting a proper heat map of body parts would be a trivial task with some python code running on the Pi. However I didn't, I resorted to image processing to try and build a heatmap by mapping the greyscale values, while the results were not all too great, here they are:
I am currently trying to source a better thermal camera, so that I can explore thermal imaging in more detail. Fortunately I have been selected for this year's Google Summer of Code (with Arduino nonetheless!) so I'll be putting that stipend money to good use. Hopefully one that is compatible with the Pi. There are thermal image sensors for the Arduino such as the AMG 8833 but they have too low of a resolution (8x8 pixels) to be of much use. Here's an Image of the complete setup, with the thermal camera.
The other sensors
Apart from the two mentioned above, I incorporated the following things into my project:
- Breathalyzer: The MQ3 sensor (left of center in the bottom of the above image, just next to the thermal camera) can detect even low quantities of ethanol in the air. This makes for an excellent breathalyzer, which can measure alcohol in one's breath. Its also capable of detecting other dangerous gases like Benzene and LPG.
- Temperature probe: To detect body temperature I decided to use the water proof version of the DS18B20 sensor. It comes in a rubber jacket with a metal tip. This allows the sensor to measure oral, under the armpit and rectal temperatures from the body, should the need arise.
- Pulse: I used a KY039 sensor for pulse rate. I used a bit of velcro wrapped around it to wrap around the finger. There is another Arduino sensor that can supposedly measure pulse from the wrist, I will be using that in future iterations.
- GPS: The exact location of the patient is really important. Since there is an off chance that a very poorly equipped ambulance might not even have GPS, I incorporated it into the design. The NMEA data is sent to the app, and the app uses google maps api so that the doctor can know how far away the ambulance is.
- Outside temperature and Air Pressure: High Altitude can cause hypoxia. Similarly extreme outside temperatures can also cause problems, so I decided to use BMP180 (I know its outdated now, but its what I had).
- Display: Since I didn't want the person using the kit to be forced to choose what data to see, I decided on incorporating a second display. A 2.8 inch ILI9341 display was adequate for the job, and it could be run off the Arduino Nano alone. Since ILI9341 is a 3.3V board, I had to use a pair of Adafruit Bidirectional Logic Level converters.
All of the sensors mentioned above were connected to the Arduino Nano, which was in turn connected to the Raspberry Pi. I left the collection of the ECG and EMG data to the Arduino Uno, because receiving data from the other sensors would mess up the Arduino serial plotter.
I wanted to use the Arduino Nano BLE 33 for this project, as it was much more powerful than the older Nano board. I thought the higher clock speed and additional RAM along with extra flash memory would help in running more complex algorithms on the board itself instead of relying on an Arduino, also, the BLE 33 being a 3.3V board would not need Bidirectional LLCs unlike the AVR Nano.. However, the BLE 33 being a new board, still has a few kinks to iron out:
- The screen refresh rate was very slow, even over hardware SPI. I don't know why this is the case, perhaps it involves with working with MBedOS that runs under the hood of the Arduino, or something else. A few other users have reported the same problems on the Arduino forums, and there appears to be no easy solution to this.
- The upload times for the sketches were really long. Some of the sketches took 5-7 minutes to compile and upload, I don't know why its so slow.
Given below is an approximate circuit diagram. Most of the component sketching websites did not have some of the components I used, so keep in mind that both the diagram here and the one on my github profile are approximates. I'll eventually get around to drawing an eagle schematic by hand, but for now this will have to do.
Working Video of the Hardware assembly:
Working Video of the Mobile application:
An Older iteration I built a couple of weeks before the above version
Some Final Words
I'd like to thank my friends/teammates Aman, Amogh and Yash who helped a lot with coding the mobile application. I look forward to developing this project further, a few interesting ideas apart from the ones mentioned above include making a DIY Digital stethoscope that can pick up abnormalities in heart noise, and fabricating a single PCB for this. I'd also like to thank the Element14 community for providing me with a space to exhibit my projects. From running a Micro:Bit summer code club: Ashutosh Pandey's Blog to Roadtesting the Raspberry Pi 4B What Is A RoadTest? , I've come a long way.
All the work with electronics thanks to element14 led to me getting selected for Google Summer of Code with Arduino this year, I'll be working with them to create a transcompiler for converting Arduino code into MicroPython for the upcoming Arduino Portenta H7. Thank you!