1
0
mirror of https://github.com/devfake/flox.git synced 2024-11-24 02:52:28 +01:00

add language translations for flox

This commit is contained in:
devfake 2016-11-23 21:16:41 +01:00
parent c4b836f43a
commit 2e8e41a4be
19 changed files with 187 additions and 46 deletions

View File

@ -59,7 +59,11 @@ Export and import can also be used for the update of flox itself. Export your mo
### Translation
All movie titles are in english by default. You can change your language by setting `TRANSLATION` in `backend/.env`. The most commons are `DE`, `IT`, `FR`, `ES` and `RU`. You can try to use your language code. If there isn't a translation for your language, the english title will be used.
All movie titles are in english by default. You can change your language by setting `TRANSLATION` in `backend/.env`. The most commons are `DE`, `IT`, `FR`, `ES` and `RU`. You can try to use your language code.
This will also affect the language of you website. See in `client/resources/languages` if your language is supported. Pull requests are welcome :)
If there isn't a translation for your language, english will be used.
### Better Search

View File

@ -0,0 +1,16 @@
<?php
namespace App\Http\Controllers;
use App\Services\Storage;
class HomeController {
public function app($uri = null, Storage $storage)
{
$language = $storage->parseLanguage();
return view('app')
->withLang($language);
}
}

View File

@ -38,4 +38,22 @@
{
LaravelStorage::delete($poster);
}
/**
* Parse language file.
*
* @return mixed
*/
public function parseLanguage()
{
$alternative = config('app.TRANSLATION') ?: 'EN';
$filename = strtolower($alternative) . '.json';
// Get english fallback
if( ! LaravelStorage::disk('languages')->exists($filename)) {
$filename = 'en.json';
}
return LaravelStorage::disk('languages')->get($filename);
}
}

View File

@ -53,6 +53,11 @@
'root' => base_path('../public/exports'),
],
'languages' => [
'driver' => 'local',
'root' => base_path('../client/resources/languages'),
],
'public' => [
'driver' => 'local',
'root' => storage_path('app/public'),

View File

@ -30,6 +30,4 @@
});
});
Route::get('/{uri?}', function($uri = null) {
return view('app');
})->where('uri', '(.*)');
Route::get('/{uri?}', 'HomeController@app')->where('uri', '(.*)');

View File

