【AMP対応】CSSのみでアニメーションするアコーディオン

AMPサイトでもアニメーションするアコーディオンの実装方法を検討しました。

    AMPの仕様に対応してアニメーションするアコーディオンを作る

    AMPではアコーディオンに関して以下のような制約があります。

    • javascript使用不可
    • transitionまたは@keyframes…opasity/transformのみ対応

    こういった制約があるため、AMPでアコーディオンを実装するにはamp-accordionを使うか、チェックボックスを使うことになると思います。しかし、普通にやるとアニメーション無しでカクっと開閉する挙動になってしまうので、アニメーションしながらヌルヌルと滑らかに開閉するアコーディオンを頑張って検討したいと思います。

    デモ

    デモ1:amp-accrodion

    AMPでレイアウト用コンポーネントとして用意されているamp-accrodionを使用したパターン。こちらは、開/閉の切り替えのみでアニメーションさせることはできないようです。

    ほぼリファレンスのサンプルそのままなのでコードは省略。

    デモ2:CSSのみでアコーディオン

    ポイント

    • チェックボックスの状態で開閉
    • transform:translateでアニメーション
    • transform:scaleにするとpositionやz-indexを考えなくていいので楽だが、動作はtranslateの方がキレイ(好みの問題かも)
    • heightを指定せずにtransformだけを指定した場合、後ろの要素があるとボックスの高さ分の空間が空いてしまうのでやむを得ず指定
    • 全部IDを振る必要があるところがちょっと邪魔くさい

    サンプルコード

    HTML
    <div class="wrap">
    	<label class="title" for="box1">クリックして開閉</label>
    	<input type="checkbox" id="box1">
    	<ul class="toggle">
    		<li>なんらか</li>
    		<li>なんらか</li>
    		<li>なんらか</li>
    	</ul>
    </div>
    CSS
    .wrap{
    	overflow: hidden;
    }
    
    input{
    	display: none;
    }
    
    .title{
    	position: relative;
    	z-index: 2;
    }
    
    input + .toggle{
    	height: 0;
    	transform: translateY(-100%);
    	transform-origin: top;
    	transition: .3s;
    }
    
    input + .toggle li{
    	opacity: 0;
    }
    
    input:checked + .toggle{
    	height: auto;
    	transform: translateY(0);
    }
    
    input:checked + .toggle > li{
    	opacity: 1;
    }

    ※cssは要点のみで装飾は割愛。以下同。

    デモ3:ヘッダーメニューのアコーディオン

    ポイント

    • 基本はデモ2と同じ
    • 他の要素を気にしなくていいのでheightの指定は不要。かわりにposition:absoluteを指定する
    • よって閉じるときもきれいにアニメーションできる
    • 他の要素にz-indexが指定されている場合は、展開する要素にはそれより大きな値を指定しておく
    • 開閉でラベルの記号を切り替える処理もつけてみた。デモ2とはlabelとinputの位置関係とセレクタがちょっと変わる

    サンプルコード

    HTML
    <div id="header">
    	<input type="checkbox" id="menu">
    	<label class="title" for="menu">メニュー</label>
    	<ul class="toggle">
    		<li>なんらか</li>
    		<li>なんらか</li>
    		<li>なんらか</li>
    	</ul>
    </div>
    CSS
    #header{
    	position: relative;
    }
    
    input{
    	display: none;
    }
    
    .title{
    	position: relative;
    	z-index: 9999;
    }
    
    .title::before{
    	content: "▼";
    }
    
    input ~ .toggle{
    	position: absolute;
    	z-index: 9998;
    	width: 100%;
    	transform: translateY(-100%);
    	transition: .3s;
    }
    
    input:checked ~ .title::before{
    	content: "×";
    }
    
    input:checked ~ .toggle{
    	transform: translateY(0);
    }

    まとめ:腰が痛い

    今日は娘がこども園に初登園の日でした。はやいものですね。

    ところで送っていく途中に突然の腰痛に襲われて今とてもやばい状態です。今日はルルドで揉みほぐしつつ、コルセットでも巻いて休み休み過ごします。痛みが引いたら体幹のトレーニングをちゃんとやろう…。

    と、いうことで、AMPの制約は辛いですが、知恵と工夫で頑張りましょう。

    サポートが必要ですか?

    ご質問・お見積り依頼はお気軽にどうぞ

    お問い合わせはこちら
    シェア
    野良人 代表
    新免祥太
    1988年岡山生まれ。外食企業のWEB・EC担当を経験したのち、2013年12月より「野良人(のらんど)」の屋号で独立しWEBデザイン・プログラミングなどWEBサイト制作の工程全般を請け負っています。お気軽にご相談ください。
    広告
    次の記事(2018/04/17)
    SSL対応をやりました
    前の記事(2018/04/02)
    今月のブックマーク・読んだ本・反省など 2018/03
    記事一覧