Run image transition and animation simultaneously with some precision? - javascript

I am building a website as part of some university coursework and my landing page design is fairly ambitious, designed to wow my professor.
It requires many images of different types, jpegs, pngs and animated gifs which all appear to have a negative impact on loading time and gracefulness.
So what I'm building is a little stage-themed image carousel, what I'm trying to make it do is:
Roll curtain up revealing first image
Roll curtain down & change to second image
Roll curtain up revealing second image
Roll curtain down & change to third image
Roll curtain up revealing third image
and so on.. looping through the images indefinitely
Whilst this is going on there is a simple animated spotlight gif overlaying the image carousel, running constantly.
I am aware that there are a number of ways to achieve this, I'm trying to find the most smooth and precise method. What I have managed to constuct so far is a basic image carousel that isn't very wow, and a curtain that rolls up first time only on most browsers (it only rolls up and down constantly on Dreamweaver CS5).
I am asking here because I have tried a number of different ways and have been searching the web for 3 days trying to find a relevant example to work from. Any suggestions would be greatly appreciated.
You can view a working example here
Here is my javascript:
$(document).ready(function() {
var imgs = ['images/logopic.png','images/lobby.png','images/worksofshake.jpg','images/worksofshake.jpg'];
var cnt = imgs.length;
setInterval(Slider, 6000);
function Slider() {
$('#imageSlide').fadeOut("fast", function() {
$(this).attr('src', imgs[(imgs.length++) % cnt]).fadeIn("slow");
});
$("#curtaindown").animate({height:"95%"});
/*$("#curtaindown").animate({height:"75%"});
$("#curtaindown").animate({height:"50%"});
$("#curtaindown").animate({height:"30%"});*/
$("#curtaindown").animate({height:"5%"},5000);
$("#curtaindown").animate({height:"95%"},5000);
$(".leadinfo").hide();
}
});
Thank-you for any and all help.

This solution assumes that on page load, the curtain is covering up the image and the first image is already set on #imageSlide. I haven't tested it, but the general idea should be correct. One problem with this solution is that with a bad internet connection, there's a chance the curtain will pull away before the image is actually done downloading. Accounting for that is a bit messier, so I didn't get into it.
var imgs = [...];
var nextImage = 1;
var $image = $('#imageSlide');
var $curtain = $('#curtaindown');
hideCurtain();
preloadNextImage();
// Show the next image in 6 seconds
setTimeout(showNextImage, 6000);
function showNextImage() {
showCurtain(function(){
// Set the img tag to the new image
$image.attr('src', imgs[nextImage]);
nextImage++;
if (nextImage.length >= imgs.length)
nextImage = 0;
preloadNextImage();
// After the curtain is hidden, wait 5 more seconds before
// switching to the next one.
hideCurtain(function(){
setTimeout(showNextImage, 5000);
});
});
}
function showCurtain(onComplete) {
$curtain.animate({height:'95%'},
{ duration: 500,
complete: onComplete });
}
function hideCurtain(onComplete) {
$curtain.animate({height:'5%'},
{ duration: 500,
complete: onComplete });
}
function preloadNextImage() {
// Start downloading the next image.
(new Image()).src = imgs[nextImage];
}

