Arduino×hifiveで見えるIoT×HTML5の形
今回はいつもと少し趣向を変えて・・・早速ですが、こんなものを作ってみましたので動画をご覧ください。
Arduinoを使って、明るさを数値化して読み取っています。小さな部品がそうで、指で隠したり手で覆ったりすると数値が下がります。
ArduinoにはWiFiサーバになるシールド(CC3000)をつなげていて、Webサーバの役割を担っています。
Arduinoはloopメソッドの中で入力待ちをしたりするループ処理を記述しますが、今回は次のようになっています。
void loop(void) { // Try to get a client which is connected. Adafruit_CC3000_ClientRef client = httpServer.available(); Serial.println("Client waiting"); if (client) { bool parsed = false; while (!parsed && (millis() < endtime) && (bufindex < BUFFER_SIZE)) { : parsed = parseRequest(buffer, bufindex, action, path); } // Handle the request if it was parsed. if (parsed) { // Check the action to see if it was a GET request. if (strcmp(action, "GET") == 0) { client.fastrprintln(F("HTTP/1.1 200 OK")); if (strcmp(path, "/") == 0) { client.fastrprintln(F("Content-Type: text/html")); client.fastrprintln(F("Connection: close")); client.fastrprintln(F("Server: Adafruit CC3000")); client.fastrprintln(F("")); client.fastrprintln(F("<!DOCTYPE html>")); client.fastrprintln(F("<html lang=\"en\">")); client.fastrprintln(F(" <head>")); client.fastrprintln(F(" <meta charset=\"utf-8\">")); client.fastrprintln(F(" <meta http-equiv=\"X-UA-Compatible\" content=\"IE=edge\">")); client.fastrprintln(F(" <meta name=\"viewport\" content=\"width=device-width, initial-scale=1\">")); client.fastrprintln(F(" <link href=\"//code.htmlhifive.com/h5.css\" rel=\"stylesheet\">")); client.fastrprintln(F(" <link href=\"//hifive.github.io/hifive-ui-library/hifive-ui-library/WebContent/components/chart/src/chart.css\" rel=\"stylesheet\">")); client.fastrprintln(F(" <title>hifive</title>")); client.fastrprintln(F(" </head>")); client.fastrprintln(F(" <body>")); client.fastrprintln(F(" <div id=\"container\">")); client.fastrprintln(F(" <h1>Arduino & hifive!</h1>")); client.fastrprintln(F(" <div id=\"chart\" ></div>")); client.fastrprintln(F(" </div>")); client.fastrprintln(F(" <script src=\"//ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js\"></script>")); client.fastrprintln(F(" <script src=\"//code.htmlhifive.com/ejs-h5mod.js\"></script>")); client.fastrprintln(F(" <script src=\"//code.htmlhifive.com/h5.dev.js\"></script>")); client.fastrprintln(F(" <script src=\"//code.htmlhifive.com/h5-dev-tool.js\"></script>")); client.fastrprintln(F(" <script src=\"//hifive.github.io/hifive-ui-library/hifive-ui-library/WebContent/components/chart/src/graphic-renderer.js\"></script>")); client.fastrprintln(F(" <script src=\"//hifive.github.io/hifive-ui-library/hifive-ui-library/WebContent/components/chart/src/chart.js\"></script>")); client.fastrprintln(F(" <script src=\"//dl.dropboxusercontent.com/u/49508/hifive-examples/javascripts/chartController.js\"></script>")); client.fastrprintln(F(" </body>")); client.fastrprintln(F("</html>")); }else if (strcmp(path, "/data.json") == 0){ client.fastrprintln(F("Content-Type: application/json; charset=utf-8")); client.fastrprintln(F("Connection: close")); client.fastrprintln(F("Server: Adafruit CC3000")); client.fastrprintln(F("")); client.fastrprintln(F("[")); for (i = 0; i < 99; i++){ if (arr[i] == 0) { continue; } str = String(arr[i]); str.toCharArray(b, 4); Serial.println(val); if (i > 0) { client.fastrprint(F(",")); } client.fastrprint(b); arr[i] = 0; } max_val = 0; client.fastrprintln(F("]")); } } else { } } delay(100); Serial.println(F("Client disconnected")); client.close(); }else{ val = analogRead(0); arr[max_val] = val; if (max_val < 99) { max_val += 1; } delay(200); } }
細かい処理は省いていますが、 ルート(今回は http://192.168.100.126/ )にアクセスすると、Webページが表示されます。
内容は次のようになっています。最低限のhifive構成と、前回の記事で紹介したリアルタイムチャートを描く構成になっています。
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1"> <link href="//code.htmlhifive.com/h5.css" rel="stylesheet"> <link href="//hifive.github.io/hifive-ui-library/hifive-ui-library/WebContent/components/chart/src/chart.css" rel="stylesheet"> <title>hifive</title> </head> <body> <div id="container"> <h1>Arduino & hifive!</h1> <div id="chart" ></div> </div> <script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> <script src="//code.htmlhifive.com/ejs-h5mod.js"></script> <script src="//code.htmlhifive.com/h5.dev.js"></script> <script src="//hifive.github.io/hifive-ui-library/hifive-ui-library/WebContent/components/chart/src/graphic-renderer.js"></script> <script src="//hifive.github.io/hifive-ui-library/hifive-ui-library/WebContent/components/chart/src/chart.js"></script> <script src="//dl.dropboxusercontent.com/u/49508/hifive-examples/javascripts/arduino_chartController.js"></script> </body> </html>
Webアクセスがない時には次の処理が実行されています。
val = analogRead(0); arr[max_val] = val; if (max_val < 99) { max_val += 1; }
つまり配列の中にアナログ入力(今回は明るさの数字)を入れています。これは200〜800くらいの数字を出します。
そして /data.json にアクセスが来ると、配列に入っているデータをまとめて出力し、自分自身を0リセットします。
client.fastrprintln(F("Content-Type: application/json; charset=utf-8")); client.fastrprintln(F("Connection: close")); client.fastrprintln(F("Server: Adafruit CC3000")); client.fastrprintln(F("")); client.fastrprintln(F("[")); for (i = 0; i < 99; i++){ if (arr[i] == 0) { continue; } str = String(arr[i]); str.toCharArray(b, 4); Serial.println(val); if (i > 0) { client.fastrprint(F(",")); } client.fastrprint(b); arr[i] = 0; } max_val = 0; client.fastrprintln(F("]"));
Webページでグラフを描画する
こうすることで、HTML5を表示しつつ、JSONデータとして明るさの変化を取得できるようになります。後はグラフとして描けば良いのですが、通常のグラフはいったん表示した後のデータ更新が苦手です。そこで使うのが後からデータ追加もできるhifiveのチャートライブラリになります。
getChartData = function() { return h5.ajax({ url: '/data.json', type: 'get', dataType: 'json' }); };
前回の記事はダミーデータを生成していましたが、今回は外部からの取得になるので、非同期処理を行う形になります。Promiseを使うことで大きな変更なく実装できるかと思います。
その結果が一番最初に表示した動画で、グラフ部分だけを抜き出すと次のようになります。

コンテンツ置き場
今回はJavaScriptファイルをすべてDropboxやWeb上で公開されているものを使っていますが、SDカードを使えばArduinoだけで完結させることもできるでしょう。
まとめ
ArduinoとCC3000を使うと無線LANでクライアント、サーバ両方になることができます(できないシールドもあります)。これと何らかの入力系シールドと絡めることができると、HTTPを使って簡単に送受信できるようになるでしょう。今回はデータ取得のみですが、逆にデータを送ることもできます。
IoTはWebの可能性をさらに広げる可能性を秘めていると思います。ぜひアイディアを形にしてみてください!
コメントは受け付けていません。