mirror of
https://github.com/mealie-recipes/mealie.git
synced 2025-07-09 03:04:54 -04:00
Localize more dates and texts (#341)
* Localize more dates and texts * Adapt source language to 4-letter code for VS code * Make page titles more reactive to language change * Translate missing text + fix missed refactoring * Fix missed page titles refactoring * Translate nutrition view * Translate Image upload vue * Fix default text being defined twice in upload btn
This commit is contained in:
parent
048d3d5469
commit
80f8806604
2
.vscode/settings.json
vendored
2
.vscode/settings.json
vendored
@ -10,7 +10,7 @@
|
||||
"python.testing.pytestArgs": ["tests"],
|
||||
"cSpell.enableFiletypes": ["!javascript", "!python"],
|
||||
"i18n-ally.localesPaths": "frontend/src/locales/messages",
|
||||
"i18n-ally.sourceLanguage": "en",
|
||||
"i18n-ally.sourceLanguage": "en-US",
|
||||
"i18n-ally.enabledFrameworks": ["vue"],
|
||||
"i18n-ally.keystyle": "nested",
|
||||
"cSpell.words": ["performant"],
|
||||
|
@ -3,7 +3,7 @@
|
||||
<v-card-title class=" headline">
|
||||
{{ $t("meal-plan.create-a-new-meal-plan") }}
|
||||
<v-btn color="info" class="ml-auto" @click="setQuickWeek()">
|
||||
<v-icon left>mdi-calendar-minus</v-icon> Quick Week
|
||||
<v-icon left>mdi-calendar-minus</v-icon> {{$t('meal-plan.quick-week')}}
|
||||
</v-btn>
|
||||
</v-card-title>
|
||||
|
||||
@ -110,7 +110,6 @@ export default {
|
||||
this.meals.push({
|
||||
slug: "empty",
|
||||
date: this.getDate(i),
|
||||
dateText: this.getDayText(i),
|
||||
});
|
||||
}
|
||||
},
|
||||
@ -193,10 +192,6 @@ export default {
|
||||
);
|
||||
return dateText;
|
||||
},
|
||||
getDayText(index) {
|
||||
const dateObj = this.processTime(index);
|
||||
return utils.getDateAsText(dateObj);
|
||||
},
|
||||
getDate(index) {
|
||||
const dateObj = this.processTime(index);
|
||||
return utils.getDateAsPythonDate(dateObj);
|
||||
|
@ -3,10 +3,10 @@
|
||||
<v-dialog v-model="dialog" width="650">
|
||||
<v-card>
|
||||
<v-card-title class="headline">
|
||||
Shopping List
|
||||
{{$t('meal-plan.shopping-list')}}
|
||||
<v-spacer></v-spacer>
|
||||
<v-btn text color="accent" @click="group = !group">
|
||||
Group (Beta)
|
||||
{{$t('meal-plan.group')}}
|
||||
</v-btn>
|
||||
</v-card-title>
|
||||
<v-divider></v-divider>
|
||||
|
@ -3,13 +3,13 @@
|
||||
<v-menu offset-y top nudge-top="6" :close-on-content-click="false">
|
||||
<template v-slot:activator="{ on, attrs }">
|
||||
<v-btn color="accent" dark v-bind="attrs" v-on="on">
|
||||
Image
|
||||
{{$t('recipe.image')}}
|
||||
</v-btn>
|
||||
</template>
|
||||
<v-card width="400">
|
||||
<v-card-title class="headline flex mb-0">
|
||||
<div>
|
||||
Recipe Image
|
||||
{{$t('recipe.recipe-image')}}
|
||||
</div>
|
||||
<TheUploadBtn
|
||||
class="ml-auto"
|
||||
@ -22,7 +22,7 @@
|
||||
</v-card-title>
|
||||
<v-card-text class="mt-n5">
|
||||
<div>
|
||||
<v-text-field label="URL" class="pt-5" clearable v-model="url">
|
||||
<v-text-field :label="$t('general.url')" class="pt-5" clearable v-model="url">
|
||||
<template v-slot:append-outer>
|
||||
<v-btn
|
||||
class="ml-2"
|
||||
@ -30,7 +30,7 @@
|
||||
@click="getImageFromURL"
|
||||
:loading="loading"
|
||||
>
|
||||
Get
|
||||
{{$t('general.get')}}
|
||||
</v-btn>
|
||||
</template>
|
||||
</v-text-field>
|
||||
@ -46,7 +46,6 @@ const REFRESH_EVENT = "refresh";
|
||||
const UPLOAD_EVENT = "upload";
|
||||
import TheUploadBtn from "@/components/UI/Buttons/TheUploadBtn";
|
||||
import { api } from "@/api";
|
||||
// import axios from "axios";
|
||||
export default {
|
||||
components: {
|
||||
TheUploadBtn,
|
||||
@ -55,7 +54,6 @@ export default {
|
||||
slug: String,
|
||||
},
|
||||
data: () => ({
|
||||
items: [{ title: "Upload Image" }, { title: "From URL" }],
|
||||
url: "",
|
||||
loading: false,
|
||||
}),
|
||||
|
@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<div v-if="valueNotNull || edit">
|
||||
<h2 class="my-4">Nutrition</h2>
|
||||
<h2 class="my-4">{{$t('recipe.nutrition')}}</h2>
|
||||
<div v-if="edit">
|
||||
<div v-for="(item, key, index) in value" :key="index">
|
||||
<v-text-field
|
||||
@ -45,14 +45,14 @@ export default {
|
||||
return {
|
||||
labels: {
|
||||
calories: {
|
||||
label: "Calories",
|
||||
suffix: "calories",
|
||||
label: this.$t('recipe.calories'),
|
||||
suffix:this.$t('recipe.calories-suffix'),
|
||||
},
|
||||
fatContent: { label: "Fat Content", suffix: "grams" },
|
||||
fiberContent: { label: "Fiber Content", suffix: "grams" },
|
||||
proteinContent: { label: "Protein Content", suffix: "grams" },
|
||||
sodiumContent: { label: "Sodium Content", suffix: "milligrams" },
|
||||
sugarContent: { label: "Sugar Content", suffix: "grams" },
|
||||
fatContent: { label: this.$t('recipe.fat-content'), suffix: this.$t('recipe.grams') },
|
||||
fiberContent: { label: this.$t('recipe.fiber-content'), suffix: this.$t('recipe.grams') },
|
||||
proteinContent: { label: this.$t('recipe.protein-content'), suffix: this.$t('recipe.grams') },
|
||||
sodiumContent: { label: this.$t('recipe.sodium-content'), suffix: this.$t('recipe.milligrams') },
|
||||
sugarContent: { label: this.$t('recipe.sugar-content'), suffix: this.$t('recipe.grams') },
|
||||
},
|
||||
};
|
||||
},
|
||||
|
@ -23,7 +23,7 @@ export default {
|
||||
default: true,
|
||||
},
|
||||
url: String,
|
||||
text: { default: "Upload" },
|
||||
text: String,
|
||||
icon: { default: "mdi-cloud-upload" },
|
||||
fileName: { default: "archive" },
|
||||
textBtn: {
|
||||
|
@ -3,5 +3,11 @@
|
||||
"month": "short",
|
||||
"day": "numeric",
|
||||
"weekday": "long"
|
||||
},
|
||||
"medium": {
|
||||
"month": "long",
|
||||
"day": "numeric",
|
||||
"weekday": "long",
|
||||
"year": "numeric"
|
||||
}
|
||||
}
|
@ -56,7 +56,9 @@
|
||||
"thursday": "Thursday",
|
||||
"friday": "Friday",
|
||||
"saturday": "Saturday",
|
||||
"about": "About"
|
||||
"about": "About",
|
||||
"get": "Get",
|
||||
"url": "URL"
|
||||
},
|
||||
"page": {
|
||||
"home-page": "Home Page",
|
||||
@ -122,7 +124,9 @@
|
||||
"create-a-new-meal-plan": "Create a New Meal Plan",
|
||||
"start-date": "Start Date",
|
||||
"end-date": "End Date",
|
||||
"only-recipes-with-these-categories-will-be-used-in-meal-plans": "Only recipes with these categories will be used in Meal Plans"
|
||||
"only-recipes-with-these-categories-will-be-used-in-meal-plans": "Only recipes with these categories will be used in Meal Plans",
|
||||
"quick-week": "Quick Week",
|
||||
"group": "Group (Beta)"
|
||||
},
|
||||
"recipe": {
|
||||
"description": "Description",
|
||||
@ -150,7 +154,19 @@
|
||||
"key-name-required": "Key Name Required",
|
||||
"no-white-space-allowed": "No White Space Allowed",
|
||||
"delete-recipe": "Delete Recipe",
|
||||
"delete-confirmation": "Are you sure you want to delete this recipe?"
|
||||
"delete-confirmation": "Are you sure you want to delete this recipe?",
|
||||
"nutrition": "Nutrition",
|
||||
"calories": "Calories",
|
||||
"calories-suffix": "calories",
|
||||
"fat-content": "Fat Content",
|
||||
"fiber-content": "Fiber Content",
|
||||
"protein-content": "Protein Content",
|
||||
"sodium-content": "Sodium Content",
|
||||
"sugar-content": "Sugar Content",
|
||||
"grams": "grams",
|
||||
"milligrams": "milligrams",
|
||||
"recipe-image": "Recipe Image",
|
||||
"image": "Image"
|
||||
},
|
||||
"search": {
|
||||
"search-mealie": "Search Mealie",
|
||||
@ -238,7 +254,8 @@
|
||||
"custom-pages": "Custom Pages",
|
||||
"new-page": "New Page",
|
||||
"edit-page": "Edit Page",
|
||||
"page-name": "Page Name"
|
||||
"page-name": "Page Name",
|
||||
"remove-existing-entries-matching-imported-entries": "Remove existing entries matching imported entries"
|
||||
},
|
||||
"migration": {
|
||||
"recipe-migration": "Recipe Migration",
|
||||
|
@ -27,7 +27,7 @@
|
||||
<div class="text-truncate">
|
||||
<strong>{{ backup.name }}</strong>
|
||||
</div>
|
||||
<div class="text-truncate">{{ readableTime(backup.date) }}</div>
|
||||
<div class="text-truncate">{{ $d(new Date(backup.date), "medium") }}</div>
|
||||
</v-col>
|
||||
</v-row>
|
||||
</v-card-text>
|
||||
@ -40,7 +40,6 @@
|
||||
<script>
|
||||
import ImportDialog from "./ImportDialog";
|
||||
import { api } from "@/api";
|
||||
import utils from "@/utils";
|
||||
export default {
|
||||
props: {
|
||||
backups: Array,
|
||||
@ -57,14 +56,10 @@ export default {
|
||||
},
|
||||
methods: {
|
||||
openDialog(backup) {
|
||||
this.selectedDate = this.readableTime(backup.date);
|
||||
this.selectedDate = backup.date;
|
||||
this.selectedName = backup.name;
|
||||
this.$refs.import_dialog.open();
|
||||
},
|
||||
readableTime(timestamp) {
|
||||
let date = new Date(timestamp);
|
||||
return utils.getDateAsText(date);
|
||||
},
|
||||
async importBackup(data) {
|
||||
this.$emit("loading");
|
||||
let response = await api.backups.import(data.name, data);
|
||||
|
@ -26,7 +26,7 @@
|
||||
<div>
|
||||
<strong>{{ backup.name }}</strong>
|
||||
</div>
|
||||
<div>{{ readableTime(backup.date) }}</div>
|
||||
<div>{{ $d(new Date(backup.date), "medium") }}</div>
|
||||
</v-col>
|
||||
</v-row>
|
||||
</v-card-text>
|
||||
@ -39,7 +39,6 @@
|
||||
<script>
|
||||
import ImportDialog from "./ImportDialog";
|
||||
import { api } from "@/api";
|
||||
import utils from "@/utils";
|
||||
export default {
|
||||
props: {
|
||||
backups: Array,
|
||||
@ -56,14 +55,10 @@ export default {
|
||||
},
|
||||
methods: {
|
||||
openDialog(backup) {
|
||||
this.selectedDate = this.readableTime(backup.date);
|
||||
this.selectedDate = backup.date;
|
||||
this.selectedName = backup.name;
|
||||
this.$refs.import_dialog.open();
|
||||
},
|
||||
readableTime(timestamp) {
|
||||
let date = new Date(timestamp);
|
||||
return utils.getDateAsText(date);
|
||||
},
|
||||
async importBackup(data) {
|
||||
this.$emit("loading");
|
||||
let response = await api.backups.import(data.name, data);
|
||||
|
@ -19,7 +19,7 @@
|
||||
</v-toolbar-items>
|
||||
</v-toolbar>
|
||||
<v-card-title> {{ name }} </v-card-title>
|
||||
<v-card-subtitle class="mb-n3"> {{ date }} </v-card-subtitle>
|
||||
<v-card-subtitle class="mb-n3"> {{ $d(new Date(date), "medium") }} </v-card-subtitle>
|
||||
<v-divider></v-divider>
|
||||
|
||||
<v-card-text>
|
||||
@ -29,7 +29,7 @@
|
||||
|
||||
<v-checkbox
|
||||
dense
|
||||
label="Remove existing entries matching imported entries"
|
||||
:label="$t('settings.remove-existing-entries-matching-imported-entries')"
|
||||
v-model="forceImport"
|
||||
></v-checkbox>
|
||||
</v-card-text>
|
||||
|
@ -32,7 +32,7 @@
|
||||
<strong>{{ migration.name }}</strong>
|
||||
</div>
|
||||
<div class="text-truncate">
|
||||
{{ readableTime(migration.date) }}
|
||||
{{ $d(new Date(migration.date), "medium") }}
|
||||
</div>
|
||||
</v-col>
|
||||
</v-row>
|
||||
@ -67,7 +67,6 @@
|
||||
|
||||
<script>
|
||||
import TheUploadBtn from "@/components/UI/Buttons/TheUploadBtn";
|
||||
import utils from "@/utils";
|
||||
import { api } from "@/api";
|
||||
import MigrationDialog from "./MigrationDialog";
|
||||
export default {
|
||||
@ -98,10 +97,6 @@ export default {
|
||||
// this.$emit("imported", response.successful, response.failed);
|
||||
this.loading = false;
|
||||
},
|
||||
readableTime(timestamp) {
|
||||
let date = new Date(timestamp);
|
||||
return utils.getDateAsText(date);
|
||||
},
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
@ -112,10 +112,6 @@ export default {
|
||||
generateKey(name, index) {
|
||||
return utils.generateUniqueKey(name, index);
|
||||
},
|
||||
formatDate(timestamp) {
|
||||
let dateObject = new Date(timestamp);
|
||||
return utils.getDateAsTextAlt(dateObject);
|
||||
},
|
||||
getImage(image) {
|
||||
return api.recipes.recipeTinyImage(image);
|
||||
},
|
||||
|
@ -8,7 +8,6 @@ import ManageUsers from "@/pages/Admin/ManageUsers";
|
||||
import Settings from "@/pages/Admin/Settings";
|
||||
import About from "@/pages/Admin/About";
|
||||
import { store } from "../store";
|
||||
import i18n from '@/i18n.js';
|
||||
|
||||
export const adminRoutes = {
|
||||
path: "/admin",
|
||||
@ -27,7 +26,7 @@ export const adminRoutes = {
|
||||
path: "profile",
|
||||
component: Profile,
|
||||
meta: {
|
||||
title: i18n.t('settings.profile'),
|
||||
title: "settings.profile",
|
||||
},
|
||||
},
|
||||
|
||||
@ -35,49 +34,49 @@ export const adminRoutes = {
|
||||
path: "backups",
|
||||
component: Backup,
|
||||
meta: {
|
||||
title: i18n.t('settings.backup-and-exports'),
|
||||
title: "settings.backup-and-exports",
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "themes",
|
||||
component: Theme,
|
||||
meta: {
|
||||
title: i18n.t('general.themes'),
|
||||
title: "general.themes",
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "meal-planner",
|
||||
component: MealPlanner,
|
||||
meta: {
|
||||
title: i18n.t('meal-plan.meal-planner'),
|
||||
title: "meal-plan.meal-planner",
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "migrations",
|
||||
component: Migration,
|
||||
meta: {
|
||||
title: i18n.t('settings.migrations'),
|
||||
title: "settings.migrations",
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "manage-users",
|
||||
component: ManageUsers,
|
||||
meta: {
|
||||
title: i18n.t('settings.manage-users'),
|
||||
title: "settings.manage-users",
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "settings",
|
||||
component: Settings,
|
||||
meta: {
|
||||
title: i18n.t('settings.site-settings'),
|
||||
title: "settings.site-settings",
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "about",
|
||||
component: About,
|
||||
meta: {
|
||||
title: i18n.t('general.about'),
|
||||
title: "general.about",
|
||||
},
|
||||
},
|
||||
],
|
||||
|
@ -1,4 +1,3 @@
|
||||
import i18n from "@/i18n.js";
|
||||
import SearchPage from "@/pages/SearchPage";
|
||||
import HomePage from "@/pages/HomePage";
|
||||
|
||||
@ -9,7 +8,7 @@ export const generalRoutes = [
|
||||
path: "/search",
|
||||
component: SearchPage,
|
||||
meta: {
|
||||
title: i18n.t("search.search"),
|
||||
title: "search.search",
|
||||
},
|
||||
},
|
||||
];
|
||||
|
@ -9,6 +9,7 @@ import VueRouter from "vue-router";
|
||||
import VueI18n from "@/i18n";
|
||||
import Vuetify from "@/plugins/vuetify";
|
||||
import Vue from "vue";
|
||||
import i18n from '@/i18n.js';
|
||||
|
||||
export const routes = [
|
||||
...generalRoutes,
|
||||
@ -34,8 +35,8 @@ router.afterEach(to => {
|
||||
const title = await to.meta.title(to);
|
||||
document.title = title + TITLE_SUFFIX;
|
||||
} else {
|
||||
document.title = to.meta.title
|
||||
? to.meta.title + TITLE_SUFFIX
|
||||
document.title = i18n.t(to.meta.title)
|
||||
? i18n.t(to.meta.title) + TITLE_SUFFIX
|
||||
: DEFAULT_TITLE;
|
||||
}
|
||||
});
|
||||
|
@ -1,6 +1,5 @@
|
||||
import Planner from "@/pages/MealPlan/Planner";
|
||||
import ThisWeek from "@/pages/MealPlan/ThisWeek";
|
||||
import i18n from "@/i18n.js";
|
||||
import { api } from "@/api";
|
||||
|
||||
export const mealRoutes = [
|
||||
@ -8,14 +7,14 @@ export const mealRoutes = [
|
||||
path: "/meal-plan/planner",
|
||||
component: Planner,
|
||||
meta: {
|
||||
title: i18n.t("meal-plan.meal-planner"),
|
||||
title: "meal-plan.meal-planner",
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "/meal-plan/this-week",
|
||||
component: ThisWeek,
|
||||
meta: {
|
||||
title: i18n.t("meal-plan.dinner-this-week"),
|
||||
title: "meal-plan.dinner-this-week",
|
||||
},
|
||||
},
|
||||
{
|
||||
|
@ -9,45 +9,6 @@ const notifyHelpers = {
|
||||
info: "notify-info-color",
|
||||
};
|
||||
|
||||
const days = [
|
||||
"Sunday",
|
||||
"Monday",
|
||||
"Tuesday",
|
||||
"Wednesday",
|
||||
"Thursday",
|
||||
"Friday",
|
||||
"Saturday",
|
||||
];
|
||||
const months = [
|
||||
"January",
|
||||
"February",
|
||||
"March",
|
||||
"April",
|
||||
"May",
|
||||
"June",
|
||||
"July",
|
||||
"August",
|
||||
"September",
|
||||
"October",
|
||||
"November",
|
||||
"December",
|
||||
];
|
||||
|
||||
const monthsShort = [
|
||||
"Jan",
|
||||
"Feb",
|
||||
"March",
|
||||
"April",
|
||||
"May",
|
||||
"June",
|
||||
"July",
|
||||
"Aug",
|
||||
"Sept",
|
||||
"Oct",
|
||||
"Nov",
|
||||
"Dec",
|
||||
];
|
||||
|
||||
export default {
|
||||
getImageURL(image) {
|
||||
return `/api/recipes/${image}/image?image_type=small`;
|
||||
@ -56,22 +17,6 @@ export default {
|
||||
const uniqueKey = `${item}-${index}`;
|
||||
return uniqueKey;
|
||||
},
|
||||
getDateAsText(dateObject) {
|
||||
const dow = days[dateObject.getUTCDay()];
|
||||
const month = months[dateObject.getUTCMonth()];
|
||||
const day = dateObject.getUTCDate();
|
||||
// const year = dateObject.getFullYear();
|
||||
|
||||
return `${dow}, ${month} ${day}`;
|
||||
},
|
||||
getDateAsTextAlt(dateObject) {
|
||||
const dow = days[dateObject.getUTCDay()];
|
||||
const month = monthsShort[dateObject.getUTCMonth()];
|
||||
const day = dateObject.getUTCDate();
|
||||
// const year = dateObject.getFullYear();
|
||||
|
||||
return `${dow}, ${month} ${day}`;
|
||||
},
|
||||
getDateAsPythonDate(dateObject) {
|
||||
const month = dateObject.getUTCMonth() + 1;
|
||||
const day = dateObject.getUTCDate();
|
||||
|
Loading…
x
Reference in New Issue
Block a user