Skip to content
better-i18n.com
本页内容

This guide walks you through installing better_i18n and setting up BetterI18nProvider in your Flutter app.

Install #

Add better_i18n to your pubspec.yaml:

pubspec.yaml
dependencies:
  better_i18n: ^0.1.0

Then run:

Bash
flutter pub get

For offline caching (recommended), also add shared_preferences:

pubspec.yaml
dependencies:
  better_i18n: ^0.1.0
  shared_preferences: ^2.3.0  # for SharedPrefsStorage

Wrap with BetterI18nProvider #

Wrap your root widget (typically MaterialApp or CupertinoApp) with BetterI18nProvider:

lib/main.dart
import 'package:better_i18n/better_i18n.dart';
import 'package:flutter/material.dart';

void main() {
  runApp(
    BetterI18nProvider(
      projectId: 'your-org/your-project', // [!code highlight]
      defaultLocale: 'en',
      child: const MyApp(),
    ),
  );
}

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return const MaterialApp(
      home: HomeScreen(),
    );
  }
}

BetterI18nProvider fetches translations from CDN when the app starts and rebuilds its subtree when the locale changes.

Translate #

Use context.t('namespace.key') anywhere in the widget tree below BetterI18nProvider:

lib/home_screen.dart
import 'package:better_i18n/better_i18n.dart';
import 'package:flutter/material.dart';

class HomeScreen extends StatelessWidget {
  const HomeScreen({super.key});

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text(context.t('common.appTitle')), // [!code highlight]
      ),
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            Text(context.t('common.welcome')), // [!code highlight]
            // With interpolation arguments
            Text(
              context.t('common.greeting', args: {'name': 'Osman'}), // [!code highlight]
            ),
          ],
        ),
      ),
    );
  }
}

Key format is "namespace.key" — matching your CDN translation structure. If the key is not found, the key itself is returned as fallback.

Switch Locale #

Use context.setI18nLocale(code) to switch the active language at runtime:

lib/settings_screen.dart
import 'package:better_i18n/better_i18n.dart';
import 'package:flutter/material.dart';

class LanguagePicker extends StatelessWidget {
  const LanguagePicker({super.key});

  @override
  Widget build(BuildContext context) {
    final languages = context.i18nLanguages; // [!code highlight]
    final currentLocale = context.i18nLocale; // [!code highlight]

    return ListView.builder(
      itemCount: languages.length,
      itemBuilder: (context, index) {
        final lang = languages[index];
        return ListTile(
          title: Text(lang.nativeName ?? lang.name ?? lang.code),
          trailing: lang.code == currentLocale
              ? const Icon(Icons.check)
              : null,
          onTap: () => context.setI18nLocale(lang.code), // [!code highlight]
        );
      },
    );
  }
}

With Offline Support

For production apps, enable offline caching and locale persistence:

lib/main.dart
import 'package:better_i18n/better_i18n.dart';
import 'package:flutter/material.dart';

void main() {
  runApp(
    BetterI18nProvider(
      projectId: 'your-org/your-project',
      defaultLocale: 'en',
      storage: SharedPrefsStorage(), // [!code highlight]
      loadingBuilder: (_) => const MaterialApp( // [!code highlight]
        home: Scaffold(body: Center(child: CircularProgressIndicator())),
      ),
      child: const MyApp(),
    ),
  );
}

See Offline & Caching for the full caching guide.

Next Steps #