SCRIPTING:

Taylor
AUTO LOOPING SCROLLING LAYERS
Layers that can scroll either from bottom to top or from top to bottom; from left to right or from right to left; and whatever combinations of the above.
They can auto scroll in a continuous homogeneous loop, like news tickers do, restarting from the opposite edge once reached one.
They can alternatively scroll only under event inputs and as long as the event lasts. They can save the memory of their previous state or abolish it.
You can thus provide your pages with fully customized scrolling layers, either automatic or after user inputs.
March 2004
{ @ }

The model above is Taylor
VISIT MRS. TAYLOR WEBSITE


PURPOSES OF THE SCRIPTS
As many as 8 functions to do whatever you want with your dhtml layer scrollers

Updated on May 2006: new versions of Firefox were absolutely requiring the unit of measurement to be defined also when assiging the values via scripting: the script now does that.

Updated on March 2006: now the nested layer can scroll also within a container whose dimensions are inferior to the contained layer.

[Related Topic: MULTIPLE MENUS AUTO SLIDING IN A TRACK UPON SCROLLING OF THE PAGE]
Once I found a cute snippet of code 4 lines long at the italian Polizia di Stato (police) website. I pondered it a bit and then I developed all the paraphernalia that you'll find here. Maybe another would have not mentioned this small thing, but I am a decent person and I do. Indeed, those four lines were cute, or at least enough to provide me either with good ideas or with the right stimuli to develop new "web applications".
You'd always have a look at the codes of the others, if it wouldn't sound so strange to be said!

These scripts let you perform scrolling layers: this means that the layer, regardless of whatever html is included within it (and thus overcoming the, so to say, shortcomings of the analogous yet less powerful procedure -less powerful because not originally or specifically meant to scroll layers but mere texts without html formattings- that scrolls a layer as a scrolling ticker), will scroll either automatically or under specified events, like clicks on some link or some sort of scrolling bars/commands you may provide in the shape of links or of linked images you find suitable to flag the scrolling options.
Scrolling a layer is not the same as a layer clipper because clippers don't scroll but clip (crop) layers; it is not either a scrolling clipper for though that scrolls a layer, it also clips it all the while.
Related topics can be, for completeness's sake: layer zoomings and css arpeggios.

Your layer can scroll, using these functions, in a variety of ways:
  • From top to bottom
  • From bottom to top
  • From left to right
  • From right to left
  • From right-left and top-bottom at once
  • From right-left and bottom-top at once
  • From left-right and top-bottomat once
  • From left-right and bottom-top at once
Additionally, they can be started and take care of themselves restarting with an infinite loop and in the right way without any further interaction. They can self-calculate when they are stopped or moved along how they should restart the loop.
So they are indeed one among the most comprehensive javascript approach to scrolling layers available on the net.

To initialize your scrollers you must perform 3 steps, now described.


STEP 1
Create your layers

Define two layers, nested one within the other. To make these scrollers work it is critical your layers are two, nested.

The outermost layer will be a mere container, so that you can scroll within it the nested one taking avail of the overflow properties of this conteiner as you'll see soon.

In fact both layers must have their css style declared (we imagine here it is declared inline the tag itself, though nothing prevents you from stating the css rules from an external and linked style sheet).
Both layers can have the same width and height values, no problem because the outermost is just a container. However since 2006 the outermost layer can also be smaller (yet, not bigger) than the contained layer.

It is preferred if for the innermost layer you set a z-index higher than 1, at any rate certainly higher than the container if to the container a z-index applies.

The css position property can be set as either relative or absolute in the outermost layer: also the innermost layer can have a position statement set as either relative or absolute, though arguably a relative one makes more sense since it is nested.
The main setback if you set for the innermost layer the position property to absolute, is that it will significantly slow down the scrolling process on Netscape 5 and above (at least up to Netscape 7.01, to date) and Firefox. This is clearly a Netscape "bug".

IMPORTANT CAVEAT!

Netscape, Firefox, the Mozilla family: if you find problems on them, a possible workaround is that they may require that you openly set a style width and height inside your innermost layer.

