Get the FREE Ultimate OpenClaw Setup Guide →

flutter-internationalization

Scanned
npx machina-cli add skill MADTeacher/mad-agents-skills/flutter-internationalization --openclaw
Files (1)
SKILL.md
8.9 KB

Flutter Internationalization

Overview

Comprehensive guide for adding internationalization (i18n) to Flutter applications. Covers setup, configuration, message management, number/date formatting, and advanced topics like locale override and custom language support.

Quick Start

Choose approach based on app needs:

gen-l10n (Recommended) - Modern, automated, code generation

  • Best for: Most new projects, teams, complex apps
  • Uses: ARB files, automated code generation
  • See: Setup gen-l10n

intl package - Manual control, code-based

  • Best for: Simple apps, legacy projects, full control
  • Uses: Intl.message() code, manual translation files
  • See: Setup intl package

Manual/Custom - Maximum flexibility

  • Best for: Very simple apps, custom workflows
  • Uses: Direct Map-based lookups
  • See: Custom localizations

Setup gen-l10n

1. Add Dependencies

Update pubspec.yaml:

dependencies:
  flutter:
    sdk: flutter
  flutter_localizations:
    sdk: flutter
  intl: any

Run:

flutter pub add flutter_localizations --sdk=flutter
flutter pub add intl:any

2. Enable Code Generation

Add to pubspec.yaml:

flutter:
  generate: true

3. Configure l10n.yaml

Create l10n.yaml in project root:

arb-dir: lib/l10n
template-arb-file: app_en.arb
output-localization-file: app_localizations.dart

For advanced options, see l10n-config.md.

4. Create ARB Files

Create directory lib/l10n/.

Template file lib/l10n/app_en.arb:

{
  "helloWorld": "Hello World!",
  "@helloWorld": {
    "description": "Greeting message"
  }
}

Translation file lib/l10n/app_es.arb:

{
  "helloWorld": "¡Hola Mundo!"
}

For complete ARB format, see arb-format.md.

5. Generate Code

Run:

flutter gen-l10n

Or run app to trigger auto-generation:

flutter run

6. Configure MaterialApp

Import and setup:

import 'package:flutter/material.dart';
import 'package:flutter_localizations/flutter_localizations.dart';
import 'l10n/app_localizations.dart';

MaterialApp(
  localizationsDelegates: [
    AppLocalizations.delegate,
    GlobalMaterialLocalizations.delegate,
    GlobalWidgetsLocalizations.delegate,
    GlobalCupertinoLocalizations.delegate,
  ],
  supportedLocales: [
    Locale('en'),
    Locale('es'),
  ],
  home: MyHomePage(),
)

7. Use Localizations

Access in widgets:

Text(AppLocalizations.of(context)!.helloWorld)

Message Types

Simple Messages

No parameters:

{
  "welcome": "Welcome to our app",
  "@welcome": {
    "description": "Welcome message"
  }
}

Placeholder Messages

With parameters:

{
  "greeting": "Hello {userName}!",
  "@greeting": {
    "description": "Personalized greeting",
    "placeholders": {
      "userName": {
        "type": "String",
        "example": "Alice"
      }
    }
  }
}

Use in code:

Text(AppLocalizations.of(context)!.greeting('Alice'))

Plural Messages

Based on count:

{
  "itemCount": "{count, plural, =0{No items} =1{1 item} other{{count} items}}",
  "@itemCount": {
    "placeholders": {
      "count": {
        "type": "int"
      }
    }
  }
}

Use in code:

Text(AppLocalizations.of(context)!.itemCount(5))

Select Messages

Based on string value:

{
  "pronoun": "{gender, select, male{he} female{she} other{they}}",
  "@pronoun": {
    "placeholders": {
      "gender": {
        "type": "String"
      }
    }
  }
}

Use in code:

Text(AppLocalizations.of(context)!.pronoun('male'))

Number and Date Formatting

Numbers

Format numbers automatically:

{
  "price": "Price: {value}",
  "@price": {
    "placeholders": {
      "value": {
        "type": "int",
        "format": "simpleCurrency"
      }
    }
  }
}

Format options: compact, currency, simpleCurrency, decimalPattern, etc.

Dates

Format dates automatically:

{
  "eventDate": "Event on {date}",
  "@eventDate": {
    "placeholders": {
      "date": {
        "type": "DateTime",
        "format": "yMMMd"
      }
    }
  }
}

Format options: yMd, yMMMd, yMMMMd, Hm, etc.

For complete formatting options, see number-date-formats.md.

Advanced Topics

Locale Override

Override locale for specific widgets:

Localizations.override(
  context: context,
  locale: const Locale('es'),
  child: CalendarDatePicker(...),
)

Custom Locale Definitions

For complex locales (Chinese, French regions):

supportedLocales: [
  Locale.fromSubtags(languageCode: 'zh'),
  Locale.fromSubtags(languageCode: 'zh', scriptCode: 'Hans'),
  Locale.fromSubtags(languageCode: 'zh', scriptCode: 'Hant', countryCode: 'TW'),
]

Locale Resolution Callback

Control locale fallback:

MaterialApp(
  localeResolutionCallback: (locale, supportedLocales) {
    // Always accept user's locale
    return locale;
  },
)

Access Current Locale

Get current app locale:

Locale myLocale = Localizations.localeOf(context);

Setup intl Package

Manual Setup

  1. Add dependencies (same as gen-l10n)
  2. Create localization class:
class DemoLocalizations {
  DemoLocalizations(this.localeName);

  static Future<DemoLocalizations> load(Locale locale) {
    final String name = Intl.canonicalizedLocale(locale.toString());
    return initializeMessages(name).then((_) => DemoLocalizations(name));
  }

  static DemoLocalizations of(BuildContext context) {
    return Localizations.of<DemoLocalizations>(context, DemoLocalizations)!;
  }

  String get title {
    return Intl.message(
      'Hello World',
      name: 'title',
      desc: 'Title',
      locale: localeName,
    );
  }
}
  1. Create delegate:
class DemoLocalizationsDelegate extends LocalizationsDelegate<DemoLocalizations> {
  const DemoLocalizationsDelegate();

  @override
  bool isSupported(Locale locale) => ['en', 'es'].contains(locale.languageCode);

  @override
  Future<DemoLocalizations> load(Locale locale) => DemoLocalizations.load(locale);

  @override
  bool shouldReload(DemoLocalizationsDelegate old) => false;
}
  1. Generate ARB files:
dart run intl_translation:extract_to_arb --output-dir=lib/l10n lib/main.dart
dart run intl_translation:generate_from_arb --output-dir=lib/l10n lib/main.dart lib/l10n/intl_*.arb

Custom Localizations

For maximum simplicity:

class DemoLocalizations {
  DemoLocalizations(this.locale);

  final Locale locale;

  static DemoLocalizations of(BuildContext context) {
    return Localizations.of<DemoLocalizations>(context, DemoLocalizations)!;
  }

  static const _localizedValues = <String, Map<String, String>>{
    'en': {'title': 'Hello World'},
    'es': {'title': 'Hola Mundo'},
  };

  String get title {
    return _localizedValues[locale.languageCode]!['title']!;
  }
}

Best Practices

  1. Use gen-l10n for new projects - simpler, safer, better tooling
  2. Add descriptions to ARB entries - provides context for translators
  3. Format numbers/dates with format types - automatic locale handling
  4. Test all locales - verify formatting, RTL, and translations
  5. Use pluralization - handle count variations correctly
  6. Keep messages short - easier to translate, more consistent
  7. Don't concatenate strings - use placeholders instead
  8. Enable nullable-getter to reduce null checks in user code

Resources

references/

l10n-config.md - Complete reference for l10n.yaml configuration options, including output directories, code generation settings, and locale handling.

arb-format.md - Comprehensive guide to ARB file format, covering simple messages, placeholders, plurals, selects, and metadata.

number-date-formats.md - Number and date formatting reference with format types, patterns, and locale-specific examples.

assets/

Example templates and boilerplate code can be added here for common internationalization patterns.

When to Use This Skill

Use this skill when:

  • Adding localization support to a new Flutter app
  • Translating existing Flutter app to multiple languages
  • Configuring number/date formatting for different locales
  • Setting up RTL (right-to-left) language support
  • Implementing locale-specific layouts or widgets
  • Managing ARB files and translations
  • Troubleshooting localization issues
  • Adding custom language support beyond built-in locales
  • Optimizing app bundle size with deferred loading

Source

git clone https://github.com/MADTeacher/mad-agents-skills/blob/main/flutter-internationalization/SKILL.mdView on GitHub

Overview

A comprehensive guide to adding internationalization (i18n) to Flutter apps. It covers setup, configuration, message management, and formatting for numbers and dates across locales, with advanced topics like locale override and custom language support.

How This Skill Works

The guide walks you through choosing between gen-l10n and the intl package, then shows how to enable code generation or manual localization. It covers ARB files, code generation with flutter gen-l10n, and wiring MaterialApp with the necessary localization delegates and supportedLocales.

When to Use It

  • Add localization support to a Flutter app
  • Translate UI text into multiple languages
  • Format numbers and dates for different locales
  • Configure multi-language support for Material and Cupertino widgets
  • Migrate an app from a manual i18n approach to gen-l10n or intl

Quick Start

  1. Step 1: Pick gen-l10n (recommended) or intl and add dependencies in pubspec.yaml
  2. Step 2: Enable code generation and set up ARB files (lib/l10n) and l10n.yaml
  3. Step 3: Run flutter gen-l10n and configure MaterialApp with localization delegates; use AppLocalizations in widgets

Best Practices

  • Choose gen-l10n for most projects to automate code generation and reduce boilerplate
  • Keep ARB files under lib/l10n and provide clear descriptions for keys
  • Use well-named keys (e.g., helloWorld, greeting) and metadata for translators
  • Test across locales, including RTL support and locale overrides
  • Configure localization delegates and supportedLocales in MaterialApp

Example Use Cases

  • An e-commerce Flutter app localized into English, Spanish, and French using ARB files and AppLocalizations
  • An app that formats currency, dates, and numbers according to the user’s locale
  • An app with locale overrides to restrict available languages per region
  • A legacy app migrated from Intl.message to gen-l10n with automated codegen
  • A cross-platform app delivering localized UI across Material and Cupertino widgets

Frequently Asked Questions

Add this skill to your agents
Sponsor this space

Reach thousands of developers