Home > JavaScript >
DHTML Slideshow with Fading Effect - Explanation | Sitemap Search |
|
Sections Membership Features
Recent comments
very difficult by alfin Taking the credit for another persons work ? by curious dude. |
DHTML Slideshow with Fading Effect - ExplanationPosted by martin on 1 Jun 2002, last updated on 12 Sep 2002. Compatibility
I have seen many slideshow scripts almost all support version 3 browsers but require equal sized photos. My script does not require equal sized photos at all, in addition it also adds a fading effect. Clipping is a powerful CSS property. It tells the browser what area of the visual element should be displayed, as far as I know only the rect area (rectangle) is supported by now. You can produce amazing fade effects dynamically changing its value. The scriptThe HTML<h1>My DHTML slideshow gallery</h1> <div align="center"> <a href="javascript:changeSlide(-1)">Previous</a> <a href="javascript:changeSlide(1)">Next</a> <a href="javascript:setFade(false)">No fade</a> <a href="javascript:setFade(true)">Fade</a><br> </div> <div id="slide0" class="slide"> <img src="slide0.jpg" alt="slide0" width="100" height="50"> </div> <div id="slide1" class="slide"> <img src="slide1.jpg" alt="slide1" width="100" height="50"> </div> <div id="slide2" class="slide"> <img src="slide2.jpg" alt="slide2" width="50" height="100"> </div> <div id="slide3" class="slide"> <img src="slide3.jpg" alt="slide3" width="100" height="50"> </div> Simple but working. Of course you do not have to name your images slide0.jpg and so on. The stylesheet<style type="text/css">
.slide {
position : absolute;
visibility : hidden;
top : 200px;
left : 50px;
}
#slide0 {
visibility : visible;
}
</style>
Maybe you are wondering why I didn't set the clipping in the stylesheet but left it to the JavaScript. The answer is simple: Netscape Navigator 4 can get only the height/width of the block (actually the clipping area), when no clipping is set (apparently it doesn't get the height value properly, but I have never seen a difference of more than 10 pixels). The JavaScriptThe code is too long to be displayed on the page so it is located in an external file. ExplanationThe HTMLFirst the controls are set using anchors. <div id="slide0" class="slide"> <img src="images/slide0.jpg" alt="slide0" width="100" height="50" border="0"></div> This sets the first slide of your DHTML slideshow. The The stylesheet
.slide {
position : absolute;
visibility : hidden;
top : 200px;
left : 50px;
}
#slide0 {
visibility : visible;
}
First the class definition for all the slides. It sets the The following style rule is to make only the first slide visible to the user. The script
var DHTML =
(document.getElementById || document.all || document.layers);
if (!DHTML) {
alert('Your browser is not capable of displaying DHTML');
}
function getObj(name) {
if (document.getElementById) {
this.obj = document.getElementById(name);
this.style = document.getElementById(name).style;
} else
if (document.all) {
this.obj = document.all[name];
this.style = document.all[name].style;
} else
if (document.layers) {
this.obj = document.layers[name];
this.style = document.layers[name];
}
}
function visib(objName, flag) { // triggers layer visibility
x = new getObj(objName);
x.style.visibility = (flag) ? 'visible' : 'hidden';
}
These are basic DHTML functions that I use for the slideshow by Peter Paul-Koch. I consider them self explaining, but for the uninitiated:
Only to note that in NN 4 if you want to get a reference to a sublayer you have to use
slides = new Array( // The id's of the slides
'slide0',
'slide1',
'slide2',
'slide3',
'slide4',
'slide5',
'slide6',
'slide7');
var fadeOn = false;
function setFade(switchFade) {// Fade switch function
if ( !fadeOn ) {
prepLyr(slides[curImg], true);
} else { // No fade
stopFade();
for ( var i = 0; i < 8; i++ ) {
prepLyr(slides[i], true);
if ( slides[i] != slides[curImg] )
visib(slides[i], false);
}
}
fadeOn = switchFade;
}
First create an array of the id's of the slides, later used when switching from one image to another. The
var curImg = 0; // index of the array entry
var lastImg = 0;
function changeSlide ( change ) {
if (!DHTML) return;
curImg += change;
if ( curImg < 0 ) curImg = slides.length-1;
else
if ( curImg >= slides.length ) curImg = 0;
if ( fadeOn ) {
firstFade = true;
prepLyr(slides[lastImg], true );
fadeLayer(slides[lastImg], 10, 50);
} else {
visib(slides[lastImg], false);
visib(slides[curImg], true);
}
lastImg = curImg;
}
This is the function that I use to change the current slide displayed. If no fade is set it only hides the previous image and shows the next one, otherwise it sets the firstFade variable to true, which is required to determine whether after the fade a next one should be invoked. Then the layers clipping is set to no-clipping by the prepLayer function (the true parameter), and the fadeLayer function executed sets the global variables which are later used by the realFade function.
var clipTop, clipWidth, clipBottom, lyrheight;
var time,amount,theTime,middle;
var slideSize = new Array()
function prepLyr(lyr, vis) {
if (!DHTML) return;
x = new getObj( lyr );
if (document.layers) {
if ( !slideSize[lyr] ) {
lyrheight = x.style.clip.bottom;
clipWidth = x.style.clip.right;
slideSize[lyr] = lyrheight + 'x' + clipWidth;
} else {
lyrheight = parseInt(slideSize[lyr]);
clipWidth = slideSize[lyr].substr(
slideSize[lyr].indexOf('x')+1);
}
if ( vis ) {
clipTop = 0;
middle = Math.round(lyrheight/2);
clipBottom = lyrheight;
} else {
middle = Math.round(lyrheight/2);
clipBottom = middle;
clipTop = middle;
}
x.style.clip.top = clipTop;
x.style.clip.left = 0;
x.style.clip.right = clipWidth;
x.style.clip.bottom = clipBottom;
x.style.visibility = 'show';
} else
if (document.getElementById || document.all) {
lyrheight = x.obj.offsetHeight;
clipWidth = x.obj.offsetWidth;
if ( vis ) {
clipTop = 0;
middle = Math.round(lyrheight/2);
clipBottom = lyrheight;
} else {
middle = Math.round(lyrheight/2);
clipBottom = middle;
clipTop = middle;
}
x.style.clip =
'rect('+clipTop+' '+clipWidth+' '+ clipBottom +' 0)';
visib(lyr, true);
}
}
First declaration of the global variables. The prepLyr function first tests the global variable DHTML whether to be executed or not. Then it creates object x which refers to the layer manipulated, when it comes to the hard part of it. This is where there is no way to write a code that will be executed on all browsers, and especially great problems with NN 4 (not wondering). I use the fact that arrays in JavaScript can have string indices, not only numbers to determine whether this layer's size has been determined before. If not set the
When all these calculations have been made we actually apply the settings to the layer, in NN 4 it is through the Then we have finished NN 4 code and we check for DOM 1 or IE 4 support. The task is easier here because no matter what clipping set we can always get the image height/width. Then we make the same test for fade in or fade out, and at the end apply the settings as a string to the clip property. Actually I first made a version of the slideshow with the units specified (px), but I didn't like it at all because I couldn't get it to work in NN 4 and Opera 5. Then I found this layer scroll script, and I got the idea of the compatibility and decided to make a version in which the fading can be switched off. The thing is that the browser assume the pixels as default measure units, and I can't really tell you whether you should specify them.
function fadeLayer(layername, amt, tim) {
if (!DHTML) return;
thelayer = new getObj( layername );
if (!thelayer) return;
amount = amt;
theTime = tim;
realFade();
}
function stopFade() {
if (time) clearTimeout(time);
}
The The only thing that the
function realFade() {
clipTop += amount;
clipBottom -= amount;
if (clipTop < 0 || clipBottom > lyrheight || clipTop > middle) {
if ( clipTop > middle ) thelayer.style.visibility = 'hidden';
if ( firstFade ) nextFade();
return;
}
if (document.getElementById || document.all) {
clipstring = 'rect('+clipTop+' '+clipWidth+' '+clipBottom+' 0)'
thelayer.style.clip = clipstring;
} else
if (document.layers) {
thelayer.style.clip.top = clipTop;
thelayer.style.clip.bottom = clipBottom;
}
time = setTimeout('realFade()',theTime);
}
var firstFade = true;
function nextFade() {
firstFade = false;
prepLyr(slides[curImg], false);
fadeLayer(slides[curImg], -10, 50);
}
The The CommentsSlideshow by Peter (peter.kamin@gmx.de) on 6 Jul 2002 7:57pm GMT I was looking for a simple well written slide show program -- and found it in your descriptions. Thanks! Peter Thanks by martin on 6 Jul 2002 11:28pm GMT Thank you for the good words, there's also a live demo of the slideshow running at this site. Slideshow with Fading Effect by Bob V (bobv7@hotmail.com) on 17 Sep 2002 1:10am GMT This is cool and very informative. Write some more, please. center? by mitch () on 23 Oct 2002 3:19pm GMT hey, I'm trying to use your script and get the (variable width) elements to center all contents of the div (I'm acutally using it for more than photos). I can get the first one to center if I turn absolute positionig off of the "slide" style, but the slide show functions don't work. I'm sorry, this is probably simple but i'm pretty new to DHTML stuff (btw, I don't care about the fading. It would be a nice bonus, but centering is more important). Any ideas? Try a different method by martin on 24 Oct 2002 8:30am GMT If you want to center the images but don't want the fading you can do it like the usual rollovers. You know how to do rollovers, right? Error with the script by shkiat (hksim@rocketmail.com) on 23 Jan 2003 5:34am GMT Hi martin, I have error running the script. Can you teach me on how to install it properly step by step? One more question, this sliding only show bout images...does it support sound and display content of an attachment as well...attachement here meant here is a text file. No more error by shkiat (hksim@rocketmail.com) on 23 Jan 2003 9:38am GMT hi again martin, i manage to get the script working. The only problem now is I'm not sure or can said don't know how to pass value into the script that do the sliding images. The value i mean here is the "slide" variable where you declare how many slides are there. I would like to have a dynamic one such as before displaying that page where the sliding image resides, user can select how many pictures they wan to view. Then this number selected is pass to the script to create an array of slide[number selected in previous page] how can i do that? SlideShow by carrt on 4 Mar 2003 3:39pm GMT I attempted to pull up the external js file so I could save/copy it but all I got was a series of zeros and carriage returns. Can you help? Copyright by carrt on 4 Mar 2003 3:43pm GMT I notice that the last line on the SlideShow page refers to copyright. Do I need a release from the code author(s) or an attribute line to use the code? SlideShow by carrt on 4 Mar 2003 4:13pm GMT Tried to run the example SlideShow and got an "error on page" message. Your script or my browser? /tom Error on page by Marko (marko_one@htomail.com) on 11 Jun 2003 12:37pm GMT When visiting this page - I get a javascript error "A Runtime Error has occurred. Do you wish to debug" Line 1 Error:Invalid character. I Get this three times before I can see the page Can't download script! by Ken Dohan (ken.dohan@zginc.ca) on 20 Aug 2003 6:21pm GMT Hi Martin! When I download the .js script from your link above, the script appears in my editor as a bunch of garbled characters. I tried cutting and pasting the script from your explanation above, but am getting an 'Object Expected' error! Help? JavaScript Errors by martin on 8 Jan 2004 10:29pm GMT Sorry guys, it turned out that IE sends Accept-Encoding: gzip but doesn't actually decode the javascript if it's gzipped. That is also the cause for the Invalid character error. Mozilla Firebird by Murilo Corrêa (murilocorrea@hotmail.com) on 23 Jan 2004 12:51pm GMT Your script doesn't work in Mozilla Firebird. It does in Mozilla Firefox by Jochen () on 8 Mar 2004 9:21pm GMT Your Script works in Mozilla Firefox 0.8 Linux. Great! |