Smart Companion Fall Alert: a Health Monitor Our Elderly

by IoTagger in Circuits > Wearables

1663 Views, 22 Favorites, 0 Comments

Smart Companion Fall Alert: a Health Monitor Our Elderly

IMG_4939.JPG

Smart Companion is a wearable button that monitors if the person using it falls. It will then send an alert via text message to a relative, care taker or nurse at the front desk of a hospital. It gives the user enough time to cancel the alert in case it was mistakenly triggered. The wearable was designed thinking on elderly patients that might fall and injure themselves needing assistance right away. While alert buttons and apps are a good solution it requires the individual to report the fall which might not be possible in cases where the person is left unconscious or is unable to trigger the device. We later added two other possible modes in case the device wanted to be used on babies or individuals suffering of seizures such as epileptic patients. Smart Companion welcomes the user by lighting up all LEDs and emitting a welcome setting sound. One can chose any of the three settings (elderly, baby or health condition) by clicking on one of the four button’s on the board. A light will illuminate to indicate which setting was picked and a text message will be sent notifying that the device is now set for such setting. When the individual falls the accelerometer data will trigger all LEDs to be turned on red in the wearable and send an alert to the specified device. Other methods of alerts can be set such as sending an e-mail, a pager, etc. By setting up an Azure free account data was posted to the cloud, all servers were configured which included the namespace servers, the storage and aggregators which would then capture and analyze the data.

List of Materials

Wearhacks5.jpg
Wearhacks2.jpg
internetphotonbutton.jpg

For this project you will need:

Hardware

1) USB cable

2) Particle Internet Button or similar LED ring with accelerometer

3) Photon

Software:

1) An account at Particle.io https://build.particle.io

2) An account at IFTT http://ifttt.com/

3) An account with Azure if you wish to upload information to the cloud for later use

Flushing Your Photon

The Photon will be the part that will make your Internet Button or any other LED ring shield with acceleremoter connected to the Internet to be able to upload information to the cloud or connect it to other devices if needed.

From a terminal install particle-cli to be able to run commands for your Particle device. In Mac use the search option (Spotlight) to find "Terminal". In windows go to Start > Search and look for "cmd".

$ sudo npm install particle-cli -g
[serialport] Success: "/usr/local/lib/node_modules/particle-cli/node_modules/serialport/build/serialport/v2.0.2/Release/node-v14-darwin-x64/serialport.node" is installed via remote
/usr/local/bin/particle -> /usr/local/lib/node_modules/particle-cli/bin/particle.js particle-cli@1.8.16 /usr/local/lib/node_modules/particle-cli

Note: If you are using Windows and you don't see the successful install try running the below command instead

$ npm install particle-cli –g --msvs_version=2013

You will then need to log in to your Particles account using the credentials you created through

http://build.particle.io/build . After you log in you will use the following steps to identify your device, connect it to wifi and then add it to your account.

$ particle login
$ particle serial list
$ particle serial identify
$ particle serial wifi 
$ particle device add 
$ particle device rename < enter your device number> <give it a new name> 

Installing Prerequisites for Azure

Due to some limitations with the webhooks you will need to install an older version of Node. Please note that newer versions might not be supported.

Installs needed:

1) Node 0.12.4 https://nodejs.org/download/release/v0.12.4/

If you already have other version of Node installed you will need a version manager, for Mac please view

https://github.com/creationix/nvm

2) Download and install Python 2.x https://www.python.org/downloads/

Lets Get Codding

Instruct-SmartB2.jpg
Instruct-SmartB1.jpg

1) Log in to https://build.particle.io/build/new and create a new "App"

2) Add the needed libraries. In the Particle Build web interface, click the “Libraries” icon on the righ hand side (icon resembles that of a bookmark). You will be able to search and add the needed libraries to you application. Add libraries "internetButton", and "Simon" which should inclide math.h.

Once you select the library make sure to click the "Include in App" button and select the name of the app you just created.

The below code includes two different ways of coding the Internet Button. One way has been commented out and the second way of displaying the LED colors and playing the music was left without comments. You should be able to copy the code, comment out the sections that are uncommented and remove the comments on the portions that are commented to test out the two version.

In the below example only one of the buttons is set upto gather and analyze the acceleration information from the accelerometer. Such button is considered the "elderly" mode and has also been set up to trigger an alert when being set and a separate alert if the individual using the device falls.

#include "InternetButton/InternetButton.h"
#include "math.h"
#include "Simon/Simon.h"
InternetButton b = InternetButton();
uint8_t button1 = 0;
uint8_t button2 = 0;
uint8_t button3 = 0;
uint8_t button4 = 0;
uint8_t buttonAll = 0;
int gaugeCount = 0;
char Org[] = "Alert Buddy";
char Disp[] = "Alert Buddy";
char Locn[] = "LOCATION";

