laravel native translations management

This commit is contained in:
Olivier Legat 2022-01-25 14:07:34 +01:00
parent d9ad721862
commit b0646dd76f
37 changed files with 1084 additions and 6 deletions

View file

@ -0,0 +1,29 @@
<?php
namespace App\Http\Controllers;
use App\Enums\Lang;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Cookie;
class TranslationController extends Controller
{
public function switch($locale)
{
if (! in_array($locale, Lang::toValues())) {
abort(400);
}
// Save in DB
// $user = Auth::user();
// $user->lang = $locale;
// $user->save();
Cookie::queue(Cookie::forever('language', $locale));
if (url()->full() !== url()->previous()) {
return redirect()->back();
}
return redirect()->route('home');
}
}

View file

@ -8,6 +8,7 @@
"php": "^7.3|^8.0",
"fruitcake/laravel-cors": "^2.0",
"guzzlehttp/guzzle": "^7.0.1",
"joedixon/laravel-translation": "^1.1",
"kwaadpepper/enum": "^2.1",
"laravel/framework": "^8.65",
"laravel/sanctum": "^2.11",

52
composer.lock generated
View file

@ -4,7 +4,7 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically"
],
"content-hash": "80788c9fb7e0b768b26bfc5b32a553c9",
"content-hash": "1a3da04910070cf2f09b5d8cdb51f835",
"packages": [
{
"name": "asm89/stack-cors",
@ -937,6 +937,56 @@
],
"time": "2021-10-06T17:43:30+00:00"
},
{
"name": "joedixon/laravel-translation",
"version": "v1.1.2",
"source": {
"type": "git",
"url": "https://github.com/joedixon/laravel-translation.git",
"reference": "4a467398bae73cd16522d523b557e96f3455b9d2"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/joedixon/laravel-translation/zipball/4a467398bae73cd16522d523b557e96f3455b9d2",
"reference": "4a467398bae73cd16522d523b557e96f3455b9d2",
"shasum": ""
},
"require-dev": {
"mockery/mockery": "^1.0.0",
"orchestra/testbench": "^4.0",
"phpunit/phpunit": "^8.0"
},
"type": "library",
"extra": {
"laravel": {
"providers": [
"JoeDixon\\Translation\\TranslationServiceProvider",
"JoeDixon\\Translation\\TranslationBindingsServiceProvider"
]
}
},
"autoload": {
"psr-4": {
"JoeDixon\\Translation\\": "src"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Joe Dixon",
"email": "hello@joedixon.co.uk"
}
],
"description": "A tool for managing all of your Laravel translations",
"support": {
"issues": "https://github.com/joedixon/laravel-translation/issues",
"source": "https://github.com/joedixon/laravel-translation/tree/master"
},
"time": "2020-04-13T20:06:24+00:00"
},
{
"name": "kwaadpepper/enum",
"version": "2.1.2",

85
config/translation.php Normal file
View file

@ -0,0 +1,85 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Package driver
|--------------------------------------------------------------------------
|
| The package supports different drivers for translation management.
|
| Supported: "file", "database"
|
*/
'driver' => 'file',
/*
|--------------------------------------------------------------------------
| Route group configuration
|--------------------------------------------------------------------------
|
| The package ships with routes to handle language management. Update the
| configuration here to configure the routes with your preferred group options.
|
*/
'route_group_config' => [
'middleware' => [
'web',
'auth:web',
],
],
/*
|--------------------------------------------------------------------------
| Translation methods
|--------------------------------------------------------------------------
|
| Update this array to tell the package which methods it should look for
| when finding missing translations.
|
*/
'translation_methods' => ['trans', '__'],
/*
|--------------------------------------------------------------------------
| Scan paths
|--------------------------------------------------------------------------
|
| Update this array to tell the package which directories to scan when
| looking for missing translations.
|
*/
'scan_paths' => [
//app_path(),
//resource_path().'\views\back',
resource_path().'\views\front',
resource_path().'\views\layouts\frontend',
],
/*
|--------------------------------------------------------------------------
| UI URL
|--------------------------------------------------------------------------
|
| Define the URL used to access the language management too.
|
*/
'ui_url' => 'bo/languages',
/*
|--------------------------------------------------------------------------
| Database settings
|--------------------------------------------------------------------------
|
| Define the settings for the database driver here.
|
*/
'database' => [
'connection' => '',
'languages_table' => 'languages',
'translations_table' => 'translations',
],
];

File diff suppressed because one or more lines are too long

1
public/vendor/translation/js/app.js vendored Normal file

File diff suppressed because one or more lines are too long

View file

@ -0,0 +1,4 @@
{
"/js/app.js": "/js/app.js",
"/css/main.css": "/css/main.css"
}

View file

@ -1,5 +1,15 @@
{
"Marque":"Brand",
"Produits":"Products",
"Actualités":"News"
}
"Marque": "Brand",
"Produits": "Products",
"Actualités": "News",
"Accueil": "Home",
"Découvrez DOUX, des produits de volailles françaises.": "",
"Qui sommes-nous": "About us",
"Les produits": "products",
"Nous travaillons toujours pour améliorer nos recettes et proposer des produits de meilleur qualité": "",
"Découvrir": "",
"Nos gammes produits": "",
"Toutes nos gammes": "",
"Des produits incontournables, Authentiques et Innovants !": "",
"Doux": "Doux"
}

