Last Updated: 2021-23-11

¿Qué es la internacionalización?

La internacionalización es una extensión que se realiza sobre una aplicación para brindar soporte a otros idiomas. Muchas aplicaciones móviles pueden tener un público variado alrededor del mundo, y si se desea brindar una experiencia igualmente agradable para todos los usuarios, es necesario diseñar la aplicación pensando en los idiomas que esta debe soportar.

Conviene que una misma aplicación sea distribuida globalmente para todos, sin necesidad de manejar distintas versiones según el destino de distribución. Por lo anterior, Android brinda herramientas para hacer que una misma aplicación soporte más de un idioma sin requerir cambios estructurales significativos.

¿Qué construirá?

Al final de este tutorial usted tendrá:

¿Qué aprenderá?

Al desarrollar este tutorial aprenderá:

¿Qué necesita?

Android busca que este proceso de internacionalización sea bastante estándar sin importar el tipo de proyecto. Por este motivo, existen varios lineamientos a tener en cuenta.

Consideraciones generales

Algunas aplicaciones deben responder a los cambios de idioma por medio de configuraciones locales de la aplicación, mientras que otras deben tener en cuenta el contexto y consultar, por ejemplo, el idioma del dispositivo. Esto genera cambios en el diseño y en la implementación de la aplicación, puesto que requiere tener en cuenta el lenguaje utilizado para describir elementos gráficos y dar información por medio de textos. Además, es importante tener en cuenta, cuando se va a internacionalizar una aplicación, que algunos recursos pueden impactar la estructura y apariencia de la interfaz en la cual son renderizados. Un ejemplo claro de esta situación es la cantidad de letras que se requieren para representar una misma palabra o frase en distintas lenguas, lo cual puede hacer que la apariencia visual de los componentes gráficos sea inconsistente.

Otro aspecto importante a tener en cuenta con la internacionalización está relacionado con las particularidades de ciertas lenguas, las cuales se escriben en el sentido derecha a izquierda, mientras que la gran mayoría lo hacen en el sentido opuesto. En estos casos, puede haber problemas en el momento de renderizar cadenas de texto que se consumen desde variables.

Recursos de la aplicación

Las guías de buenas prácticas sobre el desarrollo de aplicaciones de Android indican que las cadenas literales de texto, que se van a utilizar como parte de la aplicación, deberían ser extraídas a los archivos de recursos del proyecto. Esto permite que el código sea mantenible y adaptable a distintos idiomas por medio de los mecanismos de internacionalización.

Así, es usual ver que las aplicaciones contienen las cadenas de texto que se utilizan en la interfaz para presentar indicaciones o etiquetar contenido en el archivo res/strings.xml. Así mismo, otros tipos de recursos también son almacenados en los subdirectorios del directorio res/. Android soporta la existencia de otros archivos de recursos adicionales dentro del directorio res/ para otras configuraciones regionales. Para esto, se puede crear varios directorios, cada uno con un nombre que tenga el siguiente formato:

<resource type>-b+<language code>[+<country code>]

Donde <resource type> corresponde al mismo nombre del directorio general, que indica el tipo de recursos (como values, mipmap, drawable, entre otros). Por su parte, <language code> corresponde al código de idioma, típicamente de dos letras. Finalmente, se puede incluir de forma opcional al ubicar el código de un país específico en donde se encuentra <country code>.

Estos recursos son accedidos desde el código fuente con la clase android.content.res.Resources, por medio de un identificador asignado con la sintaxis

R.<resource type>.<resource name>

El acceso a los recursos se hace eligiendo automáticamente la fuente correspondiente a la configuración local en estos casos.

Soporte RTL

Como se mencionó anteriormente, es importante tener en cuenta que algunos idiomas utilizan un sistema de escritura de derecha a izquierda (RTL), y estos pueden ser elegidos para la configuración regional de su interfaz gráfica, o también para los contenidos incluidos dentro de la aplicación.

