33// @namespace http://axSgrease.nvaccess.org/
44// @description Improves the accessibility of GitHub.
55// @author James Teh <jamie@nvaccess.org>
6- // @copyright 2015 NV Access Limited
6+ // @copyright 2015-2016 NV Access Limited
77// @license GNU General Public License version 2.0
8- // @version 2015.3
8+ // @version 2016.1
99// @grant GM_log
1010// @include https://github.com/*
1111// ==/UserScript==
@@ -19,6 +19,23 @@ function onSelectMenuItemChanged(target) {
1919 target . setAttribute ( "aria-checked" , target . classList . contains ( "selected" ) ? "true" : "false" ) ;
2020}
2121
22+ function onDropdownChanged ( target ) {
23+ target . firstElementChild . setAttribute ( "aria-haspopup" , "true" ) ;
24+ var expanded = target . classList . contains ( "active" ) ;
25+ target . children [ 0 ] . setAttribute ( "aria-expanded" , expanded ? "true" : "false" ) ;
26+ var items = target . children [ 1 ] ;
27+ if ( expanded ) {
28+ items . removeAttribute ( "aria-hidden" ) ;
29+ // Focus the first item.
30+ var elem = items . querySelector ( "a,button" ) ;
31+ if ( elem )
32+ elem . focus ( ) ;
33+ } else {
34+ // Make sure the items are hidden.
35+ items . setAttribute ( "aria-hidden" , "true" ) ;
36+ }
37+ }
38+
2239// Used when we need to generate ids for ARIA.
2340var idCounter = 0 ;
2441
@@ -103,15 +120,35 @@ function onNodeAdded(target) {
103120 elem . setAttribute ( "title" , tooltip ) ;
104121 elem . removeAttribute ( "aria-label" ) ;
105122 }
123+ // Dropdowns; e.g. for "Add your reaction".
124+ if ( target . classList && target . classList . contains ( "dropdown" ) )
125+ onDropdownChanged ( target ) ;
126+ else {
127+ for ( elem of target . querySelectorAll ( ".dropdown" ) )
128+ onDropdownChanged ( elem ) ;
129+ }
130+ // Reactions.
131+ for ( elem of target . querySelectorAll ( ".add-reactions-options-item" ) )
132+ elem . setAttribute ( "aria-label" , elem . getAttribute ( "data-reaction-label" ) ) ;
133+ for ( elem of target . querySelectorAll ( ".user-has-reacted" ) ) {
134+ var user = elem . getAttribute ( "aria-label" ) ;
135+ // This will unfortunately change the visual presentation.
136+ elem . setAttribute ( "title" , user ) ;
137+ elem . setAttribute ( "aria-label" , user + " " + elem . getAttribute ( "value" ) ) ;
138+ }
106139}
107140
108141function onClassModified ( target ) {
109142 var classes = target . classList ;
110143 if ( ! classes )
111144 return ;
112- // Checkable menu items; e.g. in watch and labels pop-ups.
113- if ( classes . contains ( "select-menu-item" ) )
145+ if ( classes . contains ( "select-menu-item" ) ) {
146+ // Checkable menu items; e.g. in watch and labels pop-ups.
114147 onSelectMenuItemChanged ( target ) ;
148+ } else if ( classes . contains ( "dropdown" ) ) {
149+ // Container for a dropdown.
150+ onDropdownChanged ( target ) ;
151+ }
115152}
116153
117154var observer = new MutationObserver ( function ( mutations ) {
0 commit comments