View file

@ -0,0 +1,21 @@
<?php
return array (
'balanced_menu_type' =>
array (
'kid' => 'kid',
'man' => 'man',
'senior' => 'senior',
'teenager' => 'teenager',
'withPrefix' =>
array (
'kid' => 'a kid',
'man' => 'a man',
'senior' => 'a senior',
'teenager' => 'a teenager',
'woman' => 'a woman',
),
'woman' => 'woman',
),
'kid' => 'kid',
);

15
resources/lang/es.json Normal file
View file

@ -0,0 +1,15 @@
{
"Marque": "Marca",
"Produits": "productos",
"Actualités": "Noticias",
"Accueil": "",
"Découvrez DOUX, des produits de volailles françaises.": "",
"Qui sommes-nous": "",
"Les produits": "",
"Nous travaillons toujours pour améliorer nos recettes et proposer des produits de meilleur qualité": "",
"Découvrir": "",
"Nos gammes produits": "",
"Toutes nos gammes": "",
"Des produits incontournables, Authentiques et Innovants !": "",
"Doux": ""
}

View file

@ -0,0 +1,18 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Authentication Language Lines
|--------------------------------------------------------------------------
|
| The following language lines are used during authentication for various
| messages that we need to display to the user. You are free to modify
| these language lines according to your application's requirements.
|
*/
'failed' => 'Ces identifiants ne correspondent pas à nos enregistrements',
'password' => 'Le mot de passe fourni est incorrect.',
'throttle' => 'Tentatives de connexion trop nombreuses. Veuillez essayer de nouveau dans :seconds secondes.',
];

View file

@ -0,0 +1,19 @@
<?php
return [
'kid' => 'enfant',
'balanced_menu_type' => [
'kid' => 'enfant',
'teenager' => 'adolescent',
'woman' => 'femme',
'man' => 'homme',
'senior' => 'senior',
'withPrefix' => [
'kid' => 'un enfant',
'teenager' => 'un adolescent',
'woman' => 'une femme',
'man' => 'un homme',
'senior' => 'un senior'
]
]
];

View file

@ -0,0 +1,17 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Pagination Language Lines
|--------------------------------------------------------------------------
|
| The following language lines are used by the paginator library to build
| the simple pagination links. You are free to change them to anything
| you want to customize your views to better match your application.
|
*/
'previous' => '&laquo; Précédent',
'next' => 'Suivant &raquo;',
];

View file

@ -0,0 +1,20 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Password Reminder Language Lines
|--------------------------------------------------------------------------
|
| The following language lines are the default lines which match reasons
| that are given by the password broker for a password update attempt
| has failed, such as for an invalid token or invalid new password.
|
*/
'reset' => 'Votre mot de passe a été réinitialisé !',
'sent' => 'Nous vous avons envoyé par email le lien de réinitialisation du mot de passe !',
'throttled' => 'Veuillez patienter avant de réessayer.',
'token' => "Ce jeton de réinitialisation du mot de passe n'est pas valide.",
'user' => "Aucun utilisateur n'a été trouvé avec cette adresse email.",
];

View file

