Skip to content

Latest commit

 

History

History
64 lines (42 loc) · 2.25 KB

File metadata and controls

64 lines (42 loc) · 2.25 KB

Traduction et internationalisation

Haxe

La traduction est encore expérimentale dans le framework Sugoï, elle se base sur Gettext ( fichiers .po .pot .mo), technologie très utilisée dans l'open-source : Wordpress, Libre-office...

Dans config.xml, "lang" permet de définir la langue par défaut, "langs" permet de définir la liste des langues disponibles, "langnames" définit les noms des langues disponibles.

lang="fr"
langs="fr,en"
langnames="Français,English"

Parser le code pour extraire les chaines à traduire

Exécuter cd backend && haxe build.hxml -D i18n_parsing

Une macro Haxe ( code exécuté à la compilation ) parse l'ensemble du code Haxe et des templates à la recherche de fonctions de type _("english text to translate") ou __("english text with ::token::",{token:"variables"}).

Ce parsing va générer un fichier www/lang/allTexts.pot qui liste toutes les chaines à traduire.

Traduction

On va ensuite créer un fichier po pour chaque langue, par exemple texts_fr.po, et mettre une traduction en face de chaque clé (texte en anglais). Le traducteur peut utiliser des logiciels comme PoEdit ou Weblate (app en ligne).

Un fichier po lorsqu'on le sauve, génère un fichier mo, optimisé et compressé, qui sera utilisé par l'app au final. On peut mettre à jour le fichier po à partir du allTexts.pot afin d'ajouter les nouvelles chaînes à traduire.

Templates

Côté templates, Sugoï utilise les templates de référence dans /lang/master/tpl pour traduire les chaines dans chaque langue, par exemple /lang/fr/tpl ( cf doc sur les templates )

Typescript

En TS, la traduction (côté Front en React) est gérée avec la librairie i18next basé sur des fichiers JSON.

La hook useCamapTranslation permet la gestion des traductions.

// <trans-dir>/foo.json
{ "hello": "bonjour" }

// <trans-dir>/nested/bar.json
{ "world": "monde" }
const MyComponent = () => {
  const { tFoo, tBar } = useCamapTranslation({
    tFoo: "foo",
    tBar: "nested/bar"
  })

  return (
    <div>
      <span>{tFoo("hello")}</span>
      <span>{tBar("world")}</span>
    </div>
  );
}

// Affiche : "bonjour monde"