I have this tiny script:
var $totalHeight;
$(document).ready(function() {
$totalHeight = $('#sidebar-container').innerHeight();
$('.sidebar-heading').each(function() {
$totalHeight = ($totalHeight - $(this).outerHeight());
});
$('.sidebar-contents').each(function() {
if ($(this).hasClass('active')) {
$(this).css('height',$totalHeight);
}
});
$('.sidebar-heading').click(function() {
$('.sidebar-contents').slideUp().removeClass('active').addClass('inactive')/*.css('height','').removeAttr('style')*/;
$('.sidebar-heading').removeClass('active')/*.next().slideUp()*/;
$(this).addClass('active').next().addClass('active').removeClass('inactive').css('height',$totalHeight).slideDown();
});
});
I am pretty sure it's obvious what it is supposed to do.
My problem is: The first click on a ('.sidebar-heading') does not apply the desired $totalHeight to its sibling. The following clicks, it does. What am I doing wrong?
I have a draft-HTML with this code in action. I commented out those parts above to check, where the bug is, but couldn't figure it out anyway.
The slideUp() animation takes a while to run and cleans up all the heights and display styles after it gets done. This erases the setting you made in the next two lines.
Try waiting until slideUp() is done to do the other ones.
$('.sidebar-heading').click(function() {
var self = this;
$('.sidebar-contents').slideUp(undefined, function() {
$('.sidebar-heading').removeClass('active')/*.next().slideUp()*/;
$(self).addClass('active')
.next().addClass('active').removeClass('inactive')
.css('height',$totalHeight).slideDown();
}).removeClass('active').addClass('inactive')
/*.css('height','').removeAttr('style')*/;
});
I figured this out by running in Chrome with the debugger and noticing that the styles were changing in a wierd way. The first click on the 2nd heading would leave the height set on the 1st heading even though the code was clearing it. That means something was, maybe, setting it wrong. So I tried the above code on the jsFiddle someone set up. Lo and behold ...
You can also let the fx function set the height by itself to avoid conflict mentioned in @LeeMeador's answer.
Since the slideDown() doesn't accept any css value, we can use the animate() function directly instead.
$('.sidebar-heading').click(function () {
$('.sidebar-heading').removeClass('active');
$('.sidebar-contents').removeClass('active').addClass('inactive').stop().animate({ height: '0px' });
$(this).addClass('active').next().addClass('active').removeClass('inactive').stop().animate({ height: $totalHeight + 'px' });
});
In addition, use stop() before perform any animation to prevent weird behavior if you click the heading again while the previous animation haven't finished.
Modified jsfiddle: http://jsfiddle.net/z62tr/4/
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With