Topic List Animation

The Topics page of the presentation shows a full-sized representation of the topic lists. When the "Next" link is clicked, it scales down and moves to the lower-right corner, where it stays for the rest of the presentation.

This animation doesn't fully work on IE6/Windows, since that browser does not correctly display timed changes to the style of an object. While that browser does support timed changes to individual CSS properties, it was decided to change the style of the topic list, since that also makes it easier to support rgba() colors.

If getComputedStyle() were implemented by more browsers, we could have used it to get the current values, compute the steps towards the end values, and set the individual properties that way. We also would have been able to tell whether the browser were using rgba() values, and use the appropriate colors.

General Concepts

The list of topics is the same one which appears in the lower-right corner of each page. We override the default CSS to position the page close to the center of our page so it looks like the other pages. When the "Next" link is clicked, we call a function which repeatedly sets a class to the topic list which sets different position, size, and color for the list, eventually being the same as in the centrally-managed style sheet. We then reset the page location to the link destination of the "Next" link.

HTML

The HTML for the topic list is the same as used by all the other files as shown in the Main Navigation page.

CSS

The CSS defined for the topics list is:

ol#topics {
    position: absolute;
    color: #888;
    background: transparent;
    width: 12em;
    right: 0;
    bottom: 0;
    margin: 0.5em;
    padding-left: 2em;
    font-size: 0.5em;
}
html>body ol#topics {
    color: rgba(0,0,0,0.5);
}

As explained in the CSS3 Colors page, the second rule is for browsers which understand rgba() colors or for browsers which correctly ignore the declaration if they don't support rgba().

Overriding central CSS

For the Topics page, we also declare:

ol#topics {
    right: 20%;
    bottom: 32%;
    color: #000;
    font-size: 1em;
}
html>body ol#topics {
    color: #000;
}

We approximate the position of the page, using trial-and-error to find the best settings for the actual browser we'll be using, while making sure things still look close for other browsers or window sizes. The second rule is needed to override the second rule in the central style sheet for those browsers which support rgba().

We know that for the next page, the first item will be black, so we declare:

ol#topics li:first-child { /* only works for CSS2 browsers */
    color: #000;
}

As mentioned in the comment, browsers which do not support CSS2 will not apply this rule. It was decided that it would be OK for older browsers to fade the first topic and then have it appear dark again when we move to the next page. A workaround would be to make sure the curtopic identifier is set for the first item when this page is viewed by assuring the test in the central include file will be true for this page. That can be done either by changing the test itself or by making sure the filenames for the topics page and the "Why Standards-Based Coding?" page begin with the same string.

Animation CSS

We define eight sets of rules to support our animation. The first one is:

ol#topics.a1 {
    right: 17.5%;
    bottom: 28%;
    color: #111;
    font-size: 0.94em;
}
html>body ol#topics.a1 {
    color: rgba(0,0,0,0.94);
}

We also define the a2 through a8 classes, each stepping towards the same right, bottom, color, and font-size declarations in the central style sheet.

DHTML

We use the concepts for interval timers in the DHTML Timers Snippet to animate this page. We declare only one function, and then assign that function as the onclick handler for the "Next" link.

donext()

This function sets everything up for the animation, defines the function which will be called at repeated intervals, and then starts everything in motion.

function donext () {
    var a = document.getElementById ('next');
    var ol = document.getElementById ('topics');
    if (! ol || ! a)
        return true;
    a = a.firstChild;       // Go to actual link

We first check if the page has the objects we need. If something doesn't look right, we return true which tells the browser to go ahead and follow the link. We know that the document's structure has the link as a list item, and it's the list item which has the identifier, so we make the a variable point to the actual link.

    ol.topicshref = a.href;
    ol.topicsarr = new Array ('a1', 'a2', 'a3', 'a4',
                                'a5', 'a6', 'a7', 'a8');
    ol.topicsidx = 0;

We will save all of our information as variables of the topics list itself. We grab the destination of the link, create an array for all the class names we will apply to the link, and save our position in the array.

    ol.className = ol.topicsarr[0];
    document.oltocallback = ol;

We go ahead and set the first class name, and save a pointer to the topics list in the global document variable, making sure the name is obscure enough to not collide with existing names.

    ol.callback = function () {
        if (++this.topicsidx >= this.topicsarr.length) {
            clearInterval (document.oltocallback.topicstimerid);
            document.location = this.topicshref;
        }
        this.className = this.topicsarr[this.topicsidx];
    };

Next we declare an anonymous function as our callback from the interval timer, similar to the callback function in the Timers Snippet. If we've already set the last class name, we clear the interval timer and cause the page to advance to the destination defined by the "Next" link. If we still have more class names, we set the next one.

    ol.topicstimerid =
            setInterval ('document.oltocallback.callback ()', 100);
    return false;
}

We initiate the inteval timer, saving the ID for later use. Note the function string we pass references the topics list object using our global reference. Our callback function will execute every 0.1 seconds.

Finally, we return false which will prevent the "Next" link from being followed right away.

window.onload

After defining the function which sets up our animation, we make sure it gets called when the "Next" link is clicked.

window.onload = function () {
    if (! document.getElementById)
        return;
    var nxt = document.getElementById ('next');
    if (nxt)
        nxt.firstChild.onclick = donext;
}

We make sure that the DOM is implemented and that the "Next" link is correctly tagged. Once everything looks correct, we set the onclick event handler for the actual link (which is a child of the link which has id="next".

This function will get called after the window has been loaded.