If you do not know exactly which width and height could be (like in case of dinamically generated contents or say a sequence of images inside the innermost layer whose dimensions you haven't calculated manually or that include margins), you can set the innermost layer's style width by assigning to it the value of its scrollWidth (or scrollHeight for the style height) before the animation starts; say for instance:
document.getElementById( 'foo' ).style.width = document.getElementById( 'foo' ).scrollWidth;

document.getElementById( 'foo' ).style.height = document.getElementById( 'foo' ).scrollHeight;
However, such operation must never be performed in the middle of the document: either you perform it after the document has loaded, or as close as possible to the closing of the BODY tag, so to be sure to accommodate Internet Explorer that calculates safely scrollWidth, scrollHeight only after a full image of the document (99% at least say) is in its memory (which in fact is tantamount to saying: nearby the closing of the BODY tag).

This workaround applies particularly if the outermost layer is smaller than the innermost one: in such settings Netscape and Firefox seem to fail to report the innermost layer's correct offsetWidth, offsetHeight values that the script uses (Explorer reports them correctly instead) - and strangely enough using the very same scrollWidth, scrollHeight properties that worked before the animation to set the style width and height properly, would have not fixed the issue if these very same properties (that is, still scrollWidth, scrollHeight) would have been used inside the scripts. Very strange indeed. Let's talk of Firefox being " better" than Explorer.
Beware, in case you'd think of it, that setting an overflow property for the innermost layer to a value like auto may cause problems, because Netscape 5+ and some Firefox versions, if you do such a move, would show ghost boundaries while the layer scrolls (a Netscape bug, positively).

Eventually, you will remember that the outermost layer should have an overflow property set to hidden, and that the innermost layer should have a z-index property set to something like number 2, anyway higher than the outermost container, to be sure the latter won't overlap the former.
Of course, remember to assign an ID to your innermost layer at least.
Thus, as an example and with the innermost layer id set as id="foo":



STEP 2
INITIALIZE your scrollers - plus the CODES

Once you have defined your layers, soon after (and never before them) you pick a variable name which is identical to the ID you have assigned to the innermost layer (in our example such name is foo, and of course it could have been anything else!) and you declare:
var foo=new emptyShell("foo");
the keyword var is necessary.
Remember to put in between quotes the variable name also as the argument of the emptyShell function, in our case: "foo"
Also, of course I assume you are aware that ID are unique identifiers for a layer, so there cannot be two or more layers carrying the same ID value.

Now you have to choose the type of scrollers you want to use, and you enable its relative function name with a statement like:
foo.enable("scrollTB")
whereas scrollTB is the function name (case sensitive) of the function that scrolls from Top to Bottom.

Here are your codes: I feature them in 3 text areas.
  • The first textarea will list the emptyShell and shellGuest functions: you need them anyway, whatever scrollers you choose.
  • The second textarea will list all the available scrollers
  • The third textarea allows you to pick only one codex for one selected scroller. yet you still must remember to include in your scripts also the codes for the emptyShell and shellGuest functions.
A Robert Doisneau photo
A Robert Doisneau photo, the sidelong glance, Paris 1948
THE CODES
The emptyShell and the shellGuest functions:
lines:
ALL the SCROLLING functions at once:
lines:
ONE scrolling function at a time: pick from the menu on the left to show the code here:
lines:
A Robert Doisneau photo
A Robert Doisneau photo, M. Barre's Merry go round (under rain), Paris 1955


STEP 3
Assign the speeds, scrolling amounts etc...

In order to set the properties of your scrollers, such as the speeds, scrolling amounts, and so on, you must be aware that as soon as you have enabled a scroller on your layer with, say, the statement:
foo.enable("scrollTB")
from then on you have on an object like, in that example:
foo.scrollTB
which is endowed with a variety or properties and built in methods you can either query or set.
These methods and properties are the same regardless of which scrolling method you have enabled, provided you remember to change, for instance, foo.scrollTB with, say, foo.scrollLR in case you want to address the latter scroller method, if enabled (yes, you can enable multiple methods on each foo variable you have initialized as a new emptyShell).
Here is the list of the methods and properties available:


A Robert Doisneau photo
A Robert Doisneau photo, Seaside solitary Castaway, Chalkwell Beach Theatre, England
AVAILABLE PROPERTIES
isRunning
It is a property. As soon as a scroller is started, it is set to number 1. As soon as it is stopped, it is set to zero. By that you can deduce whether a scroller is still scrolling prior to deciding whether to stop it or to trigger another one. Very useful.

foo.scrollTB.isRunning
currentCycles
It is a property. It is a mere counter, it keeps track of how many complete scrolling cycles have been performed. It is reset to zero if the scrolling is stopped.

foo.scrollTB.currentCycles

It has been included to allow an advanced feature in case you want to custom your functions: by nesting in whatever scrolling function codex a statement like:
if(this.currentCycles==5){
this.stop();
}

whereas 5 is a placeholder for whatever number, you can arrange your scrollers to perform only that specified amount of loops. It can be useful only if you don't want them to auto loop continuously (default behaviour) and also you don't want to stop or restart them by specified events.
lastCalled
It is a property. Unlike the previous ones that are addressed from the scroller instance, this can be addressed only directly from the foo variable name, that is:
foo.lastCalled

It reveals which scrolling function was last called upon that foo variable. It can be useful. If no scroller had ever been triggered on that variable yet, it returns undefined (false).
A Robert Doisneau photo
A Robert Doisneau photo, Foxterrier on the Pont Des Arts with the painter Daniel Pipart, Paris 1953
AVAILABLE METHODS
setAttributes()
With this function you can set the two main attributes for your scroller.
Such attributes are:
  • speed
  • scroll
speed is the speed in milliseconds (defaults to 200). scroll is the scrolling amount (defaults to 1).

You use setAttributes for instance as follows:
foo.scrollTB.setAttributes(
"speed", 200,
"scroll", 3
)


That is, the name of the properties to set in between quotes, the values as bare numbers.

Be sure you don't call this method if you have not enabled the relative scroller first:
foo.enable("scrollTB")
Enabling should be done only once for each scroller you want to initialize for that foo variable: from then on the scroller belongs to the pool of scroller available in the belongings of foo.
run()
By declaring:
foo.scrollTB.run()
The layer will start scrolling and auto looping, at the speed and scrolling amount defined by setAttributes.

Be sure you don't call this method if you have not enabled the relative scroller first:
foo.enable("scrollTB")
Enabling should be done only once for each scroller you want to initialize for that foo variable: from then on the scroller belongs to the pool of scroller available in the belongings of foo.
stop()
By declaring:
foo.scrollTB.stop()
the scrolling layer will stop scrolling.

Be sure you don't call this method if you have not enabled the relative scroller first:
foo.enable("scrollTB")
Enabling should be done only once for each scroller you want to initialize for that foo variable: from then on the scroller belongs to the pool of scroller available in the belongings of foo.
reset()
A bit more radical than stop: reset will reset all the internal variables and also the position of the layer to its original one, whereas stop just freezes it where it is at the current step of the scrolling process.

Be sure you don't call this method if you have not enabled the relative scroller first:
foo.enable("scrollTB")
Enabling should be done only once for each scroller you want to initialize for that foo variable: from then on the scroller belongs to the pool of scroller available in the belongings of foo.
execute()
By declaring:
foo.scrollTB.execute()
the scrolling layer will perform only one (subsequent) step of the scrolling process, unlike with run() where it goes on performing steps as long as it is not stopped.

Be sure you don't call this method if you have not enabled the relative scroller first:
foo.enable("scrollTB")
Enabling should be done only once for each scroller you want to initialize for that foo variable: from then on the scroller belongs to the pool of scroller available in the belongings of foo.
A Robert Doisneau photo
A Robert Doisneau photo, Children in Place Hebert, Paris 1957


Remember now to set the attributes:
foo.scrollTB.setAttributes(
"speed", 200,
"scroll", 3
)


Now you can declare, if you want:
foo.scrollTB.run()
The only big caveat is that you should never make such a call to the execution of the initalized class and enabled methods (that is, running them) if the page has not fully loaded.
This basically means that either your codes are triggered by some onload event handler, or you put the script tag that hosts such run command very close to the closing body tag, this because the script entirely relies upon properties such as offsetWidth, offsetHeight, offsetTop, offsetLeft that the browser will calculate only once the whole document is present into its memory.


EVENT HANDLING and TEST FORM
Hints on how to trigger your scrollers from user input or mouse events

You can decide to trigger whatever of the methods described above (run, stop, execute, reset, also setAttributes) only upon specified mouse events.
Of course, the most direct way would be to set a mouse event handler directly on your layer tag such as onMouseOver="bla bla". Yet you can address your layer scrollers from whatever other elements of the page, such as a link out of the layer, provided that your event addresses the layer via the variable (in our case foo) which handles the layer.
Trivial instance:
<a href="#" onClick="foo.scrollTB.execute();"> click me </a>

THE TEST FORM
Choose a scrolling method:
scrollTB
scrollBT
scrollLR
scrollRL
scrollRLTB
scrollRLBT
scrollLRBT
scrollLRTB
Container dimensions: width: height:
Set Attributes
scrolling amount: speed:
set overflow porperty to auto for the innermost (scrolling) layer:
               
A nicely formatted layer as a news scroller. It scrolls and autoloops.
You can include as much html as you prefer

basquiat
Above: Jean-Michel Basquiat painting
Alternative Commands:

simulate scrolling: events are onMouseDown, onMouseUp & onMouseOut (onMouseOut is necessary in case mouse up occurs AFTER the user has moved the mouse out of the link which is sensitive to the event onMouseUp).

Click and do keep the mouse down on a link to reiterate the execute() command it triggers.

Note: with the innermost layer position set to relative, Explorer and Netscape 5 do not show the scrolling bars. Opera and Firebird in a few tests did. Just in case, keep in mind you may want to consider nesting the innermost layer in a slightly wider layer, and then load them all in an iframe slightly narrower than the outermost: that would positively conceal the bars also on those browsing platforms.