Multi-idioma con React Native de forma automática según el idioma del dispositivo. Compatible con Android e iOS y web

En este tutorial os voy a enseñar cómo añadir soporte multi-idioma en React Native.

Vamos a utilizar la librería i18next (https://react.i18next.com/)

Primero vamos a instalar las siguientes dependencias:

npm install i18next --save 
npm install react-i18next --save

Una vez instaladas, creamos una nueva carpeta en nuestro proyecto llamada language y dentro añadimos dos archivos con el código de país que queramos implementar. En mi caso en.json y es.json.

El contenido de es.json es el siguiente:

{
    "translation": {
      "mis_cursos":"Mis cursos",
      "perfil":"Perfil",
      "ajustes": "Ajustes",
      "buscar": "Buscar",
      "recursos": "Recursos"
    }
  }

Y el de en.json:

{
    "translation": {
      "mis_cursos":"My courses",
      "perfil":"Profile",
      "ajustes": "Settings",
      "buscar": "Search",
      "recursos": "Resources"
    }
  }

Ahora configuramos nuestro archivo de traducciones translate.js dónde vamos a inicializar el módulo de traducción:

import i18n from 'i18next';
import { initReactI18next, useTranslation } from 'react-i18next';
import { Platform, NativeModules } from 'react-native';

import en from './en.json';
import es from './es.json';

//Aqui se añaden los lenguajes que se quieran

i18n.use(initReactI18next).init({
  lng: idioma(),
  fallbackLng: idioma(),
  compatibilityJSON: 'v3',
  resources: {
    en: en,
    es: es,
  },
  interpolation: {
    escapeValue: false // react already safes from xss
  }
});

export default i18n;

export function iniciarTraduccion(){
  const { t } = useTranslation();
  return t;
}

function idioma() {
  try {
    const deviceLanguage =
      Platform.OS === 'ios'
        ? NativeModules.SettingsManager.settings.AppleLocale ||
        NativeModules.SettingsManager.settings.AppleLanguages[0] //iOS 13
        : NativeModules.I18nManager.localeIdentifier;
    var deviceLanguageSplit = deviceLanguage.split("_")[0];
    return deviceLanguageSplit;
  } catch (error) {
    return "en";
  }
}

Ahora voy a explicar el código.

  • Necesitamos importar las librerías de i18n para manejar las traducciones:

import i18n from 'i18next';
import { initReactI18next, useTranslation } from 'react-i18next';

  • También hay que importar el módulo NativeModules para obtener el idioma actual del dispositivo. Y platform para distinguir según plataforma.

    import { Platform, NativeModules } from 'react-native';
  • Ahora se importan los idiomas que hemos creado antes en formato JSON:

    import en from './en.json';
    import es from './es.json';
  • Se inicializa la configuración del módulo de idiomas i18next, se configura el idioma por defecto llamando a la función idioma() qué devuelve el idioma seleccionado en el dispositivo. Luego se añade compatibilidad con JSON v3 para qué funcione en Android.
    Además, se añaden los idiomas que queramos utilizar dentro del objeto resources:
i18n.use(initReactI18next).init({
  lng: idioma(),
  fallbackLng: idioma(),
  compatibilityJSON: 'v3',
  resources: {
    en: en,
    es: es,
  },
  interpolation: {
    escapeValue: false // react already safes from xss
  }
});
  • Y con la función idioma(), se retorna el idioma del dispositivo en el que se está ejecutando la APP. (Solo funciona para iOS y Android):
function idioma() {
  try {
    const deviceLanguage =
      Platform.OS === 'ios'
        ? NativeModules.SettingsManager.settings.AppleLocale ||
        NativeModules.SettingsManager.settings.AppleLanguages[0] //iOS 13
        : NativeModules.I18nManager.localeIdentifier;
    var deviceLanguageSplit = deviceLanguage.split("_")[0];
    return deviceLanguageSplit;
  } catch (error) { 
    var idiomaDevuelve = "es"; //Idioma por defecto
    //Comprueba idioma de navegador:
    if (navigator.language != null) {
      idiomaDevuelve = navigator.language.split("-")[0];
    }
    // alert(idiomaDevuelve);
    return idiomaDevuelve;//Por defecto en navegador
  }
}

Para usarlo tendremos que importarlo de la siguiente forma en nuestro Screen o APP.js:

import React from "react";
import { View, StyleSheet, Text } from "react-native";

import { iniciarTraduccion } from '../language/translate';

const App = () => {

    var t = iniciarTraduccion();

    return (
        <View
            style={styles.container}>
            <Text >
                {t('perfil')}
            </Text>
        </View>
    );
};
export default App ;

const styles = StyleSheet.create({
    container: {
        flex: 1,
                backgroundColor: 'white',
                alignItems: 'center',
    }
});

En este ejemplo se crea una pantalla de texto dónde añadimos la traducción:

  • Primero se importa translate.js qué hemos creado antes:

import { iniciarTraduccion } from '../language/translate';

  • Ahora se inicializa el módulo de traducción, usa la variable t por defecto:

var t = iniciarTraduccion();

Y listo, ya podemos traducir nuestras APPs según el idioma de nuestro dispositivo.

Deja un comentario