vue-i18n国际化+iview组件国际化

251 阅读4分钟

vue-i18n国际化+iview组件国际化

背景

一个现有的中文的大型且复杂的VUE项目,页面巨多,有n多个组件和页面!!!需要国际化语言,翻译成英文。

需要干的事

1.引入vue-i18n(vue的国际化插件),配置语言包,注意用了组件的,还得将组件的语言包导进来。

2.将项目里的文本提取出来,并翻译,作为翻译的语言包。

3.替换js和vue的文本。

说明

​ 在这个项目中,需要把现有的巨多的页面文本都提取出来做一个翻译语言包,而且页面巨多,文本巨多。如果采用中文一个语言包(例如:{"note":"保存的名称重复"}),英文一个语言包({"note":"The saved name is duplicated."}),不仅要另外取属性名字,而且页面文本替换也不方便,得把中文文本替换成改的属性名,再包裹翻译方法。

​ 于是,我们最终决定采用这样的一个语言包格式,中英文都在这一个包里面,例如:{"保存的名称重复":"The saved name is duplicated."} ,即左边中文,右边英文。这样不仅不用另外取属性名,方便语言包的提取和翻译,而且在页面中可以直接在中文文本上包裹翻译方法。就无需再替换中文文本为取的属性名,再包裹翻译方法了。

具体实现

1.引入vue-i18n(vue的国际化插件),配置语言包,注意用了组件的,还得将组件的语言包导进来。

安装

要安装指定版本的自行加@版本号

npm install vue-i18n

创建文件夹

在src文件夹下创建i18n文件夹(如图目录结构)

编辑

lan文件夹下存放各个页面用到的语言包

注:本来是准备将lan里面的文本语言包直接放在一个js文件里面的,但是页面实在是太多了,就对应把view目录下的所有文本,放到view.js(虽然一个view.js里面还是有好几百条数据,但是结构会清晰一点);components目录下的所有文本,放到component.js中这样了。最后再在lan文件夹下的index.js里把lan文件夹下的所有语言包(view.js,component.js,router.js等这些)合为一个语言包,暴露出去。(这么干就是为了结构清晰一点,和一个文件的语言包没啥区别)

再来以view.js为例,看看语言包格式长啥样吧,如下图。

编辑

编辑

在i18n下创建index.js,用来引入VueI18n并且导入语言包。

这里需要注意,要把组件的语言包也导进去,不然引用的组件还是中文的,本项目中用的组件是iview组件,国际化导包可以去对应的组件官网查看

import Vue from 'vue'
import VueI18n from 'vue-i18n'
import iView from 'iview';
import en from './lan';
//iview组件国际化语言包
import zhLocale from 'iview/src/locale/lang/zh-CN';
import enLocale from 'iview/src/locale/lang/en-US';
​
Vue.use(VueI18n);
​
// 自动根据浏览器系统语言设置语言
const navLang = navigator.language
const localLang = (navLang === 'zh-CN' || navLang === 'en-US') ? navLang : false
let lang = localLang || 'zh-CN'Vue.config.lang = lang;
​
//lan里面的中文语言包
const customZhCn = function () {
  return Object.keys(en).reduce((acc, key) => {
    acc[key] = key; // 中文环境下,键和值相同  
    return acc;
  }, {})
}
export const i18n = new VueI18n({
  locale: lang,
  // locale: 'en-US',
  messages: {
    /**
这里是在将项目里的文本和iview组件里的包合并为一个包。
如果只需要一个项目里的语言包,不用iview组件的话,就直接'en-US':en这样**/
    'zh-CN': Object.assign(customZhCn(), zhLocale),
    'en-US': Object.assign(en, enLocale)
  }
})
​
Vue.use(iView, {
  i18n: (key, value) => i18n.t(key, value)
})
export default i18n;

在main.js里面全局引用i18n

编辑

编辑

2.将项目里的文本提取出来,并翻译,作为翻译的语言包。

3.替换js和vue的文本。

这两步真的累死个人,页面巨多,妥妥搬砖打杂,就单纯找项目里的所有文本提取到语言包里去,格式就是上面提到的view.js这样。

替换vue的文本,例如:

标签里的文本:

您好
替换为
{{$t('您好')}}

标签有属性的: 替换为

替换js的文本,例如:

1.在每个页面需要用到的先导入 import lang from '@/i18n'

再把js里面的文本用lang.t方法包裹,进行翻译,如下图:

编辑

2.如果不在每个js用翻译的地方import lang from '@/i18n'的话,就直接使用全局挂载的t方法。

例如:this.$t('请注意')

3.要注意的是!!

要是js里面有return的template的html语法,里面有文本的话,记得包裹{lang.t('文本')}翻译,如图:

编辑

4.还有要注意的是,一段文本里面,既有文本又有属性的时候,要包裹正确,如图:

当然这里i18n里面有占位的翻译,就不用去拆分一句话了。(可以去官网查看)

编辑

不过!我的同事在项目里写脚本全局提取中文文本,生成对应的目录结构存到里面!(虽然可能脚本写的可能不是很全,有些文本没有提取进去,也就是这样,我又干了很多打杂的活,去找文本提取,很栓q啊!)

和全局替换vue页面的(像

您好
,直接全局替换成了
{{Extra close brace or missing open brace​t('输入文本')" >,这时候就需要手动加 :了,变成您好这样才对)

和全局替换js文本,用lang.t(")包裹,并在使用了这个方法的script中,自动引入import lang from '@/i18n'。

当然,我不会这脚本,待我去研究研究,偷师学艺一下,哈哈哈。