add vue i18n

This commit is contained in:
LouisLam 2021-08-24 16:44:58 +08:00
parent 752ac05149
commit dd4c00eed3
7 changed files with 7791 additions and 477 deletions

8140
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -67,6 +67,7 @@
"vue": "^3.2.2", "vue": "^3.2.2",
"vue-chart-3": "^0.5.7", "vue-chart-3": "^0.5.7",
"vue-confirm-dialog": "^1.0.2", "vue-confirm-dialog": "^1.0.2",
"vue-i18n": "^9.1.7",
"vue-multiselect": "^3.0.0-alpha.2", "vue-multiselect": "^3.0.0-alpha.2",
"vue-router": "^4.0.11", "vue-router": "^4.0.11",
"vue-toastification": "^2.0.0-rc.1" "vue-toastification": "^2.0.0-rc.1"

3
src/languages/en.js Normal file
View File

@ -0,0 +1,3 @@
export default {
languageName: "English",
}

10
src/languages/zh-hk.js Normal file
View File

@ -0,0 +1,10 @@
export default {
languageName: "繁體中文 (香港)",
Settings: "設定",
Dashboard: "錶板",
"New Update": "有更新",
Language: "語言",
Appearance: "外觀",
Theme: "主題",
General: "一般",
}

View File

@ -14,18 +14,18 @@
</router-link> </router-link>
<a v-if="hasNewVersion" target="_blank" href="https://github.com/louislam/uptime-kuma/releases" class="btn btn-info me-3"> <a v-if="hasNewVersion" target="_blank" href="https://github.com/louislam/uptime-kuma/releases" class="btn btn-info me-3">
<font-awesome-icon icon="arrow-alt-circle-up" /> New Update <font-awesome-icon icon="arrow-alt-circle-up" /> {{ $t("New Update") }}
</a> </a>
<ul class="nav nav-pills"> <ul class="nav nav-pills">
<li class="nav-item"> <li class="nav-item">
<router-link to="/dashboard" class="nav-link"> <router-link to="/dashboard" class="nav-link">
<font-awesome-icon icon="tachometer-alt" /> Dashboard <font-awesome-icon icon="tachometer-alt" /> {{ $t("Dashboard") }}
</router-link> </router-link>
</li> </li>
<li class="nav-item"> <li class="nav-item">
<router-link to="/settings" class="nav-link"> <router-link to="/settings" class="nav-link">
<font-awesome-icon icon="cog" /> Settings <font-awesome-icon icon="cog" /> {{ $t("Settings") }}
</router-link> </router-link>
</li> </li>
</ul> </ul>
@ -58,7 +58,7 @@
<nav v-if="$root.isMobile" class="bottom-nav"> <nav v-if="$root.isMobile" class="bottom-nav">
<router-link to="/dashboard" class="nav-link"> <router-link to="/dashboard" class="nav-link">
<div><font-awesome-icon icon="tachometer-alt" /></div> <div><font-awesome-icon icon="tachometer-alt" /></div>
Dashboard {{ $t("Dashboard") }}
</router-link> </router-link>
<router-link to="/list" class="nav-link"> <router-link to="/list" class="nav-link">
@ -73,7 +73,7 @@
<router-link to="/settings" class="nav-link"> <router-link to="/settings" class="nav-link">
<div><font-awesome-icon icon="cog" /></div> <div><font-awesome-icon icon="cog" /></div>
Settings {{ $t("Settings") }}
</router-link> </router-link>
</nav> </nav>
</div> </div>

View File

