I recently had the opportunity to work on WAI-ARIA additions to the Vaadin core framework. WAI-ARIA is short for Web Accessibility Initiative - Accessible Rich Internet Applications Suite. Through this, it is possible to make web application like the one's created with Vaadin accessible for assistive devices like screen readers.
Having had the pleasure to study at a campus together with students with disabilities, I know very well how hard life can be without eyesight or the ability to walk. This is why I'm feeling very proud for being able to work on reducing this pain at least a bit in the context of Vaadin. For me, every user wins when some thoughts are spent for accessibility, as the usability for everyone will increase.
And it is often the simple things that make work unnecessarily difficult. One great example we had today in the office, were an Eclipse plug-in marked an area in the window sidebar red, to indicate a certain area in source code. Well, when the person in front of the computer is colour blind for red, this doesn't help at all (yes, there is a Vaadin add-on to learn about such situations in your Vaadin applications).
Obviously, the framework can't make your application accessible on it's own, but it should make it easy for you to get there. And this is what we are targeting. We also understand that accessibility is an ongoing process, and we are just at the beginning. We also would be very interested to learn about the requirements you have regarding accessibility for your applications.
Very short intro
As I was working on support for JAWS (currently the most widely used screen reader), the content of this post is somewhat specific to using a Vaadin application with this screen reader. Alternatives to this application exist. More about this later.
Now, the task here is to help the screen reader to understand the content of an HTML page. This is easier with static HTML, where mostly regular elements are used, as these are directly recognized. For example, when the following is used for a button, this will be automatically recognized:
<button name="button">Click me</button>
Things get tricky when a button suddenly looks like this:
<div tabindex="0" class="v-button">
<span class="v-button-wrap">
<img alt="" class="v-icon" src="/path/action_save.gif">
<span class="v-button-caption">Save</span>
</span>
</div>
So in such cases, the screen reader needs some help. For this, WAI-ARIA specifies additional attributes that can be added to the important elements. The first step for the button above would be, to add a role to the root element. This will define the whole element as a button:
<div role="button" tabindex="0"...
To make it clear where the label of the button is hidden, it is possible to add an attribute aria-labelledby
<div role="button" aria-labelledby="uniquelabelid" tabindex="0"...
Then the label needs an id
<span id="uniquelabelid" class="v-button-caption">Save</span>
The next information that is important to know is, if the button is pressed or not
<div role="button" aria-pressed="false" aria-labelledby="uniquelabelid" tabindex="0" ...
Now, we have specified what kind of widget we are dealing with, where to find important information related to it and defined its state. Of course this is only a very simple example, but I hope you get the idea. You can find some links to introductions at the bottom of this post.
One thing that is also very important for the browser is, when, based on a user interaction in one part of the page, content in a different area of the page changes. These need to be specified as so called live regions. An example would be a notification. This is of course very important for the user to know, but the screen reader would not be aware of it on its own.
Helper
As I always wrote about GWT functions on this blog so far, I bet you already guessed it - yes GWT offers an easy way to handle the WAI-ARIA attributes. The class com.google.gwt.aria.client.Roles provides a lot of static functions, to help you set the correct attribute for the specific element. Setting the button role looks like this:
Roles.getButtonRole().set(buttonElement);
Specifying the label element:
Roles.getButtonRole().setAriaLabelledbyProperty(buttonelement, Id.of(labelelement));
And finally to define the state
Roles.getButtonRole().setAriaPressedState(buttonelement, PressedValue.TRUE);
Now you may be thinking, "well, this should the Vaadin framework do automatically". Correct, this is exactly what I was working on and will hopefully soon be available in the repository for the button, form fields and the tree.
But there are things the framework can't decide for you. For example, every image that is not there for pure visual reasons need an alt text, which the screen reader can read out loud so the image can be understood when it can't be seen. This needs to be set by the application developer (and the framework needs to offer the respective calls).
And when writing your own Components and add-ons, please don't forget about accessibility.
Of course the widgets are only part of the story. Structuring your content is at least equally important. Screen readers extract all the headings, links, landmarks and the likes from the page, and makes it easy for the user to get to know the content of the page and jump directly to it.
There is a lot of information on the web about accessibility. Sites I check regularly is WebAIM, which offers information about any subject around accessability. Very practical information can be found in the blog of Marko Zehe. When you are in Germany and have a chance to attend a conference talk from him, this is a must do! You can find more resources at the end of this post.
How to test
Now the tricky part - testing. Of course, the best way is to switch off the screen, fire up an assistive device and try to use your application. Most of the things that are not optimal yet will become very clear to you pretty fast. Working that way through your application together with the best practices specification from W3C will help you a lot to understand what is needed to make your application accessible.
JAWS is a commercial product, that is available in an evaluation form, that can be used for 40 minutes. When you want to continue to use it, you need to restart the computer. I read somewhere, that its license does not allow developers to use this version for testing, so you can use it only for evaluation. We contacted them because we saw JAWS doing things not correctly, to understand where the problem comes from. They outright answered to us, they don't provide support. Good thing, NVDA did most of the things correctly.
NVDA is one of the many free alternatives, that was mentioned to me a lot. It is not so widely used as JAWS, but it is increasing. And there are specific plug-ins for Firefox and Chrome.
But, there is a catch: Screen readers bring a whole new level of browser dependant behaviour. What the screen reader reads out varies not only between screen readers, but also based on the browser (and version) it is used with. So maybe it is a good idea to choose a screen reader / browser combination when you are starting to make your application accessible. Once again, choosing Firefox over Internet Explorer showed better results.
Yes it is hard to get started, and it is even harder to get it right, but it is an important thing to do, to allow everybody to take advantage of your application. Having the possibility to let your application checked by a regular user of assistive devices is enormously helpful.
I would be very interested to hear from you what specific requirements you have regarding accessibility that the framework should provide for you. Especially feedback about my changes are very welcome. The first batch should soon be in the repository, and hopefully soon in a beta near you.
Let's work together on this. It will take its time, but I am sure we will get there.
Resources
Michael works at the Vaadin team as GWT expert helping our customers in building custom widgets and solutions on top of Vaadin Framework and GWT.