Text extraction tools for macOS and iOS app localization Jul 10 2019
Localization is not only translating content but adapting the content to culture, language and customs. This makes our apps more intuitive and engaging for our users. We can localize not only text, but we can also localize images, sounds, shortcuts, etcetera. A crucial part of localization is obtaining the text to be localized. In this post, I'll focus on text extraction for localization. This post is not a general introduction to localization of apps, but when you finish reading the post, you'll have a better understanding of crucial aspects of localization and can research other specific topics that you are interested in. As always, check my notes at the end of the posts where I add links and notes to explore related topics, let's begin.
Table of Contents
Prepare your app for localization
If we want our app to support multiple languages, we need to prepare our app for localization. You might find the steps easy if you do it regularly, but if you seldom do work on your apps translations, it'll be easy to forget some small detail. You can bookmark this post and come back to check for any information that will help you.
The good news is that once you finish preparing the texts on your app for localization, they can easily be extracted and you can generate files that you can share with the person that is helping you with the translation.
Let's have a look at some generalities on how to prepare your app. We'll start with Storyboards and xib
files, the process is simple.
Preparing Storyboards and xib
s for localization
If you are using Storyboards or custom xib
s (Interface Builder), you have it easy. By default, all apple components support localization. The only task you need to do is to make sure you add the Localizer hint
for every component (label, button or text). You can find the Localizer hint
in the identity inspector in Xcode (Alt+Command+3).
That’s it for Storyboards and xib
files, now let's see how to prepare our code when we declare our views in code.
Preparing our code for localization
If you have created your views in code, go through all your code and make sure all the text that is being presented to the user goes through NSLocalizedString
. This is easier explained with an example, imagine we have the following code:
1
2
3
4
5
6
let button = UIButton(frame: CGRect(x: 100, y: 100, width: 100, height: 100))
button.backgroundColor = .red
button.setTitle("Profile", for: .normal)
button.addTarget(self, action: #selector(buttonAction), for: .touchUpInside)
self.view.addSubview(button)
Look at the title, the text is hardcoded so that button title will always be "Profile" no matter the user preferences in language. To prepare the code for localization use NSLocalizedString
, let's see the following example:
1
2
3
4
5
let button = UIButton(frame: CGRect(x: 100, y: 100, width: 100, height: 100))
button.backgroundColor = .red
let title = NSLocalizedString("profileButtonTitle", comment: "This is the button the user sees when he wants to see its profile")
button.setTitle(title, for: .normal)
button.addTarget(self, action: #selector(buttonAction), for: .touchUpInside)
Notice that the key we are using to identify the localized string is profileButtonTitle
this will be the key in the translation file not necessarily the text that will appear to the user.
If the key is not defined in the translation file for a specific language, it will show the value in the base.lproj
. If it doesn't exist in the base language dictionary, it will display the key.
Now that we have all our text ready for exportation in our Storyboards, Interface builder files (xib
s) and code, we can extract the text and share the files with a translator or someone that will help us with the localization. To generate a file that our translators can work with, we need to extract a list of all the text that needs a translation. I'm going to show you how to use the tools from the command line, it is faster, and you can create scripts to automate the tasks (e.g. you could add your script as a hook in your git workflow to run after you do a commit).
Tools for extracting text to be translated
If you want to extract all the text to be localized, you can use the xcodebuild
command to do it.:
1
$ xcodebuild -exportLocalizations -localizationPath ~/Desktop/my_project_localizations -project ~/Work/current_project/project.xcodeproj -exportLanguage es -exportLanguage en
This will get you all the text you want to translate in XLIFF
format. You can then give those files to your translator and work on the translation of your app going back and forth, you exporting and importing and the translator working on your XLIFF files.
That is the preferred way to obtain the text for translation. If you wish to get the translation texts of individual xib
files or source files, you will use other tools. Let's first see how to do it for xib
files and Storyboards, and then for source files.
Working with xib
files and storyboards
To obtain all the text to be translated from a xib
file use ibtool
, this will generate a file that you can send to your translator. You would use a command similar to the following:
1
$ ibtool YourFComponent.xib --generate-strings-file YourComponent_new.strings
This will generate a strings
file that contains the texts you would want to translate, you can generate the files manually and then send them to your translator. The only problem is that you'll have to merge the changes from the translator to the strings
file manually (using a difftool that is).
For storyboards, the process and tool are the same, but we use our storyboard file instead of the xib
. For example:
1
$ ibtool Main.storyboard --generate-strings-file YourMainStoryboard_new.strings
And that will generate the file YourMainStoryboard_new.strings
file. That’s it for xib
files and storyboards, let's check how to obtain the text from source files.
Working with source files
If we want to only extract the translated text for source files, we can use the genstrings
tool to do this.
1
$ genstrings -o directory_to_store_strings_files/ the_file_we_want_to_parse.swift
After running that command, you'll obtain a Localizable.strings
file inside the output directory (directory_to_store_string_files
in our example). You can then send the Localizable.strings
file to your translator. We have the same problem that we had with xib
and ibtool
, you'll be in charge of doing the merge of the translations.
And that is it, those are the main ways to extract the text to be translated from our Apps.
Final thoughts
If we create the habit of using NSLocalizedString
and adding Localazer hint
in our source-code and interface builder(and storyboards) respectively, we will make the process of localization much more easy for us. We could have exported the localization using Xcode. If you want to go with that is an option, just navigate to your Project info by selecting your project icon from the File Navigator, then click on Editor > Export For Localization…
this will generate the files to send to your translator. To import the translations, go to Editor > Import Localizations
in the main menu when you are viewing your Project info.
I like using the command line, it gives me more flexibility and the ability to create scripts to automate this type of tasks. As I mentioned before we could create a git hook that runs a script that is in charge of exporting our translations, check if there are any differences (using a diff tool) and if there are any new required translations send an email. That is beyond the scope of this post, but if you think it is useful you can send me a message, and I'll write a post explaining how to do that.
As always I hope this was useful, if you have any comments, questions or feedback let me know.
Related topics/notes of interest
- A general tutorial on Localization of apps. It goes from beginning to end.
- Apple's documentation on Localization and here. Lots of information but sometimes hard to go through all the content.
- AppleGlot is a Localization tool created by Apple, you can download the app from Apple's website it includes a user manual.
- XLIFF is the name of the file format for the translations generated from Xcode, you can read more about the format here
- If you want to localize Property List files, you can check the documentation here. This would be the technique you'll use to Localize your Apps name in the
info.plist
. - An interesting Storyboard
xib
localization article on how to use Runtime Attributes to declare the translation strings. - Use named images with combination of
NSLocalizedString
to localize Images. question in SO