Article
Get Cooking with Photoshop and CSS - 3 Low-fat Recipes
Ordinary Lists to Extraordinary Menus
Now, we'll work on the top menu. It's currently an unordered list of links, which is what navigation bars are in theory, right? But I'd rather have it look a little more like a navigation bar and less like a bulleted list.
The first step is to get rid of the bullet marker.
ccWeb/styles.css (excerpt)
#topmenu ul {
list-style: none; /* removes list marker */
}
Now, the bullet list looks like this:

Next, I get rid of the left indent by setting the padding and margin to 0 for the list. (This won't appear to make much of a difference since we have that section right-aligned already; you'll see it more visibly when we work on the vertical navigation later.)
ccWeb/styles.css (excerpt)
#topmenu ul {
list-style: none; /* removes list marker */
padding: 0px; /* removes left indent */
margin: 0px;
}
To get the list items to display in a row, I can just set the display to "inline" for the list items (li). I'll also add some padding to the left side so that there's some space between the links.
ccWeb/styles.css (excerpt)
#topmenu ul {
list-style: none; /* removes list marker */
padding: 0px; /* removes left indent */
margin: 0px;
}
#topmenu ul li {
display: inline; /* sets list items to display in a row */
padding-left: 10px; /* puts space in between list items */
}
![]()
Finally, I'll add some styling to the links so they display as bold, blue text. I also add styles for the a:active and a:hover pseudo-classes for a hover effect on the links.
ccWeb/styles.css (excerpt)
#topmenu ul {
list-style: none; /* removes list marker */
padding: 0px; /* removes left indent */
margin: 0px;
}
#topmenu ul li {
display: inline; /* sets list items to display in a row */
padding-left: 10px; /* puts space in between list items */
}
#topmenu a:link, #topmenu a:visited {
color: #334392;
text-decoration: none;
font: bold 1.1em Verdana, Arial, Helvetica, sans-serif;
}
#topmenu a:active, #topmenu a:hover {
color: #032BF2;
text-decoration: underline;
}
The menu now looks like this (with Site Map in the "hover" state):
![]()
Next, I'll work on the left vertical navigation links. I'll take you through this process step-by-step as well, as we'll use the techniques we'll see here in later parts of this tutorial.
First, we'll apply a class to the div that holds the links for the vertical menu. I'll call mine "verticalmenu."
ccWeb/index.htm (excerpt)
<div id="leftcol">
<div class="verticalmenu">
<ul>
<li><a href="#">Home</a></li>
<li><a href="#">About Us</a></li>
<li><a href="#">Products</a></li>
<li><a href="#">Services</a></li>
<li><a href="#">Contacts</a></li>
</ul>
</div>
</div>
Repeating what we've already done for the top menu, I'll get rid of the list markers and set the margins and padding to 0 to get rid of the indent. Then, I'll give the <div> a width and border.
ccWeb/styles.css (excerpt)
.verticalmenu ul {
list-style: none;
padding: 0px;
margin: 0px;
}
.verticalmenu {
width: 145px;
border: 1px solid #A4A4A4;
}
The list currently looks like this:

A major difference between the styling for the top menu and what we're going to do here is that instead of formatting the list items (<li>), I'm going to format the links (<a>) instead.
Why? Well, I would like to set some background colors and borders and change the border when someone hovers over the link. But some browsers, IE in particular, only allow you to use :hover with respect to the <a> tag, not the <li> tag. So, with this vertical menu, we'll ignore the <li> attributes for now and focus on formatting the links (<a>).
We want to give the <a> tag a height, width, background color, etc. By default, links are "inline" elements. Thus, I'll set the links to have a "block" display so that the height and widths will apply. Then, I'll add a background color, font formatting, and the thick left border.
ccWeb/styles.css (excerpt)
.verticalmenu a:link, .verticalmenu a:visited, .verticalmenu a:hover {
display: block;
width: 145px;
height: 26px;
color: #334392;
font: bold 1.1em Verdana, Arial, Helvetica, sans-serif;
text-decoration: none;
border-left: 10px solid #6F6E7F;
}
I'll add another few lines to change the left border for the :hover pseudoclass:
ccWeb/styles.css (excerpt)
.verticalmenu a:hover {
border-left: solid 10px #334392;
}
This is what we have so far (note the blue left border of the "hovered" link):

You might think that, to get the dividers between the links, it's enough to set a bottom border for each link. Not so! Setting a border for the link will give you a border in the light gray area, but will not create a separating line in the left border area. Let's go back to the <li> attributes, setting a bottom border for each list item.
ccWeb/styles.css (excerpt)
.verticalmenu li {
border-bottom: solid 1px #a4a4a4;
}
When you do this, you'll get a 2px "double border" at the bottom of the list: one from the bottom border of the div, and one from the border that's around the entire list. We'll counteract the extra bottom border by modifying the .verticalmenu class to only use top, left, and right borders; our code now looks like this:
ccWeb/styles.css (excerpt)
.verticalmenu {
width: 145px;
border-left: 1px solid #A4A4A4;
border-right: 1px solid #A4A4A4;
border-top: 1px solid #A4A4A4;
}

