JSを使わずにアニメーションしながら展開するドロワーメニュー(スライドメニュー)の実装方法
Javascriptを使わずに、HTMLとCSSだけでアニメーションしながら展開するドロワーメニュー(スライドメニュー)を実装する方法です。
クリックでドロワーメニューを展開させる場合、jQuery等でちょっとしたプログラムを組むのが一般的だと思いますが、以下の方法では、スクリプトを一切使わずにドロワーメニューを出したり隠したりしています。
タイトルで「アニメーションしながら」とありますけど、これについてはおまけみたいなもので、あくまでも「ドロワーが出現するきっかけをCSSでやる」がメインになります。なので、アニメーションについてはあまり触れていませんがご了承ください。一応、アニメーションも全てCSSだけでやっていまして、こちらのエントリーで紹介しているものを使用しています。
JSを利用しないドロワーメニュー
まずは以下のデモをご覧ください。
デモ右上の「MENU」ボタンをクリックすることでドロワーメニューを開閉させることができます。また、閉じるときは左側のコンテンツ(サイドメニューじゃない)部分をクリックすることでも、閉じることができるようになっています。
:checked疑似クラスを利用
開閉には、HTML側でinput
タグのchecked
属性をクリックのポイントに設置し、CSSの:checked
疑似クラスで、チェックの有無によってそれぞれのスタイルを設定し開閉を行っています。
HTML
<!-- チェックボックス -->
<input type="checkbox" class="check" id="checked">
<label class="menu-btn" for="checked">
<!-- MENUボタン -->
</label>
<label class="close-menu" for="checked"></label>
<!-- ドロワー -->
<nav class="drawer-menu">
<!-- ここはメニューのリスト -->
</nav>
<!-- メインコンテンツ -->
<div class="contents">
<!-- ここはコンテンツ -->
</div>
HTMLでのポイントは、input
タグを一番上に配置しているところです。こうすることで、間接セレクタを利用することができ、:checked
疑似クラスとあわせて、後ろの要素(ドロワーとメインコンテンツ部分)のスタイルを変化させることができるようになります。
2つのlabel要素
input
タグ1つに対して、label
タグが2つありますが、input
とlabel
は、for
属性によって関連づけ(idを指定)ているため、実際には、この2つのlabel
によってチェックをコントロールすることができるようになっています。分かりづらいですけど、つまりはlabel
の部分をクリックすることで、チェックボックスの入り切りができるようになるということです。
2つのうち1つはMENUボタン部分に使い、もう1つはコンテンツ部分(閉じる時)で使っていて、それぞれCSSで位置や大きさ等を調整しています。
CSS
かなり長くなってしまうので、不要な部分やアニメーションの部分は割愛しています。全てのコードはcodepenにおいてありますので、そちらも合わせてどうぞ。
/* メインコンテンツ */
.contents {
width: 100%;
height: 100vh;
padding: 0;
margin: 0;
background: #f6bc60;
}
/* チェックボックスオンの時 */
.check:checked ~ .contents {
-webkit-transform: translateX(-300px);
-ms-transform: translateX(-300px);
transform: translateX(-300px);
}
/* ドロワー */
.drawer-menu {
position: fixed;
top: 0;
right: 0;
width: 300px;
height: 100%;
background: #222;
-webkit-transform: perspective(500px) rotateY(-90deg);
transform: perspective(500px) rotateY(-90deg);
opacity: 0;
}
/* チェックボックスオンの時 */
.check:checked ~ .drawer-menu {
-webkit-transform: none;
-ms-transform: none;
transform: none;
opacity: 1;
}
/* チェックボックスを非表示 */
.check {
display: none;
}
/* メニューボタン(label) */
.menu-btn {
position: fixed;
display: block;
top: 40px;
right: 40px;
width: 40px;
height: 40px;
background: #fff;
cursor: pointer;
z-index: 3;
}
/* コンテンツの閉じる。普段は非表示(label)*/
.close-menu {
position: fixed;
top: 0;
right: 300px;
width: 100%;
height: 100vh;
visibility: hidden;
opacity: 0;
}
/* チェックボックスオンの時 */
.check:checked ~ .close-menu {
visibility: visible;
opacity: 1;
z-index: 3;
}
チェックボックス自体はdisplay: none;
で非表示にしていますが、各label
要素と紐づけているため、クリックするとちゃんと機能するようになっています。
ポイントは、:checked
からの間接セレクタ(~)で、各要素にチェックボックスがオンされた時のスタイルを指定しているところです。この部分のスタイルによって、ドロワーメニューが開く際のエフェクトをアニメーションにしたりすることができるようになります。
ブラウザについて
Chrome、Safari、Firefoxのそれぞれ最新版、それとIE11で問題なく表示されていることを確認しています。
:checked
疑似クラスが使えるのは、IE9からとなるらしいので、古いブラウザを考慮しなければいけない場合は、使用を控えたほうがいいでしょう。
おわり
チェックボックス本来の使い方ではないものの、個人的にはありだと思っています。ドロワーメニューの開閉に限らず、様々に応用できるテクニックなので、今後、色々とやってみたいですね。
古いブラウザを気にしなくて良い場合は、積極的に使っていきたいと思っています。