From 009ae3911c421ca99e31d52c38bf01738e6a5435 Mon Sep 17 00:00:00 2001 From: Christoph Daum Date: Tue, 7 Apr 2026 00:33:45 +0200 Subject: [PATCH 1/3] feat(toolbar): add keyboard shortcut to toggle toolbar visibility MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add access+w (Alt+Shift+W / Ctrl+Option+W) keyboard shortcut to temporarily hide/show the toolbar on the frontend. Slides the bar out with a CSS transition and adjusts page spacing via the --wp-admin--admin-bar--height custom property. Includes screen reader announcements for accessibility. Frontend only — the toolbar remains fixed in wp-admin per existing core policy. --- src/js/_enqueues/lib/admin-bar.js | 75 ++++++++++++++++++++++++++ src/wp-includes/class-wp-admin-bar.php | 9 ++++ src/wp-includes/css/admin-bar.css | 18 +++++++ 3 files changed, 102 insertions(+) diff --git a/src/js/_enqueues/lib/admin-bar.js b/src/js/_enqueues/lib/admin-bar.js index eb18c61f8b5b8..7fed19582efdf 100644 --- a/src/js/_enqueues/lib/admin-bar.js +++ b/src/js/_enqueues/lib/admin-bar.js @@ -23,6 +23,7 @@ skipLink, mobileEvent, adminBarSearchInput, + isMac = /Mac|iPhone|iPad|iPod/.test( navigator.platform ), i; if ( ! adminBar || ! ( 'querySelectorAll' in adminBar ) ) { @@ -108,8 +109,82 @@ if ( adminBarLogout ) { adminBarLogout.addEventListener( 'click', emptySessionStorage ); } + + // Toggle toolbar visibility with access+w keyboard shortcut (frontend only). + if ( ! document.body.classList.contains( 'wp-admin' ) ) { + document.addEventListener( 'keydown', function( event ) { + var isAccessModifier; + + if ( event.which !== 87 ) { // 'W' key. + return; + } + + if ( isMac ) { + isAccessModifier = event.ctrlKey && event.altKey && ! event.metaKey && ! event.shiftKey; + } else { + isAccessModifier = event.altKey && event.shiftKey && ! event.ctrlKey && ! event.metaKey; + } + + if ( ! isAccessModifier ) { + return; + } + + event.preventDefault(); + toggleToolbar( adminBar ); + } ); + } } ); + /** + * Toggle the toolbar visibility. + * + * Slides the toolbar out of view and adjusts page spacing by toggling + * the `wp-toolbar-hidden` class on the document element. + * + * @since 6.9.0 + * + * @param {HTMLElement} adminBar The admin bar element. + */ + function toggleToolbar( adminBar ) { + var isHidden = document.documentElement.classList.toggle( 'wp-toolbar-hidden' ); + + adminBar.setAttribute( 'aria-hidden', isHidden ? 'true' : 'false' ); + announceToolbarState( isHidden ); + } + + /** + * Announce toolbar visibility state to screen readers. + * + * @since 6.9.0 + * + * @param {boolean} isHidden Whether the toolbar is hidden. + */ + function announceToolbarState( isHidden ) { + var message = isHidden ? window.wpAdminBarL10n.toolbarHidden : window.wpAdminBarL10n.toolbarVisible, + el; + + if ( ! message ) { + return; + } + + el = document.getElementById( 'wp-toolbar-announce' ); + + if ( ! el ) { + el = document.createElement( 'div' ); + el.id = 'wp-toolbar-announce'; + el.className = 'screen-reader-text'; + el.setAttribute( 'role', 'status' ); + el.setAttribute( 'aria-live', 'polite' ); + document.body.appendChild( el ); + } + + // Clear then set to ensure screen readers re-announce. + el.textContent = ''; + setTimeout( function() { + el.textContent = message; + }, 100 ); + } + /** * Remove hover class for top level menu item when escape is pressed. * diff --git a/src/wp-includes/class-wp-admin-bar.php b/src/wp-includes/class-wp-admin-bar.php index dfebbb20e4c86..f3f5dd7ecc4c2 100644 --- a/src/wp-includes/class-wp-admin-bar.php +++ b/src/wp-includes/class-wp-admin-bar.php @@ -72,6 +72,15 @@ public function initialize() { wp_enqueue_script( 'admin-bar' ); wp_enqueue_style( 'admin-bar' ); + wp_localize_script( + 'admin-bar', + 'wpAdminBarL10n', + array( + 'toolbarHidden' => __( 'Toolbar hidden.' ), + 'toolbarVisible' => __( 'Toolbar visible.' ), + ) + ); + /** * Fires after WP_Admin_Bar is initialized. * diff --git a/src/wp-includes/css/admin-bar.css b/src/wp-includes/css/admin-bar.css index 7f89c7a942de4..5a362c64deed7 100644 --- a/src/wp-includes/css/admin-bar.css +++ b/src/wp-includes/css/admin-bar.css @@ -99,6 +99,24 @@ html:lang(he-il) .rtl #wpadminbar * { background: #1d2327; /* Only visible in Windows High Contrast mode */ outline: 1px solid transparent; + transition: transform 0.2s ease-in-out, visibility 0.2s ease-in-out; +} + +/** + * Toolbar toggle hidden state. + * + * Toggled via access+w keyboard shortcut on the frontend. + * Sets the admin bar height variable to 0 so all dependent spacing + * (scroll-padding, bump margin) adjusts automatically. + */ +html.wp-toolbar-hidden { + --wp-admin--admin-bar--height: 0px; + margin-top: 0 !important; +} + +html.wp-toolbar-hidden #wpadminbar { + transform: translateY(-100%); + visibility: hidden; } #wpadminbar .ab-sub-wrapper, From 603434167aab6b2e346c8f3fef6a6456d095bcc5 Mon Sep 17 00:00:00 2001 From: Christoph Daum Date: Tue, 7 Apr 2026 09:11:49 +0200 Subject: [PATCH 2/3] chore(toolbar): change (at)since to TBD --- src/js/_enqueues/lib/admin-bar.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/js/_enqueues/lib/admin-bar.js b/src/js/_enqueues/lib/admin-bar.js index 7fed19582efdf..eb2c79c0d2208 100644 --- a/src/js/_enqueues/lib/admin-bar.js +++ b/src/js/_enqueues/lib/admin-bar.js @@ -141,7 +141,7 @@ * Slides the toolbar out of view and adjusts page spacing by toggling * the `wp-toolbar-hidden` class on the document element. * - * @since 6.9.0 + * @since TBD * * @param {HTMLElement} adminBar The admin bar element. */ @@ -155,7 +155,7 @@ /** * Announce toolbar visibility state to screen readers. * - * @since 6.9.0 + * @since TBD * * @param {boolean} isHidden Whether the toolbar is hidden. */ From 0acc2d5551e042f12378ecae1b2fa926a5acffc1 Mon Sep 17 00:00:00 2001 From: Christoph Daum Date: Tue, 7 Apr 2026 10:18:54 +0200 Subject: [PATCH 3/3] refactor(toolbar): use Ctrl+Shift+F shortcut Replace access+w (Ctrl+Option+W / Alt+Shift+W) with Ctrl+Shift+F. Unified across all platforms, no per-OS modifier branching needed. --- src/js/_enqueues/lib/admin-bar.js | 17 ++--------------- src/wp-includes/css/admin-bar.css | 2 +- 2 files changed, 3 insertions(+), 16 deletions(-) diff --git a/src/js/_enqueues/lib/admin-bar.js b/src/js/_enqueues/lib/admin-bar.js index eb2c79c0d2208..7143fbd3d2429 100644 --- a/src/js/_enqueues/lib/admin-bar.js +++ b/src/js/_enqueues/lib/admin-bar.js @@ -23,7 +23,6 @@ skipLink, mobileEvent, adminBarSearchInput, - isMac = /Mac|iPhone|iPad|iPod/.test( navigator.platform ), i; if ( ! adminBar || ! ( 'querySelectorAll' in adminBar ) ) { @@ -110,22 +109,10 @@ adminBarLogout.addEventListener( 'click', emptySessionStorage ); } - // Toggle toolbar visibility with access+w keyboard shortcut (frontend only). + // Toggle toolbar visibility with Ctrl+Shift+F keyboard shortcut (frontend only). if ( ! document.body.classList.contains( 'wp-admin' ) ) { document.addEventListener( 'keydown', function( event ) { - var isAccessModifier; - - if ( event.which !== 87 ) { // 'W' key. - return; - } - - if ( isMac ) { - isAccessModifier = event.ctrlKey && event.altKey && ! event.metaKey && ! event.shiftKey; - } else { - isAccessModifier = event.altKey && event.shiftKey && ! event.ctrlKey && ! event.metaKey; - } - - if ( ! isAccessModifier ) { + if ( event.which !== 70 || ! event.ctrlKey || ! event.shiftKey || event.altKey || event.metaKey ) { // Ctrl+Shift+F. return; } diff --git a/src/wp-includes/css/admin-bar.css b/src/wp-includes/css/admin-bar.css index 5a362c64deed7..20da7b2949503 100644 --- a/src/wp-includes/css/admin-bar.css +++ b/src/wp-includes/css/admin-bar.css @@ -105,7 +105,7 @@ html:lang(he-il) .rtl #wpadminbar * { /** * Toolbar toggle hidden state. * - * Toggled via access+w keyboard shortcut on the frontend. + * Toggled via Ctrl+Shift+F keyboard shortcut on the frontend. * Sets the admin bar height variable to 0 so all dependent spacing * (scroll-padding, bump margin) adjusts automatically. */