Flutter Localization

Learn via video courses
Topics Covered

Overview

In our interconnected world, mobile apps have the potential to reach users from diverse linguistic backgrounds. Flutter localization empowers developers to adapt their apps to different languages, regions, and cultural norms. By seamlessly translating text strings, adapting UI layouts, and customizing date, time, and currency formats, Flutter localization enables apps to provide tailored experiences to a global audience. In this article, we'll explore the importance of Flutter localization, learn how to implement it effectively, and discover the techniques for reaching a wider user base in international markets.

Introduction

Creating mobile applications that cater to a global audience requires more than just translation. It involves adapting the user interface, handling date and time formats, and supporting plurals and selects based on different languages and regions. Flutter localization offers a comprehensive solution for developing multilingual apps with ease. By setting up an internationalized app and utilizing localization packages, such as intl and flutter_localizations, developers can seamlessly integrate their own localized messages, placeholders, and handle complex language-specific features. In this article, we'll explore the technical aspects of Flutter localization, including the process of setting up an internationalized app, managing localized messages, incorporating placeholders, handling plurals and selects, and implementing language-specific features. By the end, you'll have the knowledge and tools to create robust multilingual apps that resonate with users worldwide.

Setting up an Internationalized App: The Flutter_localizations Package

To begin building a multilingual app in Flutter, the first step is to set up the necessary tools and dependencies. One crucial package for Flutter localization is flutter_localizations. This package provides localization support by offering pre-defined translations for various languages and locales.

To get started, you'll need to add the flutter_localizations package to your pubspec.yaml file as a dependency:

Once you've added the package, you can import the necessary classes in your Dart files:

Now that you have the flutter_localizations package set up, you need to configure it in your Flutter app. This involves adding the MaterialApp widget and specifying the supportedLocales and localizationsDelegates properties.

The supportedLocales property defines the list of locales your app supports. For example, to support English and Spanish, you would define it as follows:

Next, the localizationsDelegates property determines which delegates to use for localization. The flutter_localizations package provides the GlobalMaterialLocalizations and GlobalWidgetsLocalizations delegates, which handle translations for standard material widgets and text directionality, respectively. To include these delegates, you can use the following code:

With the MaterialApp widget configured, you can now run your app and see the default localization in action. The app will automatically adapt to the system's language settings and display the appropriate translations for the supported locales.

Overriding the Locale

While Flutter automatically adapts the app's language based on the device's system settings, there may be situations where you want to allow users to override the default locale and select their preferred language within the app. Flutter Localization provides a straightforward way to accomplish this.

To allow users to override the locale, you can start by defining a Locale variable in your app's state or a global state management solution like Provider or Bloc. This variable will hold the selected locale:

Next, you can create a mechanism for users to choose their preferred language. This can be done through a settings screen or any other user interface element. When the user selects a new language, you can update the appLocale variable accordingly:

Once the appLocale variable is updated, you can use it to override the locale in your app. One way to achieve this is by using the MaterialApp's locale property:

By overriding the locale with the user-selected appLocale, your app will display the content and translations for the chosen language. Remember to handle cases where the user has not explicitly chosen a language and provide appropriate fallback logic, such as falling back to the device's default language or a default language set by your app.

Overriding the locale allows you to provide a more personalized experience to your users, catering to their language preferences within the app itself.

Adding Your Own Localized Messages

Flutter localization goes beyond translating static text; it involves providing customized and context-specific messages in different languages. In Flutter localization, adding your own localized messages is a straightforward process.

To begin, you'll need to define a set of message keys that represent the text you want to localize. These keys serve as identifiers for the translated messages in different languages. For example, you might define a helloMessage key:

Next, create a localization file for each supported language. These files can be in the ARB (Application Resource Bundle) format, which is a JSON-like format. Each file contains key-value pairs for the message keys and their translations. For instance, in the English localization file (en.arb), you could define the translation for the helloMessage key:

To load the localized messages into your Flutter app, you'll need to use the flutter_localizations package and the Localizations widget. Wrap your app's root widget with Localizations and specify the delegate property, which loads the localization resources:

Create a custom AppLocalizations class that extends LocalizationsDelegate, and implement the necessary methods to load the localized messages:

Finally, to access the localized messages within your app, use the AppLocalizations.of(context) method and specify the message key:

With this setup, your app will display the appropriate translation for the specified message key, based on the selected locale.

Placeholders, Plurals, and Selects

Localizing an app often involves handling more complex scenarios beyond simple text translations. Flutter localization provides powerful mechanisms to deal with placeholders, plurals, and selects in your localized messages.

Placeholders:

Placeholders allow you to dynamically insert values into your localized messages. In Flutter, you can use the intl package to handle placeholders efficiently. Define placeholder names enclosed in curly braces {} within your message strings. For example:

To substitute the placeholder with an actual value, use the intl package's MessageFormat class:

The formattedMessage will contain the localized string with the {username} placeholder replaced by the provided value.

Plurals:

Plurals are essential for correctly handling singular and plural forms in different languages. In Flutter, you can use the intl package's plural function. Define your plural message with appropriate placeholders and use the plural function to select the correct plural form based on the provided quantity. For example:

In this example, the unreadMessageCount message handles different plural forms based on the count parameter.

Selects:

Selects are useful when you need to choose different localized messages based on a specific value or condition. The intl package's select function allows you to achieve this. Define your select message with different cases and use the select function to choose the appropriate case. For example:

In this case, the greetingMessage message will select the appropriate greeting based on the provided gender value.

By utilizing placeholders, plurals, and selects, you can handle a wide range of localization scenarios in your Flutter app. These powerful features ensure that your app's localized messages are contextually accurate and linguistically appropriate for users across different languages and regions.

Escaping Syntax

