# 多语言覆盖

Vela 的能力会覆盖多个国家地区,框架支持多语言的能力后,可以做到让一个JS 应用产品(一个 RPK 文件)同时支持多个语言版本的切换,开发者无需开发多个不同语言的源码项目,避免给项目维护带来困难。

使用系统默认的语言,开发者配置多语言的方式非常简单,只需要定义资源引用资源两个步骤即可。

# 定义资源文件

资源文件用于存放多个语言的业务信息定义,与其它技术平台类似(它们使用properties文件或者xml文件的格式),JS 应用平台使用JSON文件保存资源定义;

在项目源码src目录下定义i18n文件夹,内部放置每个语言地区下的资源定义文件即可。

# 资源文件命名查找规则及建议

文件命名可使用当前系统获取到的语言以及国家信息,例如文件名可定义为:zh-CN.jsonzh.json

如果开发者当前产品仅计划支持一种语言,同时还希望用到多语言能力,那么仅声明一个名称为defaults.json的文件即可。

JSON文件名匹配优先级,优先级高的匹配到就停止查找,否则就向下一级查找。

优先级匹配规则如下:

<语言代码>-<国家代码>

<语言代码>

defaults

默认i18n配置文件首个

命名建议

  • 如果需要精确匹配语言+地区进行多语言配置建议使用<语言代码>-<国家代码>.json命名资源文件;

  • 不需要匹配地区的建议使用<语言代码>.json命名资源文件;

  • defaults.json可以作为默认选项单独使用,也可配合以上两种方式结合使用;

  • 不推荐使用系统最终的兜底默认首个的方案,可能会造成不符合预期的显示结果。

温馨提示

<语言代码>-<国家代码> 可参考:支持的语言列表

# 资源文件支持的配置语法

# 基础文本配置

{
  "message": {
    "hello": "hello world"
  }
}

# 数组配置

匹配到会把数据内容序列化转成文本输出,此种配置不支持与插值语法混用。

{
  "message": {
    "array": ["a", 2, {"c": 3}]
  }
}

# 命名插值配置

支持使用{}占位符进行命名插值,调用时通过具名参数传入替代占位内容。

{
  "message": {
    "hello": "{msg} world"
  }
}

# 列表插值配置

支持使用{}占位符进行列表插值,通过配置列表取值索引,在调用时传入备选列表进行取值替代占位内容。

{
  "message": {
    "hello": "{0} world"
  }
}

# 单复数语法配置

支持使用|占位符进行单复数语法配置,不同的选择项使用占位符分隔。

{
  "message": {
    car: 'car | cars',
  }
}

# 页面中引用资源

使用多语言配置的方式主要通过ViewModel 实例上$t$tc函数实现,这些方法可以在<template><script>中使用。

# 简单格式化方法

this.$t(path, opts)

参数说明

参数 类型 是否必填 说明
path String 获取多语言配置的资源路径,对象取值通过.连接,例如:”message.hello“
opts Array | Object 进行插值替换的配置项,可以传入对象或数组,配合配置中的差值配置使用
若传入对象则需要指定配置的命名key进行传参
若传入数组取值为传入列表对应的列表插值配置的index值

使用示例

使用基础文本配置对应取值示例:

<template>
  <div>
    <!-- 显示结果 hello world -->
    <text>{{ $t('message.hello') }}</text>
  </div>
</template>

<script>
  export default {
    onInit () {
      // 简单格式化:
      console.log(this.$t('message.hello')) // hello world
    }
  }
</script>

使用数组配置对应取值示例:

<template>
  <div>
    <!-- 直接显示数组,显示结果 ["a", 2, {"c": 3}] -->
    <text>{{ $t('message.array') }}</text>
  </div>
</template>

<script>
  export default {
    onInit () {
      // 简单格式化:
      console.log(this.$t('message.array')) // ["a", 2, {"c": 3}]
    }
  }
</script>

使用命名插值配置对应取值示例:

<template>
  <div>
    <!-- 显示结果 hello world -->
    <text>{{ $t('message.hello', { msg: 'hello' }) }}</text>
  </div>
</template>

<script>
  export default {
    onInit () {
      // 简单格式化:
      console.log(this.$t('message.hello', { msg: 'hello' }))  // hello world
    }
  }
</script>

使用列表插值配置对应取值示例:

<template>
  <div>
    <!-- 显示结果 hello world -->
    <text>{{ $t('message.hello', ['hello', 'hi']) }}</text>
  </div>
</template>

<script>
  export default {
    onInit () {
      // 简单格式化:
      console.log(this.$t('message.hello', ['hello', 'hi'])) // hello world
    }
  }
</script>

# 单复数格式化方法

this.$tc(path, choice, opts)

参数说明

参数 类型 是否必填 说明
path String 获取多语言配置的资源路径,对象取值通过.连接,例如:”message.hello“
choice Number 用于判断使用第几个选项的值,在不传入第三个参数时也可用作插值显示
特殊值说明
值必须是整数,错参报错不显示返回空字符串
单复数判断忽略正负符号
0作为偶数处理
opts Array | Object 进行插值替换的配置项,可以传入对象或数组,配合配置中的差值配置使用
若传入对象则需要指定配置的命名key进行传参
若传入数组取值为传入列表对应的列表插值配置的index值

单复数配置说明

目前单复数在资源文件中支持两种写法并支持与插值语法混用。

两段式配置:单数|复数;

三段式配置:空值|单数|复数。

配置示例

{
  "message": {
    car: 'car | cars', // 两段式配置
    apple: 'no apples | one apple | {count} apples' // 三段式配置
  }
}

使用示例

<template>
  <div>
    <!-- 两段单复数 -->
    <!-- 显示结果 cars -->
    <text>{{ $tc('message.car', 0) }}</text>
    <!-- 显示结果 car -->
    <text>{{ $tc('message.car', 1) }}</text>
    <!-- 显示结果 cars -->
    <text>{{ $tc('message.car', 2) }}</text>

    <!-- 三段单复数 -->
    <!-- 显示结果 no apples -->
    <text>{{ $tc('message.apple', 0) }}</text>
    <!-- 显示结果 one apple -->
    <text>{{ $tc('message.apple', 1) }}</text>
    <!-- 显示结果 2 apples -->
    <text>{{ $tc('message.apple', 2) }}</text>
    <!-- 三段单复数混合插值使用 -->
    <!-- 显示结果 6 apples -->
    <text>{{ $tc('message.apple', 2, {count: 6}) }}</text>
  </div>
</template>

<script>
  export default {
    onInit () {
      // 两段单复数:
      console.log(this.$tc('message.car', 0)) // cars
      console.log(this.$tc('message.car', 1)) // car
      console.log(this.$tc('message.car', 2)) // cars

      // 三段单复数:
      console.log(this.$tc('message.apple', 0)) // no apples
      console.log(this.$tc('message.apple', 1)) // one apple
      console.log(this.$tc('message.apple', 2)) // 2 apples
      console.log(this.$tc('message.apple', 2, {count: 6})) // 6 apples
    }
  }
</script>

# 获取系统语言

上面的能力用于资源内容的格式化,在某些场景下开发者可能需要获取当前系统的地区语言locale并进行更改,来完成不同的逻辑处理。比如:

  • 不同的 locale 对应的页面布局不同;

  • 开发者为用户提供设置某种语言的能力;

框架system.configuration提供了相关功能,文档参考:应用配置 configuration

# 修改地区语言后的回调

当用户在系统设置切换地区语言,会触发 onConfigurationChanged 回调,且返回来的 event.type 值为locale。

详情可参考文档

示例代码:

// 监听语言变化
onConfigurationChanged(event) {
  if (event && event.type && event.type === 'locale') {
    console.log('locale or language changed!')
  }
}