Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: support i18n #1339

Merged
merged 46 commits into from
Jan 17, 2023
Merged
Show file tree
Hide file tree
Changes from 9 commits
Commits
Show all changes
46 commits
Select commit Hold shift + click to select a range
84e85b2
merge feat-i18n
brc-dd Sep 9, 2022
cf77a39
fix carbon ads
brc-dd Sep 9, 2022
533ebd8
Merge branch 'main' into feat/i18n-next
brc-dd Sep 9, 2022
5ed5ff9
feat: support using .vitepress/config/index.ts
brc-dd Sep 9, 2022
74f0206
feat: merge theme config too
brc-dd Sep 10, 2022
2509ab9
fix: don't add base to relative links
brc-dd Sep 10, 2022
ad8a368
fix: don't remove relative part from url during normalization
brc-dd Sep 10, 2022
b2a89ca
Merge branch 'main' into feat/i18n-next
brc-dd Sep 14, 2022
fd0beb5
feat: allow specifying dir attribute for html
brc-dd Sep 14, 2022
df14075
remove stuff from translations
brc-dd Sep 16, 2022
f18132c
Merge branch 'main' into feat/i18n-next
brc-dd Sep 16, 2022
89ed8eb
Merge branch 'main' into feat/i18n-next
brc-dd Sep 21, 2022
a0f4e1e
Merge branch 'main' into feat/i18n-next
brc-dd Sep 24, 2022
7ea68f4
Merge branch 'main' into feat/i18n-next
brc-dd Sep 28, 2022
335c0b3
feat: use current locale link in 404 page
brc-dd Sep 28, 2022
4d35ae5
Merge branch 'main' into feat/i18n-next
brc-dd Sep 28, 2022
4884707
Merge branch 'main' into feat/i18n-next
brc-dd Sep 28, 2022
01bae65
Merge branch 'main' into feat/i18n-next
brc-dd Oct 11, 2022
064857c
fix(theme): properly apply base in locale links
brc-dd Oct 11, 2022
5df3e19
Merge branch 'main' into feat/i18n-next
brc-dd Oct 13, 2022
49fe1b0
Merge branch 'main' into feat/i18n-next
brc-dd Oct 20, 2022
50d1202
Merge branch 'main' into feat/i18n-next
brc-dd Nov 2, 2022
3f89591
Merge branch 'main' into feat/i18n-next
brc-dd Nov 7, 2022
b4e1483
feat(theme): add rtlcss directive (#1512)
sadeghbarati Nov 7, 2022
43fdc7c
Merge branch 'main' into feat/i18n-next
brc-dd Nov 18, 2022
bf129ec
Merge branch 'main' into feat/i18n-next
brc-dd Dec 5, 2022
0075b27
feat: multilingual search
brc-dd Dec 7, 2022
5322e4b
revert: useData type to any
brc-dd Dec 7, 2022
907de58
use typed useData in theme-default
brc-dd Dec 7, 2022
2b65d80
Merge branch 'main' into feat/i18n-next
brc-dd Dec 11, 2022
8392442
Merge branch 'main' into feat/i18n-next
brc-dd Dec 21, 2022
f77b51f
feat: go to corresponding link on changing locale
brc-dd Dec 21, 2022
e842edf
feat: allow disabling automatic locale link mapping
brc-dd Dec 21, 2022
f185032
fix i18n routing for root locale
brc-dd Dec 21, 2022
aa82162
Merge branch 'main' into feat/i18n-next
brc-dd Jan 4, 2023
4306708
fix merge
brc-dd Jan 4, 2023
857d97e
fix?
brc-dd Jan 4, 2023
f748f8a
Merge branch 'main' into feat/i18n-next
brc-dd Jan 8, 2023
7e217a8
Merge branch 'main' into feat/i18n-next
brc-dd Jan 12, 2023
3d0ce5d
fix ts
brc-dd Jan 12, 2023
12c9a1f
fix locale change on home page
brc-dd Jan 13, 2023
b2ac950
docs
brc-dd Jan 13, 2023
5559bb3
fix conflicts
brc-dd Jan 17, 2023
511911b
Merge branch 'main' into feat/i18n-next
brc-dd Jan 17, 2023
7ca1b9f
fix conflicts
brc-dd Jan 17, 2023
12f8253
Merge branch 'main' into feat/i18n-next
brc-dd Jan 17, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 8 additions & 12 deletions src/client/app/data.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,9 @@ import {
PageData,
SiteData,
resolveSiteDataByRoute,
createTitle
createTitle,
DefaultTheme
} from '../shared.js'
import { withBase } from './utils.js'

export const dataSymbol: InjectionKey<VitePressData> = Symbol()

Expand All @@ -19,7 +19,8 @@ export interface VitePressData<T = any> {
title: Ref<string>
description: Ref<string>
lang: Ref<string>
localePath: Ref<string>
dir: Ref<string>
localeIndex: Ref<string>
}

// site data is a singleton
Expand All @@ -39,7 +40,7 @@ if (import.meta.hot) {
// per-app data
export function initData(route: Route): VitePressData {
const site = computed(() =>
resolveSiteDataByRoute(siteDataRef.value, route.path)
resolveSiteDataByRoute(siteDataRef.value, route.data.relativePath)
)

return {
Expand All @@ -48,13 +49,8 @@ export function initData(route: Route): VitePressData {
page: computed(() => route.data),
frontmatter: computed(() => route.data.frontmatter),
lang: computed(() => site.value.lang),
localePath: computed(() => {
const { langs, lang } = site.value
const path = Object.keys(langs).find(
(langPath) => langs[langPath].lang === lang
)
return withBase(path || '/')
}),
dir: computed(() => site.value.dir),
localeIndex: computed(() => site.value.localeIndex || 'root'),
title: computed(() => {
return createTitle(site.value, route.data)
}),
Expand All @@ -64,7 +60,7 @@ export function initData(route: Route): VitePressData {
}
}

export function useData<T = any>(): VitePressData<T> {
export function useData<T = DefaultTheme.Config>(): VitePressData<T> {
const data = inject(dataSymbol)
if (!data) {
throw new Error('vitepress data not properly injected in app')
Expand Down
13 changes: 5 additions & 8 deletions src/client/app/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import {
defineComponent,
h,
onMounted,
watch
watchEffect
} from 'vue'
import Theme from '@theme/index'
import { inBrowser, pathToFile } from './utils.js'
Expand All @@ -27,13 +27,10 @@ const VitePressApp = defineComponent({

// change the language on the HTML element based on the current lang
onMounted(() => {
watch(
() => site.value.lang,
(lang: string) => {
document.documentElement.lang = lang
},
{ immediate: true }
)
watchEffect(() => {
document.documentElement.lang = site.value.lang
document.documentElement.dir = site.value.dir
})
})

if (import.meta.env.PROD) {
Expand Down
4 changes: 2 additions & 2 deletions src/client/app/utils.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { siteDataRef } from './data.js'
import { inBrowser, EXTERNAL_URL_RE } from '../shared.js'

export { inBrowser }
export { inBrowser } from '../shared.js'

/**
* Join two paths by resolving the slash collision.
Expand All @@ -11,7 +11,7 @@ export function joinPath(base: string, path: string): string {
}

export function withBase(path: string) {
return EXTERNAL_URL_RE.test(path)
return EXTERNAL_URL_RE.test(path) || path.startsWith('.')
? path
: joinPath(siteDataRef.value.base, path)
}
Expand Down
3 changes: 1 addition & 2 deletions src/client/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,7 @@ export type {
PageData,
SiteData,
HeadConfig,
Header,
LocaleConfig
Header
} from '../../types/shared.js'

// composables
Expand Down
8 changes: 6 additions & 2 deletions src/client/theme-default/components/VPAlgoliaSearchBox.vue
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,16 @@ import { default as docsearch } from '@docsearch/js'
import { onMounted } from 'vue'
import { useRouter, useRoute, useData } from 'vitepress'

const props = defineProps<{
algolia: DefaultTheme.AlgoliaSearchOptions
}>()

const router = useRouter()
const route = useRoute()
const { theme, site } = useData()
const { site } = useData()

onMounted(() => {
initialize(theme.value.algolia)
initialize(props.algolia)
setTimeout(poll, 16)
})

Expand Down
9 changes: 6 additions & 3 deletions src/client/theme-default/components/VPCarbonAds.vue
Original file line number Diff line number Diff line change
@@ -1,10 +1,13 @@
<script setup lang="ts">
import type { DefaultTheme } from 'vitepress/theme'
import { ref, watch, onMounted } from 'vue'
import { useData } from 'vitepress'
import { useAside } from '../composables/aside.js'

const { theme } = useData()
const carbonOptions = theme.value.carbonAds
const props = defineProps<{
carbonAds: DefaultTheme.CarbonAdsOptions
}>()

const carbonOptions = props.carbonAds
const { isAsideEnabled } = useAside()
const container = ref()

Expand Down
8 changes: 6 additions & 2 deletions src/client/theme-default/components/VPDocAside.vue
Original file line number Diff line number Diff line change
@@ -1,9 +1,13 @@
<script setup lang="ts">
import { defineAsyncComponent } from 'vue'
import { useData } from 'vitepress'
import VPDocAsideOutline from './VPDocAsideOutline.vue'
import VPDocAsideCarbonAds from './VPDocAsideCarbonAds.vue'

const { theme } = useData()

const VPCarbonAds = __CARBON__
? defineAsyncComponent(() => import('./VPCarbonAds.vue'))
: () => null
</script>

<template>
Expand All @@ -17,7 +21,7 @@ const { theme } = useData()
<div class="spacer" />

<slot name="aside-ads-before" />
<VPDocAsideCarbonAds v-if="theme.carbonAds" />
<VPCarbonAds v-if="theme.carbonAds" :carbonAds="theme.carbonAds" />
<slot name="aside-ads-after" />

<slot name="aside-bottom" />
Expand Down
13 changes: 0 additions & 13 deletions src/client/theme-default/components/VPDocAsideCarbonAds.vue

This file was deleted.

2 changes: 1 addition & 1 deletion src/client/theme-default/components/VPDocAsideOutline.vue
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ function handleClick({ target: el }: Event) {
<div class="outline-marker" ref="marker" />

<div class="outline-title">
{{ theme.outlineTitle || 'On this page' }}
{{ theme.translations?.outlineTitle || 'On this page' }}
</div>

<nav aria-labelledby="doc-outline-aria-label">
Expand Down
4 changes: 2 additions & 2 deletions src/client/theme-default/components/VPDocFooter.vue
Original file line number Diff line number Diff line change
Expand Up @@ -42,13 +42,13 @@ const showFooter = computed(() => {
<div v-if="control.prev || control.next" class="prev-next">
<div class="pager">
<a v-if="control.prev" class="pager-link prev" :href="normalizeLink(control.prev.link)">
<span class="desc">{{ theme.docFooter?.prev ?? 'Previous page' }}</span>
<span class="desc">{{ theme.translations?.docFooter?.prev || 'Previous page' }}</span>
<span class="title">{{ control.prev.text }} </span>
</a>
</div>
<div class="pager" :class="{ 'has-prev': control.prev }">
<a v-if="control.next" class="pager-link next" :href="normalizeLink(control.next.link)">
<span class="desc">{{ theme.docFooter?.next ?? 'Next page' }}</span>
<span class="desc">{{ theme.translations?.docFooter?.next || 'Next page' }}</span>
<span class="title">{{ control.next.text }}</span>
</a>
</div>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ onMounted(() => {

<template>
<p class="VPLastUpdated">
{{ theme.lastUpdatedText ?? 'Last updated' }}:
{{ theme.translations?.lastUpdatedText || 'Last updated' }}:
<time :datatime="isoDatetime">{{ datetime }}</time>
</p>
</template>
Expand Down
8 changes: 6 additions & 2 deletions src/client/theme-default/components/VPLocalNav.vue
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
<script lang="ts" setup>
import { useData } from 'vitepress'
import { useSidebar } from '../composables/sidebar.js'
import VPIconAlignLeft from './icons/VPIconAlignLeft.vue'

Expand All @@ -10,6 +11,7 @@ defineEmits<{
(e: 'open-menu'): void
}>()

const { theme } = useData()
const { hasSidebar } = useSidebar()

function scrollToTop() {
Expand All @@ -26,11 +28,13 @@ function scrollToTop() {
@click="$emit('open-menu')"
>
<VPIconAlignLeft class="menu-icon" />
<span class="menu-text">Menu</span>
<span class="menu-text">
{{ theme.translations?.sidebarMenuLabel || 'Menu' }}
</span>
</button>

<a class="top-link" href="#" @click="scrollToTop">
Return to top
{{ theme.translations?.returnToTopLabel || 'Return to top' }}
</a>
</div>
</template>
Expand Down
21 changes: 15 additions & 6 deletions src/client/theme-default/components/VPNavBarExtra.vue
Original file line number Diff line number Diff line change
@@ -1,29 +1,38 @@
<script lang="ts" setup>
import { useData } from 'vitepress'
import { computed } from 'vue'
import VPFlyout from './VPFlyout.vue'
import VPMenuLink from './VPMenuLink.vue'
import VPSwitchAppearance from './VPSwitchAppearance.vue'
import VPSocialLinks from './VPSocialLinks.vue'
import { computed } from 'vue'
import { useLangs } from '../composables/langs.js'

const { site, theme } = useData()
const { localeLinks, currentLang } = useLangs()

const hasExtraContent = computed(() => theme.value.localeLinks || site.value.appearance || theme.value.socialLinks)
const hasExtraContent = computed(
() =>
(localeLinks.value.length && currentLang.value.label) ||
site.value.appearance ||
theme.value.socialLinks
)
</script>

<template>
<VPFlyout v-if="hasExtraContent" class="VPNavBarExtra" label="extra navigation">
<div v-if="theme.localeLinks" class="group">
<p class="trans-title">{{ theme.localeLinks.text }}</p>
<div v-if="localeLinks.length && currentLang.label" class="group">
<p class="trans-title">{{ currentLang.label }}</p>

<template v-for="locale in theme.localeLinks.items" :key="locale.link">
<template v-for="locale in localeLinks" :key="locale.link">
<VPMenuLink :item="locale" />
</template>
</div>

<div v-if="site.appearance" class="group">
<div class="item appearance">
<p class="label">Appearance</p>
<p class="label">
{{ theme.translations?.darkModeSwitchLabel || 'Appearance' }}
</p>
<div class="appearance-action">
<VPSwitchAppearance />
</div>
Expand Down
2 changes: 1 addition & 1 deletion src/client/theme-default/components/VPNavBarSearch.vue
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ function load() {

<template>
<div v-if="theme.algolia" class="VPNavBarSearch">
<VPAlgoliaSearchBox v-if="loaded" />
<VPAlgoliaSearchBox v-if="loaded" :algolia="theme.algolia" />

<div v-else id="docsearch" @click="load">
<button
Expand Down
7 changes: 5 additions & 2 deletions src/client/theme-default/components/VPNavBarTitle.vue
Original file line number Diff line number Diff line change
@@ -1,17 +1,20 @@
<script setup lang="ts">
import { useData } from 'vitepress'
import { useSidebar } from '../composables/sidebar.js'
import { useLangs } from '../composables/langs.js'
import { normalizeLink } from '../support/utils.js'
import VPImage from './VPImage.vue'

const { site, theme } = useData()
const { hasSidebar } = useSidebar()
const { currentLang } = useLangs()
</script>

<template>
<div class="VPNavBarTitle" :class="{ 'has-sidebar': hasSidebar }">
<a class="title" :href="site.base">
<a class="title" :href="normalizeLink(currentLang.link)">
<slot name="nav-bar-title-before" />
<VPImage class="logo" :image="theme.logo" />
<VPImage v-if="theme.logo" class="logo" :image="theme.logo" />
<template v-if="theme.siteTitle">{{ theme.siteTitle }}</template>
<template v-else-if="theme.siteTitle === undefined">{{ site.title }}</template>
<slot name="nav-bar-title-after" />
Expand Down
10 changes: 5 additions & 5 deletions src/client/theme-default/components/VPNavBarTranslations.vue
Original file line number Diff line number Diff line change
@@ -1,22 +1,22 @@
<script lang="ts" setup>
import { useData } from 'vitepress'
import VPIconLanguages from './icons/VPIconLanguages.vue'
import VPFlyout from './VPFlyout.vue'
import VPMenuLink from './VPMenuLink.vue'
import { useLangs } from '../composables/langs.js'

const { theme } = useData()
const { localeLinks, currentLang } = useLangs()
</script>

<template>
<VPFlyout
v-if="theme.localeLinks"
v-if="localeLinks.length && currentLang.label"
class="VPNavBarTranslations"
:icon="VPIconLanguages"
>
<div class="items">
<p class="title">{{ theme.localeLinks.text }}</p>
<p class="title">{{ currentLang.label }}</p>

<template v-for="locale in theme.localeLinks.items" :key="locale.link">
<template v-for="locale in localeLinks" :key="locale.link">
<VPMenuLink :item="locale" />
</template>
</div>
Expand Down
6 changes: 4 additions & 2 deletions src/client/theme-default/components/VPNavScreenAppearance.vue
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,14 @@
import { useData } from 'vitepress'
import VPSwitchAppearance from './VPSwitchAppearance.vue'

const { site } = useData()
const { site, theme } = useData()
</script>

<template>
<div v-if="site.appearance" class="VPNavScreenAppearance">
<p class="text">Appearance</p>
<p class="text">
{{ theme.translations?.darkModeSwitchLabel || 'Appearance' }}
</p>
<VPSwitchAppearance />
</div>
</template>
Expand Down
Loading