@ -1,5 +1,6 @@
import "bootstrap"; import "bootstrap";
import { createApp, h } from "vue"; import { createApp, h } from "vue";
import { createI18n } from "vue-i18n"
import { createRouter, createWebHistory } from "vue-router"; import { createRouter, createWebHistory } from "vue-router";
import Toast from "vue-toastification"; import Toast from "vue-toastification";
import "vue-toastification/dist/index.css"; import "vue-toastification/dist/index.css";
@ -22,6 +23,9 @@ import List from "./pages/List.vue";
import { appName } from "./util.ts"; import { appName } from "./util.ts";
import en from "./languages/en";
import zhHK from "./languages/zh-hk";
const routes = [ const routes = [
{ {
path: "/", path: "/",
@ -83,6 +87,19 @@ const router = createRouter({
routes, routes,
}) })
const languageList = {
en,
zhHK,
};
const i18n = createI18n({
locale: localStorage.locale || "en",
fallbackLocale: "en",
silentFallbackWarn: true,
silentTranslationWarn: true,
messages: languageList
});
const app = createApp({ const app = createApp({
mixins: [ mixins: [
socket, socket,
@ -98,7 +115,8 @@ const app = createApp({
render: () => h(App), render: () => h(App),
}) })
app.use(router) app.use(router);
app.use(i18n);
const options = { const options = {
position: "bottom-right", position: "bottom-right",

View File

@ -2,48 +2,58 @@
<transition name="slide-fade" appear> <transition name="slide-fade" appear>
<div> <div>
<h1 v-show="show" class="mb-3"> <h1 v-show="show" class="mb-3">
Settings {{ $t("Settings") }}
</h1> </h1>
<div class="shadow-box"> <div class="shadow-box">
<div class="row"> <div class="row">
<div class="col-md-6"> <div class="col-md-6">
<h2 class="mb-2">General</h2> <h2 class="mb-2">{{ $t("Appearance") }}</h2>
<div class="mb-3">
<label for="language" class="form-label">{{ $t("Language") }}</label>
<select id="language" v-model="$i18n.locale" class="form-select">
<option v-for="(lang, i) in $i18n.availableLocales" :key="`Lang${i}`" :value="lang">
{{ $i18n.messages[lang].languageName }}
</option>
</select>
</div>
<div class="mb-3">
<label for="timezone" class="form-label">{{ $t("Theme") }}</label>
<div>
<div class="btn-group" role="group" aria-label="Basic checkbox toggle button group">
<input id="btncheck1" v-model="$root.userTheme" type="radio" class="btn-check" name="theme" autocomplete="off" value="light">
<label class="btn btn-outline-primary" for="btncheck1">Light</label>
<input id="btncheck2" v-model="$root.userTheme" type="radio" class="btn-check" name="theme" autocomplete="off" value="dark">
<label class="btn btn-outline-primary" for="btncheck2">Dark</label>
<input id="btncheck3" v-model="$root.userTheme" type="radio" class="btn-check" name="theme" autocomplete="off" value="auto">
<label class="btn btn-outline-primary" for="btncheck3">Auto</label>
</div>
</div>
</div>
<div class="mb-3">
<label class="form-label">Theme - Heartbeat Bar</label>
<div>
<div class="btn-group" role="group" aria-label="Basic checkbox toggle button group">
<input id="btncheck4" v-model="$root.userHeartbeatBar" type="radio" class="btn-check" name="heartbeatBarTheme" autocomplete="off" value="normal">
<label class="btn btn-outline-primary" for="btncheck4">Normal</label>
<input id="btncheck5" v-model="$root.userHeartbeatBar" type="radio" class="btn-check" name="heartbeatBarTheme" autocomplete="off" value="bottom">
<label class="btn btn-outline-primary" for="btncheck5">Bottom</label>
<input id="btncheck6" v-model="$root.userHeartbeatBar" type="radio" class="btn-check" name="heartbeatBarTheme" autocomplete="off" value="none">
<label class="btn btn-outline-primary" for="btncheck6">None</label>
</div>
</div>
</div>
<h2 class="mt-5 mb-2">{{ $t("General") }}</h2>
<form class="mb-3" @submit.prevent="saveGeneral"> <form class="mb-3" @submit.prevent="saveGeneral">
<div class="mb-3">
<label for="timezone" class="form-label">Theme</label>
<div>
<div class="btn-group" role="group" aria-label="Basic checkbox toggle button group">
<input id="btncheck1" v-model="$root.userTheme" type="radio" class="btn-check" name="theme" autocomplete="off" value="light">
<label class="btn btn-outline-primary" for="btncheck1">Light</label>
<input id="btncheck2" v-model="$root.userTheme" type="radio" class="btn-check" name="theme" autocomplete="off" value="dark">
<label class="btn btn-outline-primary" for="btncheck2">Dark</label>
<input id="btncheck3" v-model="$root.userTheme" type="radio" class="btn-check" name="theme" autocomplete="off" value="auto">
<label class="btn btn-outline-primary" for="btncheck3">Auto</label>
</div>
</div>
</div>
<div class="mb-3">
<label class="form-label">Theme - Heartbeat Bar</label>
<div>
<div class="btn-group" role="group" aria-label="Basic checkbox toggle button group">
<input id="btncheck4" v-model="$root.userHeartbeatBar" type="radio" class="btn-check" name="heartbeatBarTheme" autocomplete="off" value="normal">
<label class="btn btn-outline-primary" for="btncheck4">Normal</label>
<input id="btncheck5" v-model="$root.userHeartbeatBar" type="radio" class="btn-check" name="heartbeatBarTheme" autocomplete="off" value="bottom">
<label class="btn btn-outline-primary" for="btncheck5">Bottom</label>
<input id="btncheck6" v-model="$root.userHeartbeatBar" type="radio" class="btn-check" name="heartbeatBarTheme" autocomplete="off" value="none">
<label class="btn btn-outline-primary" for="btncheck6">None</label>
</div>
</div>
</div>
<div class="mb-3"> <div class="mb-3">
<label for="timezone" class="form-label">Timezone</label> <label for="timezone" class="form-label">Timezone</label>
<select id="timezone" v-model="$root.userTimezone" class="form-select"> <select id="timezone" v-model="$root.userTimezone" class="form-select">
@ -195,6 +205,10 @@ export default {
"password.repeatNewPassword"() { "password.repeatNewPassword"() {
this.invalidPassword = false; this.invalidPassword = false;
}, },
"$i18n.locale"() {
localStorage.locale = this.$i18n.locale;
},
}, },
mounted() { mounted() {