【html/css/jQuery】アコーディオンメニューの開閉がカクカクになる【ハマりメモ】
2020/10/3
ブログを作った翌日からさっそく体調を崩したpullkawaです。
病気するとお金がかかっていやね。
アコーディオンを実装する中で、地味にハマったことがあったのでメモ。
■アコーディオンメニューの開閉アニメがカクカクする
「ひとつのメニューを開いたら、他のメニューは閉じる」というアコーディオンメニューを実装しました。
これ自体はサクッとできましたが、他部分のコードを書いているうちになぜか開閉時にカクカクするように。。
横の開閉マークは問題なく動作しているので、jQueryの記述ミスではなさそう。
結論から言うと、メニュー内の要素(.list_content)にtransition:allを指定してるのがよくなかったようです。
開閉するタイミングでstyleを変更してて、そこにtransition:allのアニメーションが干渉してしまっているらしい。
というわけで、今回は.list_contentのtransition設定を削除すると、スムーズにアニメーションするようになりました。
html/css/jQueryの記述は以下。
html
<div class="list_sample">
<h2>スムーズなアコーディオン</h2>
<ul class="list_good">
<li class="list_box">
<div class="list_title">
<p>アコーディオン</p>
</div>
<div class="list_content">
<p>
自然な動き
</p>
</div>
</li>
<li class="list_box">
<div class="list_title">
<p>アコーディオン</p>
</div>
<div class="list_content">
<p>
スムーズ<br>
スムーズ<br>
スムーズ<br>
スムーズ<br>
スムーズ<br>
スムーズ
</p>
</div>
</li>
</ul>
</div>
css
.list_sample{
margin:40px;
position: relative;
width: 60%;
max-width: 640px;
}
.list_box{
margin-bottom:20px;
border: 1px solid #aaa;
position: relative;
width: 100%;
}
.list_title{
padding:20px;
display: block;
position: relative;
text-decoration: none;
text-align: center;
cursor: pointer;
width: 100%;
}
.list_content{
display: block;
position: relative;
}
.list_title p, .list_content p{
position: relative;
margin-right: 5px;
line-height:22px;
}
.list_title p{
margin-right: 35px
}
.list_title p:before, .list_content p:before{
position: absolute;
color: #aaa;
font-size: 26px;
font-weight: bold;
left:-40px;
}
.list_title:before,
.list_title:after {
content: '';
display: block;
width: 16px;
height:1px;
background: #aaa;
position:absolute;
right:15px;
top:50%;
transform: translateY(-50%);
}
.list_title:after{
transform: translateY(-50%) rotate(90deg);
transition: 0.5s;
}
.list_title.active:after{
transform:rotate(0);
transition: 0.5s;
top:50%
}
.list_content{
display: none;
padding:12px;
}
$(function(){
$('.list_title').click(function(){
if($(this).next().is(':hidden')){
$('.list_content').slideUp('selected');
$(this).next().slideDown('selected');
$(this).addClass('active');
} else {
$(this).next().slideUp('selected');
$(this).removeClass('active');
}
});
});
参考にさせていただいた記事
http://b-nana.com/slidetoggle-not-working/
今回の場合、slideToggleではなくslideUp/slideDownだったのですが、同様の手段で解決できました。
今回の場合メニュー内の要素にtransitionを指定する必要はないので、
そもそも無駄なコードを書かないことが大事ですね。。
もし、開閉時にフェードイン・アウトなどさせたい場合は
こちらの記事にもあるように、transition-propatyを指定する必要がありそう。