Form validation done right

One of most useful additions of HTML5 is definitely the built-in form validation. No more complicated scripts, just set the required attribute and you are ready to go. Unfortunately there’s a snag to it: the current state of form validation is pretty mediocre. While the “trinity” Chrome, Firefox and Opera all bring decent support, Safari stays far behind and the only Internet Explorer capable of this feature is IE10. So what to do now if you want to validate a form so that it works in every browser?

Of course you could relapse to jQuery and use one of the many ready-made plugins, but that’s anything but future-proof. Definitely the way to go is to let the capable browser do their native thing and for the rest resort to a polyfill. The downside: JavaScript and jQuery are still needed, but the time will come when you can purely rely on the native support of the browsers and chuck out the script. So what do we need to validate a form in the the said way?

The official way

For the “modern” browsers the only thing really needed for validation is the required attribute:

<input type="email" required/>

Since that’s a boolean attribute you don’t need to set a value. Admittedly you get a different error message for every browser, but the result is what matters. Beyond that you can also use the title attribute to set a custom message that gets displayed alongside the default message:

<input type="email" required title="You really need to fill out this field!"/>

Unfortunately Chrome is the only one to display this custom message at the moment.

But how to tell the browser which content is actually allowed to be inputted? That’s when the pattern attribute comes into play. It takes a regular expression as a value:

<input type="email" required title="You really need to fill out this field!" pattern="[0-9]{4}"/>

In this case a four-digit combination of numbers needs to be inserted. If you are not that into this kind of stuff, you can visit the excellent website html5pattern.com which gives you a wealth of different patterns.

Let’s polyfill

Now that we’ve taken care of the modern guys let’s turn towards the retarded pals. Although there are a few different polyfills to choose from the most feasible one is the WEBSHIMS LIB, a collection of numerous polyfills for the not-so-capable browsers. Basically the employment is pretty simple: Load up Modernizr, jQuery and the WEBSHIM polyfill (polyfiller.js) and add the script to the <head> of your website:

<script>
     $.webshims.polyfill();
</script>

Now browsers with no native support for form validation will show a nice little error message for every required field. Unfortunately there’s a little drawback: pretty every browser with native support gives you a different text. Wouldn’t it be nice to get a a nice uniform one for every single one? That’s when the WEBSHIMS LIB also assists modern browsers.

Just expand the above invocation with a few lines:

<script>
	$.webshims.setOptions('forms', {
		overrideMessages: true
	});
	$.webshims.setOptions({
		waitReady: false
	});
	$.webshims.polyfill();
</script>

Now you get the same text for every browser, even with language support. Here’s an example for such a form.

To go one step further you can also instruct the script to use the same appearance for the error messages for every single browser:

<script>
	$.webshims.setOptions('forms', {
		overrideMessages: true,
		replaceValidationUI: true
	});
	$.webshims.setOptions({
		waitReady: false
	});
	$.webshims.polyfill();
</script>

Neat, huh? To change this appearance use the CSS classes .validity-alert-wrapper .va-arrow (for the arrow) and .validity-alert-wrapper .va-box (for the container itself).

Additionally the WEBSHIMS LIB also enables a few other features for legacy browsers like a date picker. If you often have to deal with forms and especially their validation you should check out this polyfill. It’s very powerful and can both assist modern and legacy browsers.

  • http://twitter.com/a_almeida84 Antonio Almeida

    Hello Chris.
    This is great! Thanks for that.
    My only concern is the polyfiller.js doesn’t seem to be loading locally.
    Whenever I link the polyfiller.js to the url below it wokrs fine. But not locally.

    http://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js

    have you came across that before?

    Thanks,
    Antonio

    • Chris_Krammer

      Hey Antonio! For me it also works locally. You just have to take care that you load everything exactly as in my example file. I also noticed that you need a specific version of Modernizr. Please try it again and if it doesn’t work I’m here to help.

  • arnold

    Chris, this is absolutely brilliant. Being a very ad-hoc developer in-between other jobs, I was dreading form validation. Your posting has saved me hours of work. Thank you!

    PS your link for WEBSHIM polyfill isn’t working, I think it should read: https://github.com/aFarkas/webshim

  • arnold

    Out of interest, can you recommend a way to catch validation via php for form input to database in case js is turned off?

    • Chris_Krammer

      Thanks for the compliment. Always glad if I can help. I also changed the link to polyfill. Looks like it has changed after I posted my article.

      Regarding the form validation: I’m no PHP pro and it’s been a long time since I have used it, but as far as I remember you can go for the tutorial in the link you have posted.