3ステップで横並びのメニューで文字の長さの比率を保ちつつ均等配置にする方法

2021年7月22日

はじめに

ナビゲーションなどで横並びのメニューを作る時、横幅を均等にするか、各メニューのテキストの長さに合わせて長さを変えるか、みたいな感じになると思います(文章で説明するのが難しいですが)。

私はメニューに関してはflexboxをよく使用するのですが、後者を採用する際に少し調べる必要がありましたので、その方法を紹介したいと思います。

やりたいこと

  • 横並びのメニューを作る
  • メニュー内のテキストの長さに合わせて均等にメニューの長さを設定する

仕上がりイメージ

  • メ1
  • メニューその2その2
  • メニ3
  • メニュ

flexboxで横並びのメニューを作る

まずはflexboxで横並びのメニューを作ります。

メニューに関してはulliを使用しますが、liは端が分かりやすいようにborderを設定しています。

HTML

<ul class="test">
	<li>メニ1</li>
	<li>メニューその2</li>
	<li>メニュ3</li>
	<li>メニュー4</li>
</ul>

CSS

.test {
	list-style:none;
	display:flex;
	align-items: flex-start;
	justify-content: space-between;
}
.test li {
	border-right: 1px solid #000;
	border-left: 1px solid #000;
}

できあがったもの

  • メニ1
  • メニューその2
  • メニュ3
  • メニュー4

justify-content: space-between;を指定することで、メニューの間隔は均一になるのですが、メニュー自体の長さは変わりません。

メニューの横幅を調整する

メニューの長さを調整するためにCSSを追記します。
flexboxの子要素にflex: 1 0 auto;を追記することで、それぞれのメニュー割合に合わせた長さになります。

CSS

.test {
	list-style:none;
	display:flex;
	align-items: flex-start;
	justify-content: space-between;
}
.test li {
	flex: 1 0 auto;
	border-right: 1px solid #000;
	border-left: 1px solid #000;
}
	

できあがったもの

  • メ1
  • メニューその2その2
  • メニ3
  • メニュー4

flex: 1 0 auto;を指定することで、均等な配置ができました。

flexプロパティは左から順に

flex-glow「空間があった時に、どの割合で空間を割り当てるか」
flex-shrink「空間が足りない時に、どの割合で縮小させるか」
flex-basis「コンテナ内のflexの幅を指定」

を指定しています(正直ピンと来ていません)。
私はflex: 1とする事で、同じ割合で余白をシェアしているのかな~と理解しています。

とにかく、これでやりたいことはできたので、最後に見た目の調整をします。

リストの微調整をする

テキストが左寄せになっているのと、borderが重なって一部太く見えているのを調整します。

CSS

	.test {
	list-style:none;
	display:flex;
	align-items: flex-start;
	justify-content: space-between;
}
.test li {
	flex: 1 0 auto;
	text-align: center;
	border-right: 1px solid #000;
}
.test li:first-child {
	border-left: 1px solid #000;
}

できあがったもの

  • メ1
  • メニューその2その2
  • メニ3
  • メニュ

という訳で完成しました。

横幅全体をリンクにしたい時は?

メニューを作る、ということは、そのメニューは通常リンクにすると思いますので、リンクを張る場合についても少し補足しておきます。

上記は先ほど完成したソースにリンクタグを付けた物に、分かりやすいように背景色を付けました。

そのままリンクタグをつけたままだとリンク範囲はテキストのサイズのみとなりますので、borderの内側全てリンク範囲にしたい場合は、CSSに追記をします。

html

<ul class="test">
	<li><a href="#">メ1</a></li>
	<li><a href="#">メニューその2その2</a></li>
	<li><a href="#">メニ3</a></li>
	<li><a href="#">メニュ</a></li>
</ul>

CSS(追記部分のみ)

.test li a {
	display: block;
	line-height: 36px;
	background: #eeeeee;
	color: #333;
	text-decoration: none;
}

できあがったもの

adisplay: block;を指定することで、リンク範囲を枠の横全体に広げることができます。

また、縦にもリンク範囲を広げるため、line-heightで高さを持たせました。
高さを調整したい場合は、line-height以外にもpaddingで上下に値を指定する方法もあります。

追記

flexboxのalign-itemsをcenterあるいはstrechに設定すると、liの最後が少し下にズレて表示されました。

解消する方法はあるのかもしれませんが、現状私は見つけられていません。

現象の再現