CSSだけで作るamazon風な縦型メガメニュー

先日、「CSSだけで作る動きのあるドロップダウンメニュー」という記事のコメント内で、amazonのようなメガメニューをCSSだけで作れないのかというコメントいただきましたので作ってみました。

amazon-like-mega-menu.png

サンプルを用意していますのでぜひご覧ください。

CSSだけですのでメニューの現れ方など若干違います。box-shadowとborder-radiusはIE8以下で、矢印を作るための擬似要素はIE7以下で非対応ですが、メニューとしての機能は果たせます。

では解説していきます。

HTML

まずはHTMLから説明します。長いのでメニュー1つ分のみ載せます。コード全体はサンプルの下に載せていますのでご覧ください。

<div id="menu-tittle">メニュー</div>
<ul id="sample">
  <li>
    <a href="#">メインカテゴリー1</a>
    <ul>
      <h3>メインカテゴリー1</h3>
      <li><a href="#">サブメニュー1-1</a></li>
      <li><a href="#">サブメニュー1-2</a></li>
      <li><a href="#">サブメニュー1-3</a></li>
      <li><a href="#">サブメニュー1-4</a></li>
      <li><a href="#">サブメニュー1-5</a></li>
    </ul>
  </li>
</ul>

menu-tittleの部分は上に付いている黒いタブ風になっている部分です。id「sample」直下のli要素を繰り返すことでメニューの数を調整します。

初期状態は現れるメニューが1列ですが、クラス「big」を追加すると2列になります。

<li>
  <a href="#">メインカテゴリー3</a>
  <ul class="big">
    <h3>メインカテゴリー3</h3>
    <li><a href="#">サブメニュー3-1</a></li>
    <li><a href="#">サブメニュー3-2</a></li>
    <li><a href="#">サブメニュー3-3</a></li>
    <li><a href="#">サブメニュー3-4</a></li>
    <li><a href="#">サブメニュー3-5</a></li>
    <li><a href="#">サブメニュー3-6</a></li>
    <li><a href="#">サブメニュー3-7</a></li>
    <li><a href="#">サブメニュー3-8</a></li>
    <li><a href="#">サブメニュー3-9</a></li>
    <li><a href="#">サブメニュー3-10</a></li>
    <li><a href="#">サブメニュー3-11</a></li>
    <li><a href="#">サブメニュー3-12</a></li>
  </ul>
</li>

サンプルでいうとカテゴリー3と5が大きい方になります。

CSS

続いてCSSです。いつものように最初に全体を載せて、後で個別に解説します。

#menu-tittle{
  width: 80px;
  margin: 20px 0 0 20px;
  padding: 8px 10px 5px 10px;
  border-radius: 3px 3px 0 0;
  background: #2f3842;
  color: #fff;
  font-size: 13px;
  text-align: center;
}
#sample{
  position: relative;
  z-index: 100;
  width: 200px;
  margin: 0 0 20px 20px;
  padding: 10px 0;
  border-top: 3px solid #2f3842;
  border-radius: 0 0 3px 3px;
  box-shadow: 3px 3px 5px #aaa, -3px 3px 5px #aaa;
  font-size: 14px;
  background: #fff;
  color:#333;
}
#sample li{
  list-style-type : none;
  margin: 0;
  padding: 0;
  color:#333;
}
#sample li a{
  position: relative;
  display: block;
  padding: 10px 15px;
  color: #0e2236;
  text-decoration: none;
  line-height: 15px;
}
#sample > li:hover > a{
  color: #e47911;
  font-weight: bold;
}
#sample ul li a:hover{
  color:#e47911;
  text-decoration: underline;
}
#sample > li:hover > a:after{
  display: block;
  position: absolute;
  content: "";
  top: 50%;
  right: 5px;
  width: 0px;
  height: 0px;
  margin-top: -8px;
  border: 8px solid transparent;
  border-left-color: #aaa;
}
#sample ul{
  display: none;
  position: absolute;
  top: -3px;
  right: -217px;
  width: 200px;
  height: 280px;
  margin: 0;
  padding: 10px;
  border-top: 3px solid #2f3842;
  border-radius: 0 0 3px 0;
  background: #fff;
  box-shadow: 3px 3px 5px #aaa, 3px 0px 3px #ccc inset;
}
#sample li:hover ul{
  display: block;
}
#sample ul.big{
  right: -417px;
  width: 400px;
}
#sample ul.big li{
  float: left;
  width: 200px;
}
#sample ul h3{
  padding: 5px 5px 5px 15px;
  margin: 0;
  color:#e47911;
  font-size: 16px;
  font-weight: normal;
}
#sample ul li a{
  padding: 8px 15px;
}

