In this chapter we want to prepare for the case your app is sold worldwide and you like to offer alternative languages.
Common approaches to this problem involve xml-based platform-dependent string resources. In contrast, we will demonstrate how to translate UI text using C# only.
We will propose two approaches with three major parts each:
- Obtaining the current language code.
This part is identically solved in both approaches using the cross-platform property CultureInfo.CurrentCulture.TwoLetterISOLanguageName. - Initializing the dictionary.
The dictionary is either created at compile time or loaded at runtime. - Accessing vocabularies.
The individual vocabularies are either made accessible as a static class property like Translate.HelloWorld or as an extension method for strings like "HelloWorld".Translate().
13.1 Compiling a dictionary, accessible as static class properties
First we implement a static class Translate providing vocabulary properties for all UI strings and an initialization method allowing to initialize each string depending on the current system language. In case the languageCode parameter is not recognized, the Initialize method is called recursively with the default language English.
public static class Translate
{
public static string HelloWorld { get; private set; }
public static string NowInThreeLanguages { get; private set; }
public static void Initialize(string languageCode)
{
switch (languageCode) {
case "en":
HelloWorld = "Hello world!";
NowInThreeLanguages = "Now in three languages!";
break;
case "de":
HelloWorld = "Hallo Welt!";
NowInThreeLanguages = "Jetzt in drei Sprachen!";
break;
case "fr":
HelloWorld = "Bonjour le monde!";
NowInThreeLanguages = "Maintenant en trois langues!";
break;
default:
Initialize("en");
break;
}
}
}
The initialization method is called at the beginning of the App() constructor. It uses the cross-platform property TwoLetterISOLanguageName, representing the current language setting of the executing device.
Translate.Initialize(CultureInfo.CurrentCulture.TwoLetterISOLanguageName);
Now we can create a simple MainPage with a Label. Instead of initializing the Text property with a string like "Hello world!" we use Translate.HelloWorld.
MainPage = new ContentPage {
Content = new Label {
Text = Translate.HelloWorld + "\n" + Translate.NowInThreeLanguages,
HorizontalTextAlignment = TextAlignment.Center,
VerticalOptions = LayoutOptions.CenterAndExpand,
},
};
Advantages of extension methods for vocabularies
- The reference to the Translate class is short and intuitive. It’s like a command: Translate “Hello world”!
- Once all vocabulary is defined, you get automatic code completion, which is very handy for large dictionaries and long property names.
- You can easily refactor property names to reflect their content. If, for example, you changed the displayed text to “Hello, dear app user!”, you can rename the corresponding property to HelloDearAppUser.
- Although the property definitions and initializations in the Translate class are rather lengthy, it is trivial code that can even be generated from other file formats like plain text or spreadsheets.
Advantage of creating the dictionary at compile time
- The translation is fast. Since the dictionary is built at compile time, displaying a translation is very cheap.