CSS3 Pseudo-Classes and HTML5 Forms: Their Limitations and a Possible Solution

November 5th, 2012 by zoltan · 2 Comments


I have been playing around with HTML5 Forms for a while now, and have used it in production in a variety of projects. One of my favorite parts of the spec is the use of CSS3 pseudo-classes to show the validation state of the form fields to the user. I believe these validation hints make a better user experience and makes the process of filling out the form less frustrating. In my humble opinion, however, I think there are some shortcomings in the existing psuedo-classes that produce these validation hints, and would like to start a discussion for a possible solution that could be easily added to the CSS3 UI specification.

The “Problem”

If you look at the form below, you will see that:

  • if a form element is mandatory, a star appears after the field label
  • if it has an invalid value, a red X appears in the background
  • if it has a valid value, a greed tick appears in it’s background



In order to produce these effects, we use the CSS3 :required, :valid, :invalid and :focus pseudo-classes (if you are not familiar with them, you may want to read my previous article Cross Browser Styling of HTML5 Forms — Even In Older Browsers before you continue). However, after using them on a few projects, I keep hearing from users and clients that it is confusing for focused form elements to have red x’s next to them if they have not even been filled in yet, unless this element has lost focus. Also, it would be great if the user could see all the invalid form fields at once if a form submission has been attempted. Unfortunately, the way the HTML5 psuedo-classes are set up today, it is impossible to implement these use-cases.

The “Solution” (For the Time Being)

In order to work around these issues (and after an interesting discussion with my friend and colleague Dan Van Brunt, I added the above functionality into my HTML5 Forms polyfill, html5Forms.js. This is implemented using three special classes:

  • .wf2_isBlank, .wf2_notBlank – these classes are applied to form field when a form element is blank/not blank repectively.
  • .wf2_lostFocus -this class is applied to a form element when a form field loses focus.
  • .wf2_submitAttempted – this class is applied to a <form> tag when a form submission is attempted.

These classes exist when html5Forms.js is included in your document. For those of you not familiar with this library, html5Forms.js includes a modified version of Weston Ruter’s webforms2.js polyfill that is only loaded into a document if the browser doesn’t support HTML5 Forms natively. These classes, however, will be applied to the document whether or not the polyfill is loaded, so even if the browser is using a native implementation of HTML5 Forms, the browser will still use these classes.

Download the latest version of html5Forms.js from github in order to use this functionality.

The “Solution” (For the Long Term)

I added this functionality to html5Forms.js as a proof of concept to show how this improves the usability of the HTML5 Forms module. I believe it would be nice to have these classes be converted into pseudo-classes (i.e. :isBlank, :notBlank, :lostFocus, and :submitAttempted) and have included in CSS3, if possible. To that end, I have submitted a simplified “clean-room” page with the example above (no IE support to make the CSS simpler to follow) and submitted a small blurb about these proposed pseudo-classes to the W3C’s www-style mailing list. I don’t know if it will go anywhere (I sent this out in July and didn’t hear anything back about it), but what do you think? If you are front-end developer and believe this kind of functionality would be useful, even if you think there is a better way to implement them, please add yourself to the list and reply to the thread on this subject, or submit your opinion in the comment form below. If you passionately disagree, I would love to know why. I think this discussion is worth having now while HTML5 Forms implementations are in their infancy and currently not fully implemented in any web browser.


Image above includes work from SALi-Design and uses the Skyhook Mono font by FontomType.

Tags: CSS3 · forms · HTML5 · psuedo-classes · standard proposal · Uncategorized

2 responses so far ↓
  • 1 Rudie // Nov 6, 2012 at 12:00 pm

    I really don’t see the point of :lostFocus, and :submitAttempted, but I’ve missed :isBlank/:empty as well. At first I expected :empty to work for form elements too, but it only does for node content. :isBlank would be fine.

  • 2 zoltan // Nov 6, 2012 at 10:18 pm

    @Rudie: Let’s use the second form above as an example. If you don’t fill out the whole form and click submit, you’ll see that all the invalid fields will “reveal themselves” all at once — this is why I believe I propose :submitAttempted, since it is the only way I know of that one could style this use-case. If you reload this page and tab through each field without filling it out, you can see the mandatory fields you should have filled-in that were left empty. This “tabbing-out-and-seeing-what-you-forgot” functionality can be done with a :lostFocus pseudo-class.

Give Feedback

Don't be shy! Give feedback and join the discussion.

Please Note: If you are asking for help using the information on this page or if you are reporting a bug with the code featured here, please include a URL that shows the problem you are experiencing along with the browser/version number/operating system combination where the issue manifests itself. Without this information, I may not be able to respond.

An orange star denotes a required field.