Reputation: 524
I'm trying to create an infinite slider using jquery. My page has some tags, with the width equal to the window width.
I want to slide every image after 10 seconds, and when the last image comes up and it's time for the first image to show, I want it to come still from the right.
Now I created a div with a big width, 10000px to hold my unordered list of images and they have display:none. My question is why when I'm giving margin-left: -1000px for one list item, the images appear to overlap one above the other, instead of appearing one after the other. I tried to take a screenshot but I don't know what is happening with my dropbox.
This is my CSS:
.slider {
position: relative;
height: 498px;
/*display: inline-block;*/
overflow: hidden;
}
.slider-list {
/*display: inline-block;*/
float: left;
padding: 0;
margin: 0;
width: 10000px
/*height: 496px;*/
}
.slider-list li{
display: inline-block;
/*float: left;*/
/*width: 100%;*/
height: 496px;
z-index: 1;
And here is my HTML:
<div class="slider">
<ul class="slider-list">
<li><img class="homepage-img"src="images/homepage.jpg"></li>
<li><img class="homepage-img"src="images/image1.jpg"></li>
<li><img class="homepage-img"src="images/image2.jpg"></li>
<li><img class="homepage-img"src="images/image3.jpg"></li>
<li><img class="homepage-img"src="images/image4.jpg"></li>
</ul>
The div with the class .slider will close after some more elements.
UPDATE:
This is my jQuery code since I written this post:
$(document).ready(function(){
slide();
});
slide = function() {
var img = $('.homepage-img');
var content = $('.slider-content');
var slider = $('.slider-list');
var elements = $('.slider-list li').children();
var auto_slide_speed = 100;//ms
var timer;
var i = 0;
img.width($(window).width());
$("li").width($(window).width());
img.height($('.slider-list').height());
content.height($('.slider-list').height());
var img_width = $('.slider-list li').outerWidth();
console.log($('.slider-list li').length);
console.log(elements);
//calculam margin-left = -latimea unei imagini
// while(1)
// {
var left = parseInt(slider.css('margin-left')) - img_width;
for(i = 0; i <= $('.slider-list li').length; i++)
{
console.log(i);
slider.animate({
"margin-left": "+=" + left},
1500,
function() {
// $('.slider-list li:last').after($('.slider-list li:first'));
// $('slider').css({'margin-left' : '0px'});
});
// left = left + left;
// $('slider li').append($(elements[i]).clone());
}
console.log(i);
}
With this, my slider ony goes as far as my list goes. How do I append the first item after the last item and so on so it can be infinite?
Upvotes: 2
Views: 8800
Reputation: 10047
I've made two simple jquery plugins for that:
I recommend the item slider because the items are forced to be aligned, and it's simpler in the end.
Now to answer your question: How do I append the first item after the last item and so on so it can be infinite?
You could just display your slider items two times (or more) in a row. Given your html code:
var jSliderList = $(".slider-list");
var jSliderOriginalItems = $("li", jSliderList); // keep track of this one
function init(){
jSliderList.append(jSliderOriginalItems.clone()); // should work, not tested
}
Then with css, you would narrow the slider to the width of your choice.
Suggestions:
I would suggest that you append a page rather than just one item.
A basic approach would be to encapsulate things into functions, like this:
slideToRight()
appendItemsToTheRight()
removeUnecessaryItemsToTheLeft()
slide()
To perform the slide, you could use css transitions. In your css, put something like this:
.sliderContainer {
transition: transform 2s ease;
}
And then in your js code, to slide, just use a function such as:
function moveSlider(the_offset) {
jSliderContent.css({
transform: "translate3d(" + the_offset + "px, 0px, 0px)"
});
}
Now to actually append an item, you could use a renderItem function to generate them, instead of cloning things.
Upvotes: 0
Reputation: 196296
If you are targeting modern browsers that support transitions and transforms i would do it that way..
Demo at http://jsfiddle.net/gaby/dbLu5/
jQuery
var slides = $('.slider-list li'); // cache a reference to the slides
setInterval(function(){
var current = slides.filter('.current'), // find slide in view
next = current.next(); // find next slide
if (!next.length){next = slides.first();} // loop if at last slide
slides.removeClass('off'); // reposition already viewed slides to the right
current.removeClass('current').addClass('off'); // set current slide to animate left
next.removeClass('off').addClass('current'); // set next slide to slide in view
}, 10000); // set the interval
CSS (you need to add vendor prefixes for the transform and transition properties)
.slider-list {
position:relative;
padding: 0;
margin: 0;
overflow:hidden;
height: 496px;
}
.slider-list li {
width:100%;
height: 100%;
display: block;
z-index: 1;
transition:transform 1s;
transform:translateX(100%);
left:0; top:0;
position:absolute;
overflow:hidden;
}
.slider-list li.current{
transform:translateX(0%);
z-index:100;
}
.slider-list li.off{
transform:translateX(-100%);
z-index:100;
}
Upvotes: 3
Reputation: 2984
Here is a FIDDLE that will get you started.
Put all your images in a hidden div
Clone them and put them in the visible div
Animate the image by changing the left margin
You can adjust the time between images by the set interval function
You can adjust the slidein time by the animate time.
Because it's an infinite loop, I put the button in to stop the animation any time you want.
JS
var pictxtnumber = 1;
loadpictxt(pictxtnumber);
var fadeintime = 500;
animatediv();
function animatediv()
{
var number = 0;
var interval = setInterval(function() {
pictxtnumber = pictxtnumber + 1;
if(pictxtnumber > 6)
{
pictxtnumber = 1;
}
loadpictxt(pictxtnumber);
$('#stopanim').on('click', function(){
clearInterval(interval);
});
}, 1000);
}
function loadpictxt(num)
{
$('.picturediv').html('');
$(".hiddenimage img:nth-child(" + num + ") ").clone().appendTo('.picturediv');
$('.picturediv img').css('margin-left', '100px');
$('.picturediv img').animate({marginLeft: "0"}, 100);
}
Upvotes: 1