//enum Position: int { Top = 0 , Right = 1, Bottom = 2, Left = 3, None = -1};<br>//enum State: int { Welcome, Ready, Showing};
//State state;
//Position read = anyButtonOn();
//int person;
/*
void welcome ()
{
    b.playSong("C4,8,E4,8,G4,8,C5,8,G5,4");
    b.allLedsOn(0,20,20); 
    delay(500);
    b.allLedsOff();
    
    flash(Top, true, true);
    flash(Right, true, true);
    flash(Bottom, true, true);
    flash(Left, true, true);
    state = Ready;
}
*/
void welcome ()
{
    b.playSong("C4,8,E4,8,G4,8,C5,8,G5,4");
    //b.allLedsOn(0,20,20); 
    delay(500);
    b.ledOn(11, 30, 250, 0); //255,0,0
    b.ledOn(1, 30, 20, 0);
    b.playNote("C4",4);
    delay(20);
    b.allLedsOff();
    
    b.ledOn(2, 0, 0, 255);
    b.ledOn(3, 0, 0, 255);
    b.ledOn(4, 0, 0, 255);
    b.playNote("E4",4);
    delay(20);
    
    b.ledOn(5, 120, 120, 0);
    b.ledOn(6, 120, 120, 0);
    b.ledOn(7, 120, 120, 0);
    b.playNote("G4",4);
    delay(20);
    
    b.ledOn(8, 255, 0, 0);
    b.ledOn(9, 255, 0, 0);
    b.ledOn(10, 255, 0, 0);
    b.playNote("C5",4);
    //state = Ready;
    exit;
}
void loop(){
    //switch (state) { 
        //case Welcome: 
            //welcome();
            //break;
        //case Ready: 
            ready();
            //break;
        //case Showing:
            show();
            //break;
//}
/*
int ledPos = b.lowestLed();
 char payload[255]; 
 snprintf(payload, sizeof(payload), "{ \"s\":\"Giroscope\", \"u\":\"Gir\",\"l\":\"%s\",\"m\":\"Movement\",\"o\":\"%s\",\"v\": %f,\"d\":\"%s\" }", Locn, Org, ledPos, Disp);
 Serial.println(payload);
 Spark.publish("ConnectTheDots", payload);
 delay(500);
 */
}
/*
void flash(Position p, bool timed, bool sound) {
    switch (p) {
        case Top: //button 1 green
            b.ledOn(11, 30, 250, 0); //255,0,0
            b.ledOn(1, 30, 20, 0);
            if (sound) { b.playNote("C4",4); }
            break;
        case Right: //button 2 blue
            b.ledOn(2, 0, 0, 255);
            b.ledOn(3, 0, 0, 255);
            b.ledOn(4, 0, 0, 255);
            if (sound) { b.playNote("E4",4); }
            break;
        case Bottom: //button 3 yellow
            b.ledOn(5, 120, 120, 0);
            b.ledOn(6, 120, 120, 0);
            b.ledOn(7, 120, 120, 0);
            if (sound) { b.playNote("G4",4); }
            break;
        case Left: //button 4 red
            b.ledOn(8, 255, 0, 0);
            b.ledOn(9, 255, 0, 0);
            b.ledOn(10, 255, 0, 0);
            if (sound) { b.playNote("C5",4); }
            break;
        case None: 
            delay(100);
            return;
    }
    if (timed) {
        b.allLedsOff();
    }
}
*/
void ready() {
    if(b.allButtonsOn()){
        if(!buttonAll){
            buttonAll = 1;
            Spark.publish("allbuttons",NULL, 60, PRIVATE);
            b.rainbow(10);
            delay(100);
            b.allLedsOff();
        }
    }
    else {buttonAll = 0;}
    
    if(b.buttonOn(1)){
        if(!button1){
            button1 = 1;
            Spark.publish("button1",NULL, 60, PRIVATE);
            b.ledOn(12,30, 250, 0); //top green
            delay(200);
            b.ledOff(12);
        }
    }
    else {button1 = 0;}
    
    if(b.buttonOn(2)){ 
        if(!button2){
            button2 = 1;
            Spark.publish("ElderHelp",NULL, 60, PRIVATE);
            b.ledOn(3,0, 0, 255); //right blue
            delay(100);
            b.ledOff(3);
        }
    }
    else {button2 = 0;}
    
    if(b.buttonOn(3)){
        if(!button3){
            button3 = 1;
            Spark.publish("button3",NULL, 60, PRIVATE);
            b.ledOn(6,120, 120, 0); //bottom yellow
            delay(100);
            b.ledOff(6);
        }
    }
    else {button3 = 0;}
    
    if(b.buttonOn(4)){
        if(!button4){
            button4 = 1;
            Spark.publish("button4",NULL, 60, PRIVATE);
            b.ledOn(9,255,0,0); //left red
            delay(100);
            b.ledOff(9);
        }
    }
    else {button4 = 0;}
    //Wait a mo'
    delay(50);
/*    Position read = anyButtonOn();
    
    switch (read) {
        case None:
            return;
        case Top:
        //elderly person GREEN
            person = 1;
            break;
        case Right:
        // epileptic BLUE
            object = 4;
            break;
        case Bottom:
        //baby YELLOW
            object = 8;
            break;
    }
    */
    //celebrate();
}
/*
void setColor() {
    if (object > 0 && object < 2) {
        RGB.color(30, 250, 0); // green
        //red (255,0,0)
        return;    
    }
    if (object > 3 && object < 6) { 
        RGB.color(0, 0, 255);
        //blue
        return;
    }
    if (object > 7 && object < 20) { 
        RGB.color(120, 120, 0);
        //yellow
        return;
    }
    
    RGB.color(0, 255, 0);
}
*
*
void start() {
        
    //generate(object);
    setColor();
    state = Showing;
}
void generate(int size) {
}
*/
void show() {
    
        //b.allLedsOff();
    //How much are you moving in the x direction? (look at the white text on the board)
    int xValue = b.readX();
    //How about in the y direction?
    int yValue = b.readY();
    //And the z!
    int zValue = b.readZ();
    int sumAccel = (abs(xValue) + abs(yValue) + abs(zValue))/30;
    if (sumAccel > 10)
    {
        b.allLedsOn(255, 0, 0); //if accelerates flash red
        b.playNote("G4",4);
        delay(900);
        b.allLedsOff();
        Spark.publish("ALERT FALLING DOWN",NULL, 60, PRIVATE);
    }
//int ledPos = b.lowestLed();
/* char payload[255]; 
 snprintf(payload, sizeof(payload), "{ \"s\":\"Giroscope\", \"u\":\"Gir\",\"l\":\"%s\",\"m\":\"Movement\",\"o\":\"%s\",\"v\": %f,\"d\":\"%s\" }", Locn, Org, sumAccel, Disp);
 Serial.println(payload);
 Spark.publish("ConnectTheDots", payload);
 delay(500);    
*/
}
/*
enum anyButtonOn() {
    if (b.buttonOn(1)) {
        return Top; 
    }
    if (b.buttonOn(2)) {
        return Right; 
    }
    if (b.buttonOn(3)) {
        return Bottom; 
    }
    if (b.buttonOn(4)) {
        return Left; 
    }
    return None;
}
*/
/*
void celebrate() {
    delay(500);
    b.ledOn(11, 30, 250, 0); //255,0,0
    b.ledOn(1, 30, 20, 0);
    b.playNote("C4",4);
    delay(20);
    b.allLedsOff();
    
    b.ledOn(2, 0, 0, 255);
    b.ledOn(3, 0, 0, 255);
    b.ledOn(4, 0, 0, 255);
    b.playNote("E4",4);
    delay(20);
    
    b.ledOn(5, 120, 120, 0);
    b.ledOn(6, 120, 120, 0);
    b.ledOn(7, 120, 120, 0);
    b.playNote("G4",4);
    delay(20);
    
    b.ledOn(8, 255, 0, 0);
    b.ledOn(9, 255, 0, 0);
    b.ledOn(10, 255, 0, 0);
    b.playNote("C5",4);
    */
