I’ll build this as a reusable RX Theme accessibility utility CSS file: screen-reader helpers, focus states, skip links, reduced motion, high contrast, keyboard navigation, touch targets, forms, media, tables, print, and WordPress-specific accessibility helpers.
Friend, place this full code inside:
assets/static/static-css/utilities/accessibility.css
/*!
Theme Name: RX Theme
File: assets/static/static-css/utilities/accessibility.css
Purpose: Advanced accessibility utilities for keyboard, screen reader, focus, contrast,
reduced motion, forms, tables, media, WordPress content, and UI states.
Author: RxHarun
*/
/* ==========================================================================
01. Accessibility Design Tokens
========================================================================== */
:root {
--rx-a11y-focus-color: #005fcc;
--rx-a11y-focus-color-alt: #ffffff;
--rx-a11y-focus-ring: 0 0 0 3px rgba(0, 95, 204, 0.35);
--rx-a11y-focus-ring-strong: 0 0 0 4px rgba(0, 95, 204, 0.55);
--rx-a11y-focus-offset: 3px;
--rx-a11y-error-color: #b00020;
--rx-a11y-success-color: #087f23;
--rx-a11y-warning-color: #8a5a00;
--rx-a11y-info-color: #005fcc;
--rx-a11y-text-high: #111111;
--rx-a11y-text-muted: #555555;
--rx-a11y-bg-high: #ffffff;
--rx-a11y-border: #767676;
--rx-a11y-touch-target: 44px;
--rx-a11y-line-height-readable: 1.65;
--rx-a11y-skip-bg: #000000;
--rx-a11y-skip-color: #ffffff;
--rx-a11y-transition-fast: 150ms ease;
}
/* ==========================================================================
02. Global Readability Foundation
========================================================================== */
html {
-webkit-text-size-adjust: 100%;
text-size-adjust: 100%;
scroll-behavior: smooth;
}
body {
text-rendering: optimizeLegibility;
}
main,
article,
section,
aside,
nav,
header,
footer {
scroll-margin-top: 6rem;
}
p,
li,
dd,
figcaption {
line-height: var(--rx-a11y-line-height-readable);
}
img,
svg,
video,
canvas {
max-width: 100%;
}
img {
height: auto;
}
[hidden] {
display: none !important;
}
/* Prevent accidental horizontal overflow for long URLs or medical terms */
.rx-content,
.entry-content,
.post-content,
.page-content {
overflow-wrap: break-word;
word-wrap: break-word;
}
/* ==========================================================================
03. Screen Reader Utilities
========================================================================== */
.screen-reader-text,
.sr-only,
.rx-sr-only,
.visually-hidden,
.rx-visually-hidden {
position: absolute !important;
width: 1px !important;
height: 1px !important;
min-width: 0 !important;
min-height: 0 !important;
padding: 0 !important;
margin: -1px !important;
overflow: hidden !important;
clip: rect(0, 0, 0, 0) !important;
clip-path: inset(50%) !important;
white-space: nowrap !important;
border: 0 !important;
}
.screen-reader-text:focus,
.sr-only-focusable:focus,
.rx-sr-only-focusable:focus,
.rx-visually-hidden-focusable:focus {
position: fixed !important;
z-index: 999999 !important;
top: 1rem !important;
left: 1rem !important;
width: auto !important;
height: auto !important;
min-width: auto !important;
min-height: auto !important;
padding: 0.75rem 1rem !important;
margin: 0 !important;
overflow: visible !important;
clip: auto !important;
clip-path: none !important;
white-space: normal !important;
color: var(--rx-a11y-skip-color) !important;
background: var(--rx-a11y-skip-bg) !important;
border: 2px solid var(--rx-a11y-focus-color-alt) !important;
border-radius: 0.375rem !important;
box-shadow: var(--rx-a11y-focus-ring-strong) !important;
text-decoration: none !important;
}
.rx-not-sr-only {
position: static !important;
width: auto !important;
height: auto !important;
padding: initial !important;
margin: initial !important;
overflow: visible !important;
clip: auto !important;
clip-path: none !important;
white-space: normal !important;
}
/* ==========================================================================
04. Skip Links
========================================================================== */
.skip-link,
.rx-skip-link,
.rx-skip-to-content {
position: fixed;
z-index: 999999;
top: 1rem;
left: 1rem;
transform: translateY(-150%);
display: inline-flex;
align-items: center;
justify-content: center;
min-height: var(--rx-a11y-touch-target);
padding: 0.75rem 1rem;
color: var(--rx-a11y-skip-color);
background: var(--rx-a11y-skip-bg);
border: 2px solid var(--rx-a11y-focus-color-alt);
border-radius: 0.375rem;
font-weight: 700;
line-height: 1.2;
text-decoration: none;
box-shadow: var(--rx-a11y-focus-ring);
transition: transform var(--rx-a11y-transition-fast);
}
.skip-link:focus,
.rx-skip-link:focus,
.rx-skip-to-content:focus {
transform: translateY(0);
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: var(--rx-a11y-focus-offset);
}
/* ==========================================================================
05. Focus System
========================================================================== */
:focus {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: var(--rx-a11y-focus-offset);
}
:focus:not(:focus-visible) {
outline: none;
}
:focus-visible {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: var(--rx-a11y-focus-offset);
box-shadow: var(--rx-a11y-focus-ring);
}
a:focus-visible,
button:focus-visible,
input:focus-visible,
select:focus-visible,
textarea:focus-visible,
summary:focus-visible,
[tabindex]:focus-visible,
[role="button"]:focus-visible,
[role="link"]:focus-visible,
[role="menuitem"]:focus-visible,
[role="tab"]:focus-visible,
[role="checkbox"]:focus-visible,
[role="radio"]:focus-visible,
[role="switch"]:focus-visible {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: var(--rx-a11y-focus-offset);
box-shadow: var(--rx-a11y-focus-ring);
}
.rx-focus-ring:focus-visible {
outline: 3px solid var(--rx-a11y-focus-color) !important;
outline-offset: var(--rx-a11y-focus-offset) !important;
box-shadow: var(--rx-a11y-focus-ring) !important;
}
.rx-focus-ring-inset:focus-visible {
outline: 3px solid var(--rx-a11y-focus-color) !important;
outline-offset: -3px !important;
box-shadow: inset 0 0 0 3px var(--rx-a11y-focus-color) !important;
}
.rx-focus-none:focus,
.rx-focus-none:focus-visible {
outline: none !important;
box-shadow: none !important;
}
/* Use only when another visible focus indicator exists */
.rx-focus-custom:focus,
.rx-focus-custom:focus-visible {
outline: none;
}
/* ==========================================================================
06. Keyboard Navigation Helpers
========================================================================== */
.rx-keyboard-only,
.rx-keyboard-visible {
display: none;
}
body.rx-using-keyboard .rx-keyboard-only,
body.rx-using-keyboard .rx-keyboard-visible {
display: initial;
}
body.rx-using-mouse :focus {
outline: none;
}
.rx-tab-target,
[tabindex="0"] {
scroll-margin: 6rem;
}
[tabindex="-1"]:focus {
outline: none;
}
.rx-no-tab {
pointer-events: none;
}
/* ==========================================================================
07. Links and Text Accessibility
========================================================================== */
a {
text-decoration-thickness: max(1px, 0.08em);
text-underline-offset: 0.16em;
}
a:hover,
a:focus-visible {
text-decoration-thickness: max(2px, 0.12em);
}
.rx-link-underline {
text-decoration: underline !important;
text-decoration-thickness: max(1px, 0.08em) !important;
text-underline-offset: 0.16em !important;
}
.rx-link-no-underline {
text-decoration: none !important;
}
.rx-link-no-underline:hover,
.rx-link-no-underline:focus-visible {
text-decoration: underline !important;
}
.rx-external-link::after {
content: " ↗";
font-size: 0.85em;
}
.rx-content a[href^="http"]:not([href*="rxharun.com"])::after {
content: " ↗";
font-size: 0.85em;
}
.rx-readable {
max-width: 75ch;
line-height: var(--rx-a11y-line-height-readable);
}
.rx-text-balance {
text-wrap: balance;
}
.rx-text-pretty {
text-wrap: pretty;
}
.rx-no-color-only {
text-decoration: underline;
font-weight: 600;
}
/* ==========================================================================
08. Touch Target Accessibility
========================================================================== */
button,
[type="button"],
[type="submit"],
[type="reset"],
a.button,
.wp-block-button__link,
.rx-button,
.rx-btn,
[role="button"] {
min-width: var(--rx-a11y-touch-target);
min-height: var(--rx-a11y-touch-target);
}
.rx-touch-target {
min-width: var(--rx-a11y-touch-target) !important;
min-height: var(--rx-a11y-touch-target) !important;
}
.rx-touch-target-inline {
display: inline-flex !important;
align-items: center !important;
justify-content: center !important;
min-width: var(--rx-a11y-touch-target) !important;
min-height: var(--rx-a11y-touch-target) !important;
}
.rx-click-area {
position: relative;
}
.rx-click-area::before {
content: "";
position: absolute;
inset: -0.5rem;
}
/* ==========================================================================
09. Buttons and Interactive State Helpers
========================================================================== */
button,
[role="button"],
summary {
cursor: pointer;
}
button:disabled,
input:disabled,
select:disabled,
textarea:disabled,
[aria-disabled="true"],
.rx-disabled {
cursor: not-allowed !important;
opacity: 0.6;
}
[aria-disabled="true"] {
pointer-events: none;
}
.rx-loading,
[aria-busy="true"] {
cursor: progress;
}
.rx-hidden-interactive[aria-hidden="true"] {
pointer-events: none;
}
details > summary {
list-style-position: inside;
}
summary::-webkit-details-marker {
display: inline-block;
}
/* ==========================================================================
10. Forms Accessibility
========================================================================== */
label {
cursor: pointer;
}
input,
select,
textarea {
font: inherit;
}
input,
select,
textarea,
.rx-form-control {
min-height: var(--rx-a11y-touch-target);
}
textarea {
min-height: 7rem;
resize: vertical;
}
fieldset {
border: 1px solid var(--rx-a11y-border);
}
legend {
padding-inline: 0.35rem;
font-weight: 700;
}
::placeholder {
color: #666666;
opacity: 1;
}
.required,
.rx-required,
[aria-required="true"] + label::after {
color: var(--rx-a11y-error-color);
}
.rx-field-help,
.rx-form-help,
.description {
color: var(--rx-a11y-text-muted);
font-size: 0.9375rem;
line-height: 1.5;
}
.rx-field-error,
.rx-form-error,
[aria-invalid="true"] {
border-color: var(--rx-a11y-error-color) !important;
}
[aria-invalid="true"]:focus-visible {
outline-color: var(--rx-a11y-error-color);
box-shadow: 0 0 0 3px rgba(176, 0, 32, 0.25);
}
.rx-error-message,
.rx-validation-error {
color: var(--rx-a11y-error-color);
font-weight: 600;
}
.rx-success-message {
color: var(--rx-a11y-success-color);
font-weight: 600;
}
.rx-warning-message {
color: var(--rx-a11y-warning-color);
font-weight: 600;
}
.rx-info-message {
color: var(--rx-a11y-info-color);
font-weight: 600;
}
input[type="checkbox"],
input[type="radio"] {
width: 1.125rem;
height: 1.125rem;
min-width: 1.125rem;
min-height: 1.125rem;
}
input[type="search"] {
-webkit-appearance: textfield;
appearance: textfield;
}
input[type="search"]::-webkit-search-decoration {
-webkit-appearance: none;
}
/* ==========================================================================
11. Form Utility Layouts
========================================================================== */
.rx-form-row {
display: grid;
gap: 0.5rem;
}
.rx-form-row + .rx-form-row {
margin-top: 1rem;
}
.rx-checkbox-row,
.rx-radio-row {
display: flex;
align-items: flex-start;
gap: 0.625rem;
}
.rx-checkbox-row label,
.rx-radio-row label {
line-height: 1.45;
}
.rx-input-with-button {
display: flex;
gap: 0.5rem;
align-items: stretch;
}
.rx-input-with-button input {
flex: 1 1 auto;
}
/* ==========================================================================
12. ARIA State Utilities
========================================================================== */
[aria-hidden="true"] {
speak: never;
}
[aria-current="page"],
.rx-current-page {
font-weight: 700;
}
[aria-current="page"]::before {
content: "";
}
[aria-expanded="true"] .rx-icon-expand,
[aria-expanded="true"] .rx-caret {
transform: rotate(180deg);
}
[aria-selected="true"],
.rx-is-selected {
font-weight: 700;
}
[aria-pressed="true"],
.rx-is-pressed {
box-shadow: inset 0 0 0 2px currentColor;
}
[aria-busy="true"] {
position: relative;
}
[aria-busy="true"]::after {
content: "";
display: inline-block;
width: 1em;
height: 1em;
margin-inline-start: 0.5em;
border: 2px solid currentColor;
border-right-color: transparent;
border-radius: 50%;
vertical-align: -0.15em;
animation: rx-a11y-spin 0.8s linear infinite;
}
@keyframes rx-a11y-spin {
to {
transform: rotate(360deg);
}
}
/* ==========================================================================
13. Reduced Motion Support
========================================================================== */
@media (prefers-reduced-motion: reduce) {
html {
scroll-behavior: auto !important;
}
*,
*::before,
*::after {
animation-duration: 0.001ms !important;
animation-iteration-count: 1 !important;
scroll-behavior: auto !important;
transition-duration: 0.001ms !important;
}
video,
.rx-autoplay,
.rx-parallax,
.rx-marquee,
.rx-slider,
.rx-carousel {
animation: none !important;
transition: none !important;
}
[aria-busy="true"]::after {
animation: none !important;
}
}
.rx-reduce-motion *,
.rx-reduce-motion *::before,
.rx-reduce-motion *::after {
animation: none !important;
scroll-behavior: auto !important;
transition: none !important;
}
/* ==========================================================================
14. High Contrast and Forced Colors
========================================================================== */
@media (forced-colors: active) {
* {
forced-color-adjust: auto;
}
a {
color: LinkText;
}
button,
input,
select,
textarea,
.rx-button,
.rx-btn {
border: 1px solid ButtonText;
}
:focus,
:focus-visible {
outline: 3px solid Highlight !important;
outline-offset: 3px !important;
box-shadow: none !important;
}
.skip-link,
.rx-skip-link,
.screen-reader-text:focus {
color: HighlightText !important;
background: Highlight !important;
border-color: HighlightText !important;
}
[aria-current="page"],
.rx-current-page {
outline: 1px solid Highlight;
}
}
@media (prefers-contrast: more) {
:root {
--rx-a11y-focus-color: #003d99;
--rx-a11y-focus-ring: 0 0 0 4px rgba(0, 61, 153, 0.55);
--rx-a11y-text-muted: #333333;
--rx-a11y-border: #333333;
}
a {
text-decoration-thickness: max(2px, 0.12em);
}
button,
input,
select,
textarea {
border-width: 2px;
}
}
/* ==========================================================================
15. Color Scheme Accessibility
========================================================================== */
@media (prefers-color-scheme: dark) {
:root {
--rx-a11y-focus-color: #7ab7ff;
--rx-a11y-focus-color-alt: #000000;
--rx-a11y-text-high: #f5f5f5;
--rx-a11y-text-muted: #cccccc;
--rx-a11y-bg-high: #111111;
--rx-a11y-border: #aaaaaa;
--rx-a11y-error-color: #ff8a9a;
--rx-a11y-success-color: #7ee787;
--rx-a11y-warning-color: #ffd166;
--rx-a11y-info-color: #7ab7ff;
}
}
.rx-high-contrast {
color: #000000 !important;
background: #ffffff !important;
}
.rx-high-contrast a {
color: #003d99 !important;
}
.rx-invert-contrast {
color: #ffffff !important;
background: #000000 !important;
}
.rx-invert-contrast a {
color: #9dccff !important;
}
/* ==========================================================================
16. Navigation Accessibility
========================================================================== */
nav ul,
.rx-nav ul,
.menu {
list-style: none;
}
nav a,
.rx-nav a,
.menu a {
min-height: var(--rx-a11y-touch-target);
}
.rx-nav a[aria-current="page"],
.menu a[aria-current="page"],
.current-menu-item > a,
.current_page_item > a {
font-weight: 700;
text-decoration: underline;
text-underline-offset: 0.2em;
}
.rx-nav-toggle[aria-expanded="true"] + .rx-nav-panel {
display: block;
}
.rx-nav-panel[hidden] {
display: none !important;
}
.rx-menu-item-has-children > a,
.menu-item-has-children > a {
position: relative;
}
.rx-dropdown-menu {
z-index: 1000;
}
.rx-dropdown-menu[aria-hidden="true"] {
display: none;
}
.rx-dropdown-menu[aria-hidden="false"] {
display: block;
}
/* ==========================================================================
17. Modal, Dialog, Drawer Accessibility
========================================================================== */
dialog {
max-width: min(90vw, 42rem);
max-height: 90vh;
padding: 0;
border: 0;
border-radius: 0.75rem;
}
dialog::backdrop {
background: rgba(0, 0, 0, 0.65);
}
.rx-dialog,
.rx-modal,
.rx-drawer {
color: var(--rx-a11y-text-high);
background: var(--rx-a11y-bg-high);
}
.rx-modal[aria-hidden="true"],
.rx-dialog[aria-hidden="true"],
.rx-drawer[aria-hidden="true"] {
display: none !important;
}
.rx-modal[aria-hidden="false"],
.rx-dialog[aria-hidden="false"],
.rx-drawer[aria-hidden="false"] {
display: block;
}
.rx-modal-close,
.rx-dialog-close,
.rx-drawer-close {
min-width: var(--rx-a11y-touch-target);
min-height: var(--rx-a11y-touch-target);
}
body.rx-modal-open,
body.rx-dialog-open,
body.rx-drawer-open {
overflow: hidden;
}
/* ==========================================================================
18. Tables Accessibility
========================================================================== */
table {
border-collapse: collapse;
}
caption {
font-weight: 700;
text-align: start;
margin-block-end: 0.5rem;
}
th {
text-align: start;
}
th,
td {
vertical-align: top;
}
.rx-table-responsive {
overflow-x: auto;
-webkit-overflow-scrolling: touch;
}
.rx-table-responsive:focus {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: var(--rx-a11y-focus-offset);
}
.rx-table-responsive table {
min-width: 42rem;
}
.rx-table-caption {
caption-side: top;
}
.rx-table-sticky-header th {
position: sticky;
top: 0;
z-index: 1;
background: var(--rx-a11y-bg-high);
}
/* ==========================================================================
19. Media Accessibility
========================================================================== */
figure {
margin-inline: 0;
}
figcaption {
color: var(--rx-a11y-text-muted);
}
video[controls],
audio[controls] {
width: 100%;
}
.rx-media-caption,
.wp-caption-text {
color: var(--rx-a11y-text-muted);
font-size: 0.9375rem;
line-height: 1.5;
}
.rx-decorative {
pointer-events: none;
}
img[alt=""] {
speak: never;
}
.rx-image-link {
display: inline-block;
}
.rx-image-link:focus-visible {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: 4px;
}
/* ==========================================================================
20. Icons Accessibility
========================================================================== */
.rx-icon[aria-hidden="true"],
.icon[aria-hidden="true"],
svg[aria-hidden="true"] {
speak: never;
}
.rx-icon-button {
display: inline-flex;
align-items: center;
justify-content: center;
min-width: var(--rx-a11y-touch-target);
min-height: var(--rx-a11y-touch-target);
}
.rx-icon-button svg {
width: 1.25em;
height: 1.25em;
}
/* ==========================================================================
21. Alerts, Notices, Toasts
========================================================================== */
[role="alert"],
.rx-alert,
.rx-notice,
.rx-toast {
padding: 1rem;
border: 1px solid currentColor;
border-radius: 0.5rem;
line-height: 1.5;
}
.rx-alert-error,
.rx-notice-error {
color: var(--rx-a11y-error-color);
}
.rx-alert-success,
.rx-notice-success {
color: var(--rx-a11y-success-color);
}
.rx-alert-warning,
.rx-notice-warning {
color: var(--rx-a11y-warning-color);
}
.rx-alert-info,
.rx-notice-info {
color: var(--rx-a11y-info-color);
}
.rx-toast {
position: fixed;
z-index: 99999;
right: 1rem;
bottom: 1rem;
max-width: min(24rem, calc(100vw - 2rem));
background: var(--rx-a11y-bg-high);
}
/* ==========================================================================
22. Live Region Utilities
========================================================================== */
.rx-live-region,
.rx-status-region,
.rx-announcer {
position: absolute !important;
width: 1px !important;
height: 1px !important;
overflow: hidden !important;
clip-path: inset(50%) !important;
white-space: nowrap !important;
}
[role="status"],
[aria-live] {
overflow-wrap: break-word;
}
/* ==========================================================================
23. WordPress Core Accessibility Helpers
========================================================================== */
.aligncenter {
display: block;
margin-inline: auto;
}
.wp-caption {
max-width: 100%;
}
.wp-caption img {
display: block;
}
.gallery {
display: grid;
gap: 1rem;
}
.gallery-item a:focus-visible,
.wp-block-image a:focus-visible,
.wp-block-gallery a:focus-visible {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: 4px;
}
.wp-block-button__link:focus-visible,
.wp-block-file__button:focus-visible {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: var(--rx-a11y-focus-offset);
box-shadow: var(--rx-a11y-focus-ring);
}
.wp-block-navigation a[aria-current="page"] {
font-weight: 700;
text-decoration: underline;
}
.wp-block-search__input {
min-height: var(--rx-a11y-touch-target);
}
.wp-block-search__button {
min-height: var(--rx-a11y-touch-target);
}
.comment-form input,
.comment-form textarea {
width: 100%;
}
.comment-reply-link,
.logged-in-as a {
min-height: var(--rx-a11y-touch-target);
}
/* ==========================================================================
24. WordPress Admin Bar Frontend Safety
========================================================================== */
.admin-bar .skip-link:focus,
.admin-bar .rx-skip-link:focus,
.admin-bar .screen-reader-text:focus {
top: calc(32px + 1rem) !important;
}
@media (max-width: 782px) {
.admin-bar .skip-link:focus,
.admin-bar .rx-skip-link:focus,
.admin-bar .screen-reader-text:focus {
top: calc(46px + 1rem) !important;
}
}
/* ==========================================================================
25. Medical Content Accessibility Helpers
========================================================================== */
.rx-medical-term {
font-weight: 700;
}
.rx-medical-warning {
padding: 1rem;
border-inline-start: 4px solid var(--rx-a11y-warning-color);
background: rgba(138, 90, 0, 0.08);
}
.rx-medical-danger,
.rx-emergency-note {
padding: 1rem;
border-inline-start: 4px solid var(--rx-a11y-error-color);
background: rgba(176, 0, 32, 0.08);
}
.rx-medical-info {
padding: 1rem;
border-inline-start: 4px solid var(--rx-a11y-info-color);
background: rgba(0, 95, 204, 0.08);
}
.rx-disclaimer {
font-size: 0.9375rem;
line-height: 1.6;
color: var(--rx-a11y-text-muted);
}
.rx-definition-list dt {
font-weight: 700;
}
.rx-definition-list dd {
margin-inline-start: 0;
margin-block-end: 1rem;
}
/* ==========================================================================
26. Search Accessibility
========================================================================== */
.rx-search-form {
display: flex;
gap: 0.5rem;
align-items: stretch;
}
.rx-search-form label {
width: 100%;
}
.rx-search-form input[type="search"] {
width: 100%;
}
.rx-search-results-count {
font-weight: 700;
}
.rx-no-results {
padding: 1rem;
border: 1px solid var(--rx-a11y-border);
border-radius: 0.5rem;
}
/* ==========================================================================
27. Pagination Accessibility
========================================================================== */
.pagination,
.nav-links,
.rx-pagination {
display: flex;
flex-wrap: wrap;
gap: 0.5rem;
}
.page-numbers,
.rx-page-number {
display: inline-flex;
align-items: center;
justify-content: center;
min-width: var(--rx-a11y-touch-target);
min-height: var(--rx-a11y-touch-target);
padding: 0.5rem 0.75rem;
}
.page-numbers.current,
.rx-page-number[aria-current="page"] {
font-weight: 700;
text-decoration: underline;
outline: 2px solid currentColor;
}
/* ==========================================================================
28. Breadcrumb Accessibility
========================================================================== */
.breadcrumb,
.breadcrumbs,
.rx-breadcrumb {
font-size: 0.9375rem;
}
.breadcrumb ol,
.breadcrumbs ol,
.rx-breadcrumb ol {
display: flex;
flex-wrap: wrap;
gap: 0.35rem;
padding: 0;
margin: 0;
list-style: none;
}
.breadcrumb li,
.breadcrumbs li,
.rx-breadcrumb li {
display: inline-flex;
align-items: center;
}
.breadcrumb li + li::before,
.breadcrumbs li + li::before,
.rx-breadcrumb li + li::before {
content: "/";
margin-inline: 0.35rem;
color: var(--rx-a11y-text-muted);
}
/* ==========================================================================
29. Accordion and Tabs Accessibility
========================================================================== */
.rx-accordion-button {
display: flex;
align-items: center;
justify-content: space-between;
width: 100%;
min-height: var(--rx-a11y-touch-target);
text-align: start;
}
.rx-accordion-panel[hidden],
.rx-tab-panel[hidden] {
display: none !important;
}
.rx-tabs {
display: flex;
flex-wrap: wrap;
gap: 0.5rem;
}
.rx-tab {
min-height: var(--rx-a11y-touch-target);
}
.rx-tab[aria-selected="true"] {
font-weight: 700;
border-bottom: 3px solid currentColor;
}
/* ==========================================================================
30. Tooltip Accessibility
========================================================================== */
.rx-tooltip {
position: relative;
}
.rx-tooltip-content {
position: absolute;
z-index: 9999;
max-width: 18rem;
padding: 0.5rem 0.75rem;
color: #ffffff;
background: #111111;
border-radius: 0.375rem;
font-size: 0.875rem;
line-height: 1.4;
}
.rx-tooltip-content[hidden] {
display: none !important;
}
/* ==========================================================================
31. Utility Visibility Classes
========================================================================== */
.rx-hidden {
display: none !important;
}
.rx-invisible {
visibility: hidden !important;
}
.rx-visible {
visibility: visible !important;
}
.rx-opacity-0 {
opacity: 0 !important;
}
.rx-opacity-100 {
opacity: 1 !important;
}
.rx-pointer-none {
pointer-events: none !important;
}
.rx-pointer-auto {
pointer-events: auto !important;
}
/* Hide visually but preserve layout */
.rx-ghost {
opacity: 0 !important;
}
/* Hide from everyone */
.rx-hidden-all,
[aria-hidden="true"].rx-hidden-all {
display: none !important;
}
/* ==========================================================================
32. Layout Accessibility Helpers
========================================================================== */
.rx-stack {
display: flex;
flex-direction: column;
gap: 1rem;
}
.rx-cluster {
display: flex;
flex-wrap: wrap;
gap: 1rem;
}
.rx-center {
display: grid;
place-items: center;
}
.rx-full-width {
width: 100%;
}
.rx-max-readable {
max-width: 75ch;
}
.rx-scroll-margin {
scroll-margin-top: 6rem;
}
/* ==========================================================================
33. Target Highlight
========================================================================== */
:target {
scroll-margin-top: 6rem;
}
:target:not(body) {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: var(--rx-a11y-focus-offset);
}
.rx-target-highlight:target {
background: rgba(255, 230, 0, 0.2);
}
/* ==========================================================================
34. Print Accessibility
========================================================================== */
@media print {
*,
*::before,
*::after {
color: #000000 !important;
background: transparent !important;
box-shadow: none !important;
text-shadow: none !important;
}
html {
font-size: 12pt;
}
body {
line-height: 1.5;
}
a,
a:visited {
color: #000000 !important;
text-decoration: underline;
}
a[href^="http"]::after {
content: " (" attr(href) ")";
font-size: 0.85em;
word-break: break-all;
}
abbr[title]::after {
content: " (" attr(title) ")";
}
.skip-link,
.rx-skip-link,
nav,
.rx-nav,
.pagination,
.rx-pagination,
.comment-respond,
.no-print,
.rx-no-print {
display: none !important;
}
main,
article,
section {
display: block !important;
}
img {
max-width: 100% !important;
page-break-inside: avoid;
}
h1,
h2,
h3,
h4,
h5,
h6 {
page-break-after: avoid;
}
p,
blockquote,
table,
pre {
page-break-inside: avoid;
}
}
/* ==========================================================================
35. Responsive Accessibility
========================================================================== */
@media (max-width: 767px) {
:root {
--rx-a11y-focus-offset: 2px;
}
.rx-search-form,
.rx-input-with-button {
flex-direction: column;
}
.rx-toast {
right: 0.75rem;
bottom: 0.75rem;
left: 0.75rem;
max-width: none;
}
.breadcrumb ol,
.breadcrumbs ol,
.rx-breadcrumb ol {
gap: 0.25rem;
}
}
/* ==========================================================================
36. Safe Animation Utilities
========================================================================== */
.rx-fade-in {
animation: rx-a11y-fade-in 200ms ease both;
}
@keyframes rx-a11y-fade-in {
from {
opacity: 0;
}
to {
opacity: 1;
}
}
.rx-slide-up {
animation: rx-a11y-slide-up 200ms ease both;
}
@keyframes rx-a11y-slide-up {
from {
opacity: 0;
transform: translateY(0.5rem);
}
to {
opacity: 1;
transform: translateY(0);
}
}
/* ==========================================================================
37. Content Selection and Reading Helpers
========================================================================== */
::selection {
color: #ffffff;
background: #005fcc;
}
.rx-user-select-none {
user-select: none !important;
}
.rx-user-select-text {
user-select: text !important;
}
.rx-readable-spacing {
letter-spacing: 0.01em;
word-spacing: 0.05em;
line-height: 1.75;
}
.rx-large-text {
font-size: 1.125rem;
line-height: 1.7;
}
.rx-extra-large-text {
font-size: 1.25rem;
line-height: 1.7;
}
/* ==========================================================================
38. Empty and Error State Accessibility
========================================================================== */
.rx-empty-state,
.rx-error-state {
padding: 1.5rem;
border: 1px solid var(--rx-a11y-border);
border-radius: 0.75rem;
text-align: center;
}
.rx-empty-state:focus-within,
.rx-error-state:focus-within {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: var(--rx-a11y-focus-offset);
}
/* ==========================================================================
39. Loading Skeleton Accessibility
========================================================================== */
.rx-skeleton {
position: relative;
overflow: hidden;
color: transparent !important;
background: rgba(120, 120, 120, 0.25);
border-radius: 0.375rem;
}
.rx-skeleton::after {
content: "";
position: absolute;
inset: 0;
transform: translateX(-100%);
background: linear-gradient(
90deg,
transparent,
rgba(255, 255, 255, 0.35),
transparent
);
animation: rx-a11y-skeleton 1.2s ease-in-out infinite;
}
@keyframes rx-a11y-skeleton {
to {
transform: translateX(100%);
}
}
@media (prefers-reduced-motion: reduce) {
.rx-skeleton::after {
animation: none !important;
}
}
/* ==========================================================================
40. Accessibility Debug Helpers
Use only during development. Add .rx-a11y-debug to body.
========================================================================== */
.rx-a11y-debug img:not([alt]) {
outline: 4px solid red !important;
}
.rx-a11y-debug a:not([href]) {
outline: 4px solid orange !important;
}
.rx-a11y-debug button:empty,
.rx-a11y-debug a:empty {
outline: 4px solid purple !important;
}
.rx-a11y-debug [tabindex]:not([tabindex="0"]):not([tabindex="-1"]) {
outline: 4px solid #ff00ff !important;
}
.rx-a11y-debug [aria-hidden="true"] a,
.rx-a11y-debug [aria-hidden="true"] button,
.rx-a11y-debug [aria-hidden="true"] input,
.rx-a11y-debug [aria-hidden="true"] select,
.rx-a11y-debug [aria-hidden="true"] textarea,
.rx-a11y-debug [aria-hidden="true"] [tabindex] {
outline: 4px dashed red !important;
}
/* ==========================================================================
41. Helper Classes for JS Integration
========================================================================== */
.js-focus-visible :focus:not(.focus-visible) {
outline: none;
}
.js-focus-visible .focus-visible {
outline: 3px solid var(--rx-a11y-focus-color);
outline-offset: var(--rx-a11y-focus-offset);
}
.rx-js-enabled .rx-no-js-only {
display: none !important;
}
.rx-no-js .rx-js-only {
display: none !important;
}
/* ==========================================================================
42. End of RX Accessibility Utilities
========================================================================== */
Add this file in your main CSS import/enqueue order after reset/base CSS but before component CSS, like this:
@import url("./utilities/accessibility.css");
Best order for RX Theme:
01-reset.css
02-base.css
03-typography.css
utilities/accessibility.css
components/buttons.css
components/forms.css
components/navigation.css
layout/header.css
layout/footer.css
pages/single.css
This file is safe as a global utility accessibility file. Later, you can add JavaScript for .rx-using-keyboard, modal focus trap, live announcer, accordion keyboard control, and menu keyboard navigation.