I will provide you with an example using CSS3 transitions. You can adapt and improve it for your specific case.
My specific example works only with Webkit as it is written since the implementation of the transcription end callback is vendor dependent. You can fix this by using the correct vendor event handler names.
/* Fades an element to given opacity */
var fade = function(opacity, fn) {
this.addEventListener("webkitTransitionEnd", function end() {
this.removeEventListener("webkitTransitionEnd", end);
fn && fn.call(this);
}, false);
this.style.opacity = opacity;
};
/* Preloads an image */
var load = function(src, fn) {
var self = this, $img = new Image();
$img.onload = function() {
fn && fn.call(self);
};
$img.src = src;
};
/* Steps:
* 1. Fades out current image.
* 2. Preloads next image.
* 3. When loading of next image is complete, sets next image.
* 4. Fades in.
*/
var $img = document.getElementById("imgRand");
/* Fades out */
fade.call($img, 0, function() {
/* Get random dimensions */
var height = Math.ceil(Math.random() * 100) + 100;
var width = Math.ceil(Math.random() * 200) + 100;
var src = "http://placehold.it/" + width + "x" + height;
/* Preloading */
load.call(this, src, function() {
$img.setAttribute("src", src);
/* Fades in */
fade.call($img, 1);
});
});
You can see it here.
The img
element has -webkit-transition-duration
style property set to 1s
.
The most complicated and overlooked part of this is image preloading. Because, unless you preload all images that you want to use, the animation won't be smooth. But at the same time the detection of when an image has been loaded is not an easy task and the method that I'm using is a naive one that most probably will fail for images in the browser's cache. I won't go into details about that, you can search SO for it.
Disclaimer: It is too freaking late. So, I will just dump the code here and come to it later. If there's doubts.