Do not use display:none to visually hide content intended for screen readers

When auditing websites for accessibility I occasionally find elements that are incorrectly hidden with display:none. The most common example is probably skip links intended to help keyboard and screen reader users. The irony is that those well-intended skip links are made useless by display:none.

The pitfalls of using display:none have been widely known among accessibility-conscious web developers for many years (in Web terms). As I mentioned a couple of years ago in Hiding with CSS: Problems and solutions, setting an element’s display CSS property to none makes it completely invisible. It doesn’t generate a box, it doesn’t take up any place, it doesn’t affect the layout. display:none hides the element – and its descendants – visually, and it also hides the element from screen readers (most screen readers most of the time – see JAWS, Window-Eyes and display:none: Return to 2007 for more).

The property’s name being what it is, it is understandable that some think that the display property doesn’t affect non-visual user agents. The thing is that screen readers run on top of regular browsers, and those browsers do not render elements that are set to display:none. Looking at it that way it makes sense that screen readers don’t announce those elements either (or they wouldn’t be called screen readers).

So be careful when using display:none. I’m not saying that you shouldn’t use it at all as it has plenty of valid use cases, but you should not use it for the specific case of helping screen reader users.

Here are a few rules of thumb to help you determine when and how to hide something visually:

  • If you want to hide content visually but have it accessible to screen reader users, do not use display:none. Instead use the offscreen technique or the clip method (both are described in Hiding Content for Accessibility) to hide elements only visually.
  • If the content you are hiding can also be useful to sighted keyboard only users, such as skip links, reconsider whether you really have to hide it. If you do hide it, make sure it becomes visible on focus. When using the keyboard to navigate I find it very frustrating when the focus indicator disappears for an unknown number of presses of the tab key before reappearing.
  • If you want to hide something temporarily and have it display as a result of user interaction, display:none is probably what you want. An important consideration in this case is that since you will most likely be using JavaScript to make the content visible by changing the display property’s value, you should almost always be using JavaScript to hide the content as well, or it will be hidden from non-JS users.

It all comes down to thinking before hiding and being aware that display:none hides content from everybody who uses a CSS capable browser.

Posted on August 16, 2011 in Accessibility, CSS

Comments are disabled for this post (read why), but if you have spotted an error or have additional info that you think should be in this post, feel free to contact me.