Now, all we have to do is to set the padding for the text in the links. When you set padding for elements that have defined dimensions, you need to start talking about the box model. Browsers that follow the correct W3C specs (Firefox, and IE6 in standards-compliant mode, for example) will take your specified width and height to be the content area. If you add padding or borders, those dimensions will be added on to the outside of the content area. Here's a diagram that illustrates this point:

In the above diagram, the object is 303px x wide and 159px high. With an added border of 5px and padding of 15px, the actual rendered object, complete with border and padding, has a width of 303px + (15px x 2) + (5px x 2) = 343px, and a height of 159px + (15px x 2) + (5px x 2) = 199px.
All this is to say that when you're setting padding for elements whose widths you've already defined in the style sheet, you'll have to do a bit of subtraction to get the actual width of the element. In this case, the navigation links had defined dimensions of width: 145px, height: 26px. If I want to add padding of 5px, I'd then get width: 135px, height: 16px. But I also need to take into account the extra-thick left border, and subtract 10 pixels from the width, to get the final width: 125px. (I would have modified the widths earlier, when I defined the border, but for the purposes of this article, I wanted to talk about padding as well.)
ccWeb/styles.css (excerpt)
.verticalmenu a:link, .verticalmenu a:visited, .verticalmenu a:hover {
display: block;
width: 125px;
height: 16px;
padding: 5px;
color: #334392;
font: bold 1.1em Verdana, Arial, Helvetica, sans-serif;
text-decoration: none;
border-left: 10px solid #6F6E7F;
}
We're done, right?
Uh oh -- not quite. When you test the site in IE5, the floats and the menu dimensions are slightly off. Even when you fiddle with the dimensions, nothing seems to change. What's going on?

Those who have CSS experience may recognize the IE box model bug. Lower versions of IE (and IE6 when it's in "quirks" mode) interpreted the box model incorrectly. Instead of "adding on" padding and border amounts, IE takes the defined width and height, then subtracts the padding and border amounts for a limited text area, as illustrated in this diagram:

Now, it may be hard to tell if the box model bug applies in one situation or another. But because it's good practice to account for IE 5 bugs when you use borders and padding, I'll use the box model hack and you'll see that this particular problem is miraculously solved.
There are plenty of articles about the box model bug and the corresponding box model hack, so I'll just demonstrate the fix:
ccWeb/styles.css (excerpt)
.verticalmenu a:link, .verticalmenu a:visited, .verticalmenu a:hover {
display: block;
width: 145px;
height: 26px;
padding: 5px;
color: #334392;
font: bold 1.1em Verdana, Arial, Helvetica, sans-serif;
text-decoration: none;
border-left: 10px solid #6F6E7F;
/* box model hack */
voice-family: "\"}\"";
voice-family:inherit;
width: 125px;
height: 16px;
}
html>body .verticalmenu a:link, html>body .verticalmenu a:visited, html>body .verticalmenu a:hover
{
width: 125px;
height: 16px;
}
Basically, you want to change the width and height to work for IE5 (in this case, the original 145x26 pixels). Then, add the two lines of "voice-family" code (as-is), and add code that the other browsers can see, with the box-model-compliant dimensions (125x16 pixels). IE5 doesn't know how to interpret the two lines of voice-family code, or anything in the rule that follows it, so it sees the first width and height definitions and ignores the rest of the styles; meanwhile, browsers like Firefox know how to skip the voice-family code and get to the real width and height, overriding the first set of dimensions.
The bottom part of the code fixes the issue for Opera using the following format, which is often described as the "Be Nice to Opera Hack." The very specific format allows IE5 to ignore the information, while allowing Opera to understand it, thus again overriding the first set of IE5 dimensions.
html>body [selector-name] {
width: [new width]
height: [new height]
}
At last, our menu looks as it should!

Tweaking the Content Areas
The next tweaks to the code will affect the content areas. For the center area, I want to add the border and set some padding. I try applying that to the #centercol div.
ccWeb/styles.css (excerpt)
#centercol {
float: left;
position: relative;
width: 100%;
z-index: 12;
background: #cc0;
border: solid 1px #a4a4a4;
padding: 10px;
}
However, when I preview the page in IE6 and Firefox, it looks like this:

