CSS: The All-Expandable Box 155
In HTML, if you don't specify a specific width, block-level elements are vertically expandable by their nature. Think of an unordered list. That list will grow be be as big as it needs to be to fit all of it's list elements. If a user increases the font size in their browser, the list will expand vertically, growing to fit the larger content. Sometimes it feels like vertical-only expansion is limiting and it would be nice if the element could grow horizontally as well as vertically with a font size increase by the user.
Abstract
If you have been using the Firefox 3 beta much, you might notice that it handles this automatically. Increasing the size in Firefox 3 doesn't just increase the font size, it increases everything in size, which actually feel really natural and nice. But despite it's growing market share, we can't count on Firefox for the resizing needs of our users.
I am going to attempt to explain how to make an All-Expandable box, with the following features:
- Works in all major browsers
- Expands both vertically and horizontally
- Uses a single background image

This is a bit of a tall order, especially the use of the background image. This will end up using kind of a combination of the CSS sprites technique since different areas of the image will be used in different places and the Sliding Doors technique, since different amounts of those images will be visible depending on the current size.
Make the box horizontally expandable
There is one way simple way to make a box horizontally expandable: specify your width in em's. For example:
.box {
width: 35em;
margin: 50px auto;
}
The margin is there for example purposes, to keep it centered and away from the top edge of the browser window.
Thinking about image placement
In this example, the box has rounded corners, a bit of a drop shadow, and a bit of an inner shadow. This means that all of the four corners of the box are distinctly different. This is uniquely challenging since images are not expandable. We will need a way to apply the four different corner images to the four corners of the box separately.
Also, we will need to overlap them in such a way that the transitions are seamless. And also, we are trying to do this with only a single background image, to make it as efficient as possible.
Below is an image of how you might think of what we need to do. The boxes would be overlapping, I nudged them apart so you can see the whole boxes.

When creating the background image, think big. The bigger your background image, the larger you will be able to expand without borking the layout. The example background is 700px wide which gets you about 4 or 5 different text sizings it works at, but it does eventually break apart above that.
Coding the box
Of course we always like to be as semantic as possible with our XTHML. That means not using extra markup for things that aren't really content but are purely design. Unfortunately, with all this craziness of needing four boxes for our single box, it ain't gonna happen.
This is how it's done:
<div class="box">
<div class="topleft">
<div class="topright">
<div>
CONTENT GOES HERE
</div>
</div>
</div>
<div class="bottomleft">
<div class="bottomright">
</div>
</div>
</div>
Styling the box
Here is the CSS for the four areas within the box:
.box div.topleft {
display: block;
background: url("images/box-bg.png") top left no-repeat white;
padding: 2.0em 0em 0em 2.0em;
}
.box div.topright {
display: block;
background: url("images/box-bg.png") top right no-repeat white;
padding: 2.0em;
margin: -2.0em 0 0 2.0em;
}
.box div.bottomleft {
display: block;
height: 45px;
margin-top: -2.0em;
background: url("images/box-bg.png") bottom left no-repeat white;
}
.box div.bottomright {
display: block;
background: url("images/box-bg.png") bottom right no-repeat white;
height: 45px;
margin-left: 3.0em;
}
Note the negative margins are necessary to pull back from the padding applied from the parent spans. It just works out good that way with the padding, keeping text inside the box. Also note the height of the bottom spans are set in pixels. That is on purpose as they need to be kept short and not be expandable.
This has been tested in Firefox, Safari, Opera, and IE 6 and is working in all of them, so I'm fairly satisfed it's a solid technique.
Credits
This tutorial is contributed by Chris Coyier. Visit CSS-Tricks to learn more CSS tricks from Chris.
Update:
The code in this example was updated to fix the div within a span issue and now validates.
I was wondering if any of you designers/front-end coders have a good example of a project timeline or a good estimate of how long the front-end code takes to build. The site is probably going to contain 3-4 different sub-page layouts and maybe 100 to 200 total pages. I use table-less (X)HTML and good current CSS. I just started a new job with full responsibility for redesigning and rebuilding the entire web site. I’m bad just at figuring out how long it takes to drive to work or get a cup of coffee, much less how many minutes per page I’ll spend!
I got it working -http://www.flawlessfinish.com.au
thanks
antonio
try defining it in the style sheet
img { border:none }
:]
Would you(or someone) please fix this in IE7?
Has any one an idea how to fix it in ie6 and ie7?
fix for IE is to give div.bottomright style 0px on top margin….however the great expanding box cannot handle this
expandabilityexpandabilityexpandabilityexpandabilityexpandabilityexpandabilityexpandability
it breaks if you increase the view too much
Thanks I’ll use that in my site. Already written a cool window close thing, gonna have to make it resize that as well. http://www.wecomparemobiles.co.uk
I increased the font size with FF, and it breaks. I edited the page with Firebug also, and put more text. It breaks again.
Great post! I will use this soon
Thanks a lot Guys. U are doing the great job. This is what I looking before.
Really useful, nice and cool ever. Nice tutorial sure easy to understand. I must show all this to my group. Keep in touch.
Seriously, who gives a flip it “breaks semantics.” In a perfect world maybe. And plenty of professionals use negative margins.
Not saying if it does or doesn’t, but I only care if it works, and works cross-browser.
NIce and flexi box.
Would you(or someone) please fix this in IE7? thanks
Nice example. For those having problems in IE7, add a margin-top:0; (or your favorite shorthand equivalent) to .box div .bottomright.
Also suggest using strict doctype (mine appears off page to the left with transitional). To use strict, replace the doctype with: DOCTYPE html PUBLIC “-//W3C//DTD XHTML 1.0 Strict//EN” “http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd”
and add this to the
headsection:meta http-equiv="Content-Type" content="text/html;charset=utf-8".it no longer breaks if you increase the width too much
Great , CSS: The All-Expandable Box
Great article. CSS saved web design
Cyrus
Visit http://www.psdtoxhtmlcoder.com
I got it working on this application (www.qooshi.com) as well
This is probably the best way to do the rounded corners with divs and css. Unfortunately, it is not infinitely expandable, and will break down the larger it gets. The larger you need the box, the more image data needs to be sent. The best infinite rounded box that will work in ie7 is this:
.lcrt div,.rcrt div,.lcrb div,.rcrb div{ width:15px; height:20; background-image: url(images/box.png); background-repeat:no-repeat;}
.lcrt div{ background-position:0 0;}
.rcrt div{ background-position:100% 0;}
.lcrb div{ background-position:0 100%;}
.rcrb div{ background-position:100% 100%;}
NIce and flexi box. Thanks