Accessibilité
Accessibilité
Rendre ton application accessible, c’est avant tout la rendre utilisable par le plus grand nombre.
Les utilisateurs qui interagiront avec tes futures apps sont tous différents, certains ont une excellente vision, d’autres non, certains naviguent facilement avec des gestes complexes, d’autres ont du mal à swiper ou à scroller, et d’autres encore utilisent leur appareil dans des conditions qui limitent leurs capacités (fatigue, luminosité, blessure, etc.).
En tant que développeur, tu as donc un rôle clé : concevoir des applications inclusives, qui s’adaptent aux besoins et aux contraintes de chacun. Et c’est loin d’être un simple geste altruiste, une application accessible, c’est aussi une application plus claire, plus intuitive et plus confortable pour tous.
Apple met à notre disposition de nombreux outils pour rendre nos interfaces accessibles, et bonne nouvelle, ils s’intègrent naturellement à SwiftUI.
Dans ce cours, on va donc découvrir comment concevoir une application iOS inclusive, étape par étape, en explorant les différents profils d’utilisateurs et les solutions concrètes pour les accompagner.
Panorama des besoins spécifiques
Pour répondre correctement aux différents besoins d’accessibilité, je te propose de faire un tour d’horizon des différents publics à accompagner, afin de bien comprendre leurs problématiques et d’optimiser au mieux nos applications.
Déficience visuelle
C’est sans doute le public le plus large à accompagner lorsqu’on parle d’accessibilité. Une grande partie de la population est concernée, à des degrés divers, par des troubles de la vision. Ça peut être une personne âgée dont la vue baisse naturellement avec l’âge, une personne atteinte de daltonisme qui ne perçoit pas les couleurs comme la majorité, ou encore une personne en situation de cécité partielle ou totale. Chacun de ces profils rencontre des obstacles bien spécifiques dans l’usage d’une interface numérique.
Dans le cas d’une personne âgée ou d’un utilisateur ayant une vision affaiblie, la lisibilité devient un enjeu central, il est important que les textes soient facilement repérables, que la hiérarchie visuelle soit claire, et que l’interface ne soit pas trop chargée. Pour les personnes daltoniennes, l’enjeu porte sur la perception des couleurs, ce public ne distingue pas certains contrastes que d’autres perçoivent naturellement, ce qui peut entraîner des confusions ou des informations manquées si les couleurs sont le seul indicateur. Enfin, pour les personnes aveugles ou très malvoyantes, la question de l’accès à l’information ne passe plus par la vue, mais par des outils d’assistance qui permettent d’écouter ce qui est affiché à l’écran.
L’accessibilité visuelle ne concerne donc pas un cas unique, mais bien une diversité de situations, permanentes ou temporaires, qui nécessitent d’adapter nos interfaces pour qu’elles soient réellement utilisables par tous.
Vision affaiblie / presbytie / myopie
C’est la difficulté la plus courante, une vision diminuée n’empêche pas l’utilisation d’un smartphone, mais elle rend la lecture et l’interaction beaucoup plus fatigantes.
Les utilisateurs concernés sont nombreux, personnes âgées, myopes, presbytes, mais aussi toute personne consultant son téléphone dans de mauvaises conditions (fatigue visuelle, soleil, écran sale…).
Contraste
Pour aider un public ayant des troubles de la vision, même mineurs, la première chose à faire pour l’accompagner, c’est de gérer le contraste des couleurs de ton application.
Sans entrer dans la question de l’esthétisme, l’objectif ici est de rendre tes différents textes et éléments lisibles par le plus grand nombre.
Ci-dessus, tu as un exemple simple d’un contraste bien travaillé à gauche, et un contre-exemple à droite. La lecture y devient difficile, et le bouton est à peine perceptible.
Pour éviter toute erreur dans le choix de tes couleurs, prends le temps de les tester en amont. Il existe de nombreux outils en ligne pour ça.
Personnellement, j’utilise Coolors Contrast Checker.
Texte
Les principaux problèmes liés au texte sont souvent des tailles de police trop petites ou trop fines, ce qui réduit la lisibilité.
On peut également rencontrer un manque de contraste avec le fond, un mauvais usage des ombres, ou encore un espacement des lettres et des lignes mal gérées, trop serré ou, au contraire, trop espacé.
Voici quelque solutions pour t’assurer de rendre tes textes accessibles.
Utiliser des polices dynamiques (Dynamic Type)
Les Dynamic Type, ou en clair les police mise à disposition par défaut par Apple sont conçues pour s’adapter automatiquement à la taille de texte choisie par l’utilisateur dans ses réglages d’accessibilité.
Text("Bienvenue")
.font(.title2) // Police sémantique, qui s’adapte à Dynamic Type
Dans les réglages d’accessibilité de l’iPhone, un utilisateur peut ajuster la taille du texte afin d’améliorer sa lecture sur l’ensemble des applications qui utilisent le Dynamic Type (les polices natives d’Apple).
En utilisant les polices natives d’Apple, les textes de cette application se sont adaptés aux préférences de l’utilisateur.
(On peut observer que l’interface est partiellement “cassée”, avec des textes qui grossissent de manière désordonnée.
Dans l’idéal, pour rendre nos applications réellement accessibles, il faudrait adapter l’UI dynamiquement en fonction des choix d’accessibilité de chaque utilisateur.)
.dynamicTypeSize()
Pour éviter le problème précédent et permettre à l’utilisateur d’adapter la taille du texte de nos applications en fonction de ses réglages d’accessibilité, on peut définir des règles afin de ne pas casser l’UI. Pour ça, on utilise le modificateur .dynamicTypeSize(), qui permet d’indiquer qu’un texte ne pourra jamais être plus petit qu’une certaine taille de police, ni plus grand qu’une autre.
En clair, ça crée un cadre de flexibilité qui permet au designer et au développeur d’anticiper le comportement de l’interface en fonction des choix de l’utilisateur.
VStack(alignment: .leading, spacing: 8) {
Text("Titre principal")
.font(.title)
Text("Sous-titre explicatif")
.font(.headline)
.foregroundStyle(.secondary)
Text("Voici un paragraphe de texte plus long qui illustre le corps de contenu. "
+ "Il est conçu pour être facilement lisible et s’adaptera à la taille de texte préférée de l’utilisateur.")
.font(.body)
.foregroundStyle(.primary)
}
.padding()
.dynamicTypeSize(.small ... .accessibility3)
Ici, on définit les règles du texte de la VStack. Le texte ne pourra pas être inférieur à .small (donc pas en taille .xSmall), et il ne pourra pas être supérieur à la taille .accessibility3. Réfère-toi au tableau ci-dessous pour voir les différents paramètres disponibles.
| Valeur | Description | Usage typique |
|---|---|---|
| .xSmall | Très petit texte | Pour économiser de l’espace, rarement conseillé |
| .small | Petit texte | Pour les labels discrets ou secondaires |
| .medium | Taille par défaut du système | La plus utilisée, base de tout design |
| .large | Légèrement plus grand que la moyenne | Pour le confort visuel sur les écrans moyens |
| .xLarge | Texte large | Souvent utilisé sur iPad ou affichages distants |
| .xxLarge | Très large | Lecture à distance, meilleure visibilité |
| .xxxLarge | Extra large | Pour les interfaces à forte lisibilité (bornes, seniors) |
| .accessibility1 | Premier niveau d’agrandissement | Recommandé pour une bonne lisibilité |
| .accessibility2 | Texte encore plus grand | Idéal pour les personnes âgées ou myopes |
| .accessibility3 | Très grand texte | Bon compromis entre accessibilité et design |
| .accessibility4 | Texte extrêmement grand | Pour les utilisateurs malvoyants |
| .accessibility5 | Taille maximale possible | Lecture assistée / VoiceOver |
| .fixed | Désactive la mise à l’échelle | ⚠️ À éviter : empêche toute adaptation du texte |
Daltonisme (protanopie, deutéranopie, tritanopie)
Ci-dessus, tu peux voir un écran classique avec un bouton de suppression rouge, utilisé pour représenter une action d’urgence. C’est une couleur culturellement associée à l’importance et au danger, que l’on retrouve dans la majorité des applications pour signaler un événement critique.
Cependant, une personne daltonienne percevra cette couleur comme sur l’écran de droite, le rouge apparaît alors légèrement brun, ce qui altère totalement le message d’alerte que l’on souhaite transmettre.
Pour pallier ce problème, c’est Apple qui fait le travail. Dans les paramètres d’un iPhone, on retrouve les filtres de couleur, un utilisateur daltonien peut y sélectionner le type de filtre correspondant à sa vision afin d’adapter les couleurs à ses besoins.
Ci-dessus, tu peux observer une application utilisant le rouge natif d’iOS.
À gauche, tu vois la version perçue par un utilisateur daltonien après l’application des filtres de couleur adaptés.
@Environment(\.accessibilityDifferentiateWithoutColor)
Le plus grand problème rencontré par les daltoniens, c’est le choix culturel des couleurs.
Le vert représente un succès, le rouge une urgence ou une erreur, et le jaune un avertissement ou une alerte, etc. Mais comme les daltoniens ne perçoivent pas les couleurs de la même façon, ces informations leur sont souvent invisibles. Une solution consiste donc à ajouter une iconographie adaptée pour renforcer le sens d’un message important ou d’un bouton, et ainsi rendre l’information accessible à tous. C’est la qu’entre en jeu la propriété d’environnement .accessibilityDifferentiateWithoutColor qui permettra de changer l’UI si l’utilisateur à coché dans ses réglage d’accessibilité l’option “Différencier sans la couleur”
struct StatusView: View {
@Environment(\.accessibilityDifferentiateWithoutColor) var noColor
var status: String = "success"
var body: some View {
HStack(spacing: 12) {
if noColor {
Label("Succès", systemImage: "checkmark.circle.fill")
.foregroundStyle(.primary)
} else {
Text("Succès")
.foregroundStyle(.green)
}
}
.padding()
}
}
Cécité partielle ou totale
Cette fois, on va se pencher sur le problème de la cécité, qu’elle soit partielle ou totale, l’utilisateur ne voit plus le contenu, ou très peu.
Pour l’aider, Apple a mis à disposition un lecteur d’écran intégré nativement (VoiceOver) à ses différents systèmes d’exploitation, dont iOS dans notre cas.
Une fois activé dans les réglages, le fonctionnement tactile change complètement, une voix guide l’utilisateur et annonce chaque étape.
Il faut balayer de gauche à droite pour naviguer entre les éléments, et effectuer un double tap pour activer l’élément sélectionné (comme un bouton ou un lien de navigation, par exemple).
Il existe d’autres gestes et techniques, et je t’invite vivement à activer VoiceOver pour les découvrir.
Un tutoriel interactif t’accompagne lors de la première utilisation, c’est un peu déroutant au début, mais on comprend très vite toute l’utilité de cet outil.
Modificateurs SwiftUI utiles pour VoiceOver
Quand on développe nos applications en SwiftUI, on dispose de nombreux outils permettant d’adapter le contenu à VoiceOver, afin que celui-ci puisse le lire de façon claire et logique.
Par exemple, ici, en utilisant le modificateur .accessibilityLabel, VoiceOver va annoncer vocalement « Supprimer l’élément » à l’utilisateur.
Ensuite, le modificateur .accessibilityHint va permettre à VoiceOver d’indiquer quelle action l’utilisateur doit effectuer pour activer l’élément, ici, « Double-touchez pour supprimer. »
C’est donc à nous, développeurs, d’être vigilants lors de la conception de nos applications et d’intégrer correctement les différents modificateurs pour paramétrer efficacement VoiceOver.
Je te joins ci-dessous le tableau des principaux modificateurs.
| Modificateur | Description | Exemple d’utilisation | VoiceOver dira |
|---|---|---|---|
| accessibilityLabel | Donne un nom lisible à un élément. Remplace le texte visuel ou le complète. | Image(systemName: « trash »).accessibilityLabel(« Supprimer l’élément ») | “Supprimer l’élément.” |
| accessibilityValue | Fournit la valeur actuelle d’un élément (utile pour sliders, steppers, etc.). | Slider(value: $volume).accessibilityValue(« (Int(volume * 100)) % ») | “Volume : 80 %.” |
| accessibilityHint | Ajoute une explication sur ce que fait l’action (sans être répétitive). | Button(« Envoyer »).accessibilityHint(« Double-touchez pour confirmer l’envoi ») | “Envoyer. Double-touchez pour confirmer l’envoi.” |
| accessibilityHidden | Cache un élément au lecteur d’écran (utile pour les icônes décoratives). | Image(« background »).accessibilityHidden(true) | Ignoré par VoiceOver. |
| accessibilityAddTraits | Ajoute un rôle ou un comportement à un élément (ex. bouton, titre, en-tête). | Text(« Supprimer »).accessibilityAddTraits(.isButton) | “Supprimer, bouton.” |
| accessibilityRemoveTraits | Supprime un rôle par défaut (par exemple si un bouton n’est pas cliquable). | Button(« Inactif »).accessibilityRemoveTraits(.isButton) | “Inactif.” |
| accessibilityElement(children:) | Définit comment regrouper les sous-éléments pour une lecture fluide. | .accessibilityElement(children: .combine) | Regroupe tous les textes d’une carte comme un seul bloc lu. |
| accessibilitySortPriority | Définit l’ordre de lecture (plus la valeur est haute, plus c’est lu en premier). | Text(« Titre »).accessibilitySortPriority(2) | VoiceOver lit ce texte avant les autres. |
| accessibilityAdjustableAction | Permet à l’utilisateur de modifier une valeur avec des gestes VoiceOver (swipe haut/bas). | .accessibilityAdjustableAction { direction in … } | “Augmenter” / “Diminuer.” |
| accessibilityFocused | Permet de gérer la mise au point VoiceOver sur un élément spécifique (utile pour formulaires). | @AccessibilityFocusState private var focus: Field? | VoiceOver se place automatiquement sur le champ ciblé. |
On conclut ici avec VoiceOver sur la conception accessible de nos applications iOS pour un public ayant des troubles de la vision. Apple dispose encore de nombreux outils à disposition. Si ce sujet t’intéresse et que tu souhaites en savoir plus, je t’invite à consulter ces ressources :
SwiftUI – Accessibilité (Apple Developer)
https://ravi6997.medium.com/swiftui-accessibility-apis-whats-new-in-ios-26-d5d7f24ba2a7
SwiftUI Accessibility : goodies & gotchas (part 1) – Deque
Déficience auditive
Pour le public présentant une déficience auditive, l’approche est généralement plus simple, à condition de bien prendre en compte certains cas spécifiques. Si notre application utilise des sons, que ce soit une vidéo, un contenu audio comme de la musique ou un podcast, ou encore un effet sonore destiné à signaler un événement, il est essentiel de proposer une alternative accessible. Ça peut passer par l’ajout de sous-titres, d’animations visuelles, ou d’éléments visuels qui remplacent ou accompagnent le son. L’idée fondamentale est de ne jamais transmettre une information uniquement par le biais du son, afin de ne laisser personne de côté.
Bonnes pratiques à adopter dans ton code
| Cas de figure | Bonne pratique SwiftUI |
|---|---|
| Bouton ou alerte sonore | Ajouter une animation ou un retour haptique |
| Vidéo sans sous-titre | Fournir un texte alternatif ou des sous-titres |
| Message audio | Afficher la transcription |
| Notification sonore | Ajouter une bannière ou un signal visuel |
| Feedback utilisateur | Combiner son + haptique + visuel |
Troubles moteurs
Les troubles moteurs regroupent toutes les situations où un utilisateur rencontre des difficultés à interagir physiquement avec une interface. Ça peut concerner des personnes présentant une paralysie partielle, des tremblements, une motricité fine réduite ou simplement un usage limité d’un membre. Dans ces cas, la réalisation de gestes précis ou complexes comme le pinch (pincer pour zoomer) ou le swipe (balayer) peut devenir compliquée, voire impossible.
L’accessibilité passe donc par la simplification des interactions, proposer de gros boutons bien espacés, offrir des actions alternatives accessibles au clavier ou via des dispositifs d’assistance comme Switch Control ou AssistiveTouch sur iOS. L’objectif est que chaque action essentielle puisse être réalisée sans contrainte, même sans gestes complexes, afin que la navigation reste fluide, simple et inclusive pour tous les utilisateurs, quelles que soient leurs capacités motrices.
Les technologies Switch Control et AssistiveTouch, présentes par défaut sur iOS, permettent justement de compenser ces limitations.
- Switch Control s’adresse notamment aux personnes utilisant des dispositifs de suivi du regard (eye tracking) ou un interrupteur physique pour parcourir l’écran et valider des actions sans toucher directement l’appareil.
- AssistiveTouch, quant à lui, remplace les gestes complexes et l’utilisation des boutons physiques par un menu flottant personnalisable, offrant ainsi un contrôle simplifié et adapté aux besoins de chaque utilisateur.
Pour accompagner ces utilisateurs de la manière la plus simple possible, il est essentiel de proposer une alternative aux mouvements complexes.
| Geste complexe | Alternative accessible |
|---|---|
| Swipe pour supprimer | Bouton “Supprimer” clair et large |
| Pinch pour zoomer | Boutons “+ / –” |
| Drag pour trier | Boutons “Monter / Descendre” |
| Swipe pour revenir en arrière | Bouton “Retour” explicite |
Troubles cognitifs ou neurologiques
Les troubles cognitifs ou neurologiques concernent des utilisateurs qui peuvent avoir des difficultés à comprendre, mémoriser ou se repérer dans une interface numérique. Ces troubles peuvent se manifester par une surcharge cognitive face à une interface trop dense, un manque de repères dans une navigation non intuitive, ou une gêne causée par des animations trop rapides ou trop nombreuses. L’enjeu ici est de concevoir une expérience claire, stable et cohérente, limiter les éléments distracteurs, structurer visuellement les informations, et respecter les préférences d’accessibilité.
Pour limiter les animations, qui peuvent fortement gêner certains utilisateurs, il est possible de réduire les animations de nos applications via les réglages d’accessibilité de l’iPhone, à condition que celles-ci soient configurées avec le modificateur .accessibilityReduceMotion(). Voici un exemple :
struct ReduceMotionSimpleView: View {
@Environment(\.accessibilityReduceMotion) var reduceMotion
@State private var showCircle = false
var body: some View {
VStack(spacing: 40) {
Button("Apparition du cercle") {
withAnimation(reduceMotion ? nil : .spring(duration: 0.5)) {
showCircle.toggle()
}
}
.buttonStyle(.borderedProminent)
if showCircle {
Circle()
.fill(Color.blue)
.frame(width: 150, height: 150)
.transition(reduceMotion ? .identity : .scale)
}
}
.padding()
}
}
Inclusive design
L’accessibilité ne concerne pas uniquement les handicaps permanents. Tout utilisateur peut, un jour ou l’autre, se retrouver dans une situation temporairement handicapante. Avoir un bras dans le plâtre, utiliser son téléphone en plein soleil, écouter une vidéo sans le son dans les transports, ou subir une mauvaise connexion internet, autant de cas qui limitent ponctuellement l’accès à l’information ou la capacité d’interagir avec l’application. Le design universel, aussi appelé inclusive design, consiste justement à anticiper ces situations pour rendre l’expérience fluide dans tous les contextes. En pensant dès le départ à ces contraintes temporaires, on conçoit des interfaces adaptables et confortables pour chacun, qu’il s’agisse d’une personne en situation de handicap ou simplement d’un utilisateur du quotidien.
Tips
L’accessibilité ne concerne pas uniquement les handicaps permanents. Tout utilisateur peut, un jour ou l’autre, se retrouver dans une situation temporairement handicapante. Avoir un bras dans le plâtre, utiliser son téléphone en plein soleil, écouter une vidéo sans le son dans les transports, ou subir une mauvaise connexion internet, autant de cas qui limitent ponctuellement l’accès à l’information ou la capacité d’interagir avec l’application. Le design universel, aussi appelé inclusive design, consiste justement à anticiper ces situations pour rendre l’expérience fluide dans tous les contextes. En pensant dès le départ à ces contraintes temporaires, on conçoit des interfaces adaptables et confortables pour chacun, qu’il s’agisse d’une personne en situation de handicap ou simplement d’un utilisateur du quotidien.