Photograph of a marble bust of PericlesPericles was a prominent statesman, orator, and naval general of Athens during the city-state’s Golden Age, from 448BCE until his death in 429. Pericles was a promoter of the arts (particularly plays), architecture (it was under his patronage that the Parthenon was built), and the principles of democracy, but he was also an instigator of war: Pericles is widely held to be responsible for maneuvering Athens into the disastrous Peloponnesian War with Sparta.
A typical misuse of absolute positioning

Developers who know just enough CSS to get them into trouble, along with obsessive, pixel-perfect designers, tend to jump on position: absolute as a godsend. “At last!“ they exclaim. “I can position everything on my web page exactly where I want it!“ Unfortunately they ignore several important points, and almost inevitably get wrapped up in two consequences that rapidly become an overwhelming labyrinth.

First, let’s see what position: absolute does to our page. Our code becomes:


<p><img src="assets/images/pericles.jpg" 
style="absolute; top: 0; left: 30px;" alt="Bust of Pericles">
Pericles was a prominent statesman, orator, and naval general of Athens 
during the city-states's <q>Golden Age</q>, from 448BCE until his death 
in 429.  Pericles was a promoter of the arts (particularly plays), 
architecture (it was under his patronage that the Parthenon was built), 
and the principles of democracy, but he was also an instigator of war:
Pericles is widely held to be responsible for maneuvering Athens 
into the disastrous Peloponnesian  War with Sparta.</p>

When position: absolute is applied, neither float nor margin make any difference, so they have been removed from our inline style. absolute causes our image to be taken out of the flow of the document completely, lifted up and above the rest of the content, which now slides underneath it. Essentially, the rest of the web page acts like the image is not there at all.

So why do people use position: absolute? Because with absolute on, the position of the element is measured from the top left corner of its parent containing element: in our case, the body.

position: absolute becomes very attractive, as it appears to promise pixel-perfect positioning of everything on our web page. This is an especially seductive proposition to traditional designers in the desktop publishing and print industries, who are used to being able to control the position of everything on an A4 page, and to whom fluid designs are an anathema. However, they neglect to note several points:

  1. The web is not a legal-sized piece of paper. Monitors, browsers and devices have different sizes, aspect ratios, and resolutions. Placing absolute position on an element tends to force a series of assumptions on the user that corrodes the flexibility of the web.
  2. Once you apply position: absolute to one element, you’ll usually find yourself applying it to everything else on the page. Because position: absolute takes the element out of the flow of the document, everything else has to be adjusted to compensate for it, to make sure that elements don’t overlap where you don’t want them to. This tends to lead to increasingly complex CSS that breaks as soon as new content is added to a page. (Again, the web is not an unchangeable printed page: revisions and additions occur constantly, and your design should be flexible enough to accommodate those alterations.) Using position: absolute tends to set things in concrete, making changes extremely time-consuming.

So why use position: absolute at all? Well, applied judiciously, it can be a very useful way of overlapping separate elements that might otherwise have to be merged into one image, adding time and limiting flexibility in your design.

For example, let’s say that you wanted to expand an article on Pericles to include other major figures of the Athenian Golden Age. You have several images: busts of Aeschylus, Plato, and Alcibiades. You would like to have these on the right-hand side of your document, overlapping with each other.

One solution would be to take the images into PhotoShop, merging them together as one picture. However, that removes any ability to easily change the order, alignment, or spacing of each individual image – you would have to go back into the original composite PhotoShop document, make your changes, re-export, and likely re-upload your image. Instead, let’s keep the busts as individual images, and place them inside a <div>. The HTML code is:

<div id="greek-figures">
	<img src="aeschylus-bust.jpg" alt="Marble bust of Aeschylus" id="aeschylus">
	<img src="plato-bust.jpg" alt="Marble bust of Plato" id="plato">
	<img src="alcibiades-bust.jpg" alt="Marble bust of Alcibiades" id="alcibiades">
</div>

As we know these images are all the same size, we don’t have to specify their height and width individually – instead, we will make that part of the CSS:

div#greek-figures {
	float: right; 
}
div#greek-figures img {
	height: 150px;
	width: 150px;
	position: absolute;
}

If you left the code at this point, you would find the <div> would collapse, only one image would be shown, and it would be off the page. Now: do you have any idea as to why?

…waits …

Answer: the images, being positioned absolutely, are taken out of the flow of the page, and no longer push anything around. The div, being floated, tries to determine its width from the content it contains – but because that content (the images) is set to position: absolute, they don’t count… and as they are the only content of the <div>, effectively the <div> has no width. Finally, every absolutely positioned image inside the <div> is going to try to position itself in the very top left corner of this <div> with no dimension… meaning that they all stack on top of each other. Note that it is the last image inside the div that is on top of the others: this will become important later. For now, let’s try to fix the problems we have by modifying the CSS: <style>

body p {
	text-align: justify;
}
div#greek-figures {
	float: right;
	width: 250px;
	height: 450px;
	margin-left: 2em;
}
div#greek-figures img { 
	height: 150px;
	width: 150px;
	position: absolute;
}
img#plato {
	top: 155px;
	right: 15px;
}
img#alcibiades { 
	top: 290px;
}

(We have provided a height to the div as the absolutely positioned images inside it don’t contribute to that either; and without a height, our page’s paragraphs have nothing to wrap around. The text alignment and margins are just to make a nicer presentation. )

This works well, but you’ll discover something a little odd: if you change the right property of the plato image to left, you don’t get what you might expect:

Instead of measuring its position from its container, the image is judging itself against the ultimate container, the <body>. We can get around this by exploiting an under-appreciated rule in CSS positioning:

div#greek-figures {
	float: right;
	width: 250px;
	height: 450px;
	margin-left: 2em;
	position: relative;
}

Which changes our layout to what you see on the right.Absolute layout Example 2

The rule is this: if an absolutely-positioned element is contained inside another element with position: relative applied, the inner element must measure its position against the top left corner of its container. Otherwise the position of the element will be measured against the top left corner of the body.

In general, if you insist on using position: absolute, it is a good idea to wrap multiple elements that are positioned absolutely in a containing “canvas“ – which could be a <div> or the <canvas> element.) Doing so allows you to move it around with the reassurance that absolutely positioned elements contained within it will move in harmony with their container.

Enjoy this piece? I invite you to follow me at twitter.com/dudleystorey to learn more.