It is a common need to be able to scroll the contents of layers to eliminate the need for long drawn out pages. You could separate your content into smaller scrollable boxes to make your pages appear lighter even though they contain much more information.
Understanding how to scroll a layer is quite easy. There are a couple ways of accomplishing it. But I will show you what I believe to be the best technique which is to use nested layers, and slide the child layer within the parent layer.
The first thing to overcome is that we need to find the height (or width) of a layer that hasn't been clipped, and has not had it's height (or width) defined in it's CSS style. For example:
<STYLE TYPE="text/css"> <!-- #mylayerDiv {position:absolute; left:100; top:100;} --> </STYLE> <DIV ID="mylayerDiv"> <P>Content to scroll. Content to scroll. <P>Content to scroll. Content to scroll. <P>Content to scroll. Content to scroll. <P>Content to scroll. Content to scroll. <P>Content to scroll. Content to scroll. </DIV>
Now even though I haven't set the height or width of that layer, it obviously must have specific dimensions that can be captured - and it does.
For Netscape:
To find the width or height of a layer that hasn't had it's dimensions set, I recommend using the following:
document.layername.document.height document.layername.document.width
I should point out that the clip.height and clip.width values will also return with the same numbers, however I don't believe it makes much sense conceptually to use the clip values since the layer has not had any clip values assigned.
For IE:
In IE you won't be able to use the clip values because they haven't been assigned (which is what Netscape should do), and you can't use document.height or width because layers in IE do not have their own document object. However there are 2 specific properties in IE which we can use to obtain the values we want:
document.all.layername.scrollHeight document.all.layername.scrollWidth
These values are also the same as if you use the IE specific offsetHeight and offsetWidth properties.
Using the DynLayer to retrieve the Height and Width
If you're keen you will have noticed that to obtain the height and width in each browser you have to use different objects. In Netscape you target the layers' document object, whereas in IE you target the actual layer. We can use the DynLayer properties doc and elm to target these objects. Recall what the doc and elm properties are targeting:
In Netscape:
doc = document.layername.document
elm = document.layername
In IE:
doc = document
elm = document.all.layername
So if you want to use the DynLayer to retrieve the height or width you will have to use this:
if (is.ns) var height = mylayer.doc.height else var height = mylayer.elm.scrollHeight if (is.ns) var width = mylayer.doc.width else var width = mylayer.elm.scrollWidth
I prefer to squish those into one liners:
var height = (is.ns)? mylayer.doc.height : mylayer.elm.scrollHeight var width = (is.ns)? mylayer.doc.width : mylayer.elm.scrollWidth
I know it seems weird using an event property in there, but in actuality the event property is just a pointer to the actual layer element. I named it event because usually the only need for targeting that aspect of the layer is for defining events to it. However what we're doing is an exception.
View scrollconcepts1.html [source] - for an example that finds the height and width of a layer.
If you're wondering why the heck we need to know this then maybe the following diagram will help. It is graphical representation of a layer that has text ("This is my content...") that is nested inside another layer that has been clipped (the grey square):
We need to know the height of that content layer because we have to know exactly how high to move it up. The distance we have to move the content layer is generally referred to as the offset height. The offset height is obviously the difference between the content layer's height and the window layer's height.
So to put this down on paper, here's the HTML/CSS for a simple scroll window:
<STYLE TYPE="text/css"> <!-- #scrollWindowDiv {position:absolute; left:180; top:100; width:200; height:150; clip:rect(0,200,150,0); background-color:#C0C0C0; layer-background-color:#C0C0C0;} #scrollContentDiv {position:absolute; left:10; top:0; width:180;} --> </STYLE> <DIV ID="scrollWindowDiv"> <DIV ID="scrollContentDiv"> <P>Top <P>Content to scroll. Content to scroll. Content to scroll. Content to scroll. Content to scroll. Content to scroll. <P>Content to scroll. Content to scroll. Content to scroll. Content to scroll. Content to scroll. Content to scroll. <P>Content to scroll. Content to scroll. Content to scroll. Content to scroll. Content to scroll. Content to scroll. <P>Bottom </DIV> </DIV>
Then for the JavaScript, I assign the DynLayers. Since I named those with 'Div' the DynlayerInit() function will automatically define scrollWindow and scrollContent:
function init() { DynLayerInit() }
And to find the difference in height between the content layer and the window layer, I used the following function:
function findOffsetHeight() { var windowHeight = scrollWindow.h var contentHeight = (is.ns)? scrollContent.doc.height : scrollContent.event.scrollHeight var offsetHeight = contentHeight - windowHeight alert(offsetHeight) }
The windowHeight value is nothing tricky. That layer is clipped so it is easy to find its height using the clip values. I included the w and h properties into the DynLayer to have a quick way of obtaining the clip width and height values. Otherwise you'd have to initialize the clip methods and retrieve the clipValues('r') value.
View scrollconcepts2.html [source] - it sets up the scroll structure and finds the offset height value.
So now that we've found the offset height we need to implement a mechanism to shift the content layer up and down. To make this easy to explain I'll first show a novice way to do it.
The following code finds the offset height and has 2 functions, up() and down() which moves the content layer accordingly. Notice in those functions, it actually moves the content layer in the opposite direction - if you want to scroll down the page, you move the content layer up, and vica-versa:
function init() { DynLayerInit() // find offsetHeight windowHeight = scrollWindow.h contentHeight = (is.ns)? scrollContent.doc.height : scrollContent.event.scrollHeight offsetHeight = contentHeight - windowHeight } function up() { if (scrollContent.y < 0) scrollContent.moveBy(0,15) } function down() { if (scrollContent.y > -offsetHeight) scrollContent.moveBy(0,-15) }
Note how I've limited how far the content can scroll. When scrolling up, the content layer can only move down if it hasn't reached to top, in other words a location of 0 (where it began). When scrolling down, it can only move up until it has reached the bottom. And yes I said that correctly because remember the layer goes in the opposite direction it's scrolling. The bottom of the content layer is the negative of offsetHeight because it's always in negative territory, the following diagram will illustrate this:
View scrollconcepts3.html [source] -for an example with a minimal scroll mechanism.
Home | Next Lesson: MiniScroll |