Para brindar una experiencia consistente a los usuarios que utilizan configuraciones de este tipo es importante:

  1. Modificar los aspectos necesarios del diseño de la interfaz gráfica para las configuraciones regionales con escritura de derecha a izquierda. Esto puede incluir alineaciones, tamaños y órdenes de los widgets.
  2. Detectar y declarar la dirección de los datos textuales que se muestran en mensajes con formato. Es posible que al mostrar cadenas de texto concatenadas por medio de formateo existan errores en la orientación de los datos que acceden como parámetro. Esto se logra con el método unicodeWrap() de la clase BidiFormatter, el cual detecta la dirección de una cadena y se une con caracteres unicode que declaran la dirección.
  3. Declarar en la etiqueta application del archivo de manifiesto AndroidManifest.xml la propiedad android:supportsRtl="true".
  4. Utilizar los atributos de alineación de la interfaz start y end en lugar de left y right. Existen varias propiedades de los elementos gráficos de la interfaz que permiten configurar alineaciones, márgenes, paddings, gravedad, entre otras; y aceptan los conceptos de izquierda y derecha estricta. Todas estas propiedades tienen una contraparte que acepta los conceptos de inicio y final de la orientación para adaptarse a configuraciones locales distintas.

Para este tutorial, utilizará la misma aplicación que se ha venido trabajando a lo largo de los anteriores tutoriales. En el caso de este tutorial, se va a incluir soporte para otras lenguas adicionales al español. El código de la aplicación está disponible en el siguiente repositorio: https://github.com/TheSoftwareDesignLab/MISW4104-Ejemplos/tree/main/starters/CL19-intl.

Descargue el proyecto a su máquina como lo ha hecho en tutoriales anteriores, e importe en Android Studio el contenido del directorio CL19-intl. Es necesario que genere un archivo .APK de este proyecto, de la misma forma como lo hizo en tutoriales anteriores.

En este repositorio, también podrá encontrar el archivo .jar de ITDroid. Este fue generado a partir del proyecto alojado en https://github.com/TheSoftwareDesignLab/ITDroid, con unos cambios puntuales para asegurar su funcionamiento en Windows para este tutorial. Este archivo lo necesitará para ejecutar las pruebas de internacionalización en el siguiente paso.

Para poder ejecutar dichas pruebas a partir de este archivo .jar, se agregaron archivos al repositorio, cuyo uso se justifica en un paso posterior.

Para este tutorial usted utilizará el proyecto ITDroid para probar el soporte a la internacionalización de aplicaciones Android.

Crear una cuenta en IBM watson

Dado que ITDroid requiere de un API KEY de la herramienta de traducción de IBM Watson para generar los archivos de recursos de strings traducidos, es necesario que comience por crear una cuenta personal de IBM. Para esto, siga las siguientes instrucciones:

  1. Acceda al enlace: https://www.ibm.com/co-es/watson.
  2. En la parte superior derecha de la página encontrará un ícono de una persona, el cual contiene las opciones del perfil. Seleccione la opción "Iniciar Sesión".
  3. En la página de inicio de sesión, haga clic en el enlace "¿No tiene ninguna cuenta? Crear un IBMid".
  4. Complete la información del perfil y haga clic en el botón "Next".
  5. Confirme su dirección de correo con el código que llegó a su bandeja de entrada y presione el botón "Create account".
  6. Seleccione la opción "Mi IBM" en el menú de la parte superior derecha.
  7. Haga clic en el botón "Ver catálogo" y busque el producto "Watson Language Translator".
  8. Presione el botón "Empiece gratis" de la parte superior derecha.
  9. Inicie sesión nuevamente con su correo electrónico.
  10. Indique que está de acuerdo con las condiciones de Privacidad de la cuenta de IBMid para continuar.
  11. Ahora, desde la consola de IBM Cloud, presione el botón "Crear recurso", y busque el servicio "Language Translator".
  12. Cree el recurso en la versión gratuita.
  13. En la pestaña "Gestionar", seleccione la opción Acceso (IAM) del menú. En el menú desplegado en la parte izquierda, seleccione la opción "Claves de API".
  14. Presione el botón "Crear clave de API" y asigne un nombre cualquiera a la llave.
  15. Copie el valor de la llave que se acaba de generar.