@ -0,0 +1,187 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Validation Language Lines
|--------------------------------------------------------------------------
|
| The following language lines contain the default error messages used by
| the validator class. Some of these rules have multiple versions such
| as the size rules. Feel free to tweak each of these messages.
|
*/
'accepted' => 'Le champ :attribute doit être accepté.',
'active_url' => "Le champ :attribute n'est pas une URL valide.",
'after' => 'Le champ :attribute doit être une date postérieure au :date.',
'after_or_equal' => 'Le champ :attribute doit être une date postérieure ou égale au :date.',
'alpha' => 'Le champ :attribute doit contenir uniquement des lettres.',
'alpha_dash' => 'Le champ :attribute doit contenir uniquement des lettres, des chiffres et des tirets.',
'alpha_num' => 'Le champ :attribute doit contenir uniquement des chiffres et des lettres.',
'array' => 'Le champ :attribute doit être un tableau.',
'before' => 'Le champ :attribute doit être une date antérieure au :date.',
'before_or_equal' => 'Le champ :attribute doit être une date antérieure ou égale au :date.',
'between' => [
'numeric' => 'La valeur de :attribute doit être comprise entre :min et :max.',
'file' => 'La taille du fichier de :attribute doit être comprise entre :min et :max kilo-octets.',
'string' => 'Le texte :attribute doit contenir entre :min et :max caractères.',
'array' => 'Le tableau :attribute doit contenir entre :min et :max éléments.',
],
'boolean' => 'Le champ :attribute doit être vrai ou faux.',
'confirmed' => 'Le champ de confirmation :attribute ne correspond pas.',
'date' => "Le champ :attribute n'est pas une date valide.",
'date_equals' => 'Le champ :attribute doit être une date égale à :date.',
'date_format' => 'Le champ :attribute ne correspond pas au format :format.',
'different' => 'Les champs :attribute et :other doivent être différents.',
'digits' => 'Le champ :attribute doit contenir :digits chiffres.',
'digits_between' => 'Le champ :attribute doit contenir entre :min et :max chiffres.',
'dimensions' => "La taille de l'image :attribute n'est pas conforme.",
'distinct' => 'Le champ :attribute a une valeur en double.',
'email' => 'Le champ :attribute doit être une adresse email valide.',
'ends_with' => 'Le champ :attribute doit se terminer par une des valeurs suivantes : :values',
'exists' => 'Le champ :attribute sélectionné est invalide.',
'file' => 'Le champ :attribute doit être un fichier.',
'filled' => 'Le champ :attribute doit avoir une valeur.',
'gt' => [
'numeric' => 'La valeur de :attribute doit être supérieure à :value.',
'file' => 'La taille du fichier de :attribute doit être supérieure à :value kilo-octets.',
'string' => 'Le texte :attribute doit contenir plus de :value caractères.',
'array' => 'Le tableau :attribute doit contenir plus de :value éléments.',
],
'gte' => [
'numeric' => 'La valeur de :attribute doit être supérieure ou égale à :value.',
'file' => 'La taille du fichier de :attribute doit être supérieure ou égale à :value kilo-octets.',
'string' => 'Le texte :attribute doit contenir au moins :value caractères.',
'array' => 'Le tableau :attribute doit contenir au moins :value éléments.',
],
'image' => 'Le champ :attribute doit être une image.',
'in' => 'Le champ :attribute est invalide.',
'in_array' => "Le champ :attribute n'existe pas dans :other.",
'integer' => 'Le champ :attribute doit être un entier.',
'ip' => 'Le champ :attribute doit être une adresse IP valide.',
'ipv4' => 'Le champ :attribute doit être une adresse IPv4 valide.',
'ipv6' => 'Le champ :attribute doit être une adresse IPv6 valide.',
'json' => 'Le champ :attribute doit être un document JSON valide.',
'lt' => [
'numeric' => 'La valeur de :attribute doit être inférieure à :value.',
'file' => 'La taille du fichier de :attribute doit être inférieure à :value kilo-octets.',
'string' => 'Le texte :attribute doit contenir moins de :value caractères.',
'array' => 'Le tableau :attribute doit contenir moins de :value éléments.',
],
'lte' => [
'numeric' => 'La valeur de :attribute doit être inférieure ou égale à :value.',
'file' => 'La taille du fichier de :attribute doit être inférieure ou égale à :value kilo-octets.',
'string' => 'Le texte :attribute doit contenir au plus :value caractères.',
'array' => 'Le tableau :attribute doit contenir au plus :value éléments.',
],
'max' => [
'numeric' => 'La valeur de :attribute ne peut être supérieure à :max.',
'file' => 'La taille du fichier de :attribute ne peut pas dépasser :max kilo-octets.',
'string' => 'Le texte de :attribute ne peut contenir plus de :max caractères.',
'array' => 'Le tableau :attribute ne peut contenir plus de :max éléments.',
],
'mimes' => 'Le champ :attribute doit être un fichier de type : :values.',
'mimetypes' => 'Le champ :attribute doit être un fichier de type : :values.',
'min' => [
'numeric' => 'La valeur de :attribute doit être supérieure ou égale à :min.',
'file' => 'La taille du fichier de :attribute doit être supérieure à :min kilo-octets.',
'string' => 'Le texte :attribute doit contenir au moins :min caractères.',
'array' => 'Le tableau :attribute doit contenir au moins :min éléments.',
],
'multiple_of' => 'La valeur de :attribute doit être un multiple de :value',
'not_in' => "Le champ :attribute sélectionné n'est pas valide.",
'not_regex' => "Le format du champ :attribute n'est pas valide.",
'numeric' => 'Le champ :attribute doit contenir un nombre.',
'password' => 'Le mot de passe est incorrect',
'present' => 'Le champ :attribute doit être présent.',
'regex' => 'Le format du champ :attribute est invalide.',
'required' => 'Le champ :attribute est obligatoire.',
'required_if' => 'Le champ :attribute est obligatoire quand la valeur de :other est :value.',
'required_unless' => 'Le champ :attribute est obligatoire sauf si :other est :values.',
'required_with' => 'Le champ :attribute est obligatoire quand :values est présent.',
'required_with_all' => 'Le champ :attribute est obligatoire quand :values sont présents.',
'required_without' => "Le champ :attribute est obligatoire quand :values n'est pas présent.",
'required_without_all' => "Le champ :attribute est requis quand aucun de :values n'est présent.",
'same' => 'Les champs :attribute et :other doivent être identiques.',
'size' => [
'numeric' => 'La valeur de :attribute doit être :size.',
'file' => 'La taille du fichier de :attribute doit être de :size kilo-octets.',
'string' => 'Le texte de :attribute doit contenir :size caractères.',
'array' => 'Le tableau :attribute doit contenir :size éléments.',
],
'starts_with' => 'Le champ :attribute doit commencer avec une des valeurs suivantes : :values',
'string' => 'Le champ :attribute doit être une chaîne de caractères.',
'timezone' => 'Le champ :attribute doit être un fuseau horaire valide.',
'unique' => 'La valeur du champ :attribute est déjà utilisée.',
'uploaded' => "Le fichier du champ :attribute n'a pu être téléversé.",
'url' => "Le format de l'URL de :attribute n'est pas valide.",
'uuid' => 'Le champ :attribute doit être un UUID valide',
/*
|--------------------------------------------------------------------------
| Custom Validation Language Lines
|--------------------------------------------------------------------------
|
| Here you may specify custom validation messages for attributes using the
| convention "attribute.rule" to name the lines. This makes it quick to
| specify a specific custom language line for a given attribute rule.
|
*/
'phone' => 'Le champ :attribute n\'est pas un numéro de téléphone valide.',
'custom' => [
'attribute-name' => [
'rule-name' => 'custom-message',
],
],
/*
|--------------------------------------------------------------------------
| Custom Validation Attributes
|--------------------------------------------------------------------------
|
| The following language lines are used to swap attribute place-holders
| with something more reader friendly such as E-Mail Address instead
| of "email". This simply helps us make messages a little cleaner.
|
*/
'attributes' => [
'name' => 'nom',
'username' => "nom d'utilisateur",
'email' => 'adresse email',
'first_name' => 'prénom',
'last_name' => 'nom',
'password' => 'mot de passe',
'password_confirmation' => 'confirmation du mot de passe',
'city' => 'ville',
'country' => 'pays',
'address' => 'adresse',
'phone' => 'téléphone',
'mobile' => 'portable',
'age' => 'âge',
'sex' => 'sexe',
'gender' => 'genre',
'day' => 'jour',
'month' => 'mois',
'year' => 'année',
'hour' => 'heure',
'minute' => 'minute',
'second' => 'seconde',
'title' => 'titre',
'content' => 'contenu',
'description' => 'description',
'excerpt' => 'extrait',
'date' => 'date',
'time' => 'heure',
'available' => 'disponible',
'size' => 'taille',
'answers' => 'réponses',
'answers.*' => 'réponse',
'postal_code' => 'code postal',
'picture' => 'image',
'breeder_code' => 'code éleveur'
],
];