/*   flash(Top, false, false);
    flash(Right, false, false);
    flash(Bottom, false, false);
    flash(Left, false, false);
    b.playSong("C4,8,E4,8,G4,8,C5,8,G5,4");
    delay(300);
    b.allLedsOff();
*/
/*
    delay(100);
    //start();
}
*/
void setup() {
    //Tell b to get everything ready to go
    // Use b.begin(1); if you have the original SparkButton, which does not have a buzzer or a plastic enclosure
    // to use, just add a '1' between the parentheses in the code below.
    //state = Welcome;
    RGB.control(true);
    //int person = 0;
    b.begin();
    welcome();
    b.allLedsOff();
}

Getting the Code Up and Running

Instruct-SmartB3.png
Wearhacks1.jpg
Instruct-SmartB7.jpg

By now you should be logged in to your Particle account, your Photon should be connected to the Wifi and either plugged in to an external power supply or to your computer.

1) On https://build.particle.io/build click the "Save" button.

2) Click the "Verify" button. This acts as a compiler and flaggs any error you might have on your code.

3) Lastly click the "Flash" button to upload the code to your hardware. You should see a purpleish light flashing on your photon as you upload the code. Once the Flashing is completed you will se a status update at the bottom of build.particle.io page.

If you have any issues with Flashing, first check that under "Devices" your device is listed and has a star right next to it. The start indicates that that is the default device.