When working with localized messages in Flutter, you may encounter scenarios where you need to include special characters or escape certain syntax elements within your message strings. Flutter localization provides mechanisms to handle escaping syntax to ensure the correct interpretation of your messages.

  1. Escaping Special Characters: To include special characters in your localized messages, you can escape them using a backslash (\). For example, if you want to include a double quotation mark ("), you would escape it like this:

In this case, the backslash before the double quotation mark tells Flutter to treat it as part of the string instead of closing the string prematurely.

  1. Escaping Placeholders, Plurals, and Selects: In situations where you need to include literal placeholder, plural, or select syntax within your message strings, you can escape them using curly braces with an additional pair of curly braces around them ({{}}). For example:

In this case, the double curly braces {} are interpreted as literal curly braces and will be displayed as such in the localized message, rather than being treated as placeholders.

By properly escaping special characters and syntax elements, you can ensure that your localized messages are accurately interpreted and displayed as intended, without any unintended effects or errors.

Messages with numbers and currencies

Localization often involves handling numbers and currencies in your app's messages. Flutter localization provides convenient ways to format numbers and currencies based on the user's locale.

  1. Formatting Numbers: To format numbers according to the user's locale, you can use the NumberFormat class from the intl package. This class allows you to format numbers with options for decimal separators, grouping separators, and decimal precision. For example:

In this example, formattedNumber will contain the localized representation of the number 10,000, formatted according to the user's locale.

  1. Formatting Currencies: Formatting currencies requires additional considerations, such as currency symbols and appropriate decimal precision. The NumberFormat class also supports currency formatting. You can specify the currency code and other formatting options to format currencies correctly. For example:

In this example, formattedCurrency will contain the localized representation of the amount $50.99, formatted as per the 'en_US' locale.

By utilizing the NumberFormat class, you can ensure that numbers and currencies are presented consistently and accurately for users across different locales.

Messages with Dates

When working with localized messages, it's often necessary to include dates in your app's content. Flutter localization provides robust features for formatting dates according to the user's locale.

  1. Formatting Dates: To format dates in Flutter, you can use the DateFormat class from the intl package. This class allows you to format dates based on different patterns, including full date, short date, and custom patterns. For example:

In this example, formattedDate will contain the localized representation of the current date in the format July 14, 2023 (depending on the user's locale).

  1. Customizing Date Formats: The DateFormat class provides various predefined formats, but you can also customize the date format to meet your specific requirements. You can define your own date patterns using symbols like yyyy for the year, MM for the month, and dd for the day. For example:

In this case, customFormattedDate will contain the localized representation of the current date in the format 14/07/2023 (day/month/year).

By utilizing the DateFormat class and its various options, you can ensure that dates in your app's messages are presented accurately and appropriately for users in different locales.

Localizing for iOS: Updating the iOS app bundle

When localizing a Flutter app for iOS, it's important to update the iOS app bundle to include the necessary localization resources. This ensures that the localized content is available to iOS devices.

To update the iOS app bundle for localization, follow these steps:

  1. Open the ios/Runner.xcworkspace Xcode file from your project.
  2. Open the Info.plist file in the Runner project's Runner folder in the Project Navigator.
  3. Choose the Information Property List option. Then, from the Editor menu, choose Add Item, and then Localizations from the pop-up menu.
  4. The newly created Localizations item is selected and expanded. Add a new item and choose the locale you want to add from the pop-up menu in the Value field for each locale your application supports. This list must match the supportedLocales parameter's list of supported languages.
  5. Save the file once all supported locales have been added.

Advanced Topics for Further Customization

Advanced Locale Definition:

Flutter provides the Locale class to represent a specific language and region combination. You can use advanced techniques to define custom locales beyond the basic language and country code. For example, you can define locales with script codes to handle specific language variants. By utilizing the advanced locale definition, you can cater to even more specific language requirements and provide a more tailored localization experience for your app's users.

Tracking the Locale: The Locale Class and the Localizations Widget:

Tracking the selected locale is essential for maintaining language preferences within your app. Flutter's Locale class allows you to store and access the currently selected locale. You can integrate the Locale class into your app's state management solution or leverage Flutter's built-in state management options like Provider or Bloc for efficient locale tracking. Additionally, the Localizations widget acts as a bridge between your app and the localization resources, providing access to the localized messages and handling locale changes. By effectively utilizing the Locale class and the Localizations widget, you can build a robust localization system that dynamically updates the app's content based on the user's language preferences.

Specifying the App's SupportedLocales Parameter:

The supportedLocales parameter in the MaterialApp widget allows you to specify the list of locales supported by your app. By explicitly defining the supported locales, you ensure that only the specified languages are available for selection in your app. This parameter also helps Flutter to optimize the app's performance by loading only the necessary localization resources for the supported locales. By accurately specifying the supportedLocales parameter, you can provide a seamless and efficient localization experience for your users.

Configuring the l10n.yaml File:

The l10n.yaml file is a configuration file that controls various aspects of the process in Flutter localization. It allows you to define properties like the default locale, the location of your localization files, and other settings. By modifying the l10n.yaml file, you can configure advanced options such as changing the file naming conventions, enabling placeholders and formatting options, or incorporating additional tools and packages for localization management. Proper configuration of the l10n.yaml file allows you to fine-tune the localization process according to your specific requirements.

By delving into these advanced topics, you can further customize and optimize your Flutter app's localization experience. These techniques provide flexibility, control, and efficiency in managing different locales and language preferences within your app.

Working of Internationalization in Flutter

Internationalization plays a crucial role in developing multilingual apps in Flutter. Understanding how internationalization works in Flutter can help you effectively implement localization in your app. Let's explore the key aspects of internationalization in Flutter:

Loading and Retrieving Localized Values:

In Flutter, the intl package provides essential classes and methods for loading and retrieving localized values. The Intl class offers functions like Intl.message() and Intl.plural() that facilitate the localization process. By using these functions, you can load and retrieve localized values based on the user's selected locale. Flutter automatically handles the loading and retrieval of localized values, ensuring the appropriate translations are displayed to the user.

Defining a Class for the App's Localized Resources:

To organize and manage the app's localized resources efficiently, you can define a class that encapsulates the localized values. This class can hold static variables or methods that correspond to the app's various localized messages, strings, and other content. By structuring your localized resources in a dedicated class, you can easily access and update the localized values throughout your app's codebase.

Adding Support for a New Language:

Adding support for a new language involves several steps. First, you need to create a new localization file in the ARB format for the target language. This file should contain translations for the app's content in the new language. Once you have the localization file, you can include it in your app by adding the necessary locale definition and importing the localization class. Additionally, you should update the supportedLocales property in the MaterialApp widget to include the new language. With these changes in place, Flutter will recognize and use the new language based on the user's locale selection.

By understanding the loading and retrieval of localized values, defining a class for localized resources, and adding support for new languages, you can effectively implement internationalization in your Flutter app. This enables your app to reach a wider global audience and provide a personalized and localized experience for users in different languages and regions.

Alternative Internationalization Workflows

While Flutter provides a robust framework for localization, there are alternative workflows and tools available that can enhance the internationalization process. Let's explore a couple of them:

An Alternative Class for the App's Localized Resources:

In addition to the traditional approach of defining a class for localized resources, you can leverage code generation tools to automate the process. Tools like flutter_i18n and easy_localization generate a dedicated class based on your localization files. This generated class provides static access to the localized values, eliminating the need for manual maintenance of a separate localization class. With these tools, you can simplify the organization and access of localized resources, making the localization workflow more efficient.

Using the Dart Intl Tools:

The Dart SDK provides the intl package with additional tools to streamline the internationalization process. The intl package includes command-line tools such as intl_translation and intl_translation_generator. These tools enable you to extract messages from your code, generate .arb files, and automatically generate Dart code from your localized resource files. By utilizing the Dart Intl tools, you can automate various aspects of the internationalization workflow and ensure that your app stays up to date with the latest translations.

By considering alternative approaches like code generation and leveraging the Dart Intl tools, you can enhance your Flutter app's internationalization workflow. These alternative workflows provide convenience, automation, and flexibility, allowing you to focus more on the localization itself and streamline the development process.

Example Application

example flutter application

In this example, we create a basic localization app that supports English and Spanish languages. The LocalizationApp widget serves as the root widget for the app, where we define the supported locales, configure the localization delegates, and handle language changes.

The AppLocalizations class represents the localized resources, providing access to the translated messages such as "Hello" and "Goodbye". The AppLocalizationsDelegate is responsible for loading the appropriate localization resources based on the selected locale.

The HomePage widget showcases the localization functionality. It displays a greeting message in the app bar and offers buttons to switch between English and Spanish languages. The "Goodbye" message is also displayed on the screen.

To run the app, ensure that you have the necessary dependencies (flutter_localizations and intl) added to your pubspec.yaml file and run flutter run in the terminal.

Conclusion

  • Flutter localization is essential for building multilingual apps that cater to users across different languages and regions.
  • Flutter provides built-in support for localization through the flutter_localizations package, which offers tools and delegates for handling translations.
  • Localization involves setting up the flutter_localizations package, specifying supported locales, and configuring the app's localization delegates.
  • Advanced features like placeholders, plurals, and selects allow for dynamic and context-specific translations in your app.
  • Escaping syntax ensures the correct interpretation of special characters and syntax elements within localized messages.
  • Flutter provides options for formatting numbers, currencies, and dates based on the user's locale using the intl package.
  • Updating the iOS app bundle is necessary to include the necessary localization resources for iOS devices.
  • Advanced topics for further customization include advanced locale definition, tracking the locale with the Locale class and Localizations widget, specifying the app's supported locales, and configuring the l10n.yaml file.
  • Alternative workflows like code generation tools and the Dart intl package provide additional flexibility and efficiency in managing localized resources.
  • By implementing Flutter localization effectively, you can create a personalized and localized experience for your app's users, expanding your app's reach to a global audience.