15
resources/lang/fr.json Normal file
View file

@ -0,0 +1,15 @@
{
"Marque": "Marque",
"Produits": "Produits",
"Actualités": "Actualités",
"Accueil": "Accueil",
"Découvrez DOUX, des produits de volailles françaises.": "Découvrez DOUX, des produits de volailles françaises",
"Qui sommes-nous": "Qui sommes-nous",
"Les produits": "Les produits",
"Nous travaillons toujours pour améliorer nos recettes et proposer des produits de meilleur qualité": "Nous travaillons toujours pour améliorer nos recettes et proposer des produits de meilleur qualité",
"Découvrir": "Découvrir",
"Nos gammes produits": "Nos gammes produits",
"Toutes nos gammes": "Toutes nos gammes",
"Des produits incontournables, Authentiques et Innovants !": "Des produits incontournables, Authentiques et Innovants !",
"Doux": "Doux"
}

View file

@ -0,0 +1,6 @@
<?php
return [
'language_exists' => 'Die Sprache { :language } ist bereits vorhanden',
'key_exists' => 'Der Übersetzungsschlüssel { :key } ist bereits vorhanden',
];

View file

@ -0,0 +1,52 @@
<?php
return [
'languages' => 'Sprachen',
'language' => 'Sprache',
'type' => 'Typ',
'file' => 'Datei',
'key' => 'Schlüssel',
'prompt_language' => 'Geben Sie den Sprachcode ein, den Sie hinzufügen möchten (z.B. en).',
'language_added' => 'Neue Sprache wurde erfolgreich hinzugefügt 🙌',
'prompt_language_for_key' => 'Geben Sie die Sprache für den Schlüssel ein (z.B. en)',
'prompt_type' => 'Ist das ein Json- oder Array-Schlüssel?',
'prompt_file' => 'In welcher Datei wird das gespeichert?',
'prompt_key' => 'Was ist der Schlüssel für diese Übersetzung?',
'prompt_value' => 'Was ist der Wert für diese Übersetzung',
'type_error' => 'Übersetzungstyp muss json oder ein Array sein',
'language_key_added' => 'Neuer Sprachenschlüssel wurde erfolgreich hinzugefügt 👏',
'no_missing_keys' => 'Es fehlen keine Übersetzungsschlüssel in der App 🎉',
'keys_synced' => 'Fehlende Schlüssel erfolgreich synchronisiert 🎊',
'search' => 'Alle Übersetzungen suchen',
'translations' => 'Übersetzung',
'language_name' => 'Name',
'locale' => 'locale',
'add' => '+ Hinzufügen',
'add_language' => 'Neue Sprache hinzufügen',
'save' => 'save',
'language_exists' => 'Das :attribute ist bereits vorhanden.',
'uh_oh' => 'Etwas ist nicht ganz richtig',
'group_single' => 'Gruppe / Single',
'Gruppe' => 'Gruppe',
'single' => 'single',
'value' => 'Wert',
'namespace' => 'Namespace',
'prompt_from_driver' => 'Von welchem Treiber möchten Sie Übersetzungen übernehmen?',
'prompt_to_driver' => 'Zu welchem Treiber möchten Sie die Übersetzungen hinzufügen?',
'prompt_language_if_any' => 'Welche Sprache? (leer lassen für alle) ',
'synchronisieren' => 'Übersetzungen synchronisieren ⏳',
'synced' => 'Übersetzungen wurden synchronisiert 😎',
'invalid_driver' => 'Ungültiger Treiber',
'invalid_language' => 'Ungültige Sprache',
'add_translation' => 'Übersetzung hinzufügen',
'translation_added' => 'Neue Übersetzung erfolgreich hinzugefügt 🙌',
'namespace_label' => 'Namespace (optional)',
'group_label' => 'Gruppe (optional)',
'key_label' => 'Schlüssel',
'value_label' => 'Wert',
'namespace_placeholder' => 'z.B. my_package',
'group_placeholder' => 'z.B. validation',
'key_placeholder' => 'z.B. invalid_key',
'value_placeholder' => 'z.B. Schlüssel müssen eine einzige Zeichenfolge sein',
'advanced_options' => 'Erweiterte Optionen umschalten',
];

