前言
项目国际化效果是根据不同语言及地区显示对应语言的界面内容,需要对工程中的资源、字符串等进行相应的国际化操作。在实际的项目需求中,有可能进行应用内语言切换,除了默认的跟随系统之外,还要实现动态的语言版本切换;国际化后相应的会增加安装包的大小,主要是因为资源文件的多语言版本数据造成的。
语言切换方式
- 手机系统设置语言
- App 在支持语言里切换
- App 内部语言切换管理
国际化操作
- App 名称
- 权限使用说明
- 原生代码中字符串
- 图片、文件、音视频等资源文件
- Storyboard / Xib 文件
- 时间
- 网络请求数据(后端支持国际化数据)
项目配置语言
国际化的准备工作是配置需要国际化的语言,这是我们国际化操作的必要配置。
-
配置语言
-
结果如下
1. App 名称
App 名称国际化是指应用在不同的语言环境下显示不同的名称,也就是手机设备的语言设置;
注意 App 名称只受手机设备系统的语言影响,也就是上面切换语言的第一种方式控制的;
- 创建
InfoPlist.strings
文件、配置需要国际化的语言
-
InfoPlist.strings
文件中设置不同语言对应的 App 名字
/// en
CFBundleDisplayName = "LocalizeDemo";
/// zh-Hans
CFBundleDisplayName = "本地化示例";
/// zh-Hant
CFBundleDisplayName = "本地話示例";
2. 权限使用说明
应用在使用到系统权限时,会询问用户是否同意使用该权限,说明理由的文案需要国际化
-
InfoPlist.strings
文件中设置不同语言对应的权限 key 对应的描述
NSBluetoothAlwaysUsageDescription = "APP需要您的允许才能允许蓝牙与设备通信";
NSBluetoothPeripheralUsageDescription ="APP需要您的允许才能允许蓝牙与设备通信";
NSCalendarsUsageDescription ="APP需要您的允许才能访问日历";
NSCameraUsageDescription ="APP需要您的允许才能使用照相机功能";
NSContactsUsageDescription ="APP需要您的允许才能访问您的通讯簿";
NSLocationAlwaysUsageDescription ="APP需要您的允许才能始终启用位置功能 ";
NSLocationWhenInUseUsageDescription ="APP需要您的允许才能始终启用位置功能 ";
NSMicrophoneUsageDescription ="APP需要您的允许才能录制";
NSPhotoLibraryAddUsageDescription ="APP需要您的允许才能将照片保存到相册 ";
NSPhotoLibraryUsageDescription ="APP需要您的允许才能访问相册";
NSSpeechRecognitionUsageDescription ="APP需要您的允许才能使用语音识别";
NSAppleMusicUsageDescription = "APP需要你的允许才能访问多媒体";
3. 原生代码中字符串
字符串国际化指 App 内的字符串在不同的语言环境下显示不同的内容;字符串国际化和 App 名称国际化相同,只是创建的文件不一样,必须是 Localizable.strings
。
-
Localizable.strings
文件中设置不同语言对应的字符串展示的内容
/// en
"这是一个示例!" = "Here's an example!";
/// zh-Hans
"这是一个示例!" = "这是一个示例!";
/// zh-Hant
"这是一个示例!" = "這是一個示例!";
- 代码中使用
/// 国际化字符串宏定义,key:需要国际化的字符串,comment:一个注释,一般设置为nil
NSLocalizedString(<#T##key: String##String#>, comment: <#T##String#>)
// 举例
Text(NSLocalizedString("这是一个示例!", comment: ""))
4. 图片、文件、音视频等资源文件
-
图片国际化
图片存放方式:Assets.xcassets、项目文件夹;
针对不同的存放方式,图片国际化也有对应的方式;
-
Assets.xcassets
Assets资源文件直接设置支持的语言,不同语言设置对应的资源图片,使用时直接使用同一个文件名
/// 直接使用文件名加载图片
Image("icon")
- 项目文件夹存放
项目文件夹存放图片时,有两种国际方式:
(1).不同语言存放不同文件名的资源文件, Localizable.strings
文件中配置不同语言的资源图片名字,通过国际化字符串的方式获取对应的图片资源
/// en
"book" = "book_en";
/// zh-Hans
"book" = "book_hans";
/// zh-Hant
"book" = "book_hant";
/// 通过国际化字符串的方式获取对应的图片资源
Image(uiImage: UIImage(named: NSLocalizedString("book", comment: ""))!)
(2).图片资源文件直接设置支持的语言,不同语言对应文件夹下存放对应的资源文件,使用时直接使用同一个文件名
/// 直接使用文件名加载图片
Image(uiImage: UIImage(named: "cup")!)
-
文件、音视频等资源文件国际化
文件、音视频等存放方式与图片存放在项目文件夹中一样,国际化方式通图片存放在项目文件夹中的国际化方式相同
5. Storyboard / Xib 文件
Storyboard / Xib 文件国际化原理和字符串差不多,需要开启Storyboard / Xib 文件的国际化支持,在Storyboard / Xib 文件右侧添加需要国际化的语言,然后Xcode会自动生成xxx.strings
文件,我们只需要翻译该文件中的字符串即可,如下图所示:
/// zh-Hans
"A6V-b6-9hZ.text" = "测试";
/// zh-Hant
"A6V-b6-9hZ.text" = "測試";
UILabel
的text属性,其中 key 是 Storyboard 自动生成的控件的唯一编码,value则是我们需要国际化的字符串,只需要将翻译好的字符串进行替换就可以了。
6. 时间
时间涉及业务和显示的地方,在不同时区时间应该是不一样的,让应用根据不同的时区来显示时间。
- 前后端统一系统中和时间相关的字段,都需要返回时间戳格式
- 通过
NSDateFormatter
对象将时间戳转换成可用的字符串,NSDateFormatter
对象里面TimeZone
属性,默认系统当前时区,无需setTimeZone
,获取到的时间就是当前系统对应的时间,随系统时区切换,时间会跟着变化。
7. 网络请求数据(后端支持国际化数据)
建议在请求头header中增加当前展示语言类型的字段,服务端获根据语言类型返回对应语言的数据,一般差异会体现在文案、图片等方面