ダイエットを続けるために玄関で懸垂しないと家の鍵が開かない仕組みを爆速でつくってみた【プログラム編】
Twitterのつぶやきから始まった筋トレしないとお家に入れないアイデアのプログラムの説明編
こんにちは!わみ(@wamisnet)です。
私の住んでるシェアハウス、入り口にチンニングバーがあって10回懸垂しないと家に入れない仕組みになってるんですよ、逆に10回懸垂すれば誰でも入れるのでぜひ、ギークハウス新宿ってところです pic.twitter.com/ykQcSFxvdK
— awa (@VITAMIN_DOSUKOI) July 21, 2020
【懸垂しないと家に入れないお家】 そんなおかしなアイデアをテクノロジーで実現させちゃったお話です。
この記事は裏話的なプログラム編として、どんな風にこれができているのか紹介していきます。
どんなものを作ったのかは下記の記事をご覧ください!
つくったもの
ダイエットを頑張れないあなたに!
— わみ (@wamisnet) July 30, 2020
筋トレしないと玄関の鍵が開かないシステム作ってみた
いいねとかRTで広めてくれると次とか作るときの励みになるのでお願いします!!#ダイエット #筋トレハック pic.twitter.com/P4hNkEJUVj
プログラム解説
さて、早速ですがプログラムの説明をしていきましょう。
ハードウエア
コード全体については下記のリンクよりご覧ください。
https://github.com/wamisnet/chin-up-counter/blob/master/chin-up-counter.ino
Arduinoのライブラリを活用して距離センサーを使用します。
Arduinoはいろんなセンサーのライブラリが多数あるのがとても便利ですね。
後で出てくる「obniz」は簡単にIoTをつくることができるのですが、対応しているセンサーはそれなりにあり、普段使うようなセンサーなどは簡単に扱えるようになっています。
ただ、対応していないセンサーについては、少々obnizの知識が必要になるので、ちょっと開発が面倒です。
その欠陥も、今回使用している「obniz plug-in」ではArduinoのメリットとobnizのメリットをどっちも使うことができるんです!
そんなわけで、これからの説明でメインとなるのは、obniz plug-inの説明になります。
obniz plug-inをつかった初めての解説記事かもしれません?
データの受信
void onCommand(uint8_t* data, uint16_t length) {
if (length > 2 && data[0] == 'm' && data[1] == 'd' && data[1] == 'c') {
count_clear();
} else {
chin_up_finish = data[0];
}
}
まず受信する関数を用意します。
obniz.commandReceive(onCommand);
obniz.commandReceive
関数の引数に、先ほど用意した関数名を入れます。これでコマンドを受け取ったら上記の関数名の関数が呼び出され処理します。
void onCommand(uint8_t* data, uint16_t length)
では、data
にjavascriptから送信された内容が入っています。lengthはそのdata
のデータ長が入っています。
今回ではこのような形で、Webページからカウントをクリアする指示と懸垂の上限回数の指示を受け取れるようにします。
ちなみに、if (length > 2 && data[0] == 'm' && data[1] == 'd' && data[1] == 'c')
でいろんなコマンドを送れるようにしようと思いましたが、一個しか利用しなかったですw
データの送信
Webページに懸垂の回数を送信する部分を作っていきます。
void sendCommand(uint8_t chin_up_count,bool finish_flg,uint8_t chin_up_finish,bool up_flg){
char message[100];
sprintf(message,"{\"count\":%d,\"max_count\":%d,\"finish\":%s,\"mode\":""\"%s\"}",chin_up_count, chin_up_finish, finish_flg?"true":"false", up_flg?"up":"down");
if (!obniz.commandSend((uint8_t *)message, strlen(message))) {
Serial.printf("send message : %s\n", message);
}
}
obniz.commandSend(送信したいデータ, 送信したいデータ長)
このような形でjavascriptに送信したいデータを準備します。
今回はobniz.commandSend
関数でWebページにsprintfで生成したJSONフォーマットの文字列を送信します。
obnizOSの開始
obniz.start();
でobnizOSを開始させて、ネットワークの接続などを行います。
その他
uint16_t meter = sensor.readRangeContinuousMillimeters();
if (meter > 2000 ) return;
ここで、距離センサーからデータを取得します。0-2000mmで距離を取得できるので、それ以外はエラーなので、再度センサーの値を取得するようにしています。
それ以外のコードはカウントアップ用のIF文なので読めばわかると思います。
Web (javascript)
コード全体については下記のリンクよりご覧ください。
https://github.com/wamisnet/chin-up-counter/blob/master/web/index.html
データ送信
obniz.plugin.send("mdc");
obniz.plugin.send(Number($("#finish_input").val()));
ここで送信したものが、先に説明したハードウエア側の受信で取得できます。
シンプルですね
データ受信
obniz.plugin.onreceive = data => {
let str = "";
for (const dt of data) {
str += String.fromCharCode(dt);
}
const json = JSON.parse(str);
console.log(json);
}
受信にはちょいと一工夫が必要です。
バイナリのデータが届くので、今回はJsonのフォーマットのデータとして使いたいので、文字列化してからJsonParseを通して扱いやすいようにしています。
javascriptで扱うならJsonが一番扱いやすいのではないのでしょうか?
一つしかデータを扱わないのであれば、そのままバイナリで扱うのもよいでしょう。
その他
あとは、受信したJsonを基準にどの画像を表示するか切り替えます。
シンプルなjavascriptのコードかなと思います。
まとめ
obniz plug-inを活用することでシンプルなコードで作れました。
ハードウエアとWebのコードはそれぞれ100行に収まり、いともも簡単にIoTのデバイスを作れるようになりました。
便利な世の中ですね。
別の関連記事もありますので、ぜひご覧ください。