View file

@ -0,0 +1,6 @@
<?php
return [
'language_exists' => 'The language { :language } already exists',
'key_exists' => 'The translation key { :key } already exists',
];

View file

@ -0,0 +1,52 @@
<?php
return [
'languages' => 'Languages',
'language' => 'Language',
'type' => 'Type',
'file' => 'File',
'key' => 'Key',
'prompt_language' => 'Enter the language code you would like to add (e.g. en)',
'language_added' => 'New language added successfully 🙌',
'prompt_language_for_key' => 'Enter the language for the key (e.g. en)',
'prompt_type' => 'Is this a json or array key?',
'prompt_file' => 'Which file will this be stored in?',
'prompt_key' => 'What is the key for this translation?',
'prompt_value' => 'What is the value for this translation',
'type_error' => 'Translation type must be json or array',
'language_key_added' => 'New language key added successfully 👏',
'no_missing_keys' => 'There are no missing translation keys in the app 🎉',
'keys_synced' => 'Missing keys synchronised successfully 🎊',
'search' => 'Search all translations',
'translations' => 'Translation',
'language_name' => 'Name',
'locale' => 'Locale',
'add' => '+ Add',
'add_language' => 'Add a new language',
'save' => 'Save',
'language_exists' => 'The :attribute already exists.',
'uh_oh' => 'Something\'s not quite right',
'group_single' => 'Group / Single',
'group' => 'Group',
'single' => 'Single',
'value' => 'Value',
'namespace' => 'Namespace',
'prompt_from_driver' => 'Which driver would you like to take translations from?',
'prompt_to_driver' => 'Which driver would you like to add the translations to?',
'prompt_language_if_any' => 'Which language? (leave blank for all)',
'syncing' => 'Syncing translations ⏳',
'synced' => 'Translations have been synced 😎',
'invalid_driver' => 'Invalid driver',
'invalid_language' => 'Invalid language',
'add_translation' => 'Add a translation',
'translation_added' => 'New translation added successfull 🙌',
'namespace_label' => 'Namespace (Optional)',
'group_label' => 'Group (Optional)',
'key_label' => 'Key',
'value_label' => 'Value',
'namespace_placeholder' => 'e.g. my_package',
'group_placeholder' => 'e.g. validation',
'key_placeholder' => 'e.g. invalid_key',
'value_placeholder' => 'e.g. Keys must be a single string',
'advanced_options' => 'Toggle advanced options',
];

View file

@ -0,0 +1,6 @@
<?php
return [
'key_exists' => 'La clé de traduction { :key } existe déjà',
'language_exists' => 'La langue { :language } existe déjà',
];

View file

