Skip to content

Commit 92ce56d

Browse files
authored
Accessibility: add global event handler for anchors with button role triggering the click on spacebar keydown (#59578)
* Add global keydown event handler to anchors with button role * Remove specific event handlers duplicating global one * Remove specific event handler duplicating the global one in add-to-cart.js * Add changelog * Remove unnecessary comment and bring back previous styling * Replace jQuery code with vanilla JS
1 parent df5c949 commit 92ce56d

File tree

3 files changed

+33
-53
lines changed

3 files changed

+33
-53
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
Significance: patch
2+
Type: enhancement
3+
4+
Accessibility: add global event handler for anchors with button role triggering the click on spacebar keydown

plugins/woocommerce/client/legacy/js/frontend/add-to-cart.js

Lines changed: 0 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@ jQuery( function( $ ) {
1717
$( document.body )
1818
.on( 'click', '.add_to_cart_button:not(.wc-interactive)', { addToCartHandler: this }, this.onAddToCart )
1919
.on( 'click', '.remove_from_cart_button', { addToCartHandler: this }, this.onRemoveFromCart )
20-
.on( 'keydown', '.remove_from_cart_button', this.onKeydownRemoveFromCart )
2120
.on( 'added_to_cart', { addToCartHandler: this }, this.onAddedToCart )
2221
.on( 'removed_from_cart', { addToCartHandler: this }, this.onRemovedFromCart )
2322
.on( 'ajax_request_not_sent.adding_to_cart', this.updateButton );
@@ -170,18 +169,6 @@ jQuery( function( $ ) {
170169
});
171170
};
172171

173-
/**
174-
* Handle when pressing the Space key on the remove item link.
175-
* This is necessary because the link got the role="button" attribute
176-
* and needs to act like a button.
177-
*/
178-
AddToCartHandler.prototype.onKeydownRemoveFromCart = function( event ) {
179-
if ( event.key === ' ' ) {
180-
event.preventDefault();
181-
$( this ).trigger( 'click' );
182-
}
183-
};
184-
185172
/**
186173
* Update cart page elements after add to cart events.
187174
*/

plugins/woocommerce/client/legacy/js/frontend/woocommerce.js

Lines changed: 29 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,19 @@ jQuery( function ( $ ) {
1414
}
1515
} );
1616

17+
// Global accessibility handler for all links with role="button"
18+
// This ensures both spacebar and enter keypresses trigger click events, as per ARIA specification
19+
document.body.addEventListener( 'keydown', function ( event ) {
20+
if ( ! event.target.matches( 'a[role="button"]' ) ) {
21+
return;
22+
}
23+
24+
if ( event.key === ' ' || event.key === 'Enter' ) {
25+
event.preventDefault();
26+
event.target.click();
27+
}
28+
} );
29+
1730
var noticeID = $( '.woocommerce-store-notice' ).data( 'noticeId' ) || '',
1831
cookieName = 'store_notice' + noticeID;
1932

@@ -22,31 +35,22 @@ jQuery( function ( $ ) {
2235
$( '.woocommerce-store-notice' ).hide();
2336
} else {
2437
$( '.woocommerce-store-notice' ).show();
25-
/**
26-
* After adding the role="button" attribute to the
27-
* .woocommerce-store-notice__dismiss-link element,
28-
* we need to add the keydown event listener to it.
29-
*/
30-
function store_notice_keydown_handler( event ) {
31-
if ( ['Enter', ' '].includes( event.key ) ) {
32-
event.preventDefault();
33-
$( '.woocommerce-store-notice__dismiss-link' ).click();
34-
}
35-
}
3638

3739
// Set a cookie and hide the store notice when the dismiss button is clicked
3840
function store_notice_click_handler( event ) {
3941
Cookies.set( cookieName, 'hidden', { path: '/' } );
4042
$( '.woocommerce-store-notice' ).hide();
4143
event.preventDefault();
42-
$( '.woocommerce-store-notice__dismiss-link' )
43-
.off( 'click', store_notice_click_handler )
44-
.off( 'keydown', store_notice_keydown_handler );
44+
$( '.woocommerce-store-notice__dismiss-link' ).off(
45+
'click',
46+
store_notice_click_handler
47+
);
4548
}
46-
47-
$( '.woocommerce-store-notice__dismiss-link' )
48-
.on( 'click', store_notice_click_handler )
49-
.on( 'keydown', store_notice_keydown_handler );
49+
50+
$( '.woocommerce-store-notice__dismiss-link' ).on(
51+
'click',
52+
store_notice_click_handler
53+
);
5054
}
5155

5256
// Make form field descriptions toggle on focus.
@@ -182,27 +186,12 @@ jQuery( function ( $ ) {
182186
} );
183187
} );
184188

185-
// If the "Enable AJAX add to cart buttons on archives" setting is disabled
186-
// the add-to-cart.js file won't be loaded, so we need to add the event listener here.
187-
if ( typeof wc_add_to_cart_params === 'undefined') {
188-
$( document.body ).on( 'keydown', '.remove_from_cart_button', on_keydown_remove_from_cart );
189-
}
190-
191-
$( document.body ).on( 'item_removed_from_classic_cart updated_wc_div', focus_populate_live_region );
189+
$( document.body ).on(
190+
'item_removed_from_classic_cart updated_wc_div',
191+
focus_populate_live_region
192+
);
192193
} );
193194

194-
/**
195-
* Handle when pressing the Space key on the remove item link.
196-
* This is necessary because the link has the role="button" attribute
197-
* and needs to act like a button.
198-
*/
199-
function on_keydown_remove_from_cart( event ) {
200-
if ( event.key === ' ' ) {
201-
event.preventDefault();
202-
event.currentTarget.click();
203-
}
204-
}
205-
206195
/**
207196
* Focus on the first notice element on the page.
208197
*
@@ -248,10 +237,10 @@ function refresh_sorted_by_live_region() {
248237

249238
if ( sorted_by_live_region ) {
250239
var text = sorted_by_live_region.innerHTML;
251-
sorted_by_live_region.setAttribute('aria-hidden', 'true');
252-
240+
sorted_by_live_region.setAttribute( 'aria-hidden', 'true' );
241+
253242
var sorted_by_live_region_id = setTimeout( function () {
254-
sorted_by_live_region.setAttribute('aria-hidden', 'false');
243+
sorted_by_live_region.setAttribute( 'aria-hidden', 'false' );
255244
sorted_by_live_region.innerHTML = '';
256245
sorted_by_live_region.innerHTML = text;
257246
clearTimeout( sorted_by_live_region_id );

0 commit comments

Comments
 (0)