Vertical Alignment with Cascading Style Sheets

Posted on September 27, 2006 by Garrett Murphey
Cascading Style Sheets, Javascript

It's not often that you'll hear me say I miss something about designing with tables. Cascading style sheets have made my markup cleaner, slimmer, and much easier to maintain. And, for the most part, designing with CSS has been a blast. I can't believe I actually resisted moving to CSS for a while. But, there's one attribute from the good old td tag that I sorely miss -- valign. I used to find it very annoying that valign would always default to middle and that, for the most part, I'd have to go through every table cell and set valign="top". Now that I've moved to a complete CSS workflow, there's no valign and, to be honest, I kind of missing the little guy. So, I decided to bring the power of valign to the twenty-first century.

It's actually not as hard as you might think to set vertical alignment in CSS. Say we had some HTML that looked like this.

HTML:
  1.     <body>
  2.         <div id="container">
  3.             <div id="element">valign me</div>
  4.         </div>
  5.     </body>
  6. </html>

And that HTML was styled like so.

CSS:
  1. #container {
  2.     width: 410px;
  3.     height: 50px;
  4.     padding: 0 10px;
  5.     background-color: #CCCCCC;
  6. }
  7.  
  8. #element {
  9.     width: 150px;
  10.     height: 20px;
  11.     line-height: 20px;
  12. }

We'd get something that looks like this, right?

align_noscript.gif

That was a little anticlimactic. Let's try that again with a few more styles.

CSS:
  1. #container {
  2.     position: relative;
  3.     width: 410px;
  4.     height: 50px;
  5.     padding: 0 10px;
  6.     background-color: #CCCCCC;
  7. }
  8.  
  9. #element {
  10.     position: absolute;
  11.     top: 50%;
  12.     margin-top: -10px;
  13.     width: 150px;
  14.     height: 20px;
  15.     line-height: 20px;
  16. }

align.gif

That'll do it. See all that positioning going on in the stylesheet? If anyone doesn't know, positioning an element absolutely within a relatively positioned container will position the element based on the container. Basically what's happening is that we're telling element to position itself halfway down from the top (top: 50%) of container. Where did the margin-top: -10px come from, though? To align the horizontal centers of the container and element, we have to pull the element up half of its height (20px / 2 = 10px).

And there you have it -- a pretty painless method of vertically centering an element. But wait, there's more. Let's make our lives a bit easier.

A Dynamic Solution (Javascript)

Don't worry, I hear you. You don't want to have to calculate the margins for each individual element you want vertically align. Or there may be cases where you're attempting to load content dynamically and you really have no way of to calculate the margin yourself. I ran into this problem a few times with both my gallery and slideshow applications (coming soon, I promise). The result was a javascript align method I wrote. It wasn't always so complex. Until yesterday, it could only vertically and horizontally center. But now (with a little work on the original method) we can do things like the following.

JAVASCRIPT:
  1. // vertically center the element within its container
  2. align('element', { vAlign: 'middle' });
  3.  
  4. // horizontally align to the right and center vertically
  5. align('element', { hAlign: 'right', vAlign: 'middle' });
  6.  
  7. // horizontally center and vertically align to the bottom
  8. align('element', { hAlign: 'center', vAlign: 'bottom' });

The method takes every combination you can think of. If you'd like some help constructing the method with parameters, head over to the sandbox.

Resources

The script in this post uses Sam Stephenson's Prototype library. There's some very good documentation for Prototype written by Sergio Pereira and over at script.aculo.us (another great javascript library).

Download the Source

All source code is provided under the Creative Commons Attribution-Sharealike License. If you agree to these terms, please view and download the entire source now.

7 Responses to
“Vertical Alignment with Cascading Style Sheets”

Hi I know this article is in german, but code and css is international.

vertical and horizontal alignment in css is ~~ three or four years old- I 'm shure

;)

Mohika

Garrett Murphey

Hi Monika: The CSS in your article doesn't work if you set a height for the div. That was one of the biggest reasons for writing my align method -- I wanted it to be able to deal with dynamic container heights (or heights that weren't explicitly set).

Thanks for sharing another way to vertically align an element in an auto-height container though.

Anonymous

I really appriciate your work, thankyou for letting us know about it.

Leave a Reply

If you'd like to post a code snippet in your comments, please surround the code with code language tags (e.g. [php][/php], [html][/html], [javascript][/javascript]).