@ -0,0 +1,52 @@
<?php
return [
'add' => '+ Ajouter',
'add_language' => 'Ajouter une nouvelle langue',
'add_translation' => 'Ajouter une traduction',
'advanced_options' => 'Afficher les options avancées',
'file' => 'Fichier',
'group' => 'Groupe',
'group_label' => 'Groupe (Optionnel)',
'group_placeholder' => 'Ex: validation',
'group_single' => 'Groupe / Unique',
'invalid_driver' => 'Driver invalide',
'invalid_language' => 'Langue invalide',
'key' => 'Clé',
'key_label' => 'Clé',
'key_placeholder' => 'Par exemple : invalid_key',
'keys_synced' => 'Clés manquantes synchronisées avec succès 🎊',
'language' => 'Langue',
'language_added' => 'Nouvelle langue ajoutée avec succés 🙌',
'language_exists' => 'Le :attribute existe déjà.',
'language_key_added' => 'Nouvelle clé dans la langue ajoutée avec succès 👏',
'language_name' => 'Nom',
'languages' => 'Langues',
'locale' => 'Locale',
'namespace' => 'Namespace',
'namespace_label' => 'Namespace (Optionnel)',
'namespace_placeholder' => 'Par exemple : my_package',
'no_missing_keys' => 'Il ne manque aucune clé de traduction dans l\'application 🎉',
'prompt_file' => 'Dans quel fichier sera t\'elle stockée ?',
'prompt_from_driver' => 'De quel driver voudriez-vous prendre les traductions ?',
'prompt_key' => 'Quelle est la clé de cette traduction ?',
'prompt_language' => 'Entrez le code langue que vous aimeriez ajouter (Ex: fr)',
'prompt_language_for_key' => 'Entrez la langue pour la clé (Ex: fr)',
'prompt_language_if_any' => 'Quelle langue ? (Laissez vide pour tous)',
'prompt_to_driver' => 'À quel driver désirez-vous ajouter les traductions ?',
'prompt_type' => 'Est-ce une clé Json ou Array ?',
'prompt_value' => 'Quelle est la valeur de la traduction',
'save' => 'Sauvegarder',
'search' => 'Rechercher toutes les traductions',
'single' => 'Unique',
'synced' => 'Les traductions sont synchronisées 😎',
'syncing' => 'Synchronisation des traductions ⏳',
'translation_added' => 'Nouvelle traduction ajoutée avec succès 🙌',
'translations' => 'Traduction',
'type' => 'Type',
'type_error' => 'Le type de traduction doit être en json ou en array',
'uh_oh' => 'Quelque chose ne fonctionne pas',
'value' => 'Valeur',
'value_label' => 'Valeur',
'value_placeholder' => 'Par exemple : Les clés doivent être une seule chaîne',
];

View file

@ -0,0 +1,6 @@
<?php
return [
'language_exists' => 'De taal { :language } bestaat al',
'key_exists' => 'De vertaalsleutel { :key } bestaat al',
];

View file

@ -0,0 +1,52 @@
<?php
return [
'languages' => 'Talen',
'language' => 'Taal',
'type' => 'Type',
'file' => 'Bestand',
'key' => 'Sleutel',
'prompt_language' => 'Voer de taalcode in die u wilt toevoegen (bijvoorbeeld: en)',
'language_added' => 'Nieuwe taal met succes toegevoegd 🙌',
'prompt_language_for_key' => 'Voer de taal voor de sleutel in (bijvoorbeeld: en)',
'prompt_type' => 'Is dit een json- of arraysleutel?',
'prompt_file' => 'In welk bestand wordt dit opgeslagen?',
'prompt_key' => 'Wat is de sleutel voor deze vertaling?',
'prompt_value' => 'Wat is de text voor deze vertaling',
'type_error' => 'Het vertaaltype moet json of array zijn',
'language_key_added' => 'Nieuwe taalcode toegevoegd 👏',
'no_missing_keys' => 'Er zijn geen ontbrekende vertaalsleutels in de app 🎉',
'keys_synced' => 'Ontbrekende toetsen gesynchroniseerd met succes 🎊',
'search' => 'Doorzoek alle vertalingen',
'translations' => 'Vertaling',
'language_name' => 'Naam',
'locale' => 'locale',
'add' => '+ Toevoegen',
'add_language' => 'Voeg een nieuwe taal toe',
'save' => 'Opslaan',
'language_exists' => 'Het kenmerk :attribute bestaat al.',
'uh_oh' => 'Er klopt iets niet helemaal',
'group_single' => 'Groep / Enkelvoudig',
'group' => 'Groep',
'single' => 'Enkelvoudig',
'value' => 'Waarde',
'namespace' => 'Namespace',
'prompt_from_driver' => 'Van welke driver wilt u vertalingen meenemen?',
'prompt_to_driver' => 'Aan welke driver wilt u de vertalingen toevoegen?',
'prompt_language_if_any' => 'Welke taal? (laat leeg voor alle)',
'syncing' => 'Vertaling synchroniseren ⏳',
'synced' => 'Vertalingen zijn gesynchroniseerd 😎',
'invalid_driver' => 'Ongeldige driver',
'invalid_language' => 'Ongeldige taal',
'add_translation' => 'Voeg een vertaling toe',
'translation_added' => 'Nieuwe vertaling succesvol toegevoegd 🙌',
'namespace_label' => 'Namespace (optioneel)',
'group_label' => 'Groep (optioneel)',
'key_label' => 'Sleutel',
'value_label' => 'Waarde',
'namespace_placeholder' => 'bijv. Mijn_pakket',
'group_placeholder' => 'bijv. bevestiging',
'key_placeholder' => 'bijv. ongeldige sleutel',
'value_placeholder' => 'bijv. Sleutels mogen geen spaties bevatten',
'advanced_options' => 'Schakel geavanceerde opties in',
];

View file

@ -131,6 +131,14 @@
</div>
</div>
</div>
<div class="col-12">
<ul class="nav flex-column mb-2">
<li class="nav-item">
<a class="btn btn-secondary" href="{{route('languages.translations.index', Session::get('lang') )}}">{{ __('Traductions système') }}</a>
</li>
</ul>
</div>
</div>
{{-- DECONNEXION --}}
<div class="col-12 mt-5">
@ -144,4 +152,4 @@
</ul>
</div>
</div>
</nav>
</nav>