結構長くなってしまった。。ひとつひとつはそんなに難しいこともないので諦めずに最後までお付き合いいただければと思います。

最初から表示されているメインカテゴリー1~8の部分を「メインメニュー」、マウスを乗せて現れるサブメニュー1~ の部分を「サブメニュー」と読んでいきますのでよろしくお願いします。

タブ風な「メニュー」の部分
#menu-tittle{
  width: 80px;
  margin: 20px 0 0 20px;
  padding: 8px 10px 5px 10px;
  border-radius: 3px 3px 0 0;
  background: #2f3842;
  color: #fff;
  font-size: 13px;
  text-align: center;
}

左側marginの20px(メインメニューと同じ値)、下側marginの0px以外は自由に変更しても大丈夫です。border-radiusは大きすぎないのが今時かなと思います。

メインメニュー全体
#sample{
  position: relative;
  z-index: 100;
  width: 200px;
  margin: 0 0 20px 20px;
  padding: 10px 0;
  border-top: 3px solid #2f3842;
  border-radius: 0 0 3px 3px;
  box-shadow: 3px 3px 5px #aaa, -3px 3px 5px #aaa;
  font-size: 14px;
  background: #fff;
  color:#333;
}

最初から見えているメインメニュー全体です。

サブメニューが開いた際、元々あるコンテンツとかぶることになります。かぶった際サブメニューが優先的に表示されるよう「z-index」を指定します。かぶる可能性のある部分には「position: relative」と「z-index: 値」が必要になります。z-indexの値はメニューの方が大きければいくつでも大丈夫です。

リストのリンク
#sample li{
  list-style-type : none;
  margin: 0;
  padding: 0;
  color:#333;
}
#sample li a{
  position: relative;
  display: block;
  padding: 10px 15px;
  color: #0e2236;
  text-decoration: none;
  line-height: 15px;
}

li要素はmargin、paddingを0にして、その中にあるa要素でpaddingを指定することでリンクを押しやすくします。a要素のline-heightはメニュー全体の高さを計算しやすくするために設定しています。

マウスを乗せたときのリンク
#sample > li:hover > a{
  color: #e47911;
  font-weight: bold;
}
#sample ul li a:hover{
  color: #e47911;
  text-decoration: underline;
}

マウスを乗せたときの変化についてです。

最初の方がメインカテゴリー1~8にマウスを乗せたときの変化になります。「#sample > li> a:hover 」でもよさそうですが、これだとマウスを乗せたときに現れるサブメニューにマウスが移ったときに元の色に戻ります。

後の方はサブメニューのリンクにマウスを乗せたときの変化です。下線が表示されるようにしています。

マウスを乗せたときに現れる矢印
#sample > li:hover > a:after{
  display: block;
  position: absolute;
  content: "";
  top: 50%;
  right: 5px;
  width: 0px;
  height: 0px;
  margin-top: -8px;
  border: 8px solid transparent;
  border-left-color: #aaa;
}

メインカテゴリー1~8にマウスを乗せたときに現れる矢印の表示になります。ボーダーを使って三角形を表現しています。上下真ん中に表示したいときの「top: 50%;」と「margin-top: -8px;(高さの半分の値)」の組み合わせは結構使えます。

マウスを乗せたときに現れるサブメニュー
#sample ul{
  display: none;
  position: absolute;
  top: -3px;
  right: -217px;
  width: 200px;
  height: 280px;
  margin: 0;
  padding: 10px;
  border-top: 3px solid #2f3842;
  border-radius: 0 0 3px 0;
  background: #fff;
  box-shadow: 3px 3px 5px #aaa, 3px 0px 3px #ccc inset;
}#sample li:hover ul{
  display: block;
}

マウスを乗せたときに現れるサブメニューの内容です。初期状態では「display: none;」で表示しないようになっていて、メインカテゴリー1~8にマウスを乗せたときに表示されるようになります。

メインメニューと上の位置(top)、高さ(height)を合わせる必要があります。topの値は、ゼロにするとメインメニューのボーダーの下になりますので、ボーダーの太さ分(3px)上に配置するため「top: -3px;」とします。

高さはメインメニューの高さを計算して指定する必要があります。具体的にはこんな感じです。

