Reputation: 899
I'm trying to achieve an effect where on the hover of an element A, an element B is fadeOut
and an element C is fadeIn
, both inside the element A.
That's what I tried:
$('.button').hover(function() {
info = $(this).find('.info');
download = $(this).find('.download');
info.stop().fadeOut(150, function() {
download.stop().fadeIn(150);
})
}, function() {
download.stop().fadeOut(150, function() {
info.stop().fadeIn(150);
})
})
.button {
background-color: orange;
padding: 10px;
width: 250px;
height: 40px;
line-height: 40px;
text-align: center;
margin-bottom: 10px;
}
.download {
display: none;
font-size: 17px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="button">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
<div class="button">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
<div class="button">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
<div class="button">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
Hovering one element at a time seems working fine but when you try to hover more elements concurrently the animation it starts to break.
Any solution? Other approaches are accepted. Thanks.
Upvotes: 1
Views: 41
Reputation: 7913
You are inadvertently creating global variables for info
and download
by omitting the var
, let
, or const
keywords. That means every function call is using and overwriting those variables. You need to create local variables in each function.
$('.button').hover(function() {
var info = $(this).find('.info');
var download = $(this).find('.download');
download.stop();
info.stop().fadeOut(150, function() {
download.stop().fadeIn(150);
})
}, function() {
var info = $(this).find('.info');
var download = $(this).find('.download');
info.stop();
download.stop().fadeOut(150, function() {
info.stop().fadeIn(150);
})
})
.button {
background-color: orange;
padding: 10px;
width: 250px;
height: 40px;
line-height: 40px;
text-align: center;
margin-bottom: 10px;
}
.download {
display: none;
font-size: 17px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="button">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
<div class="button">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
<div class="button">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
<div class="button">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
Upvotes: 1
Reputation: 9614
The main problem is to stop the animation before assigning another. This way there are no glitches:
$('.button').each(function(i) {
var thisButton = $(this);
var thisInfo = thisButton.find('.info');
var thisDownload = thisButton.find('.download');
thisButton.on('mouseenter', function(e) {
thisDownload.stop();
thisInfo.stop().fadeOut(150, function() {
thisDownload.stop().fadeIn(150);
});
}).on('mouseleave', function(e) {
thisInfo.stop();
thisDownload.stop().fadeOut(150, function() {
thisInfo.stop().fadeIn(150);
});
});
});
.button {
background-color: orange;
padding: 10px;
width: 250px;
height: 40px;
line-height: 40px;
text-align: center;
margin-bottom: 10px;
}
.download {
display: none;
font-size: 17px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="button">
<div class="button_inner">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
</div>
<div class="button">
<div class="button_inner">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
</div>
<div class="button">
<div class="button_inner">
<div class="info">
<i class="fas fa-download"></i> <strong>Mega Limited</strong> 1GB
</div>
<div class="download">Download</div>
</div>
</div>
Also on JSFiddle
Posting this because this may happen to skyline's answer:
Upvotes: 2