Articles
Vertical Align with CSS
published on February 20th, 2005
If vertical align is a snap using tables, it can prove quite troublesome with CSS layouts. But you shouldn’t let such a small thing discourage you. I, for one, don’t like to see a perfectly valid CSS layout mingled with some tables just for this purpose. So, if you want to know how you can achieve vertical-align functionality the right way, read on.
Step1 — One line vertical-align:middle
This one is quite easy. Let’s say you set up a nice graphical container for your text but when you add the text, it just sticks to the top of your container — not a very nice visual effect. To center it vertically, simply specify the line-height for your text the same height as that of the container’s.
Things get a bit more complicated when you have more than one line of text. Stick around and we’ll fix this too.
Step 2 — Multiple lines (one line) vertical-align:bottom
An absolute positioned div inside a relative positioned one can basically be placed anywhere you want inside the parent div. So we’ll just use this setup and absolute position a div with bottom:0 within a relative positioned one. The relative positioned div inherits its height from its parent.
Step 3 — Multiple lines vertical-align:middle
This must be the trickiest part of the vertical-align functionality to be achieved with CSS. If we were to just use the trick from Step2 and set the absolutely aligned div to top:50% or bottom:50%, this would align the top part of the text (or its baseline) at the middle — so its not really middle vertically aligned. We could use the actual vertical-align property but it only works for inline elements, so we should use display:table and display:table-cell for the enclosing divs.
All nice and easy but for one problem: IE — it doesn’t recognize display:table. Nevertheless that shouldn’t stop us. We’ll use this setup and achieve the desired result even though only for last-generation browsers.
So, how can we trick IE in vertically aligning the text? We’ll use its bugs against it. IE has some issues with rendering relative and absolute positioned elements. I won’t go into details on this specific bug right here as I don’t want to complicate things even more. The important thing to remember is the solution to this practical problem: positioning a relative div into an absolute one into a relative one once again. Weird, huh? Let me try and explain a bit better: we already have the relative positioned container from the last setup where we want to vertically align the text. Inside it we’ll place an absolute positioned div at top:50%, and inside this one another div relatively positioned at top:-50%. Ta da! It works even for IE.
So now, let’s combine the two solutions and create one that works on every browser. We’ll use the attributes for the modern browsers in a way that IE can’t read them (with some help from the direct child selector), and then, also add the code for IE.
That’s it. Have fun working with vertical align and CSS layouts, and always remember: there’s not been yet a layout that couldn’t be coded with CSS.
Comments:
- Joel Bernstein
- October 6th, 2006
- 3:05 pm
That’s a wonderful method, except for the tiny detail that it adds an extra layer of divs that serve no semantic purpose. Since vertical alignment is more a luxury than anything else, why not align the text using Javascript instead?
- Paul
- October 6th, 2006
- 3:06 pm
This idea of top:-50% is brilliant, however IE5 (on OSX) ignores it. I think we’re stuck with a table/css compromise until os9 is gone(and by then hopefully IE7 will catch on!)
- John A
- October 6th, 2006
- 3:06 pm
Nice site … I really like the simplicity of it. Interesting article as well … tend to agree with Paul … as ugly as it is … I’m going to use tables etc until CSS is fully supported in modern browsers.
- Raven
- October 6th, 2006
- 3:07 pm
Except that all of the solutions are very old, even the one for multiple line vertical align, that one is about 6 months old :D
- John A
- October 6th, 2006
- 3:08 pm
I like the fact that he has consoldated them all right here for us … makes it alot easier … thanks badboy :)
- badboy
- October 6th, 2006
- 3:09 pm
I know that some of these methods have been around for a while, but still they were not addopted into the mainstream. So I though it would be usefull to have them all in one place as future reference.
- Matthew Bonner
- October 6th, 2006
- 3:09 pm
If it was a choice between adding unnecessary layers over javascript to achieve something like this I would have used Javascript, although the article was nice to read and things could be learnt from it.
- Arthur Clemens
- October 6th, 2006
- 3:10 pm
The element that is centered can only be a p or a span, not a div. Still looking for a way for divs.
Very nice. I’ve been meaning to do similar things, but the problems with IE have always thrown me off.