これはTSUKURUBA Advent Calendar 2022 の3日目の記事です
Zennのみなさん、こんにちは!
株式会社TSUKURUBAで、Web フロントエンドエンジニアをしているkiiです
新卒で入社してもう1年半ほど経ちました。時間の進みを感じます🍂
※この記事は、Zennで書いた記事の転載記事です✍
- 、事例ないので、Sample code用意した割に、あまり読まれていなくて悲しかったので...
はじめに
2022年3月、Safari(15.4)にも待望の<dialog>
タグがやってきて、
モダンブラウザでは、Web標準の技術を用いて、簡単に良いモーダルUIを作れるようになる!と期待が高まったんじゃないでしょうか?
ただ現実的には、プロダクトやサイトの対応ブラウザバージョンを考慮すると、利用を躊躇してしまい、頑張ってJavaScriptを書いたり、既存のモーダルライブラリを利用して対応することも多いはず...😢
私も2022年5月に、Web Appのモーダルを新しく作ることになったのですが、
複数の実装方法で比較検討してみた所、
<dialog>
タグを利用して、マルチプラットフォーム対応で良い感じのモーダルUIが作れそうだと分かりました💡
実際にプロダクト開発に利用した所上手くいったので、その知見を共有したいと思います📝
🚩 記事の目的
<dialog>
タグを利用した良い感じのモーダルUIが作れる🧩
良い感じのモーダルUI
- マルチプラットフォーム対応📱🖥
- モーダルを操作している時に、背景がスクロールしない🖱
- 各インターフェースで操作しやすい⌨️
スコープ外のこと
- モーダルUI実装の方法比較検討
- 対応ブラウザや既存システムの性質によりけりなので、今回は省きます
- Scrapboxに軽く書いているので参考までにどうぞ。この記事の反応良ければ頑張ってまとめるかも...
- dialogタグの細かい利用方法
- わかりやすい神記事があるので、そちら見てください(自分も熟読しました)
- Building a dialog component
🏃♂️ 3行まとめ
- マルチプラットフォーム用に、dialog-polyfillを利用🤝
- 後ろがスクロールしないようにするために、body-scroll-lockを利用🖱👆🏽
- Code Exampleを用意したので、forkして遊んでみてください⚽️
📄今回、作りたいモーダルUIの要件定義
はじめに、今回作りたいモーダルUIの要件を整理します。
マルチプラットフォーム対応📱🖥
自身が提供するサービスの対応ブラウザ全てで、機能的、視覚的に問題なく利用出来る。
自身が提供するサービスの対応ブラウザは、各社それぞれ基準があると思います。
2022年現在だと、dialog
要素に対応していないブラウザ(Safari iOS ver15.3以前など)を使っているユーザーが一定数いるので、dialog
要素単体で実装することは難しそうです😢
モーダルを操作している時に、背景がスクロールしない🖱👆🏽
Dialog外の背景部分もスクロールで動いてしまっているgif
現在のdialog
タグを利用しただけだと、dialog内でスクロールした際、dialog外もスクロールされてしまいます。
これだと、画面全体を覆うUIを作った際、謎に画面がスクロールされている現象に直面します。困りますね😥
各インターフェースで操作しやすい⌨️🖱📱
キーボード⌨️、マウス🖱、タッチ📱で操作出来る。
WebAppを利用しているユーザーは、様々な環境下で利用しています。それぞれのユーザーに正しく体験を提供したい所です。
特に、キーボード⌨️時のフォーカスがモーダルUI実装時に見逃されがちな割に、体験を悪化させるので、以下の点に注意したいです。
- モーダルを開いた際、フォーカスをモーダルに「閉じ込め」て、Tab移動がモーダル内だけで行われる
- モーダルを閉じたら、フォーカスがモーダルを開くボタンにフォーカスが移動する
🪄実現のための工夫
マルチプラットフォーム対応にするため、Polyfillを利用🎁
dialog
要素に対応していないブラウザ(Safari iOS ver15.3以前など)に対応するために、polyfillで挟んでサポートします。
幸い、Chromeチーム製のdialog-polyfillがあるので、そちらを利用します。最終リリース日が、2021年1月であることが気になりますが、自分が気になる各ブラウザで動作確認した所、特に問題なかったので利用しました。
モーダルUIの裏側をスクロールしないようにするために、body-scroll-lockを利用🖱
dialog
タグやdialog-polyfillでは、裏側のスクロール周りの扱いについてサポートされていないため、別途対応が必要です。
スクラッチでサポートするか何かしらのライブラリを利用する必要があります。
そんな時に、body-scroll-lockを利用します。
依存パッケージ無しで、2021年6月更新ですが一定利用されており、自身でスクラッチで記述するよりメンテが楽そうです。
もし、パッケージを利用したくない場合は、大したcode量じゃないので、body-scroll-lockのコードをコピペして調整するのもいいかもしれません。
キーボード操作のための、フォーカスの位置調整⌨️
こちらの要件は、新しい<dialog>
の利用とdialog-polyfillで、ある程度カバー出来ました。(なんて便利なんでしょう✨)
⚽️Code Example
今回の説明したものを含めたシンプルな例を作りました。参考にしたり、forkして遊んでみてください🙏
案外、実装が簡単なことが分かると思います!
また、記事化出来なかった注意点も、codeのコメントで残しています。特にiOS限定のバグ対処やその他体験改善の工夫を盛り込んでいます📝
(時間あれば、もっと見た目綺麗にして、記事に説明増やしたかった...🥺)
気になる所あれば、コメント下さい〜
おわりに
今回の実装方法だと、
- モーダルUIライブラリのお作法を気にせずWeb標準のAPI使って、カスタマイズしやすい点、
- ユーザーの利用ブラウザのバージョンが上がったり、dialogタグの機能が拡張されると、ライブラリを剥がしてScriptのSizeを軽く出来る点、
が良いなと思っています!
今回の紹介で、dialog
要素を利用して、簡単に良い感じのモーダルUIが作れたら、嬉しいです。
おわり
参考リンク群と補足
- Adam Argyleさんが書いた神記事
-
dialog
タグを利用して、凄く良い体験のモーダルUI作って紹介してくれています - 概念ごとに紹介してくれていて、とても分かりやすいです✨まず、見て各概念理解するのオススメします!
- 一度、↑で紹介していますが、私がモーダルUI実装するにあたり、メモしていたノートです
- 他の実装方法とか気になればどうぞ