An article by Gerson Villanueva, Mr. Developer for GlobalLogic Mobile.

When starting the development of an application, one of the biggest concerns of any developer is who will use your application, it will be an audience that understands and speaks your language, or a totally different audience that you were not considering but is where the higher percentage of downloads and use of mobile applications.

There are many factors that decide if an application is successful and profitable, and one of those factors is to provide support to different languages and region through internationalization and localization.

 

Image taken from developer.apple 

Definition of Internationalization and Localization

Internationalization :  process of making an application adaptable and compatible to different languages, regions and cultures. For example:

  • Manage the language of input and output texts.
  • Handle formats of dates, times, numbers and currencies.
  • Manage time zone and dates for the process and handling of information.

Location :  process of translating an application into multiple languages using the previously defined internationalization, thus allowing even to modify the interface

visual y recursos que utiliza la aplicación.

Paso a paso: Tutorial de localización

A continuación vamos a ir paso a paso en el desarrollo de una pequeña aplicación ejemplo donde daremos soporte a dos idiomas: español e inglés. En este ejemplo vamos a utilizar Xcode 8.3 y vamos a poder ver aplicada la internacionalización sobre:

  • Una interfaz visual (StoryBoard).
  • En textos e imágenes.
  • El uso de las clases NumberFormatter y DateFormatter para el formato de números, fechas y monedas.

Comencemos con el ejemplo:

  1. Abrir Xcode, crear un nuevo proyecto dando click en File sobre la barra de menú -> New -> Project

2. Seleccionar la plantilla (template) para el proyecto, en este ejemplo usaremos ‘Single View Application’.

3. En la siguiente pantalla dale un nombre a tu proyecto “I18n Demo” y selecciona “Swift” como lenguaje de desarrollo, por último selecciona el lugar donde deseas guardar el proyecto.

4. Con el proyecto ya creado lo siguiente sería realizar cambios en la UI, utilizando UILabels y UIImageView. Para realizar estos cambios, navega al “Main.storyboard” selecciona el “View Controller” que está creado por default, arrastramos UILabels y un UIImageView desde la lista de componentes y tratamos de ubicarlos tal como se muestra en la imagen de abajo.

Declaración de IBOutlets para los UIControls

5. Para hacer este proceso abriremos por medio de un click el archivo “ViewController.swift” que podemos encontrar en el navegador del proyecto, sobre este archivo agregamos los siguientes IBOutlets después de la declaración de la clase:

  • @IBOutlet var textLabel: UILabel!
  • @IBOutlet var currencyLabel: UILabel!
  • @IBOutlet var dateLabel: UILabel!
  • @IBOutlet var imageView: UIImageView!
 

Luego de la declaración regresamos al “Main.storyboard” para conectar los respectivos outlets.

Después de haber conectado, tendríamos como resultado lo siguiente:

Asignación de valores a los controles definidos

6. Sobre el archivo ViewController.swift definimos una nueva función privada llamada “populateValues”.

private func populateValues() {
    textLabel.text = "Hello world!"
    currencyLabel.text = "10000"
    dateLabel.text = "07/08/2016"
    imageView.image = UIImage(named: "flag")
}

Esta misma la estaremos llamando dentro de la función “viewDidLoad()”. De no tenerla definida, la agregamos.

override func viewDidLoad() {
  super.viewDidLoad()
  populateValues()
}

Usando la opción de agregar archivos nuevos al proyecto, agregaremos las imágenes que serán utilizadas.

Ahora si compilamos y corremos la aplicación deberíamos ver en el simulador una vista como la siguiente:

Hasta este punto no hemos aplicado ningún formato a los valores de fecha y moneda. Para darle ese formato mostraremos cómo podemos utilizar “NSNumberFormatter” para dar formato a el valor según el tipo de moneda y “NSDateFormatter” para dar formato a la fecha. A continuación crearemos estas propiedades debajo de la función “viewDidLoad” en el archivo ViewController.swift:

var currencyFormatter: NumberFormatter {
    let formatter = NumberFormatter()
    formatter.numberStyle = .CurrencyStyle
    return formatter
}
 
var dateFormatter: DateFormatter {
    let formatter = DateFormatter()
    formatter.dateStyle = .MediumStyle
    formatter.timeStyle = .MediumStyle
    return formatter
}

En las funciones anteriores estamos creando instancias respectivas de “DateFormatter” y “NumberFormatter”, y definiendo los correspondientes estilos tales como “CurrencyStyle” para los valores de moneda y “MediumStyle” para los valores de fecha y hora. Ahora necesitamos actualizar la función “populateValues” para utilizar estas propiedades y realizar una correcta visualización de los valores.

private func populateValues() {
  textLabel.text = "Hello world!"
  currencyLabel.text = currencyFormatter.stringFromNumber(10000)
  dateLabel.text = dateFormatter.stringFromDate(NSDate())
  imageView.image = UIImage(named: "flag")
}

Después de este cambio nuevamente compilamos la aplicación y veremos el formato correcto para cada uno de los valores modificados.

Agregando soporte a otros idiomas a la aplicación