Incluir credenciales en el proyecto

Si explora el código fuente de ITDroid, podrá ver en el archivo IBM/IBMTranslator.java que se utiliza un API KEY configurado por medio de una variable de entorno y consultada con la librería Dotenv de Java.

De esta forma, es necesario que usted configure el entorno local en su dispositivo con la variable de nombre API_KEY, y el valor que IBM le asigna a su cuenta. Este valor lo debió guardar en el portapapeles desde el último paso de la sección anterior. Cree en el directorio CL19-intl un archivo llamado .env, el cual permitirá la definición de variables de entorno. En la primera línea de este archivo agregue la variable API_KEY=<Valor tomado de IBM>.

Preparar el ambiente para ejecutar ITDroid

En primer lugar, debe tener en cuenta que ITDroid funciona solo en emuladores. Con esto en mente, es necesario que haya configurado previamente un dispositivo virtual en su máquina. En este tutorial se recomienda utilizar el emulador Nexus_6_API_27, dado que este fue el modelo y nivel de API utilizado para probar las herramientas ITDroid y RIP en el momento de su desarrollo.

Para poder utilizar ITDroid, también es necesario que en el archivo .env que creó previamente (o en una variable de entorno), declare una variable que indique la ubicación de la herramienta AAPT (Android Asset Packaging Tool), la cual permite empaquetar y compilar los recursos de una aplicación de Android. Esta se encuentra ubicada por lo general en el directorio build-tools, en la ruta del SDK.

[IMPORTANTE: las siguientes instrucciones son necesarias únicamente si desea generar un archivo .jar para ITDroid].

Si desea generar el archivo .jar para ITDroid en su máquina, es necesario que tenga Maven Instalado. Para probar si ya lo tiene instalado en su máquina, abra una terminal y ejecute el siguiente comando:

mvn -v

Este comando debería mostrar la versión de Maven instalada en la máquina. En caso de no obtener una respuesta de este comando, es necesario que haga la instalación desde cero. Para esto, descargue el archivo binario del siguiente enlace: https://maven.apache.org/download.cgi. Una vez tenga el archivo comprimido en su máquina, descomprima su contenido y siga las instrucciones del siguiente enlace: https://maven.apache.org/install.html.

Recuerde que, adicionalmente, es necesario que cuente con el JDK instalado y que este sea referenciado por la variable de entorno JAVA_HOME.

Luego de esto, descargue el código del proyecto de ITDroid por medio del manejador de versiones Git con el siguiente comando:

git clone https://github.com/TheSoftwareDesignLab/ITDroid.git

Luego de que el proyecto esté descargado en su máquina, ubíquese en el directorio del proyecto desde su terminal y ejecute los siguientes comandos para empaquetar el proyecto en un archivo .jar.

mvn clean
mvn package

Ejecutar ITDroid

Usualmente, antes de ejecutar ITDroid, es necesario modificar el archivo settings.properties para configurar el listado de idiomas que serán tenidos en cuenta en la ejecución para el proyecto. No obstante, en este caso se aceptarán los valores por defecto, que incluyen Español, Hindi, Árabe, Ruso, Portugués, Francés e Italiano.

Una vez se completó el comando de empaquetado en un .jar, la ejecución de ITDroid se realiza por medio de un llamado a este archivo .jar con el siguiente comando:

java -jar ITDroid-1.0.0.jar <APKPath> <AppPackage> <ExtraLibsFolder> <settingsDir> <amountUnstranslatable> <OutputFolder> <emulatorID>

