メガメニューのトグルがうまく行かない
ヘッダーにメガメニューを実装しようとしています。
下記スニペットのような実装をしているのですが、
- 初めて.nav(または.nav__item)をホバーした場合はslideDownで開く
- .nav内でかつ.nav__itemを行き来する場合はfadeInとhideで切り替え
- .navのエリアから出た場合はslideUpで閉じる
ということがやりたいです。
.nav内にいる場合は.navに.is-activeを付与して
is-activeがあれば.nav__itemをfadeIn,hideする
なければ.nav__itemをslideDown,slideUpする
上記の考えで大丈夫だと思っていましたが、.navを出た際にis-activeが消えるより早くitemのhideが実行されてしまいました。
delayやsetTimeoutでタイミングをずらせば出来そうではありますが、
あまりそういうことはやりたくないと感じました。
何か良い実装方法はありますでしょうか。
ご回答のほど、よろしくお願いいたします。
$(function(){
const $nav = $('.nav');
const $item = $('.nav__item');
$nav.hover(
function(){
$nav.addClass('is-active');
},
function(){
$nav.removeClass('is-active');
}
);
$item.hover(
function (){
const $this = $(this);
if($nav.hasClass('is-active')) $this.find('.megamenu__body:not(:animated)').fadeIn();
else $this.find('.megamenu__body:not(:animated)').slideDown();
},
function (){
const $this = $(this);
if($nav.hasClass('is-active')) $this.find('.megamenu__body:not(:animated)').hide();
else $this.find('.megamenu__body:not(:animated)').slideUp();
}
);
});
body {
margin: 0;
padding: 0;
}
.nav {
display: flex;
}
.nav__item {
flex: 1 1 auto;
height: 50px;
border: 1px solid #000;
}
.nav__item:hover {
background: gray;
}
.megamenu {
background: blue;
position: absolute;
top: 50px;
right: 0;
left: 0;
}
.megamenu__body {
display: none;
height: 100px;
background: blue;
color: white;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="nav">
<div class="nav__item">itemA
<div class="megamenu">
<div class="megamenu__body">contentA</div>
</div>
</div>
<div class="nav__item">itemB
<div class="megamenu">
<div class="megamenu__body">contentB</div>
</div>
</div>
</div>