WordPress de A à Z — I comme Internationalisation avec GetText et Poedit

Interface de Poedit

WordPress est livré avec des fonctions pour traduire le Back Office, le thème que vous avez téléchargé sur le web ou celui que vous êtes en train de créer. La traduction de l’administration de WordPress est réalisée à chaque nouvelle version par les membres de WordPress-fr et il est rare que l’on ait besoin d’y mettre la souris (sauf si vous voulez adapter certaines formulations selon la charte éditoriale de votre client). En ce qui concerne les thèmes, deux cas de figure se présentent. Soit le thème est prêt pour chanter l’internationale, soit les chaines de caractères sont écrites en dur dans les fichiers. Dans le premier cas, il suffira de paramétrer le logiciel Poedit pour commencer votre traduction ; dans le deuxième cas, il faudra mettre les mains dans les fichiers de votre thème pour envelopper patiemment les chaines à traduire dans les fonctions adéquates. Voici le sommaire complet des 26 articles de WordPress de A à Z.

Article mis à jour le 18/06/2015

Traduire un site web WordPress

Il existe différentes méthodes pour faire un site multi-langues (ou multilingue). La discussion Pour traduire vite fait bien fait un mini-site en deux ou trois langues sur Google Plus m’a permis en sont temps d’y voir plus clair sur les différentes méthodes possibles, dont voici un exemple :

[pastacode lang= »php » message= » » highlight= » » provider= »manual »]

<?php
$l = array(
    'fr' = array(
        'my_first_string' => 'Mon premier string',
        'my_second_string' => 'Mon second string'
    ),
    'en' = array(
        'my_first_string' => '',
        'my_second_string' => ''
    );
);
?>

[/pastacode]

Les développeurs de WordPress ont opté pour le système gettext mis en place par le projet GNU.

gettext

gettext est la bibliothèque logicielle du projet GNU qui sert à internationaliser des logiciels (i18n), couramment utilisée pour écrire des programmes multilingues. Son utilisation est relativement simple, mais nécessite toutefois un peu de rigueur lorsqu’on a une nouvelle entrée à traduire.

Voici un exemple de titre écrit « en dur » dans les templates qui ne serait pas du tout prêt pour une éventuelle traduction :

<h1>Site navigation</h1>

Voici l’équivalent gettext ready :

<h1><?php _e( 'Site navigation', 'basics' ); ?></h1>

Dans le premier exemple, il faudrait modifier le contenu de la balise <h1> sur toutes les occurrences de la chaine «Site navigation». Dans le deuxième cas, le programme Poedit sera capable de repérer cette même chaine de caractère partout où vous l’aurez utilisée.

Le deuxième paramètre concerne le domaine de traduction, ici «basics». Quant à la fonction _e( $text, $domain ), elle se contente de faire un echo (un affichage en PHP) de la chaine traduite, si elle existe, ou de la chaine entre les guillemets simples si aucune traduction n’a été trouvée.

