Do you forget to change your contact lenses when your supposed to? Well I do, and I normally realise a week later than I should and at the worst times such as when I am in a meeting and my eyes start to dry up bad and I am squinting to read the power-point I am presenting.
Yes there are phone apps and reminder services but when I change my lenses I do not always have my phone to hand.
I figured it would be great if I could put a Dash in the bathroom and when I changed my lenses I would register that through a click on the Dash. From that point I would get warnings to change my contact lenses, if I did not I would keep getting stronger warnings from myself until I reset the system through another click.
This project can easily be tweaked for all sorts of reminders, such as when to take your medication, which could be useful for you or elderly relatives.
Sounds simple and for the most part it is, but it does require using a number of software applications and a bit of coding. I found this project to be an excellent introduction to a real world use-case for Google Apps scripts and IFTTT.
This was my second Amazon Dash hack, the first one which uses Dash to play a Sonos playlist can be found here (Step 1 and Step 2 are the same for both projects).
Step 1 - Get and Hack your Amazon Dash ButtonGet an Amazon Dash button and download the Amazon App to your mobile.
Follow the instructions on the app to register the Dash button BUT make sure you skip the last part where you are asked to associate the Dash with a particular product. Just quit from the app.
Amazon will keep on reminding you to complete the setup, however if this gets annoying just uninstall the app.
Step 2 - Setup Dasher on your Raspberry PiDasher is the piece of software that will talk to your Dash button and allow you to do cool things with it. Follow this link and scroll down to the Setup part. I used a Raspberry Pi 3.
I do strongly suggest that your Pi is wired up to your network via Ethernet. With WiFi I frequently found that the Dash click was not being picked up by dasher.
Step 3 - Get Dasher to trigger IFTTTIFTTT is an excellent tool for stitching together different IoT services and applications. In this example we are using IFTTTs Webhook Service. This allows you to trigger and IFTTT event by simply calling a specifically defined URL. We get Dasher to call this specific URL when the Dash button is pressed.
Firstly go into the configuration file for Dasher using the nano editor (or whatever editor you prefer):
pi@raspberrypi:~/dasher/config $ sudo nano config.json
The configuration file controls what happens when you click the Dash button. As you can see I have two buttons setup. For this project we are looking at the "Contact Lens Changed" one, as you can see I have configured it to call a specified URL when the button is pushed.
{"buttons":[
{
"name": "Sonos Playlist",
"address": "50:f5:da:1d:01:86",
"url": "http://192.168.1.93:5005/office/playlist/work%20tunes",
"protocol": "udp"
},
{
"name": "Contact Lens Changed",
"address": "44:65:0d:64:da:13",
"url": "https://maker.ifttt.com/trigger/changed_contacts/with/key/ABCD1234",
"protocol": "udp"
}
]}
Step 4 - Get IFTTT to Update Google SheetsSo far if everything has worked when you hit your dash button you should get an IFTTT notification event. If you download the mobile IFTTT mobile app this event will trigger as an alert on your phone. The next step is to create an IFTTT applet that binds your IFTTT Webhook to Google Drive and specifically to a Sheet in your Google Drive. Start the process here. Your IFTTT applet should look like this.
If your successful, when you now click on your Amazon Dash button you see your Google Sheet update columns A and B as below (don't worry about C for now, the Google Apps Scritp code will do that).
Now the really fun and smart part! Google Apps Script (GAS) is a JavaScript based language Google offers inside of its application ecosystem. This was my first project using it and I was impressed at the ease of use and power it can offer to automate events. It took me way back to the days when I was hacking VBA in Excel for Traders.
For this project we want to trigger an email alert to the user during various times after they had changed their contacts and GAS will help us achieve that. Firstly we need to defined when we want to notify the user, these were the events that I wanted to trigger an email for:
- Just after they have changed and clicked the Dash button.
- A day before the contacts expire.
- The day of expiry.
- Each day after expiry (this will get annoying of course and serve as an incentive the user to change their lenses).
The email message to send to the user for each of these events and the duration of wear for my lenses (mine are bi-weekly but I know others might be a month) are static defaults set in the Google Sheet as shown below.
The following GAS code glued everything together. I have over annotated it so you can follow what I was thinking. I should add, if its not evident already, that I am not a developer by profession. The code below is functional but I am sure a proper developer could make it more elegant. Still it gets the job done!
function updateFromDash(e) {
// Initialize Spreadsheet and particular Sheet
var ss = SpreadsheetApp.getActiveSpreadsheet();
var log = ss.getSheetByName("Log");
// Get last row
var lr = log.getLastRow();
var check = log.getRange(lr,2).getValue();
// If last row column 2 is blank then put Date into column 3
if (check =! "") {log.getRange(lr,3).setValue(new Date());}
// Now switch to the Calcs Sheet
var calcs = ss.getSheetByName("Calcs");
// Get the Date value we just created and put it into the Calcs sheet.
// This stores the Date of last click
var lastDate = log.getRange(lr,3).getValue();
calcs.getRange('B1').setValue(lastDate);
// Send email, message code = 0
sendEmail(0,0);
}
function checkDays(e) {
// Initialize Spreadsheet and particular Sheet
var ss = SpreadsheetApp.getActiveSpreadsheet();
var calcs = ss.getSheetByName("Calcs");
/* The number of days I have worn my contacts is calculated through a Sheet function
Get this value */
var daysWorn = calcs.getRange('B2').getValue();
var ss = SpreadsheetApp.getActiveSpreadsheet();
/* Now switch to the Static sheet and get the maximum days I should be wearing my
contacts for.*/
var static = ss.getSheetByName("Static");
var maxDaysAllowed = static.getRange('B6').getValue();
/* Check for how long they have been worn for and depending on that
send different message */
if (daysWorn == (maxDaysAllowed-1)) {sendEmail(daysWorn,1);}
else if (daysWorn == maxDaysAllowed) {sendEmail(daysWorn,2);}
else if (daysWorn > maxDaysAllowed) {sendEmail(daysWorn,3);}
}
function sendEmail(days,msg) {
// Initialize Spreadsheet and particular Sheet
var ss = SpreadsheetApp.getActiveSpreadsheet();
var sheet = ss.getSheetByName("Static");
/* Get email address of user. Range can also be called by row, column as well,
this is just to illustrate that fact*/
var emailAddress = sheet.getRange(1, 2).getValue();
/* Now send the email, depending on the message code supplied.
The email specifies how long user has worn contacts for in subject
line */
if (msg == 1) {var message = sheet.getRange('B2').getValue();}
else if (msg == 2) {var message = sheet.getRange('B3').getValue();}
else if (msg == 3) {var message = sheet.getRange('B4').getValue();}
else if (msg == 0) {var message = sheet.getRange('B5').getValue();}
var subject = 'Contact Lens Worn for ' + days + ' days';
// This one line sends the email!
MailApp.sendEmail(emailAddress, subject, message);
}
The final part of this Step is to setup the project triggers that tell Google when to run your GAS code. From the GAS Editor go to 'Edit -> Current Project Triggers' and setup the below scenario. When we hit the Dash button it (through IFTTT) changes the Sheet and triggers the 'updateFromDash' function.
That is it! If you get stuck or have any questions reach out to me.
Comments