@ -7,10 +7,10 @@
:date="displayDate"
></Item>
<span class="nothing-found" v-if=" ! items.length">No Movies Found</span>
<span class="nothing-found" v-if=" ! items.length">{{ lang('nothing found') }}</span>
<div class="load-more-wrap">
<span class="load-more" v-if=" ! clickedMoreLoading && paginator" @click="loadMore()">Load More</span>
<span class="load-more" v-if=" ! clickedMoreLoading && paginator" @click="loadMore()">{{ lang('load more') }}</span>
<span class="loader" v-if="clickedMoreLoading"><i></i></span>
</div>
</div>
@ -22,10 +22,13 @@
<script>
import Item from './Item.vue';
import { mapActions, mapState } from 'vuex'
import Helper from '../../helper';
import http from 'axios';
export default {
mixins: [Helper],
created() {
this.fetchData();
this.fetchSettings();

View File

@ -9,8 +9,8 @@
<span class="loader smallsize-loader" v-if="rated"><i></i></span>
<i class="icon-add" v-if=" ! rated"></i>
</span>
<router-link :to="'/suggestions?for=' + localItem.tmdb_id" class="recommend-item">Suggestions</router-link>
<span class="remove-item" v-if="localItem.rating && auth" @click="removeItem()">Delete Movie</span>
<router-link :to="'/suggestions?for=' + localItem.tmdb_id" class="recommend-item">{{ lang('suggestions') }}</router-link>
<span class="remove-item" v-if="localItem.rating && auth" @click="removeItem()">{{ lang('delete movie') }}</span>
<img v-if="localItem.poster" :src="poster" class="item-image" width="185" height="278">
<img v-if=" ! localItem.poster" :src="noImage" class="item-image" width="185" height="278">
</div>
@ -26,8 +26,11 @@
<script>
import http from 'axios';
import Helper from '../../helper';
export default {
mixins: [Helper],
props: ['item', 'genre', 'date'],
data() {
@ -111,7 +114,7 @@
removeItem() {
if(this.auth) {
const confirm = window.confirm('Are you sure?');
const confirm = window.confirm(this.lang('confirm delete'));
if(confirm) {
http.delete(`${config.api}/remove/${this.localItem.id}`).then(value => {

View File

@ -14,7 +14,7 @@
:date="true"
></Item>
<span class="nothing-found" v-if=" ! floxItems.length && ! tmdbItems.length">Nothing Found</span>
<span class="nothing-found" v-if=" ! floxItems.length && ! tmdbItems.length">{{ lang('nothing found') }}</span>
</div>
<span class="loader fullsize-loader" v-if="loading"><i></i></span>

View File

@ -2,36 +2,36 @@
<main>
<div class="wrap-content" v-if=" ! loading">
<div class="settings-box">
<span class="nothing-found">User</span>
<span class="nothing-found">{{ lang('headline user') }}</span>
<form class="login-form" @submit.prevent="editUser()">
<input type="text" placeholder="Username" v-model="username">
<input type="password" placeholder="Password" v-model="password" autocomplete="off">
<span class="userdata-info">Leave the password field blank if you don't want to change it</span>
<span class="userdata-changed"><span v-if="success">Successful changed</span></span>
<input type="submit" value="Save">
<input type="text" :placeholder="lang('username')" v-model="username">
<input type="password" :placeholder="lang('password')" v-model="password" autocomplete="off">
<span class="userdata-info">{{ lang('password message') }}</span>
<span class="userdata-changed"><span v-if="success">{{ lang('success message') }}</span></span>
<input type="submit" :value="lang('save button')">
</form>
</div>
<div class="settings-box">
<span class="nothing-found">Export / Import</span>
<a :href="exportLink" class="export-btn">Export Movies</a>
<span class="nothing-found">{{ lang('headline export import') }}</span>
<a :href="exportLink" class="export-btn">{{ lang('export button') }}</a>
<form class="login-form" @submit.prevent="importMovies()">
<span class="import-info">OR</span>
<span class="import-info">{{ lang('or divider') }}</span>
<input type="file" @change="upload" class="file-btn" required>
<span class="userdata-changed"><span v-if="uploadSuccess">Movies successful imported</span></span>
<input type="submit" value="Import movies">
<span class="userdata-changed"><span v-if="uploadSuccess">{{ lang('success import') }}</span></span>
<input type="submit" :value="lang('import button')">
</form>
</div>
<div class="settings-box">
<span class="nothing-found">Misc</span>
<button @click="updateGenre()" class="export-btn">Update Genre</button>
<span class="import-info">OR</span>
<button @click="syncScout()" class="export-btn">Sync Laravel Scout</button>
<span class="import-info">OR</span>
<span class="nothing-found">{{ lang('headline misc') }}</span>
<button @click="updateGenre()" class="export-btn">{{ lang('update genre') }}</button>
<span class="import-info">{{ lang('or divider') }}</span>
<button @click="syncScout()" class="export-btn">{{ lang('sync scout') }}</button>
<span class="import-info">{{ lang('or divider') }}</span>
<div class="checkbox">
<input type="checkbox" value="genre" v-model="displayGenre" id="genre" @change="updateSettings"><label for="genre">Display Genre</label>
<input type="checkbox" value="genre" v-model="displayGenre" id="genre" @change="updateSettings"><label for="genre">{{ lang('display genre') }}</label>
</div>
<div class="checkbox">
<input type="checkbox" value="date" v-model="displayDate" id="date" @change="updateSettings"><label for="date">Display Date</label>
<input type="checkbox" value="date" v-model="displayDate" id="date" @change="updateSettings"><label for="date">{{ lang('display date') }}</label>
</div>
</div>
</div>
@ -42,10 +42,13 @@
<script>
import { mapState, mapMutations } from 'vuex';
import Helper from '../../helper';
import http from 'axios';
export default {
mixins: [Helper],
created() {
this.fetchSettings();
},
@ -93,7 +96,7 @@
importMovies() {
if(this.uploadedFile) {
const confirm = window.confirm('All movies will be replaced. Be sure you have made an backup!');
const confirm = window.confirm(this.lang('import warn'));
if(confirm) {
this.SET_LOADING(true);

View File

@ -11,8 +11,8 @@
<a class="icon-github" href="https://github.com/devfake/flox" target="_blank"></a>
<div class="sub-links">
<a v-if="auth" :href="settings" class="login-btn">Settings</a>
<a v-if="auth" :href="logout" class="login-btn">Logout</a>
<a v-if="auth" :href="settings" class="login-btn">{{ lang('settings') }}</a>
<a v-if="auth" :href="logout" class="login-btn">{{ lang('logout') }}</a>
<a v-if=" ! auth" :href="login" class="login-btn">Login</a>
</div>
</div>
@ -21,8 +21,11 @@
<script>
import { mapState } from 'vuex';
import Helper from '../helper';
export default {
mixins: [Helper],
data() {
return {
auth: config.auth,

View File

@ -6,15 +6,15 @@
</router-link>
<span class="sort-wrap">
<i title="Last Seen" class="icon-sort-time" :class="{active: userFilter == 'created_at'}" @click="setUserFilter('created_at')"></i>
<i title="Best Rated" class="icon-sort-star" :class="{active: userFilter == 'rating'}" @click="setUserFilter('rating')"></i>
<span title="Toggle Color" class="icon-constrast" @click="toggleColorScheme()"><i></i></span>
<i :title="lang('last seen')" class="icon-sort-time" :class="{active: userFilter == 'created_at'}" @click="setUserFilter('created_at')"></i>
<i :title="lang('best rated')" class="icon-sort-star" :class="{active: userFilter == 'rating'}" @click="setUserFilter('rating')"></i>
<span :title="lang('change color')" class="icon-constrast" @click="toggleColorScheme()"><i></i></span>
</span>
<nav class="site-nav">
<ul>
<li><router-link to="/trending">Trending</router-link></li>
<li><router-link to="/upcoming">Upcoming</router-link></li>
<li><router-link to="/trending">{{ lang('trending') }}</router-link></li>
<li><router-link to="/upcoming">{{ lang('upcoming') }}</router-link></li>
</ul>
</nav>
@ -23,10 +23,13 @@
</template>
<script>
import Helper from '../helper';
import store from '../store/index';
import { mapActions, mapMutations, mapState } from 'vuex'
export default {
mixins: [Helper],
created() {
this.checkForUserFilter();
},

View File

@ -6,12 +6,12 @@
<img src="../../../public/assets/img/logo-login.png" class="logo-login" alt="Flox" width="108" height="32">
<form class="login-form" @submit.prevent="login()">
<input type="text" placeholder="Username" v-model="username" autofocus>
<input type="password" placeholder="Password" v-model="password">
<input type="text" :placeholder="lang('username')" v-model="username" autofocus>
<input type="password" :placeholder="lang('password')" v-model="password">
<span class="login-error"><span v-if="error">Wrong username or password</span></span>
<span class="login-error"><span v-if="error">{{ lang('login error') }}</span></span>
<input type="submit" :class="errorShake ? 'shake-horizontal shake-constant' : ''" value="Sign In">
<input type="submit" :class="errorShake ? 'shake-horizontal shake-constant' : ''" :value="lang('login button')">
</form>
</div>
@ -20,8 +20,11 @@
<script>
import http from 'axios';
import Helper from '../helper';
export default {
mixins: [Helper],
created() {
document.body.className += ' dark';
},

View File

@ -45,7 +45,8 @@
},
placeholder() {
return config.auth ? 'Search or add movie' : 'Search movie';
//return config.auth ? 'Search or add movie' : 'Search movie';
return config.auth ? this.lang('search or add') : this.lang('search');
}
},

View File

@ -1,12 +1,13 @@
import http from 'axios';
http.defaults.headers.common['X-CSRF-TOKEN'] = document.querySelector('#token').getAttribute('content');
const {url, uri, auth, scoutDriver} = document.body.dataset;
const {url, uri, auth, scoutDriver, language} = document.body.dataset;
const config = {
uri,
url,
auth,
language,
scoutDriver,
poster: url + '/assets/poster',
posterTMDB: 'http://image.tmdb.org/t/p/w185',

View File

@ -18,6 +18,13 @@ export default {
}
window.requestAnimationFrame(step);
},
// Language helper
lang(text) {
const language = JSON.parse(config.language);
return language[text];
}
}
}

View File

@ -16,6 +16,7 @@
data-uri="{{ config('app.CLIENT_URI') }}"
data-scout-driver="{{ config('scout.driver') }}"
data-auth="{{ Auth::check() }}"
data-language="{{ $lang }}"
class="{{ Auth::check() ? 'logged' : 'guest' }}"
>

View File

@ -0,0 +1,38 @@
{
"username": "Benutzer",
"password": "Passwort",
"login button": "Einloggen",
"login error": "Benutzer oder Passwort ist falsch",
"suggestions": "Vorschläge",
"delete movie": "Film löschen",
"confirm delete": "Wirklich löschen?",
"search": "Film suchen",
"search or add": "Film suchen oder hinzufügen",
"load more": "Mehr anzeigen",
"nothing found": "Nichts gefunden",
"trending": "Beliebt",
"upcoming": "Kommend",
"last seen": "Zuletzt gesehen",
"best rated": "Am besten bewertet",
"change color": "Farbmodus wechseln",
"settings": "Einstellungen",
"logout": "Ausloggen",
"headline user": "Benutzer",
"headline export import": "Exportieren / Importieren",
"headline misc": "Sonstiges",
"save button": "Speichern",
"password message": "Lasse das Passwort-Feld leer, wenn du es nicht ändern willst",
"success message": "Erfolgreich gespeichert",
"export button": "Exportieren",
"import button": "Importieren",
"or divider": "ODER",
"update genre": "Genre updaten",
"sync scout": "Sync Laravel Scout",
"display genre": "Genre anzeigen",
"display date": "Datum anzeigen",
"success import": "Filme wurden erfolgreich importiert",
"import warn": "Durch den Import werden alle Filme ersetzt. Erstelle vorher ein Backup!"
}

View File

@ -0,0 +1,38 @@
{
"username": "Username",
"password": "Password",
"login button": "Login",
"login error": "Wrong username or password",
"suggestions": "Suggestions",
"delete movie": "Delete Movie",
"confirm delete": "Are you sure?",
"search": "Search movie",
"search or add": "Search or add movie",
"load more": "Load More",
"nothing found": "Nothing found",
"trending": "Trending",
"upcoming": "Upcoming",
"last seen": "Last seen",
"best rated": "Best rated",
"change color": "Change colors",
"settings": "Settings",
"logout": "Logout",
"headline user": "User",
"headline export import": "Export / Import",
"headline misc": "Misc",
"save button": "Save",
"password message": "Leave the password field blank if you don't want to change it",
"success message": "Successful changed",
"export button": "Export movies",
"import button": "Import movies",
"or divider": "OR",
"update genre": "Update genre",
"sync scout": "Sync Laravel Scout",
"display genre": "Display genre",
"display date": "Display date",
"success import": "Movies successful imported",
"import warn": "All movies will be replaced. Be sure you have made an backup!"
}

View File

@ -3398,10 +3398,6 @@ vue-loader@^9.5.1:
vue-template-compiler "^2.0.5"
vue-template-es2015-compiler "^1.2.2"
vue-resource@^1.0.3:
version "1.0.3"
resolved "https://registry.yarnpkg.com/vue-resource/-/vue-resource-1.0.3.tgz#8d52d0d8a9ed5f2ae704c68d530c84ceaf97be14"
vue-router@^2.0.0:
version "2.0.3"
resolved "https://registry.yarnpkg.com/vue-router/-/vue-router-2.0.3.tgz#444e246fd42d65a34dea6c3be8fde3315c4ba6f7"