View file

@ -0,0 +1,3 @@
<div class="search">
<input type="text" class="search-input" placeholder="{{ __('translation::translation.search') }}" name="{{ $name }}" value="{{ $value }}">
</div>

View file

@ -0,0 +1,18 @@
<div class="select-group">
<select name="{{ $name }}" @if(isset($submit) && $submit) v-on:change="submit" @endif>
@if(isset($optional) && $optional)<option value> ----- </option>@endif
@foreach($items as $key => $value)
@if(is_numeric($key))
<option value="{{ $value }}" @if(isset($selected) && $selected === $value) selected="selected" @endif>{{ $value }}</option>
@else
<option value="{{ $key }}" @if(isset($selected) && $selected === $key) selected="selected" @endif>{{ $value }}</option>
@endif
@endforeach
</select>
<div class="caret">
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20"><path d="M9.293 12.95l.707.707L15.657 8l-1.414-1.414L10 10.828 5.757 6.586 4.343 8z"/></svg>
</div>
</div>

View file

@ -0,0 +1,18 @@
<div class="input-group">
<label for="{{ $field }}">
{{ $label }}
</label>
<input
class="@if($errors->has($field)) error @endif"
name="{{ $field }}"
id="{{ $field }}"
type="text"
placeholder="{{ isset($placeholder) ? $placeholder : '' }}"
value="{{ old($field) }}"
{{ isset($required) ? 'required' : '' }}>
@if($errors->has($field))
@foreach($errors->get($field) as $error)
<p class="error-text">{!! $error !!}</p>
@endforeach
@endif
</div>

View file

@ -0,0 +1 @@
<svg class="{{ isset($class) ? $class : 'fill-current w-4 h-4 mr-2' }}" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20"><path d="M10 20a10 10 0 1 1 0-20 10 10 0 0 1 0 20zm2-2.25a8 8 0 0 0 4-2.46V9a2 2 0 0 1-2-2V3.07a7.95 7.95 0 0 0-3-1V3a2 2 0 0 1-2 2v1a2 2 0 0 1-2 2v2h3a2 2 0 0 1 2 2v5.75zm-4 0V15a2 2 0 0 1-2-2v-1h-.5A1.5 1.5 0 0 1 4 10.5V8H2.25A8.01 8.01 0 0 0 8 17.75z"/></svg>

After

Width:  |  Height:  |  Size: 389 B

View file

@ -0,0 +1 @@
<svg class="{{ isset($class) ? $class : 'fill-current w-4 h-4 mr-2' }}" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20"><path d="M7.41 9l2.24 2.24-.83 2L6 10.4l-3.3 3.3-1.4-1.42L4.58 9l-.88-.88c-.53-.53-1-1.3-1.3-2.12h2.2c.15.28.33.53.51.7l.89.9.88-.88C7.48 6.1 8 4.84 8 4H0V2h5V0h2v2h5v2h-2c0 1.37-.74 3.15-1.7 4.12L7.4 9zm3.84 8L10 20H8l5-12h2l5 12h-2l-1.25-3h-5.5zm.83-2h3.84L14 10.4 12.08 15z"/></svg>

After

Width:  |  Height:  |  Size: 412 B

View file

@ -0,0 +1,41 @@
@extends('translation::layout')
@section('body')
<div class="panel w-1/2">
<div class="panel-header">
{{ __('translation::translation.add_language') }}
</div>
<form action="{{ route('languages.store') }}" method="POST">
<fieldset>
<input type="hidden" name="_token" value="{{ csrf_token() }}">
<div class="panel-body p-4">
@include('translation::forms.text', ['field' => 'name', 'label' => __('translation::translation.language_name'), ])
@include('translation::forms.text', ['field' => 'locale', 'label' => __('translation::translation.locale'), ])
</div>
</fieldset>
<div class="panel-footer flex flex-row-reverse">
<button class="button button-blue">
{{ __('translation::translation.save') }}
</button>
</div>
</form>
</div>
@endsection

View file

@ -0,0 +1,56 @@
@extends('translation::layout')
@section('body')
@if(count($languages))
<div class="panel w-1/2">
<div class="panel-header">
{{ __('translation::translation.languages') }}
<div class="flex flex-grow justify-end items-center">
<a href="{{ route('languages.create') }}" class="button">
{{ __('translation::translation.add') }}
</a>
</div>
</div>
<div class="panel-body">
<table>
<thead>
<tr>
<th>{{ __('translation::translation.language_name') }}</th>
<th>{{ __('translation::translation.locale') }}</th>
</tr>
</thead>
<tbody>
@foreach($languages as $language => $name)
<tr>
<td>
{{ $name }}
</td>
<td>
<a href="{{ route('languages.translations.index', $language) }}">
{{ $language }}
</a>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
@endif
@endsection

View file

