【実例あり】2017年の横並びレイアウトCSSはこれで決まり!【決定版】
※本記事は2016年2月14日に公開された記事を一部加筆・修正しています。
あけましておめでとうございます。
最近朝ジョナにハマってます山田でございます。
もくじ
横並びレイアウトのジレンマ
Web制作では毎度毎度お世話になる横並びレイアウトちゃんですが、float
にしろinline-block
にしろtable-cell
にしろ、横並びを実現するための色々な方法が巷では語られているものの、それぞれ一癖も二癖もあって扱いづらいのはみなさんご存知の通りです。
ということで、この度は僭越ながら2017年の横並びレイアウトCSSをこの場を借りまして決定させていただく運びとなりました。
ずばり、
2017年は「Flexbox」です!
異論は受け付けておりませんので、何卒ご了承の程よろしくお願い申し上げます。
Flexboxとは何や
CSS3 Flexible Box – W3Schools
こちらをご覧いただければお分かりになる通り、一言で申し上げるとflexibleなboxということですね。
あまりごちゃごちゃと基本的なことを説明するよりも、手っ取り早く実際のWebサイトを例として実例をいくつかご紹介させていただきます。
※以下、実際のHTML,CSSから一部を編集・抜粋して引用させていただいております。
実例
最も簡単な横並びメニュー
ご存知、天下のYahoo! JAPANさんですね。
検索窓上部の横並びメニューを見てみましょう。
どんな具合になっているかというと、
<ul> <li><a href="#">メニュー</a></li> <li><a href="#">メニュー</a></li> <li><a href="#">メニュー</a></li> </ul>
li { display: inline; padding: 0 5px; }
このように、li
をシンプルにdisplay: inline
、つまり普通のテキストと同じように並ばせ、padding
でメニュー間の余白を調整するシンプルな作りになっています。
最もシンプルに横並びレイアウトを実現したい場合にはこれくらいシンプルでもまったく問題ありません。
例えばカテゴリー一覧やタグ一覧をシンプルに表示させたい場合にはまだまだ使える基本オブ基本のテクニックですね。
:hover
でtext-decoration: underline
などしてあげてリンクされた要素であることを分かりやすくしてあげるとGOODです。
等幅×日本語+英語横並びメニュー
世界トップクラスのシェアを誇るレースタイム計測システム|Bee dancing
次は、コーポレートサイトなどでよく見かける「等幅×日本語+英語横並びメニュー」です。
こちらはどんな具合になっているかというと、
<ul> <li><a href="#"><span><b>メニュー1</b><small>MENU 1</small></span></a></li> <li><a href="#"><span><b>メニュー2</b><small>MENU 2</small></span></a></li> <li><a href="#"><span><b>メニュー3</b><small>MENU 3</small></span></a></li> </ul>
li { display: inline-block; vertical-align: middle; width: 16.6%; } li > a { text-align: center; display: table; width: 100%; padding: 10px; } li > a span { display: table-cell; vertical-align: middle; }
最も基本的な横並びレイアウトに比べるとすこし複雑になってはいますが、分解して見てみましょう。
まず、等幅でメニューを並べる部分はli
に対してwidth: 16.6%
(100% / 6 ≒ 16.6%)を指定しています。
※モダンブラウザではほとんどcalc()
をサポートしているため、width: calc(100% / 6)
でももちろんOKです!
そして、各メニューについては親であるa
にdisplay: table
を、子であるspan
にdisplay: table-cell
をそれぞれ指定することで垂直方向のセンタリング(vertical-align: middle
)を可能にしているわけです。
左寄せロゴ+右寄せメニュー
THE KEY HIGHLAND IZU [ザ キー ハイランド イズ]
こちらで採用されているヘッダーをFlexboxで実現してみます。
まずは、現状では
<header> <p> <a href="/">ロゴ</a> </p> <nav> <ul> <li><a href="#">メニューA</a></li> <li><a href="#">メニューB</a></li> <li><a href="#">メニューC</a></li> </ul> </nav> </header>
header { text-align: right; } p a { position: absolute; left: 20px; top: 20px; } nav ul li { display: inline-block; margin-right: 25px; }
このように、header
内は右寄せにしつつ、ロゴのみposition: absolute
で固定、横並びメニューはinline-block
で実現、という形です。
では、これをFlexboxで実現してみます。
<header> <nav> <ul> <li><a href="/">ロゴ</a></li> <li><a href="#">メニューA</a></li> <li><a href="#">メニューB</a></li> <li><a href="#">メニューC</a></li> </ul> </nav> </header>
ul { display: flex; li:first-child { margin-right: auto; } }
以上です。
本当にありがとうございました。
ありがとうCSS3、ありがとうFlexbox。
原理的には、ul
の中にli
を配置していくんですが、ul
の中で領域が余ってしまうので、li:first-child
のmargin-right
が自動で空いた領域を埋めてくれる、という考え方でOKです。
左寄せ+中央+右寄せメニュー
こちらで採用されているメニューをFlexboxで実現してみます。
まずは、現状では
<ul> <a href="#"><li>メニューA</li></a> <a href="#"><li class="blue_bnr">メニューB</li></a> <a href="#"><li>メニューC</li></a> <br class="cl"> </ul>
li { float: left; } .blue_bnr { margin: 0 14px; } .cl { clear: both; }
このように、各メニューをfloat: left
し、中央の要素で左右マージンを取るという形です。かつ、float
したので、事後はしっかり解除しないといけません。
各要素が等間隔というだけであればすべての要素で左右マージンを取ればいいのですが、このケースではメニューA、メニューCがそれぞれ左寄せ、右寄せとなっているため、このような対応となっています。
では、これをFlexboxで実現してみます。
<ul> <a href="#"><li>メニューA</li></a> <a href="#"><li>メニューB</li></a> <a href="#"><li>メニューC</li></a> </ul>
ul { display: flex; justify-content: space-between; }
以上です。
本当にありがとうございました。
ありがとうCSS3、ありがとうFlexbox。
justify-content: space-between
をコンテナ(この場合ul
)に当てることで、要素間のスペースが空いた領域を等幅で埋めてくれる、という考え方です。
アイテム(この場合li
)にjustify-content
を当ててしまうと何回リロードしても思い通りになってくれないので、注意が必要です!
上下左右中央揃え
こちらで採用されている上下左右中央揃えをFlexboxで実現してみます。
まずは、現状では
<div> <div class="inner"> <h1>ロゴ</h1> </div> </div>
div { position: relative; .inner { position: absolute; top: 52%; left: 50%; transform: translate(-50%,-50%); } }
このように、親要素を基準に中央配置したい要素をposition: absolute
とtransform: translate()
でうまいこと移動させています。
では、これをFlexboxで実現してみます。
<div> <div class="inner"> <h1>ロゴ</h1> </div> </div>
div { display: flex; align-items: center; justify-content: center; }
こんな具合に、目的の要素の大小等に関わらずこれだけですべて事足りてしまうのです!
まとめ
ここまで、実際のWebサイトを例に挙げて参りましたが、いかがでしょうか?
少ないサンプルでもFlexboxの魅力はお分かりいただけたことと思います。
今回挙げた例以外にも、高さが不確定の複数要素を同じ高さにできたり、コンテナいっぱいにアイテムを広げたり、ここでは紹介できないほど有能な子なんです!!!
要はfloat
もinline-block
もtable-cell
も要らないんです!!!!!
clearfix
忘れてレイアウト崩れ放題になることも、改行入れたせいで微妙にスペース空くことも、padding
は効くくせにmargin
はうまく効かないこともないんです!!!
2017年、今年こそFlexbox元年とします!!!!!!
それでは、アデュー