En plus de cette fonction _e( 'text', 'domain' ), WordPress offre une foultitude de possibilités pour faire face à toutes les situations :

  • __( $text, $domain ) — Retrouve la chaine traduite.
  • _e( $text, $domain ) — Affiche la chaine traduite.
  • _n( $single, $plural, $number, $domain ) — Retrouve la forme plurielle ou singulière de la chaine en fonction du « montant ».
  • _x( $text, $context, $domain ) — Retrouve la chaine traduite selon le contexte gettext.
  • _ex( $text, $context, $domain ) — Affiche la chaine traduite selon le contexte gettext.
  • _nx( $single, $plural, $number, $context, $domain ) — Mélange des fonctions _n() et _x(). Gère les formes plurielles et le contexte.
  • esc_attr__( $text, $domain ) — Retrouve la traduction de $text en échappant les caractères spéciaux — encode : < > &  » ‘ (less than, greater than, ampersand, double quote, single quote) — pour les utiliser en toute sécurité. Si la traduction n’existe pas, ou si le domaine de traduction n’est pas chargé, le texte d’origine est retourné.
  • esc_attr_e( $text, $domain ) — Affiche la traduction de $text en échappant les caractères spéciaux (Encodes < > &  » ‘ (inférieur à, supérieur à, esperluette, guillemets double, guillemets simples) — pour les utiliser en toute sécurité. Si la traduction n’existe pas (ou si le domaine de traduction n’est pas chargé), le texte d’origine est retourné. N’effectue pas de double encodage des entités. Si vous avez besoin de la valeur pour les utiliser dans une fonction PHP, utilisez esc_attr().
  • esc_html_e( $text, $domain ) — Affiche le texte traduit qui a été échappé afin de l’utiliser en toute sécurité dans votre code HTML.
  • _n_noop( $singular, $plural ) — Enregistre des formes plurielles ou singulières dans le fichier POT, sans les traduire.
  • _nx_noop( $singular, $plural, $context ) — Enregistre des formes plurielles ou singulières avec leur contexte dans le fichier POT, sans les traduire.
  • translate_nooped_plural( $nooped_plural, $count, $domain ) — Traduit le résultat de _n_noop() ou de _nx_noop().

A noter que ces fonctions sont des alias de la fonction translate() détaillées dans le fichier l10n.php de votre installation WordPress. La notion de contexte permet de préciser… le contexte d’utilisation du terme. Plus d’information sur Using contexts for solving ambiguities.

Dans la suite de cet article, je ne détaillerai pas le fonctionnement de gettext, d’autant moins que le Site GNU.org propose une documentation très complète. A la place, je vais détailler la mise en place de quelques exemples couvrant l’immense majorité des besoins, ainsi que le paramétrage et l’utilisation de Poedit afin que vous soyez autonome dans la traduction de votre thème préféré.

Utilisation

Voici quelques bouts de code utilisés dans Basics & Beyond Basics montrant les fonctions gettext en situation.

<?php _e( 'Colophon', 'basics' ); ?>

_e() permet d’afficher le texte Colophon, équivaut à echo « Colophon » en PHP.

<?php printf( _n( 'One response to %2$s', '%1$s responses to %2$s', get_comments_number(), 'basics' ),
 number_format_i18n( get_comments_number() ), '<em>' . get_the_title() . '</em>' ); ?>

_n() gère la forme plurielle selon le nombre de commentaires déjà enregistré. La fonction printf() permet de réserver des emplacements formatés dans le texte à traduire pour les variables précisées plus loin.

$basics_description = __('404 page not found: fish is gone, try again');

__() retourne la chaine de caractère sans l’afficher, ce qui permet de l’utiliser dans une fonction sous forme de variable.

Utiliser Poedit

Créez le dossier languages à la racine de votre thème. Téléchargez Poedit et ouvrez-le.

A partir d’un nouveau fichier

Créez un nouveau catalogue Fichier > Nouveau catalogue et remplissez les champs des trois onglets :

  • Informations. Ce qui ne s’invente pas, ce sont les formes plurielles : nplurals=2; plural=n>1.
  • Chemin. Cliquez sur l’icône Créer et renseignez le chemin qui mène à votre thème, par exemple : C:/wamp/www/4design/wp-content/themes/4design.
  • Onglet Mots-clés. Ajoutez les fonctions gettext que vous avez utilisé dans vos templates comme : _, gettext, gettext_noop, __, _e, _c, _n, _x, esc_attr_e, esc_attr__.

Cliquez ensuite sur OK pour enregistrer votre fichier .po (en même temps un fichier .mo est enregistré. Il s’agit du fichier binaire compressé qui sera lu par WordPress pour traduire votre thème.

Poedit devrait analyser les fichiers de votre thème à la recherche des chaines de caractères à traduire, c’est-à-dire celles que vous avez enveloppées dans les fonctions d’internationalisation abordées plus haut.

En cas de problème, vérifiez le chemin d’accès qui mène à votre thème, notamment les barres obliques en fonction de votre système d’exploitation.

A partir d’un fichier .pot

Il est parfois fastidieux de remplir les informations depuis l’interface de Poedit. C’est pourquoi, je préfère partir d’un fichier .pot ne contenant que les en-têtes :

msgid ""
msgstr ""
"Project-Id-Version: basics\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2015-06-18 19:48+0100\n"
"PO-Revision-Date: 2015-06-18 19:50+0100\n"
"Last-Translator: \n"
"Language-Team: Bruno Bichet <infographiste@gmail.com>\n"
"Language: fr_FR\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Poedit-KeywordsList: _;gettext;gettext_noop;__;_e;_c;_n;_x;esc_attr_e;"
"esc_attr__\n"
"X-Poedit-Basepath: .\n"
"Plural-Forms: nplurals=2; plural=n>1;\n"
"X-Poedit-SourceCharset: UTF-8\n"
"X-Generator: Poedit 1.5.7\n"
"X-Poedit-SearchPath-0: C:/wamp/www/4design/wp-content/themes/basics\n"
"X-Poedit-SearchPath-1: C:/wamp/www/4design/wp-content/themes/Clean\n"

Je vous laisse personnaliser ce qui doit l’être. La ligne X-Poedit-KeywordsList devrait contenir tout ce qu’il faut de variantes de la fonction translate() de gettext pour faire face à toutes les situations. Sinon, ajoutez les mots-clés dont vous avez besoin.

Notez les deux dernières lignes X-Poedit-SearchPath-0 et X-Poedit-SearchPath-1 concernent respectivement : le chemin vers le thème parent et vers le thème enfant. N’hésitez pas à ajouter vos emplacements personnalisés, comme les dossiers de plugins, par exemple.

Ouvrez votre fichier .pot et allez ensuite dans le menu Catalogue > Mise à jour depuis les sources. Le plus dur est fait, il ne vous reste plus qu’à traduire ! Si vous ajoutez de nouvelles chaines dans vos templates, il suffira de cliquez sur Catalogue > Mise à jour depuis les sources pour récupérer les nouvelles chaines à traduire.

→ Lire Comment traduire un thème ou plugin WordPress avec Poedit pour plus de détails sur l’utilisation de Poedit.