Navbar - Tillgänglighetsförbättringar
🎯 Tillgänglighetsförbättringar
Denna demo visar de tillgänglighetsförbättringar som har implementerats i SweNavbar-komponenten:
- ARIA-attribut: Semantiska roller och beskrivningar för skärmläsare
- Tangentbordsnavigation: Fullt navigerbar med Tab, Enter och Space
- Focus Trap i Drawer: Fokus fångas inom drawer-menyn när den är öppen (WCAG 2.1 Level A)
- aria-expanded: Menyalternativ med barn har aria-expanded för skärmläsare
- Skip-länk: "Hoppa till huvudinnehåll" för tangentbordsanvändare
- Fokusindikatorer: Tydliga visuella indikatorer för fokuserat element
- Semantisk HTML: Korrekt användning av nav, heading och role-attribut
- Språkstöd: Flerspråkiga ARIA-texter och beskrivningar
- Motionsrespekt: Respekterar användares preferenser för animationer
- Hög kontrast: Stöd för hög kontrast-läge
⌨️ Tangentbordsnavigation
Testa dessa tangentbordskortkommandon:
- Tab - Navigera mellan fokuserbara element (cyklar inom drawer när den är öppen)
- Shift + Tab - Navigera bakåt (cyklar bakåt inom drawer)
- Enter eller Space - Aktivera fokuserat element / Expandera menyalternativ med barn
- Escape - Stäng drawer-menyn (fokus återgår till hamburger-ikonen)
✨ Ny funktionalitet - Focus Trap:
- När drawer öppnas flyttas fokus automatiskt till stäng-knappen
- Tab på sista elementet i drawer → går till första elementet
- Shift+Tab på första elementet → går till sista elementet
- Fokus kan inte "läcka" ut till bakgrundsinnehållet
- När drawer stängs återställs fokus till hamburger-ikonen
🎛️ Testa tillgänglighetsegenskaper
Navigation:
Användarinformation:
Språk:
Sökfunktion:
Rubrik:
🔒 Testa Focus Trap i Drawer-menyn
Steg-för-steg instruktioner för att testa focus trap:
- Tryck på Tab flera gånger tills du når hamburger-ikonen (längst upp till höger)
- Tryck Enter eller Space för att öppna drawer-menyn
- Observera: Fokus flyttas automatiskt till stäng-knappen (×)
- Tryck Tab upprepade gånger för att navigera genom drawer-menyalternativen
- Observera: När du når sista menyalternativet och trycker Tab igen, cyklar fokus tillbaka till stäng-knappen
- Testa Shift + Tab för att navigera bakåt - fokus cyklar från första till sista elementet
- Hitta ett menyalternativ med en pil (›) och tryck Enter eller Space för att expandera undermenyn
- Observera: Pilen roterar (›→∨) och aria-expanded ändras från "false" till "true"
- Tryck Escape för att stänga drawer
- Observera: Fokus återställs automatiskt till hamburger-ikonen
💡 Tips: Använd en skärmläsare (VoiceOver på Mac: Cmd+F5, NVDA/JAWS på Windows) för att höra hur aria-expanded och aria-haspopup annonseras när du navigerar.
🔍 Tillgänglighetstest
För att testa tillgängligheten kan du:
- Använda en skärmläsare (t.ex. NVDA, JAWS, eller VoiceOver)
- Navigera endast med tangentbordet
- Testa med hög kontrast aktiverat
- Kontrollera med axe-core eller liknande verktyg
- Testa med olika språkinställningar
🛠️ Teknisk implementation
De viktigaste tillgänglighetsförbättringarna som implementerats:
1. Focus Trap i Drawer (NYA!):
// Hämta alla fokuserbara element i drawer
function getFocusableElements(container) {
const selectors = 'a[href], button:not([disabled]), [tabindex]:not([tabindex="-1"])';
return Array.from(container.querySelectorAll(selectors))
.filter(el => el.offsetParent !== null);
}
// Hantera Tab/Shift+Tab för att cykla fokus
function handleDrawerFocusTrap(e) {
if (e.key !== 'Tab') return;
const focusableElements = getFocusableElements(drawer);
const firstFocusable = focusableElements[0];
const lastFocusable = focusableElements[focusableElements.length - 1];
// Cykla fokus inom drawer
if (e.shiftKey && document.activeElement === firstFocusable) {
e.preventDefault();
lastFocusable.focus();
} else if (!e.shiftKey && document.activeElement === lastFocusable) {
e.preventDefault();
firstFocusable.focus();
}
}
2. ARIA-expanded för menyalternativ med barn (NYA!):
// Sätt ARIA-attribut för menyalternativ med barn
menuItem.setAttribute('role', 'button');
menuItem.setAttribute('aria-expanded', 'false');
menuItem.setAttribute('aria-haspopup', 'true');
menuItem.setAttribute('tabindex', '0');
// Uppdatera aria-expanded vid toggle
function toggleSubmenu(e) {
const isExpanded = submenuContainer.style.maxHeight !== '0px';
if (isExpanded) {
menuItem.setAttribute('aria-expanded', 'false');
} else {
menuItem.setAttribute('aria-expanded', 'true');
}
}
// Tangentbordsstöd för expansion
menuItem.addEventListener('keydown', function(e) {
if (e.key === 'Enter' || e.key === ' ') {
e.preventDefault();
toggleSubmenu(e);
}
});
3. Fokushantering vid öppning/stängning:
function openDrawer() {
// Spara element som öppnade drawer
drawerTriggerElement = document.activeElement;
// Aktivera focus trap
document.addEventListener('keydown', handleDrawerFocusTrap);
// Flytta fokus till stäng-knappen
setTimeout(() => closeButton.focus(), 50);
}
function closeDrawer() {
// Avaktivera focus trap
document.removeEventListener('keydown', handleDrawerFocusTrap);
// Återställ fokus till hamburger-ikonen
if (drawerTriggerElement && drawerTriggerElement.focus) {
drawerTriggerElement.focus();
}
}
4. ARIA-attribut för navigation:
navbar.setAttribute('role', 'banner');
navbar.setAttribute('aria-label', 'Huvudnavigation');
brand.setAttribute('role', 'button');
brand.setAttribute('aria-label', 'Logotyp, gå till startsida');
navList.setAttribute('role', 'menubar');
link.setAttribute('role', 'menuitem');
5. Fokusindikatorer:
/* Fokusindikatorer för drawer-menyalternativ */
.drawer-menu-item:focus {
outline: 2px solid var(--navbar-yellow);
outline-offset: -2px;
background-color: rgba(255, 255, 255, 0.1) !important;
}
/* Högt kontrast för tillgänglighet */
@media (prefers-contrast: high) {
.drawer-menu-item:focus {
outline-color: var(--navbar-white);
outline-width: 3px;
}
}
📚 WCAG 2.1 Level A & AA - Riktlinjer som följs
- 1.3.1 Info och relationer (A): Semantisk struktur med nav, heading och ARIA
- 1.4.3 Kontrast (minimum) (AA): Minst 4.5:1 kontrast för normal text
- 2.1.1 Tangentbord (A): All funktionalitet tillgänglig via tangentbord (✅ inkl. drawer expansion med Enter/Space)
- 2.1.2 Ingen tangentbordsfälla (A): ✅ Focus trap i drawer med möjlighet att stänga med Escape
- 2.4.1 Bypassa block (A): Skip-länk för att hoppa över navigation
- 2.4.3 Fokusordning (A): ✅ Logisk fokusordning genom komponenten och drawer
- 2.4.7 Synligt fokus (AA): ✅ Tydliga fokusindikatorer på alla interaktiva element
- 3.1.1 Språk på sida (A): Språkattribut och flerspråkigt stöd
- 4.1.2 Namn, roll, värde (A): ✅ Korrekta ARIA-attribut (aria-expanded, aria-haspopup) och roller
✅ Ny compliance: Med focus trap-implementationen uppfyller komponenten nu
WCAG 2.1 Level A Success Criterion 2.1.2 (No Keyboard Trap) genom att:
• Fånga fokus inom drawer när den är öppen
• Tillåta användare att stänga drawer med Escape-tangenten
• Återställa fokus till utlösande element vid stängning