Setting Up Texting and Alerting

Instruct-SmartB4.jpg
Instruct-SmartB6.jpg
Instruct-SmartB5.jpg
Instruct-SmartB8.jpg

We already include in the code the information needed to link to IFTT to a Smartphone.

Example

SparkButton b = SparkButton();
uint8_t button1 = 0; uint8_t button2 = 0; uint8_t button3 = 0; uint8_t button4 = 0; uint8_t buttonAll = 0; int gaugeCount = 0;

Now you will need to create the recipe in https://ifttt.com and connect it to your Photon device.

You can find my recipe at https://ifttt.com/myrecipes/personal/29777311

1) Dowload the IFTT app on your phone or whichever device you would like to send the alert notifications.

2) Log into your account at spark.io/build and confirm that under "Devices" your current device is listed with the yellow star/dot next to it.

3) Log in to https://ifttt.com , hit “Create Recipe” to start your new recipe.

4) Select Particle (former Spark) as your trigger channel.

5) Choose a Trigger. We will use “New Event Published”

6) Complete Trigger Fields. In our example we have the alert set for Button2.

If (Event Name): Here I'll add the Event Name (Topic) from my firmware -> button2

Is (Event Contents): Event Input is actually an optional field so I’ll go ahead and leave it blank.

Device Name or ID: This is your device Name or ID.

7) Choose Action Channel. In this case I used Launch to send notifications. You can use Gmail enabled for e-mail notifications. Save and create your recipe.

8) Since I am using Launch for alert notification the next setp is to connect the device to your recipe. By now you should have installed the IFTT app. Enter your IFTTT username and password and tap the Sign in.

9) Tap on the Recipe button (mortar and pestle) in the upper right corner. Then tap on the gear icon in the bottom right corner.

10) On this screen you should see a list of blue buttons. Tap on the Channels button

11) Seach for your channel (in this case Launch) and activate the recipe.

Testing Our Werable

Instruct-SmartB9.jpg
IMG_4935.PNG
Alert Buddy wearable at Wearhacks

At this point you should have the Internet Button up and running whith a welcome ring light and sound. The option to set one of the buttons with the "elderly care" mode and get a notification of both when the setting is completed and when the accelerometer passes a specific threashold which indicates the individual fell.

Going a Step Further and Adding Azure

If you wish to use Azure to upload the accelerometer data to the cloud you can create a free Azure account at

http://azure.microsoft.com/ . As a heads up the process might be somewhat tedious for a Mac user such as myself since the web dashboard creation is targetted for Windows users.

1) Create an Azure account at http://azure.microsoft.com/

2) I followed the steps listed at

https://github.com/BretStateham/connectthedots/tre... to set up the namespace, storage and collector/agreggators. Note: Please use the same location for all three servers you are setting to avoid to have to pay any additional costs. If your storage and namespace are in different locations you will be charged for cross colo data transportation.

3) If you are using Windows you can also set up a dashboard/website following the steps at

https://github.com/BretStateham/connectthedots/blo... after you do the prep work.

4) Once you have your namsepace, storage and other boxes set up in Azure you will need to create a

webhook.json. In your machine create webhook.json, since I am used to using console I followed these steps while on a console/terminal window.

$ vi webhook.json

Copy paste the following json file. Update the XXX under URL with your namespace name that was created in Azure.

Updae the XXX key with your personal Azure key. If you are unsure of where to find the Key please review notes on

https://github.com/BretStateham/connectthedots/blo...

{ 
"event": "ConnectTheDots", "url": "https://XXXXXXX-ns.servicebus.windows.net/ehdevices/messages", "requestType": "POST", "json": { "subject": "{{s}}", "unitofmeasure": "{{u}}", "measurename": "{{m}}", "value": "{{v}}", "organization": "{{o}}", "displayname": "{{d}}", "location": "{{l}}", "timecreated": "{{SPARK_PUBLISHED_AT}}", "guid": "{{SPARK_CORE_ID}}"
},
 "azure_sas_token": { 
 "key_name": "D1", 
 "key": "XXXXXXXXXXX" 
 }, 
 "mydevices": true 
}

5) From the command prompt, get in the same folder as the webhook.json file you downloaded, and run

$ particle webhook create webhook.json
$ particle webhook list

From your Azures account restart your aggregator (step 9 on

https://github.com/BretStateham/connectthedots/tree/master/HOLs/Azure/AzurePrep ) and you should then start getting data posted to your cloud instance in Azure.