CINXE.COM

WAI-ARIA basics - Learn web development | MDN

<!doctype html><html lang="en-US" prefix="og: https://ogp.me/ns#"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width,initial-scale=1"/><link rel="icon" href="https://developer.mozilla.org/favicon-48x48.bc390275e955dacb2e65.png"/><link rel="apple-touch-icon" href="https://developer.mozilla.org/apple-touch-icon.528534bba673c38049c2.png"/><meta name="theme-color" content="#ffffff"/><link rel="manifest" href="https://developer.mozilla.org/manifest.f42880861b394dd4dc9b.json"/><link rel="search" type="application/opensearchdescription+xml" href="/opensearch.xml" title="MDN Web Docs"/><title>WAI-ARIA basics - Learn web development | MDN</title><link rel="alternate" title="Grundlagen von WAI-ARIA" href="https://developer.mozilla.org/de/docs/Learn/Accessibility/WAI-ARIA_basics" hrefLang="de"/><link rel="alternate" title="Les bases de WAI-ARIA" href="https://developer.mozilla.org/fr/docs/Learn/Accessibility/WAI-ARIA_basics" hrefLang="fr"/><link rel="alternate" title="WAI-ARIA の基本" href="https://developer.mozilla.org/ja/docs/Learn/Accessibility/WAI-ARIA_basics" hrefLang="ja"/><link rel="alternate" title="WAI-ARIA 基础" href="https://developer.mozilla.org/zh-CN/docs/Learn/Accessibility/WAI-ARIA_basics" hrefLang="zh"/><link rel="alternate" title="WAI-ARIA基礎" href="https://developer.mozilla.org/zh-TW/docs/Learn/Accessibility/WAI-ARIA_basics" hrefLang="zh-Hant"/><link rel="alternate" title="WAI-ARIA basics" href="https://developer.mozilla.org/en-US/docs/Learn/Accessibility/WAI-ARIA_basics" hrefLang="en"/><link rel="preload" as="font" type="font/woff2" href="/static/media/Inter.var.c2fe3cb2b7c746f7966a.woff2" crossorigin=""/><link rel="alternate" type="application/rss+xml" title="MDN Blog RSS Feed" href="https://developer.mozilla.org/en-US/blog/rss.xml" hrefLang="en"/><meta name="description" content="This article has by no means covered all that&#x27;s available in WAI-ARIA, but it should have given you enough information to understand how to use it, and know some of the most common patterns you will encounter that require it."/><meta property="og:url" content="https://developer.mozilla.org/en-US/docs/Learn/Accessibility/WAI-ARIA_basics"/><meta property="og:title" content="WAI-ARIA basics - Learn web development | MDN"/><meta property="og:type" content="website"/><meta property="og:locale" content="en_US"/><meta property="og:description" content="This article has by no means covered all that&#x27;s available in WAI-ARIA, but it should have given you enough information to understand how to use it, and know some of the most common patterns you will encounter that require it."/><meta property="og:image" content="https://developer.mozilla.org/mdn-social-share.d893525a4fb5fb1f67a2.png"/><meta property="og:image:type" content="image/png"/><meta property="og:image:height" content="1080"/><meta property="og:image:width" content="1920"/><meta property="og:image:alt" content="The MDN Web Docs logo, featuring a blue accent color, displayed on a solid black background."/><meta property="og:site_name" content="MDN Web Docs"/><meta name="twitter:card" content="summary_large_image"/><meta name="twitter:creator" content="MozDevNet"/><link rel="canonical" href="https://developer.mozilla.org/en-US/docs/Learn/Accessibility/WAI-ARIA_basics"/><style media="print">.article-actions-container,.document-toc-container,.language-menu,.main-menu-toggle,.on-github,.page-footer,.place,.sidebar,.top-banner,.top-navigation-main,ul.prev-next{display:none!important}.main-page-content,.main-page-content pre{padding:2px}.main-page-content pre{border-left-width:2px}</style><script src="/static/js/gtag.js" defer=""></script><script defer="" src="/static/js/main.d21ae86f.js"></script><link href="/static/css/main.26c64ea7.css" rel="stylesheet"/></head><body><script>if(document.body.addEventListener("load",(t=>{t.target.classList.contains("interactive")&&t.target.setAttribute("data-readystate","complete")}),{capture:!0}),window&&document.documentElement){const t={light:"#ffffff",dark:"#1b1b1b"};try{const e=window.localStorage.getItem("theme");e&&(document.documentElement.className=e,document.documentElement.style.backgroundColor=t[e]);const o=window.localStorage.getItem("nop");o&&(document.documentElement.dataset.nop=o)}catch(t){console.warn("Unable to read theme from localStorage",t)}}</script><div id="root"><ul id="nav-access" class="a11y-nav"><li><a id="skip-main" href="#content">Skip to main content</a></li><li><a id="skip-search" href="#top-nav-search-input">Skip to search</a></li><li><a id="skip-select-language" href="#languages-switcher-button">Skip to select language</a></li></ul><div class="page-wrapper category-learn document-page"><div class="top-banner loading"><section class="place top container"></section></div><div class="sticky-header-container"><header class="top-navigation "><div class="container "><div class="top-navigation-wrap"><a href="/en-US/" class="logo" aria-label="MDN homepage"><svg id="mdn-docs-logo" xmlns="http://www.w3.org/2000/svg" x="0" y="0" viewBox="0 0 694.9 104.4" style="enable-background:new 0 0 694.9 104.4" xml:space="preserve" role="img"><title>MDN Web Docs</title><path d="M40.3 0 11.7 92.1H0L28.5 0h11.8zm10.4 0v92.1H40.3V0h10.4zM91 0 62.5 92.1H50.8L79.3 0H91zm10.4 0v92.1H91V0h10.4z" class="logo-m"></path><path d="M627.9 95.6h67v8.8h-67v-8.8z" class="logo-_"></path><path d="M367 42h-4l-10.7 30.8h-5.5l-10.8-26h-.4l-10.5 26h-5.2L308.7 42h-3.8v-5.6H323V42h-6.5l6.8 20.4h.4l10.3-26h4.7l11.2 26h.5l5.7-20.3h-6.2v-5.6H367V42zm34.9 20c-.4 3.2-2 5.9-4.7 8.2-2.8 2.3-6.5 3.4-11.3 3.4-5.4 0-9.7-1.6-13.1-4.7-3.3-3.2-5-7.7-5-13.7 0-5.7 1.6-10.3 4.7-14s7.4-5.5 12.9-5.5c5.1 0 9.1 1.6 11.9 4.7s4.3 6.9 4.3 11.3c0 1.5-.2 3-.5 4.7h-25.6c.3 7.7 4 11.6 10.9 11.6 2.9 0 5.1-.7 6.5-2 1.5-1.4 2.5-3 3-4.9l6 .9zM394 51.3c.2-2.4-.4-4.7-1.8-6.9s-3.8-3.3-7-3.3c-3.1 0-5.3 1-6.9 3-1.5 2-2.5 4.4-2.8 7.2H394zm51 2.4c0 5-1.3 9.5-4 13.7s-6.9 6.2-12.7 6.2c-6 0-10.3-2.2-12.7-6.7-.1.4-.2 1.4-.4 2.9s-.3 2.5-.4 2.9h-7.3c.3-1.7.6-3.5.8-5.3.3-1.8.4-3.7.4-5.5V22.3h-6v-5.6H416v27c1.1-2.2 2.7-4.1 4.7-5.7 2-1.6 4.8-2.4 8.4-2.4 4.6 0 8.4 1.6 11.4 4.7 3 3.2 4.5 7.6 4.5 13.4zm-7.7.6c0-4.2-1-7.4-3-9.5-2-2.2-4.4-3.3-7.4-3.3-3.4 0-6 1.2-8 3.7-1.9 2.4-2.9 5-3 7.7V57c0 3 1 5.6 3 7.7s4.5 3.1 7.6 3.1c3.6 0 6.3-1.3 8.1-3.9 1.8-2.7 2.7-5.9 2.7-9.6zm69.2 18.5h-13.2v-7.2c-1.2 2.2-2.8 4.1-4.9 5.6-2.1 1.6-4.8 2.4-8.3 2.4-4.8 0-8.7-1.6-11.6-4.9-2.9-3.2-4.3-7.7-4.3-13.3 0-5 1.3-9.6 4-13.7 2.6-4.1 6.9-6.2 12.8-6.2 5.7 0 9.8 2.2 12.3 6.5V22.3h-8.6v-5.6h15.8v50.6h6v5.5zM493.2 56v-4.4c-.1-3-1.2-5.5-3.2-7.3s-4.4-2.8-7.2-2.8c-3.6 0-6.3 1.3-8.2 3.9-1.9 2.6-2.8 5.8-2.8 9.6 0 4.1 1 7.3 3 9.5s4.5 3.3 7.4 3.3c3.2 0 5.8-1.3 7.8-3.8 2.1-2.6 3.1-5.3 3.2-8zm53.1-1.4c0 5.6-1.8 10.2-5.3 13.7s-8.2 5.3-13.9 5.3-10.1-1.7-13.4-5.1c-3.3-3.4-5-7.9-5-13.5 0-5.3 1.6-9.9 4.7-13.7 3.2-3.8 7.9-5.7 14.2-5.7s11 1.9 14.1 5.7c3 3.7 4.6 8.1 4.6 13.3zm-7.7-.2c0-4-1-7.2-3-9.5s-4.8-3.5-8.2-3.5c-3.6 0-6.4 1.2-8.3 3.7s-2.9 5.6-2.9 9.5c0 3.7.9 6.8 2.8 9.4 1.9 2.6 4.6 3.9 8.3 3.9 3.6 0 6.4-1.3 8.4-3.8 1.9-2.6 2.9-5.8 2.9-9.7zm45 5.8c-.4 3.2-1.9 6.3-4.4 9.1-2.5 2.9-6.4 4.3-11.8 4.3-5.2 0-9.4-1.6-12.6-4.8-3.2-3.2-4.8-7.7-4.8-13.7 0-5.5 1.6-10.1 4.7-13.9 3.2-3.8 7.6-5.7 13.2-5.7 2.3 0 4.6.3 6.7.8 2.2.5 4.2 1.5 6.2 2.9l1.5 9.5-5.9.7-1.3-6.1c-2.1-1.2-4.5-1.8-7.2-1.8-3.5 0-6.1 1.2-7.7 3.7-1.7 2.5-2.5 5.7-2.5 9.6 0 4.1.9 7.3 2.7 9.5 1.8 2.3 4.4 3.4 7.8 3.4 5.2 0 8.2-2.9 9.2-8.8l6.2 1.3zm34.7 1.9c0 3.6-1.5 6.5-4.6 8.5s-7 3-11.7 3c-5.7 0-10.6-1.2-14.6-3.6l1.2-8.8 5.7.6-.2 4.7c1.1.5 2.3.9 3.6 1.1s2.6.3 3.9.3c2.4 0 4.5-.4 6.5-1.3 1.9-.9 2.9-2.2 2.9-4.1 0-1.8-.8-3.1-2.3-3.8s-3.5-1.3-5.8-1.7-4.6-.9-6.9-1.4c-2.3-.6-4.2-1.6-5.7-2.9-1.6-1.4-2.3-3.5-2.3-6.3 0-4.1 1.5-6.9 4.6-8.5s6.4-2.4 9.9-2.4c2.6 0 5 .3 7.2.9 2.2.6 4.3 1.4 6.1 2.4l.8 8.8-5.8.7-.8-5.7c-2.3-1-4.7-1.6-7.2-1.6-2.1 0-3.7.4-5.1 1.1-1.3.8-2 2-2 3.8 0 1.7.8 2.9 2.3 3.6 1.5.7 3.4 1.2 5.7 1.6 2.2.4 4.5.8 6.7 1.4 2.2.6 4.1 1.6 5.7 3 1.4 1.6 2.2 3.7 2.2 6.6zM197.6 73.2h-17.1v-5.5h3.8V51.9c0-3.7-.7-6.3-2.1-7.9-1.4-1.6-3.3-2.3-5.7-2.3-3.2 0-5.6 1.1-7.2 3.4s-2.4 4.6-2.5 6.9v15.6h6v5.5h-17.1v-5.5h3.8V51.9c0-3.8-.7-6.4-2.1-7.9-1.4-1.5-3.3-2.3-5.6-2.3-3.2 0-5.5 1.1-7.2 3.3-1.6 2.2-2.4 4.5-2.5 6.9v15.8h6.9v5.5h-20.2v-5.5h6V42.4h-6.1v-5.6h13.4v6.4c1.2-2.1 2.7-3.8 4.7-5.2 2-1.3 4.4-2 7.3-2s5.3.7 7.5 2.1c2.2 1.4 3.7 3.5 4.5 6.4 1.1-2.5 2.7-4.5 4.9-6.1s4.8-2.4 7.9-2.4c3.5 0 6.5 1.1 8.9 3.3s3.7 5.6 3.7 10.2v18.2h6.1v5.5zm42.5 0h-13.2V66c-1.2 2.2-2.8 4.1-4.9 5.6-2.1 1.6-4.8 2.4-8.3 2.4-4.8 0-8.7-1.6-11.6-4.9-2.9-3.2-4.3-7.7-4.3-13.3 0-5 1.3-9.6 4-13.7 2.6-4.1 6.9-6.2 12.8-6.2s9.8 2.2 12.3 6.5V22.7h-8.6v-5.6h15.8v50.6h6v5.5zm-13.3-16.8V52c-.1-3-1.2-5.5-3.2-7.3s-4.4-2.8-7.2-2.8c-3.6 0-6.3 1.3-8.2 3.9-1.9 2.6-2.8 5.8-2.8 9.6 0 4.1 1 7.3 3 9.5s4.5 3.3 7.4 3.3c3.2 0 5.8-1.3 7.8-3.8 2.1-2.6 3.1-5.3 3.2-8zm61.5 16.8H269v-5.5h6V51.9c0-3.7-.7-6.3-2.2-7.9-1.4-1.6-3.4-2.3-5.7-2.3-3.1 0-5.6 1-7.4 3s-2.8 4.4-2.9 7v15.9h6v5.5h-19.3v-5.5h6V42.4h-6.2v-5.6h13.6V43c2.6-4.6 6.8-6.9 12.7-6.9 3.6 0 6.7 1.1 9.2 3.3s3.7 5.6 3.7 10.2v18.2h6v5.4h-.2z" class="logo-text"></path></svg></a><button title="Open main menu" type="button" class="button action has-icon main-menu-toggle" aria-haspopup="menu" aria-label="Open main menu" aria-expanded="false"><span class="button-wrap"><span class="icon icon-menu "></span><span class="visually-hidden">Open main menu</span></span></button></div><div class="top-navigation-main"><nav class="main-nav" aria-label="Main menu"><ul class="main-menu nojs"><li class="top-level-entry-container "><button type="button" id="references-button" class="top-level-entry menu-toggle" aria-controls="references-menu" aria-expanded="false">References</button><a href="/en-US/docs/Web" class="top-level-entry">References</a><ul id="references-menu" class="submenu references hidden inline-submenu-lg" aria-labelledby="references-button"><li class="apis-link-container mobile-only "><a href="/en-US/docs/Web" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">Overview / Web Technology</div><p class="submenu-item-description">Web technology reference for developers</p></div></a></li><li class="html-link-container "><a href="/en-US/docs/Web/HTML" class="submenu-item "><div class="submenu-icon html"></div><div class="submenu-content-container"><div class="submenu-item-heading">HTML</div><p class="submenu-item-description">Structure of content on the web</p></div></a></li><li class="css-link-container "><a href="/en-US/docs/Web/CSS" class="submenu-item "><div class="submenu-icon css"></div><div class="submenu-content-container"><div class="submenu-item-heading">CSS</div><p class="submenu-item-description">Code used to describe document style</p></div></a></li><li class="javascript-link-container "><a href="/en-US/docs/Web/JavaScript" class="submenu-item "><div class="submenu-icon javascript"></div><div class="submenu-content-container"><div class="submenu-item-heading">JavaScript</div><p class="submenu-item-description">General-purpose scripting language</p></div></a></li><li class="http-link-container "><a href="/en-US/docs/Web/HTTP" class="submenu-item "><div class="submenu-icon http"></div><div class="submenu-content-container"><div class="submenu-item-heading">HTTP</div><p class="submenu-item-description">Protocol for transmitting web resources</p></div></a></li><li class="apis-link-container "><a href="/en-US/docs/Web/API" class="submenu-item "><div class="submenu-icon apis"></div><div class="submenu-content-container"><div class="submenu-item-heading">Web APIs</div><p class="submenu-item-description">Interfaces for building web applications</p></div></a></li><li class="apis-link-container "><a href="/en-US/docs/Mozilla/Add-ons/WebExtensions" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">Web Extensions</div><p class="submenu-item-description">Developing extensions for web browsers</p></div></a></li><li class="apis-link-container desktop-only "><a href="/en-US/docs/Web" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">Web Technology</div><p class="submenu-item-description">Web technology reference for developers</p></div></a></li></ul></li><li class="top-level-entry-container active"><button type="button" id="guides-button" class="top-level-entry menu-toggle" aria-controls="guides-menu" aria-expanded="false">Guides</button><a href="/en-US/docs/Learn" class="top-level-entry">Guides</a><ul id="guides-menu" class="submenu guides hidden inline-submenu-lg" aria-labelledby="guides-button"><li class="apis-link-container mobile-only "><a href="/en-US/docs/Learn" class="submenu-item "><div class="submenu-icon learn"></div><div class="submenu-content-container"><div class="submenu-item-heading">Overview / MDN Learning Area</div><p class="submenu-item-description">Learn web development</p></div></a></li><li class="apis-link-container desktop-only "><a href="/en-US/docs/Learn" class="submenu-item "><div class="submenu-icon learn"></div><div class="submenu-content-container"><div class="submenu-item-heading">MDN Learning Area</div><p class="submenu-item-description">Learn web development</p></div></a></li><li class="html-link-container "><a href="/en-US/docs/Learn/HTML" class="submenu-item "><div class="submenu-icon html"></div><div class="submenu-content-container"><div class="submenu-item-heading">HTML</div><p class="submenu-item-description">Learn to structure web content with HTML</p></div></a></li><li class="css-link-container "><a href="/en-US/docs/Learn/CSS" class="submenu-item "><div class="submenu-icon css"></div><div class="submenu-content-container"><div class="submenu-item-heading">CSS</div><p class="submenu-item-description">Learn to style content using CSS</p></div></a></li><li class="javascript-link-container "><a href="/en-US/docs/Learn/JavaScript" class="submenu-item "><div class="submenu-icon javascript"></div><div class="submenu-content-container"><div class="submenu-item-heading">JavaScript</div><p class="submenu-item-description">Learn to run scripts in the browser</p></div></a></li><li class=" "><a href="/en-US/docs/Web/Accessibility" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">Accessibility</div><p class="submenu-item-description">Learn to make the web accessible to all</p></div></a></li></ul></li><li class="top-level-entry-container "><button type="button" id="mdn-plus-button" class="top-level-entry menu-toggle" aria-controls="mdn-plus-menu" aria-expanded="false">Plus</button><a href="/en-US/plus" class="top-level-entry">Plus</a><ul id="mdn-plus-menu" class="submenu mdn-plus hidden inline-submenu-lg" aria-labelledby="mdn-plus-button"><li class=" "><a href="/en-US/plus" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">Overview</div><p class="submenu-item-description">A customized MDN experience</p></div></a></li><li class=" "><a href="/en-US/plus/ai-help" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">AI Help</div><p class="submenu-item-description">Get real-time assistance and support</p></div></a></li><li class=" "><a href="/en-US/plus/updates" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">Updates</div><p class="submenu-item-description">All browser compatibility updates at a glance</p></div></a></li><li class=" "><a href="/en-US/plus/docs/features/overview" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">Documentation</div><p class="submenu-item-description">Learn how to use MDN Plus</p></div></a></li><li class=" "><a href="/en-US/plus/docs/faq" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">FAQ</div><p class="submenu-item-description">Frequently asked questions about MDN Plus</p></div></a></li></ul></li><li class="top-level-entry-container "><a class="top-level-entry menu-link" href="/en-US/curriculum/">Curriculum <sup class="new">New</sup></a></li><li class="top-level-entry-container "><a class="top-level-entry menu-link" href="/en-US/blog/">Blog</a></li><li class="top-level-entry-container "><button type="button" id="tools-button" class="top-level-entry menu-toggle" aria-controls="tools-menu" aria-expanded="false">Tools</button><ul id="tools-menu" class="submenu tools hidden inline-submenu-lg" aria-labelledby="tools-button"><li class=" "><a href="/en-US/play" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">Playground</div><p class="submenu-item-description">Write, test and share your code</p></div></a></li><li class=" "><a href="/en-US/observatory" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">HTTP Observatory</div><p class="submenu-item-description">Scan a website for free</p></div></a></li><li class=" "><a href="/en-US/plus/ai-help" class="submenu-item "><div class="submenu-icon"></div><div class="submenu-content-container"><div class="submenu-item-heading">AI Help</div><p class="submenu-item-description">Get real-time assistance and support</p></div></a></li></ul></li></ul></nav><div class="header-search"><form action="/en-US/search" class="search-form search-widget" id="top-nav-search-form" role="search"><label id="top-nav-search-label" for="top-nav-search-input" class="visually-hidden">Search MDN</label><input aria-activedescendant="" aria-autocomplete="list" aria-controls="top-nav-search-menu" aria-expanded="false" aria-labelledby="top-nav-search-label" autoComplete="off" id="top-nav-search-input" role="combobox" type="search" class="search-input-field" name="q" placeholder="   " required="" value=""/><button type="button" class="button action has-icon clear-search-button"><span class="button-wrap"><span class="icon icon-cancel "></span><span class="visually-hidden">Clear search input</span></span></button><button type="submit" class="button action has-icon search-button"><span class="button-wrap"><span class="icon icon-search "></span><span class="visually-hidden">Search</span></span></button><div id="top-nav-search-menu" role="listbox" aria-labelledby="top-nav-search-label"></div></form></div><div class="theme-switcher-menu"><button type="button" class="button action has-icon theme-switcher-menu small" aria-haspopup="menu"><span class="button-wrap"><span class="icon icon-theme-os-default "></span>Theme</span></button></div><ul class="auth-container"><li><a href="/users/fxa/login/authenticate/?next=%2Fen-US%2Fdocs%2FLearn%2FAccessibility%2FWAI-ARIA_basics" class="login-link" rel="nofollow">Log in</a></li><li><a href="/users/fxa/login/authenticate/?next=%2Fen-US%2Fdocs%2FLearn%2FAccessibility%2FWAI-ARIA_basics" target="_self" rel="nofollow" class="button primary mdn-plus-subscribe-link"><span class="button-wrap">Sign up for free</span></a></li></ul></div></div></header><div class="article-actions-container"><div class="container"><button type="button" class="button action has-icon sidebar-button" aria-label="Expand sidebar" aria-expanded="false" aria-controls="sidebar-quicklinks"><span class="button-wrap"><span class="icon icon-sidebar "></span></span></button><nav class="breadcrumbs-container" aria-label="Breadcrumb"><ol typeof="BreadcrumbList" vocab="https://schema.org/" aria-label="breadcrumbs"><li property="itemListElement" typeof="ListItem"><a href="/en-US/docs/Learn" class="breadcrumb" property="item" typeof="WebPage"><span property="name">Guides</span></a><meta property="position" content="1"/></li><li property="itemListElement" typeof="ListItem"><a href="/en-US/docs/Learn/Accessibility" class="breadcrumb" property="item" typeof="WebPage"><span property="name">Accessibility</span></a><meta property="position" content="2"/></li><li property="itemListElement" typeof="ListItem"><a href="/en-US/docs/Learn/Accessibility/WAI-ARIA_basics" class="breadcrumb-current-page" property="item" typeof="WebPage"><span property="name">WAI-ARIA basics</span></a><meta property="position" content="3"/></li></ol></nav><div class="article-actions"><button type="button" class="button action has-icon article-actions-toggle" aria-label="Article actions"><span class="button-wrap"><span class="icon icon-ellipses "></span><span class="article-actions-dialog-heading">Article Actions</span></span></button><ul class="article-actions-entries"><li class="article-actions-entry"><div class="languages-switcher-menu open-on-focus-within"><button id="languages-switcher-button" type="button" class="button action small has-icon languages-switcher-menu" aria-haspopup="menu"><span class="button-wrap"><span class="icon icon-language "></span>English (US)</span></button><div class="hidden"><ul class="submenu language-menu " aria-labelledby="language-menu-button"><li class=" "><form class="submenu-item locale-redirect-setting"><div class="group"><label class="switch"><input type="checkbox" name="locale-redirect"/><span class="slider"></span><span class="label">Remember language</span></label><a href="https://github.com/orgs/mdn/discussions/739" rel="external noopener noreferrer" target="_blank" title="Enable this setting to automatically switch to this language when it&#x27;s available. (Click to learn more.)"><span class="icon icon-question-mark "></span></a></div></form></li><li class=" "><a data-locale="de" href="/de/docs/Learn/Accessibility/WAI-ARIA_basics" class="button submenu-item"><span>Deutsch</span><span title="Diese Übersetzung ist Teil eines Experiments."><span class="icon icon-experimental "></span></span></a></li><li class=" "><a data-locale="fr" href="/fr/docs/Learn/Accessibility/WAI-ARIA_basics" class="button submenu-item"><span>Français</span></a></li><li class=" "><a data-locale="ja" href="/ja/docs/Learn/Accessibility/WAI-ARIA_basics" class="button submenu-item"><span>日本語</span></a></li><li class=" "><a data-locale="zh-CN" href="/zh-CN/docs/Learn/Accessibility/WAI-ARIA_basics" class="button submenu-item"><span>中文 (简体)</span></a></li><li class=" "><a data-locale="zh-TW" href="/zh-TW/docs/Learn/Accessibility/WAI-ARIA_basics" class="button submenu-item"><span>正體中文 (繁體)</span></a></li></ul></div></div></li></ul></div></div></div></div><div class="main-wrapper"><div class="sidebar-container"><aside id="sidebar-quicklinks" class="sidebar" data-macro="LearnSidebar"><button type="button" class="button action backdrop" aria-label="Collapse sidebar"><span class="button-wrap"></span></button><nav aria-label="Related Topics" class="sidebar-inner"><header class="sidebar-actions"><section class="sidebar-filter-container"><div class="sidebar-filter "><label id="sidebar-filter-label" class="sidebar-filter-label" for="sidebar-filter-input"><span class="icon icon-filter"></span><span class="visually-hidden">Filter sidebar</span></label><input id="sidebar-filter-input" autoComplete="off" class="sidebar-filter-input-field false" type="text" placeholder="Filter" value=""/><button type="button" class="button action has-icon clear-sidebar-filter-button"><span class="button-wrap"><span class="icon icon-cancel "></span><span class="visually-hidden">Clear filter input</span></span></button></div></section></header><div class="sidebar-inner-nav"><div class="in-nav-toc"><div class="document-toc-container"><section class="document-toc"><header><h2 class="document-toc-heading">In this article</h2></header><ul class="document-toc-list"><li class="document-toc-item "><a class="document-toc-link" href="#what_is_wai-aria">What is WAI-ARIA?</a></li><li class="document-toc-item "><a class="document-toc-link" href="#practical_wai-aria_implementations">Practical WAI-ARIA implementations</a></li><li class="document-toc-item "><a class="document-toc-link" href="#test_your_skills!">Test your skills!</a></li><li class="document-toc-item "><a class="document-toc-link" href="#summary">Summary</a></li><li class="document-toc-item "><a class="document-toc-link" href="#see_also">See also</a></li></ul></section></div></div><div class="sidebar-body"><ol><li class="section"><a href="/en-US/docs/Learn/Getting_started_with_the_web">Complete beginners start here!</a></li><li><details><summary>Getting started with the web</summary><ol><li><a href="/en-US/docs/Learn/Getting_started_with_the_web">Getting started with the web</a></li><li><a href="/en-US/docs/Learn/Getting_started_with_the_web/Installing_basic_software">Installing basic software</a></li><li><a href="/en-US/docs/Learn/Getting_started_with_the_web/What_will_your_website_look_like">What will your website look like?</a></li><li><a href="/en-US/docs/Learn/Getting_started_with_the_web/Dealing_with_files">Dealing with files</a></li><li><a href="/en-US/docs/Learn/Getting_started_with_the_web/HTML_basics">HTML basics</a></li><li><a href="/en-US/docs/Learn/Getting_started_with_the_web/CSS_basics">CSS basics</a></li><li><a href="/en-US/docs/Learn/Getting_started_with_the_web/JavaScript_basics">JavaScript basics</a></li><li><a href="/en-US/docs/Learn/Getting_started_with_the_web/Publishing_your_website">Publishing your website</a></li><li><a href="/en-US/docs/Learn/Getting_started_with_the_web/How_the_Web_works">How the web works</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/HTML">HTML — Structuring the web</a></li><li><details><summary>Introduction to HTML</summary><ol><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML">Introduction to HTML</a></li><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML/Getting_started">Getting started with HTML</a></li><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML/The_head_metadata_in_HTML">What's in the head? Metadata in HTML</a></li><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML/HTML_text_fundamentals">HTML text fundamentals</a></li><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML/Creating_hyperlinks">Creating hyperlinks</a></li><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML/Advanced_text_formatting">Advanced text formatting</a></li><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML/Document_and_website_structure">Document and website structure</a></li><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML/Debugging_HTML">Debugging HTML</a></li><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML/Marking_up_a_letter">Marking up a letter</a></li><li><a href="/en-US/docs/Learn/HTML/Introduction_to_HTML/Structuring_a_page_of_content">Structuring a page of content</a></li></ol></details></li><li><details><summary>Multimedia and embedding</summary><ol><li><a href="/en-US/docs/Learn/HTML/Multimedia_and_embedding">Multimedia and embedding</a></li><li><a href="/en-US/docs/Learn/HTML/Multimedia_and_embedding/Images_in_HTML">Images in HTML</a></li><li><a href="/en-US/docs/Learn/HTML/Multimedia_and_embedding/Video_and_audio_content">Video and audio content</a></li><li><a href="/en-US/docs/Learn/HTML/Multimedia_and_embedding/Other_embedding_technologies">From object to iframe — other embedding technologies</a></li><li><a href="/en-US/docs/Learn/HTML/Multimedia_and_embedding/Adding_vector_graphics_to_the_Web">Adding vector graphics to the web</a></li><li><a href="/en-US/docs/Learn/HTML/Multimedia_and_embedding/Responsive_images">Responsive images</a></li><li><a href="/en-US/docs/Learn/HTML/Multimedia_and_embedding/Mozilla_splash_page">Mozilla splash page</a></li></ol></details></li><li><details><summary>HTML tables</summary><ol><li><a href="/en-US/docs/Learn/HTML/Tables">HTML tables</a></li><li><a href="/en-US/docs/Learn/HTML/Tables/Basics">HTML table basics</a></li><li><a href="/en-US/docs/Learn/HTML/Tables/Advanced">HTML table advanced features and accessibility</a></li><li><a href="/en-US/docs/Learn/HTML/Tables/Structuring_planet_data">Structuring planet data</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/CSS">CSS — Styling the web</a></li><li><details><summary>CSS first steps</summary><ol><li><a href="/en-US/docs/Learn/CSS/First_steps">CSS first steps</a></li><li><a href="/en-US/docs/Learn/CSS/First_steps/What_is_CSS">What is CSS?</a></li><li><a href="/en-US/docs/Learn/CSS/First_steps/Getting_started">Getting started with CSS</a></li><li><a href="/en-US/docs/Learn/CSS/First_steps/How_CSS_is_structured">How CSS is structured</a></li><li><a href="/en-US/docs/Learn/CSS/First_steps/How_CSS_works">How CSS works</a></li><li><a href="/en-US/docs/Learn/CSS/First_steps/Styling_a_biography_page">Styling a biography page</a></li></ol></details></li><li><details><summary>CSS building blocks</summary><ol><li><a href="/en-US/docs/Learn/CSS/Building_blocks">CSS building blocks</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Selectors">CSS selectors</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Selectors/Type_Class_and_ID_Selectors">Type, class, and ID selectors</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Selectors/Attribute_selectors">Attribute selectors</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Selectors/Pseudo-classes_and_pseudo-elements">Pseudo-classes and pseudo-elements</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Selectors/Combinators">Combinators</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Cascade_and_inheritance">Cascade, specificity, and inheritance</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Cascade_layers">Cascade layers</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/The_box_model">The box model</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Backgrounds_and_borders">Backgrounds and borders</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Handling_different_text_directions">Handling different text directions</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Overflowing_content">Overflowing content</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Values_and_units">CSS values and units</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Sizing_items_in_CSS">Sizing items in CSS</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Images_media_form_elements">Images, media, and form elements</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Styling_tables">Styling tables</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Advanced_styling_effects">Advanced styling effects</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Debugging_CSS">Debugging CSS</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Organizing">Organizing your CSS</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Fundamental_CSS_comprehension">Fundamental CSS comprehension</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/Creating_fancy_letterheaded_paper">Creating fancy letterheaded paper</a></li><li><a href="/en-US/docs/Learn/CSS/Building_blocks/A_cool_looking_box">A cool-looking box</a></li></ol></details></li><li><details><summary>Styling text</summary><ol><li><a href="/en-US/docs/Learn/CSS/Styling_text">CSS styling text</a></li><li><a href="/en-US/docs/Learn/CSS/Styling_text/Fundamentals">Fundamental text and font styling</a></li><li><a href="/en-US/docs/Learn/CSS/Styling_text/Styling_lists">Styling lists</a></li><li><a href="/en-US/docs/Learn/CSS/Styling_text/Styling_links">Styling links</a></li><li><a href="/en-US/docs/Learn/CSS/Styling_text/Web_fonts">Web fonts</a></li><li><a href="/en-US/docs/Learn/CSS/Styling_text/Typesetting_a_homepage">Typesetting a community school homepage</a></li></ol></details></li><li><details><summary>CSS layout</summary><ol><li><a href="/en-US/docs/Learn/CSS/CSS_layout">CSS layout</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Introduction">Introduction to CSS layout</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Normal_Flow">Normal Flow</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Flexbox">Flexbox</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Grids">Grids</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Floats">Floats</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Positioning">Positioning</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Multiple-column_Layout">Multiple-column layout</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Responsive_Design">Responsive design</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Media_queries">Beginner's guide to media queries</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Legacy_Layout_Methods">Legacy layout methods</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Supporting_Older_Browsers">Supporting older browsers</a></li><li><a href="/en-US/docs/Learn/CSS/CSS_layout/Fundamental_Layout_Comprehension">Fundamental layout comprehension</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/JavaScript">JavaScript — Dynamic client-side scripting</a></li><li><details><summary>JavaScript first steps</summary><ol><li><a href="/en-US/docs/Learn/JavaScript/First_steps">JavaScript first steps</a></li><li><a href="/en-US/docs/Learn/JavaScript/First_steps/What_is_JavaScript">What is JavaScript?</a></li><li><a href="/en-US/docs/Learn/JavaScript/First_steps/A_first_splash">A first splash into JavaScript</a></li><li><a href="/en-US/docs/Learn/JavaScript/First_steps/What_went_wrong">What went wrong? Troubleshooting JavaScript</a></li><li><a href="/en-US/docs/Learn/JavaScript/First_steps/Variables">Storing the information you need — Variables</a></li><li><a href="/en-US/docs/Learn/JavaScript/First_steps/Math">Basic math in JavaScript — numbers and operators</a></li><li><a href="/en-US/docs/Learn/JavaScript/First_steps/Strings">Handling text — strings in JavaScript</a></li><li><a href="/en-US/docs/Learn/JavaScript/First_steps/Useful_string_methods">Useful string methods</a></li><li><a href="/en-US/docs/Learn/JavaScript/First_steps/Arrays">Arrays</a></li><li><a href="/en-US/docs/Learn/JavaScript/First_steps/Silly_story_generator">Silly story generator</a></li></ol></details></li><li><details><summary>JavaScript building blocks</summary><ol><li><a href="/en-US/docs/Learn/JavaScript/Building_blocks">JavaScript building blocks</a></li><li><a href="/en-US/docs/Learn/JavaScript/Building_blocks/conditionals">Making decisions in your code — conditionals</a></li><li><a href="/en-US/docs/Learn/JavaScript/Building_blocks/Looping_code">Looping code</a></li><li><a href="/en-US/docs/Learn/JavaScript/Building_blocks/Functions">Functions — reusable blocks of code</a></li><li><a href="/en-US/docs/Learn/JavaScript/Building_blocks/Build_your_own_function">Build your own function</a></li><li><a href="/en-US/docs/Learn/JavaScript/Building_blocks/Return_values">Function return values</a></li><li><a href="/en-US/docs/Learn/JavaScript/Building_blocks/Events">Introduction to events</a></li><li><a href="/en-US/docs/Learn/JavaScript/Building_blocks/Event_bubbling">Event bubbling</a></li><li><a href="/en-US/docs/Learn/JavaScript/Building_blocks/Image_gallery">Image gallery</a></li></ol></details></li><li><details><summary>Introducing JavaScript objects</summary><ol><li><a href="/en-US/docs/Learn/JavaScript/Objects">Introducing JavaScript objects</a></li><li><a href="/en-US/docs/Learn/JavaScript/Objects/Basics">JavaScript object basics</a></li><li><a href="/en-US/docs/Learn/JavaScript/Objects/Object_prototypes">Object prototypes</a></li><li><a href="/en-US/docs/Learn/JavaScript/Objects/Object-oriented_programming">Object-oriented programming</a></li><li><a href="/en-US/docs/Learn/JavaScript/Objects/Classes_in_JavaScript">Classes in JavaScript</a></li><li><a href="/en-US/docs/Learn/JavaScript/Objects/JSON">Working with JSON</a></li><li><a href="/en-US/docs/Learn/JavaScript/Objects/Object_building_practice">Object building practice</a></li><li><a href="/en-US/docs/Learn/JavaScript/Objects/Adding_bouncing_balls_features">Adding features to our bouncing balls demo</a></li></ol></details></li><li><details><summary>Asynchronous JavaScript</summary><ol><li><a href="/en-US/docs/Learn/JavaScript/Asynchronous">Asynchronous JavaScript</a></li><li><a href="/en-US/docs/Learn/JavaScript/Asynchronous/Introducing">Introducing asynchronous JavaScript</a></li><li><a href="/en-US/docs/Learn/JavaScript/Asynchronous/Promises">How to use promises</a></li><li><a href="/en-US/docs/Learn/JavaScript/Asynchronous/Implementing_a_promise-based_API">How to implement a promise-based API</a></li><li><a href="/en-US/docs/Learn/JavaScript/Asynchronous/Introducing_workers">Introducing workers</a></li><li><a href="/en-US/docs/Learn/JavaScript/Asynchronous/Sequencing_animations">Sequencing animations</a></li></ol></details></li><li><details><summary>Client-side web APIs</summary><ol><li><a href="/en-US/docs/Learn/JavaScript/Client-side_web_APIs">Client-side web APIs</a></li><li><a href="/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Introduction">Introduction to web APIs</a></li><li><a href="/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Manipulating_documents">Manipulating documents</a></li><li><a href="/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Fetching_data">Fetching data from the server</a></li><li><a href="/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Third_party_APIs">Third-party APIs</a></li><li><a href="/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Drawing_graphics">Drawing graphics</a></li><li><a href="/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Video_and_audio_APIs">Video and Audio APIs</a></li><li><a href="/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Client-side_storage">Client-side storage</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/Forms">Web forms — Working with user data</a></li><li><details><summary>Web form building blocks</summary><ol><li><a href="/en-US/docs/Learn/Forms">Web form building blocks</a></li><li><a href="/en-US/docs/Learn/Forms/Your_first_form">Your first form</a></li><li><a href="/en-US/docs/Learn/Forms/How_to_structure_a_web_form">How to structure a web form</a></li><li><a href="/en-US/docs/Learn/Forms/Basic_native_form_controls">Basic native form controls</a></li><li><a href="/en-US/docs/Learn/Forms/HTML5_input_types">The HTML5 input types</a></li><li><a href="/en-US/docs/Learn/Forms/Other_form_controls">Other form controls</a></li><li><a href="/en-US/docs/Learn/Forms/Styling_web_forms">Styling web forms</a></li><li><a href="/en-US/docs/Learn/Forms/Advanced_form_styling">Advanced form styling</a></li><li><a href="/en-US/docs/Learn/Forms/UI_pseudo-classes">UI pseudo-classes</a></li><li><a href="/en-US/docs/Learn/Forms/Form_validation">Client-side form validation</a></li><li><a href="/en-US/docs/Learn/Forms/Sending_and_retrieving_form_data">Sending form data</a></li></ol></details></li><li><details><summary>Advanced web form techniques</summary><ol><li><a href="/en-US/docs/Learn/Forms/How_to_build_custom_form_controls">How to build custom form controls</a></li><li><a href="/en-US/docs/Learn/Forms/Sending_forms_through_JavaScript">Sending forms through JavaScript</a></li><li><a href="/en-US/docs/Learn/Forms/Property_compatibility_table_for_form_controls">CSS property compatibility table for form controls</a></li><li><a href="/en-US/docs/Learn/Forms/HTML_forms_in_legacy_browsers">HTML forms in legacy browsers</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/Accessibility">Accessibility — Make the web usable by everyone</a></li><li><details open=""><summary>Accessibility guides</summary><ol><li><a href="/en-US/docs/Learn/Accessibility">Accessibility</a></li><li><a href="/en-US/docs/Learn/Accessibility/What_is_accessibility">What is accessibility?</a></li><li><a href="/en-US/docs/Learn/Accessibility/HTML">HTML: A good basis for accessibility</a></li><li><a href="/en-US/docs/Learn/Accessibility/CSS_and_JavaScript">CSS and JavaScript accessibility best practices</a></li><li><em><a href="/en-US/docs/Learn/Accessibility/WAI-ARIA_basics" aria-current="page">WAI-ARIA basics</a></em></li><li><a href="/en-US/docs/Learn/Accessibility/Multimedia">Accessible multimedia</a></li><li><a href="/en-US/docs/Learn/Accessibility/Mobile">Mobile accessibility</a></li><li><a href="/en-US/docs/Learn/Accessibility/Accessibility_troubleshooting">Assessment: Accessibility troubleshooting</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/Performance">Performance — Making websites fast and responsive</a></li><li><details><summary>Performance guides</summary><ol><li><a href="/en-US/docs/Learn/Performance">Web performance</a></li><li><a href="/en-US/docs/Learn/Performance/why_web_performance">The "why" of web performance</a></li><li><a href="/en-US/docs/Learn/Performance/What_is_web_performance">What is web performance?</a></li><li><a href="/en-US/docs/Learn/Performance/Perceived_performance">Perceived performance</a></li><li><a href="/en-US/docs/Learn/Performance/Measuring_performance">Measuring performance</a></li><li><a href="/en-US/docs/Learn/Performance/Multimedia">Multimedia: Images</a></li><li><a href="/en-US/docs/Learn/Performance/video">Multimedia: video</a></li><li><a href="/en-US/docs/Learn/Performance/JavaScript">JavaScript performance optimization</a></li><li><a href="/en-US/docs/Learn/Performance/HTML">HTML performance optimization</a></li><li><a href="/en-US/docs/Learn/Performance/CSS">CSS performance optimization</a></li><li><a href="/en-US/docs/Learn/Performance/business_case_for_performance">The business case for web performance</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/MathML">MathML — Writing mathematics with MathML</a></li><li><details><summary>MathML first steps</summary><ol><li><a href="/en-US/docs/Learn/MathML/First_steps">MathML first steps</a></li><li><a href="/en-US/docs/Learn/MathML/First_steps/Getting_started">Getting started with MathML</a></li><li><a href="/en-US/docs/Learn/MathML/First_steps/Text_containers">MathML Text Containers</a></li><li><a href="/en-US/docs/Learn/MathML/First_steps/Fractions_and_roots">MathML fractions and roots</a></li><li><a href="/en-US/docs/Learn/MathML/First_steps/Scripts">MathML scripted elements</a></li><li><a href="/en-US/docs/Learn/MathML/First_steps/Tables">MathML tables</a></li><li><a href="/en-US/docs/Learn/MathML/First_steps/Three_famous_mathematical_formulas">Three famous mathematical formulas</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/../Games">Games — Developing games for the web</a></li><li><details><summary>Guides and tutorials</summary><ol><li><a href="/en-US/docs/Games/Introduction">Introduction to game development for the Web</a></li><li><a href="/en-US/docs/Games/Techniques">Techniques for game development</a></li><li><a href="/en-US/docs/Games/Tutorials">Tutorials</a></li><li><a href="/en-US/docs/Games/Publishing_games">Publishing games</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/Tools_and_testing">Tools and testing</a></li><li><details><summary>Client-side web development tools</summary><ol><li><a href="/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools">Understanding client-side web development tools</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Overview">Client-side tooling overview</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Command_line">Command line crash course</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Package_management">Package management basics</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Introducing_complete_toolchain">Introducing a complete toolchain</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Deployment">Deploying our app</a></li></ol></details></li><li><details><summary>Introduction to client-side frameworks</summary><ol><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Introduction">Introduction to client-side frameworks</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Main_features">Framework main features</a></li></ol></details></li><li><details><summary>React</summary><ol><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_getting_started">Getting started with React</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_todo_list_beginning">Beginning our React todo list</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_components">Componentizing our React app</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_interactivity_events_state">React interactivity: Events and state</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_interactivity_filtering_conditional_rendering">React interactivity: Editing, filtering, conditional rendering</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_accessibility">Accessibility in React</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_resources">React resources</a></li></ol></details></li><li><details><summary>Ember</summary><ol><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_getting_started">Getting started with Ember</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_structure_componentization">Ember app structure and componentization</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_interactivity_events_state">Ember interactivity: Events, classes and state</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_conditional_footer">Ember Interactivity: Footer functionality, conditional rendering</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_routing">Routing in Ember</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_resources">Ember resources and troubleshooting</a></li></ol></details></li><li><details><summary>Vue</summary><ol><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_getting_started">Getting started with Vue</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_first_component">Creating our first Vue component</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_rendering_lists">Rendering a list of Vue components</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_methods_events_models">Adding a new todo form: Vue events, methods, and models</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_styling">Styling Vue components with CSS</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_computed_properties">Using Vue computed properties</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_conditional_rendering">Vue conditional rendering: editing existing todos</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_refs_focus_management">Vue refs and lifecycle methods for focus management</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_resources">Vue resources</a></li></ol></details></li><li><details><summary>Svelte</summary><ol><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_getting_started">Getting started with Svelte</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_Todo_list_beginning">Starting our Svelte to-do list app</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_variables_props">Dynamic behavior in Svelte: working with variables and props</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_components">Componentizing our Svelte app</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_reactivity_lifecycle_accessibility">Advanced Svelte: Reactivity, lifecycle, accessibility</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_stores">Working with Svelte stores</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_TypeScript">TypeScript support in Svelte</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_deployment_next">Deployment and next steps</a></li></ol></details></li><li><details><summary>Angular</summary><ol><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_getting_started">Getting started with Angular</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_todo_list_beginning">Beginning our Angular todo list app</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_styling">Styling our Angular app</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_item_component">Creating an item component</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_filtering">Filtering our to-do items</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_building">Building Angular applications and further resources</a></li></ol></details></li><li><details><summary>Git and GitHub</summary><ol><li><a href="/en-US/docs/Learn/Tools_and_testing/GitHub">Git and GitHub</a></li></ol></details></li><li><details><summary>Cross browser testing</summary><ol><li><a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing">Cross browser testing</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Introduction">Introduction to cross-browser testing</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Testing_strategies">Strategies for carrying out testing</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/HTML_and_CSS">Handling common HTML and CSS problems</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/JavaScript">Handling common JavaScript problems</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Accessibility">Handling common accessibility problems</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Feature_detection">Implementing feature detection</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Automated_testing">Introduction to automated testing</a></li><li><a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Your_own_automation_environment">Setting up your own test automation environment</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/Server-side">Server-side website programming</a></li><li><details><summary>First steps</summary><ol><li><a href="/en-US/docs/Learn/Server-side/First_steps">Server-side website programming first steps</a></li><li><a href="/en-US/docs/Learn/Server-side/First_steps/Introduction">Introduction to the server side</a></li><li><a href="/en-US/docs/Learn/Server-side/First_steps/Client-Server_overview">Client-Server Overview</a></li><li><a href="/en-US/docs/Learn/Server-side/First_steps/Web_frameworks">Server-side web frameworks</a></li><li><a href="/en-US/docs/Learn/Server-side/First_steps/Website_security">Website security</a></li></ol></details></li><li><details><summary>Django web framework (Python)</summary><ol><li><a href="/en-US/docs/Learn/Server-side/Django">Django Web Framework (Python)</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Introduction">Django introduction</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/development_environment">Setting up a Django development environment</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Tutorial_local_library_website">Django Tutorial: The Local Library website</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/skeleton_website">Django Tutorial Part 2: Creating a skeleton website</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Models">Django Tutorial Part 3: Using models</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Admin_site">Django Tutorial Part 4: Django admin site</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Home_page">Django Tutorial Part 5: Creating our home page</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Generic_views">Django Tutorial Part 6: Generic list and detail views</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Sessions">Django Tutorial Part 7: Sessions framework</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Authentication">Django Tutorial Part 8: User authentication and permissions</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Forms">Django Tutorial Part 9: Working with forms</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Testing">Django Tutorial Part 10: Testing a Django web application</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/Deployment">Django Tutorial Part 11: Deploying Django to production</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/web_application_security">Django web application security</a></li><li><a href="/en-US/docs/Learn/Server-side/Django/django_assessment_blog">Assessment: DIY Django mini blog</a></li></ol></details></li><li><details><summary>Express Web Framework (Node.js/JavaScript)</summary><ol><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs">Express web framework (Node.js/JavaScript)</a></li><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs/Introduction">Express/Node introduction</a></li><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs/development_environment">Setting up a Node development environment</a></li><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs/Tutorial_local_library_website">Express Tutorial: The Local Library website</a></li><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs/skeleton_website">Express Tutorial Part 2: Creating a skeleton website</a></li><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs/mongoose">Express Tutorial Part 3: Using a Database (with Mongoose)</a></li><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs/routes">Express Tutorial Part 4: Routes and controllers</a></li><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs/Displaying_data">Express Tutorial Part 5: Displaying library data</a></li><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs/forms">Express Tutorial Part 6: Working with forms</a></li><li><a href="/en-US/docs/Learn/Server-side/Express_Nodejs/deployment">Express Tutorial Part 7: Deploying to production</a></li></ol></details></li><li class="section"><a href="/en-US/docs/Learn/Common_questions">Further resources</a></li><li><details><summary>Common questions</summary><ol><li><a href="/en-US/docs/Learn/Common_questions">Common questions</a></li><li><a href="/en-US/docs/Learn/HTML/Howto">Use HTML to solve common problems</a></li><li><a href="/en-US/docs/Learn/CSS/Howto">Use CSS to solve common problems</a></li><li><a href="/en-US/docs/Learn/JavaScript/Howto">Solve common problems in your JavaScript code</a></li><li><a href="/en-US/docs/Learn/Common_questions/Web_mechanics">Web mechanics</a></li><li><a href="/en-US/docs/Learn/Common_questions/Tools_and_setup">Tools and setup</a></li><li><a href="/en-US/docs/Learn/Common_questions/Design_and_accessibility">Design and accessibility</a></li></ol></details></li></ol></div></div><section class="place side"></section></nav></aside><div class="toc-container"><aside class="toc"><nav><div class="document-toc-container"><section class="document-toc"><header><h2 class="document-toc-heading">In this article</h2></header><ul class="document-toc-list"><li class="document-toc-item "><a class="document-toc-link" href="#what_is_wai-aria">What is WAI-ARIA?</a></li><li class="document-toc-item "><a class="document-toc-link" href="#practical_wai-aria_implementations">Practical WAI-ARIA implementations</a></li><li class="document-toc-item "><a class="document-toc-link" href="#test_your_skills!">Test your skills!</a></li><li class="document-toc-item "><a class="document-toc-link" href="#summary">Summary</a></li><li class="document-toc-item "><a class="document-toc-link" href="#see_also">See also</a></li></ul></section></div></nav></aside><section class="place side"></section></div></div><main id="content" class="main-content "><article class="main-page-content" lang="en-US"><header><h1>WAI-ARIA basics</h1></header><div class="section-content"><ul class="prev-next"> <li><a class="button secondary" href="/en-US/docs/Learn/Accessibility/CSS_and_JavaScript"><span class="button-wrap"> Previous </span></a></li> <li><a class="button secondary" href="/en-US/docs/Learn/Accessibility"><span class="button-wrap"> Overview: Accessibility</span></a></li> <li><a class="button secondary" href="/en-US/docs/Learn/Accessibility/Multimedia"><span class="button-wrap"> Next </span></a></li> </ul> <p>Following on from the previous article, sometimes making complex UI controls that involve unsemantic HTML and dynamic JavaScript-updated content can be difficult. WAI-ARIA is a technology that can help with such problems by adding in further semantics that browsers and assistive technologies can recognize and use to let users know what is going on. Here we'll show how to use it at a basic level to improve accessibility.</p> <figure class="table-container"><table> <tbody> <tr> <th scope="row">Prerequisites:</th> <td> A basic understanding of HTML, CSS, and JavaScript. An understanding of the <a href="/en-US/docs/Learn/Accessibility">previous articles in the course</a>. </td> </tr> <tr> <th scope="row">Objective:</th> <td> To gain familiarity with WAI-ARIA, and how it can be used to provide useful additional semantics to enhance accessibility where required. </td> </tr> </tbody> </table></figure></div><section aria-labelledby="what_is_wai-aria"><h2 id="what_is_wai-aria"><a href="#what_is_wai-aria">What is WAI-ARIA?</a></h2><div class="section-content"><p>Let's start by looking at what WAI-ARIA is, and what it can do for us.</p></div></section><section aria-labelledby="a_whole_new_set_of_problems"><h3 id="a_whole_new_set_of_problems"><a href="#a_whole_new_set_of_problems">A whole new set of problems</a></h3><div class="section-content"><p>As web apps started to get more complex and dynamic, a new set of accessibility features and problems started to appear.</p> <p>For example, HTML introduced a number of semantic elements to define common page features (<a href="/en-US/docs/Web/HTML/Element/nav"><code>&lt;nav&gt;</code></a>, <a href="/en-US/docs/Web/HTML/Element/footer"><code>&lt;footer&gt;</code></a>, etc.). Before these were available, developers would use <a href="/en-US/docs/Web/HTML/Element/div"><code>&lt;div&gt;</code></a>s with IDs or classes, e.g. <code>&lt;div class="nav"&gt;</code>, but these were problematic, as there was no easy way to easily find a specific page feature such as the main navigation programmatically.</p> <p>The initial solution was to add one or more hidden links at the top of the page to link to the navigation (or whatever else), for example:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;a href="#hidden" class="hidden"&gt;Skip to navigation&lt;/a&gt; </code></pre></div> <p>But this is still not very precise, and can only be used when the screen reader is reading from the top of the page.</p> <p>As another example, apps started to feature complex controls like date pickers for choosing dates, sliders for choosing values, etc. HTML provides special input types to render such controls:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;input type="date" /&gt; &lt;input type="range" /&gt; </code></pre></div> <p>These were originally not well-supported and it was, and still is to a lesser extent, difficult to style them, leading designers and developers to opt for custom solutions. Instead of using these native features, some developers rely on JavaScript libraries that generate such controls as a series of nested <a href="/en-US/docs/Web/HTML/Element/div"><code>&lt;div&gt;</code></a>s which are then styled using CSS and controlled using JavaScript.</p> <p>The problem here is that visually they work, but screen readers can't make any sense of what they are at all, and their users just get told that they can see a jumble of elements with no semantics to describe what they mean.</p></div></section><section aria-labelledby="enter_wai-aria"><h3 id="enter_wai-aria"><a href="#enter_wai-aria">Enter WAI-ARIA</a></h3><div class="section-content"><p><a href="https://www.w3.org/TR/wai-aria/" class="external" target="_blank">WAI-ARIA</a> (Web Accessibility Initiative - Accessible Rich Internet Applications) is a specification written by the W3C, defining a set of additional HTML attributes that can be applied to elements to provide additional semantics and improve accessibility wherever it is lacking. There are three main features defined in the spec:</p> <dl> <dt id="roles"><a href="/en-US/docs/Web/Accessibility/ARIA/Roles">Roles</a></dt> <dd> <p>These define what an element is or does. Many of these are so-called landmark roles, which largely duplicate the semantic value of structural elements, such as <code>role="navigation"</code> (<a href="/en-US/docs/Web/HTML/Element/nav"><code>&lt;nav&gt;</code></a>) or <code>role="complementary"</code> (<a href="/en-US/docs/Web/HTML/Element/aside"><code>&lt;aside&gt;</code></a>). Some other roles describe different page structures, such as <code>role="banner"</code>, <code>role="search"</code>, <code>role="tablist"</code>, and <code>role="tabpanel"</code>, which are commonly found in UIs.</p> </dd> <dt id="properties"><a href="#properties">Properties</a></dt> <dd> <p>These define properties of elements, which can be used to give them extra meaning or semantics. As an example, <code>aria-required="true"</code> specifies that a form input needs to be filled in order to be valid, whereas <code>aria-labelledby="label"</code> allows you to put an ID on an element, then reference it as being the label for anything else on the page, including multiple elements, which is not possible using <code>&lt;label for="input"&gt;</code>. As an example, you could use <code>aria-labelledby</code> to specify that a key description contained in a <a href="/en-US/docs/Web/HTML/Element/div"><code>&lt;div&gt;</code></a> is the label for multiple table cells, or you could use it as an alternative to image alt text — specify existing information on the page as an image's alt text, rather than having to repeat it inside the <code>alt</code> attribute. You can see an example of this at <a href="/en-US/docs/Learn/Accessibility/HTML#text_alternatives">Text alternatives</a>.</p> </dd> <dt id="states"><a href="#states">States</a></dt> <dd> <p>Special properties that define the current conditions of elements, such as <code>aria-disabled="true"</code>, which specifies to a screen reader that a form input is currently disabled. States differ from properties in that properties don't change throughout the lifecycle of an app, whereas states can change, generally programmatically via JavaScript.</p> </dd> </dl> <p>An important point about WAI-ARIA attributes is that they don't affect anything about the web page, except for the information exposed by the browser's accessibility APIs (where screen readers get their information from). WAI-ARIA doesn't affect webpage structure, the DOM, etc., although the attributes can be useful for selecting elements by CSS.</p> <div class="notecard note"> <p><strong>Note:</strong> You can find a useful list of all the ARIA roles and their uses, with links to further information, in the WAI-ARIA spec — see <a href="https://www.w3.org/TR/wai-aria-1.1/#role_definitions" class="external" target="_blank">Definition of Roles</a> — on this site — see <a href="/en-US/docs/Web/Accessibility/ARIA/Roles">ARIA roles</a>.</p> <p>The spec also contains a list of all the properties and states, with links to further information — see <a href="https://www.w3.org/TR/wai-aria-1.1/#state_prop_def" class="external" target="_blank">Definitions of States and Properties (all <code>aria-*</code> attributes)</a>.</p> </div></div></section><section aria-labelledby="where_is_wai-aria_supported"><h3 id="where_is_wai-aria_supported"><a href="#where_is_wai-aria_supported">Where is WAI-ARIA supported?</a></h3><div class="section-content"><p>This is not an easy question to answer. It is difficult to find a conclusive resource that states what features of WAI-ARIA are supported, and where, because:</p> <ol> <li>There are a lot of features in the WAI-ARIA spec.</li> <li>There are many combinations of operating systems, browsers, and screen readers to consider.</li> </ol> <p>This last point is key — To use a screen reader in the first place, your operating system needs to run browsers that have the necessary accessibility APIs in place to expose the information screen readers need to do their job. Most popular OSes have one or two browsers in place that screen readers can work with. The Paciello Group has a fairly up-to-date post that provides data for this — see <a href="https://www.tpgi.com/rough-guide-browsers-operating-systems-and-screen-reader-support-updated/" class="external" target="_blank">Rough Guide: browsers, operating systems and screen reader support updated</a>.</p> <p>Next, you need to worry about whether the browsers in question support ARIA features and expose them via their APIs, but also whether screen readers recognize that information and present it to their users in a useful way.</p> <ol> <li>Browser support is almost universal.</li> <li>Screen reader support for ARIA features isn't quite at this level, but the most popular screen readers are getting there. You can get an idea of support levels by looking at Powermapper's <a href="https://www.powermapper.com/tests/screen-readers/aria/" class="external" target="_blank">WAI-ARIA Screen reader compatibility</a> article.</li> </ol> <p>In this article, we won't attempt to cover every WAI-ARIA feature, and its exact support details. Instead, we will cover the most critical WAI-ARIA features for you to know about; if we don't mention any support details, you can assume that the feature is well-supported. We will clearly mention any exceptions to this.</p> <div class="notecard note"> <p><strong>Note:</strong> Some JavaScript libraries support WAI-ARIA, meaning that when they generate UI features like complex form controls, they add ARIA attributes to improve the accessibility of those features. If you are looking for a 3rd party JavaScript solution for rapid UI development, you should definitely consider the accessibility of its UI widgets as an important factor when making your choice. Good examples are jQuery UI (see <a href="https://jqueryui.com/about/#deep-accessibility-support" class="external" target="_blank">About jQuery UI: Deep accessibility support</a>), <a href="https://www.sencha.com/products/extjs/" class="external" target="_blank">ExtJS</a>, and <a href="https://dojotoolkit.org/reference-guide/1.10/dijit/a11y/statement.html" class="external" target="_blank">Dojo/Dijit</a>.</p> </div></div></section><section aria-labelledby="when_should_you_use_wai-aria"><h3 id="when_should_you_use_wai-aria"><a href="#when_should_you_use_wai-aria">When should you use WAI-ARIA?</a></h3><div class="section-content"><p>We talked about some of the problems that prompted WAI-ARIA to be created earlier on, but essentially, there are four main areas that WAI-ARIA is useful in:</p> <dl> <dt id="signpostslandmarks"><a href="#signpostslandmarks">Signposts/Landmarks</a></dt> <dd> <p>ARIA's <a href="/en-US/docs/Web/Accessibility/ARIA/Roles"><code>role</code></a> attribute values can act as landmarks that either replicate the semantics of HTML elements (e.g., <a href="/en-US/docs/Web/HTML/Element/nav"><code>&lt;nav&gt;</code></a>), or go beyond HTML semantics to provide signposts to different functional areas, for example, <code>search</code>, <code>tablist</code>, <code>tab</code>, <code>listbox</code>, etc.</p> </dd> <dt id="dynamic_content_updates"><a href="#dynamic_content_updates">Dynamic content updates</a></dt> <dd> <p>Screen readers tend to have difficulty with reporting constantly changing content; with ARIA we can use <code>aria-live</code> to inform screen reader users when an area of content is updated dynamically: for example, by JavaScript in the page <a href="/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Fetching_data">fetching new content from the server and updating the DOM</a>.</p> </dd> <dt id="enhancing_keyboard_accessibility"><a href="#enhancing_keyboard_accessibility">Enhancing keyboard accessibility</a></dt> <dd> <p>There are built-in HTML elements that have native keyboard accessibility; when other elements are used along with JavaScript to simulate similar interactions, keyboard accessibility and screen reader reporting suffers as a result. Where this is unavoidable, WAI-ARIA provides a means to allow other elements to receive focus (using <code>tabindex</code>).</p> </dd> <dt id="accessibility_of_non-semantic_controls"><a href="#accessibility_of_non-semantic_controls">Accessibility of non-semantic controls</a></dt> <dd> <p>When a series of nested <code>&lt;div&gt;</code>s along with CSS/JavaScript is used to create a complex UI-feature, or a native control is greatly enhanced/changed via JavaScript, accessibility can suffer — screen reader users will find it difficult to work out what the feature does if there are no semantics or other clues. In these situations, ARIA can help to provide what's missing with a combination of roles like <code>button</code>, <code>listbox</code>, or <code>tablist</code>, and properties like <code>aria-required</code> or <code>aria-posinset</code> to provide further clues as to functionality.</p> </dd> </dl> <p>One thing to remember though — <strong>you should only use WAI-ARIA when you need to!</strong> Ideally, you should <em>always</em> use <a href="/en-US/docs/Learn/Accessibility/HTML">native HTML features</a> to provide the semantics required by screen readers to tell their users what is going on. Sometimes this isn't possible, either because you have limited control over the code, or because you are creating something complex that doesn't have an easy HTML element to implement it. In such cases, WAI-ARIA can be a valuable accessibility enhancing tool.</p> <p>But again, only use it when necessary!</p> <div class="notecard note"> <p><strong>Note:</strong> Also, try to make sure you test your site with a variety of <em>real</em> users — non-disabled people, people using screen readers, people using keyboard navigation, etc. They will have better insights than you about how well it works.</p> </div></div></section><section aria-labelledby="practical_wai-aria_implementations"><h2 id="practical_wai-aria_implementations"><a href="#practical_wai-aria_implementations">Practical WAI-ARIA implementations</a></h2><div class="section-content"><p>In the next section, we'll look at the four areas in more detail, along with practical examples. Before you continue, you should get a screen reader testing setup put in place, so you can test some of the examples as you go through.</p> <p>See our section on <a href="/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Accessibility#screen_readers">testing screen readers</a> for more information.</p></div></section><section aria-labelledby="signpostslandmarks_2"><h3 id="signpostslandmarks_2"><a href="#signpostslandmarks_2">Signposts/Landmarks</a></h3><div class="section-content"><p>WAI-ARIA adds the <a href="https://www.w3.org/TR/wai-aria-1.1/#role_definitions" class="external" target="_blank"><code>role</code> attribute</a> to browsers, which allows you to add extra semantic value to elements on your site wherever they are needed. The first major area in which this is useful is providing information for screen readers so that their users can find common page elements. Let's look at an example — our <a href="https://github.com/mdn/learning-area/tree/main/accessibility/aria/website-no-roles" class="external" target="_blank">website-no-roles</a> example (<a href="https://mdn.github.io/learning-area/accessibility/aria/website-no-roles/" class="external" target="_blank">see it live</a>) has the following structure:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;header&gt; &lt;h1&gt;…&lt;/h1&gt; &lt;nav&gt; &lt;ul&gt; … &lt;/ul&gt; &lt;form&gt; &lt;!-- search form --&gt; &lt;/form&gt; &lt;/nav&gt; &lt;/header&gt; &lt;main&gt; &lt;article&gt;…&lt;/article&gt; &lt;aside&gt;…&lt;/aside&gt; &lt;/main&gt; &lt;footer&gt;…&lt;/footer&gt; </code></pre></div> <p>If you try testing the example with a screen reader in a modern browser, you'll already get some useful information. For example, VoiceOver gives you the following:</p> <ul> <li>On the <code>&lt;header&gt;</code> element — "banner, 2 items" (it contains a heading and the <code>&lt;nav&gt;</code>).</li> <li>On the <code>&lt;nav&gt;</code> element — "navigation 2 items" (it contains a list and a form).</li> <li>On the <code>&lt;main&gt;</code> element — "main 2 items" (it contains an article and an aside).</li> <li>On the <code>&lt;aside&gt;</code> element — "complementary 2 items" (it contains a heading and a list).</li> <li>On the search form input — "Search query, insertion at beginning of text".</li> <li>On the <code>&lt;footer&gt;</code> element — "footer 1 item".</li> </ul> <p>If you go to VoiceOver's landmarks menu (accessed using VoiceOver key + U and then using the cursor keys to cycle through the menu choices), you'll see that most of the elements are nicely listed so they can be accessed quickly.</p> <p> <img src="/en-US/docs/Learn/Accessibility/WAI-ARIA_basics/landmarks-list.png" alt="Mac's VoiceOver menu for quick accessibility. Landmarks header and landmarks list including banner, navigation, main, and complementary." width="729" height="532" loading="lazy"> </p> <p>However, we could do better here. The search form is a really important landmark that people will want to find, but it is not listed in the landmarks menu or treated like a notable landmark beyond the actual input being called out as a search input (<code>&lt;input type="search"&gt;</code>).</p> <p>Let's improve it by the use of some ARIA features. First, we'll add some <a href="/en-US/docs/Web/Accessibility/ARIA/Roles"><code>role</code></a> attributes to our HTML structure. You can try taking a copy of our original files (see <a href="https://github.com/mdn/learning-area/blob/main/accessibility/aria/website-no-roles/index.html" class="external" target="_blank"><code>index.html</code></a> and <a href="https://github.com/mdn/learning-area/blob/main/accessibility/aria/website-no-roles/style.css" class="external" target="_blank"><code>style.css</code></a>), or navigating to our <a href="https://github.com/mdn/learning-area/tree/main/accessibility/aria/website-aria-roles" class="external" target="_blank">website-aria-roles</a> example (<a href="https://mdn.github.io/learning-area/accessibility/aria/website-aria-roles/" class="external" target="_blank">see it live</a>), which has a structure like this:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;header&gt; &lt;h1&gt;…&lt;/h1&gt; &lt;nav role="navigation"&gt; &lt;ul&gt; … &lt;/ul&gt; &lt;form role="search"&gt; &lt;!-- search form --&gt; &lt;/form&gt; &lt;/nav&gt; &lt;/header&gt; &lt;main&gt; &lt;article role="article"&gt;…&lt;/article&gt; &lt;aside role="complementary"&gt;…&lt;/aside&gt; &lt;/main&gt; &lt;footer&gt;…&lt;/footer&gt; </code></pre></div> <p>We've also given you a bonus feature in this example — the <a href="/en-US/docs/Web/HTML/Element/input"><code>&lt;input&gt;</code></a> element has been given the attribute <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-label"><code>aria-label</code></a>, which gives it a descriptive label to be read out by a screen reader, even though we haven't included a <a href="/en-US/docs/Web/HTML/Element/label"><code>&lt;label&gt;</code></a> element. In cases like these, this is very useful — a search form like this one is a very common, easily recognized feature, and adding a visual label would spoil the page design.</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;input type="search" name="q" placeholder="Search query" aria-label="Search through site content" /&gt; </code></pre></div> <p>Now if we use VoiceOver to look at this example, we get some improvements:</p> <ul> <li>The search form is called out as a separate item, both when browsing through the page, and in the Landmarks menu.</li> <li>The label text contained in the <code>aria-label</code> attribute is read out when the form input is highlighted.</li> </ul> <p>Beyond this, the site is more likely to be accessible to users of older browsers such as IE8; it is worth including ARIA roles for that purpose. And if for some reason your site is built using just <code>&lt;div&gt;</code>s, you should definitely include the ARIA roles to provide these much needed semantics!</p> <p>The improved semantics of the search form have shown what is made possible when ARIA goes beyond the semantics available in HTML. You'll see a lot more about these semantics and the power of ARIA properties/attributes below, especially in the <a href="#accessibility_of_non-semantic_controls">Accessibility of non-semantic controls</a> section. For now though, let's look at how ARIA can help with dynamic content updates.</p></div></section><section aria-labelledby="dynamic_content_updates_2"><h3 id="dynamic_content_updates_2"><a href="#dynamic_content_updates_2">Dynamic content updates</a></h3><div class="section-content"><p>Content loaded into the DOM can be easily accessed using a screen reader, from textual content to alternative text attached to images. Traditional static websites with largely text content are therefore easy to make accessible for people with visual impairments.</p> <p>The problem is that modern web apps are often not just static text — they often update parts of the page by fetching new content from the server and updating the DOM. These are sometimes referred to as <strong>live regions</strong>.</p> <p>Let's look at a quick example — see <a href="https://github.com/mdn/learning-area/blob/main/accessibility/aria/aria-no-live.html" class="external" target="_blank"><code>aria-no-live.html</code></a> (also <a href="https://mdn.github.io/learning-area/accessibility/aria/aria-no-live.html" class="external" target="_blank">see it running live</a>). In this example, we have a simple random quote box:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;section&gt; &lt;h1&gt;Random quote&lt;/h1&gt; &lt;blockquote&gt; &lt;p&gt;&lt;/p&gt; &lt;/blockquote&gt; &lt;/section&gt; </code></pre></div> <p>Our JavaScript uses the <a href="/en-US/docs/Web/API/Window/fetch" title="fetch()"><code>fetch()</code></a> API to load a JSON file via containing a series of random quotes and their authors. Once that is done, we start up a <a href="/en-US/docs/Web/API/Window/setInterval" title="setInterval()"><code>setInterval()</code></a> loop that loads a new random quote into the quote box every 10 seconds:</p> <div class="code-example"><div class="example-header"><span class="language-name">js</span></div><pre class="brush: js notranslate"><code>const intervalID = setInterval(showQuote, 10000); </code></pre></div> <p>This works OK, but it is not good for accessibility — the content update is not detected by screen readers, so their users would not know what is going on. This is a fairly trivial example, but just imagine if you were creating a complex UI with lots of constantly updating content, like a chat room, or a strategy game UI, or a live updating shopping cart display — it would be impossible to use the app in any effective way without some kind of way of alerting the user to the updates.</p> <p>WAI-ARIA, fortunately, provides a useful mechanism to provide these alerts — the <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-live"><code>aria-live</code></a> property. Applying this to an element causes screen readers to read out the content that is updated. How urgently the content is read out depends on the attribute value:</p> <dl> <dt id="off"><a href="#off"><code>off</code></a></dt> <dd> <p>The default. Updates should not be announced.</p> </dd> <dt id="polite"><a href="#polite"><code>polite</code></a></dt> <dd> <p>Updates should be announced only if the user is idle.</p> </dd> <dt id="assertive"><a href="#assertive"><code>assertive</code></a></dt> <dd> <p>Updates should be announced to the user as soon as possible.</p> </dd> </dl> <p>We'd like you to take a copy of <a href="https://github.com/mdn/learning-area/blob/main/accessibility/aria/aria-no-live.html" class="external" target="_blank"><code>aria-no-live.html</code></a> and <a href="https://github.com/mdn/learning-area/blob/main/accessibility/aria/quotes.json" class="external" target="_blank"><code>quotes.json</code></a>, and update your <code>&lt;section&gt;</code> opening tag as follows:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;section aria-live="assertive"&gt;…&lt;/section&gt; </code></pre></div> <p>This will cause a screen reader to read out the content as it is updated.</p> <div class="notecard note"> <p><strong>Note:</strong> Most browsers will throw a security exception if you try to make an HTTP request from a <code>file://</code> URL, e.g. if you just load the file by loading it directly into the browser (via double clicking, etc.). See <a href="/en-US/docs/Learn/Common_questions/Tools_and_setup/set_up_a_local_testing_server">how to set up a local testing server</a>.</p> </div> <p>There is an additional consideration here — only the bit of text that updates is read out. It might be nice if we always read out the heading too, so the user can remember what is being read out. To do this, we can add the <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-atomic"><code>aria-atomic</code></a> property to the section. Update your <code>&lt;section&gt;</code> opening tag again, like so:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;section aria-live="assertive" aria-atomic="true"&gt;…&lt;/section&gt; </code></pre></div> <p>The <code>aria-atomic="true"</code> attribute tells screen readers to read out the entire element contents as one atomic unit, not just the bits that were updated.</p> <div class="notecard note"> <p><strong>Note:</strong> You can see the finished example at <a href="https://github.com/mdn/learning-area/blob/main/accessibility/aria/aria-live.html" class="external" target="_blank"><code>aria-live.html</code></a> (<a href="https://mdn.github.io/learning-area/accessibility/aria/aria-live.html" class="external" target="_blank">see it running live</a>).</p> </div> <div class="notecard note"> <p><strong>Note:</strong> The <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-relevant"><code>aria-relevant</code></a> property is also quite useful for controlling what gets read out when a live region is updated. You can for example only get content additions or removals read out.</p> </div></div></section><section aria-labelledby="enhancing_keyboard_accessibility_2"><h3 id="enhancing_keyboard_accessibility_2"><a href="#enhancing_keyboard_accessibility_2">Enhancing keyboard accessibility</a></h3><div class="section-content"><p>As discussed in a few other places in the module, one of the key strengths of HTML with respect to accessibility is the built-in keyboard accessibility of features such as buttons, form controls, and links. Generally, you can use the tab key to move between controls, the Enter/Return key to select or activate controls, and occasionally other controls as needed (for example the up and down cursor to move between options in a <code>&lt;select&gt;</code> box).</p> <p>However, sometimes you will end up having to write code that either uses non-semantic elements as buttons (or other types of control), or uses focusable controls for not quite the right purpose. You might be trying to fix some bad code you've inherited, or you might be building some kind of complex widget that requires it.</p> <p>In terms of making non-focusable code focusable, WAI-ARIA extends the <code>tabindex</code> attribute with some new values:</p> <ul> <li><code>tabindex="0"</code> — as indicated above, this value allows elements that are not normally tabbable to become tabbable. This is the most useful value of <code>tabindex</code>.</li> <li><code>tabindex="-1"</code> — this allows not normally tabbable elements to receive focus programmatically, e.g. via JavaScript, or as the target of links.</li> </ul> <p>We discussed this in more detail and showed a typical implementation back in our HTML accessibility article — see <a href="/en-US/docs/Learn/Accessibility/HTML#building_keyboard_accessibility_back_in">Building keyboard accessibility back in</a>.</p></div></section><section aria-labelledby="accessibility_of_non-semantic_controls_2"><h3 id="accessibility_of_non-semantic_controls_2"><a href="#accessibility_of_non-semantic_controls_2">Accessibility of non-semantic controls</a></h3><div class="section-content"><p>This follows on from the previous section — when a series of nested <code>&lt;div&gt;</code>s along with CSS/JavaScript is used to create a complex UI-feature, or a native control is greatly enhanced/changed via JavaScript, not only can keyboard accessibility suffer, but screen reader users will find it difficult to work out what the feature does if there are no semantics or other clues. In such situations, ARIA can help to provide those missing semantics.</p> <h4 id="form_validation_and_error_alerts">Form validation and error alerts</h4> <p>First of all, let's revisit the form example we first looked at in our CSS and JavaScript accessibility article (read <a href="/en-US/docs/Learn/Accessibility/CSS_and_JavaScript#keeping_it_unobtrusive">Keeping it unobtrusive</a> for a full recap). At the end of this section, we showed that we have included some ARIA attributes on the error message box that displays any validation errors when you try to submit the form:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;div class="errors" role="alert" aria-relevant="all"&gt; &lt;ul&gt;&lt;/ul&gt; &lt;/div&gt; </code></pre></div> <ul> <li><a href="/en-US/docs/Web/Accessibility/ARIA/Roles/alert_role"><code>role="alert"</code></a> automatically turns the element it is applied to into a live region, so changes to it are read out; it also semantically identifies it as an alert message (important time/context-sensitive information), and represents a better, more accessible way of delivering an alert to a user (modal dialogs like <a href="/en-US/docs/Web/API/Window/alert"><code>alert()</code></a> calls have a number of accessibility problems; see <a href="https://webaim.org/techniques/javascript/other#popups" class="external" target="_blank">Popup Windows</a> by WebAIM).</li> <li>An <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-relevant"><code>aria-relevant</code></a> value of <code>all</code> instructs the screen reader to read out the contents of the error list when any changes are made to it — i.e., when errors are added or removed. This is useful because the user will want to know what errors are left, not just what has been added or removed from the list.</li> </ul> <p>We could go further with our ARIA usage, and provide some more validation help. How about indicating whether fields are required in the first place, and what range the age should be?</p> <ol> <li> <p>At this point, take a copy of our <a href="https://github.com/mdn/learning-area/blob/main/accessibility/css/form-validation.html" class="external" target="_blank"><code>form-validation.html</code></a> and <a href="https://github.com/mdn/learning-area/blob/main/accessibility/css/validation.js" class="external" target="_blank"><code>validation.js</code></a> files, and save them in a local directory.</p> </li> <li> <p>Open them both in a text editor and have a look at how the code works.</p> </li> <li> <p>First of all, add a paragraph just above the opening <code>&lt;form&gt;</code> tag, like the one below, and mark both the form <code>&lt;label&gt;</code>s with an asterisk. This is normally how we mark required fields for sighted users.</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;p&gt;Fields marked with an asterisk (*) are required.&lt;/p&gt; </code></pre></div> </li> <li> <p>This makes visual sense, but it isn't as easy to understand for screen reader users. Fortunately, WAI-ARIA provides the <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-required"><code>aria-required</code></a> attribute to give screen readers hints that they should tell users that form inputs need to be filled in. Update the <code>&lt;input&gt;</code> elements like so:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;input type="text" name="name" id="name" aria-required="true" /&gt; &lt;input type="number" name="age" id="age" aria-required="true" /&gt; </code></pre></div> </li> <li> <p>If you save the example now and test it with a screen reader, you should hear something like "Enter your name star, required, edit text".</p> </li> <li> <p>It might also be useful if we give screen reader users and sighted users an idea of what the age value should be. This is often presented as a tooltip or placeholder inside the form field. WAI-ARIA does include <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-valuemin"><code>aria-valuemin</code></a> and <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-valuemax"><code>aria-valuemax</code></a> properties to specify min and max values, and screen readers support the native <code>min</code> and <code>max</code> attributes. Another well-supported feature is the HTML <code>placeholder</code> attribute, which can contain a message that is shown in the input when no value is entered and is read out by a few screen readers. Update your number input like this:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;label for="age"&gt;Your age:&lt;/label&gt; &lt;input type="number" name="age" id="age" placeholder="Enter 1 to 150" required aria-required="true" /&gt; </code></pre></div> </li> </ol> <p>Always include a <a href="/en-US/docs/Web/HTML/Element/label"><code>&lt;label&gt;</code></a> for every input. While some screen readers announce the placeholder text, most do not. Acceptable substitutions for providing form controls with an accessible name include <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-label"><code>aria-label</code></a> and <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-labelledby"><code>aria-labelledby</code></a>. But the <code>&lt;label&gt;</code> element with a <code>for</code> attribute is the preferred method as it provides usability for all users, including mouse users.</p> <div class="notecard note"> <p><strong>Note:</strong> You can see the finished example live at <a href="https://mdn.github.io/learning-area/accessibility/aria/form-validation-updated.html" class="external" target="_blank"><code>form-validation-updated.html</code></a>.</p> </div> <p>WAI-ARIA also enables some advanced form labelling techniques, beyond the classic <a href="/en-US/docs/Web/HTML/Element/label"><code>&lt;label&gt;</code></a> element. We already talked about using the <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-label"><code>aria-label</code></a> property to provide a label where we don't want the label to be visible to sighted users (see the <a href="#signpostslandmarks">Signposts/Landmarks</a> section, above). Some other labeling techniques use other properties such as <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-labelledby"><code>aria-labelledby</code></a> if you want to designate a non-<code>&lt;label&gt;</code> element as a label or label multiple form inputs with the same label, and <a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-describedby"><code>aria-describedby</code></a>, if you want to associate other information with a form input and have it read out as well. See <a href="https://webaim.org/techniques/forms/advanced" class="external" target="_blank">WebAIM's Advanced Form Labeling article</a> for more details.</p> <p>There are many other useful properties and states too, for indicating the status of form elements. For example, <code>aria-disabled="true"</code> can be used to indicate that a form field is disabled. Many browsers will skip past disabled form fields which leads to them not being read out by screen readers. In some cases, a disabled element will be perceived, so it is a good idea to include this attribute to let the screen reader know that a disabled form control is in fact disabled.</p> <p>If the disabled state of an input is likely to change, then it is also a good idea to indicate when it happens, and what the result is. For example, in our <a href="https://mdn.github.io/learning-area/accessibility/aria/form-validation-checkbox-disabled.html" class="external" target="_blank"><code>form-validation-checkbox-disabled.html</code></a> demo, there is a checkbox that when checked, enables another form input to allow further information to be entered. We've set up a hidden live region:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;p class="hidden-alert" aria-live="assertive"&gt;&lt;/p&gt; </code></pre></div> <p>which is hidden from view using absolute positioning. When this is checked/unchecked, we update the text inside the hidden live region to tell screen reader users what the result of checking this checkbox is, as well as updating the <code>aria-disabled</code> state, and some visual indicators too:</p> <div class="code-example"><div class="example-header"><span class="language-name">js</span></div><pre class="brush: js notranslate"><code>function toggleMusician(bool) { const instrument = formItems[formItems.length - 1]; if (bool) { instrument.input.disabled = false; instrument.label.style.color = "#000"; instrument.input.setAttribute("aria-disabled", "false"); hiddenAlert.textContent = "Instruments played field now enabled; use it to tell us what you play."; } else { instrument.input.disabled = true; instrument.label.style.color = "#999"; instrument.input.setAttribute("aria-disabled", "true"); instrument.input.removeAttribute("aria-label"); hiddenAlert.textContent = "Instruments played field now disabled."; } } </code></pre></div> <h4 id="describing_non-semantic_buttons_as_buttons">Describing non-semantic buttons as buttons</h4> <p>A few times in this course already, we've mentioned the native accessibility of (and the accessibility issues behind using other elements to fake) buttons, links, or form elements (see <a href="/en-US/docs/Learn/Accessibility/HTML#ui_controls">UI controls</a> in the HTML accessibility article, and <a href="#enhancing_keyboard_accessibility">Enhancing keyboard accessibility</a>, above). Basically, you can add keyboard accessibility back in without too much trouble in many cases, using <code>tabindex</code> and a bit of JavaScript.</p> <p>But what about screen readers? They still won't see the elements as buttons. If we test our <a href="https://mdn.github.io/learning-area/tools-testing/cross-browser-testing/accessibility/fake-div-buttons.html" class="external" target="_blank"><code>fake-div-buttons.html</code></a> example in a screen reader, our fake buttons will be reported using phrases like "Click me!, group", which is obviously confusing.</p> <p>We can fix this using a WAI-ARIA role. Make a local copy of <a href="https://github.com/mdn/learning-area/blob/main/tools-testing/cross-browser-testing/accessibility/fake-div-buttons.html" class="external" target="_blank"><code>fake-div-buttons.html</code></a>, and add <a href="/en-US/docs/Web/Accessibility/ARIA/Roles/button_role"><code>role="button"</code></a> to each button <code>&lt;div&gt;</code>, for example:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;div data-message="This is from the first button" tabindex="0" role="button"&gt; Click me! &lt;/div&gt; </code></pre></div> <p>Now when you try this using a screen reader, you'll have buttons be reported using phrases like "Click me!, button". While this is much better, you still have to add in all the native button features users expect, like handling <kbd>enter</kbd> and click events, as explained in the <a href="/en-US/docs/Web/Accessibility/ARIA/Roles/button_role"><code>button</code> role documentation</a>.</p> <div class="notecard note"> <p><strong>Note:</strong> Don't forget however that using the correct semantic element where possible is always better. If you want to create a button, and can use a <a href="/en-US/docs/Web/HTML/Element/button"><code>&lt;button&gt;</code></a> element, you should use a <a href="/en-US/docs/Web/HTML/Element/button"><code>&lt;button&gt;</code></a> element!</p> </div> <h4 id="guiding_users_through_complex_widgets">Guiding users through complex widgets</h4> <p>There are a whole host of other <a href="/en-US/docs/Web/Accessibility/ARIA/Roles">roles</a> that can identify non-semantic element structures as common UI features that go beyond what's available in standard HTML, for example <a href="/en-US/docs/Web/Accessibility/ARIA/Roles/combobox_role"><code>combobox</code></a>, <a href="/en-US/docs/Web/Accessibility/ARIA/Roles/slider_role"><code>slider</code></a>, <a href="/en-US/docs/Web/Accessibility/ARIA/Roles/tabpanel_role"><code>tabpanel</code></a>, <a href="/en-US/docs/Web/Accessibility/ARIA/Roles/tree_role"><code>tree</code></a>. You can see several useful examples in the <a href="https://dequeuniversity.com/library/" class="external" target="_blank">Deque university code library</a> to give you an idea of how such controls can be made accessible.</p> <p>Let's go through an example of our own. We'll return to our simple absolutely-positioned tabbed interface (see <a href="/en-US/docs/Learn/Accessibility/CSS_and_JavaScript#hiding_things">Hiding things</a> in our CSS and JavaScript accessibility article), which you can find at <a href="https://mdn.github.io/learning-area/css/css-layout/practical-positioning-examples/tabbed-info-box.html" class="external" target="_blank">Tabbed info box example</a> (see <a href="https://github.com/mdn/learning-area/blob/main/css/css-layout/practical-positioning-examples/tabbed-info-box.html" class="external" target="_blank">source code</a>).</p> <p>This example as-is works fine in terms of keyboard accessibility — you can happily tab between the different tabs and select them to show the tab contents. It is also fairly accessible too — you can scroll through the content and use the headings to navigate, even if you can't see what is happening on screen. It is however not that obvious what the content is — a screen reader currently reports the content as a list of links, and some content with three headings. It doesn't give you any idea of what the relationship is between the content. Giving the user more clues as to the structure of the content is always good.</p> <p>To improve things, we've created a new version of the example called <a href="https://github.com/mdn/learning-area/blob/main/accessibility/aria/aria-tabbed-info-box.html" class="external" target="_blank"><code>aria-tabbed-info-box.html</code></a> (<a href="https://mdn.github.io/learning-area/accessibility/aria/aria-tabbed-info-box.html" class="external" target="_blank">see it running live</a>). We've updated the structure of the tabbed interface like so:</p> <div class="code-example"><div class="example-header"><span class="language-name">html</span></div><pre class="brush: html notranslate"><code>&lt;ul role="tablist"&gt; &lt;li class="active" role="tab" aria-selected="true" aria-setsize="3" aria-posinset="1" tabindex="0"&gt; Tab 1 &lt;/li&gt; &lt;li role="tab" aria-selected="false" aria-setsize="3" aria-posinset="2" tabindex="0"&gt; Tab 2 &lt;/li&gt; &lt;li role="tab" aria-selected="false" aria-setsize="3" aria-posinset="3" tabindex="0"&gt; Tab 3 &lt;/li&gt; &lt;/ul&gt; &lt;div class="panels"&gt; &lt;article class="active-panel" role="tabpanel" aria-hidden="false"&gt;…&lt;/article&gt; &lt;article role="tabpanel" aria-hidden="true"&gt;…&lt;/article&gt; &lt;article role="tabpanel" aria-hidden="true"&gt;…&lt;/article&gt; &lt;/div&gt; </code></pre></div> <div class="notecard note"> <p><strong>Note:</strong> The most striking change here is that we've removed the links that were originally present in the example, and just used the list items as the tabs — this was done because it makes things less confusing for screen reader users (the links don't really take you anywhere; they just change the view), and it allows the setsize/position in set features to work better — when these were put on the links, the browser kept reporting "1 of 1" all the time, not "1 of 3", "2 of 3", etc.</p> </div> <p>ARIA features used include:</p> <dl> <dt id="new_roles_—"><a href="#new_roles_—">New roles — </a><a href="/en-US/docs/Web/Accessibility/ARIA/Roles/tablist_role"><code>tablist</code></a>, <a href="/en-US/docs/Web/Accessibility/ARIA/Roles/tab_role"><code>tab</code></a>, <a href="/en-US/docs/Web/Accessibility/ARIA/Roles/tabpanel_role"><code>tabpanel</code></a></dt> <dd> <p>These identify the important areas of the tabbed interface — the container for the tabs, the tabs themselves, and the corresponding tabpanels.</p> </dd> <dt id="aria-selected"><a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-selected"><code>aria-selected</code></a></dt> <dd> <p>Defines which tab is currently selected. As different tabs are selected by the user, the value of this attribute on the different tabs is updated via JavaScript.</p> </dd> <dt id="aria-hidden"><a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-hidden"><code>aria-hidden</code></a></dt> <dd> <p>Hides an element from being read out by a screen reader. As different tabs are selected by the user, the value of this attribute on the different tabs is updated via JavaScript.</p> </dd> <dt id="tabindex0"><a href="#tabindex0"><code>tabindex="0"</code></a></dt> <dd> <p>As we've removed the links, we need to give the list items this attribute to provide it with keyboard focus.</p> </dd> <dt id="aria-setsize"><a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-setsize"><code>aria-setsize</code></a></dt> <dd> <p>This property allows you to specify to screen readers that an element is part of a series, and how many items the series has.</p> </dd> <dt id="aria-posinset"><a href="/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-posinset"><code>aria-posinset</code></a></dt> <dd> <p>This property allows you to specify what position in a series an element is in. Along with <code>aria-setsize</code>, it provides a screen reader with enough information to tell you that you are currently on item "1 of 3", etc. In many cases, browsers should be able to infer this information from the element hierarchy, but it certainly helps to provide more clues.</p> </dd> </dl> <p>In our tests, this new structure did serve to improve things overall. The tabs are now recognized as tabs (e.g. "tab" is spoken by the screen reader), the selected tab is indicated by "selected" being read out with the tab name, and the screen reader also tells you which tab number you are currently on. In addition, because of the <code>aria-hidden</code> settings (only the non-hidden tab ever has <code>aria-hidden="false"</code> set), the non-hidden content is the only one you can navigate down to, meaning the selected content is easier to find.</p> <div class="notecard note"> <p><strong>Note:</strong> If there is anything you explicitly don't want screen readers to read out, you can give them the <code>aria-hidden="true"</code> attribute.</p> </div></div></section><section aria-labelledby="test_your_skills!"><h2 id="test_your_skills!"><a href="#test_your_skills!">Test your skills!</a></h2><div class="section-content"><p>You've reached the end of this article, but can you remember the most important information? You can find some further tests to verify that you've retained this information before you move on — see <a href="/en-US/docs/Learn/Accessibility/WAI-ARIA_basics/Test_your_skills:_WAI-ARIA">Test your skills: WAI-ARIA</a>.</p></div></section><section aria-labelledby="summary"><h2 id="summary"><a href="#summary">Summary</a></h2><div class="section-content"><p>This article has by no means covered all that's available in WAI-ARIA, but it should have given you enough information to understand how to use it, and know some of the most common patterns you will encounter that require it.</p></div></section><section aria-labelledby="see_also"><h2 id="see_also"><a href="#see_also">See also</a></h2><div class="section-content"><ul> <li><a href="/en-US/docs/Web/Accessibility/ARIA/Attributes">Aria states and properties</a>: All <code>aria-*</code> attributes</li> <li><a href="/en-US/docs/Web/Accessibility/ARIA/Roles">WAI-ARIA roles</a>: Categories of ARIA roles and the roles covered on MDN</li> <li><a href="https://www.w3.org/TR/html-aria/" class="external" target="_blank">ARIA in HTML</a> on W3C: A specification that defines, for each HTML feature, the accessibility (ARIA) semantics implicitly applied on it by the browser and the WAI-ARIA features you may set on it if extra semantics are required</li> <li><a href="https://dequeuniversity.com/library/" class="external" target="_blank">Deque university code library</a>: A library of really useful and practical examples showing complex UI controls made accessible using WAI-ARIA features</li> <li><a href="https://www.w3.org/WAI/ARIA/apg/" class="external" target="_blank">WAI-ARIA authoring practices</a> on W3C: A very detailed design pattern from the W3C, explaining how to implement different types of complex UI control whilst making them accessible using WAI-ARIA features</li> </ul><ul class="prev-next"> <li><a class="button secondary" href="/en-US/docs/Learn/Accessibility/CSS_and_JavaScript"><span class="button-wrap"> Previous </span></a></li> <li><a class="button secondary" href="/en-US/docs/Learn/Accessibility"><span class="button-wrap"> Overview: Accessibility</span></a></li> <li><a class="button secondary" href="/en-US/docs/Learn/Accessibility/Multimedia"><span class="button-wrap"> Next </span></a></li> </ul></div></section></article><aside class="article-footer"><div class="article-footer-inner"><div class="svg-container"><svg xmlns="http://www.w3.org/2000/svg" width="162" height="162" viewBox="0 0 162 162" fill="none" role="none"><mask id="b" fill="#fff"><path d="M97.203 47.04c8.113-7.886 18.004-13.871 28.906-17.492a78 78 0 0 1 33.969-3.39c11.443 1.39 22.401 5.295 32.024 11.411s17.656 14.28 23.476 23.86c5.819 9.579 9.269 20.318 10.083 31.385a69.85 69.85 0 0 1-5.387 32.44c-4.358 10.272-11.115 19.443-19.747 26.801-8.632 7.359-18.908 12.709-30.034 15.637l-6.17-21.698c7.666-2.017 14.746-5.703 20.694-10.773 5.948-5.071 10.603-11.389 13.606-18.467a48.14 48.14 0 0 0 3.712-22.352c-.561-7.625-2.938-15.025-6.948-21.625s-9.544-12.226-16.175-16.44-14.181-6.904-22.065-7.863a53.75 53.75 0 0 0-23.405 2.336c-7.513 2.495-14.327 6.62-19.918 12.053z"></path></mask><path stroke="url(#a)" stroke-dasharray="6, 6" stroke-width="2" d="M97.203 47.04c8.113-7.886 18.004-13.871 28.906-17.492a78 78 0 0 1 33.969-3.39c11.443 1.39 22.401 5.295 32.024 11.411s17.656 14.28 23.476 23.86c5.819 9.579 9.269 20.318 10.083 31.385a69.85 69.85 0 0 1-5.387 32.44c-4.358 10.272-11.115 19.443-19.747 26.801-8.632 7.359-18.908 12.709-30.034 15.637l-6.17-21.698c7.666-2.017 14.746-5.703 20.694-10.773 5.948-5.071 10.603-11.389 13.606-18.467a48.14 48.14 0 0 0 3.712-22.352c-.561-7.625-2.938-15.025-6.948-21.625s-9.544-12.226-16.175-16.44-14.181-6.904-22.065-7.863a53.75 53.75 0 0 0-23.405 2.336c-7.513 2.495-14.327 6.62-19.918 12.053z" mask="url(#b)" style="stroke:url(#a)" transform="translate(-63.992 -25.587)"></path><ellipse cx="8.066" cy="111.597" fill="var(--background-tertiary)" rx="53.677" ry="53.699" transform="matrix(.71707 -.697 .7243 .6895 0 0)"></ellipse><g clip-path="url(#c)" transform="translate(-63.992 -25.587)"><path fill="#9abff5" d="m144.256 137.379 32.906 12.434a4.41 4.41 0 0 1 2.559 5.667l-9.326 24.679a4.41 4.41 0 0 1-5.667 2.559l-8.226-3.108-2.332 6.17c-.466 1.233-.375 1.883-1.609 1.417l-2.253-.527c-.411-.155-.95-.594-1.206-1.161l-4.734-10.484-12.545-4.741a4.41 4.41 0 0 1-2.559-5.667l9.325-24.679a4.41 4.41 0 0 1 5.667-2.559m9.961 29.617 8.227 3.108 3.264-8.638-.498-6.768-4.113-1.555.548 7.258-4.319-1.632zm-12.339-4.663 8.226 3.108 3.264-8.637-.498-6.769-4.113-1.554.548 7.257-4.319-1.632z"></path></g><g clip-path="url(#d)" transform="translate(-63.992 -25.587)"><path fill="#81b0f3" d="M135.35 60.136 86.67 41.654c-3.346-1.27-7.124.428-8.394 3.775L64.414 81.938c-1.27 3.347.428 7.125 3.774 8.395l12.17 4.62-3.465 9.128c-.693 1.826-1.432 2.457.394 3.15l3.014 1.625c.609.231 1.637.274 2.477-.104l15.53-6.983 18.56 7.047c3.346 1.27 7.124-.428 8.395-3.775l13.862-36.51c1.27-3.346-.428-7.124-3.775-8.395M95.261 83.207l-12.17-4.62 4.852-12.779 7.19-7.017 6.085 2.31-7.725 7.51 6.389 2.426zm18.255 6.93-12.17-4.62 4.852-12.778 7.189-7.017 6.085 2.31-7.725 7.51 6.39 2.426z"></path></g><defs><clipPath id="c"><path fill="#fff" d="m198.638 146.586-65.056-24.583-24.583 65.057 65.056 24.582z"></path></clipPath><clipPath id="d"><path fill="#fff" d="m66.438 14.055 96.242 36.54-36.54 96.243-96.243-36.54z"></path></clipPath><linearGradient id="a" x1="97.203" x2="199.995" y1="47.04" y2="152.793" gradientUnits="userSpaceOnUse"><stop stop-color="#086DFC"></stop><stop offset="0.246" stop-color="#2C81FA"></stop><stop offset="0.516" stop-color="#5497F8"></stop><stop offset="0.821" stop-color="#80B0F6"></stop><stop offset="1" stop-color="#9ABFF5"></stop></linearGradient></defs></svg></div><h2>Help improve MDN</h2><fieldset class="feedback"><label>Was this page helpful to you?</label><div class="button-container"><button type="button" class="button primary has-icon yes"><span class="button-wrap"><span class="icon icon-thumbs-up "></span>Yes</span></button><button type="button" class="button primary has-icon no"><span class="button-wrap"><span class="icon icon-thumbs-down "></span>No</span></button></div></fieldset><a class="contribute" href="https://github.com/mdn/content/blob/main/CONTRIBUTING.md" title="This will take you to our contribution guidelines on GitHub." target="_blank" rel="noopener noreferrer">Learn how to contribute</a>.<p class="last-modified-date">This page was last modified on<!-- --> <time dateTime="2024-10-25T00:08:46.000Z">Oct 25, 2024</time> by<!-- --> <a href="/en-US/docs/Learn/Accessibility/WAI-ARIA_basics/contributors.txt" rel="nofollow">MDN contributors</a>.</p><div id="on-github" class="on-github"><a href="https://github.com/mdn/content/blob/main/files/en-us/learn/accessibility/wai-aria_basics/index.md?plain=1" title="Folder: en-us/learn/accessibility/wai-aria_basics (Opens in a new tab)" target="_blank" rel="noopener noreferrer">View this page on GitHub</a> <!-- -->•<!-- --> <a href="https://github.com/mdn/content/issues/new?template=page-report.yml&amp;mdn-url=https%3A%2F%2Fdeveloper.mozilla.org%2Fen-US%2Fdocs%2FLearn%2FAccessibility%2FWAI-ARIA_basics&amp;metadata=%3C%21--+Do+not+make+changes+below+this+line+--%3E%0A%3Cdetails%3E%0A%3Csummary%3EPage+report+details%3C%2Fsummary%3E%0A%0A*+Folder%3A+%60en-us%2Flearn%2Faccessibility%2Fwai-aria_basics%60%0A*+MDN+URL%3A+https%3A%2F%2Fdeveloper.mozilla.org%2Fen-US%2Fdocs%2FLearn%2FAccessibility%2FWAI-ARIA_basics%0A*+GitHub+URL%3A+https%3A%2F%2Fgithub.com%2Fmdn%2Fcontent%2Fblob%2Fmain%2Ffiles%2Fen-us%2Flearn%2Faccessibility%2Fwai-aria_basics%2Findex.md%0A*+Last+commit%3A+https%3A%2F%2Fgithub.com%2Fmdn%2Fcontent%2Fcommit%2Fbaac7f2a43813a7930ff97b11d9c38b413f97c78%0A*+Document+last+modified%3A+2024-10-25T00%3A08%3A46.000Z%0A%0A%3C%2Fdetails%3E" title="This will take you to GitHub to file a new issue." target="_blank" rel="noopener noreferrer">Report a problem with this content</a></div></div></aside></main></div></div><footer id="nav-footer" class="page-footer"><div class="page-footer-grid"><div class="page-footer-logo-col"><a href="/" class="mdn-footer-logo" aria-label="MDN homepage"><svg width="48" height="17" viewBox="0 0 48 17" fill="none" xmlns="http://www.w3.org/2000/svg"><title id="mdn-footer-logo-svg">MDN logo</title><path d="M20.04 16.512H15.504V10.416C15.504 9.488 15.344 8.824 15.024 8.424C14.72 8.024 14.264 7.824 13.656 7.824C12.92 7.824 12.384 8.064 12.048 8.544C11.728 9.024 11.568 9.64 11.568 10.392V14.184H13.008V16.512H8.472V10.416C8.472 9.488 8.312 8.824 7.992 8.424C7.688 8.024 7.232 7.824 6.624 7.824C5.872 7.824 5.336 8.064 5.016 8.544C4.696 9.024 4.536 9.64 4.536 10.392V14.184H6.6V16.512H0V14.184H1.44V8.04H0.024V5.688H4.536V7.32C5.224 6.088 6.32 5.472 7.824 5.472C8.608 5.472 9.328 5.664 9.984 6.048C10.64 6.432 11.096 7.016 11.352 7.8C11.992 6.248 13.168 5.472 14.88 5.472C15.856 5.472 16.72 5.776 17.472 6.384C18.224 6.992 18.6 7.936 18.6 9.216V14.184H20.04V16.512Z" fill="currentColor"></path><path d="M33.6714 16.512H29.1354V14.496C28.8314 15.12 28.3834 15.656 27.7914 16.104C27.1994 16.536 26.4154 16.752 25.4394 16.752C24.0154 16.752 22.8954 16.264 22.0794 15.288C21.2634 14.312 20.8554 12.984 20.8554 11.304C20.8554 9.688 21.2554 8.312 22.0554 7.176C22.8554 6.04 24.0634 5.472 25.6794 5.472C26.5594 5.472 27.2794 5.648 27.8394 6C28.3994 6.352 28.8314 6.8 29.1354 7.344V2.352H26.9754V0H32.2314V14.184H33.6714V16.512ZM29.1354 11.04V10.776C29.1354 9.88 28.8954 9.184 28.4154 8.688C27.9514 8.176 27.3674 7.92 26.6634 7.92C25.9754 7.92 25.3674 8.176 24.8394 8.688C24.3274 9.2 24.0714 10.008 24.0714 11.112C24.0714 12.152 24.3114 12.944 24.7914 13.488C25.2714 14.032 25.8394 14.304 26.4954 14.304C27.3114 14.304 27.9514 13.96 28.4154 13.272C28.8954 12.584 29.1354 11.84 29.1354 11.04Z" fill="currentColor"></path><path d="M47.9589 16.512H41.9829V14.184H43.4229V10.416C43.4229 9.488 43.2629 8.824 42.9429 8.424C42.6389 8.024 42.1829 7.824 41.5749 7.824C40.8389 7.824 40.2709 8.056 39.8709 8.52C39.4709 8.968 39.2629 9.56 39.2469 10.296V14.184H40.6869V16.512H34.7109V14.184H36.1509V8.04H34.5909V5.688H39.2469V7.344C39.9669 6.096 41.1269 5.472 42.7269 5.472C43.7509 5.472 44.6389 5.776 45.3909 6.384C46.1429 6.992 46.5189 7.936 46.5189 9.216V14.184H47.9589V16.512Z" fill="currentColor"></path></svg></a><p>Your blueprint for a better internet.</p><ul class="social-icons"><li><a href="https://mozilla.social/@mdn" target="_blank" rel="me noopener noreferrer"><span class="icon icon-mastodon"></span><span class="visually-hidden">MDN on Mastodon</span></a></li><li><a href="https://twitter.com/mozdevnet" target="_blank" rel="noopener noreferrer"><span class="icon icon-twitter-x"></span><span class="visually-hidden">MDN on X (formerly Twitter)</span></a></li><li><a href="https://github.com/mdn/" target="_blank" rel="noopener noreferrer"><span class="icon icon-github-mark-small"></span><span class="visually-hidden">MDN on GitHub</span></a></li><li><a href="/en-US/blog/rss.xml" target="_blank"><span class="icon icon-feed"></span><span class="visually-hidden">MDN Blog RSS Feed</span></a></li></ul></div><div class="page-footer-nav-col-1"><h2 class="footer-nav-heading">MDN</h2><ul class="footer-nav-list"><li class="footer-nav-item"><a href="/en-US/about">About</a></li><li class="footer-nav-item"><a href="/en-US/blog/">Blog</a></li><li class="footer-nav-item"><a href="https://www.mozilla.org/en-US/careers/listings/?team=ProdOps" target="_blank" rel="noopener noreferrer">Careers</a></li><li class="footer-nav-item"><a href="/en-US/advertising">Advertise with us</a></li></ul></div><div class="page-footer-nav-col-2"><h2 class="footer-nav-heading">Support</h2><ul class="footer-nav-list"><li class="footer-nav-item"><a class="footer-nav-link" href="https://support.mozilla.org/products/mdn-plus">Product help</a></li><li class="footer-nav-item"><a class="footer-nav-link" href="/en-US/docs/MDN/Community/Issues">Report an issue</a></li></ul></div><div class="page-footer-nav-col-3"><h2 class="footer-nav-heading">Our communities</h2><ul class="footer-nav-list"><li class="footer-nav-item"><a class="footer-nav-link" href="/en-US/community">MDN Community</a></li><li class="footer-nav-item"><a class="footer-nav-link" href="https://discourse.mozilla.org/c/mdn/236" target="_blank" rel="noopener noreferrer">MDN Forum</a></li><li class="footer-nav-item"><a class="footer-nav-link" href="/discord" target="_blank" rel="noopener noreferrer">MDN Chat</a></li></ul></div><div class="page-footer-nav-col-4"><h2 class="footer-nav-heading">Developers</h2><ul class="footer-nav-list"><li class="footer-nav-item"><a class="footer-nav-link" href="/en-US/docs/Web">Web Technologies</a></li><li class="footer-nav-item"><a class="footer-nav-link" href="/en-US/docs/Learn">Learn Web Development</a></li><li class="footer-nav-item"><a class="footer-nav-link" href="/en-US/plus">MDN Plus</a></li><li class="footer-nav-item"><a href="https://hacks.mozilla.org/" target="_blank" rel="noopener noreferrer">Hacks Blog</a></li></ul></div><div class="page-footer-moz"><a href="https://www.mozilla.org/" class="footer-moz-logo-link" target="_blank" rel="noopener noreferrer"><svg width="112" height="32" fill="none" xmlns="http://www.w3.org/2000/svg"><title id="mozilla-footer-logo-svg">Mozilla logo</title><path d="M41.753 14.218c-2.048 0-3.324 1.522-3.324 4.157 0 2.423 1.119 4.286 3.29 4.286 2.082 0 3.447-1.678 3.447-4.347 0-2.826-1.522-4.096-3.413-4.096Zm54.89 7.044c0 .901.437 1.618 1.645 1.618 1.427 0 2.949-1.024 3.044-3.352-.649-.095-1.365-.185-2.02-.185-1.426-.005-2.668.397-2.668 1.92Z" fill="currentColor"></path><path d="M0 0v32h111.908V0H0Zm32.56 25.426h-5.87v-7.884c0-2.423-.806-3.352-2.39-3.352-1.924 0-2.702 1.365-2.702 3.324v4.868h1.864v3.044h-5.864v-7.884c0-2.423-.806-3.352-2.39-3.352-1.924 0-2.702 1.365-2.702 3.324v4.868h2.669v3.044H6.642v-3.044h1.863v-7.918H6.642V11.42h5.864v2.11c.839-1.489 2.3-2.39 4.252-2.39 2.02 0 3.878.963 4.566 3.01.778-1.862 2.361-3.01 4.566-3.01 2.512 0 4.812 1.522 4.812 4.84v6.402h1.863v3.044h-.005Zm9.036.307c-4.314 0-7.296-2.635-7.296-7.106 0-4.096 2.484-7.481 7.514-7.481s7.481 3.38 7.481 7.29c0 4.472-3.228 7.297-7.699 7.297Zm22.578-.307H51.942l-.403-2.11 7.7-8.846h-4.376l-.621 2.17-2.888-.313.498-4.907h12.294l.313 2.11-7.767 8.852h4.533l.654-2.172 3.167.308-.872 4.908Zm7.99 0h-4.191v-5.03h4.19v5.03Zm0-8.976h-4.191v-5.03h4.19v5.03Zm2.618 8.976 6.054-21.358h3.945l-6.054 21.358h-3.945Zm8.136 0 6.048-21.358h3.945l-6.054 21.358h-3.939Zm21.486.307c-1.863 0-2.887-1.085-3.072-2.792-.805 1.427-2.232 2.792-4.498 2.792-2.02 0-4.314-1.085-4.314-4.006 0-3.447 3.323-4.253 6.518-4.253.778 0 1.584.034 2.3.124v-.465c0-1.427-.034-3.133-2.3-3.133-.84 0-1.488.061-2.143.402l-.453 1.578-3.195-.34.549-3.224c2.45-.996 3.692-1.27 5.992-1.27 3.01 0 5.556 1.55 5.556 4.75v6.083c0 .805.314 1.085.963 1.085.184 0 .375-.034.587-.095l.034 2.11a5.432 5.432 0 0 1-2.524.654Z" fill="currentColor"></path></svg></a><ul class="footer-moz-list"><li class="footer-moz-item"><a href="https://www.mozilla.org/privacy/websites/" class="footer-moz-link" target="_blank" rel="noopener noreferrer">Website Privacy Notice</a></li><li class="footer-moz-item"><a href="https://www.mozilla.org/privacy/websites/#cookies" class="footer-moz-link" target="_blank" rel="noopener noreferrer">Cookies</a></li><li class="footer-moz-item"><a href="https://www.mozilla.org/about/legal/terms/mozilla" class="footer-moz-link" target="_blank" rel="noopener noreferrer">Legal</a></li><li class="footer-moz-item"><a href="https://www.mozilla.org/about/governance/policies/participation/" class="footer-moz-link" target="_blank" rel="noopener noreferrer">Community Participation Guidelines</a></li></ul></div><div class="page-footer-legal"><p id="license" class="page-footer-legal-text">Visit<!-- --> <a href="https://www.mozilla.org" target="_blank" rel="noopener noreferrer">Mozilla Corporation’s</a> <!-- -->not-for-profit parent, the<!-- --> <a target="_blank" rel="noopener noreferrer" href="https://foundation.mozilla.org/">Mozilla Foundation</a>.<br/>Portions of this content are ©1998–<!-- -->2024<!-- --> by individual mozilla.org contributors. Content available under<!-- --> <a href="/en-US/docs/MDN/Writing_guidelines/Attrib_copyright_license">a Creative Commons license</a>.</p></div></div></footer></div><script type="application/json" id="hydration">{"url":"/en-US/docs/Learn/Accessibility/WAI-ARIA_basics","doc":{"isMarkdown":true,"isTranslated":false,"isActive":true,"flaws":{},"title":"WAI-ARIA basics","mdn_url":"/en-US/docs/Learn/Accessibility/WAI-ARIA_basics","locale":"en-US","native":"English (US)","sidebarHTML":"<ol><li class=\"section\"><a href=\"/en-US/docs/Learn/Getting_started_with_the_web\">Complete beginners start here!</a></li><li><details><summary>Getting started with the web</summary><ol><li><a href=\"/en-US/docs/Learn/Getting_started_with_the_web\">Getting started with the web</a></li><li><a href=\"/en-US/docs/Learn/Getting_started_with_the_web/Installing_basic_software\">Installing basic software</a></li><li><a href=\"/en-US/docs/Learn/Getting_started_with_the_web/What_will_your_website_look_like\">What will your website look like?</a></li><li><a href=\"/en-US/docs/Learn/Getting_started_with_the_web/Dealing_with_files\">Dealing with files</a></li><li><a href=\"/en-US/docs/Learn/Getting_started_with_the_web/HTML_basics\">HTML basics</a></li><li><a href=\"/en-US/docs/Learn/Getting_started_with_the_web/CSS_basics\">CSS basics</a></li><li><a href=\"/en-US/docs/Learn/Getting_started_with_the_web/JavaScript_basics\">JavaScript basics</a></li><li><a href=\"/en-US/docs/Learn/Getting_started_with_the_web/Publishing_your_website\">Publishing your website</a></li><li><a href=\"/en-US/docs/Learn/Getting_started_with_the_web/How_the_Web_works\">How the web works</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/HTML\">HTML — Structuring the web</a></li><li><details><summary>Introduction to HTML</summary><ol><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML\">Introduction to HTML</a></li><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML/Getting_started\">Getting started with HTML</a></li><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML/The_head_metadata_in_HTML\">What's in the head? Metadata in HTML</a></li><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML/HTML_text_fundamentals\">HTML text fundamentals</a></li><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML/Creating_hyperlinks\">Creating hyperlinks</a></li><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML/Advanced_text_formatting\">Advanced text formatting</a></li><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML/Document_and_website_structure\">Document and website structure</a></li><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML/Debugging_HTML\">Debugging HTML</a></li><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML/Marking_up_a_letter\">Marking up a letter</a></li><li><a href=\"/en-US/docs/Learn/HTML/Introduction_to_HTML/Structuring_a_page_of_content\">Structuring a page of content</a></li></ol></details></li><li><details><summary>Multimedia and embedding</summary><ol><li><a href=\"/en-US/docs/Learn/HTML/Multimedia_and_embedding\">Multimedia and embedding</a></li><li><a href=\"/en-US/docs/Learn/HTML/Multimedia_and_embedding/Images_in_HTML\">Images in HTML</a></li><li><a href=\"/en-US/docs/Learn/HTML/Multimedia_and_embedding/Video_and_audio_content\">Video and audio content</a></li><li><a href=\"/en-US/docs/Learn/HTML/Multimedia_and_embedding/Other_embedding_technologies\">From object to iframe — other embedding technologies</a></li><li><a href=\"/en-US/docs/Learn/HTML/Multimedia_and_embedding/Adding_vector_graphics_to_the_Web\">Adding vector graphics to the web</a></li><li><a href=\"/en-US/docs/Learn/HTML/Multimedia_and_embedding/Responsive_images\">Responsive images</a></li><li><a href=\"/en-US/docs/Learn/HTML/Multimedia_and_embedding/Mozilla_splash_page\">Mozilla splash page</a></li></ol></details></li><li><details><summary>HTML tables</summary><ol><li><a href=\"/en-US/docs/Learn/HTML/Tables\">HTML tables</a></li><li><a href=\"/en-US/docs/Learn/HTML/Tables/Basics\">HTML table basics</a></li><li><a href=\"/en-US/docs/Learn/HTML/Tables/Advanced\">HTML table advanced features and accessibility</a></li><li><a href=\"/en-US/docs/Learn/HTML/Tables/Structuring_planet_data\">Structuring planet data</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/CSS\">CSS — Styling the web</a></li><li><details><summary>CSS first steps</summary><ol><li><a href=\"/en-US/docs/Learn/CSS/First_steps\">CSS first steps</a></li><li><a href=\"/en-US/docs/Learn/CSS/First_steps/What_is_CSS\">What is CSS?</a></li><li><a href=\"/en-US/docs/Learn/CSS/First_steps/Getting_started\">Getting started with CSS</a></li><li><a href=\"/en-US/docs/Learn/CSS/First_steps/How_CSS_is_structured\">How CSS is structured</a></li><li><a href=\"/en-US/docs/Learn/CSS/First_steps/How_CSS_works\">How CSS works</a></li><li><a href=\"/en-US/docs/Learn/CSS/First_steps/Styling_a_biography_page\">Styling a biography page</a></li></ol></details></li><li><details><summary>CSS building blocks</summary><ol><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks\">CSS building blocks</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Selectors\">CSS selectors</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Selectors/Type_Class_and_ID_Selectors\">Type, class, and ID selectors</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Selectors/Attribute_selectors\">Attribute selectors</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Selectors/Pseudo-classes_and_pseudo-elements\">Pseudo-classes and pseudo-elements</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Selectors/Combinators\">Combinators</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Cascade_and_inheritance\">Cascade, specificity, and inheritance</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Cascade_layers\">Cascade layers</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/The_box_model\">The box model</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Backgrounds_and_borders\">Backgrounds and borders</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Handling_different_text_directions\">Handling different text directions</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Overflowing_content\">Overflowing content</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Values_and_units\">CSS values and units</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Sizing_items_in_CSS\">Sizing items in CSS</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Images_media_form_elements\">Images, media, and form elements</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Styling_tables\">Styling tables</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Advanced_styling_effects\">Advanced styling effects</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Debugging_CSS\">Debugging CSS</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Organizing\">Organizing your CSS</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Fundamental_CSS_comprehension\">Fundamental CSS comprehension</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/Creating_fancy_letterheaded_paper\">Creating fancy letterheaded paper</a></li><li><a href=\"/en-US/docs/Learn/CSS/Building_blocks/A_cool_looking_box\">A cool-looking box</a></li></ol></details></li><li><details><summary>Styling text</summary><ol><li><a href=\"/en-US/docs/Learn/CSS/Styling_text\">CSS styling text</a></li><li><a href=\"/en-US/docs/Learn/CSS/Styling_text/Fundamentals\">Fundamental text and font styling</a></li><li><a href=\"/en-US/docs/Learn/CSS/Styling_text/Styling_lists\">Styling lists</a></li><li><a href=\"/en-US/docs/Learn/CSS/Styling_text/Styling_links\">Styling links</a></li><li><a href=\"/en-US/docs/Learn/CSS/Styling_text/Web_fonts\">Web fonts</a></li><li><a href=\"/en-US/docs/Learn/CSS/Styling_text/Typesetting_a_homepage\">Typesetting a community school homepage</a></li></ol></details></li><li><details><summary>CSS layout</summary><ol><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout\">CSS layout</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Introduction\">Introduction to CSS layout</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Normal_Flow\">Normal Flow</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Flexbox\">Flexbox</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Grids\">Grids</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Floats\">Floats</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Positioning\">Positioning</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Multiple-column_Layout\">Multiple-column layout</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Responsive_Design\">Responsive design</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Media_queries\">Beginner's guide to media queries</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Legacy_Layout_Methods\">Legacy layout methods</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Supporting_Older_Browsers\">Supporting older browsers</a></li><li><a href=\"/en-US/docs/Learn/CSS/CSS_layout/Fundamental_Layout_Comprehension\">Fundamental layout comprehension</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/JavaScript\">JavaScript — Dynamic client-side scripting</a></li><li><details><summary>JavaScript first steps</summary><ol><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps\">JavaScript first steps</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps/What_is_JavaScript\">What is JavaScript?</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps/A_first_splash\">A first splash into JavaScript</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps/What_went_wrong\">What went wrong? Troubleshooting JavaScript</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps/Variables\">Storing the information you need — Variables</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps/Math\">Basic math in JavaScript — numbers and operators</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps/Strings\">Handling text — strings in JavaScript</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps/Useful_string_methods\">Useful string methods</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps/Arrays\">Arrays</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/First_steps/Silly_story_generator\">Silly story generator</a></li></ol></details></li><li><details><summary>JavaScript building blocks</summary><ol><li><a href=\"/en-US/docs/Learn/JavaScript/Building_blocks\">JavaScript building blocks</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Building_blocks/conditionals\">Making decisions in your code — conditionals</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Building_blocks/Looping_code\">Looping code</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Building_blocks/Functions\">Functions — reusable blocks of code</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Building_blocks/Build_your_own_function\">Build your own function</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Building_blocks/Return_values\">Function return values</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Building_blocks/Events\">Introduction to events</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Building_blocks/Event_bubbling\">Event bubbling</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Building_blocks/Image_gallery\">Image gallery</a></li></ol></details></li><li><details><summary>Introducing JavaScript objects</summary><ol><li><a href=\"/en-US/docs/Learn/JavaScript/Objects\">Introducing JavaScript objects</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Objects/Basics\">JavaScript object basics</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Objects/Object_prototypes\">Object prototypes</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Objects/Object-oriented_programming\">Object-oriented programming</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Objects/Classes_in_JavaScript\">Classes in JavaScript</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Objects/JSON\">Working with JSON</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Objects/Object_building_practice\">Object building practice</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Objects/Adding_bouncing_balls_features\">Adding features to our bouncing balls demo</a></li></ol></details></li><li><details><summary>Asynchronous JavaScript</summary><ol><li><a href=\"/en-US/docs/Learn/JavaScript/Asynchronous\">Asynchronous JavaScript</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Asynchronous/Introducing\">Introducing asynchronous JavaScript</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Asynchronous/Promises\">How to use promises</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Asynchronous/Implementing_a_promise-based_API\">How to implement a promise-based API</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Asynchronous/Introducing_workers\">Introducing workers</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Asynchronous/Sequencing_animations\">Sequencing animations</a></li></ol></details></li><li><details><summary>Client-side web APIs</summary><ol><li><a href=\"/en-US/docs/Learn/JavaScript/Client-side_web_APIs\">Client-side web APIs</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Introduction\">Introduction to web APIs</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Manipulating_documents\">Manipulating documents</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Fetching_data\">Fetching data from the server</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Third_party_APIs\">Third-party APIs</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Drawing_graphics\">Drawing graphics</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Video_and_audio_APIs\">Video and Audio APIs</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Client-side_storage\">Client-side storage</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/Forms\">Web forms — Working with user data</a></li><li><details><summary>Web form building blocks</summary><ol><li><a href=\"/en-US/docs/Learn/Forms\">Web form building blocks</a></li><li><a href=\"/en-US/docs/Learn/Forms/Your_first_form\">Your first form</a></li><li><a href=\"/en-US/docs/Learn/Forms/How_to_structure_a_web_form\">How to structure a web form</a></li><li><a href=\"/en-US/docs/Learn/Forms/Basic_native_form_controls\">Basic native form controls</a></li><li><a href=\"/en-US/docs/Learn/Forms/HTML5_input_types\">The HTML5 input types</a></li><li><a href=\"/en-US/docs/Learn/Forms/Other_form_controls\">Other form controls</a></li><li><a href=\"/en-US/docs/Learn/Forms/Styling_web_forms\">Styling web forms</a></li><li><a href=\"/en-US/docs/Learn/Forms/Advanced_form_styling\">Advanced form styling</a></li><li><a href=\"/en-US/docs/Learn/Forms/UI_pseudo-classes\">UI pseudo-classes</a></li><li><a href=\"/en-US/docs/Learn/Forms/Form_validation\">Client-side form validation</a></li><li><a href=\"/en-US/docs/Learn/Forms/Sending_and_retrieving_form_data\">Sending form data</a></li></ol></details></li><li><details><summary>Advanced web form techniques</summary><ol><li><a href=\"/en-US/docs/Learn/Forms/How_to_build_custom_form_controls\">How to build custom form controls</a></li><li><a href=\"/en-US/docs/Learn/Forms/Sending_forms_through_JavaScript\">Sending forms through JavaScript</a></li><li><a href=\"/en-US/docs/Learn/Forms/Property_compatibility_table_for_form_controls\">CSS property compatibility table for form controls</a></li><li><a href=\"/en-US/docs/Learn/Forms/HTML_forms_in_legacy_browsers\">HTML forms in legacy browsers</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/Accessibility\">Accessibility — Make the web usable by everyone</a></li><li><details open=\"\"><summary>Accessibility guides</summary><ol><li><a href=\"/en-US/docs/Learn/Accessibility\">Accessibility</a></li><li><a href=\"/en-US/docs/Learn/Accessibility/What_is_accessibility\">What is accessibility?</a></li><li><a href=\"/en-US/docs/Learn/Accessibility/HTML\">HTML: A good basis for accessibility</a></li><li><a href=\"/en-US/docs/Learn/Accessibility/CSS_and_JavaScript\">CSS and JavaScript accessibility best practices</a></li><li><em><a href=\"/en-US/docs/Learn/Accessibility/WAI-ARIA_basics\" aria-current=\"page\">WAI-ARIA basics</a></em></li><li><a href=\"/en-US/docs/Learn/Accessibility/Multimedia\">Accessible multimedia</a></li><li><a href=\"/en-US/docs/Learn/Accessibility/Mobile\">Mobile accessibility</a></li><li><a href=\"/en-US/docs/Learn/Accessibility/Accessibility_troubleshooting\">Assessment: Accessibility troubleshooting</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/Performance\">Performance — Making websites fast and responsive</a></li><li><details><summary>Performance guides</summary><ol><li><a href=\"/en-US/docs/Learn/Performance\">Web performance</a></li><li><a href=\"/en-US/docs/Learn/Performance/why_web_performance\">The \"why\" of web performance</a></li><li><a href=\"/en-US/docs/Learn/Performance/What_is_web_performance\">What is web performance?</a></li><li><a href=\"/en-US/docs/Learn/Performance/Perceived_performance\">Perceived performance</a></li><li><a href=\"/en-US/docs/Learn/Performance/Measuring_performance\">Measuring performance</a></li><li><a href=\"/en-US/docs/Learn/Performance/Multimedia\">Multimedia: Images</a></li><li><a href=\"/en-US/docs/Learn/Performance/video\">Multimedia: video</a></li><li><a href=\"/en-US/docs/Learn/Performance/JavaScript\">JavaScript performance optimization</a></li><li><a href=\"/en-US/docs/Learn/Performance/HTML\">HTML performance optimization</a></li><li><a href=\"/en-US/docs/Learn/Performance/CSS\">CSS performance optimization</a></li><li><a href=\"/en-US/docs/Learn/Performance/business_case_for_performance\">The business case for web performance</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/MathML\">MathML — Writing mathematics with MathML</a></li><li><details><summary>MathML first steps</summary><ol><li><a href=\"/en-US/docs/Learn/MathML/First_steps\">MathML first steps</a></li><li><a href=\"/en-US/docs/Learn/MathML/First_steps/Getting_started\">Getting started with MathML</a></li><li><a href=\"/en-US/docs/Learn/MathML/First_steps/Text_containers\">MathML Text Containers</a></li><li><a href=\"/en-US/docs/Learn/MathML/First_steps/Fractions_and_roots\">MathML fractions and roots</a></li><li><a href=\"/en-US/docs/Learn/MathML/First_steps/Scripts\">MathML scripted elements</a></li><li><a href=\"/en-US/docs/Learn/MathML/First_steps/Tables\">MathML tables</a></li><li><a href=\"/en-US/docs/Learn/MathML/First_steps/Three_famous_mathematical_formulas\">Three famous mathematical formulas</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/../Games\">Games — Developing games for the web</a></li><li><details><summary>Guides and tutorials</summary><ol><li><a href=\"/en-US/docs/Games/Introduction\">Introduction to game development for the Web</a></li><li><a href=\"/en-US/docs/Games/Techniques\">Techniques for game development</a></li><li><a href=\"/en-US/docs/Games/Tutorials\">Tutorials</a></li><li><a href=\"/en-US/docs/Games/Publishing_games\">Publishing games</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/Tools_and_testing\">Tools and testing</a></li><li><details><summary>Client-side web development tools</summary><ol><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools\">Understanding client-side web development tools</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Overview\">Client-side tooling overview</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Command_line\">Command line crash course</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Package_management\">Package management basics</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Introducing_complete_toolchain\">Introducing a complete toolchain</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Understanding_client-side_tools/Deployment\">Deploying our app</a></li></ol></details></li><li><details><summary>Introduction to client-side frameworks</summary><ol><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Introduction\">Introduction to client-side frameworks</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Main_features\">Framework main features</a></li></ol></details></li><li><details><summary>React</summary><ol><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_getting_started\">Getting started with React</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_todo_list_beginning\">Beginning our React todo list</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_components\">Componentizing our React app</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_interactivity_events_state\">React interactivity: Events and state</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_interactivity_filtering_conditional_rendering\">React interactivity: Editing, filtering, conditional rendering</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_accessibility\">Accessibility in React</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/React_resources\">React resources</a></li></ol></details></li><li><details><summary>Ember</summary><ol><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_getting_started\">Getting started with Ember</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_structure_componentization\">Ember app structure and componentization</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_interactivity_events_state\">Ember interactivity: Events, classes and state</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_conditional_footer\">Ember Interactivity: Footer functionality, conditional rendering</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_routing\">Routing in Ember</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Ember_resources\">Ember resources and troubleshooting</a></li></ol></details></li><li><details><summary>Vue</summary><ol><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_getting_started\">Getting started with Vue</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_first_component\">Creating our first Vue component</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_rendering_lists\">Rendering a list of Vue components</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_methods_events_models\">Adding a new todo form: Vue events, methods, and models</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_styling\">Styling Vue components with CSS</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_computed_properties\">Using Vue computed properties</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_conditional_rendering\">Vue conditional rendering: editing existing todos</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_refs_focus_management\">Vue refs and lifecycle methods for focus management</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Vue_resources\">Vue resources</a></li></ol></details></li><li><details><summary>Svelte</summary><ol><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_getting_started\">Getting started with Svelte</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_Todo_list_beginning\">Starting our Svelte to-do list app</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_variables_props\">Dynamic behavior in Svelte: working with variables and props</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_components\">Componentizing our Svelte app</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_reactivity_lifecycle_accessibility\">Advanced Svelte: Reactivity, lifecycle, accessibility</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_stores\">Working with Svelte stores</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_TypeScript\">TypeScript support in Svelte</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Svelte_deployment_next\">Deployment and next steps</a></li></ol></details></li><li><details><summary>Angular</summary><ol><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_getting_started\">Getting started with Angular</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_todo_list_beginning\">Beginning our Angular todo list app</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_styling\">Styling our Angular app</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_item_component\">Creating an item component</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_filtering\">Filtering our to-do items</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Client-side_JavaScript_frameworks/Angular_building\">Building Angular applications and further resources</a></li></ol></details></li><li><details><summary>Git and GitHub</summary><ol><li><a href=\"/en-US/docs/Learn/Tools_and_testing/GitHub\">Git and GitHub</a></li></ol></details></li><li><details><summary>Cross browser testing</summary><ol><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing\">Cross browser testing</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Introduction\">Introduction to cross-browser testing</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Testing_strategies\">Strategies for carrying out testing</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/HTML_and_CSS\">Handling common HTML and CSS problems</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/JavaScript\">Handling common JavaScript problems</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Accessibility\">Handling common accessibility problems</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Feature_detection\">Implementing feature detection</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Automated_testing\">Introduction to automated testing</a></li><li><a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Your_own_automation_environment\">Setting up your own test automation environment</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/Server-side\">Server-side website programming</a></li><li><details><summary>First steps</summary><ol><li><a href=\"/en-US/docs/Learn/Server-side/First_steps\">Server-side website programming first steps</a></li><li><a href=\"/en-US/docs/Learn/Server-side/First_steps/Introduction\">Introduction to the server side</a></li><li><a href=\"/en-US/docs/Learn/Server-side/First_steps/Client-Server_overview\">Client-Server Overview</a></li><li><a href=\"/en-US/docs/Learn/Server-side/First_steps/Web_frameworks\">Server-side web frameworks</a></li><li><a href=\"/en-US/docs/Learn/Server-side/First_steps/Website_security\">Website security</a></li></ol></details></li><li><details><summary>Django web framework (Python)</summary><ol><li><a href=\"/en-US/docs/Learn/Server-side/Django\">Django Web Framework (Python)</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Introduction\">Django introduction</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/development_environment\">Setting up a Django development environment</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Tutorial_local_library_website\">Django Tutorial: The Local Library website</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/skeleton_website\">Django Tutorial Part 2: Creating a skeleton website</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Models\">Django Tutorial Part 3: Using models</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Admin_site\">Django Tutorial Part 4: Django admin site</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Home_page\">Django Tutorial Part 5: Creating our home page</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Generic_views\">Django Tutorial Part 6: Generic list and detail views</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Sessions\">Django Tutorial Part 7: Sessions framework</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Authentication\">Django Tutorial Part 8: User authentication and permissions</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Forms\">Django Tutorial Part 9: Working with forms</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Testing\">Django Tutorial Part 10: Testing a Django web application</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/Deployment\">Django Tutorial Part 11: Deploying Django to production</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/web_application_security\">Django web application security</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Django/django_assessment_blog\">Assessment: DIY Django mini blog</a></li></ol></details></li><li><details><summary>Express Web Framework (Node.js/JavaScript)</summary><ol><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs\">Express web framework (Node.js/JavaScript)</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs/Introduction\">Express/Node introduction</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs/development_environment\">Setting up a Node development environment</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs/Tutorial_local_library_website\">Express Tutorial: The Local Library website</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs/skeleton_website\">Express Tutorial Part 2: Creating a skeleton website</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs/mongoose\">Express Tutorial Part 3: Using a Database (with Mongoose)</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs/routes\">Express Tutorial Part 4: Routes and controllers</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs/Displaying_data\">Express Tutorial Part 5: Displaying library data</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs/forms\">Express Tutorial Part 6: Working with forms</a></li><li><a href=\"/en-US/docs/Learn/Server-side/Express_Nodejs/deployment\">Express Tutorial Part 7: Deploying to production</a></li></ol></details></li><li class=\"section\"><a href=\"/en-US/docs/Learn/Common_questions\">Further resources</a></li><li><details><summary>Common questions</summary><ol><li><a href=\"/en-US/docs/Learn/Common_questions\">Common questions</a></li><li><a href=\"/en-US/docs/Learn/HTML/Howto\">Use HTML to solve common problems</a></li><li><a href=\"/en-US/docs/Learn/CSS/Howto\">Use CSS to solve common problems</a></li><li><a href=\"/en-US/docs/Learn/JavaScript/Howto\">Solve common problems in your JavaScript code</a></li><li><a href=\"/en-US/docs/Learn/Common_questions/Web_mechanics\">Web mechanics</a></li><li><a href=\"/en-US/docs/Learn/Common_questions/Tools_and_setup\">Tools and setup</a></li><li><a href=\"/en-US/docs/Learn/Common_questions/Design_and_accessibility\">Design and accessibility</a></li></ol></details></li></ol>","sidebarMacro":"LearnSidebar","body":[{"type":"prose","value":{"id":null,"title":null,"isH3":false,"content":"<ul class=\"prev-next\">\n <li><a class=\"button secondary\" href=\"/en-US/docs/Learn/Accessibility/CSS_and_JavaScript\"><span class=\"button-wrap\"> Previous </span></a></li>\n <li><a class=\"button secondary\" href=\"/en-US/docs/Learn/Accessibility\"><span class=\"button-wrap\"> Overview: Accessibility</span></a></li>\n <li><a class=\"button secondary\" href=\"/en-US/docs/Learn/Accessibility/Multimedia\"><span class=\"button-wrap\"> Next </span></a></li>\n</ul>\n<p>Following on from the previous article, sometimes making complex UI controls that involve unsemantic HTML and dynamic JavaScript-updated content can be difficult. WAI-ARIA is a technology that can help with such problems by adding in further semantics that browsers and assistive technologies can recognize and use to let users know what is going on. Here we'll show how to use it at a basic level to improve accessibility.</p>\n<figure class=\"table-container\"><table>\n <tbody>\n <tr>\n <th scope=\"row\">Prerequisites:</th>\n <td>\n A basic understanding of HTML, CSS, and\n JavaScript. An understanding of the\n <a href=\"/en-US/docs/Learn/Accessibility\">previous articles in the course</a>.\n </td>\n </tr>\n <tr>\n <th scope=\"row\">Objective:</th>\n <td>\n To gain familiarity with WAI-ARIA, and how it can be used to provide\n useful additional semantics to enhance accessibility where required.\n </td>\n </tr>\n </tbody>\n</table></figure>"}},{"type":"prose","value":{"id":"what_is_wai-aria","title":"What is WAI-ARIA?","isH3":false,"content":"<p>Let's start by looking at what WAI-ARIA is, and what it can do for us.</p>"}},{"type":"prose","value":{"id":"a_whole_new_set_of_problems","title":"A whole new set of problems","isH3":true,"content":"<p>As web apps started to get more complex and dynamic, a new set of accessibility features and problems started to appear.</p>\n<p>For example, HTML introduced a number of semantic elements to define common page features (<a href=\"/en-US/docs/Web/HTML/Element/nav\"><code>&lt;nav&gt;</code></a>, <a href=\"/en-US/docs/Web/HTML/Element/footer\"><code>&lt;footer&gt;</code></a>, etc.). Before these were available, developers would use <a href=\"/en-US/docs/Web/HTML/Element/div\"><code>&lt;div&gt;</code></a>s with IDs or classes, e.g. <code>&lt;div class=\"nav\"&gt;</code>, but these were problematic, as there was no easy way to easily find a specific page feature such as the main navigation programmatically.</p>\n<p>The initial solution was to add one or more hidden links at the top of the page to link to the navigation (or whatever else), for example:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;a href=\"#hidden\" class=\"hidden\"&gt;Skip to navigation&lt;/a&gt;\n</code></pre></div>\n<p>But this is still not very precise, and can only be used when the screen reader is reading from the top of the page.</p>\n<p>As another example, apps started to feature complex controls like date pickers for choosing dates, sliders for choosing values, etc. HTML provides special input types to render such controls:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;input type=\"date\" /&gt; &lt;input type=\"range\" /&gt;\n</code></pre></div>\n<p>These were originally not well-supported and it was, and still is to a lesser extent, difficult to style them, leading designers and developers to opt for custom solutions. Instead of using these native features, some developers rely on JavaScript libraries that generate such controls as a series of nested <a href=\"/en-US/docs/Web/HTML/Element/div\"><code>&lt;div&gt;</code></a>s which are then styled using CSS and controlled using JavaScript.</p>\n<p>The problem here is that visually they work, but screen readers can't make any sense of what they are at all, and their users just get told that they can see a jumble of elements with no semantics to describe what they mean.</p>"}},{"type":"prose","value":{"id":"enter_wai-aria","title":"Enter WAI-ARIA","isH3":true,"content":"<p><a href=\"https://www.w3.org/TR/wai-aria/\" class=\"external\" target=\"_blank\">WAI-ARIA</a> (Web Accessibility Initiative - Accessible Rich Internet Applications) is a specification written by the W3C, defining a set of additional HTML attributes that can be applied to elements to provide additional semantics and improve accessibility wherever it is lacking. There are three main features defined in the spec:</p>\n<dl>\n <dt id=\"roles\"><a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles\">Roles</a></dt>\n <dd>\n <p>These define what an element is or does. Many of these are so-called landmark roles, which largely duplicate the semantic value of structural elements, such as <code>role=\"navigation\"</code> (<a href=\"/en-US/docs/Web/HTML/Element/nav\"><code>&lt;nav&gt;</code></a>) or <code>role=\"complementary\"</code> (<a href=\"/en-US/docs/Web/HTML/Element/aside\"><code>&lt;aside&gt;</code></a>). Some other roles describe different page structures, such as <code>role=\"banner\"</code>, <code>role=\"search\"</code>, <code>role=\"tablist\"</code>, and <code>role=\"tabpanel\"</code>, which are commonly found in UIs.</p>\n </dd>\n <dt id=\"properties\"><a href=\"#properties\">Properties</a></dt>\n <dd>\n <p>These define properties of elements, which can be used to give them extra meaning or semantics. As an example, <code>aria-required=\"true\"</code> specifies that a form input needs to be filled in order to be valid, whereas <code>aria-labelledby=\"label\"</code> allows you to put an ID on an element, then reference it as being the label for anything else on the page, including multiple elements, which is not possible using <code>&lt;label for=\"input\"&gt;</code>. As an example, you could use <code>aria-labelledby</code> to specify that a key description contained in a <a href=\"/en-US/docs/Web/HTML/Element/div\"><code>&lt;div&gt;</code></a> is the label for multiple table cells, or you could use it as an alternative to image alt text — specify existing information on the page as an image's alt text, rather than having to repeat it inside the <code>alt</code> attribute. You can see an example of this at <a href=\"/en-US/docs/Learn/Accessibility/HTML#text_alternatives\">Text alternatives</a>.</p>\n </dd>\n <dt id=\"states\"><a href=\"#states\">States</a></dt>\n <dd>\n <p>Special properties that define the current conditions of elements, such as <code>aria-disabled=\"true\"</code>, which specifies to a screen reader that a form input is currently disabled. States differ from properties in that properties don't change throughout the lifecycle of an app, whereas states can change, generally programmatically via JavaScript.</p>\n </dd>\n</dl>\n<p>An important point about WAI-ARIA attributes is that they don't affect anything about the web page, except for the information exposed by the browser's accessibility APIs (where screen readers get their information from). WAI-ARIA doesn't affect webpage structure, the DOM, etc., although the attributes can be useful for selecting elements by CSS.</p>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> You can find a useful list of all the ARIA roles and their uses, with links to further information, in the WAI-ARIA spec — see <a href=\"https://www.w3.org/TR/wai-aria-1.1/#role_definitions\" class=\"external\" target=\"_blank\">Definition of Roles</a> — on this site — see <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles\">ARIA roles</a>.</p>\n <p>The spec also contains a list of all the properties and states, with links to further information — see <a href=\"https://www.w3.org/TR/wai-aria-1.1/#state_prop_def\" class=\"external\" target=\"_blank\">Definitions of States and Properties (all <code>aria-*</code> attributes)</a>.</p>\n</div>"}},{"type":"prose","value":{"id":"where_is_wai-aria_supported","title":"Where is WAI-ARIA supported?","isH3":true,"content":"<p>This is not an easy question to answer. It is difficult to find a conclusive resource that states what features of WAI-ARIA are supported, and where, because:</p>\n<ol>\n <li>There are a lot of features in the WAI-ARIA spec.</li>\n <li>There are many combinations of operating systems, browsers, and screen readers to consider.</li>\n</ol>\n<p>This last point is key — To use a screen reader in the first place, your operating system needs to run browsers that have the necessary accessibility APIs in place to expose the information screen readers need to do their job. Most popular OSes have one or two browsers in place that screen readers can work with. The Paciello Group has a fairly up-to-date post that provides data for this — see <a href=\"https://www.tpgi.com/rough-guide-browsers-operating-systems-and-screen-reader-support-updated/\" class=\"external\" target=\"_blank\">Rough Guide: browsers, operating systems and screen reader support updated</a>.</p>\n<p>Next, you need to worry about whether the browsers in question support ARIA features and expose them via their APIs, but also whether screen readers recognize that information and present it to their users in a useful way.</p>\n<ol>\n <li>Browser support is almost universal.</li>\n <li>Screen reader support for ARIA features isn't quite at this level, but the most popular screen readers are getting there. You can get an idea of support levels by looking at Powermapper's <a href=\"https://www.powermapper.com/tests/screen-readers/aria/\" class=\"external\" target=\"_blank\">WAI-ARIA Screen reader compatibility</a> article.</li>\n</ol>\n<p>In this article, we won't attempt to cover every WAI-ARIA feature, and its exact support details. Instead, we will cover the most critical WAI-ARIA features for you to know about; if we don't mention any support details, you can assume that the feature is well-supported. We will clearly mention any exceptions to this.</p>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> Some JavaScript libraries support WAI-ARIA, meaning that when they generate UI features like complex form controls, they add ARIA attributes to improve the accessibility of those features. If you are looking for a 3rd party JavaScript solution for rapid UI development, you should definitely consider the accessibility of its UI widgets as an important factor when making your choice. Good examples are jQuery UI (see <a href=\"https://jqueryui.com/about/#deep-accessibility-support\" class=\"external\" target=\"_blank\">About jQuery UI: Deep accessibility support</a>), <a href=\"https://www.sencha.com/products/extjs/\" class=\"external\" target=\"_blank\">ExtJS</a>, and <a href=\"https://dojotoolkit.org/reference-guide/1.10/dijit/a11y/statement.html\" class=\"external\" target=\"_blank\">Dojo/Dijit</a>.</p>\n</div>"}},{"type":"prose","value":{"id":"when_should_you_use_wai-aria","title":"When should you use WAI-ARIA?","isH3":true,"content":"<p>We talked about some of the problems that prompted WAI-ARIA to be created earlier on, but essentially, there are four main areas that WAI-ARIA is useful in:</p>\n<dl>\n <dt id=\"signpostslandmarks\"><a href=\"#signpostslandmarks\">Signposts/Landmarks</a></dt>\n <dd>\n <p>ARIA's <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles\"><code>role</code></a> attribute values can act as landmarks that either replicate the semantics of HTML elements (e.g., <a href=\"/en-US/docs/Web/HTML/Element/nav\"><code>&lt;nav&gt;</code></a>), or go beyond HTML semantics to provide signposts to different functional areas, for example, <code>search</code>, <code>tablist</code>, <code>tab</code>, <code>listbox</code>, etc.</p>\n </dd>\n <dt id=\"dynamic_content_updates\"><a href=\"#dynamic_content_updates\">Dynamic content updates</a></dt>\n <dd>\n <p>Screen readers tend to have difficulty with reporting constantly changing content; with ARIA we can use <code>aria-live</code> to inform screen reader users when an area of content is updated dynamically: for example, by JavaScript in the page <a href=\"/en-US/docs/Learn/JavaScript/Client-side_web_APIs/Fetching_data\">fetching new content from the server and updating the DOM</a>.</p>\n </dd>\n <dt id=\"enhancing_keyboard_accessibility\"><a href=\"#enhancing_keyboard_accessibility\">Enhancing keyboard accessibility</a></dt>\n <dd>\n <p>There are built-in HTML elements that have native keyboard accessibility; when other elements are used along with JavaScript to simulate similar interactions, keyboard accessibility and screen reader reporting suffers as a result. Where this is unavoidable, WAI-ARIA provides a means to allow other elements to receive focus (using <code>tabindex</code>).</p>\n </dd>\n <dt id=\"accessibility_of_non-semantic_controls\"><a href=\"#accessibility_of_non-semantic_controls\">Accessibility of non-semantic controls</a></dt>\n <dd>\n <p>When a series of nested <code>&lt;div&gt;</code>s along with CSS/JavaScript is used to create a complex UI-feature, or a native control is greatly enhanced/changed via JavaScript, accessibility can suffer — screen reader users will find it difficult to work out what the feature does if there are no semantics or other clues. In these situations, ARIA can help to provide what's missing with a combination of roles like <code>button</code>, <code>listbox</code>, or <code>tablist</code>, and properties like <code>aria-required</code> or <code>aria-posinset</code> to provide further clues as to functionality.</p>\n </dd>\n</dl>\n<p>One thing to remember though — <strong>you should only use WAI-ARIA when you need to!</strong> Ideally, you should <em>always</em> use <a href=\"/en-US/docs/Learn/Accessibility/HTML\">native HTML features</a> to provide the semantics required by screen readers to tell their users what is going on. Sometimes this isn't possible, either because you have limited control over the code, or because you are creating something complex that doesn't have an easy HTML element to implement it. In such cases, WAI-ARIA can be a valuable accessibility enhancing tool.</p>\n<p>But again, only use it when necessary!</p>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> Also, try to make sure you test your site with a variety of <em>real</em> users — non-disabled people, people using screen readers, people using keyboard navigation, etc. They will have better insights than you about how well it works.</p>\n</div>"}},{"type":"prose","value":{"id":"practical_wai-aria_implementations","title":"Practical WAI-ARIA implementations","isH3":false,"content":"<p>In the next section, we'll look at the four areas in more detail, along with practical examples. Before you continue, you should get a screen reader testing setup put in place, so you can test some of the examples as you go through.</p>\n<p>See our section on <a href=\"/en-US/docs/Learn/Tools_and_testing/Cross_browser_testing/Accessibility#screen_readers\">testing screen readers</a> for more information.</p>"}},{"type":"prose","value":{"id":"signpostslandmarks_2","title":"Signposts/Landmarks","isH3":true,"content":"<p>WAI-ARIA adds the <a href=\"https://www.w3.org/TR/wai-aria-1.1/#role_definitions\" class=\"external\" target=\"_blank\"><code>role</code> attribute</a> to browsers, which allows you to add extra semantic value to elements on your site wherever they are needed. The first major area in which this is useful is providing information for screen readers so that their users can find common page elements. Let's look at an example — our <a href=\"https://github.com/mdn/learning-area/tree/main/accessibility/aria/website-no-roles\" class=\"external\" target=\"_blank\">website-no-roles</a> example (<a href=\"https://mdn.github.io/learning-area/accessibility/aria/website-no-roles/\" class=\"external\" target=\"_blank\">see it live</a>) has the following structure:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;header&gt;\n &lt;h1&gt;…&lt;/h1&gt;\n &lt;nav&gt;\n &lt;ul&gt;\n …\n &lt;/ul&gt;\n &lt;form&gt;\n &lt;!-- search form --&gt;\n &lt;/form&gt;\n &lt;/nav&gt;\n&lt;/header&gt;\n\n&lt;main&gt;\n &lt;article&gt;…&lt;/article&gt;\n &lt;aside&gt;…&lt;/aside&gt;\n&lt;/main&gt;\n\n&lt;footer&gt;…&lt;/footer&gt;\n</code></pre></div>\n<p>If you try testing the example with a screen reader in a modern browser, you'll already get some useful information. For example, VoiceOver gives you the following:</p>\n<ul>\n <li>On the <code>&lt;header&gt;</code> element — \"banner, 2 items\" (it contains a heading and the <code>&lt;nav&gt;</code>).</li>\n <li>On the <code>&lt;nav&gt;</code> element — \"navigation 2 items\" (it contains a list and a form).</li>\n <li>On the <code>&lt;main&gt;</code> element — \"main 2 items\" (it contains an article and an aside).</li>\n <li>On the <code>&lt;aside&gt;</code> element — \"complementary 2 items\" (it contains a heading and a list).</li>\n <li>On the search form input — \"Search query, insertion at beginning of text\".</li>\n <li>On the <code>&lt;footer&gt;</code> element — \"footer 1 item\".</li>\n</ul>\n<p>If you go to VoiceOver's landmarks menu (accessed using VoiceOver key + U and then using the cursor keys to cycle through the menu choices), you'll see that most of the elements are nicely listed so they can be accessed quickly.</p>\n<p>\n <img src=\"/en-US/docs/Learn/Accessibility/WAI-ARIA_basics/landmarks-list.png\" alt=\"Mac's VoiceOver menu for quick accessibility. Landmarks header and landmarks list including banner, navigation, main, and complementary.\" width=\"729\" height=\"532\" loading=\"lazy\">\n</p>\n<p>However, we could do better here. The search form is a really important landmark that people will want to find, but it is not listed in the landmarks menu or treated like a notable landmark beyond the actual input being called out as a search input (<code>&lt;input type=\"search\"&gt;</code>).</p>\n<p>Let's improve it by the use of some ARIA features. First, we'll add some <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles\"><code>role</code></a> attributes to our HTML structure. You can try taking a copy of our original files (see <a href=\"https://github.com/mdn/learning-area/blob/main/accessibility/aria/website-no-roles/index.html\" class=\"external\" target=\"_blank\"><code>index.html</code></a> and <a href=\"https://github.com/mdn/learning-area/blob/main/accessibility/aria/website-no-roles/style.css\" class=\"external\" target=\"_blank\"><code>style.css</code></a>), or navigating to our <a href=\"https://github.com/mdn/learning-area/tree/main/accessibility/aria/website-aria-roles\" class=\"external\" target=\"_blank\">website-aria-roles</a> example (<a href=\"https://mdn.github.io/learning-area/accessibility/aria/website-aria-roles/\" class=\"external\" target=\"_blank\">see it live</a>), which has a structure like this:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;header&gt;\n &lt;h1&gt;…&lt;/h1&gt;\n &lt;nav role=\"navigation\"&gt;\n &lt;ul&gt;\n …\n &lt;/ul&gt;\n &lt;form role=\"search\"&gt;\n &lt;!-- search form --&gt;\n &lt;/form&gt;\n &lt;/nav&gt;\n&lt;/header&gt;\n\n&lt;main&gt;\n &lt;article role=\"article\"&gt;…&lt;/article&gt;\n &lt;aside role=\"complementary\"&gt;…&lt;/aside&gt;\n&lt;/main&gt;\n\n&lt;footer&gt;…&lt;/footer&gt;\n</code></pre></div>\n<p>We've also given you a bonus feature in this example — the <a href=\"/en-US/docs/Web/HTML/Element/input\"><code>&lt;input&gt;</code></a> element has been given the attribute <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-label\"><code>aria-label</code></a>, which gives it a descriptive label to be read out by a screen reader, even though we haven't included a <a href=\"/en-US/docs/Web/HTML/Element/label\"><code>&lt;label&gt;</code></a> element. In cases like these, this is very useful — a search form like this one is a very common, easily recognized feature, and adding a visual label would spoil the page design.</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;input\n type=\"search\"\n name=\"q\"\n placeholder=\"Search query\"\n aria-label=\"Search through site content\" /&gt;\n</code></pre></div>\n<p>Now if we use VoiceOver to look at this example, we get some improvements:</p>\n<ul>\n <li>The search form is called out as a separate item, both when browsing through the page, and in the Landmarks menu.</li>\n <li>The label text contained in the <code>aria-label</code> attribute is read out when the form input is highlighted.</li>\n</ul>\n<p>Beyond this, the site is more likely to be accessible to users of older browsers such as IE8; it is worth including ARIA roles for that purpose. And if for some reason your site is built using just <code>&lt;div&gt;</code>s, you should definitely include the ARIA roles to provide these much needed semantics!</p>\n<p>The improved semantics of the search form have shown what is made possible when ARIA goes beyond the semantics available in HTML. You'll see a lot more about these semantics and the power of ARIA properties/attributes below, especially in the <a href=\"#accessibility_of_non-semantic_controls\">Accessibility of non-semantic controls</a> section. For now though, let's look at how ARIA can help with dynamic content updates.</p>"}},{"type":"prose","value":{"id":"dynamic_content_updates_2","title":"Dynamic content updates","isH3":true,"content":"<p>Content loaded into the DOM can be easily accessed using a screen reader, from textual content to alternative text attached to images. Traditional static websites with largely text content are therefore easy to make accessible for people with visual impairments.</p>\n<p>The problem is that modern web apps are often not just static text — they often update parts of the page by fetching new content from the server and updating the DOM. These are sometimes referred to as <strong>live regions</strong>.</p>\n<p>Let's look at a quick example — see <a href=\"https://github.com/mdn/learning-area/blob/main/accessibility/aria/aria-no-live.html\" class=\"external\" target=\"_blank\"><code>aria-no-live.html</code></a> (also <a href=\"https://mdn.github.io/learning-area/accessibility/aria/aria-no-live.html\" class=\"external\" target=\"_blank\">see it running live</a>). In this example, we have a simple random quote box:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;section&gt;\n &lt;h1&gt;Random quote&lt;/h1&gt;\n &lt;blockquote&gt;\n &lt;p&gt;&lt;/p&gt;\n &lt;/blockquote&gt;\n&lt;/section&gt;\n</code></pre></div>\n<p>Our JavaScript uses the <a href=\"/en-US/docs/Web/API/Window/fetch\" title=\"fetch()\"><code>fetch()</code></a> API to load a JSON file via containing a series of random quotes and their authors. Once that is done, we start up a <a href=\"/en-US/docs/Web/API/Window/setInterval\" title=\"setInterval()\"><code>setInterval()</code></a> loop that loads a new random quote into the quote box every 10 seconds:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">js</span></div><pre class=\"brush: js notranslate\"><code>const intervalID = setInterval(showQuote, 10000);\n</code></pre></div>\n<p>This works OK, but it is not good for accessibility — the content update is not detected by screen readers, so their users would not know what is going on. This is a fairly trivial example, but just imagine if you were creating a complex UI with lots of constantly updating content, like a chat room, or a strategy game UI, or a live updating shopping cart display — it would be impossible to use the app in any effective way without some kind of way of alerting the user to the updates.</p>\n<p>WAI-ARIA, fortunately, provides a useful mechanism to provide these alerts — the <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-live\"><code>aria-live</code></a> property. Applying this to an element causes screen readers to read out the content that is updated. How urgently the content is read out depends on the attribute value:</p>\n<dl>\n <dt id=\"off\"><a href=\"#off\"><code>off</code></a></dt>\n <dd>\n <p>The default. Updates should not be announced.</p>\n </dd>\n <dt id=\"polite\"><a href=\"#polite\"><code>polite</code></a></dt>\n <dd>\n <p>Updates should be announced only if the user is idle.</p>\n </dd>\n <dt id=\"assertive\"><a href=\"#assertive\"><code>assertive</code></a></dt>\n <dd>\n <p>Updates should be announced to the user as soon as possible.</p>\n </dd>\n</dl>\n<p>We'd like you to take a copy of <a href=\"https://github.com/mdn/learning-area/blob/main/accessibility/aria/aria-no-live.html\" class=\"external\" target=\"_blank\"><code>aria-no-live.html</code></a> and <a href=\"https://github.com/mdn/learning-area/blob/main/accessibility/aria/quotes.json\" class=\"external\" target=\"_blank\"><code>quotes.json</code></a>, and update your <code>&lt;section&gt;</code> opening tag as follows:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;section aria-live=\"assertive\"&gt;…&lt;/section&gt;\n</code></pre></div>\n<p>This will cause a screen reader to read out the content as it is updated.</p>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> Most browsers will throw a security exception if you try to make an HTTP request from a <code>file://</code> URL, e.g. if you just load the file by loading it directly into the browser (via double clicking, etc.). See <a href=\"/en-US/docs/Learn/Common_questions/Tools_and_setup/set_up_a_local_testing_server\">how to set up a local testing server</a>.</p>\n</div>\n<p>There is an additional consideration here — only the bit of text that updates is read out. It might be nice if we always read out the heading too, so the user can remember what is being read out. To do this, we can add the <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-atomic\"><code>aria-atomic</code></a> property to the section. Update your <code>&lt;section&gt;</code> opening tag again, like so:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;section aria-live=\"assertive\" aria-atomic=\"true\"&gt;…&lt;/section&gt;\n</code></pre></div>\n<p>The <code>aria-atomic=\"true\"</code> attribute tells screen readers to read out the entire element contents as one atomic unit, not just the bits that were updated.</p>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> You can see the finished example at <a href=\"https://github.com/mdn/learning-area/blob/main/accessibility/aria/aria-live.html\" class=\"external\" target=\"_blank\"><code>aria-live.html</code></a> (<a href=\"https://mdn.github.io/learning-area/accessibility/aria/aria-live.html\" class=\"external\" target=\"_blank\">see it running live</a>).</p>\n</div>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> The <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-relevant\"><code>aria-relevant</code></a> property is also quite useful for controlling what gets read out when a live region is updated. You can for example only get content additions or removals read out.</p>\n</div>"}},{"type":"prose","value":{"id":"enhancing_keyboard_accessibility_2","title":"Enhancing keyboard accessibility","isH3":true,"content":"<p>As discussed in a few other places in the module, one of the key strengths of HTML with respect to accessibility is the built-in keyboard accessibility of features such as buttons, form controls, and links. Generally, you can use the tab key to move between controls, the Enter/Return key to select or activate controls, and occasionally other controls as needed (for example the up and down cursor to move between options in a <code>&lt;select&gt;</code> box).</p>\n<p>However, sometimes you will end up having to write code that either uses non-semantic elements as buttons (or other types of control), or uses focusable controls for not quite the right purpose. You might be trying to fix some bad code you've inherited, or you might be building some kind of complex widget that requires it.</p>\n<p>In terms of making non-focusable code focusable, WAI-ARIA extends the <code>tabindex</code> attribute with some new values:</p>\n<ul>\n <li><code>tabindex=\"0\"</code> — as indicated above, this value allows elements that are not normally tabbable to become tabbable. This is the most useful value of <code>tabindex</code>.</li>\n <li><code>tabindex=\"-1\"</code> — this allows not normally tabbable elements to receive focus programmatically, e.g. via JavaScript, or as the target of links.</li>\n</ul>\n<p>We discussed this in more detail and showed a typical implementation back in our HTML accessibility article — see <a href=\"/en-US/docs/Learn/Accessibility/HTML#building_keyboard_accessibility_back_in\">Building keyboard accessibility back in</a>.</p>"}},{"type":"prose","value":{"id":"accessibility_of_non-semantic_controls_2","title":"Accessibility of non-semantic controls","isH3":true,"content":"<p>This follows on from the previous section — when a series of nested <code>&lt;div&gt;</code>s along with CSS/JavaScript is used to create a complex UI-feature, or a native control is greatly enhanced/changed via JavaScript, not only can keyboard accessibility suffer, but screen reader users will find it difficult to work out what the feature does if there are no semantics or other clues. In such situations, ARIA can help to provide those missing semantics.</p>\n<h4 id=\"form_validation_and_error_alerts\">Form validation and error alerts</h4>\n<p>First of all, let's revisit the form example we first looked at in our CSS and JavaScript accessibility article (read <a href=\"/en-US/docs/Learn/Accessibility/CSS_and_JavaScript#keeping_it_unobtrusive\">Keeping it unobtrusive</a> for a full recap). At the end of this section, we showed that we have included some ARIA attributes on the error message box that displays any validation errors when you try to submit the form:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;div class=\"errors\" role=\"alert\" aria-relevant=\"all\"&gt;\n &lt;ul&gt;&lt;/ul&gt;\n&lt;/div&gt;\n</code></pre></div>\n<ul>\n <li><a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/alert_role\"><code>role=\"alert\"</code></a> automatically turns the element it is applied to into a live region, so changes to it are read out; it also semantically identifies it as an alert message (important time/context-sensitive information), and represents a better, more accessible way of delivering an alert to a user (modal dialogs like <a href=\"/en-US/docs/Web/API/Window/alert\"><code>alert()</code></a> calls have a number of accessibility problems; see <a href=\"https://webaim.org/techniques/javascript/other#popups\" class=\"external\" target=\"_blank\">Popup Windows</a> by WebAIM).</li>\n <li>An <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-relevant\"><code>aria-relevant</code></a> value of <code>all</code> instructs the screen reader to read out the contents of the error list when any changes are made to it — i.e., when errors are added or removed. This is useful because the user will want to know what errors are left, not just what has been added or removed from the list.</li>\n</ul>\n<p>We could go further with our ARIA usage, and provide some more validation help. How about indicating whether fields are required in the first place, and what range the age should be?</p>\n<ol>\n <li>\n <p>At this point, take a copy of our <a href=\"https://github.com/mdn/learning-area/blob/main/accessibility/css/form-validation.html\" class=\"external\" target=\"_blank\"><code>form-validation.html</code></a> and <a href=\"https://github.com/mdn/learning-area/blob/main/accessibility/css/validation.js\" class=\"external\" target=\"_blank\"><code>validation.js</code></a> files, and save them in a local directory.</p>\n </li>\n <li>\n <p>Open them both in a text editor and have a look at how the code works.</p>\n </li>\n <li>\n <p>First of all, add a paragraph just above the opening <code>&lt;form&gt;</code> tag, like the one below, and mark both the form <code>&lt;label&gt;</code>s with an asterisk. This is normally how we mark required fields for sighted users.</p>\n <div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;p&gt;Fields marked with an asterisk (*) are required.&lt;/p&gt;\n</code></pre></div>\n </li>\n <li>\n <p>This makes visual sense, but it isn't as easy to understand for screen reader users. Fortunately, WAI-ARIA provides the <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-required\"><code>aria-required</code></a> attribute to give screen readers hints that they should tell users that form inputs need to be filled in. Update the <code>&lt;input&gt;</code> elements like so:</p>\n <div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;input type=\"text\" name=\"name\" id=\"name\" aria-required=\"true\" /&gt;\n\n&lt;input type=\"number\" name=\"age\" id=\"age\" aria-required=\"true\" /&gt;\n</code></pre></div>\n </li>\n <li>\n <p>If you save the example now and test it with a screen reader, you should hear something like \"Enter your name star, required, edit text\".</p>\n </li>\n <li>\n <p>It might also be useful if we give screen reader users and sighted users an idea of what the age value should be. This is often presented as a tooltip or placeholder inside the form field. WAI-ARIA does include <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-valuemin\"><code>aria-valuemin</code></a> and <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-valuemax\"><code>aria-valuemax</code></a> properties to specify min and max values, and screen readers support the native <code>min</code> and <code>max</code> attributes. Another well-supported feature is the HTML <code>placeholder</code> attribute, which can contain a message that is shown in the input when no value is entered and is read out by a few screen readers. Update your number input like this:</p>\n <div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;label for=\"age\"&gt;Your age:&lt;/label&gt;\n&lt;input\n type=\"number\"\n name=\"age\"\n id=\"age\"\n placeholder=\"Enter 1 to 150\"\n required\n aria-required=\"true\" /&gt;\n</code></pre></div>\n </li>\n</ol>\n<p>Always include a <a href=\"/en-US/docs/Web/HTML/Element/label\"><code>&lt;label&gt;</code></a> for every input. While some screen readers announce the placeholder text, most do not. Acceptable substitutions for providing form controls with an accessible name include <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-label\"><code>aria-label</code></a> and <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-labelledby\"><code>aria-labelledby</code></a>. But the <code>&lt;label&gt;</code> element with a <code>for</code> attribute is the preferred method as it provides usability for all users, including mouse users.</p>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> You can see the finished example live at <a href=\"https://mdn.github.io/learning-area/accessibility/aria/form-validation-updated.html\" class=\"external\" target=\"_blank\"><code>form-validation-updated.html</code></a>.</p>\n</div>\n<p>WAI-ARIA also enables some advanced form labelling techniques, beyond the classic <a href=\"/en-US/docs/Web/HTML/Element/label\"><code>&lt;label&gt;</code></a> element. We already talked about using the <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-label\"><code>aria-label</code></a> property to provide a label where we don't want the label to be visible to sighted users (see the <a href=\"#signpostslandmarks\">Signposts/Landmarks</a> section, above). Some other labeling techniques use other properties such as <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-labelledby\"><code>aria-labelledby</code></a> if you want to designate a non-<code>&lt;label&gt;</code> element as a label or label multiple form inputs with the same label, and <a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-describedby\"><code>aria-describedby</code></a>, if you want to associate other information with a form input and have it read out as well. See <a href=\"https://webaim.org/techniques/forms/advanced\" class=\"external\" target=\"_blank\">WebAIM's Advanced Form Labeling article</a> for more details.</p>\n<p>There are many other useful properties and states too, for indicating the status of form elements. For example, <code>aria-disabled=\"true\"</code> can be used to indicate that a form field is disabled. Many browsers will skip past disabled form fields which leads to them not being read out by screen readers. In some cases, a disabled element will be perceived, so it is a good idea to include this attribute to let the screen reader know that a disabled form control is in fact disabled.</p>\n<p>If the disabled state of an input is likely to change, then it is also a good idea to indicate when it happens, and what the result is. For example, in our <a href=\"https://mdn.github.io/learning-area/accessibility/aria/form-validation-checkbox-disabled.html\" class=\"external\" target=\"_blank\"><code>form-validation-checkbox-disabled.html</code></a> demo, there is a checkbox that when checked, enables another form input to allow further information to be entered. We've set up a hidden live region:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;p class=\"hidden-alert\" aria-live=\"assertive\"&gt;&lt;/p&gt;\n</code></pre></div>\n<p>which is hidden from view using absolute positioning. When this is checked/unchecked, we update the text inside the hidden live region to tell screen reader users what the result of checking this checkbox is, as well as updating the <code>aria-disabled</code> state, and some visual indicators too:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">js</span></div><pre class=\"brush: js notranslate\"><code>function toggleMusician(bool) {\n const instrument = formItems[formItems.length - 1];\n if (bool) {\n instrument.input.disabled = false;\n instrument.label.style.color = \"#000\";\n instrument.input.setAttribute(\"aria-disabled\", \"false\");\n hiddenAlert.textContent =\n \"Instruments played field now enabled; use it to tell us what you play.\";\n } else {\n instrument.input.disabled = true;\n instrument.label.style.color = \"#999\";\n instrument.input.setAttribute(\"aria-disabled\", \"true\");\n instrument.input.removeAttribute(\"aria-label\");\n hiddenAlert.textContent = \"Instruments played field now disabled.\";\n }\n}\n</code></pre></div>\n<h4 id=\"describing_non-semantic_buttons_as_buttons\">Describing non-semantic buttons as buttons</h4>\n<p>A few times in this course already, we've mentioned the native accessibility of (and the accessibility issues behind using other elements to fake) buttons, links, or form elements (see <a href=\"/en-US/docs/Learn/Accessibility/HTML#ui_controls\">UI controls</a> in the HTML accessibility article, and <a href=\"#enhancing_keyboard_accessibility\">Enhancing keyboard accessibility</a>, above). Basically, you can add keyboard accessibility back in without too much trouble in many cases, using <code>tabindex</code> and a bit of JavaScript.</p>\n<p>But what about screen readers? They still won't see the elements as buttons. If we test our <a href=\"https://mdn.github.io/learning-area/tools-testing/cross-browser-testing/accessibility/fake-div-buttons.html\" class=\"external\" target=\"_blank\"><code>fake-div-buttons.html</code></a> example in a screen reader, our fake buttons will be reported using phrases like \"Click me!, group\", which is obviously confusing.</p>\n<p>We can fix this using a WAI-ARIA role. Make a local copy of <a href=\"https://github.com/mdn/learning-area/blob/main/tools-testing/cross-browser-testing/accessibility/fake-div-buttons.html\" class=\"external\" target=\"_blank\"><code>fake-div-buttons.html</code></a>, and add <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/button_role\"><code>role=\"button\"</code></a> to each button <code>&lt;div&gt;</code>, for example:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;div data-message=\"This is from the first button\" tabindex=\"0\" role=\"button\"&gt;\n Click me!\n&lt;/div&gt;\n</code></pre></div>\n<p>Now when you try this using a screen reader, you'll have buttons be reported using phrases like \"Click me!, button\". While this is much better, you still have to add in all the native button features users expect, like handling <kbd>enter</kbd> and click events, as explained in the <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/button_role\"><code>button</code> role documentation</a>.</p>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> Don't forget however that using the correct semantic element where possible is always better. If you want to create a button, and can use a <a href=\"/en-US/docs/Web/HTML/Element/button\"><code>&lt;button&gt;</code></a> element, you should use a <a href=\"/en-US/docs/Web/HTML/Element/button\"><code>&lt;button&gt;</code></a> element!</p>\n</div>\n<h4 id=\"guiding_users_through_complex_widgets\">Guiding users through complex widgets</h4>\n<p>There are a whole host of other <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles\">roles</a> that can identify non-semantic element structures as common UI features that go beyond what's available in standard HTML, for example <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/combobox_role\"><code>combobox</code></a>, <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/slider_role\"><code>slider</code></a>, <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/tabpanel_role\"><code>tabpanel</code></a>, <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/tree_role\"><code>tree</code></a>. You can see several useful examples in the <a href=\"https://dequeuniversity.com/library/\" class=\"external\" target=\"_blank\">Deque university code library</a> to give you an idea of how such controls can be made accessible.</p>\n<p>Let's go through an example of our own. We'll return to our simple absolutely-positioned tabbed interface (see <a href=\"/en-US/docs/Learn/Accessibility/CSS_and_JavaScript#hiding_things\">Hiding things</a> in our CSS and JavaScript accessibility article), which you can find at <a href=\"https://mdn.github.io/learning-area/css/css-layout/practical-positioning-examples/tabbed-info-box.html\" class=\"external\" target=\"_blank\">Tabbed info box example</a> (see <a href=\"https://github.com/mdn/learning-area/blob/main/css/css-layout/practical-positioning-examples/tabbed-info-box.html\" class=\"external\" target=\"_blank\">source code</a>).</p>\n<p>This example as-is works fine in terms of keyboard accessibility — you can happily tab between the different tabs and select them to show the tab contents. It is also fairly accessible too — you can scroll through the content and use the headings to navigate, even if you can't see what is happening on screen. It is however not that obvious what the content is — a screen reader currently reports the content as a list of links, and some content with three headings. It doesn't give you any idea of what the relationship is between the content. Giving the user more clues as to the structure of the content is always good.</p>\n<p>To improve things, we've created a new version of the example called <a href=\"https://github.com/mdn/learning-area/blob/main/accessibility/aria/aria-tabbed-info-box.html\" class=\"external\" target=\"_blank\"><code>aria-tabbed-info-box.html</code></a> (<a href=\"https://mdn.github.io/learning-area/accessibility/aria/aria-tabbed-info-box.html\" class=\"external\" target=\"_blank\">see it running live</a>). We've updated the structure of the tabbed interface like so:</p>\n<div class=\"code-example\"><div class=\"example-header\"><span class=\"language-name\">html</span></div><pre class=\"brush: html notranslate\"><code>&lt;ul role=\"tablist\"&gt;\n &lt;li\n class=\"active\"\n role=\"tab\"\n aria-selected=\"true\"\n aria-setsize=\"3\"\n aria-posinset=\"1\"\n tabindex=\"0\"&gt;\n Tab 1\n &lt;/li&gt;\n &lt;li\n role=\"tab\"\n aria-selected=\"false\"\n aria-setsize=\"3\"\n aria-posinset=\"2\"\n tabindex=\"0\"&gt;\n Tab 2\n &lt;/li&gt;\n &lt;li\n role=\"tab\"\n aria-selected=\"false\"\n aria-setsize=\"3\"\n aria-posinset=\"3\"\n tabindex=\"0\"&gt;\n Tab 3\n &lt;/li&gt;\n&lt;/ul&gt;\n&lt;div class=\"panels\"&gt;\n &lt;article class=\"active-panel\" role=\"tabpanel\" aria-hidden=\"false\"&gt;…&lt;/article&gt;\n &lt;article role=\"tabpanel\" aria-hidden=\"true\"&gt;…&lt;/article&gt;\n &lt;article role=\"tabpanel\" aria-hidden=\"true\"&gt;…&lt;/article&gt;\n&lt;/div&gt;\n</code></pre></div>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> The most striking change here is that we've removed the links that were originally present in the example, and just used the list items as the tabs — this was done because it makes things less confusing for screen reader users (the links don't really take you anywhere; they just change the view), and it allows the setsize/position in set features to work better — when these were put on the links, the browser kept reporting \"1 of 1\" all the time, not \"1 of 3\", \"2 of 3\", etc.</p>\n</div>\n<p>ARIA features used include:</p>\n<dl>\n <dt id=\"new_roles_—\"><a href=\"#new_roles_—\">New roles — </a><a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/tablist_role\"><code>tablist</code></a>, <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/tab_role\"><code>tab</code></a>, <a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles/tabpanel_role\"><code>tabpanel</code></a></dt>\n <dd>\n <p>These identify the important areas of the tabbed interface — the container for the tabs, the tabs themselves, and the corresponding tabpanels.</p>\n </dd>\n <dt id=\"aria-selected\"><a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-selected\"><code>aria-selected</code></a></dt>\n <dd>\n <p>Defines which tab is currently selected. As different tabs are selected by the user, the value of this attribute on the different tabs is updated via JavaScript.</p>\n </dd>\n <dt id=\"aria-hidden\"><a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-hidden\"><code>aria-hidden</code></a></dt>\n <dd>\n <p>Hides an element from being read out by a screen reader. As different tabs are selected by the user, the value of this attribute on the different tabs is updated via JavaScript.</p>\n </dd>\n <dt id=\"tabindex0\"><a href=\"#tabindex0\"><code>tabindex=\"0\"</code></a></dt>\n <dd>\n <p>As we've removed the links, we need to give the list items this attribute to provide it with keyboard focus.</p>\n </dd>\n <dt id=\"aria-setsize\"><a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-setsize\"><code>aria-setsize</code></a></dt>\n <dd>\n <p>This property allows you to specify to screen readers that an element is part of a series, and how many items the series has.</p>\n </dd>\n <dt id=\"aria-posinset\"><a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes/aria-posinset\"><code>aria-posinset</code></a></dt>\n <dd>\n <p>This property allows you to specify what position in a series an element is in. Along with <code>aria-setsize</code>, it provides a screen reader with enough information to tell you that you are currently on item \"1 of 3\", etc. In many cases, browsers should be able to infer this information from the element hierarchy, but it certainly helps to provide more clues.</p>\n </dd>\n</dl>\n<p>In our tests, this new structure did serve to improve things overall. The tabs are now recognized as tabs (e.g. \"tab\" is spoken by the screen reader), the selected tab is indicated by \"selected\" being read out with the tab name, and the screen reader also tells you which tab number you are currently on. In addition, because of the <code>aria-hidden</code> settings (only the non-hidden tab ever has <code>aria-hidden=\"false\"</code> set), the non-hidden content is the only one you can navigate down to, meaning the selected content is easier to find.</p>\n<div class=\"notecard note\">\n <p><strong>Note:</strong> If there is anything you explicitly don't want screen readers to read out, you can give them the <code>aria-hidden=\"true\"</code> attribute.</p>\n</div>"}},{"type":"prose","value":{"id":"test_your_skills!","title":"Test your skills!","isH3":false,"content":"<p>You've reached the end of this article, but can you remember the most important information? You can find some further tests to verify that you've retained this information before you move on — see <a href=\"/en-US/docs/Learn/Accessibility/WAI-ARIA_basics/Test_your_skills:_WAI-ARIA\">Test your skills: WAI-ARIA</a>.</p>"}},{"type":"prose","value":{"id":"summary","title":"Summary","isH3":false,"content":"<p>This article has by no means covered all that's available in WAI-ARIA, but it should have given you enough information to understand how to use it, and know some of the most common patterns you will encounter that require it.</p>"}},{"type":"prose","value":{"id":"see_also","title":"See also","isH3":false,"content":"<ul>\n <li><a href=\"/en-US/docs/Web/Accessibility/ARIA/Attributes\">Aria states and properties</a>: All <code>aria-*</code> attributes</li>\n <li><a href=\"/en-US/docs/Web/Accessibility/ARIA/Roles\">WAI-ARIA roles</a>: Categories of ARIA roles and the roles covered on MDN</li>\n <li><a href=\"https://www.w3.org/TR/html-aria/\" class=\"external\" target=\"_blank\">ARIA in HTML</a> on W3C: A specification that defines, for each HTML feature, the accessibility (ARIA) semantics implicitly applied on it by the browser and the WAI-ARIA features you may set on it if extra semantics are required</li>\n <li><a href=\"https://dequeuniversity.com/library/\" class=\"external\" target=\"_blank\">Deque university code library</a>: A library of really useful and practical examples showing complex UI controls made accessible using WAI-ARIA features</li>\n <li><a href=\"https://www.w3.org/WAI/ARIA/apg/\" class=\"external\" target=\"_blank\">WAI-ARIA authoring practices</a> on W3C: A very detailed design pattern from the W3C, explaining how to implement different types of complex UI control whilst making them accessible using WAI-ARIA features</li>\n</ul><ul class=\"prev-next\">\n <li><a class=\"button secondary\" href=\"/en-US/docs/Learn/Accessibility/CSS_and_JavaScript\"><span class=\"button-wrap\"> Previous </span></a></li>\n <li><a class=\"button secondary\" href=\"/en-US/docs/Learn/Accessibility\"><span class=\"button-wrap\"> Overview: Accessibility</span></a></li>\n <li><a class=\"button secondary\" href=\"/en-US/docs/Learn/Accessibility/Multimedia\"><span class=\"button-wrap\"> Next </span></a></li>\n</ul>"}}],"toc":[{"text":"What is WAI-ARIA?","id":"what_is_wai-aria"},{"text":"Practical WAI-ARIA implementations","id":"practical_wai-aria_implementations"},{"text":"Test your skills!","id":"test_your_skills!"},{"text":"Summary","id":"summary"},{"text":"See also","id":"see_also"}],"summary":"This article has by no means covered all that's available in WAI-ARIA, but it should have given you enough information to understand how to use it, and know some of the most common patterns you will encounter that require it.","popularity":0.045,"modified":"2024-10-25T00:08:46.000Z","other_translations":[{"locale":"de","title":"Grundlagen von WAI-ARIA","native":"Deutsch"},{"locale":"fr","title":"Les bases de WAI-ARIA","native":"Français"},{"locale":"ja","title":"WAI-ARIA の基本","native":"日本語"},{"locale":"zh-CN","title":"WAI-ARIA 基础","native":"中文 (简体)"},{"locale":"zh-TW","title":"WAI-ARIA基礎","native":"正體中文 (繁體)"}],"pageType":"learn-module-chapter","source":{"folder":"en-us/learn/accessibility/wai-aria_basics","github_url":"https://github.com/mdn/content/blob/main/files/en-us/learn/accessibility/wai-aria_basics/index.md","last_commit_url":"https://github.com/mdn/content/commit/baac7f2a43813a7930ff97b11d9c38b413f97c78","filename":"index.md"},"short_title":"WAI-ARIA basics","parents":[{"uri":"/en-US/docs/Learn","title":"Guides"},{"uri":"/en-US/docs/Learn/Accessibility","title":"Accessibility"},{"uri":"/en-US/docs/Learn/Accessibility/WAI-ARIA_basics","title":"WAI-ARIA basics"}],"pageTitle":"WAI-ARIA basics - Learn web development | MDN","noIndexing":false}}</script></body></html>

Pages: 1 2 3 4 5 6 7 8 9 10