Para habilitar y dar soporte a un nuevo idioma, lo primero que tenemos que hacer es agregar un nuevo idioma el proyecto. Esto lo podemos hacer siguiendo los siguientes pasos:

  • Selecciona el archivo del proyecto y luego el “PROJECT” en nuestro caso “I18n Demo”.
  • Después en la pantalla que se muestra ir a la sección de localización, dar click en el signo “+” y elegir el idioma que deseamos agregar.
  • Luego seleccionamos los archivos a los cuales queremos aplicar este idioma.
  • Ahora deberíamos poder ver el idioma que seleccionamos en la lista que se muestra en la sección de localización.

Agregando localización a los controles en el Storyboard

Primero verificaremos que tenemos un archivo “Main.strings (idioma seleccionado)”.

Al seleccionar el archivo creado vamos a ver los diferentes controles que tenemos en el “Storyboard”, con el valor que le hemos definido en el “Storyboard” previamente.

Ahora actualizaremos los textos de los componentes, con la traducción equivalente al idioma que hemos definido.

/* Class = "UILabel"; text = "text"; ObjectID = "5XF-nA-sJp"; */
"5XF-nA-sJp.text" = "text";
/* Class = "UILabel"; text = "Currency:"; ObjectID = "Zeb-RN-eTk"; */
"Zeb-RN-eTk.text" = "Moneda:";
/* Class = "UILabel"; text = "Date:"; ObjectID = "clt-KD-8sY"; */
"clt-KD-8sY.text" = "Fecha:";
/* Class = "UILabel"; text = "Text:"; ObjectID = "iMV-8h-lsZ"; */
"iMV-8h-lsZ.text" = "Texto:";
/* Class = "UILabel"; text = "Image:"; ObjectID = "lEy-1H-FAf"; */
"lEy-1H-FAf.text" = "Imagen:";
/* Class = "UILabel"; text = "currency"; ObjectID = "n3p-9f-cVV"; */
"n3p-9f-cVV.text" = "currency";
/* Class = "UILabel"; text = "date"; ObjectID = "plM-DX-hnq"; */
"plM-DX-hnq.text" = "date";

Probando los cambios de localización en el simulador

Ahora para probar los cambios realizados seguimos los siguientes pasos:

  • Hacer click sobre el “scheme” activo y seleccionar la opción “Edit Scheme…” en el menú que se despliega.
  • Luego seleccionamos la opción “Run” con el ambiente “Debug”, después de esto vamos al tab “Options” y seleccionamos el idioma que agregamos. Este mismo debe ser seleccionado como “Application Language” y “Application Region”.

Ahora si compilamos y ejecutamos la aplicación en el simulador deberíamos ver la aplicación con los textos en español.

 

Internacionalización de textos usando NSLocalizedString

Actualmente el texto “Hello world” no fue traducido al cambiar el idioma de la aplicación, eso se debe a que no hemos definido el archivo de internacionalización. Para agregar un nuevo archivo donde podemos definir los textos en otro idioma seguimos estos pasos:

  • Agregar un nuevo archivo de tipo “Strings” con el nombre “Localizable.strings”
 
  • Después de haber creado el archivo “Localizable.strings”, lo seleccionamos y presionamos el botón “Localize” que se encuentra a mano derecha en el área de “File inspector”, como se muestra en la siguiente imagen.
  • Luego de presionar el botón seleccionamos “Spanish” como idioma. Después de eso nos aseguraremos que en el área de “File inspector” también se encuentre seleccionado “English”, como mostramos a continuación:
  • Ahora al expandir el archivo “Localizable.Strings” deberíamos poder ver dos archivos que se generaron uno para cada idioma seleccionado, en nuestro caso “English” y “Spanish”.
  • Con estos archivos generados empezaremos a definir el texto en cada uno de los idiomas, de la siguiente manera.
En el archivo “Localizable.Strings (English)”
  
HELLO_WORLD = “Hello world!”;
En el archivo “Localizable.Strings (Spanish)”
HELLO_WORLD = “Hola mundo!”;
  • Resta reemplazar en el código fuente por la respectiva traducción de esta manera:

Antes:

textLabel.text = “Hello world!”

Después:

textLabel.text = NSLocalizedString(“HELLO_WORLD”, comment:“Hello world”)

Utilizando “NSLocalizedString” la aplicación sabe automáticamente a qué archivo dirigirse y selecciona el texto con el idioma correcto. Si compilamos y ejecutamos la aplicación lo veremos:

 

Internacionalización de imágenes

Actualmente estamos cambiando el idioma a los textos según el idioma seleccionado, pero la bandera que mostramos como imagen nunca ha cambiado, lo que haremos a continuación es agregar la bandera correspondiente, la cual mostraremos cuando seleccionemos “Spanish” como idioma. Para lograr esto lo que haremos será seleccionar la imagen de la bandera que ya tenemos en la aplicación y presionaremos en el botón “Localize” que ya conocemos de los pasos anteriores, seleccionaremos “Spanish” como idioma y después en la parte de “File Inspector” seleccionaremos los dos idiomas, como se muestra a continuación:

 

Ahora abriremos la carpeta del proyecto en nuestro explorador de archivos y esta debería contener dos carpetas, una “en.lproj” y otro “es.lproj”, como se puede ver en la siguiente imagen, correspondientes a Inglés y Español respectivamente:

Now we will copy the image to the corresponding folder, with the same name of the original image.

Finally we will perform a “clean” to the project and then compile and run the app and the result should be something similar to the following image:

 

You can download the code from  GitHub .