Donde los argumentos corresponden a lo siguiente:

  1. APKPath: la ruta al APK de la aplicación.
  2. AppPackage: el nombre del paquete utilizado para identificar la aplicación de Android.
  3. ExtraCompFolder: la ruta al directorio que contiene las librerías extra utilizadas por ITDroid. Corresponde al directorio extra del proyecto que descargó.
  4. settingsDir: la ruta al archivo de configuración settings.properties. Corresponde al directorio raíz del proyecto que descargó.
  5. amountUntranslatable: número entero positivo que define la diferencia aceptada entre la cantidad de Strings internacionalizadas para considerarse como traducida.
  6. OutputFolder: la ruta al directorio donde se almacenarán los resultados.
  7. emulatorID: el identificador del emulador donde se va a explorar la app. Este identificador se puede consultar desde la pestaña AVD manager de Android Studio.

Para poder ejecutar este comando, es necesario que antes, genere el APK de la aplicación que se va a analizar. Si no lo ha hecho aún, desde la ventana de Android Studio donde importó el proyecto de la aplicación KotlinI18n, seleccione la opción Build > Build Bundle(s) / APK > Build APK. Espere un par de minutos a que se genere el archivo APK y consulte luego el directorio app/build/outputs/apk/debug del proyecto. Allí encontrará el archivo APK resultante. Ubíquelo en el directorio raíz de ITDroid y ejecute el siguiente comando:

java -jar ./ITDroid-1.0.0.jar ./app-debug.apk com.example.jetpack_codelab ./extra/ ./ 0 ./results/ Nexus_6_API_27

Al comenzar la ejecución, podrá ver que se procesa el APK para detectar la presencia de Hardcoded Strings. Esto es, cadenas de texto que sean instanciadas directamente en la aplicación, en lugar de utilizar las referencias al archivo res/values/strings.xml. El reporte de estos Strings se encontrará en results/hcs.txt, como lo indica la terminal, cuyas primeras líneas deben verse de la siguiente forma:

Después de este paso, comienza un proceso de detección de los idiomas soportados por la aplicación y declarados en el archivo settings.properties que se descargó del repositorio. En este archivo, se pueden ver varias líneas comentadas con el carácter #, y la declaración de una lengua predeterminada y los diferentes locales que representan las lenguas a las cuales se quiere traducir la aplicación. El contenido es el siguiente:

defaultLng=en
#en                =        English
es                =        Spanish
#hi                =        Hindi
ar                =        Arabic
ru                =        Russian
#pt                =        Portuguese
#fr                =        French
#it                =        Italian
# Not available for IBM Watson
#zh-rCN        =        Chinese
#ms                =        Malay
#bn                =        Bengali

En su terminal podrá ver que se indican los idiomas seleccionados en este archivo, mostrando cuáles traducciones están presentes y cuáles faltan, como se muestra a continuación:

Siempre que exista un idioma cuya traducción no exista aún, ITDroid hará la traducción de los recursos del archivo strings.xml para agregar los equivalentes del mismo, y así poder soportar los otros locales indicados. Este proceso se muestra también en la terminal de la siguiente forma:

Donde se muestra la ubicación del archivo de Strings temporal para el modelo de traducción actual, y se muestra el resultado de cada petición de red que se hace al API de IBM Watson (también podrá detectar por este medio problemas de API KEY o servicio no disponible).

Después de esto, hay un proceso de exploración de la aplicación para descubrir los estados de la misma, y compararlos con los estados que se pueden explorar dentro de la misma aplicación cuando se cambia el idioma, de forma que se buscan inconsistencias que pudieron ser generadas por la traducción a varios idiomas.

Luego de esta exploración, se generan resultados en el archivo results/report.json. Para poder ver un reporte web que resume los resultados de este archivo JSON, copie este archivo, y péguelo en el directorio webreport/report. Luego de esto, abra el archivo index.html en su navegador, ingresando por medio de un servidor local que sirva dicho directorio de archivos.

