Position Text Labels on Forms Using CSS

Tweet

In this post, I’ll explain three common approaches to positioning text labels on web forms using CSS:

  1. top-positioned text labels
  2. left-aligned text labels
  3. right-aligned text labels

Using Top-positioned Text Labels

Positioning labels at the top of their form elements is probably the easiest layout to achieve, as we only need to tell the label to take up the entire width of its parent element.

As our form elements/labels are inside ordered list items (which are block elements), each pair will naturally fall onto a new line, as you can see from Figure 9. All we have to do is get the form elements and labels onto different lines.

This exercise is easily completed by turning the label elements into block elements, so that they’ll occupy an entire line:

label {
display: block;
}

It’s a simple change, but one which makes the form much neater, as shown below.

neater

Left-aligning Text Labels

When we create a column of text labels to the left of the form elements, we’ll have to do a little bit more work than just to position them at the top. Once we begin floating elements, all hell breaks loose!

In order to position the labels next to the form elements, we float the label elements to the left and give them an explicit width:

label {
float: left;
width: 10em;
margin-right: 1em;
}

We also apply a little bit of margin-right to each label, so that the text of the label can never push right up next to the form element. We must define an explicit width on the floated element so that all the form elements will line up in a neat vertical column. The exact width we apply will depend upon the length of the form labels. If possible, the longest form label should be accommodated without wrapping, but there shouldn’t be such a large gap that the smallest label looks like it’s unconnected to its form element. In the latter scenario, it is okay to have a label width that is smaller than the longest label, because the text will wrap naturally anyway, as you can see below.

wrapped-label

Once we float the label, however, we run into a problem with its containing list item — the list item will not expand to match the height of the floated element. This problem is highly visible in the image below, where we’ve applied a background-color to the list item.

wrapped-label-floated

One markup-free solution to ensuring a parent contains any of its floated children is to also float the parent, so that’s what we’ll do:

left-aligned-labels.css (excerpt)
fieldset li {
float: left;
clear: left;
width: 100%;
padding-bottom: 1em;
}

If the list item is floated, it’ll contain all of its floated children, but its width must then be set to 100%, because floated elements try to contract to the smallest width possible. Setting the width of the list item to 100% means that it’ll still behave as if it were an unfloated block element. We also throw a clear :left property declaration in there to make sure that we won’t find any unwanted floating of list items around form elements. clear: left means that the list item will always appear beneath any prior left-floated elements instead of beside them.

However, once we float the list item, we find the same unwanted behavior on the fieldset — it won’t expand to encompass the floated list items. So, we have to float the fieldset. This is the main reason that we removed the padding from fieldset earlier — when we set its width to 100%, any padding will throw out our dimensions:

left-aligned-labels.css (excerpt)
fieldset {
float: left;
clear: left;
width: 100%;
margin: 0 0 1.5em 0;
padding: 0;
}

Where will this float madness end? Remain calm. It ends right here, with the submit fieldset. Since it’s the last fieldset in the form, and because it doesn’t need as much special CSS styling as the other fieldsets, we can turn off that floating behavior for good:

left-aligned-labels.css (excerpt)
fieldset.submit {
float: none;
width: auto;
border: 0 none #FFF;
padding-left: 12em;
}

By turning off floating and setting the width back to auto, the final submit fieldset becomes a normal block element that clears all the other floats. This means the form will grow to encompass all the fieldset elements, and we’re back in the normal flow of the document.

None of the elements in the submit fieldset are floated, but we want the button to line up with all of the other form elements. To achieve this outcome, we apply padding to the fieldset itself, and this action pushes the submit button across to line up with all the text fields. It’s best to have the button line up with the form elements, because it forms a direct linear path that the user’s eye can follow when he or she is completing the form.

After all that floating, we now have the layout shown below — a form with a column for the form labels and a column for the form elements.

left-aligned

Right-aligning Text Labels

With all that difficult floating safely out of the way, aligning the input labels to the right is a breeze; simply set the text alignment on the label elements to achieve a form that looks like the image below:

right-aligned-labels.css (excerpt)
label {
float: left;
width: 10em;
margin-right: 1em;
text-align: right;
}

right-aligned

And we’re done! Now you can take your pick of whichever form layout best fits your pages, all by changing a little CSS!

