フォームとモーダルは相性が悪いよ という話
たまーに Web デザインプロトタイプに、以下の要件が盛り込まれているときがあります。
フォームに確認ボタンを追加し、確認ボタンを押下されたときに確認モーダルを表示する
確認モーダル内に表示されている送信ボタンが押下された場合、フォームの送信を行う
一件至極まっとうで普通なフローに見えますが、html 的にはアンチパターンだったりします。
以下ざっくりと説明をば。
モーダルを挟まず、送信ボタンがそのまま付随している場合、html 的には以下のようなイメージで組まれます。
<body>
<form onSubmit="handleSubmit">
<input />
<button type="submit">送信</button>
</form>
</body>
送信ボタンを押下したら、form の onSubmit に設定されている関数、上記の例で言うところの handleSubmit が実行されます。
対して、モーダルを挟む場合、以下のようなイメージに変わります。
<body>
<form>
<input />
<button type="button">確認</button>
</form>
<div>
<button onClick="handleSubmit" type="button">送信</button>
</div>
</body>
送信ボタンをラップしている div がモーダルとなります。
form タグから onSubmit がなくなり、モーダル内の送信ボタンが押下されたとき、submit の処理を実行する、といった感じですね。
form に onSubmit が設定されておらず、form 内の値を form 外から操作せざるを得ない状態になっちゃうので、あんまり気分は良くないですよね。
と、それならこう書けば良いじゃん!と思う方もおられると思います。
<body>
<form onSubmit="handleSubmit">
<input />
<button type="button">確認</button>
<div>
<button type="submit">送信</button>
</div>
</form>
</body>
パット見良さそうに見えますが、実はこれもアンチパターンでして。
モーダルなどを作る場合は、なるべく body に近い要素の直下において DOM の出し分けを行うのが基本となります。
モーダルを生成する以上、そのモーダルには z-index
やら position: fixed
やらがたくさん設定されると思います。
となると、そういった要素を持つ DOM は body 直下などに生成されるのが自然ですよね。
なので、結果的に form にモーダルをかませるのはあまり賢い方法ではない、ということになります。
Google など大手のフォームを思い出してみると、送信ボタンはそのまま押せるけれど、項目が正しく入力されていない場合はエラーが表示される、というのが一般的かなーと。
あとは送信ボタンの上にチェックボックスをつけて、全てチェックされないと送信ボタンが押せない、みたいなところも多いですよね。
逆に、送信ボタンがモーダルに乗っかっているサイトは、何かあるのかなーと判断できる基準でもあります。
やっぱり大手の真似をしてベタに、かつシンプルに作ることが大切だよなーと思う、今日このごろです。