Accessibility
 
 
CSS Positioning and Dynamic Re-Positioning
by Robert Crooks

Editor's Note: This article uses CSS properties and DHTML effects that will not be rendered by all browsers; for best results, you should view this one in IE 4.0+. Click HERE to download this page in .HTM format.

In my last article, I promised you some more sophisticated DHTML, but first we need to lay some groundwork by backing up to look at the positioning of HTML elements using Cascading Style Sheet properties.

CSS Positioning

Positioning is one of the areas in which CSS provides formatting possibilities that are simply not available through HTML, and CSS positioning is not difficult. The essential properties used for positioning are:

  • Position
  • Left
  • Top
  • Z-Index
  • Width
  • Height

Positioning works reliably with the following two tags:

  • DIV [used for blocks]
  • SPAN [used for elements within blocks]

The position property can take the values Static, Relative or Absolute. Static positioning simply turns positioning over to the browser and so produces the same result you would see without CSS. Relative positioning also allows the browser to position the element relative to the flow of other information on the page and so again results in the same arrangement of information you would see without CSS. However, using relative positioning for an element allows you to position its child elements absolutely in relation to the parent that is positioned relatively in this way:

As you can see from the diagram, using the relative position for an element makes it a parent that can have child elements positioned absolutely within it. The upper-left corner of the parent element forms a (0,0) point in a local coordinate system from which child elements may be positioned using the top and left style properties. Like most length properties in CSS, these can be set in several different units, including cm, in, pt, and px.

My experience has been that positioning doesn't work reliably unless you set width and height properties for all positioned elements. You can set these to particular values if there is some reason to; otherwise "auto" will do.

To demonstrate, I will create two CSS classes (this would need to be defined in a separate CSS file, or inside a STYLE tag at the top of the page):

/* position 1 for child element */
.position1{
	Color : #228b22;
	Font-Family : Wingdings;
	Font-Size : 30pt;
	Left : 20px;
	Position : absolute;
	Top : 20px;
	Width : 35 px;
	Z-index : 1;
	}

/* style for parent element */
.parent1{
	Background-Color : #add8e6;
	Border-Color : #b22222;
	Border-Style : solid;
	Border-Top-Style : solid;
	Border-Width : 1pt 1pt 1pt 1pt;
	Height : 300px;
	Position : relative;
	Width : 200px;
	Margin-left : 100px;
	}

Now I will put these style classes to work by creating a DIV element, class="parent1", containing a single SPAN, class="position1":

<div class="parent1">
	<span class="position1">M</span>
</div>

Result

M

Dynamic Positioning

So we have some positioned elements. The next step is to move them around. To do that, we will need some JavaScript a little more complex than what I showed you in the last article, but not much. Before we get to the JavaScript, though, we will need some more style classes to define new positions for our little bomb. Here is the CSS code for positions 2-6, with modified positions, and a change of color:

.position2{
	Color : #999900;
	Font-Family : Wingdings;
	Font-Size : 30pt;
	Left : 30px;
	Position : absolute;
	Top : 60px;
	Width : 35 px;
	Z-index : 1;
	}

.position3{
	Color : #cc9900;
	Font-Family : Wingdings;
	Font-Size : 30pt;
	Left : 40px;
	Position : absolute;
	Top : 100px;
	Width : 35 px;
	Z-index : 1;
	}

.position4{
	Color : #ff9900;
	Font-Family : Wingdings;
	Font-Size : 30pt;
	Left : 50px;
	Position : absolute;
	Top : 140px;
	Width : 35 px;
	Z-index : 1;
	}

.position5{
	Color : #ff6600;
	Font-Family : Wingdings;
	Font-Size : 30pt;
	Left : 60px;
	Position : absolute;
	Top : 180px;
	Width : 35 px;
	Z-index : 1;
	}

.position6{
	Color : #ff3300;
	Font-Family : Wingdings;
	Font-Size : 30pt;
	Left : 70px;
	Position : absolute;
	Top : 220px;
	Width : 35 px;
	Z-index : 1;
	}

Now we need to create some JavaScript functions to change the class of the SPAN element in response to an event, which need to be defined inside a SCRIPT tag before we need them. Before doing that, however, let's also assign an ID attribute to span tag -- the ID attribute can have its own CSS properties, but here we will just use it as a pointer we can use in the JavaScript functions. We will also add an onmouseover event to the DIV element, so that the JavaScript function will kick in to move the SPAN element, and an onmouseout event to restore the initial position:

<div class="parent1" onMouseOver="movebomb()" onMouseOut="moveback()">
	<span class="position1" id="bomb">M</span>
</div>

Here are the movebomb and moveback functions:

function movebomb() {
	bomb.className = 'position6';
}
function moveback() {
	bomb.className = 'position1';
}

(For those of you that read the previous article on Getting Started with DHTML, notice the important difference here: in that article, we only dealt with changing the class of the current element. Here we are using an event related to one element to change the style class of a different element. This is a key technique for DHTML.)

And here is the DIV and SPAN elements, with the bomb ID and the mouseover and mouseout events implemented (move the mouse pointer into the block to see it work):

M

Now let's improve on this a little by adding a "dropbomb" function to the JavaScript that will progressively cycle the SPAN element through the position classes each time the mouse pointer passes over the DIV block. For that, we will need a little conditional logic to change the className pointer and apply it. We will also need to establish some global variables outside the function: a counter that we can increment and an array of position class names:

var i = 0; // initialize counter
// create an array of class names for the 6 positions
var position=new Array();
	position[1]="position1";
	position[2]="position2";
	position[3]="position3";
	position[4]="position4";
	position[5]="position5";
	position[6]="position6";
// drop the bomb another level on each mouseover
function dropbomb() {
	i++
	if (i<=6) // progressively drop bomb bomb2.classname=position[i]; else  // reload bomb if we have run out of classes bomb2.classname='position1'; if (i>=6) // reinitialize the counter
		i=0;
}

and the HTML code now looks like this (note that I used a new ID, since these tags are on the same page, and each ID must be unique):

<div class="parent1" onMouseOver="dropbomb()">
	<span class="position1" id="bomb2">M</span>
</div>

And here's the rendered code. This time the bomb will fall a little farther each time you move the mouse on and off the DIV, until it reaches the end of the positions and goes back to the top.

M

OK, so you really don't need a falling bomb for your site. But we have covered two techniques here -- positioning and modifying the style class of any element using a JavaScript function -- that will come in handy for other DHTML tasks we will explore in the next article in this series.

-Robert

Robert Crooks is an Allaire Certified Instructor at Allaire Corp. Please direct comments on this column to talkback@allaire.com.