Which option do you prefer, and why? Let us know in the comments.

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.

  • Mitch

    What browser and versions have you tested this on? Also, it might be nice to show the html. Thanks for the article.

    • https://launchpad.net/~tim.timwahrendorff rakete

      the html?

      Name:
      [...]

      this works on all browsers, since no browser specific css conditions are used.

  • Anonymous

    Very nice, concise overview.  I appreciate the inset images of the resultant page.  Like Mitch, I would like to see a bit of HTML, too, so that I can be sure not to overlook something.

  • http://twitter.com/dgeerdink Daan Geerdink

    The first option is generally the best one. It’s the easiest to read and if you’re on a mobile device you have the label right above the input, whereas with the other ones the label falls outside of the viewing area.

    Cheers

  • http://www.facebook.com/david.hucklesby David Hucklesby

    “…we find the same unwanted behavior on the fieldset — it won’t expand to encompass the floated list items.” – Are you sure? I think it will. Fieldsets are special in that they establish a new “block-formatting context” that contains floats, I believe.

  • http://laptop-rev.blogspot.com CheapLaptopTablets

    Thanks for tutorials, i want to use this insights to optimize my Google adsense blog, I think ads appears should consider this tips. thanks :D

  • http://www.graphic-design-india.com/ Kelvin

    I like the 2nd one as it is more suitable for me. thanks for sharing.

  • https://launchpad.net/~tim.timwahrendorff rakete

    nice wrap-up and bookmark to have on labels! thx!

  • http://www.facebook.com/people/Sumit-Jaisingh/100000652534890 Sumit Jaisingh

    You could style the labels to have display: inline-block for the 2nd and 3rd approach. This way you don’t have to float the element and no need to clear the float. Just a thought.

    • Seb

      I agree, it is the best way to do it…

  • Terry Price

    Foe mw by far and away the best text arrangement is ranged right text labels. It’s rare to see them, but hey have a better unit relationship with the field they refer to and are much more space efficient than the top positioned alternative. The ranged right option because it makes your eye move slightly left tp right, it keeps you focused on the words much more.

    Terry Price

  • Paul O’Brien

    I used to use floats for the labels but for IE6 and 7 you would need to clear each row if the label height exceeded the input height otherwise elements would snag.

    These days I more or less always use inline-block for the labels (as already mentioned by someone else above) which gives you the added benefit of not needing to clear anything, no snagging and a third bonus of perfect vertical alignment as you can use vertical align on inline-block elements unlike floats. This is especially useful if you have labels that may run to two or three short lines.

    inline-block is pretty well supported these days and IE6 upwards have no problem when used on inline elements like labels ( and there is a simple hack if you want them to use it on block elements also).

    The drawbacks of inline-block are the usual white space bugs (just like the space between words) but they are rarely an issue unless you have controlled every pixel.

  • Rolland

    The different form patterns have there advantages and dis-advantages. The left aligned labels are better suited for unfamiliar labels and the user can easily scan the list of items. The right aligned labels are for the opposite case and it’s easier for the eyes to track the label to input elements. Both of these patterns also provide a smaller foot print on the page.  I actually prefer the top label over the input field myself for clarity.

  • http://twitter.com/jcubic Jakub Jankiewicz

    The first one. Read this article: http://www.uxmatters.com/mt/archives/2006/07/label-placement-in-forms.php

  • http://geekygirlinteractive.com Jodi Henderson

    As someone still new to CSS, I find tutorials this specific a great find. It’s really, really helpful in the learning process to understand the ‘why’ of an approach as much as it is the steps themselves. Thanks very much!

  • http://www.headbank.co.uk/ Robin Bankhead

    Would really have helped if you included the HTML source in this article (which Sitepoint articles usually do). Reading it, I’m not clear whether the structure is

    Label Text

    or

    Label text

    Personally I have hit patchy browser support last time I tried the latter, meaning clicking the label failed to focus the form element named in the FOR attribute. (Maybe things are better now)

    If you are using the latter, semantically DL/DT/DD tags would surely be more appropriate, though it’d be preferable not to have to enclose these structures in any list-structure at all, no?

  • http://www.headbank.co.uk/ Robin Bankhead

    Sorry, with my tags stripped the above is a bit meaningless!

    Example #1 was the form element nested inside the label (which is what I do at present); #2 was a label with FOR attribute to identify a form-element external to it.

  • Spandana

    Nice and really helpful… good job!