Hi
Does anyone know how I would go about adding a counter (i.e. 1/12, 2/12, 3/12 etc.) to this slideshow?
http://www.switchonthecode.com/tutorials/jquery-creating-a-slideshow
Also, I would like the option to have another button that takes the user back to the first image at any given point during the slideshow.
Any help on this would be really appreciated.
Thanks!!
The following should work for creating a counter:
New HTML
<div id="slideshow-area">
<div id="slideshow-scroller">
... slideshow holder html (same as in the example) ...
</div>
<div id="slideshow-previous"></div>
<div id="slideshow-next"></div>
<div id="slideshow-counter"></div>
<div id="slideshow-reset"></div>
</div>
Additional CSS
#slideshow-counter {
width: 100%;
height: 50px;
position: absolute:
left: 0;
bottom: 0;
}
Additional Javascript
function updateCounter() {
$('#slideshow-counter').html(currentSlide + "/" + totalSlides);
}
function showFirstSlide() {
currentSlide = 1;
updateContentHolder();
updateButtons();
updateCounter();
}
Then add updateCounter(); in a new line after updateButtons() is called in document.ready, showPreviousSlide and showNextSlide
Also in the $(document).ready() function you'll need to add the following line: $("#slideshow-reset").click(showFirstSlide)
Related
So, what i want to do is to create a buttons in a specified place of my image, also these buttons will be another images. I complicated it all a lot and I just have no idea what to do next and how to.
Main concept is:
I have that slider with image 1 and image 2, when it gets pressed the image will be changed to image 3 and slider will be paused. After image 3 is displayed, there will be image buttons to appear on that image 3.
I dont know if i can use position: absolute; and position: relative; or if i am just doing it wrong. My problem is that i cant use css to give that <div id="slider"> the relative effect because i want to put in there images with absolute effect.
Sorry for complicating it all so much but i don't really know how to explain it simplier, also english is not my main language.
All the code in short
So here is my JS
<script>
var numer = Math.floor(Math.random()*2)+1;
function schowaj()
{
$("#slider").fadeOut(500);
}
function zmienslajd()
{
numer++; if (numer>2) numer=1;
var plik = "<img src=\"drzewo" + numer + ".png\" />";
document.getElementById("slider").innerHTML = plik;
$("#slider").fadeIn(500);
setTimeout("zmienslajd()", 5000);
setTimeout("schowaj()", 4500);
}
</script>
And here is HTML
<body onload="zmienslajd()">
<div id="slider">
</div>
</body>
Also CSS
#slider
{
background-color: #b3ffb3;
width: 90%;
height: 800px;
float: left;
}
Thanks for any help in advance.
I'm new to JavaScript and I'm trying to build a web page and I've 3 images of that product in my sidebar and one main image in the middle now I want to get the sidebar image in the middle when a user clicks on that sidebar image. I don't know how to go about this. I've already tried couple of ways which I've found online, one of them is this
1. How to swap image and video to another div?
But these are not working out for me.
What you have to do is save both images in a variable and then swap them. Look at the example below
var imgleft,
imgcenter,
$center = $(".center img");
$(".sidebar img").click(function(){
imgleft = $(this).attr("src");
imgcenter = $center.attr("src");
$center.attr("src", imgleft);
$(this).attr("src", imgcenter);
});
.sidebar{
position: absolute;
top: 0;
width: 70px;
height: 100%;
background: red;
}
.center{
width: 80px;
height: 80px;
margin:25% auto;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="sidebar">
<img src="http://placehold.it/70x70">
<img src="http://placehold.it/70x60">
<img src="http://placehold.it/70x50">
</div>
<div class="center">
<img src="http://placehold.it/70x40">
</div>
You can use javascript's event handling (on each of your sidebar images) to solve this problem. First add the following java script code in your html:
<script type="text/javascript">
function changeToImage1(){
if(centerImage.src != "[1st-image-url.*]"){
centerImage.src = "[1st-image-url.*]";
}
}
function changeToImage2(){
if(centerImage.src != "[2nd-image-url.*]"){
centerImage.src = "[2nd-image-url.*]";
}
}
function changeToImage3(){
if(centerImage.src != "[3rd-image-url.*]"){
centerImage.src = "[3rd-image-url.*]";
}
}
</script>
Then you can simply add the above functions in the onClick attributes of your three sidebar div's accordingly. This can be done like this:
<div id = "first" onclick = "changeToImage1()">
...
</div>
<div id = "second" onclick = "changeToImage2()">
...
</div>
<div id = "third" onclick = "changeToImage3()">
...
</div>
I have trying for some time. And I gave a look at the image slider questions already. But I would really appreciate if I get some specific help here. Please tell me where the following code went wrong.
Here's my jQuery code:
function slideMe {
$('.imgcontainer').animate({"margin-left":"-= 100%"}, 2000, function () {
if($('.imgcontainer').css("margin-left") == (-300%)) {
$('.imgcontainer').css("margin-left", "0px");
}
slideMe();
});
}
window.onload = slideMe();
And here's the script on HTML page:
<div class="fitimage">
<div class="imgcontainer">
<img src="img/copywrtng.jpg" class="headerimage" alt="copywriting" />
<img src="img/copywrtng1.jpg" class="headerimage" alt="copywriting" />
<img src="img/copywrtng2.jpg" class="headerimage" alt="copywriting" />
</div>
</div>
And here's what I have on CSS:
div.fitimage {
width:100%;
height:93vh;
overflow: hidden;
}
img.headerimage {
padding: 0;
margin:0 auto;
width:100%;
/*max-height:100%;
max-width:100%;*/
height:93vh;
}
My logic is that as each image takes up 100% width, as the ".imgcontainer" div slides left with margin-left: -100%, each image should come up one by one from the right, until it reaches the last one when it reverts to the first image again.
It's not working!
Please help.
Your "main" issue is in this line:
$('.imgcontainer').css("margin-left") == (-300 % )
// ^^^^^^^^
beside you can only use string format "-300%", .css("margin-left") will give you a px value which you cannot compare with a non-computed %.
Another issue is that the slides set at 100% - will be the width of their container, which might be actually greater (300% for 3 slides).
Solution:
Instead I'd suggest you to use a c counter that goes like 0,1,2, 0,1... etc.
Than calculate the overflow-wrapper width and animate scrollLeft: width * counter (instead of -marginLeft).
Use display:flex on the parent and min-width:100%; on the child DIV elements (than place your images inside those DIVs instead!)
$(".imgcontainer").each(function(){ // Now you can have multiple independent sliders!
var $gal = $(this),
$slides = $gal.children(), // get the slides
tot = $slides.length, // number of slides
c = 0; // the counter we mentioned
(function anim() { // internal animation callback function
var w = $gal.width();
c = ++c % tot; // increment or loop-back counter to 0
$gal.delay(2000).animate({scrollLeft: w*c }, 1000, anim); // anim callback !
}()); // << START!
});
/*QuickReset*/ *{margin:0;box-sizing:border-box;font:14px/1.4 sans-serif;} html,body{height:100%;}
.imgcontainer{
position:relative;
height: 93%; /* or whatever you see fit */
display: flex;
overflow: hidden;
}
.imgcontainer > div {
min-width: 100%;
background: none 50% 50% / cover;
/* Set background-image inline (see HTML) */
/* Or use inner images like you did */
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="imgcontainer">
<div style="background-image:url(http://placehold.it/500x340/0bf);">
Slide 1
</div>
<div style="background-image:url(http://placehold.it/500x340/f0b);">
Slide 2
</div>
<div style="background-image:url(http://placehold.it/500x340/b0f);">
Slide 3
</div>
</div>
So, right now, I am using JQuery to try to made a continuous slideshow of text values. However, after some time, more than one start to display at the same time, indicating that my timing is off. I've tried to hide them, but it still doesn't work the way it show. My code currently looks like this. I have 3 strings of texts.
<h3 class="s1" style="display:none;"> ONE! </h3>
<h3 class="s2" style="display:none;"> TWO! </h3>
<h3 class="s3" style="display:none;"> THREE! </h3>
My function looks like this:
setInterval(function(){
$(".s1").fadeIn(1000);
$(".s1").fadeOut(1000,function(){
$(".s2").fadeIn(1000);
$(".s2").fadeOut(1000,function(){
$(".s3").fadeIn(1000);
$(".s3").fadeOut(1000);
});
});
},6000);
This seems to work fine from the beginning, but after a few seconds (maybe 30 or more), the string start to stack on top of one another. So, the out put I'd want is like:
0:01 --> ONE!
0:02 -->
0:03 --> TWO!
0:04 -->
0:05 --> THREE!
0:06 -->
0:07 --> ONE!
But, what I get is something like:
0:01 --> ONE!
0:02 -->
0:03 --> TWO!
0:04 -->
0:05 --> THREE!
ONE!
0:06 -->
0:07 --> TWO!
ONE!
... --> ONE!
... --> TWO!
... --> THREE!
How do I write this so the next string will display ONLY after the other has disappeared?
EDIT: Sorry, I did't read the last line, where you asked that ONLY after the other has faded. Changed to reflect.
As with most things, there is 'more than one way to skin a cat'. Although I am not sure of your overall application, perhaps the following will help and provide some scalability/versatility:
.js
var vl = [];
vl.interval = 1000;
vl.fadeSpd = 300;
vl.slide = $('.slider .slide');
vl.cntSlides = vl.slide.length;
function startSlider() {
setInterval( function() {
changeSlide();
},vl.interval);
}
function getNextSlide() {
active = $('.slider .active').index();
if(active == (vl.cntSlides - 1)) {
nextSlide = 0;
} else {
nextSlide = active + 1;
}
return nextSlide;
}
function changeSlide() {
nextSlide = getNextSlide();
$('.slider .active').fadeOut(vl.fadeSpd).removeClass('active');
setTimeout( function() {
vl.slide.eq(nextSlide).fadeIn(vl.fadeSpd).addClass('active');
},vl.fadeSpd);
}
startSlider();
As you can see, you can add items/slides and it will loop through them without having to keep writing more instances or layers of code. Basically:
a. slider starts with call 'startSlider', setting the time Interval
b. changeSlide() starts the process of changing the slide, inside of which, it will look for the next slide and compare to the overall slide count, resetting if it gets to the last slide.
c. hides prior slide with fade(), delays over fade speed/time (vl.fadeSpd), and fades in nextSlide over delay of fade speed/time.
.css
.slider {
position: relative;
text-align: center;
width: 300px;
.slide {
position: absolute;
display: none;
width: 100%;
top: 0;
left: 0;
}
.active {
display: block;
}
Not sure this needs explanation, but basically positions each item on top of one another, and hence why having to use a 'relative' container of some type (ie., slider). You can change the container, but used a 300px width in this example. There is a lot more you can do with this base. Having fun styling! :)
main page
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="slider">
<h3 class="slide active">One!</h3>
<h3 class="slide">Two!</h3>
<h3 class="slide">Three!</h3>
</div>
Just added the container, so the absolute, stacked items/slides have some type of relative positioning/parameters.
Sorry if this doesn't help given your application, but perhaps someone will glean something from it.
Using the flexbox justify-content property, elements can be distributed evenly in their container. However, I want to animate their positions when a new element is inserted or an existing one is removed.
I only managed to animate the height of the elements so far. However, there is a jump at the end of the animation since the gaps around the removed element that got animated to height: 0 vanish. Analogously, when inserting an element there is a jump at the beginning of the animation.
Is it possible to make an animation from end to end with justify-content? Here is an example to play with. Using CSS transition is preferred.
The main problem is that the behavior you are getting is the expected one.
In the very same instant that card.remove() is executed the flexbox justify-content property need to adjust the gaps around the removed element (as you said). And, as Paulie D has pointed out, there is nothing to animate about.
The only solution I can think about is to skip the flex thing and use javascript to create the necessary gaps among the card elements.
Here I leave the snippet:
var animation_time = 500;
var column_height = $('.column').height();
var cards_height = $('.card').height();
var cards_number;
var cards_total_height;
var space_to_be_distributed;
var placeholder_height;
function updateSizes(cards_number)
{
cards_total_height = cards_number * cards_height;
space_to_be_distributed = column_height - cards_total_height;
placeholder_height = space_to_be_distributed / (cards_number + 1);
}
updateSizes($('.card').length);
$('.placeholder').height(placeholder_height);
$(document).on('click', '.card', function () {
var card = $(this);
card.animate({height: 0, opacity: 0}, animation_time, function () {
card.remove();
});
updateSizes($('.card').length - 1);
var placeholder = card.next();
$('.placeholder').not(placeholder).animate({height: placeholder_height}, animation_time);
placeholder.animate({height: 0}, animation_time, function () {
placeholder.remove();
updateSizes($('.card').length);
$('.placeholder').animate({height: placeholder_height}, animation_time);
});
});
$('a').click(function () {
var card = $('<div class="card">');
card.css({opacity: 0, height: 0})
.appendTo('.column')
.animate({height: 25, opacity: 1}, animation_time);
var placeholder = $('<div class="placeholder">');
placeholder.css({height: 0})
.appendTo('.column');
updateSizes($('.card').length);
$('.placeholder').animate({height: placeholder_height}, animation_time);
});
body, html, .column {
height: 100%;
margin: 0;
}
.column {
float: left;
width: 100px;
background: navy;
overflow: hidden;
}
.card {
height: 25px;
width: 100px;
background: grey;
}
.placeholder {
height: 25px;
width: 100px;
}
<html>
<head>
<script src="http://code.jquery.com/jquery-2.1.3.min.js"></script>
</head>
<body>
<div class="column">
<div class="placeholder"></div>
<div class="card"></div>
<div class="placeholder"></div>
<div class="card"></div>
<div class="placeholder"></div>
<div class="card"></div>
<div class="placeholder"></div>
</div>
Add card
</body>
</html>
Hope it helps!
EDIT - I made the following changes in the code:
I change the fiddle for a SO snippet.
I forced an update of elements size at the end of the animation (in case you click to remove an element before the last one has been completely removed)
I change the size of the elementes to adapt it to the (small) SO snippet window.