Podrá ver que existe un reporte como el que se muestra a continuación:

En la primera sección, se muestran los parámetros de ejecución de ITDroid con el comando mencionado en pasos anteriores. Posteriormente, se muestra la cantidad de Hardcoded Strings encontradas y los problemas gráficos totales encontrados. Esto seguido de los estados y transiciones encontrados en cada idioma donde se realizó la exploración automática de la aplicación, reportando también las inconsistencias de estados y transiciones con respecto a la versión original.

En el paso anterior, usted ejecutó la herramienta ITDroid para realizar una prueba de internacionalización. Como resultado de esta prueba, se generaron traducciones del archivo de strings en el directorio temp/res. Podrá ver que existen varios directorios con el formato mencionado al inicio del tutorial, como values-ar, el cual contiene un archivo strings.xml y un archivo plurals.xml. Estos archivos generados sirven de insumo para agregar el soporte a los nuevos locales en su proyecto. Copie y pegue sus contenidos en el proyecto que descargó.

Además de esto, es necesario que tenga en cuenta que, por ejemplo, el idioma árabe se escribe en el sentido derecha a izquierda, contrario a muchos otros idiomas. Para renderizar esto adecuadamente en Android, es necesario que su aplicación declare de forma explícita que soporta RTL, como se mencionó al inicio de este tutorial, y que los layouts estén correctamente configurados de forma que los componentes se ubiquen también en este sentido. Agregue la propiedad supportsRTL en la etiqueta application del archivo AndroidManifest.xml, de forma que se vea así:

<application
   android:allowBackup="true"
   android:icon="@mipmap/ic_launcher"
   android:label="@string/app_name"
   android:roundIcon="@mipmap/ic_launcher_round"
   android:supportsRtl="true"
   android:theme="@style/Theme.Jetpackcodelab">

Si ejecuta la aplicación, y cambia el idioma del emulador a árabe (ar), podrá ver que la disposición de algunos de los componentes gráficos se acomodan en el sentido derecha a izquierda. Sin embargo, los textos no se alinean de la misma forma. Para esto, es necesario que modifique los archivos collector_item.xml, album_item.xml y comment_item.xml para que todas las etiquetas de tipo TextView tengan las siguientes propiedades:

android:textDirection="locale" 
android:textAlignment="gravity"

Vuelva a ejecutar la aplicación (con el locale ar activo), y podrá ver que ahora todos los textos de los RecyclerView se ubicarán en el sentido correspondiente de forma automática.

En este caso, el texto mostrado en las vistas se consume de un API que tiene la información en español, originalmente. Para agregar soporte a otros idiomas con respecto a estos datos, habría que hacer una modificación en el backend para mapear dicha información con sus traducciones correspondientes.
Existen otros casos en los que la aplicación muestra información de cadenas de texto que combinan un recurso de texto local con una variable. Cuando esto sucede, el texto de la variable puede generar problemas para los idiomas RTL, ya que es necesario que dicha variable sea correctamente formateada con respecto a la configuración actual del dispositivo. Si desea saber cómo manejar estos casos al momento de internacionalizar su aplicación, se recomienda leer la siguiente guía: https://developer.android.com/training/basics/supporting-devices/languages#FormatText.

¡Felicidades!

Al finalizar este tutorial, pudo familiarizarse con las guías de internacionalización de una aplicación. Así mismo, pudo explorar el contenido de una aplicación con soporte a la internacionalización. Finalmente, pudo ejecutar una prueba de internacionalización sobre una aplicación haciendo uso de la herramienta ITDroid.

Ahora podrá internacionalizar sus aplicaciones y validar que hayan sido correctamente traducidos todos sus recursos por medio de la herramienta ITDroid.

Créditos

Versión 1.1 - Noviembre 23, 2021

Juan Sebastián Espitia Acero

Autor

Norma Rocio Héndez Puerto

Revisora

Mario Linares Vásquez

Revisor