A possible implementation would be:
HTML structure:
<div> <!-- Outer wrapper -->
<ul> <!-- Main navigation bar container -->
<li> <!-- First-level item without submenu -->
<a> <!-- Destination URL -->
</a>
</li>
<li> <!-- First-level item with submenu -->
<a> <!-- Destination URL -->
</a>
<ul> <!-- Second-level menu container -->
<li> <!-- Second-level item -->
<a>
</a> <!-- Destination URL -->
</li>
</ul>
</li>
</ul>
</div>
Roles:
- role=”navigation” for outer wrapper
<div>
- role=”menubar” for
<ul>
navigation bar container - role=”menu” for second-level
<ul>
containers - role=”presentation” for first- and second-level
<li>
menu items (they are not needed in the exposed accessible menubar structure) - role=”menuitem” for first- and second-level
<a>
menu items
Properties:
- aria-haspopup=”true” for first-level
<a>
menu items having a submenu - aria-labelledby=”ID of previous
<a>
menu item” for second-level<ul>
containers
States:
- aria-selected=”true” on currently visited first- or second-level
<a>
item; aria-selected=”false” on the other<a>
items. That is to enforce the concept “selected <==> current page” - aria-expanded=”true/false” for second-level
<ul>
containers - aria-hidden=”true/false” for second-level
<ul>
containers - aria-activedescendant=”” for main
<ul>
navigation bar container. This is an alternative to working with tabindex - tabindex=0 on currently visited
<a>
item; tabindex=-1 on the other<a>
items. That is in order to first focus on the current page when tabbing to the navigation bar. It is an alternative to working with aria-activedescendant
Keyboard:
- Tab: Move focus in/out of the menu from other points in the web application.
- Shift+Tab: Move focus in/out of the menu from other points in the web application, in the reversed order.
- Right arrow: Next navigation bar item
- Left arrow: Previous navigation bar item
- Enter: Activate currently focused item (i.e. navigate to corresponding URL)
- Space: Activate currently focused item (i.e. navigate to corresponding URL)
Aug/2014: aria-selected Vs menuitem
In reply to @Joshua Muheim comment: now I can see from here, as well as from his reference, that aria-selected
attribute is not allowed for menuitem
role.
As I read from this recent SO answer there are some solutions given the current state of things, and there is a new proposed attribute too.