[new feature] add i18n support (#310)

* fix: Tabbar icon line-height

* [new feature] progress add showPivot prop

* [new feature] TabItem support vue-router

* [new feature] update document header style

* [Doc] add toast english ducoment

* [new feature] add i18n support

* feat: Extract demos from markdown

* feat: Base components demos

* [new feature] complete demo extract & translate

* [fix] text cases

* fix: add deepAssign test cases

* fix: changelog detail

* [new feature] AddressEdit support i18n
This commit is contained in:
neverland
2017-11-15 20:08:51 -06:00
committed by GitHub
parent 05abf0d509
commit d8b6ad7d54
210 changed files with 5561 additions and 5528 deletions
+7 -14
View File
@@ -1,14 +1,13 @@
<template>
<div class="app">
<zan-doc :simulators="simulators" :currentSimulator="currentSimulator" :config="config" :base="base">
<van-doc :simulators="simulators" :currentSimulator="currentSimulator" :config="config" :base="base">
<router-view @changeDemoURL="onChangeDemoURL"></router-view>
</zan-doc>
</van-doc>
</div>
</template>
<script>
import docConfig from './doc.config';
import { getLang } from './utils/lang';
export default {
data() {
@@ -19,28 +18,22 @@ export default {
return {
simulators: [`/zanui/vant/examples${location.hash}`],
demoURL: '',
lang: getLang()
demoURL: ''
};
},
computed: {
base() {
return `/${this.lang}/component`;
return `/${this.$vantLang}/component`;
},
config() {
return docConfig[this.lang];
return docConfig[this.$vantLang];
},
currentSimulator() {
return this.$route.name === 'zh-CN/demo' ? 1 : 0;
}
},
watch: {
'$route'(to) {
this.lang = to.meta.lang;
const { name } = this.$route;
return name && name.indexOf('demo') !== -1 ? 1 : 0;
}
},
-1
View File
@@ -9,6 +9,5 @@ body {
background-color: #f8f8f8;
font-family: Arial, Helvetica, "STHeiti STXihei", "Microsoft YaHei", Tohoma, sans-serif;
-webkit-font-smoothing: antialiased;
padding-bottom: 20px;
}
</style>
+4 -14
View File
@@ -16,39 +16,29 @@
<script>
import docConfig from '../doc.config';
import MobileNav from './mobile-nav';
import { getLang } from '../utils/lang';
export default {
data() {
return {
docConfig,
lang: getLang()
docConfig
};
},
beforeRouteEnter(to, from, next) {
next(vm => vm.lang = to.meta.lang);
},
beforeRouteUpdate(to, from, next) {
this.lang = to.meta.lang;
},
components: {
MobileNav
},
computed: {
base() {
return `${this.lang}/component`;
return `${this.$vantLang}/component`;
},
navList() {
return this.docConfig[this.lang].nav || [];
return this.docConfig[this.$vantLang].nav || [];
},
description() {
return this.lang === 'zh-CN' ? '有赞移动端 Vue 组件库' : 'A Vue.js 2.0 Mobile UI at YouZan';
return this.$vantLang === 'zh-CN' ? '有赞移动端 Vue 组件库' : 'A Vue.js 2.0 Mobile UI at YouZan';
}
}
};
-99
View File
@@ -1,99 +0,0 @@
<template>
<section class="zan-doc-demos">
<h2>示例</h2>
<p>下面是一些使用 Vant 搭建的示例页面点击图片切换至对应示例</p>
<div class="zan-doc-demos__gallery">
<div
:class="['zan-doc-demos__item', { 'zan-doc-demos__item--active': index === currentDemo }]"
v-for="(demo, index) in demos"
>
<h4>{{ demo.title }}</h4>
<a :href="demo.source" target="_blank">源代码</a>
<img :src="demo.preview" @click="onChangeDemo(demo, index)" />
</div>
</div>
</section>
</template>
<script>
export default {
data() {
return {
currentDemo: 0,
demos: [{
title: '商品详情',
preview: 'https://img.yzcdn.cn/public_files/2017/10/24/7070a8d1d6504b864c605114d32f2aae.png',
url: 'https://chenjiahan.github.io/vant-demo/#/goods',
source: 'https://github.com/chenjiahan/vant-demo/tree/master/src/view/goods/index.vue'
}, {
title: '会员中心',
preview: 'https://img.yzcdn.cn/public_files/2017/10/23/e1d70757e3ab88d39a360b704be8f43f.png',
url: 'https://chenjiahan.github.io/vant-demo/#/user',
source: 'https://github.com/chenjiahan/vant-demo/tree/master/src/view/user/index.vue'
}, {
title: '购物车',
preview: 'https://img.yzcdn.cn/public_files/2017/10/24/06b8b5ed3692314d434db7f6854dcdbe.png',
url: 'https://chenjiahan.github.io/vant-demo/#/cart',
source: 'https://github.com/chenjiahan/vant-demo/tree/master/src/view/cart/index.vue'
}]
};
},
beforeMount() {
this.$emit('changeDemoURL', this.demos[0].url);
},
methods: {
onChangeDemo(demo, index) {
this.currentDemo = index;
this.$emit('changeDemoURL', demo.url);
}
}
};
</script>
<style>
.zan-doc-demos {
&__gallery {
margin-top: 30px;
}
&__item {
width: 28%;
text-align: center;
margin-bottom: 40px;
display: inline-block;
&:nth-child(3n+1),
&:nth-child(3n+2) {
margin-right: 4%;
}
h4 {
font-size: 14px;
line-height: 20px;
font-weight: normal;
}
img {
width: 100%;
cursor: pointer;
border-radius: 3px;
background-color: #f8f8f8;
box-shadow: 0 2px 3px rgba(10, 10, 10, 0.1), 0 0 0 1px rgba(10, 10, 10, 0.1);
}
a {
font-size: 12px;
margin: 4px 0 7px;
display: inline-block;
}
&--active {
img {
box-shadow: 0 1px 4px rgba(51, 136, 255, .4), 0 0 0 1px rgba(51, 136, 255, .4);
}
}
}
}
</style>
+19 -8
View File
@@ -305,6 +305,17 @@ module.exports = {
path: '/changelog',
title: 'Changelog',
noExample: true
},
{
path: '/theme',
title: 'Theme (In translation)',
noExample: true
},
{
path: '/demo',
title: 'Demo pages (In translation)',
noDocument: true,
noExample: true
}
]
}
@@ -491,35 +502,35 @@ module.exports = {
list: [
{
path: '/address-edit',
title: 'AddressEdit'
title: 'AddressEdit (In translation)'
},
{
path: '/address-list',
title: 'AddressList'
title: 'AddressList (In translation)'
},
{
path: '/area',
title: 'Area'
title: 'Area (In translation)'
},
{
path: '/contact',
title: 'Contact'
title: 'Contact (In translation)'
},
{
path: '/coupon',
title: 'Coupon'
title: 'Coupon (In translation)'
},
{
path: '/goods-action',
title: 'GoodsAction'
title: 'GoodsAction (In translation)'
},
{
path: '/submit-bar',
title: 'SubmitBar'
title: 'SubmitBar (In translation)'
},
{
path: '/sku',
title: 'Sku'
title: 'Sku (In translation)'
}
]
}
+3 -12
View File
@@ -2,14 +2,13 @@ import Vue from 'vue';
import VueRouter from 'vue-router';
import App from './WapApp';
import routes from './router.config';
import { setLang } from './utils/lang';
import Vant, { Lazyload } from 'packages';
import ZanDoc from 'zan-doc';
import VantDoc from 'vant-doc';
import 'packages/vant-css/src/index.css';
import 'zan-doc/src/helper/touch-simulator';
import 'vant-doc/src/helper/touch-simulator';
Vue.use(Vant);
Vue.use(ZanDoc);
Vue.use(VantDoc);
Vue.use(Lazyload, {
lazyComponent: true
});
@@ -22,14 +21,6 @@ const router = new VueRouter({
routes: routesConfig
});
router.afterEach((route) => {
const container = document.querySelector('.examples-container');
if (container) {
document.querySelector('.examples-container').scrollTop = 0;
}
setLang(route.meta.lang);
});
window.vueRouter = router;
if (process.env.NODE_ENV !== 'production') {
+2 -2
View File
@@ -2,11 +2,11 @@ import Vue from 'vue';
import VueRouter from 'vue-router';
import App from './DocsApp';
import routes from './router.config';
import ZanDoc from 'zan-doc';
import VantDoc from 'vant-doc';
import isMobile from './utils/is-mobile';
Vue.use(VueRouter);
Vue.use(ZanDoc);
Vue.use(VantDoc);
const routesConfig = routes();
+7 -10
View File
@@ -1,18 +1,15 @@
import docConfig from './doc.config';
import { getLang } from './utils/lang';
import DemoList from './components/demo-list';
import componentDocs from '../examples-dist/entry-docs';
import componentDemos from '../examples-dist/entry-demos';
import Demo from './components/demo';
import componentDocs from '../markdown';
import componentDemos from '../demos';
import { Demos } from 'vant-doc';
import Vue from 'vue';
import './utils/iframe-router';
const registerRoute = (isExample) => {
const route = [{
path: '/',
redirect: to => `/${getLang()}/`
}, {
path: '*',
redirect: to => `/${getLang()}/`
redirect: to => `/${Vue.prototype.$vantLang}/`
}];
Object.keys(docConfig).forEach((lang, index) => {
@@ -53,9 +50,9 @@ const registerRoute = (isExample) => {
let component;
if (path === '/demo') {
component = Demo;
component = Demos;
} else {
component = isExample ? componentDemos[name] : componentDocs[name];
component = isExample ? componentDemos[path.replace('/', '')] : componentDocs[name];
}
route.push({
+9 -8
View File
@@ -13,19 +13,20 @@ window.syncPath = function(dir) {
const iframe = document.querySelector('iframe');
if (!isInIframe && !isMobile && iframe) {
const pathParts = currentDir.split('/');
let lang = pathParts[0];
if (currentDir[0] === '/') {
lang = pathParts[1];
}
setLang(lang);
iframeReady(iframe, () => {
iframe.contentWindow.changePath(currentDir);
iframe.contentWindow.changePath(lang, currentDir);
});
}
};
window.changePath = function(path = '') {
const pathParts = path.split('/');
let lang = pathParts[0];
if (path[0] === '/') {
lang = pathParts[1];
}
window.changePath = function(lang, path = '') {
setLang(lang);
window.vueRouter.replace(path);
};
+11 -7
View File
@@ -1,16 +1,20 @@
import Locale from '../../../packages/locale';
import zhCN from '../../../packages/locale/lang/zh-CN';
import enUS from '../../../packages/locale/lang/en-US';
const langMap = {
'en-US': enUS,
'zh-CN': zhCN
};
const userLang = window.localStorage.getItem('VANT_LANGUAGE') || window.navigator.language || 'en-US';
let defaultLang = 'en-US';
if (userLang.indexOf('zh-') !== -1) {
defaultLang = 'zh-CN';
}
let currentLang = defaultLang;
export function getLang() {
return currentLang;
}
setLang(defaultLang);
export function setLang(lang) {
window.localStorage.setItem('VANT_LANGUAGE', lang);
currentLang = lang;
Locale.use(lang, langMap[lang]);
}