こんにちは。今回はよく紹介される中央揃えテクニックについて思うところがあったので、最新の中央揃えを解説します。
よく紹介される、position: absolute;にしてleft: 50%; transform: translateX(-50%);を指定するような馬鹿げた記述は忘れてください。
中央揃えはflexでやれ
現代のCSSにおいてはスマートに中央揃えができる方法がいくつかあります。もちろん横方向だけでなく縦方向も自在です。直感的にも分かりやすい方法で言えば、display: flex;とjustify-content、align-itemsを組み合わせて使うのがおすすめです。
まず上下左右の中央に揃える場合を見て見ましょう。見た目は次の通り。
コードは以下になります。
<div class="Container">
<div class="Box"></div>
</div>
.Container {
width: 100%;
height: 300px;
background-color: skyblue;
display: flex;
justify-content: center; /* 横方向 */
align-items: center; /* 縦方向 */
}
.Box {
width: 100px;
height: 100px;
background-color: pink;
}
親要素にdisplay: flex;を指定し、横方向の位置を指定するjustify-contentと縦方向の位置を指定するalign-itemsをそれぞれcenterにすることで中央に配置しています。
それぞれflex-start、center、flex-endという3つの値が指定でき、以下の表のように配置できます。
flex-start | center | flex-end | |
justify-content | 左 | 中央 | 右 |
align-items | 上 | 中央 | 下 |
例えばjustify-content: flex-end; 、align-items: flex-start; なら右上に配置されます。
下にデモを作ったので、それぞれの値をセレクトボックスで変えてみてください。値の組み合わせによって9方向の位置に要素を配置することができます。
親要素のサイズ、子要素のサイズ、ブロックかインラインかなど余計なことを一切考えずに中央揃えができるので本当におすすめの方法です。ほぼ全ての場合においてこの方法さえ覚えておけば問題ありません。
モーダルウィンドウなど、他の要素と関係なく画面の中央に配置したい場合でも.Containerを画面いっぱいに広げた上でposition: fixed;にして使えば問題ありません。
.Container {
position: fixed;
top: 0;
left: 0;
width: 100vw;
height: 100vh;
background-color: skyblue;
display: flex;
justify-content: center;
align-items: center;
}
.Box {
width: 100px;
height: 100px;
background-color: pink;
}
もしくはgridでやれ
display: grid; でも同様に中央揃えができます。親要素をdisplay: grid; にした上でjustify-itemsとalign-itemsを指定してください。justify-contentではないので注意してください。
start | center | end | |
justify-items | 左 | 中央 | 右 |
align-items | 上 | 中央 | 下 |
ちなみにこちらの場合はjustify-itemsとalign-itemsを一括指定できるplace-itemsというプロパティがあり、以下のように書くと上下左右中央に子要素を配置することができます。
.Container {
display: grid;
place-items: center;
}
position: absolute; left: 50%; transform: translateX(-50%); がなぜダメなのか
レイアウト崩れの原因になりやすい
まずposition: absolute;などは安易に使うとレイアウト崩れの温床になります。positionプロパティがabsoluteやfixedの場合、要素が通常のフローから外れます。具体的には、
- 要素が重なる
- 親要素がその要素の横幅、高さを認識しなくなる
などが起こります。
そういうプロパティなので当然と言えば当然ですが、要素の中央揃え目的で使うと考えると面倒ごとが増えてますね。
また、ただ要素をposition: absolute;にすると親要素ではなくページの左上が基準点になってしまいます。必ず基準にしたい親要素をposition: relative;にして使ってください。これを忘れて数時間を失う初心者を何人も見てきました。
コードの意味が分かりにくい
パッと見でposition: absolute; left: 50%; transform: translateX(-50%); とあった時に、これが中央揃えを意味していることは正直分かりにくいですよね。実際Xの投稿でも「なんでこれで中央に行くか分からない」という声が散見されます。
一応解説すると、leftにおける%指定は親要素の横幅に対する割合を示し、translateの%指定は要素自身の横幅に対する割合を示します。
left: 50%;だけだと、50%地点を始点に要素が配置されてしまうので右に行き過ぎてしまいます。その分をtranslateX(-50%);とし、要素の半分だけ左に戻すことで中央揃えを実現しています(下画像参照)。
縦方向についても考え方は同じです。
広く用いられたコードではあるので知っておくべきだという意見も分からなくはないです。しかしflexのように明確に中央揃えができるプロパティがある中わざわざこんなものを持ち出す方が問題と言えます。
古い方法を使って可読性を下げるより、「center」という分かりやすい単語で指定できるjustify-contentやalign-itemsの方がメンテナンス性も上でしょう。
そもそもハック的なやり方であり時代遅れ
この手法、配置に関するプロパティが十分になかった頃の遺物とも言える代物です。いまだに要素の横並べにfloat: left; を使っているのと同レベルです。
総合的に見て、可読性・メンテナンス性・バグの起きやすさなど、コードの品質的にどれをとってもおすすめしません。
left: 50%; transform: translateX(-50%); はやめよう
というわけで中央揃えの書き方についてでした。ぱっと見で分からない記述はやめて、分かりやすい記述を優先しましょう。
display: flex;についてさらに詳しく書いた記事もあるので合わせてご覧ください。
こういったテクニックをもっと知ってレベルアップしたい方はぜひこちらの本で勉強してみてください。僕がフリーランスで活動する中で培ったコーディングテクニックを厳選したおすすめの本です。
コメント