現在,連簡單的杯墊都可以連上雲端了!為了健康著想,人一天需要補充兩千至三千c.c.的水分,但怎麼知道自己喝的夠不夠多?或是擔心家人和小孩水分補充的狀況?如今一個杯墊能連上網路,透過雲端運算出喝了多少水且顯示在手機App中,如果您是一位家長,不論是在辦公室、室外,都能了解小朋友水分的攝取量,不只如此,利用物聯網的技術,還可以用App遠端操作杯墊的設備,例如讓裝有蜂鳴器的杯墊播放音樂,以提醒小朋友該喝水囉!
智慧杯墊的功能為計算每一次喝水時所補充的水量,只要在喝完水後,將水杯放回智慧杯墊上,雲教授便會自動顯示此次的攝取量,同時記錄後上傳至雲端,若一段時間偵測到使用者沒有喝水,杯墊會播出依使用者喜好設定的音樂,提醒使用者該補充水分了。智慧杯墊的設計是把壓力感測器夾入杯墊之中,以測量出水杯的重力,並計算每次放上水杯時重力的差距,讓程式判斷出重力確實有減少,再顯示於雲教授APP中。非常簡單的邏輯,賦予了杯墊一個生命,接下來就讓我們實現他吧!
連接雲教授,開啟CPF Arduino,進入Lesson 8 插槽模式。
先將雲教授與相對應感應器連接至Grove擴充板,壓力感應器連接上A2插槽,蜂鳴器接至D5插槽,LED指示燈接至D2插槽,如圖:
點擊執行按鈕,可對目前感應器進行各別操作與顯示,插槽A2顯示壓力感測器的值,D2欄位可以開關LED燈,D5為蜂鳴器的欄位,開啟即可播放預設的音樂。
現在,要開始撰寫智慧杯墊的程式碼,點擊修改按鈕進入程式碼編輯介面,將預設的程式碼全部刪除,並加入以下程式碼。
var a2;
a2 = cpf.get("socket a2");
程式解析:
現在可以接收到壓力值了,接下來要開始寫如何測量自己喝的水量,首先,判斷水杯是否有被拿起,若沒有被拿起,每過1秒自動暫存目前的壓力。
var a2;
var time = new Date();
time = time.getSeconds();
var temp = temp || 0;
a2 = cpf.get("socket a2");
if(a2 < 100 || a2 == 0) {
//喝水中
}else {
//沒喝水時
if(time % 1 = 0 || time == 0) {
temp = a2;
}
}
程式解析:
若a2=0或小於杯子重量,表示有被拿起,我們先撰寫喝水時必要進行的前置動作,以便之後作判斷與計算使用。
...
var temp = temp || 0;
var drinktime;
var newtemp;
a2 = cpf.get("socket a2");
if(a2 < 100 || a2 == 0) {
//喝水中
drinktime = Date.now();
newtemp = temp;
}else {
...
程式解析:
接下來要判斷當水杯再次放回杯墊時,重量是否比拿起前的還輕,如果比較輕代表有喝過水,計算完成後,儲存要顯示出來的資訊和時間,最後顯示在content區塊中。
...
var newtemp;
var result = result || 0;
var msg;
var date = new Date();
程式解析:
水量計算方法:
裝滿水杯的重量減掉沒裝水的水杯重量,得到水杯容量(範例為400),將喝水前的重量減掉喝水後的重量,得到已補充的重量,接下來把已補充的重量除以水杯容量後,在乘上100,答案就會是你喝掉了你的水杯中多少百分比的量,最後利用Math.round方法四捨五入,得出結果。
...
newtemp = temp;
}else {
//沒喝水時
if(newtemp - a2 > 20) {
result = Math.round( ( (newtemp - a2) / 400 ) * 100);
msg = "You have already drank " + result + "% of the cup\n" + date;
ui.set("content", msg);
}
...
程式解析:
接著為了讓計算出來的結果更為精準,我們限制喝完水放下杯子後,必須讓壓力感測器讀取10秒穩定下來,再進行判斷與計算。
...
//沒喝水時
if(Date.now() - drinktime > 10000) {
if(newtemp - a2 > 20) {
result = Math.round( ( (newtemp - a2) / 400 ) * 100);
msg = "You have already drank " + result + "% of the cup\n" + date;
ui.set("content", msg);
}
newtemp = a2;
}
程式解析:
到這邊,已經完成了智慧杯墊的基本功能設置,接下來要使用到物聯網的技術,將顯示出來的結果上傳至雲端,才能在任何時段以及地點觀看小朋友喝水的狀況,新增至 ui.set("content", msg);
下方。
...
ui.set("content", msg);
index += 1;
var json = {"result": result, "date": date};
var str = JSON.stringify(json);
var storeId = "store" + index;
aop.setStore("storeId", str);
}
newtemp = a2;
}
程式解析:
我們要繼續增加額外的功能,當杯墊沒有放置任何東西時,要開啟LED燈指示杯墊目前沒有放上水杯,若已放上水杯,則關閉LED燈。
if(a2 < 100 || a2 == 0) {
//喝水中
drinktime = Date.now();
newtemp = temp;
cpf.set("socket d2", 1);
}else {
//沒喝水時
cpf.set("socket d2", 0);
if(Date.now() - drinktime > 10000) {
...
另外,若過一段時間沒有喝水,蜂鳴器就會開始播放音樂告知使用者,我們利用現在的時間減掉drinktime喝水的時間,當距離上次喝水超過一個小時(3600000毫秒)的話,執行程式碼。將下列程式碼寫在最後一行,範例程式為小星星的歌曲。
if(Date.now() - drinktime > 3600000) {
cpf.set("socket d5", 261, 500);
cpf.set("socket d5", 261, 500);
cpf.set("socket d5", 392, 500);
cpf.set("socket d5", 392, 500);
cpf.set("socket d5", 440, 500);
cpf.set("socket d5", 440, 500);
cpf.set("socket d5", 392, 500);
cpf.set("socket d5", 349, 500);
cpf.set("socket d5", 349, 500);
cpf.set("socket d5", 329, 500);
cpf.set("socket d5", 329, 500);
cpf.set("socket d5", 293, 500);
cpf.set("socket d5", 293, 500);
cpf.set("socket d5", 261, 500);
drinktime = Date.now();
}
程式解析:
以上已完成了程式碼的撰寫,最後在最後一行加上 cpf.repeat();
開啟迴圈進行重複執行的動作。
1. 準備好兩個杯墊,會呈現出一個正面(凹面)一個背面(平面),分別朝上擺放。
2. 於壓力感測器背面的膜撕開,撕開後背面可黏貼。
3. 拿起背面(平面)朝上的杯墊,將撕掉後的感測器背面黏貼於杯墊平面處的正中央。
4. 剪下透明膠帶黏貼且覆蓋於壓力感測器上,接著將兩層的泡棉膠黏貼在感測器上方,注意範圍以不覆蓋黑色邊框為基準,如圖所示。
5. 接下來撕開最上層的泡棉膠,將另外一個杯墊的正面(凹面)朝上蓋下去。
智慧杯墊,完成!
var a2;
var temp = temp || 0;
var newtemp;
var time = new Date();
time = time.getSeconds();
var result = result || 0;
var msg;
var date = new Date();
var index = index || 0;
var drinktime;
a2 = cpf.get("socket a2");
if(a2 < 100 || a2 == 0) {
//喝水中
drinktime = Date.now();
newtemp = temp;
cpf.set("socket d2", 1);
}else {
//沒喝水時
cpf.set("socket d2", 0);
if(Date.now() - drinktime > 10000) {
if(newtemp - a2 > 20) {
result = Math.round( ( (newtemp - a2) / 400 ) * 100);
msg = "You have already drank " + result + "% of the cup\n" + date;
ui.set("content", msg);
//雲端上傳
index += 1;
var json = {"result": result, "date": date};
var str = JSON.stringify(json);
var storeId = "store" + index;
aop.setStore("storeId", str);
}
newtemp = a2;
}
if(time % 1 == 0 || time == 0) {
temp = a2;
}
}
if(Date.now() - drinktime > 3600000) {
cpf.set("socket d5", 261, 500);
cpf.set("socket d5", 261, 500);
cpf.set("socket d5", 392, 500);
cpf.set("socket d5", 392, 500);
cpf.set("socket d5", 440, 500);
cpf.set("socket d5", 440, 500);
cpf.set("socket d5", 392, 500);
cpf.set("socket d5", 349, 500);
cpf.set("socket d5", 349, 500);
cpf.set("socket d5", 329, 500);
cpf.set("socket d5", 329, 500);
cpf.set("socket d5", 293, 500);
cpf.set("socket d5", 293, 500);
cpf.set("socket d5", 261, 500);
drinktime = Date.now();
}
cpf.repeat();
到這邊,我們學習到杯墊運作的邏輯思考,其實就是運用了多次的if來判斷,和迴圈的進行,也了解到壓力感測器以及蜂鳴器的使用方式,而目前所學的還可以發揮在更多的用途上,有了這些概念後,我們可以讓杯墊的運用進行延伸,例如使用者可以針對自己的體重,計算出每日所需要喝的水量,調整在程式碼中,或者提醒時能更改成自己喜歡的音樂,甚至可以搭配溫度感測器,讓使用者不但能適量的攝取外,也能調整合適的水溫,喝得更健康!又或者是否有更特別的想法,讓它擦出不一樣的火花呢,嘗試實作上述延伸的例子,依照自己的想像力,創造出自己的作品吧!