Grow your CSS skills. Land your dream job.

Relevant Dropdowns: Polyfill for Datalist

Published by Chris Coyier

The list attribute / datalist element of HTML5 forms is pretty cool. As you type in a text input, it shows you a dropdown menu of choices you can pick from. Or you can type in whatever you want. The list attribute alone doesn't lock you into any specific value. In that way, it's a bit like a group of radio buttons with an "other" type-in option.

It's like this:

<input type="text" id="search" list="states" placeholder="Find U.S. State">
	
<datalist id="states">
  <option value="Alabama">
  <option value="Alaska">
  <!-- All the other states -->
</datalist>

and turns out like this:


Supported browser (Firefox 8) showing relevant choices for what has already been typed into the text input.

Unfortunately, browser support for datalist (at the time of this writing) is limited to Firefox 4+, Opera 10.6+, and the not-yet-released IE 10. It's reasonable that you'd want WebKit support (and older browser support) for this useful feature. So I made this polyfill. It relies on Modernizr for detection and jQuery to make it work.


Unsupported browser (Chrome 16) with just about the same functionality.

I got it working on iOS 5, IE 6+, Chrome (probably any), and Safari (probably any). Older IE's don't have the box shadow but you could style it however you want with CSS.

Like any polyfill, you start with the correct most-modern markup, and it "just works" in older browsers. This one simulates the dropdown and the selecting of an option from the dropdown. It has keyboard support (up and down arrows and selecting with return) and positions itself correctly even when the window resizes.

Safari required an extra hack since it claims support of the list attribute and datalist element but it doesn't actually work. Thus the Modernizr detection is incorrect. So because Safari has these really high browser version numbers that nobody else has, we can just test for that with jQuery.

if (!Modernizr.input.list || (parseInt($.browser.version) > 400))

Update on the above from Lee Reamsnyder to prevent newer Chromes from false positive:

if (!Modernizr.input.list || (parseInt($.browser.version) > 400 && !window.chrome))

Here it is:

View Demo

It's not perfect. It should probably be a plugin and work on multiple inputs. It should look better in IE. The code could probably be optimized. It's on GitHub if you want to download it or fork it or whatever.

Update (October 2012)

Fixed GitHub Link
Updated to jQuery 1.8
Updated custom :contains method for jQuery 1.8

Comments

  1. Permalink to comment#

    Nice job.

    But it doesn’t prevent default browser’s action (Chrome also provides a list of elements taken form the form history, that show up over the datalist options)…

    Oh, and the datalist isn’t always aligned with the input (if the list changes, and the window shows or hides the scrollbar)…

  2. Permalink to comment#

    You should be able to disable the browser’s default fill action with autocomplete=’off’ in the form tag.

    • That does fix it, but it breaks Opera’s native datalist functionality.

    • Paul
      Permalink to comment#

      What about adding the autocomplete=”off” dynamically as part of the polyfill, so you don’t disable the datalist in Opera?

  3. Juanjo
    Permalink to comment#

    There’s a typo when you mention browser support. I believe the word “Opera” is missing ;-)

    @viki53 maybe autocomplete=”off” would make the default list not appear? (shot in the dark)

    • Good shot in the dark – I added autocomplete=”off” into the HTML on chrome’s developer tools and that’s exactly what happened. I’m sure it won’t take long for a clever solution to pop up though.

  4. Permalink to comment#

    It seems there’s a bug. If you start typing the name of the state, press the down arrow once and hit enter, it puts Alabama in the box. You have to press the down arrow twice to get it to select the first option in the filtered list.

  5. Iankulov Miodrag
    Permalink to comment#

    Down key it’s not working…what’s the point, typing and the use the mouse to select it, c’monn chris.You have done a great job but you need to fix this from an UX point view.

    Best Regards

  6. Permalink to comment#

    Ironically, autocomplete=”off” turns off datalist in Opera.

    • Dammit. Removed that again. I wonder if preventDefault would work for browsers that are trying to autocomplete.

  7. Permalink to comment#

    Nice work! Didn’t know this function yet. It’s still à bit buggy at the iPad bit thanks for this snippet :)

  8. Permalink to comment#

    Very nice. I hate that the community is so anal, this is a great idea and I love the attempt, regardless of it having a few bugs. People like you are what make the web a better place!

  9. Permalink to comment#

    Oh, I even found out that jquery can solve this problem.

  10. The problem I have with this Chris is it only really seems suitable for short lists. For anything large, it’s not going to happen, and we’re still going to be using jQuery AutoComplete. Which is a shame because I’m always keen to use HTML5 over jQuery if you can.

    For example on a site I built we had three fields which the user types an airport into. There are over 10,000 airports worldwide so you can imagine having 10,000 options in HTML is just ridiculous.

    I don’t know, maybe there is a way that you could pull a CSV file into the request, possibly using a little jQuery, but still in a way that’s lighter than AutoComplete and doesn’t need jQuery UI.

  11. Permalink to comment#

    Why’d you use jQuery in the polyfill? It looks like a relatively simply polyfill that could be done without jQuery. I’ve written something very similar previously in “pure” JavaScript, except it takes all the data in the constructor as an object. I might rewrite it as a polyfill :P

  12. Cool idea but unusable on my iPhone. Well, you can see it trying to work but it really isn’t made for the way the iPhone dialog boxes get rendered.

  13. Permalink to comment#

    Hardcore Forking Action

  14. The demo doesn’t seem to work for me at all in IE 7-9.

  15. Okay, the reason why it didn’t work in IE was due to IE (even up til 9) doesn’t support datalist so it doesn’t recognize the option elements of being children of datalist. Need to use conditional comments to add a select box for IE to get it to work.

    Bigger bug: If the dropdown contains a scrollbar and the user clicks on it then the scrollbar then the dropdown fades away. You can even see this in the demo in Chrome by clicking on the States field and then don’t type anything. The dropdown will show up and then you can click on the dropdown with your mouse.

  16. Max
    Permalink to comment#

    Doesnt work on iOS :(

Leave a Comment

Current day month ye@r *

*May or may not contain any actual "CSS" or "Tricks".