スマホ用Webアプリづくりには限界がある。
この2ヶ月間、あえてiPhoneからTwitterアプリを消して、ChromeでTweetをしていた。
Twitterのスマホ向けWebアプリはネイティブアプリに比べてあまりにも操作感が悪かった。
Facebookも同様だった。
TwitterとFacebookという、おそらく世界で最も金と時間と技術がかかっていそうなWebアプリでもこの程度の体験になってしまうのかとがっかりした。
そこで、不満点の指摘と提言をしたい。
題材としてTwitterを取り上げるが、決してTwitterの悪口ではない。
むしろ普段スマホ向けWebアプリを作ってる身からすると、この苦労は大変良くわかるし、Twitter Webアプリはすごく良くできていると思う。
だから「世界最高峰の人たちでもこうなるんだぞ、今のWebには色々足りないものがあるんだぞ」ということを言いたい。
不満点
Pull To Refreshの判定がきつい
Pull To Refresh(以下PtR)とは、画面を下向きに引っ張ることでコンテンツを更新できる機能である。
多くのアプリに採用されている。
Chromeもそのジェスチャでページのリロードができるようになっている。
Twitterネイティブアプリはそれでタイムラインを更新することができる。
Twitter Webアプリは画面の中央を下向きに引っ張ると同じことができる。
しかし、タブメニューのあたりを下に引っ張っるとTwitterがJSで実装したPtRではなくChrome側のPtR(以後ネイティブPtR)が反応してしまう。
中央を引っ張った場合でも、タイミングによってはネイティブPtRが反応してしまうことがある。
Context Menuが意図せず立ち上がる
コンテキストメニューとは、PCの場合右クリックした時に出るメニューだ。
コピーや印刷などの操作が選べる。
スマホのブラウザの場合、テキストを長押しするとそのメニューが出てくる。
これが厄介者である。時々そんなつもりがなくても立ち上がってしまうことがある。
iPhoneの場合、急に文字列選択UIが出てくる。
キャンセルしようとして適当な場所を押すといいねを押してしまったりする。
別の画面に行ってから戻ってくるとスクロール位置が保存されていない
この手順で再現する
1.タイムラインで結構下の方までスクロールする
2.適当なツイートをタップしてTweet詳細画面を開く
3.戻る
4.さっきと違い場所にいる
ポップアップを開いている状態で後ろの画面がスクロールしてしまう
Tweet右上のドロップダウンメニューを開いた状態で上下にスワイプすると後ろで本体がスクロールされている。
ちなみに、多くのWeb開発者は、現在のスクロール位置を変数に保存した上で後ろの画面をposition:fixedにするということをしていると思う。
画像のトリミングができない
意外なことにTwitter のWebアプリではトリミングができない。
これはわからなくもない。
自分もWebアプリでトリミング機能を作ったが、必ずちょっと残念な感じになる。
まず、結構カクつく。また、左から右にスワイプすると、ブラウザの戻るジェスチャにイベントを取られてしまうことがある。ピンチイン・ピンチアウトも指の置き場が悪いと画面全体が縮小・拡大してしまう。
なんかウニャウニャ動く
ネイティブアプリの場合、アプリの外枠が決まっており、それが動くことはない。スワイプで物の大きさが勝手に変わったりしない。
しかし、Webアプリの場合、アプリの外枠や各要素が不自然にリサイズされたりオーバースクロールしたりする。
良かった点
悪口ばかり言っては申し訳ないので補足する。
無限スクロール
無限スクロールとは下にスクロールすると、どんどん新しいコンテンツをサーバーから取ってきて下に追加していってくれる機能だ。
普通にスマホWebアプリで無限スクロールを実装するとかなり怪しい挙動をする。
これだけスムーズに無限スクロールが動いているということは、中の人が結構工夫したと思われる。
ちなみに僕はIntersection Observerとそのポリフィルをつかった。多分パフォーマンス悪いと思う。
提言
前提になる問題として、スマホのブラウザはバテリー節約のためOnTouchMoveEventとOnScrollEventの発生頻度を抑えている。
また、スマホブラウザがネイティブで持っているジェスチャUIは、多くのWebページ閲覧に必要なものだと思うので無くせとは言えない。
なので、スクロールやスワイプのイベントを取らなければ実現できないようなことは、だいたいHTML標準に入れておいてほしい。
HTMLにPtR要素を追加してほしい
また、Document内にPtR要素がある場合はネイティブPtRをオフにしてほしい。
無限スクロール要素もHTMLに追加してほしい
同上
画像トリミング画面を呼び出せるAPIを作って欲しい。あるいは矩形選択要素のようなものをHTMLに追加してほしい。
同上
レイヤーの概念とSegue的な概念を入れてほしい
今の所多くの開発者はBodyの中に適当なDivを作り、スタイル属性のpositionやz-indexを使って階層を表現している。
あるいは諦めて別Tabを開いたりする。
しかし、思い切ってサブBodyのようなものを作れるようにしてはどうか(というかDialog要素はどこへ行った)
その要素へのイベントは一切上要素に伝播されないようにしてほしい。
その要素はHistoryAPIとうまい感じに連携して戻る・進む・リロードの動作が違和感ないようにしてほしい。
スクロール位置はサブBodyごとに持って欲しい。
ちなみに、cssのoverflow:scrollを使えばいいのでは? と思った人がいるかもしれないが、最大スクロール位置を超えてスクロールすると微妙な感じになるのでちょっとストレス。
ContextMenuをオフにすることをベストプラクティスにしてほしい
これは既存のJSでできる。しかし、嫌悪感がある人も多いだろう。その人は多分おっさんである。
2000年代、まだWebページのプラクティスが確立してなかった頃、JSでマウスイベントやスクロールイベントを謎フックをしているサイトが跋扈し大変うざがられていた。
マウスにカモメがついて着たり、右クリックをすると画面がチカチカしだすなどの演出を盛り込んでる人がいたのだ。
そのため、「極力ブラウザの標準UIを妨げない」というのがお約束になった。
しかし、スマホにおいてTwitterのようなWebアプリでコンテキストメニューを出せるメリットはないだろう。
ここは思い切って「文書度合いが低くアプリ度合いが高いスマホ向けWebページはコンテキストメニューをオフにするべき」ということをベストプラクティスとしていくべきではなかろうか。
根本的な問題
WebからスマホのネイティブUIコンポーネントを作れるようにしてほしい。