乐趣区

关于flutter:Strapi助力Flutter开发国际化App-支持多语言

在 Sqlite 数据库中有一列 locale 反对了多语言,所以只须要更改一下 Sql 查问条件就能够查出不同语言的数据。

批改 VegetableDao 退出语言查问条件

[project_root]/lib/app/data/dao/vegetalbe_dao.dart

import 'package:floor/floor.dart';
import 'package:strapi_flutter_internation_poc/app/data/entity/vegetable.dart';

@dao
abstract class VegetableDao {@Query('SELECT * FROM vegetables_v WHERE  locale = :locale')
  Future<List<VegetableV>> findAll(String locale);
}

批改后从新运行 Floor 代码生成器

flutter packages pub run build_runner build

HomeController稍作调整

[project_root]/lib/app/modules/home/controllers/home_controller.dart

  Future<void> getAllVegetables() async {final result = await DbService.to.db.vegetableDao.findAll('en');
    vegetables.value = result;
  }

这样显示的数据就都是英文的了

接下来整合 GetX 的国际化个性

新建一个 language_service

[project_root]/lib/app/common/services/language_service.dart

这里用到了 get_storage 做默认语言的缓存。记得要在 Flutter 我的项目中减少这个库的依赖。应用命令 get install get_storage 就能够疾速的实现装置。

import 'dart:ui' as ui;

import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:get_storage/get_storage.dart';

class LanguageService extends GetxService {static LanguageService get to => Get.find();

  var box = GetStorage();
  var locale = Locale('en', 'US');
  var localeKey = 'en';

  Future<LanguageService> init() async {if (box.read('language') != null) {if (box.read('language') == 'zh-CN') {locale = Locale('zh', 'CN');
        localeKey = 'zh-CN';
      } else {locale = Locale('en', 'US');
        localeKey = 'en';
      }
    } else {if (ui.window.locale.languageCode == 'zh') {locale = Locale('zh', 'CN');
        localeKey = 'zh-CN';
      } else {locale = Locale('en', 'US');
        localeKey = 'en';
      }
    }

    return this;
  }

  void changeLocale(l) {if (l == Locale('zh', 'CN')) {
      localeKey = 'zh-CN';
      updateLocale(Locale('zh', 'CN'));
    } else if (l == Locale('en', 'US')) {
      localeKey = 'en';
      updateLocale(Locale('en', 'US'));
    }
    box.write('language', localeKey);
  }

  void updateLocale(_l) {
    locale = _l;
    Get.updateLocale(_l);
  }
}

GetX Cli 能够疾速的通过 JSON 文件生成 GetX 框架所须要的多语言配置。

[project_root]/assets/locales 下新建两个 JSON 文件

en_US.json

{
  "app": {"name": "VAF"},
  "locale": {
    "title": "Language",
    "zh": "中文",
    "en": "English"
  }
}

zh_CN.json

{
  "app": {"name": "蔬果"},
  "locale": {
    "title": "语言",
    "zh": "中文",
    "en": "English"
  }
}

运行命令

get generate locales assets/locales

能够失去[project_root]/lib/generated/locales.g.dart

class AppTranslation {
  static Map<String, Map<String, String>> translations = {
    'zh_CN': Locales.zh_CN,
    'en_US': Locales.en_US,
  };
}

class LocaleKeys {LocaleKeys._();
  static const app_name = 'app_name';
  static const locale_title = 'locale_title';
  static const locale_zh = 'locale_zh';
  static const locale_en = 'locale_en';
}

class Locales {
  static const zh_CN = {
    'app_name': '蔬果',
    'locale_title': '语言',
    'locale_zh': '中文',
    'locale_en': 'English',
  };
  static const en_US = {
    'app_name': 'VAF',
    'locale_title': 'Language',
    'locale_zh': '中文',
    'locale_en': 'English',
  };
}

在 main.dart 中减少对 LanguageService 的初始化

Future<void> initServices() async {print('starting services ...');
  await Get.putAsync(() => DbService().init());
  await Get.putAsync(() => LanguageService().init());
  print('All services started...');
}

批改 runApp 退出多语言配置

  runApp(
    GetMaterialApp(
      title: "Application",
      initialRoute: AppPages.INITIAL,
      getPages: AppPages.routes,
      translationsKeys: AppTranslation.translations,
      locale: LanguageService.to.locale,
      fallbackLocale: Locale('zh', 'CN'),
    ),
  );

调整 Controller 中的查问条件

final result = await DbService.to.db.vegetableDao.findAll('en');

改为

    final result = await DbService.to.db.vegetableDao
        .findAll(LanguageService.to.localeKey);

批改界面中的文字为援用多语言的资源

      appBar: AppBar(title: Text('Vegetables'),
        centerTitle: true,
      ),

改为

      appBar: AppBar(title: Text(LocaleKeys.app_name.tr),
        centerTitle: true,
      ),

再次运行就能够看到默认为中文的界面了

稍作欠缺再减少一个切换语言的按钮

appBar: AppBar(title: Text(LocaleKeys.app_name.tr),
        centerTitle: true,
        actions: [
          IconButton(onPressed: () {
                Get.dialog(SimpleDialog(title: Text(LocaleKeys.locale_title.tr),
                  children: <Widget>[
                    SimpleDialogOption(onPressed: () {LanguageService.to.changeLocale(Locale('en', 'US'));
                      },
                      child: Padding(padding: const EdgeInsets.symmetric(vertical: 6),
                        child: Text(LocaleKeys.locale_en.tr),
                      ),
                    ),
                    SimpleDialogOption(onPressed: () {LanguageService.to.changeLocale(Locale('zh', 'CN'));
                      },
                      child: Padding(padding: const EdgeInsets.symmetric(vertical: 6),
                        child: Text(LocaleKeys.locale_zh.tr),
                      ),
                    ),
                  ],
                ));
              },
              icon: Icon(Icons.language))
        ],
      ),

十分便捷疾速的就实现了语言的切换

退出移动版