Passer son design system en RTL
#19 - Ou comment j'ai retourné toute mon app comme un miroir
Ola !
Bienvenue dans cette 19ᵉ édition de Founder Naked.
La semaine dernière, je te parlais de la refonte de mon usine de traduction. Cette semaine, on reste dans la même veine, parce que traduire le texte, ce n’est que la moitié du chemin. En arabe, en hébreu ou en farsi, l’écriture va de droite à gauche, et c’est toute l’interface qui doit se retourner comme dans un miroir.
Je t’explique dans cette édition comment j’ai adapté tout mon design system.
Si ce n’est pas déjà le cas, tu peux aussi :
Me suivre sur Linkedin, où je publie des posts complémentaires,
Découvrir les services que je propose, notamment dans le secteur de la finance…
… mais pas encore découvrir Licorn, ma nouvelle boîte.
Allez, c’est parti !
Au programme
Pourquoi traduire ne suffit pas
Le piège : maintenir deux interfaces
Ce que mon framework fait pour moi (et ce qu’il ne fait pas)
Comment je m’assure que rien ne casse
Comment t’en inspirer
Pourquoi traduire ne suffit pas
Mettons que j’aie bien traduit ma page d’accueil en arabe (cf. l’édition précédente). Super. Sauf que si je l’affiche telle quelle, c’est la cata : le texte arabe se lit de droite à gauche, mais mes boutons, mes icônes, mes marges, mes menus… sont tous restés « à l’endroit », calés à gauche.
Le terme technique, c’est le RTL (right-to-left, de droite à gauche), par opposition au LTR (left-to-right) qu’on utilise en français ou en anglais.
Concrètement, passer en RTL, ça veut dire : tout ce qui était à gauche passe à droite, et inversement. Le menu, les flèches, l’alignement du texte, l’ordre des éléments… L’interface entière doit devenir le miroir d’elle-même.
Le piège : maintenir deux interfaces
La pire idée serait de dupliquer tout mon design system (ma bibliothèque de composants réutilisables) : une version « normale » et une version « miroir ». Ce serait l’enfer à maintenir — chaque bouton, chaque composant, en double.
C’était hors de question pour moi. Surtout que je vise 210 langues, dont plusieurs en RTL (arabe, hébreu, farsi, ourdou…). Mon obsession, comme d’habitude : une seule source de vérité.
Ce que mon framework fait pour moi (et ce qu’il ne fait pas)
Point très important à avoir en tête : je ne pars pas d’une feuille blanche. Je m’appuie sur des outils existants, et que je trouve fiables et bien pensés, et une bonne partie du boulot est déjà géré par eux. De mon côté, je veille surtout à bien les utiliser, et je comble les manques qu’ils ne couvrent pas, ou pas assez bien à mon goût.
Mes deux fondations :
Ark UI : la librairie de composants sur laquelle repose mon design system. Elle gère nativement la notion de direction : je lui dis « on est en arabe », et les comportements de ses composants (menus, popovers, etc.) s’adaptent. Un truc que j’ai appris à mes dépens : il ne suffit PAS de coller un
dir="rtl"sur une balise et d’espérer ; il faut vraiment passer par le mécanisme prévu par le framework.Panda CSS : mon moteur de styles. C’est lui qui me permet d’écrire mes styles de façon « logique » plutôt que « physique ».
Qu’est qu’un style “logique” ?
C’est LE truc qui évite de tout dupliquer. Au lieu d’écrire « à gauche », j’écris « au début ». Et le « début », en français c’est la gauche… mais en arabe, c’est la droite. Le navigateur fait le miroir tout seul.
Au lieu d’écrire… (physique) ➡️ J’écris… (logique)
marge à gauche ➡️ marge au début
texte aligné à gauche ➡️ texte aligné au début
collé en haut à gauche ➡️ collé en haut au début
Résultat : 90 % du miroir se fait « automatiquement », juste en écrivant mes styles correctement.
Restent les 10 % qu’aucun framework ne devine à ta place :
Les icônes directionnelles : une flèche « suivant » qui pointe à droite doit pointer à gauche en arabe. Là, je dois explicitement la retourner (un effet miroir).
Les animations : un panneau qui glisse depuis la gauche doit glisser depuis la droite. J’inverse le sens à la main.
Le contenu mixte : un chiffre ou un nom propre latin au milieu d’un texte arabe. Il faut gérer la cohabitation des deux sens dans la même phrase.
Comment je m’assure que rien ne casse
Avec un design system qui grandit, le risque, c’est qu’un composant oublie le RTL et casse l’affichage en arabe sans que personne ne s’en rende compte.
Ma parade : un script d’audit que je lance d’une seule commande (pnpm rtl:audit), et qui me dit : « ce composant n’a pas prouvé qu’il s’affiche correctement en miroir ».
Concrètement, il vérifie deux choses :
Chaque composant doit avoir une démo en arabe dans mon catalogue (Storybook), avec du vrai texte arabe — pas du faux latin. Parce que tu ne vois les vrais problèmes qu’avec du vrai contenu.
Aucun composant ne doit utiliser un style « physique » interdit (genre « marge à gauche » en dur) qui casserait le miroir.
Au moment où j’écris ces lignes, mon audit n’est pas encore tout vert. Il me pop une alerte sur ma « RecipeCard » qui n’a pas encore sa démo arabe, et sur deux-trois styles physiques qui traînent. C’est exactement le but : le chantier n’est jamais fini ni figé, il vit, et chaque nouveau composant doit prouver son rendu miroir pour que l’audit passe au vert avant de commit.
Comment t’en inspirer pour ta propre app
Pense le miroir au niveau du composant, pas de la page. Si chaque brique sait se retourner, la page se retourne toute seule.
Écris « début / fin » plutôt que « gauche / droite ». Les propriétés logiques, c’est 90 % du boulot fait automatiquement.
Appuie-toi sur ton framework, mais connais ses limites. Dans mon cas, ArkUI gère les comportements, PandaCSS les styles ; il me reste les icônes et les animations.
Teste avec du vrai contenu. Du vrai arabe ou autre langue RTL, pas du Lorem Ipsum.
Automatise la vérif. Un humain oublie ; un script d’audit te rappelle qu’il faut que tu sois carré.
Le mot de la fin
Le RTL, c'est typiquement le genre de sujet « invisible » : quand c'est bien fait, personne ne le remarque ; quand c'est bâclé, c'est immédiatement repoussant pour la moitié de tes utilisateurs potentiels. Et avec mon ambition d'adresser le monde entier, je ne pouvais pas faire l'impasse.
Si tu ne me connais pas : je m'appelle Yoann, je construis Licorn, et je documente tout ici, sans bullshit.
Bonne semaine.
Yoann