@ -0,0 +1,56 @@
@extends('translation::layout')
@section('body')
<div class="panel w-1/2">
<div class="panel-header">
{{ __('translation::translation.add_translation') }}
</div>
<form action="{{ route('languages.translations.store', $language) }}" method="POST">
<fieldset>
<input type="hidden" name="_token" value="{{ csrf_token() }}">
<div class="panel-body p-4">
@include('translation::forms.text', ['field' => 'group', 'label' => __('translation::translation.group_label'), 'placeholder' => __('translation::translation.group_placeholder')])
@include('translation::forms.text', ['field' => 'key', 'label' => __('translation::translation.key_label'), 'placeholder' => __('translation::translation.key_placeholder')])
@include('translation::forms.text', ['field' => 'value', 'label' => __('translation::translation.value_label'), 'placeholder' => __('translation::translation.value_placeholder')])
<div class="input-group">
<button v-on:click="toggleAdvancedOptions" class="text-blue">{{ __('translation::translation.advanced_options') }}</button>
</div>
<div v-show="showAdvancedOptions">
@include('translation::forms.text', ['field' => 'namespace', 'label' => __('translation::translation.namespace_label'), 'placeholder' => __('translation::translation.namespace_placeholder')])
</div>
</div>
</fieldset>
<div class="panel-footer flex flex-row-reverse">
<button class="button button-blue">
{{ __('translation::translation.save') }}
</button>
</div>
</form>
</div>
@endsection

View file

@ -0,0 +1,89 @@
@extends('translation::layout')
@section('body')
<form action="{{ route('languages.translations.index', ['language' => $language]) }}" method="get">
<div class="panel">
<div class="panel-header">
{{ __('translation::translation.translations') }}
<div class="flex flex-grow justify-end items-center">
@include('translation::forms.search', ['name' => 'filter', 'value' => Request::get('filter')])
@include('translation::forms.select', ['name' => 'language', 'items' => $languages, 'submit' => true, 'selected' => $language])
<div class="sm:hidden lg:flex items-center">
@include('translation::forms.select', ['name' => 'group', 'items' => $groups, 'submit' => true, 'selected' => Request::get('group'), 'optional' => true])
<a href="{{ route('languages.translations.create', $language) }}" class="button">
{{ __('translation::translation.add') }}
</a>
</div>
</div>
</div>
<div class="panel-body">
@if(count($translations))
<table>
<thead>
<tr>
<th class="w-1/5 uppercase font-thin">{{ __('translation::translation.group_single') }}</th>
<th class="w-1/5 uppercase font-thin">{{ __('translation::translation.key') }}</th>
<th class="uppercase font-thin">{{ config('app.locale') }}</th>
<th class="uppercase font-thin">{{ $language }}</th>
</tr>
</thead>
<tbody>
@foreach($translations as $type => $items)
@foreach($items as $group => $translations)
@foreach($translations as $key => $value)
@if(!is_array($value[config('app.locale')]))
<tr>
<td>{{ $group }}</td>
<td>{{ $key }}</td>
<td>{{ $value[config('app.locale')] }}</td>
<td>
<translation-input
initial-translation="{{ $value[$language] }}"
language="{{ $language }}"
group="{{ $group }}"
translation-key="{{ $key }}"
route="{{ config('translation.ui_url') }}">
</translation-input>
</td>
</tr>
@endif
@endforeach
@endforeach
@endforeach
</tbody>
</table>
@endif
</div>
</div>
</form>
@endsection

View file

@ -0,0 +1,24 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<meta name="csrf-token" content="{{ csrf_token() }}">
<title>{{ config('app.name') }}</title>
<link rel="stylesheet" href="{{ asset('/vendor/translation/css/main.css') }}">
</head>
<body>
<div id="app">
@include('translation::nav')
@include('translation::notifications')
@yield('body')
</div>
<script src="{{ asset('/vendor/translation/js/app.js') }}"></script>
</body>
</html>

View file

@ -0,0 +1,23 @@
<nav class="header">
<h1 class="text-lg px-6">{{ config('app.name') }}</h1>
<ul class="flex-grow justify-end pr-2">
<li>
<a href="{{ route('bo.home') }}">{{ __("Retour à l'administration générale")}}</a>
</li>
{{--<li>
<a href="{{ route('languages.index') }}" class="{{ set_active('') }}{{ set_active('/create') }}">
@include('translation::icons.globe')
{{ __('translation::translation.languages') }}
</a>
</li>
<li>
<a href="{{ route('languages.translations.index', config('app.locale')) }}" class="{{ set_active('*/translations') }}">
@include('translation::icons.translate')
{{ __('translation::translation.translations') }}
</a>
</li>--}}
</ul>
</nav>

View file

@ -0,0 +1,15 @@
@if(Session::has('success'))
<div class="bg-green-lightest text-green-darker p-6 shadow-md" role="alert">
<div class="flex justify-center">
<p>{{ Session::get('success') }}</p>
</div>
</div>
@endif
@if(Session::has('error'))
<div class="bg-red-lightest text-red-darker p-6 shadow-md" role="alert">
<div class="flex justify-center">
<p>{!! Session::get('error') !!}</p>
</div>
</div>
@endif