Reputation: 1796
I'm creating a custom jQuery carousel and its coming out really well :)
But found a little glitch / bug in it. When you click on Prev / Next like a normal user do, it works fine but when you click on it like a robot with hyper speed, it slides blank spaces.
I'm sharing my code here and also providing the JSFiddle Link. It would be nice if someone could help me out or give me better suggestions to make it more pro :)
HTML:
<div id="my_carousel">
<div class="carousel">
<ul>
<li style="background:red;"></li>
<li style="background:green;"></li>
<li style="background:blue;"></li>
<li style="background:purple;"></li>
</ul>
</div>
</div>
CSS:
* {
padding: 0;
margin: 0;
}
#my_carousel {
padding: 0 15px;
position: relative;
height: 100px;
display: inline-block;
}
.carousel {
overflow:hidden;
position: relative;
height: 100px;
}
.carousel ul {
list-style: none;
position: absolute;
left: 0;
top: 0;
}
.carousel ul li {
width: 100px;
height: 100px;
float: left;
}
.controls {
position: absolute;
top: 50%;
left: 0;
margin: -10px 0 0;
width: 100%;
}
.prev {
float: left;
}
.next {
float: right;
}
JQUERY:
(function ($) {
$.fn.my_carousel = function (defaults) {
// Default settings
var settings = $.extend({
layout: 'hort',
visible_items: 2,
item_width: this.find('li').width(),
reel_width: this.find('li').length
}, defaults);
if (settings.layout === 'hort') {
// Adding Prev/Next links
this.find('.carousel').after('<div class="controls"><a href="#" class="prev"><</a><a href="#" class="next">></a></div>');
// Setting window / reel /controls width
this.find('.carousel').width(settings.item_width * settings.visible_items);
this.find('ul').width(settings.reel_width * settings.item_width);
// Slide control
$('.controls a').click(function () {
var pos = $(this).parents(this).find('ul').offset().left;
if ($(this).hasClass('next')) {
if (pos >= ((settings.item_width * settings.visible_items) - (settings.reel_width * settings.item_width) + settings.item_width)) {
$(this).parents(this).find('ul').animate({
left: '-=' + settings.item_width + 'px'
}, 200);
} else {
return false;
}
} else {
if (pos <= 0) {
$(this).parents(this).find('ul').animate({
left: '+=' + settings.item_width + 'px'
}, 200);
} else {
return false;
}
}
});
}
};
})(jQuery);
$('#my_carousel').my_carousel();
Upvotes: 0
Views: 77
Reputation: 3387
This behavior is caused by your if()
statement, which is checking your item's left position.
When you quickly click several times on the previous button (for exemple), left value is still animated and has not reached 0
and the next click is happening again.
Please see a solution I can give you using kind of pagination:
//ADDED CODE
var currentIndex = 1;
var totalItem = $('.carousel ul li').length;
var totalIndex = totalItem - 1;
// Slide control
$('.controls a').click(function () {
var pos = $(this).parents(this).find('ul').offset().left;
if ($(this).hasClass('next')) {
//REMOVED
//if (pos >= ((settings.item_width * settings.visible_items) - (settings.reel_width * settings.item_width) + settings.item_width)) {
if (currentIndex != totalIndex) { //ADDED
$(this).parents(this).find('ul').animate({
left: '-=' + settings.item_width + 'px'
}, 200);
currentIndex++;//ADDED
} else {
return false;
}
} else {
//REMOVED
//if (pos <= 0) {
if (currentIndex != 1) { //ADDED
$(this).parents(this).find('ul').animate({
left: '+=' + settings.item_width + 'px'
}, 200);
currentIndex--;//ADDED
} else {
return false;
}
}
});
Edit 1:
Since you want to be able to manage number of displayed items, here is the updated code.
I added var displayedItems = 4;
to the very top of the code that is used in "Default settings" :
// Default settings
var settings = $.extend({
layout: 'hort',
visible_items: displayedItems,
item_width: this.find('li').width(),
reel_width: this.find('li').length
}, defaults);
And also used to calculate totalIndex
:
var totalIndex = totalItem-(displayedItems-1);
Upvotes: 3