My guess is that this has to do with the box model again; perhaps IE6 and Firefox, which use a box model compliant to standards, are adding on the border and padding to the 100% width. I check the site in IE5 and, sure enough, there's nothing seemingly wrong. Remember that IE5 goes against standards by subtracting border and padding from the total width, so in this case, the center column would stay at 100% and look "fine".
So what I'll do instead is to create another div to surround the content, then apply the border and padding to this div. I'll also set some margins for the inner div so that there is space in between the left and right columns.
Here's the revised HTML code:
ccWeb/index.htm (excerpt)
<div id="innerbody">
<div id="leftcol">left column</div>
<div id="centercol">
<div id="centercontent">
Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Duis
tellus. Phasellus nonummy viverra mi. Phasellus mauris odio,
nonummy vitae, scelerisque in, ullamcorper in, nulla.
<!-- content cropped in code sample -->
</div>
</div>
<div id="rightcol">Right column</div>
<div class="clear">
</div>
And here's the revised style sheet. I changed #centercol back to what it used to be, and added the new information for #centercontent.
ccWeb/styles.css (excerpt)
#centercol {
float: left;
position: relative;
width: 100%;
z-index: 12;
background: #cc0;
}
#centercontent {
border: solid 1px #a4a4a4;
padding: 10px;
margin: 0px 15px 0px 10px;
}
Also, because I've adjusted the right margin for #centercontent, I no longer need the #rightcol p padding definition from the original liquid layout code, so I'll delete that line of code. (Instead of constraining myself to a padded p tag, I give myself more options for what can be put into the right column – such as other divs – by working with the margins of the #centercontent div.)
/* Mozilla code */
#body > #innerbody { border-bottom: 1px solid transparent; }
#leftcol { margin-right: 1px; }
#rightcol { margin-left: 1px; }
#rightcol p { padding-left: 10px; }
#centercol { margin: 0 -8px 0 -2px; }
Here's what it looks like:

Finally, I add a top margin to the footer to make some space between it and the rest of the content, then remove all the test background colors.
ccWeb/styles.css – partial
#footer {
clear: both;
position: relative;
z-index: 13;
border: solid 1px #A4A4A4;
margin-top: 10px;
padding: 8px;
}
And here's our final result:

Click to view larger screenshot in a new window.
Click to view HTML page in a new window.
Click to view CSS file in a new window.
Liquid Two-Column Layout
A two-column layout is easy to make using what we've done already as a base. First, I'll modify the HTML code to use the #body2 selector instead of #body, and get rid of the third column content.
ccWeb/2column.htm – partial
<div id="header">header stuff</div>
<div id="body2">
<div id="innerbody">
<div id="leftcol">Left column</div>
<div id="centercol">
<div id="centercontent">
Center column
</div>
</div>
<div class="clear"></div>
</div>
</div>
<div id="footer">©2005 - Fictional Company</div>
In the CSS, #body2 can look very much like #body, without the right border definition (which creates the right column).
cssWeb/styles.css – partial
#body {
width: auto;
border-left: solid 145px #fff; /* should be same width as left column */
border-right: solid 170px #fff; /* should be same width as right column */
}
#body2 { /* almost exactly the same as #body */
width: auto;
border-left: solid 145px #fff; /* should be same width as left column */
}
Here's what that looks like:

To get rid of the extra gap on the right side of the content area, I'll also modify the HTML page to use a new #centercontent2 instead of #centercontent.
ccWeb/2column.htm – partial
<div id="header">header stuff</div>
<div id="body2">
<div id="innerbody">
<div id="leftcol">Left column</div>
<div id="centercol">
<div id="centercontent2">
Center column
</div>
</div>
<div class="clear"></div>
</div>
</div>
<div id="footer">©2005 - Fictional Company</div>
In the style sheet, #centercontent2 will look very much like #centercontent, except that the right margin will be 0px.
cssWeb/styles.css – partial
#centercontent {
border: solid 1px #a4a4a4;
padding: 10px;
margin: 0px 10px 0px 10px;
}
#centercontent2 { /* almost exactly the same as #centercontent */
margin: 0px 0px 0px 10px;
border: solid 1px #a4a4a4;
padding: 10px;
}
And finally, our two-column layout is complete:

Click to view larger screenshot in a new window.
Click to view HTML page in a new window.
Click to view CSS file.
At this point, you can create simple styles for headings, link colors, etc. -- but the basic layout is there, looking extremely clean and crisp!
Click to view a sample page with headings in a new window.
Learn more about Liquid Layouts
You can do a lot more with liquid layouts, including setting different background images for the right, left, and center columns. Be sure to take a close look at the examples at redmelon.net/tstme/3cols2/ and alistapart.com to see how they've done things.
Summary for the Clean and Crisp Flavor
Let's review what we've learned so far...
In Photoshop, you learned to:
- Create, duplicate, rename, and merge layers.
- Use the Color Picker to select colors.
- Use the Marquee and Paint Bucket to create rectangles.
- Create a Stroke layer effect.
- Copy layer effects to other layers
- Use the Shift key to constrain your movement to straight lines when drawing lines or moving objects
- Duplicate, crop, and save files for the Web
With HTML/CSS, you learned to:
- Create a liquid three-column layout with a header and footer.
- Create a liquid two-column layout with a header and footer.
- Convert a boring list of links to more interesting horizontal and vertical links using only CSS.
- Use the box-model hack and the be-nice-to-Opera hack.