️(frontend) announce mic/camera state for screen readers on shortcut

announce "Microphone/Camera turned on/off" when toggling via
keyboard shortcut so screen reader users get feedback
This commit is contained in:
Cyril
2026-03-02 12:23:22 +01:00
parent b2ad423886
commit 1d23cb889a
6 changed files with 33 additions and 1 deletions

View File

@@ -29,6 +29,7 @@ and this project adheres to
- ⬆️(python) bump minimal required python version to 3.13 #1033
- ♿️(frontend) improve accessibility of the IntroSlider carousel #1026
- ♿️(frontend) add skip link component for keyboard navigation #1019
- ♿️(frontend) announce mic/camera state to SR on shortcut toggle #1052
### Fixed

View File

@@ -1,5 +1,6 @@
import { ToggleButton } from '@/primitives'
import { useRegisterKeyboardShortcut } from '@/features/shortcuts/useRegisterKeyboardShortcut'
import { useScreenReaderAnnounce } from '@/hooks/useScreenReaderAnnounce'
import { useMemo, useState } from 'react'
import { appendShortcutLabel } from '@/features/shortcuts/utils'
import { useTranslation } from 'react-i18next'
@@ -87,10 +88,24 @@ export const ToggleDevice = <T extends ToggleSource>({
const deviceIcons = useDeviceIcons(kind)
const cannotUseDevice = useCannotUseDevice(kind)
const deviceShortcut = useDeviceShortcut(kind)
const announce = useScreenReaderAnnounce()
useRegisterKeyboardShortcut({
id: deviceShortcut?.id,
handler: async () => await toggle(),
handler: async () => {
const nextState = !enabled
try {
const didChange = await toggle(nextState)
if (didChange === false) return
const message = t(nextState ? 'turnedOn' : 'turnedOff', {
keyPrefix: `selectDevice.${kind}`,
})
announce(message, 'assertive')
} catch {
// no announce
}
},
isDisabled: cannotUseDevice,
})

View File

@@ -22,6 +22,8 @@
"permissionsNeeded": "Kamera auswählen - genehmigung erforderlich",
"disable": "Kamera deaktivieren",
"enable": "Kamera aktivieren",
"turnedOff": "Kamera deaktiviert",
"turnedOn": "Kamera aktiviert",
"label": "Kamera",
"placeholder": "Kamera aktivieren, um die Vorschau zu sehen"
},
@@ -30,6 +32,8 @@
"permissionsNeeded": "Mikrofon auswählen - genehmigung erforderlich",
"disable": "Mikrofon deaktivieren",
"enable": "Mikrofon aktivieren",
"turnedOff": "Mikrofon deaktiviert",
"turnedOn": "Mikrofon aktiviert",
"label": "Mikrofon"
},
"audiooutput": {

View File

@@ -22,6 +22,8 @@
"permissionsNeeded": "Select camera - permission needed",
"disable": "Disable camera",
"enable": "Enable camera",
"turnedOff": "Camera turned off",
"turnedOn": "Camera turned on",
"label": "Camera",
"placeholder": "Enable camera to see the preview"
},
@@ -30,6 +32,8 @@
"permissionsNeeded": "Select microphone - permission needed",
"disable": "Disable microphone",
"enable": "Enable microphone",
"turnedOff": "Microphone turned off",
"turnedOn": "Microphone turned on",
"label": "Microphone"
},
"audiooutput": {

View File

@@ -22,6 +22,8 @@
"permissionsNeeded": "Choisir la webcam - autorisations nécessaires",
"disable": "Désactiver la webcam",
"enable": "Activer la webcam",
"turnedOff": "Webcam désactivée",
"turnedOn": "Webcam activée",
"label": "Webcam",
"placeholder": "Activez la webcam pour prévisualiser l'affichage"
},
@@ -30,6 +32,8 @@
"permissionsNeeded": "Choisir le micro - autorisations nécessaires",
"disable": "Désactiver le micro",
"enable": "Activer le micro",
"turnedOff": "Micro désactivé",
"turnedOn": "Micro activé",
"label": "Microphone"
},
"audiooutput": {

View File

@@ -22,6 +22,8 @@
"permissionsNeeded": "Selecteer camera - Toestemming vereist",
"disable": "Camera uitschakelen",
"enable": "Camera inschakelen",
"turnedOff": "Camera uitgeschakeld",
"turnedOn": "Camera ingeschakeld",
"label": "Camera",
"placeholder": "Schakel de camera in om de preview te zien"
},
@@ -30,6 +32,8 @@
"permissionsNeeded": "Selecteer microfoon - Toestemming vereist",
"disable": "Microfoon dempen",
"enable": "Microfoon dempen opheffen",
"turnedOff": "Microfoon uitgeschakeld",
"turnedOn": "Microfoon ingeschakeld",
"label": "Microfoon"
},
"audiooutput": {