(#sample li aの上下paddingの合計 20px + line-height 15px
 × メインメニューの数 8つ = 280px

今回は「#sample」と「#sample ul」の上下paddingの合計が同じですが、違う場合は高さが変わってきますので、その分heightで調整が必要です。

あと、「right: -217px;」は、以下のように計算します。

width 200px + 左右paddingの合計 20px - 3px

メインメニューの右下の丸みを見えなくするために3px引いています。

ともにわずらわしい計算になりますが、メインメニューとサブメニューの位置関係をそろえるにはこれしか考えつかなかったです。

大きい方のサブメニュー
#sample ul.big{
  right: -417px;
  width: 400px;
}
#sample ul.big li{
  float: left;
  width: 200px;
}

2列に表示されるサブメニューの設定です。サンプルでいうと、メインカテゴリー3と5にマウスを乗せたときのサブメニューです。

ここの「right: -417px;」の計算方法は先ほどと同じです。

サブメニュー全体の中身
#sample ul h3{
  padding: 5px 5px 5px 15px;
  margin: 0;
  color:#e47911;
  font-size: 16px;
  font-weight: normal;
}
#sample ul li a{
  padding: 8px 15px;
}

サブメニュー内のh3要素やリスト内のリンクの設定です。

さいごに

ということで長々と説明してみました。自分いうのもなんですが色々詰まっているので結構勉強になると思います。

できだけ詳しく説明したつもりですので、サイトに合わせてカスタマイズしていただければと思います。

かなりコンテンツが多いサイトでないとこれほど大きなメニューは必要ないかもしれませんが、お役に立てればうれしいです。

フィードやTwitterで最新情報をチェック
follow us in feedly
この記事に付いているタグの最新記事一覧
loading...
コメント
jQuery無しでもここまで出来るのかと驚きました。興味を持って色々調べるきっかけになりました。ありがとうございます。細かい点でjQueryを使ったほうがユーザビリティが高いと勉強になりました。例を上げると メインカテゴリー1にマウスオーバーし、サブメニュー1-5へ直線でマウスを動かすとメインカテゴリー2の領域をまたぐのでそこが開いてしまう。AmazonライクのメニューはjQueryでそこを制御しているようです。確かにストレスなくていいですね~ CSSもjQueryも両方すごいな~ (CSSだけでも余白を小さくすればデザインは落ちますがなんとかなるかなw)
【2013/09/11 16:56】 | ネコ #- | [edit]
ネコ さん

コメントありがとうございます。

おっしゃるとおりAmazonのメガメニューは
サブメニューが切り替わるのに若干タイムラグが
あるように設計されています。

その辺はCSSでは難しそうです。
メインメニューの幅を小さめにする、
上下のpaddingに余裕を持たせる、
などの工夫が必要だと思います。
【2013/09/12 06:40】 | 管理人 #E2ywrYdA | [edit]
参考に貼ってあったHTMLとCSSを載せたのですが、アレみたいになりません。サブメニューもメニューの所に出てきてしまします。どうしてか分かりますか?
【2013/12/16 17:17】 | おはやう #- | [edit]
報告です。

#sample ul li a:hover{{

上の括弧が多い。


括弧を一つ消せばなおります。

【2014/01/19 13:07】 | れおにゃ #- | [edit]
れおにゃ さん

ご指摘ありがとうございます。
修正させていただきました。

今後もよろしくお願いします。
【2014/01/20 05:36】 | 管理人 #E2ywrYdA | [edit]
いつもブログ拝見しております。
匿名で書き込ませていただきますm(_ _)m

今後、私の制作するウェブサイトに、貴サイトが紹介している
ドロップダウンメニュー(CSS)や見出しデザイン(CSS)を採用させていただきますm(_ _)m

うまく使いこなせるかちょっと心配ですが(笑)
【2014/03/08 04:31】 | 匿名 #- | [edit]
匿名 さん

コメントありがとうざいます。
ウェブサイト作成のお役に立ててうれしいです。

今後もよろしくお願いします!
【2014/03/08 09:28】 | 管理人 #E2ywrYdA | [edit]









※コメントはご意見ご感想や間違いのご指摘等にしていただけますようお願いいたします。コメントを確認する時間がなく、技術的なご質問をいただいても答えできません。申し訳ございませんがご理解のほどお願いいたします。

Recent Entry
Popular Entry
  • このエントリーをはてなブックマークに追加