I eventually settled on a very simple implementation that works even though I'm fairly sure it logically shouldn't. If someone could comment to explain why it does work I'd be very grateful.
This is the code I eventually used:
<script type="text/javascript">
$(document).ready(function() {
$("#scroller_container_top").hide();
var imgs = ['images/logopic.png','images/lobbywithcaption.jpg','images/seatswithcaption.jpg','images/worksofshake.jpg'];
var cnt = imgs.length;
setInterval(Slider, 10000);
function Slider() {
$('#imageSlide').fadeOut("slow", function() {
$(this).attr('src', imgs[(imgs.length++) % cnt]).fadeIn("slow");
});
$("#curtaindown").animate({height:"5%"},5000);
$("#curtaindown").animate({height:"95%"},5000);
};
</script>

Related

jQuery fadeOut and fadeIn not working on live site, fadeOut/fadeIn going faster than my actual picture can change

I created this simple website with this script...
<script type="text/javascript">
var photos = ["indexphotos/1.jpg", "indexphotos/2.jpg", "indexphotos/3.jpg", "indexphotos/4.jpg",
"indexphotos/5.jpg"];
var currentPhoto = 1;
setInterval(function(){
$('#content img').fadeOut(400, function() {
if(currentPhoto == 5) {
currentPhoto = 0;
}
$('#content img').attr("src",photos[currentPhoto]);
currentPhoto++;
$('#content img').fadeIn(400);
});
},5000);
</script>
To have a slideshow that plays and fades in and out photos looping through 5 photos. It worked fine while I was developing it locally, but now when it is live on a server it is having hiccups. It will fadeout but then go back to the same picture, then eventually switch to the new picture even though it was suppose to switch to the picture before it fades back in. Like the fadein and fadeout is faster than the actual changing the picture.
If you refresh the page though once, it works fine.
Is there a way to do this better so this doesn't happen?
Try adding an onload handler for the image, that would fade-in only after image has been loaded (after changing the src)
$("#content img").one("load", function() {
$(this).fadeIn(); //fade in after loading image
}).attr("src", whatever); //change ti another image
PS. .one is not a typo here.

slow down background change duration with javascript

I was able to make my website header change it's background after certain time, but it doesn't look good when it's blinking.
Here is the website. Is there anyway to change duration of action? I tried to get it done with css animation, but turns out that "background:" is not gonna work like "background-color:" property for some browsers. Anyway here is my code, could you please advice me something. Thank you!
$(document).ready(function(){
var header = $('.header');
var backgrounds = new Array(
'url("wp-content/themes/the-best-of-the-old-school/pics/header-bg.jpg")', 'url("wp-content/themes/the-best-of-the-old-school/pics/fire-bg.jpg")'
);
var current = 0;
function nextBackground() {
current++;
current = current % backgrounds.length;
header.css('background', backgrounds[current]);
}
setInterval(nextBackground, 5000);
header.css('background', backgrounds[0]);
});
You can use jQuery Animate
Replace this line of code
header.css('background', backgrounds[current]);
With the following
header.animate({opacity: 0}, 'slow', function() {
$(this)
.css({'background-image': backgrounds[current]})
.animate({opacity: 1});
});
see the answers here and here
You can define your background-images in different CSS classes:
.bg-0 {
background: url("wp-content/themes/the-best-of-the-old-school/pics/header-bg.jpg");
}
.bg-1 {
background: url("wp-content/themes/the-best-of-the-old-school/pics/fire-bg.jpg");
}
...
and then only toggle the different classes on the header:
var backgrounds = [1,2,3,4,5,6];
function nextBackground() {
current++;
current = current % backgrounds.length;
header.removeClass("bg-"+(current-1)).addClass("bg-"+current);
}
This will make sure all the images get loaded without further ado. By the time you toggle first time probably all the images will be available. Ofc this will load all the images at page load, which means that even though a person might not stay long enough to see all images, they would be loading them nonetheless.

Setinterval Animation sometime paused

I make an animation using sequence images. i run the images using setinterval function animation going fine but i dont know why it paused some time. i posted fiddle here look this fiddle you can able to notice this pause
Unwanted Pause Happen Here
myAnim = setInterval(function(){
$("#myImageHolder8").attr('src', nextImage5[u]);
u++;
if(u==nextImage5.length)
{
u=0;
}
}, 50);
Pls friends Help me.
You need to preload the image. Setting the image source inside the loop will definately cause a hick-up at one point as loading and decoding the image(s) may very well exceed 50 ms (cached or not). This will also cause the problem to appear randomly (and faster computers may not notice while slower one or slower connections may cause this more frequent).
Preload the images and the simply insert the loaded image into the container (a parent element) instead.
You can preload the images either by hiding them in DOM and use window.onload to start, or do it in JavaScript using an array and load counter.
An example of an loader:
Live demo
var images = [],
count = nextImage5.length,
len = count,
i = 0;
for(; i < len; i++) {
var img = new Image;
images.push(img);
img.onload = loader;
img.src = nextImage5[i];
}
function loader() {
count--;
if (count === 0) {
... start animation here...
}
}
and then in the animation loop do something like (sorry, my jQuery escapes me but you see the point):
$('#myImageHolder8').html('');
$('#myImageHolder8').append(images[u]);
Before setting the animation, make sure you preload your images first. So that the images are ready and loaded to display smoothly. You can use this preloader. And I would like to suggest that instead of changing the src of an <img> it is better to draw the image to a <canvas> then create a <canvas> for your next image.

Delayed autoscroll effect on a block of text

Im fairly new to JS... please be gentle.
Can anyone suggest a way to pull off a delayed autoscroll effect on a block of text?
It's important to mention that my ultimate goal is to use this on a popup modal window, on iOS devices. And because iOS browsers do not display the scrollbar until user interaction, I am resorting to the auto-scroll.
In effect: I would like the page to load, wait a couple of seconds, then have begin to slowly scroll down. The scroll is intended to be a hint to the user that there is more content available, therefore if there is any way to stop or temporarily pause the auto-scroll on user interaction- that would be optimal.
I have searched for my answers a couple of hours now, but between not being able to initialize the found code to my design (again, I'm fairly green), and not being able to find a solution that achieves everything I need - I am turning to brighter minds.
I have set up a fiddle with my HTML and CSS: http://jsfiddle.net/zfMsQ/
Any help is greatly appreciated!
ps: This is my very first post on StackOverflow :)
My code:
Extensive. Linked above.
Here you go: http://jsfiddle.net/zfMsQ/3/
var roll = true;
var max = 0;
var text = $("#content");
function scroll() {
text.scrollTop(text.scrollTop() + 1)
var top = text.scrollTop()
if (top > max) {
max = top
if (roll) {
setTimeout(scroll, 50)
}
}
}
text.on("mouseenter mouseover mousedown", function(){
roll = false;
})
setTimeout(scroll, 2000)

CSS opacity performance. Image fading

I'm trying to fade in-out my image for my photo gallery switching. All it's done in JavaScript which simply changes the opacity CSS value of the image element. This is really laggy (slow) on some computers - for example my laptop which isn't extremely powerful, but it's brand new (Asus Eeepc).
I was wondering if there's anyway I can fix this performance issue. I've seen demos of Canvas animation and HTML5 applied to images and they're really smooth on my laptop. I wonder if I can apply the same thing to my image fading feature.
Any ideas? How would I do this?
I quickly threw together an example of an image fading away using the canvas tag as requested: http://jsfiddle.net/6wmrd/12/ (Only tested in Chrome and Firefox)
I´m not sure if there is any performance gain though, but here is at least a very simple example of how it can be done. It should also be noted that this was done in 5 min so the code can be improved and optimized.
Otherwise, from my experience, if you have a solid background behind the image, I have found that it is sometimes smoother to fade an element over the image with the same color as the background.
Other ways you can improve performance could be to reduce FPS. If I´m not mistaken MooTools has 50 FPS as standard. However, reducing the FPS might influence the perceived performance.
Here is code that works for all browsers:
add to head :
/* ****************************
* updated for all browsers by
* Evan Neumann of Orbiting Eden on
* October 6, 2011.
* www.orbitingeden.com - evan#orbitingeden.com
* original version only worked for IE
*****************************/
<!-- Begin
/* *****************************
* * editable by user
* ***************************/
var slideShowSpeed = 5000; // Set slideShowSpeed (milliseconds) shared by IE and other borwsers
var crossFadeDuration = 5; // Duration of crossfade (1/10 second) shared by IE and other borwsers
var crossFadeIncrement = .05; //crossfade step amount (1 is opaque) for non-IE browsers
// Specify the image files
var Pic = new Array(); // do not change this line
// to add more images, just continue the pattern, adding to the array below
Pic[0] = 'images/dare2wear-427ED-e.jpg';
Pic[1] = 'images/PBW_3238EDSM-e.jpg';
Pic[2] = 'images/dare2wear-441_2ED-e.jpg';
/* ********************************
* do not change anything below this line
**********************************/
var f = 0; //index of the foreground picture
var b = 1; //index of the background picture
var p = Pic.length; //number of pictures loaded and in queue - this may increase as time goes on depending on number and size of pictures and network speed
//load the picture url's into an image object array
//used to control download of images and for IE shortcut
var preLoad = new Array();
for (i = 0; i < p; i++) {
preLoad[i] = new Image();
preLoad[i].src = Pic[i];
}
function runSlideShow() {//this is trigerred by <body onload="runSlideShow()" >
//if IE, use alternate method
if (document.all) {
document.images.SlideShow.style.filter="blendTrans(duration=2)";
document.images.SlideShow.style.filter="blendTrans(duration=crossFadeDuration)";
document.images.SlideShow.filters.blendTrans.Apply();
}
//increment the foreground image source
document.images.SlideShow.src = preLoad[f].src;
//if IE, use the shortcut
if(document.all) {
document.images.SlideShow.filters.blendTrans.Play();
}
//all other browser use opacity cycling
else {
var imageContainer = document.getElementById('imageContainer');
var image = document.images.SlideShow;
//convert an integer to a textual number for stylesheets
imageContainer.style.background = "url('"+Pic[b]+"')";
//set opacity to fully opaque (not transparent)
image.style.opacity = 1;
//run fade out function to expose background image
fadeOut();
}
//increment picture index
f++;
//if you have reached the last picture, start agin at 0
if (f > (p - 1)) f = 0;
//set the background image index (b) to one advanced from foreground image
b = f+1;
//if b is greater than the number of pictures, reset to zero
if(b >= p) {b = 0;}
//recursively call this function again ad infinitum
setTimeout('runSlideShow()', slideShowSpeed);
}
function fadeOut(){
//convert to element
var el = document.images.SlideShow;
//decrement opacity by 1/20th or 5%
el.style.opacity = el.style.opacity - crossFadeIncrement;
//if we have gone below 5%, escape out to the next picture
if(el.style.opacity <= crossFadeIncrement) {
return;
}
//wait 50 milliseconds then continue on to decrement another 5%
setTimeout('fadeOut()', crossFadeDuration*10);
}
// End -->
and add two elements to the body. The first is a container background element. I have used a div, but td, body and others should work too. The second is the foreground image. Lastly, within the <body> tag, add the onload function call
<body onLoad="runSlideShow()">
<!-- this is the main image background -->
<div id="imageContainer">
<!-- this is the main image foreground -->
<img id="SlideShow" name='SlideShow' width="324" height="486">
</div>
Luca one way to make it faster is to use hardware acceleration and webkit transforms. The problem is that different browser support this to different degrees. See
http://mir.aculo.us/2010/06/04/making-an-ipad-html5-app-making-it-really-fast/
hopefully in the not-to-distant futures support for hardware acceleration in the browser will be better.
Have a look at the front page of this site It's 5 images that fade in and out in rotation, pure css2, html4, javascript, and is cross-browser (as far as I am aware). The javascript is a bit hackneyed - written some time ago :) but it seems to be smooth enough. See how it is on your machine. If it lags, you could try with a slower update, say 150 or 200ms instead of a 100.

Categories