Positioning is a method for more precisely placing an element on a Web page by specifying x, y, and in some cases z, coordinates. There are three main types of positioning:
To see how this works, consider the following examples:
Here is a simple layout with three <div> blocks. Note how one block is slightly out of position:
I started by creating three <div> blocks in the markup:
<div id="box1">Block 1</div>
<div id="box2">Block 2</div>
<div id="box3">Block 3</div>
Now for the CSS:
#box1 {
height: 100px;
width: 150px;
background-color: #FF0000;
float:left
}
#box2 {
height: 100px;
width: 150px;
background-color: #FFFF00;
float:left
}
#box3 {
height: 100px;
width: 150px;
background-color: #339900;
float:left
}
If you copy and paste this code exactly, your boxes will be arranged in a nice neat line (unlike the example above)...we'll add the positioning in a second. But first a note about the addition of the floats; these are not required for positioning. I used them here to line-up the boxes horizontally. Had I used in-line elements (like images) they would not have been required.
Okay, now for the positioning. Add some code to the CSS for box2:
#box2 {
background-color: #FFFF00;
height: 100px;
width: 150px;
position: relative;
left: 50px;
top: 50px;
float:left
}
The middle box shifts to the right and drops a bit. The 50px offsets (both top and left) are measured from the original position of the box within the markup. Note too that the red and green boxes do not move, that is because as far as they are concerned, the yellow box is still in its starting position—in other words, they ignore the positioning of the yellow box, which allows the yellow box to overlap the green box. In fact, had I not added a bunch of returns before the text that follows the boxes above, the yellow box would have overlapped the text, like this:
This text is being overlapped............................................by the yellow box.
Of course, this can make things......................................... difficult to read.
You can also position the elements from the right and/or bottom edges, something like this:
#box2 {
background-color: #FFFF00;
height: 100px;
width: 150px;
position: relative;
right: 50px;
bottom: 50px;
float:left
}
This causes the box to move up and to the left. You can also position with negative numbers; setting both the top and left positions to –50px will give you the same result as using 50px for the right and bottom positions.
When you position an item absolutely, you remove it from the flow of the document, causing the elements that follow it collapse up and/or over, closing the gap; they behave as if the positioned element were not there:
To see absolute positioning in action, we should add a containing element that is also positioned:
<div id="container">
<div id="box1">Box 1</div>
<div id="box2">Box 2</div>
<div id="box3">Box 3</div>
</div>
Now add the following style:
#container {
position:relative;
}
Finally, change the positioning of box2 to absolute. Note how the green box slides over, up against the red box, filling in the area previously occupied by the yellow box (box2).The yellow box's position is measured relative to the containing box. As with relative positioning, you can also set the position of an element from the right and/or bottom edge. However, IE 6 and below have a bug—if you wish to position from the bottom or right, you need to set a width and height for the containing element, otherwise it will be positioned relative to the screen.
Positioned elements overlap other elements. What if you have multiple positioned elements that overlap one another? Usually, the last one listed in the markup will end up on top. But what if you want an earlier item to sit atop one that comes later?
In the arrangement above, the markup is the same as we used last time (three <div> blocks wrapped in a container). The CSS is the same except that box2 and box3 are absolutely positioned (with an added z-index, see below), and I changed the x and y amounts:
#box1 {
height: 100px;
width: 150px;
background-color: #FF0000;
float:left;
}
#box2 {
background-color: #FFFF00;
height: 100px;
width: 150px;
position: absolute;
left: 50px;
top: 30px;
float:left;
z-index:20;
}
#box3 {
height: 100px;
width: 150px;
background-color: #339900;
position: absolute;
left: 100px;
top: 10px;
float:left;
z-index:10;
}
The big difference of course is the addition of the z-index. Without it, box3 would sit above box2. However, I gave box2 a greater z-index than box3; the greater the z-index, the higher it appears in the stacking order. Why did I use the values 10 and 20? I could have used z-index values of 1 and 2, but I like using larger numbers in case I want to slip something in-between later on (large numbers give me a greater margin for error). The ultimate size of the number doesn't matter, I could use 100, 1,000 or 100,000.
Let's use positioning to create a cool effect. Here is a finished example. Notice how as you resize the page, the image of the girl and her shadow remain where they are. Also, you can see the lines of the table pass through of the shadow (unless you are using IE-6 or earlier. This trick makes use of png files which older versions of IE don't support. By the way, did I mention that IE sucks?).
* {
margin:0;
padding:0;
}
#container {
position: relative;
}
table {
width:90%;
height:300px;
margin-top: 10px;
margin-left: 10px;
background-color:#339966;
background-image: url(ellieInPreserverShadow.png);
background-repeat: no-repeat;
background-position: 182px 60px;
}
td {
border: 2px solid #000;
}
Some explanation may be required. First I set a size for the table; I used a percentage for the width so it would scale with the browser window. You could set a fixed width, or no width at all (let the contents of the table determine it's size). Next I added a top and left margin to get the table away from the edge of the page. Then I added a background color (green, but you can change it), and the image of the girl with the shadow as a background image. Most important, I specified the location of the image within the table using background-positioning. Finally, I added black borders to the <td> cells.
#floatingPic {
position: absolute;
left: 192px;
top: 70px;
}
The position of absolute removes the image from its place in the markup and puts it on top of its nearest ancestor ("container"). What's more, she should line-up precisely on top of the background image of the girl, so it appears that the shadow is being cast by the foreground image. But why don't the positioning amounts match (the background image coordinates are 182 and 60; the foreground image uses 192 and 70)? Remember, we added a 10px margin to the top and side of the table; we need to account for these because the foreground image is being positioned relative to its container, which has no margin. If we had but the margin on the <div> container instead, both foreground and background images would have used the same x & y coordinates.
4 pts |
Went well above and beyond and created something special. |
3 pts |
Went above and beyond requirements. |
2 pts |
Did what was required. |
1 pts |
Missing one or more required elements or contains one or more errors. |
0 pts |
Poor showing; mostly incomplete or full of errors. |