canvas で矢印キーを受け取るサンプル - フォーカスが当たっているときにキーの動作を奪ってページがスクロールしないように
canvas で矢印キーを受け取るサンプルです。矢印キーに対応して四角が動きます。
window.addEventListener('load', function() { var canvas = document.getElementById('game-screen'); var x = 50, y = 50; var ctx = canvas.getContext('2d'); var keyFlags = 0; setInterval(function(){ if(keyFlags & 1) x -= 5; if(keyFlags & 2) y -= 5; if(keyFlags & 4) x += 5; if(keyFlags & 8) y += 5; ctx.clearRect(0, 0, canvas.width, canvas.height); ctx.fillRect(x, y, 20, 20); }, 33); document.addEventListener('keydown', function(e) { var keyCode = e.keyCode; if(37 <= keyCode && keyCode <= 40) { keyFlags |= 1 << (keyCode - 37); } }, false); document.addEventListener('keyup', function(e) { var keyCode = e.keyCode; if(37 <= keyCode && keyCode <= 40) { keyFlags &= ~(1 << (keyCode - 37)); } }, false); }, false);
さて、これには問題があって...。上下キーを押したときにページがスクロールしてしまうんです。FlashやJavaアプレットのようにフォーカスしていたらキーの動作を奪ってページがスクロールしてしまわないようにしたいので、方法を探ってみています。
追記 (2008-11-13T17:57:13+09:00)
iframe を作成してその中に canvas を突っ込んでみました。
Firefox では問題なく動作しますが、Safari, Google Chrome や Opera では親ウィンドウがスクロールされてしまいます。また、なぜか Opera では表示されるのが 1 秒くらい遅くなってしまいます。
追記 (2008-11-13T18:46:40+09:00)
Safari, Google Chrome で親ウィンドウがスクロールされてしまう問題は、iframe内のdocumentのkeydownイベントでe.preventDefault();を実行し、iframe内のtextareaのkeydownイベントでe.stopPropagation();を実行することで解決しました。
Firefox で iframe 内のカーソルが progress になっていたのが気になっていたのですが、 doc.write("
Opera で親ウィンドウがスクロールされてしまう問題と、なぜか表示が 1 秒くらい遅れる問題は未解決です。
追記 (2008-11-13T20:26:02+09:00)
Opera で表示が 1 秒くらい遅れる問題は、 doc.close(); を追加したことにより解決したみたいです。あとは Opera で親ウィンドウがスクロールされてしまう問題だけ。むー。
追記 (2008-11-13T21:29:46+09:00)
Opera で親ウィンドウがスクロールされてしまう問題も解決しました!
「opera スクロール keydown preventDefault」みたいにググって以下の記事にたどりつきました。
両ブラウザで共通させるためには keypress を用いる。
ultra blue:JavaScript : Opera と Firefox でのキーイベントの違い
document.addEventListener( 'keypress', function(e){
e.preventDefault();
}, false);
ということで、keypressイベントでpreventDefaultを呼べばよかったようです。
これでOperaでも親ウィンドウがスクロールしないようになりました。