HTML5 x Touch UI の UXを考える(補足)

昨日、ありえるえりあミニ勉強会#3 ~Sencha Touch で、「HTML5 x Touch UI の UXを考える」 を発表しました。 発表資料は こちら HTML5 × Touch UI の UX を考える

川野さんの「Sencha Touch - カスタムコンポーネントを作るためにおさえておきたい 10 のステップ」、森本さんの「About Sencha Architect」も非常に面白く、勉強になりました!Sencha 使ってない方でも勉強になるかと思いますので、ぜひ次回でも覗いてみて下さい!

そして、懇親会も楽しかった!まさかみんな Sublime Text 2 ユーザーになっているとはw 他にも Inkpod(Desktop版) を使ったことあるという方もいてびっくり!色々と刺激を受けることが出来ました。

帰って Ust で自分の発表見直してみたら、やたらと咳払いが多いですね。。。あと、ちょこちょこ移動したせいで音声が聞こえないところもチラホラ。せっかくマイク用意してもらったのに。。等々 お聞き苦しいところも多々有り申し訳ないです(−−; 今後改善したいと思います。

さて、このEntryでは、資料では書ききれなかった点、こぼれ話なんかを補足したいと思います。

Touch Position (p.5)

Nikkei BP さんの記事 iPhone/iPadに込められた「見えないデザイン」を参考にさせて頂きました。この話は、あくまで特許から実装されている機能を予測する、というもので、実際にはどうなのか検証された方もいました。日経BP『iPhone/iPadには”見えないデザイン”が込められてる』記事がホントかどうか検証してみた(エミュレータ編)

少なくともエミュレータでは6角形ではないようです。ただ、当たり判定についてはやはり動的に変わっているように見えます。iPhoneでソフトウェアキーボードを英語で表示して、「S」キー(少し左寄り)を連打すると、「Sa」と入力されます。Xperiaなどではキーピッチが見た目自体可変でしたけど、iPhoneは内部的に可変の可能性が十分にあると思います。

また、iOSでは押した場所(実際にタッチされた箇所)よりも確実に、少し上が認識されます。指で普通に使う分にはむしろ自然に狙った位置がポイントされます。タッチペンをつかってもあまり違和感を感じません。しかし、タッチペンを垂直に立てるなどすると、上向きにずれているのがよく分かります。逆さにしても同様。ボタンがタッチにしにくくなるのがわかります。

これは斜めに画面にタッチすることを想定し、指(またはペン)の軸の延長線上をタッチポイントとしたほうが自然と感じるのだと思われます。HW的なタッチエリアの楕円形状や扁平率から、傾きを検知し、ずらす量を調整、までしていればすごいんだけど、そこまではやっていないようです。

なお、Android(2.3,3.0,4.0で検証)ではこの上方向への補正は感じられません。恐らくAppleの特許が影響しているのではないかと思います。

 

Touch Feedback (p.6)

視覚フィードバックの他に、バイブレーションを使う方法もあります。Androidなんかでは結構使われています。iOS で使われていないのは特許のせいかポリシーかは分かりません。

Webで使うには、Vibration API というのが現在仕様策定中です。以下のように使えるようです。

  navigator.vibrate(1000);

ただ、2012/07/27現在、これが使えるのは Firefox Aurora Preview(Android 4.0以上)のみだとのことです。

 

Touch Event Specification (p.8)

jQuery の中の人のBlog  jQuery Blog: GETTING TOUCHY ABOUT PATENTS で、タッチイベントの歴史、現在の状況、将来、について非常に良くまとめられています。MSPointerが技術的には将来有望だとみている点など、興味深い話です。

 

Touch Event Interface (p.10)

W3Cの仕様で最後の Editor's Draft で大変興味深い仕様がありました。

Touch Events version 2 W3C Editor's Draft 14 November 2011

TouchEvent に radiusX, radiusY, rotationAngle というプロパティがあります。これは、タッチした範囲の楕円半径と、その傾き角度。つまり、タッチエリアのrawデータがとれるということです。

これが使えれば、上述の指の傾きを検知してずらす量を調整などもアプリ側でできるかもしれない。是非とも仕様に入れて欲しい!

 

TouchEvent のはまり所

touchEvent ではまりそうな所を2点。

touchEvent は現在タッチされているポイントを、touches、changedTouches, targetTouches というプロパティとして持っています。touches はすべてのタッチ、changedTouches は変更があった点、targetTouches はその要素上のタッチの配列として取得できます。

注意するのは、toucheend イベントの時、touches は空になっている、という事です。既に指が離れたため、現在タッチしている点は無いよ、ということなのだと思います。そのため、離れたタッチを取得するには changedTouches を使用します。

二つ目は、 2本以上で同時にタッチした時、touchstart イベントが1回の場合と2回発生する場合がある。ということ。

完全に同時にタッチしたときはtouchstart イベントは1回だけ発生し、changedTouchesに二つのタッチが入ります。わずかでもタイミングがずれると、touchstart イベントは2回発生し、それぞれ changedTouches に 1つずつ入ります。

なので、マルチタッチ操作を実装する場合、どちらでも動くように対応する必要があります。

 

GestureEvent (p.11)

ジェスチャーイベントの発生順序は少し癖があるため、注意が必要です。

GestureEvent Class Reference に詳しくありますが、タッチイベントとジェスチャーイベントの発生順序は以下のようになっています。

  1. touchstart: 1本目の指がタッチ。
  2. gesturestart: 2本目の指が触れると gesturestart が発生。
  3. touchstart: 2本目の指のタッチイベント
  4. gesturechange: 指を離さず、動かしたときに発生
  5. touchmove: 動いた指のタッチイベント
  6. gestureend: 2本目の指が離れたら(指が残り1本になったら)発生
  7. touchend: 2本目の指が離れたタッチイベント
  8. touchend: 最後の指が離れたタッチイベント

GestureEvent は touches プロパティをもっていません。そのため、タッチポイントを取りたいときは、TouchEvent で取得したものを保持しておく必要があります。

しかし、上記の順序 2. で、まだ2本目の指の touchstart イベントが来る前に、先にジェスチャーイベントが発生します。このとき、まだ touches は 1 つしかないのため、2つのTouchを取得できません。

 

User action event restrictions (p.21)

私が勝手に命名しました(^^; 

キーボードが出ない理由にはついては不明ですが、動画の再生については Apple から説明があります。

携帯が従量課金とかの可能性があるから、autoplayとautobufferは無効にしてるよ。ユーザが意図して再生を開始するまで、データはロードされないよ。

ということだそうです。

 

ちなみに、Sencha Touch (1.1の場合) でこれらを操作するために、ちょっとした裏技があります。Sencha Touch では通常ブラウザが出すクリックイベントは抑止して出ないようになっていますが、以下のコードをアプリ起動前に設定することで、デフォルトのクリックイベントを抑止しません。

  Ext.gesture.Manager.defaultPreventedMouseEvents = [];

これを設定すると、ブラウザが出すクリックイベントと、Sencah Touch がエミュレートしたものと2個発生します。Sencha Touch  がエミュレートしたクリックイベントは isSimulated フラグが true になるので、それでどちらか判断できます。

ブラウザが出す clickイベントの方で、これらの制限機能を使うことができるようになります。

 

Scroller (p.22)

iScroll は素晴らしいのですが、全画面でのスクロールのみになってしまいます。App Storeのサムネイルみたいに、部分的にスクロール対応したい時もあります。そういう時は以下のjQueryプラグインが便利です。

flickGal・・・iPhoneでフリックギャラリーを簡単に実装できるjQueryプラグインです 

ただ、惜しいかな縦/横スクロールのロックがありません。そこで、githubで公開されているものをフォークして、スクロール方向ロックオプションを付けたものをアップしました。

https://github.com/dsuket/flickGal

lockDirection を true にすると、 scrollMargin 分動くまでスクロールを待機し、動き出した後はその方向でロックします。