SlideShare une entreprise Scribd logo
1  sur  27
Télécharger pour lire hors ligne
WebSocketドロンくん
~その後~
『Webアプリによるフィジカルコンピューティング』
SAKURAボードユーザ会 あなたの心もSAKURA色 葉桜の木の下de交流会
2013/4/4
Yuuichi Akagawa
自己紹介
• Yuuichi Akagawa (あかがわ ゆういち)
• USBホストネタ大好き
• 本業は某SI企業でインフラ担当
• 電子工作やプログラミングは趣味での活動
• 仕組みを知ることが好きなので、最終的な作品に
至ることがほとんど無い
Copyright©2013 Yuuichi Akagawa 2
OSC2012東京Fallで発表しました
Copyright©2013 Yuuichi Akagawa 3
• WebSocket(Node.js + Socket.IO)を利用した遠隔制御
の実験
• Webアプリでフィジカルコンピューティングという提案
• みんなBluetoothでやってるからちょっと斜めで
• 当初はAndroid側をアプリとして実装したものの、
後にJavaScriptのみでイケるということに気付く
• 実用性よりも「ネタ」を重視で
• 昨年の東京Node学園祭2012に出せればウケたのに
ちょっとおさらい
Copyright©2013 Yuuichi Akagawa 4
WebSocketとは
• リアルタイムWeb
– 現在多く利用されている、XMLHttpRequest(XHR)による
AjaxポーリングやCometを代表とするロングポーリングで
はTCPハンドシェイクが都度発生したりHTTPコネクションを
長時間占有するなど、Webサーバの負荷が高いという欠
点がある。
– これを解決するためにHTML5の一部としてブラウザから
直接TCP接続を実現する独自プロトコルの策定が始まっ
た。
(現在はHTML5とは独立。RFC6455)
– 2011年末にようやく仕様確定し、メジャーなブラウザでは
問題無く利用できる状況にある。
Copyright©2013 Yuuichi Akagawa 5
主要ブラウザのWebSocketサポート状況
プラットフォーム ブラウザ バージョン
Desktop OS Internet Explorer 10以上
Firefox 6以上
Chrome 14以上
Safari 6以上
Opera 12.1以上
Android 標準ブラウザ 未サポート
Chrome 18以上
Firefox 7以上
Opera mobile 12.1以上
iOS Safari 6以上
Copyright©2013 Yuuichi Akagawa 6
ほぼどれでも使える。
Android版ChromeはOSが4.0以上で無いと動作しないが、Firefoxであれば2.2以上で
使えるので、なんとかなるかと。
Node.jsとは
• サーバサイドJavaScript実行環境
http://nodejs.org
Google V8 JavaScriptエンジン採用
シングルスレッド(JavaScriptだもんね)
イベント駆動(非同期)モデル
nvmというバージョンマネージャやnpmという
パッケージマネージャが揃っている
サーバサイドもJavaScriptでコードが書けるのは
素敵だと思う
Copyright©2013 Yuuichi Akagawa 7
Socket.IOとは
• クロスプラットフォームリアルタイムWebライブラリ
http://socket.io
Node.js用のライブラリ
サポートプロトコル
WebSocketが使えないブラウザでもXHR等に自動フォールバック
• WebSocket
• XHR
• Flash Socket
• JSONP Polling
Copyright©2013 Yuuichi Akagawa 8
Copyright©2013 Yuuichi Akagawa 9
WebSocketドロンくん
ドロンくんとは
今岡通博氏考案の
Android端末による
音声認識ロボット。
http://www.ospn.jp/press/20110516no10-useit-oss.html
DTMFによる制御や、
ブレッドボードで回路を
実装するというお手軽構成。
今回は音声認識の代わりに
WebSocket経由でコントロール
できるようにしました。
Copyright©2013 Yuuichi Akagawa 10
DTMF (Dual-Tone Multi-Frequency)
• 説明するまでもないとは思いますが、
電話の「ピ・ポ・パ」ってやつです
• 正式には「ITU-T勧告Q.24」
• これを4bitのI/Oとして取り出すDTMFデコーダ
を活用する(2個 ¥300)
高群(Hz)
1209 1336 1477 1633
低群(Hz) 697 1 2 3 A
770 4 5 6 B
852 7 8 9 C
941 * 0 # D
DTMFモータドライバ回路図
Copyright©2013 Yuuichi Akagawa 11
ブレッドボードにちょうど載る規模
Copyright©2013 Yuuichi Akagawa 12
Copyright©2013 Yuuichi Akagawa 13
コマンド送信
HTML5 ready Web Browser
(スマホのブラウザでもOK)
Socket.IO module
EC2
コマンド配信
(ブロードキャストも可能)
プロトコルは
WebSocket
or
XHR(Ajax)
DTMF
Node.js + Socket.IOを利用したWebSocketによる遠隔制御
DTMFデコーダ
+
モータードライバ
DTMF_0.ogg
.
.
.
DTMF_#.ogg
Firefox
var audio = new Audio(“/sounds/”+file);
audio.play()
DTMF音声ファイル
ダウンロード
サーバサイドコード例
Copyright©2013 Yuuichi Akagawa 14
var express = require('express‘) , routes = require('./routes');
var app = module.exports = express.createServer();
// Configuration
app.configure(function(){
app.set('views', __dirname + '/views');
app.set('view engine', 'jade');
app.use(express.bodyParser());
app.use(express.methodOverride());
app.use(app.router);
app.use(express.static(__dirname + '/public'));
});
app.configure('development', function(){
app.use(express.errorHandler({ dumpExceptions: true, showStack:
true }));
});
app.configure('production', function(){
app.use(express.errorHandler());
});
// Routes
app.get('/control', function(req, res) {
res.render('control', {title:'Socket.IO Control'});
});
app.get('/recv', function(req, res) {
res.render('recv', {title:'Socket.IO Receiver'});
});
// Socket.IO
var io = require('socket.io').listen(app);
var chats = [];
var sockets = {};
// broadcast function
function broadcast(method,message) {
for (var n in sockets) {
sockets[n].emit(method,message);
}
chats.pop;
}
io
.of('/in')
.on('connection', function(socket) {
sockets[socket.id] = socket;
socket.on('control.add', function(data) {
data.time = Date.now();
chats.push(data);
broadcast('control.add', data);
});
socket.on('disconnect', function() {
delete sockets[socket.id];
});
});
app.listen(8001);
app.js
これだけでWebサーバとして動作する。
ここがサーバ実装部分
・コネクション受付
・データ受信
・データ配信
全部やってる。
fork()
とか
pthread_create()
とか
なにそれって感じ。
操作画面ページコード例
Copyright©2013 Yuuichi Akagawa 15
script(src='http://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js')
script(src='/socket.io/socket.io.js')
script(type='text/javascript')
// add chat log
function addlog(data) {
var date = new Date(data.time);
console.log(date);
$('li#log').replaceWith( '<li id="log">' +
data.cmd
+ ' (' + date.getHours() + ':' + date.getMinutes()
+ ':' + date.getSeconds() + ')</li>');
}
var socket = io.connect('http://example.com:8001/in');
socket.on('control.add', function(data) {
addlog(data);
});
function send(data) {
socket.emit('control.add', {cmd:data} );
return false;
}
h3 WebSocketドロンくん
div
table
tr
td
input(type='button',class='btn',value='FwdL', onClick='send(1)')
td
input(type='button',class='btn',value='Forward', onClick='send(2)')
td
input(type='button',class='btn',value='FwdR', onClick='send(3)')
tr
td
input(type='button',class='btn',value='Turn L', onClick='send(4)')
td
input(type='button',class='btn',value='Stop', onClick='send(5)')
td
input(type='button',class='btn',value='Turn R', onClick='send(6)')
tr
td
input(type='button',class='btn',value='BkL', onClick='send(7)')
td
input(type='button',class='btn',value='Back', onClick='send(8)')
td
input(type='button',class='btn',value='BkR', onClick='send(9)')
div
ul
li#log
views/control.jade
Express(Webフレームワーク)+ Jade(テンプレートエンジン)を利用。
※http://example.com:8001/controlにアクセスするとこれを返す。
制御用ページコード例
Copyright©2013 Yuuichi Akagawa 16
script(src='http://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js')
script(src='/socket.io/socket.io.js')
script(type='text/javascript')
//DTMF map
var DTMFtable = [];
DTMFtable['1'] = '4';
DTMFtable['2'] = '5';
DTMFtable['3'] = '1';
DTMFtable['4'] = '6';
DTMFtable['5'] = 'D';
DTMFtable['6'] = '9';
DTMFtable['7'] = '8';
DTMFtable['8'] = '0';
DTMFtable['9'] = '2';
//DTMFaudio
var DTMFaudio = null;
var SOUND_PATH = "/sounds/";
// Get supported sound format
var AUDIO_EXT = (function(){
var audio = new Audio();
var ext = "";
if (audio.canPlayType("audio/ogg") == 'maybe') { ext="ogg"; }
return ext;
})();
//Sound play
var play = function(tone) {
// Get Filename
var name = 'DTMF_' + DTMFtable[tone];
var file_path = SOUND_PATH + name + '.' + AUDIO_EXT;
if(DTMFaudio != null){
DTMFaudio.pause();
DTMFaudio.currentTime = 0;
DTMFaudio = null;
}
DTMFaudio = new Audio(file_path);
DTMFaudio.play();
};
//Sound play
var play = function(tone) {
// Get Filename
var name = 'DTMF_' + DTMFtable[tone];
var file_path = SOUND_PATH + name + '.' + AUDIO_EXT;
if(DTMFaudio != null){
DTMFaudio.pause();
DTMFaudio.currentTime = 0;
DTMFaudio = null;
}
DTMFaudio = new Audio(file_path);
DTMFaudio.play();
};
var socket = io.connect('http://176.34.45.101:8009/in');
socket.on('control.add', function(data) {
play(data.cmd);
});
function send(data) {
socket.emit('control.add', {cmd:data} );
return false;
}
h1 HTML5 Delonkun
views/tank.jade ※http://example.com:8001/tankにアクセスするとこれを返す。
今後の予定
• Android端末側
Android端末のカメラの画像をWebSocketで
送信して操作画面に表示したい。
音声ファイル再生ではなく、Web Audio APIで
自力発音したい。
• サーバ側スクリプト
操作側と操作される側のペアリングを実現したい
Copyright©2013 Yuuichi Akagawa 17
で、それから半年が過ぎた。
Copyright©2013 Yuuichi Akagawa 18
要素技術の動向
• WebRTC (getUserMedia)
Desktop OSでのサポート状況はまずまず
AndroidではChromeβとOpera mobileで利用可能
• Web Audio API
Desktop OSのサポート状況はまずまず
Androidでは未だ使えない
iOSのSafariではサポート
→DTMFダイヤラの実装例あり!
Copyright©2013 Yuuichi Akagawa 19
主要ブラウザのサポート状況
プラットフォーム ブラウザ WebScoket
Audioの
AutoPlay
WebRTC
getUserMedia
Web Audio API
Desktop OS Internet Explorer ○ ○ × ×
Firefox ○ ○ ○ ×
Chrome ○ ○ ○ ○
Safari ○ ○ × ○
Opera ○ ○ ○ ×
Android 標準ブラウザ × × × ×
Chrome ○ × △ ×
Firefox ○ ○ × ×
Opera mobile ○ × ○ ×
iOS Safari ○ × × ○
Copyright©2013 Yuuichi Akagawa 20
2013/4/3現在
主要ブラウザのサポート状況
プラットフォーム ブラウザ WebScoket
Audioの
AutoPlay
WebRTC
getUserMedia
Web Audio API
Desktop OS Internet Explorer ○ ○ × ×
Firefox ○ ○ ○ ×
Chrome ○ ○ ○ ○
Safari ○ ○ × ○
Opera ○ ○ ○ ×
Android 標準ブラウザ × × × ×
Chrome ○ × △ ×
Firefox ○ ○ × ×
Opera mobile ○ × ○ ×
iOS Safari ○ × × ○
Copyright©2013 Yuuichi Akagawa 21
どちらかが両方サポートされてないと困る。
2013/4/3現在
○
○
○
×
×
×
×
×
×
モバイルでの対応はもう一息
• Desktop OSでは動作可能なレベル
• ○が2つ付いてるブラウザが無いんだな
• Androidはブラウザ毎にWebRTCかAudio APIの
どちらかしかサポートされていない
• しかも、Audioのautoplayに対応しているのは
Firefoxだけ
→その他ブラウザではユーザの介入が必要
Copyright©2013 Yuuichi Akagawa 22
Chromeβ for Androidに実装してみる
• 映像取得処理
getUserMedia()でカメラと接続
カメラからの映像をCanvasに描画
CanvasのデータをtoDataURL()でエンコード
上記で取得したデータをそのままWebSocketで送出
• 音声再生
コマンドに応じて、Audioのsrcにパスを設定
autoplay非対応なので、最初だけ再生ボタンを押す
必要あり
Copyright©2013 Yuuichi Akagawa 23
Copyright©2013 Yuuichi Akagawa 24
コマンド送信
HTML5 ready Web Browser
(スマホのブラウザでもOK)
Socket.IO module
さくらのVPS
コマンド配信
DTMF
WebSocketを利用したJavaScriptによる遠隔制御
DTMFデコーダ
+
モータードライバ
DTMF_0.ogg
.
.
.
DTMF_#.ogg
Chrome for Android
DTMF音声ファイルは
キャッシュマニフェストを
利用してローカルに保存
キャプチャ画像
送信
キャプチャ画像
配信
WebRTCを利用して
内蔵カメラからの
映像を取得する
急激な円安進行により、
AWSが割高になったので
さくらのVPSに引っ越し
まとめ
• JavaScriptだけでなんとか画像配信までできた
• なぜか画像がモノクロだけど
• ちょっと荷が重いので高レイテンシーだぞ
• あと半年くらい待てば、Androidでもフル機能が
サポートがされるのではないかと期待
• WebRTCがきちんと実装されれば、WebSocetで
はなくStreaming APIで滑らかな映像配信ができ
るはず
• 次回はWeb Audio APIでDTMFもね❤
Copyright©2013 Yuuichi Akagawa 25
マイコンもコンパイラもいらない
Webアプリでフィジカルコンピューティング
。*:゜☆ヽ(*’∀’*)/☆゜:。*。
Copyright©2013 Yuuichi Akagawa 26
おしまい
Copyright©2013 Yuuichi Akagawa 27

Contenu connexe

Similaire à Web socketドロンくん その後-

Real World Android Akka - 日本語版
Real World Android Akka - 日本語版Real World Android Akka - 日本語版
Real World Android Akka - 日本語版Taisuke Oe
 
PlayFramework1.2.4におけるWebSocket
PlayFramework1.2.4におけるWebSocketPlayFramework1.2.4におけるWebSocket
PlayFramework1.2.4におけるWebSocketKazuhiro Hara
 
FM音源をいじれるWebサービスを作った
FM音源をいじれるWebサービスを作ったFM音源をいじれるWebサービスを作った
FM音源をいじれるWebサービスを作ったCHY72
 
HTML5-pronama-study
HTML5-pronama-studyHTML5-pronama-study
HTML5-pronama-studyNaoya Inada
 
わんくま同盟名古屋勉強会18回目 ASP.NET MVC3を利用したHTML5な画面開発~クラウドも有るよ!~
わんくま同盟名古屋勉強会18回目 ASP.NET MVC3を利用したHTML5な画面開発~クラウドも有るよ!~わんくま同盟名古屋勉強会18回目 ASP.NET MVC3を利用したHTML5な画面開発~クラウドも有るよ!~
わんくま同盟名古屋勉強会18回目 ASP.NET MVC3を利用したHTML5な画面開発~クラウドも有るよ!~normalian
 
Titanium Mobile
Titanium MobileTitanium Mobile
Titanium MobileNaoya Ito
 
WebRTC meetup Tokyo 1
WebRTC meetup  Tokyo 1WebRTC meetup  Tokyo 1
WebRTC meetup Tokyo 1mganeko
 
リモートデバッグツール Weinerをつかってみた
リモートデバッグツール Weinerをつかってみたリモートデバッグツール Weinerをつかってみた
リモートデバッグツール WeinerをつかってみたMasakazu Muraoka
 
HTML5開発最前線
HTML5開発最前線HTML5開発最前線
HTML5開発最前線yoshikawa_t
 
フロントエンドの技術で始めるデスクトップアプリ
フロントエンドの技術で始めるデスクトップアプリフロントエンドの技術で始めるデスクトップアプリ
フロントエンドの技術で始めるデスクトップアプリTomotaka Kusaka
 
20110924 shizuoka azure-forsharing
20110924 shizuoka azure-forsharing20110924 shizuoka azure-forsharing
20110924 shizuoka azure-forsharingKazuki Aranami
 
jQuery MobileとPhoneGapでスマートフォンアプリ楽々クッキング
 jQuery MobileとPhoneGapでスマートフォンアプリ楽々クッキング jQuery MobileとPhoneGapでスマートフォンアプリ楽々クッキング
jQuery MobileとPhoneGapでスマートフォンアプリ楽々クッキングTakashi Okamoto
 
【de:code 2020】 「あつまれ フロントエンドエンジニア」 Azure Static Web Apps がやってきた
【de:code 2020】 「あつまれ フロントエンドエンジニア」 Azure Static Web Apps がやってきた【de:code 2020】 「あつまれ フロントエンドエンジニア」 Azure Static Web Apps がやってきた
【de:code 2020】 「あつまれ フロントエンドエンジニア」 Azure Static Web Apps がやってきた日本マイクロソフト株式会社
 
Endo kitura on_bluemix
Endo kitura on_bluemixEndo kitura on_bluemix
Endo kitura on_bluemixjoohoun song
 
WebSocket+Akka(Remote)+Play 2.1 Java
WebSocket+Akka(Remote)+Play 2.1 JavaWebSocket+Akka(Remote)+Play 2.1 Java
WebSocket+Akka(Remote)+Play 2.1 JavaKazuhiro Hara
 
さくらのIoT Platformを使ってみよう ~Developers in KOBE編~
さくらのIoT Platformを使ってみよう ~Developers in KOBE編~さくらのIoT Platformを使ってみよう ~Developers in KOBE編~
さくらのIoT Platformを使ってみよう ~Developers in KOBE編~法林浩之
 
さくらのIoT Platformを使ってみよう ~OSC大阪編~
さくらのIoT Platformを使ってみよう ~OSC大阪編~さくらのIoT Platformを使ってみよう ~OSC大阪編~
さくらのIoT Platformを使ってみよう ~OSC大阪編~法林浩之
 
6th oct2012 kobeit_webintents
6th oct2012 kobeit_webintents6th oct2012 kobeit_webintents
6th oct2012 kobeit_webintentsKensaku Komatsu
 

Similaire à Web socketドロンくん その後- (20)

Real World Android Akka - 日本語版
Real World Android Akka - 日本語版Real World Android Akka - 日本語版
Real World Android Akka - 日本語版
 
PlayFramework1.2.4におけるWebSocket
PlayFramework1.2.4におけるWebSocketPlayFramework1.2.4におけるWebSocket
PlayFramework1.2.4におけるWebSocket
 
Mvc conf session_5_isami
Mvc conf session_5_isamiMvc conf session_5_isami
Mvc conf session_5_isami
 
FM音源をいじれるWebサービスを作った
FM音源をいじれるWebサービスを作ったFM音源をいじれるWebサービスを作った
FM音源をいじれるWebサービスを作った
 
HTML5-pronama-study
HTML5-pronama-studyHTML5-pronama-study
HTML5-pronama-study
 
わんくま同盟名古屋勉強会18回目 ASP.NET MVC3を利用したHTML5な画面開発~クラウドも有るよ!~
わんくま同盟名古屋勉強会18回目 ASP.NET MVC3を利用したHTML5な画面開発~クラウドも有るよ!~わんくま同盟名古屋勉強会18回目 ASP.NET MVC3を利用したHTML5な画面開発~クラウドも有るよ!~
わんくま同盟名古屋勉強会18回目 ASP.NET MVC3を利用したHTML5な画面開発~クラウドも有るよ!~
 
Titanium Mobile
Titanium MobileTitanium Mobile
Titanium Mobile
 
WebRTC meetup Tokyo 1
WebRTC meetup  Tokyo 1WebRTC meetup  Tokyo 1
WebRTC meetup Tokyo 1
 
リモートデバッグツール Weinerをつかってみた
リモートデバッグツール Weinerをつかってみたリモートデバッグツール Weinerをつかってみた
リモートデバッグツール Weinerをつかってみた
 
HTML5開発最前線
HTML5開発最前線HTML5開発最前線
HTML5開発最前線
 
フロントエンドの技術で始めるデスクトップアプリ
フロントエンドの技術で始めるデスクトップアプリフロントエンドの技術で始めるデスクトップアプリ
フロントエンドの技術で始めるデスクトップアプリ
 
20110924 shizuoka azure-forsharing
20110924 shizuoka azure-forsharing20110924 shizuoka azure-forsharing
20110924 shizuoka azure-forsharing
 
Jqm20120804 publish
Jqm20120804 publishJqm20120804 publish
Jqm20120804 publish
 
jQuery MobileとPhoneGapでスマートフォンアプリ楽々クッキング
 jQuery MobileとPhoneGapでスマートフォンアプリ楽々クッキング jQuery MobileとPhoneGapでスマートフォンアプリ楽々クッキング
jQuery MobileとPhoneGapでスマートフォンアプリ楽々クッキング
 
【de:code 2020】 「あつまれ フロントエンドエンジニア」 Azure Static Web Apps がやってきた
【de:code 2020】 「あつまれ フロントエンドエンジニア」 Azure Static Web Apps がやってきた【de:code 2020】 「あつまれ フロントエンドエンジニア」 Azure Static Web Apps がやってきた
【de:code 2020】 「あつまれ フロントエンドエンジニア」 Azure Static Web Apps がやってきた
 
Endo kitura on_bluemix
Endo kitura on_bluemixEndo kitura on_bluemix
Endo kitura on_bluemix
 
WebSocket+Akka(Remote)+Play 2.1 Java
WebSocket+Akka(Remote)+Play 2.1 JavaWebSocket+Akka(Remote)+Play 2.1 Java
WebSocket+Akka(Remote)+Play 2.1 Java
 
さくらのIoT Platformを使ってみよう ~Developers in KOBE編~
さくらのIoT Platformを使ってみよう ~Developers in KOBE編~さくらのIoT Platformを使ってみよう ~Developers in KOBE編~
さくらのIoT Platformを使ってみよう ~Developers in KOBE編~
 
さくらのIoT Platformを使ってみよう ~OSC大阪編~
さくらのIoT Platformを使ってみよう ~OSC大阪編~さくらのIoT Platformを使ってみよう ~OSC大阪編~
さくらのIoT Platformを使ってみよう ~OSC大阪編~
 
6th oct2012 kobeit_webintents
6th oct2012 kobeit_webintents6th oct2012 kobeit_webintents
6th oct2012 kobeit_webintents
 

Web socketドロンくん その後-