The Two Ways of Sizing Absolute Elements in CSS

Absolute SizingAnyone who has used CSS for a while will know about the merits of absolute and relative positioning. To recap:

position: relative allows an element to be shifted from its original position either horizontally (using left or right) or vertically (using top or bottom).

position: absolute allows an element to be positioned with respect to a containing block using left, right, top or bottom (the containing block is the nearest ancestor node with a position of relative, absolute or fixed).

Positioning nodes is therefore straightforward, e.g.

HTML:


<div id="outer">
	<div id="inner"></div>
</div>

CSS:


#outer
{
	position: relative;
	width: 200px;
	height: 200px;
	margin: 20px auto;
	border: 2px solid #c00;
}

#inner
{
	position: absolute;
	left: 50px;
	top: 50px;
	width: 96px;
	height: 96px;
	background-color: #ddc;
	border: 2px solid #00c;
}

(The actual width and height of the inner block will be 100px owing to the addition of the border).

The following boxes are rendered in every modern browser (including IE6):

 

Less well known is that you can apply all the left, right, top and bottom properties at the same time. The following CSS will render the inner element identically:


#inner
{
	position: absolute;
	left: 50px;
	right: 50px;
	top: 50px;
	bottom: 50px;
	background-color: #ddc;
	border: 2px solid #00c;
}

The width and height of the inner box will remain 100px, but we do not need to need to explicitly set the dimensions.

This could be useful when:

  • the spacing around the element is more critical than the width or height. You can also use negative left, right, top and/or bottom properties to make the inner box larger than its outer parent.
  • you have multiple inner elements with differing borders and padding but need consistent outer spacing. This method allows you to create a single style for all those elements.

JavaScript animations can also benefit since it can be easier and quicker to resize an element if you do not need to calculate the resulting width and height, e.g.


// expands and contracts the inner box
window.onload = function() {

	var inner = document.getElementById("inner");
	var offset = 100, dir = -1;
	setInterval(function() {
		inner.style.left = inner.style.right = inner.style.top = inner.style.bottom = offset+"px";
		offset += dir;
		if (offset == 0 || offset == 100) dir = -dir;
	}, 10);
	
}

A note about browser compatibility: this technique works in all the main browsers, except IE6 which only understands explicit widths and heights. There’s a surprise!

Free book: Jump Start HTML5 Basics

Grab a free copy of one our latest ebooks! Packed with hints and tips on HTML5's most powerful new features.

  • Zeno

    Wait a minute… did you just imply IE6 is a modern browser!?

  • Matthew Booth

    That is a really nifty fact. I hate trying to calculate width and height when all I care about is spacing from the parent container.

  • http://www.delvarworld.com DelvarWorld

    Wow, I’m surprised, this is actually a pretty useful tip. I’ll have to remember this one. Thanks!

  • Todo Sobre Dinero Y Negocios

    Thanks for this information.
    I will be very helpful.

    Greetings

    David Hernandez

  • Marcos Neves

    Greate tip, I’ve never thought this way!

  • Mike

    Wow, I didn’t know that! This is very cool and seemingly useful feature. I hope I get the opportunity to try it out soon!

  • Nicolaj Kirkgaard Nielsen

    I did not know this… Pretty cool!

    I can see the value in this when defining e.g. three column layouts. You could make the three columns the same height (something I regularly struggle with) by making them depend on the height of the surrounding div. I have to think this through, but I bet there are brilliant uses for this…

  • http://www.qiboo.com artemis

    I tried this a few years ago and must have tested it only in IE6 at the time and was quite disappointed. another great one to know when we can ditch IE6.

  • sitehatchery

    Interesting. But in this case, instead of on the inner block:
    left: 50px;
    right: 50px;
    top: 50px;
    bottom: 50px;

    You could just:
    margin: 50px;

  • http://www.optimalworks.net/ Craig Buckler

    @sitehatchery
    The #inner element is absolutely positioned; just using a margin will set it’s width and height to the whatever the content requires. In the example above, it’s nothing – you will just get a small blue dot.

    If #inner is set to static or relative, you would get a line – it’s a block element so the width will be 100% but the height is still determined by the content.

  • sitehatchery

    Craig, actually it works in IE 6 + and Firefox.

    http://realtimedar.com/test.html

  • sitehatchery

    Scrap that. I see what you are saying. The point is, you don’t have to set the height and width. Hmm… that is useful.

  • Ramakrishnan

    Dude thanks i was confused about this relative and absolute concept. now i am happy, i can do lot with this……….