{ "app": { "name": "EverShelf", "loading": "Chargement..." }, "nav": { "title": "EverShelf", "home": "Accueil", "inventory": "Garde-manger", "recipes": "Recettes", "shopping": "Courses", "log": "Journal", "settings": "Paramètres" }, "btn": { "back": "← Retour", "save": "💾 Enregistrer", "cancel": "✕ Annuler", "close": "Fermer", "add": "✅ Ajouter", "delete": "Supprimer", "edit": "✏️ Modifier", "use": "Utiliser", "edit_item": "Modifier", "search": "🔍 Rechercher", "go": "✅ Valider", "toggle_password": "👁️ Afficher/Masquer", "load_more": "Charger plus...", "save_config": "💾 Enregistrer la configuration", "save_product": "💾 Enregistrer le produit", "restart": "↺ Redémarrer", "reset_default": "↺ Rétablir les valeurs par défaut", "save_info": "💾 Enregistrer les informations", "retry": "🔄 Réessayer", "yes_short": "Oui", "no_short": "Non" }, "form": { "select_placeholder": "-- Sélectionner --" }, "locations": { "dispensa": "Garde-manger", "frigo": "Réfrigérateur", "freezer": "Congélateur", "altro": "Autre" }, "categories": { "latticini": "Produits laitiers", "carne": "Viande", "pesce": "Poisson", "frutta": "Fruits", "verdura": "Légumes", "pasta": "Pâtes & Riz", "pane": "Pain & Boulangerie", "surgelati": "Surgelés", "bevande": "Boissons", "condimenti": "Condiments", "snack": "Snacks & Sucreries", "conserve": "Conserves", "cereali": "Céréales & Légumineuses", "igiene": "Hygiène", "pulizia": "Entretien", "altro": "Autre", "select": "-- Sélectionner --" }, "units": { "pz": "pcs", "conf": "pkg", "g": "g", "ml": "ml", "pieces": "Pièces", "grams": "Grammes", "box": "Paquet", "boxes": "Paquets", "millilitres": "Millilitres", "from": "de" }, "shopping_sections": { "frutta_verdura": "Fruits & Légumes", "carne_pesce": "Viande & Poisson", "latticini": "Produits laitiers & Frais", "pane_dolci": "Pain & Pâtisseries", "pasta": "Pâtes & Céréales", "conserve": "Conserves & Sauces", "surgelati": "Surgelés", "bevande": "Boissons", "pulizia_igiene": "Nettoyage & Hygiène", "altro": "Autre" }, "dashboard": { "expired_title": "🚫 Périmé", "expiring_title": "⏰ Expire bientôt", "stats_period": "📊 30 derniers jours", "opened_title": "📦 Produits ouverts", "review_title": "🔍 À vérifier", "review_hint": "Quantités inhabituelles. Confirmez si elles sont correctes ou modifiez-les.", "quick_recipe": "Recette rapide avec les produits qui expirent", "banner_review_title": "Quantité anormale", "banner_review_action_ok": "C'est correct", "banner_review_action_finish": "🗑️ Tout fini", "banner_review_action_edit": "Corriger", "banner_review_action_weigh": "Peser", "banner_review_dismiss": "Ignorer", "banner_prediction_title": "Consommation à vérifier", "banner_prediction_hint": "L'estimation de consommation s'adapte aux données récentes : confirmez uniquement si la quantité actuelle est correcte.", "banner_prediction_action_confirm": "Confirmer {qty} {unit}", "banner_prediction_action_weigh": "Peser maintenant", "banner_prediction_action_edit": "Mettre à jour la quantité", "banner_expired_title": "Produit périmé", "banner_expired_today": "Périmé aujourd'hui", "banner_expired_days": "Périmé il y a {days} jours", "banner_expired_action_use": "Utiliser quand même", "banner_expired_action_finished": "Je l'ai terminé !", "banner_expired_action_throw": "Je l'ai jeté", "banner_expired_action_edit": "Corriger la date", "banner_anomaly_action_edit": "Corriger l'inventaire", "banner_anomaly_action_dismiss": "La quantité est correcte", "banner_no_expiry_title": "Date manquante : {name}", "banner_no_expiry_detail": "Ce produit n'a pas de date de péremption. Voulez-vous en ajouter une ou confirmer qu'il ne périme pas ?", "banner_no_expiry_action_set": "Définir une date de péremption", "banner_no_expiry_action_dismiss": "Ne périme pas ✓", "banner_no_expiry_toast_dismissed": "Marqué comme « sans date limite »", "banner_expiring_title": "Expire bientôt", "banner_expiring_today": "Expire aujourd'hui !", "banner_expiring_tomorrow": "Expire demain", "banner_expiring_days": "Expire dans {days} jours", "banner_expiring_action_use": "Utiliser maintenant", "banner_finished_title": "terminé ?", "banner_finished_detail": "J'ai enregistré que {name} a atteint zéro stock. Est-il vraiment épuisé ou en avez-vous encore ?", "banner_finished_action_yes": "Oui, c'est fini", "banner_finished_action_no": "Non, j'en ai encore", "banner_review_unusual_pkg_title": "Taille de paquet inhabituelle", "banner_review_unusual_pkg_detail": "Vous avez défini un paquet de {qty} {unit} — la taille semble très grande. Vérifiez si c'est correct ou modifiez.", "banner_review_low_qty_title": "Quantité très faible", "banner_review_low_qty_detail": "Vous n'avez que {qty} en stock — cela semble très peu, peut-être une erreur de saisie. Confirmez si c'est correct.", "banner_review_high_qty_title": "Quantité inhabituellement élevée", "banner_review_high_qty_detail": "Vous avez {qty} en stock — le chiffre semble très élevé. Confirmez si c'est correct ou modifiez.", "banner_prediction_rate_day": "Moyenne ~{n} {unit}/jour", "banner_prediction_rate_week": "Moyenne ~{n} {unit}/semaine", "banner_prediction_days_ago": "Il y a {n} jours vous avez réapprovisionné", "banner_prediction_more": "estimation précédente : {expected} {unit}{time} ; quantité actuelle : {actual} {unit}.", "banner_prediction_less": "estimation : {expected} {unit}{time} ; quantité actuelle : {actual} {unit}. Si votre rythme d'utilisation a changé, la prévision se met à jour automatiquement.", "banner_finished_zero": "L'inventaire indique zéro, mais les mouvements enregistrés suggèrent qu'il ne devrait pas être vide.", "banner_finished_expected": "D'après les enregistrements vous devriez avoir encore {qty} {unit}.", "banner_finished_check": "Pouvez-vous vérifier ?", "banner_anomaly_phantom_title": "vous avez plus de stock que prévu", "banner_anomaly_phantom_detail": "L'inventaire indique {inv_qty} {unit}, mais selon les enregistrements vous ne devriez avoir que {expected_qty} {unit}. Avez-vous ajouté du stock sans l'enregistrer ?", "banner_anomaly_untracked_title": "stock non enregistré comme entrée", "banner_anomaly_untracked_detail": "Vous avez {inv_qty} {unit} en inventaire, mais les sorties enregistrées dépassent les entrées — le stock initial n'a probablement jamais été ajouté comme transaction « entrée ». Vous pouvez corriger la quantité ou saisir les entrées manquantes.", "banner_anomaly_ghost_title": "vous avez moins de stock que prévu", "banner_anomaly_ghost_detail": "D'après les opérations enregistrées vous devriez avoir {expected_qty} {unit} de {name}, mais l'inventaire n'en montre que {inv_qty} {unit}. Avez-vous pris du stock sans l'enregistrer ?", "consumed": "Consommé : {n} ({pct}%)", "wasted": "Gaspillé : {n} ({pct}%)", "more_opened": "et {n} autres ouverts...", "banner_expired_detail": "{when} · il vous reste encore {qty}.", "banner_opened_detail": "{when} dans {location} · il vous reste encore {qty}.", "banner_explain_title": "Demander une explication à Gemini", "banner_explain_btn": "Expliquer", "banner_analyzing": "🤖 Analyse en cours…" }, "inventory": { "title": "Garde-manger", "filter_all": "Tout", "search_placeholder": "🔍 Rechercher un produit...", "recent_title": "🕐 Utilisés récemment", "popular_title": "⭐ Les plus utilisés", "empty": "Aucun produit ici.\nScannez un produit pour l'ajouter !", "no_items_found": "Aucun article trouvé", "qty_remainder_suffix": "restant", "vacuum_badge": "🫙 Sous vide", "opened_badge": "📭 Ouvert", "label_expiry": "📅 Péremption", "label_storage": "🫙 Conservation", "label_status": "📭 État", "opened_since": "Ouvert depuis le {date}", "label_position": "📍 Emplacement", "label_quantity": "📦 Quantité", "label_added": "📅 Ajouté", "empty_text": "Aucun produit ici.
Scannez un produit pour l'ajouter !", "empty_db": "Aucun produit dans la base de données.
Scannez un produit pour commencer !", "qty_trace": "< 1" }, "scan": { "title": "Scanner", "mode_shopping": "🛒 Mode courses", "mode_shopping_end": "✅ Terminer les courses", "spesa_btn": "🛒 Courses", "zoom": "Zoom", "tab_barcode": "Code-barres", "tab_name": "Nom", "tab_ai": "IA", "recents_label": "Récents", "torch_hint": "Torche", "torch_on": "Torche activée", "torch_off": "Torche désactivée", "torch_unavailable": "Torche non disponible sur cet appareil", "flip_hint": "Retourner la caméra", "flip_front": "Caméra frontale", "flip_back": "Caméra arrière", "num_ocr_btn": "🔢 Lire les chiffres avec l'IA", "num_ocr_searching": "Recherche du code-barres avec l'IA...", "num_ocr_found": "Code trouvé : {code}", "num_ocr_not_found": "Aucun code-barres trouvé dans l'image", "barcode_placeholder": "Entrez le code-barres...", "quick_name_divider": "ou tapez le nom", "quick_name_placeholder": "Ex. : Pommes, Courgettes, Pain...", "manual_entry": "✏️ Saisie manuelle", "ai_identify": "🤖 Identifier avec l'IA", "hint": "Scannez le code-barres, tapez le nom du produit ou utilisez l'IA pour l'identifier", "debug_toggle": "🐛 Journal de débogage", "barcode_acquired": "🔖 Code-barres scanné : {code}", "scan_barcode": "🔖 Scanner le code-barres", "create_named": "Créer {name}", "new_without_barcode": "Nouveau produit sans code-barres" }, "action": { "title": "Que voulez-vous faire ?", "add_btn": "📥 AJOUTER", "add_sub": "au garde-manger/réfrigérateur", "use_btn": "📤 UTILISER / CONSOMMER", "use_sub": "depuis le garde-manger/réfrigérateur", "have_title": "📦 Déjà en stock !", "add_more_sub": "en ajouter", "use_qty_sub": "combien vous avez utilisé", "throw_btn": "🗑️ JETER", "throw_sub": "jeter", "edit_sub": "péremption, emplacement…", "create_recipe_btn": "Recette" }, "add": { "title": "Ajouter au garde-manger", "location_label": "📍 Où le rangez-vous ?", "quantity_label": "📦 Quantité", "conf_size_label": "📦 Chaque paquet contient :", "conf_size_placeholder": "ex. 300", "vacuum_label": "🫙 Sous vide", "vacuum_hint": "La date de péremption sera automatiquement prolongée", "submit": "✅ Ajouter", "purchase_type_label": "🛒 Ce produit est...", "new_btn": "🆕 Vient d'être acheté", "existing_btn": "📦 Je l'avais déjà", "remaining_label": "📦 Quantité restante", "remaining_hint": "Approximativement combien en reste-t-il ?", "remaining_full": "🟢 Plein", "remaining_half": "🟠 À moitié", "estimated_expiry": "Date de péremption estimée :", "suffix_freezer": "(congélateur)", "suffix_vacuum": "(sous vide)", "hint_modify": "📝 Vous pouvez modifier la date ou la scanner avec la caméra", "scan_expiry_title": "📷 Scanner la date de péremption", "product_added": "✅ {name} ajouté !{qty}", "suffix_freezer_vacuum": "(congélateur + sous vide)", "history_badge_tip": "Moyenne de {n} entrées précédentes", "vacuum_question": "Sous vide ?", "vacuum_saved": "🔒 Sous vide !" }, "use": { "title": "Utiliser / Consommer", "location_label": "📍 Depuis où ?", "quantity_label": "Combien avez-vous utilisé ?", "change": "modifier", "partial_hint": "Ou précisez la quantité utilisée :", "partial_piece_hint": "Avez-vous utilisé seulement une partie ?", "piece": "pièce", "one_whole": "1 entier", "use_all": "🗑️ Tout utilisé / Terminé", "submit": "📤 Utiliser cette quantité", "available": "📦 Disponible :", "opened_badge": "OUVERT", "not_in_inventory": "⚠️ Produit absent de l'inventaire.", "expiry_warning": "⚠️ Utilisez en premier celui{loc} qui expire le {date} — {when} !", "expiry_warning_opened": "⚠️ Celui{loc} est ouvert depuis {when} — utilisez-le en premier !", "throw_title": "🗑️ Jeter le produit", "throw_all": "🗑️ Tout jeter ({qty})", "throw_qty_label": "Quelle quantité jeter ?", "throw_qty_hint": "ou entrez une quantité :", "throw_partial_btn": "🗑️ Jeter cette quantité", "when_expired": "périmé il y a {n} jours", "when_today": "expire aujourd'hui", "when_tomorrow": "expire demain", "when_days": "expire dans {n} jours", "toast_used": "📤 {qty} de {name} utilisé", "toast_bring": "🛒 Produit terminé → ajouté à Bring !", "toast_opened_finished": "🔓 Emballage ouvert de {name} terminé !", "disambiguation_hint": "Que voulez-vous dire par « tout fini » ?", "disambiguation_all": "🗑️ Tout finir ({qty})", "error_exceeds_stock": "⚠️ Vous ne pouvez pas utiliser plus que ce que vous avez disponible !", "use_all_confirm_title": "✅ Tout terminer", "use_all_confirm_msg": "Confirmez que vous avez terminé le produit :", "use_all_confirm_btn": "✅ Oui, terminé", "throw_all_confirm_title": "🗑️ Tout jeter", "throw_all_confirm_msg": "Voulez-vous vraiment jeter tout le produit ?", "throw_all_confirm_btn": "🗑️ Oui, jeter" }, "product": { "title_new": "Nouveau produit", "title_edit": "Modifier le produit", "ai_fill": "📷 Prendre une photo et identifier avec l'IA", "ai_fill_hint": "L'IA remplira automatiquement les champs du produit", "name_label": "🏷️ Nom du produit *", "name_placeholder": "Ex. : Lait entier, Pâtes penne...", "brand_label": "🏢 Marque", "brand_placeholder": "Ex. : Barilla, Danone, Heinz...", "category_label": "📂 Catégorie", "unit_label": "📏 Unité de mesure", "default_qty_label": "🔢 Quantité par défaut", "conf_size_label": "📦 Chaque paquet contient :", "conf_size_placeholder": "ex. 300", "notes_label": "📝 Notes", "notes_placeholder": "Ex. : sans lactose, biologique, conserver au réfrigérateur après ouverture...", "barcode_label": "🔖 Code-barres", "barcode_placeholder": "Code-barres (si disponible)", "barcode_hint": "⚠️ Ajoutez le code-barres pour la prochaine fois, il suffira de scanner !", "submit": "💾 Enregistrer le produit", "name_required": "Entrez le nom du produit", "conf_size_required": "Précisez le contenu du paquet", "expiry_estimated": "Date de péremption estimée :", "scan_expiry": "Scanner la date de péremption", "expiry_hint": "📝 Vous pouvez modifier la date ou la scanner avec la caméra", "add_batch": "📦 + Lot avec une date différente", "package_info": "📦 Paquet : {info}", "edit_catalog": "⚙️ Modifier les infos produit (nom, marque, catégorie…)", "not_recognized": "⚠️ Produit non reconnu", "edit_info": "✏️ Modifier les informations", "modify_details": "MODIFIER\npéremption, emplacement…", "already_in_pantry": "📋 Déjà dans le garde-manger", "no_barcode": "Pas de code-barres", "unknown_product": "Produit non reconnu", "edit_name_brand": "Modifier nom/marque", "weight_label": "Poids", "origin_label": "Origine", "labels_label": "Labels", "select_variant": "Sélectionnez la variante exacte ou utilisez les données IA :" }, "products": { "title": "📦 Tous les produits", "search_placeholder": "🔍 Rechercher un produit...", "empty": "Aucun produit dans la base de données.\nScannez un produit pour commencer !", "no_category": "Aucun produit dans cette catégorie" }, "recipes": { "title": "🍳 Recettes", "generate": "✨ Générer une nouvelle recette", "archive_empty": "Aucune recette enregistrée. Générez votre première recette !", "dialog_title": "🍳 Recette", "dialog_desc": "Je vais générer une recette saine en utilisant les ingrédients du garde-manger, en priorisant les produits qui expirent.", "meal_label": "🕐 Quel repas ?", "persons_label": "👥 Pour combien de personnes ?", "meal_type_label": "🎯 Type de repas", "opt_fast": "⚡ Repas rapide", "opt_light": "🥗 Appétit léger", "opt_expiry": "⏰ Prioriser les produits qui expirent", "opt_healthy": "💚 Extra sain", "opt_opened": "📦 Prioriser les produits ouverts", "opt_zero_waste": "♻️ Zéro déchet", "generate_btn": "✨ Générer la recette", "loading_msg": "Préparation de votre recette...", "start_cooking": "👨‍🍳 Mode cuisine", "regenerate": "🔄 En générer une autre", "close_btn": "✅ Fermer", "ingredients_title": "🧾 Ingrédients", "tools_title": "Matériel nécessaire", "steps_title": "👨‍🍳 Étapes", "no_steps": "Aucune étape disponible", "generate_error": "Erreur de génération", "persons_short": "pers.", "use_ingredient_title": "Utiliser l'ingrédient", "recipe_qty_label": "Recette", "from_where_label": "Depuis où ?", "amount_label": "Combien", "use_amount_btn": "Utiliser cette quantité", "use_all_btn": "Tout utiliser / Terminé", "packs_label": "Paquets", "quantity_in_total": "Quantité en {unit} (total : {total})", "packs_of_have": "Paquets de {size} (vous en avez {count})", "scale_wait_stable": "Attendez 10s de poids stable pour le remplissage automatique…", "ingredient_scaled_toast": "📦 Ingrédient déduit du garde-manger !", "finished_added_bring_toast": "🛒 Produit terminé → ajouté à Bring !", "load_error": "Erreur de chargement" }, "shopping": { "title": "🛒 Liste de courses", "bring_loading": "Connexion à Bring !...", "bring_not_configured": "Bring ! n'est pas configuré. Ajoutez votre e-mail et mot de passe dans les paramètres.", "tab_to_buy": "🛍️ À acheter", "tab_forecast": "🧠 Prévision", "total_label": "💰 Total estimé", "section_to_buy": "🛍️ À acheter", "suggestions_title": "💡 Suggestions IA", "suggestions_add": "✅ Ajouter la sélection à Bring !", "search_prices": "🔍 Rechercher tous les prix", "suggest_btn": "Suggérer des achats", "smart_title": "🧠 Prévisions intelligentes", "smart_empty": "Aucune prévision disponible.
Ajoutez des produits à votre garde-manger pour recevoir des prévisions intelligentes.", "smart_filter_all": "Tout", "smart_filter_critical": "🔴 Urgent", "smart_filter_high": "🟠 Bientôt", "smart_filter_medium": "🟡 Planifier", "smart_filter_low": "🟢 Prévision", "smart_add": "🛒 Ajouter la sélection à Bring !", "empty": "Liste de courses vide !\nUtilisez le bouton ci-dessous pour générer des suggestions.", "already_in_list": "🛒 \"{name}\" est déjà dans la liste de courses", "already_in_list_short": "ℹ️ Déjà dans la liste de courses", "add_prompt": "Voulez-vous l'ajouter à la liste de courses ?", "smart_already": "📊 Les prévisions achats prédisent déjà {name}", "all_searched": "Tous les produits ont déjà été recherchés. Utilisez 🔄 pour rechercher individuellement.", "search_complete": "Recherche terminée : {count} produits", "removed_sufficient": "🧹 {removed} produit(s) avec stock suffisant retiré(s) de la liste", "suggest_buy": "🛒 Acheter : {qty} {unit}", "suggest_buy_approx": "🛒 Au minimum : {qty} {unit}", "suggest_buy_tip": "Quantité suggérée basée sur vos 14 derniers jours de consommation", "suggest_buy_approx_tip": "Estimation minimale basée sur la consommation (achetez le format le plus proche)", "bring_badge": "🛒 Déjà sur Bring !", "add_urgent_toast": "🔴 {n} produit(s) urgent(s) automatiquement ajouté(s) à Bring !", "migration_done": "✅ {migrated} mis à jour, {skipped} déjà ok", "added_to_bring": "🛒 {n} produits ajoutés à Bring !", "added_to_bring_skip": "{n} déjà présents", "all_on_bring": "Tous les produits étaient déjà sur Bring !", "freq_high": "📈 Fréquent", "freq_regular": "📊 Régulier", "freq_occasional": "📉 Occasionnel", "out_of_stock": "Rupture de stock", "scan_toast": "📷 Scanner : {name}", "empty_category": "Aucun produit dans cette catégorie", "session_empty": "🛒 Aucun produit encore", "urgency_critical": "Urgent", "urgency_high": "Bientôt", "urgency_medium": "Planifier", "urgency_low": "Prévision", "urgency_medium_short": "Moyen", "urgency_low_short": "Ok", "tag_urgent": "🔴 Urgent", "tag_priority": "⭐ Priorité", "tag_check": "✅ Vérifier", "smart_already_predicted": "📊 Les prévisions achats prédisent déjà {name}{urgency}.", "item_removed": "✅ {name} retiré de la liste !", "urgency_spec_critical": "⚡ Urgent", "urgency_spec_high": "🟠 Bientôt", "bring_add_n": "Ajouter {n} à Bring !", "bring_add_selected": "Ajouter la sélection à Bring !", "bring_adding": "Ajout en cours...", "bring_added_one": "1 produit ajouté à Bring !", "bring_added_many": "{n} produits ajoutés à Bring !", "bring_skipped": "({n} déjà dans la liste)", "force_sync": "Forcer la synchronisation Bring !", "scan_target_label": "Vous cherchez", "scan_target_found": "Trouvé ! Retirer de la liste", "bring_add_one": "Ajouter 1 produit à Bring !", "bring_add_many": "Ajouter {n} produits à Bring !", "syncing": "Synchronisation…", "sync_done": "Synchronisation terminée", "price_searching": "Recherche en cours...", "search_action": "Rechercher", "open_action": "Ouvrir", "not_found": "Non trouvé", "search_price": "Rechercher le prix", "tap_to_scan": "Appuyez pour scanner", "tag_title": "Tag", "remove_title": "Retirer", "found_count": "{found}/{total} produits trouvés", "savings_offers": "· 🏷️ Vous économisez {amount}€ avec les offres", "searching_progress": "Recherche {current}/{total}...", "remove_error": "Erreur de suppression", "btn_fetch_prices": "Trouver les prix", "price_total_label": "💰 Total estimé :", "price_loading": "Recherche des prix…", "price_not_found": "prix n/d", "suggest_loading": "Analyse en cours...", "suggest_error": "Erreur de génération des suggestions", "priority_high": "Élevée", "priority_medium": "Moyenne", "priority_low": "Faible", "smart_last_update": "Mis à jour {time}", "names_already_updated": "Tous les noms sont déjà à jour" }, "ai": { "title": "🤖 Identification IA", "capture": "📸 Prendre une photo", "retake": "🔄 Reprendre", "hint": "Prenez une photo du produit et l'IA essaiera de l'identifier", "identifying": "🤖 Identification du produit...", "no_api_key": "⚠️ Clé API Gemini non configurée.\nAjoutez GEMINI_API_KEY au fichier .env sur le serveur.", "fields_filled": "✅ Champs remplis par l'IA", "use_data": "✅ Utiliser les données IA", "use_data_no_barcode": "✅ Utiliser les données IA (sans code-barres)" }, "log": { "title": "📒 Journal des opérations", "type_added": "Ajouté", "type_waste": "Jeté", "type_used": "Utilisé", "type_bring": "Ajouté à Bring !", "undone_badge": "Annulé", "undo_title": "Annuler cette opération", "load_error": "Erreur de chargement du journal", "empty": "Aucune opération enregistrée.", "undo_action_remove": "suppression de", "undo_action_restore": "réapprovisionnement de", "undo_confirm": "Annuler cette opération ?\n→ {action} {name}", "undo_success": "↩ Opération annulée pour {name}", "already_undone": "Opération déjà annulée", "too_old": "Impossible d'annuler des opérations de plus de 24 heures", "undo_error": "Erreur lors de l'annulation", "recipe_prefix": "Recette" }, "chat": { "title": "Chef Gemini", "welcome": "Bonjour ! Je suis votre assistant cuisine", "welcome_desc": "Demandez-moi de préparer un jus, un snack, un plat rapide… Je connais votre garde-manger, vos appareils et vos préférences !", "suggestion_snack": "🍿 Snack rapide", "suggestion_juice": "🥤 Jus/Smoothie", "suggestion_light": "🥗 Quelque chose de léger", "suggestion_expiry": "⏰ Utiliser les produits qui expirent", "clear": "Nouvelle conversation", "placeholder": "Demandez quelque chose...", "cleared": "Chat effacé", "suggestion_snack_text": "Que puis-je préparer comme snack rapide ?", "suggestion_juice_text": "Faites-moi un jus ou un smoothie avec ce que j'ai", "suggestion_light_text": "J'ai faim mais je veux quelque chose de léger", "suggestion_expiry_text": "Qu'est-ce qui va bientôt expirer et comment l'utiliser ?", "transfer_to_recipes": "Transférer aux recettes", "transferring": "Transfert en cours...", "transferred": "Ajouté aux recettes !", "open_recipe": "Ouvrir la recette", "quick_recipe_prompt": "Suggérez une recette rapide POUR UNE PERSONNE en utilisant les produits qui expirent en premier ! Ignorez les congélateurs, concentrez-vous sur le réfrigérateur et le garde-manger." }, "cooking": { "close": "Fermer", "tts_btn": "Lire à voix haute", "restart": "↺ Recommencer", "replay": "🔊 Rejouer", "timer": "⏱️ {time} · Minuterie", "prev": "◀ Précédent", "next": "Suivant ▶", "ingredient_used": "✔️ Déduit", "ingredient_use_btn": "📦 Utiliser", "ingredient_deduct_title": "Déduire du garde-manger", "timer_expired_tts": "Minuterie {label} terminée !", "timer_warning_tts": "Attention ! {label} : 10 secondes restantes !", "recipe_done_tts": "Recette terminée ! Bon appétit !", "expires_chip": "exp. {date}", "finish": "✅ Terminer", "step_fallback": "Étape {n}" }, "settings": { "title": "⚙️ Paramètres", "tab_api": "Clés API", "tab_bring": "Bring !", "tab_recipe": "Recettes", "tab_mealplan": "Plan hebdomadaire", "tab_appliances": "Appareils", "tab_spesa": "Courses en ligne", "tab_camera": "Caméra", "tab_security": "Sécurité", "tab_tts": "Voix (TTS)", "tab_language": "Langue", "tab_scale": "Balance connectée", "gemini": { "title": "🤖 Google Gemini IA", "hint": "Clé API pour l'identification des produits, les dates de péremption et les recettes.", "key_label": "Clé API Gemini" }, "bring": { "title": "🛒 Liste de courses Bring !", "hint": "Identifiants pour l'intégration de la liste de courses Bring !", "email_label": "📧 E-mail Bring !", "password_label": "🔒 Mot de passe Bring !" }, "price": { "title": "💰 Estimation des prix (IA)", "hint": "Afficher le coût estimé par produit dans la liste de courses à l'aide de l'IA.", "enabled_label": "Activer l'estimation des prix", "country_label": "🌍 Pays de référence", "currency_label": "💱 Devise", "update_label": "🔄 Actualiser les prix tous les", "update_suffix": "mois" }, "recipe": { "title": "🍳 Préférences de recettes", "hint": "Configurez les options par défaut pour la génération de recettes.", "persons_label": "👥 Portions par défaut", "options_label": "🎯 Options de recette par défaut", "fast": "⚡ Repas rapide", "light": "🥗 Repas léger", "expiry": "⏰ Priorité péremption", "healthy": "💚 Extra sain", "opened": "📦 Priorité produits ouverts", "zerowaste": "♻️ Zéro déchet", "dietary_label": "🚫 Intolérances / Restrictions", "dietary_placeholder": "Ex. : sans gluten, sans lactose, végétarien..." }, "mealplan": { "title": "📅 Plan de repas hebdomadaire", "hint": "Définissez le type de repas pour chaque jour. Il sera utilisé comme guide pour la génération de recettes.", "enabled": "✅ Activer le plan hebdomadaire", "legend": "🌤️ = Déjeuner  ·  🌙 = Dîner  ·  Appuyez sur un badge pour le modifier.", "types_title": "📋 Types disponibles", "reset_btn": "↺ Restaurer les valeurs par défaut" }, "appliances": { "title": "🔌 Appareils disponibles", "hint": "Indiquez les appareils que vous possédez. Ils seront pris en compte lors de la génération de recettes.", "new_placeholder": "Ex. : Machine à pain, Thermomix, Friteuse à air...", "quick_title": "Ajout rapide :", "oven": "🔥 Four", "microwave": "📡 Micro-ondes", "air_fryer": "🍟 Friteuse à air", "bread_maker": "🍞 Machine à pain", "bimby": "🤖 Thermomix/Cookeo", "mixer": "🌀 Robot pâtissier", "steamer": "♨️ Cuiseur vapeur", "pressure_cooker": "🫕 Cocotte-minute", "toaster": "🍞 Grille-pain", "blender": "🍹 Mixeur", "empty": "Aucun appareil ajouté" }, "spesa": { "title": "🛍️ Courses en ligne", "hint": "Configurez le fournisseur de courses en ligne.", "provider_label": "🏪 Fournisseur", "email_label": "📧 E-mail", "password_label": "🔒 Mot de passe", "login_btn": "🔐 Connexion", "ai_prompt_label": "🤖 Prompt IA de sélection de produit", "ai_prompt_placeholder": "Instructions pour l'IA lors du choix entre plusieurs produits...", "ai_prompt_hint": "L'IA utilise ce prompt pour choisir le produit le plus approprié parmi les résultats. Laissez vide pour le comportement par défaut.", "configure_first": "Configurez d'abord les courses en ligne dans les paramètres", "missing_credentials": "Entrez l'e-mail et le mot de passe", "login_in_progress": "Connexion en cours...", "login_error_prefix": "Erreur :", "login_network_error_prefix": "Erreur réseau :", "login_success_default": "Connexion réussie !", "result_name_label": "Nom", "result_card_label": "Carte", "result_pickup_label": "Point de retrait", "result_points_label": "Points fidélité", "connected_relogin": "✅ Connecté — Se reconnecter", "connected_as": "Connecté en tant que {name}" }, "camera": { "title": "📷 Caméra", "hint": "Choisissez la caméra à utiliser pour le scan de code-barres et l'identification IA.", "device_label": "📸 Caméra par défaut", "back": "📱 Arrière (par défaut)", "front": "🤳 Frontale", "devices_hint": "Si vous avez plusieurs caméras, vous pouvez en sélectionner une dans la liste ci-dessus après avoir accordé les permissions.", "detect_btn": "🔄 Détecter les caméras" }, "security": { "title": "🔒 Certificat HTTPS", "hint": "Si le navigateur affiche l'erreur « Votre connexion n'est pas privée » (ERR_CERT_AUTHORITY_INVALID), vous devez installer le certificat CA sur l'appareil.", "download_btn": "📥 Télécharger le certificat CA", "token_title": "🔑 Token de paramètres", "token_label": "Token d'accès", "token_hint": "Si `SETTINGS_TOKEN` est configuré dans le `.env` du serveur, entrez le token ici avant de sauvegarder les paramètres. Laissez vide si non configuré.", "token_placeholder": "(vide = pas de protection)", "token_required_hint": "🔒 Ce serveur nécessite un token pour sauvegarder les paramètres.", "cert_instructions": "Instructions pour Chrome (Android) :
1. Téléchargez le certificat ci-dessus
2. Allez dans Paramètres → Sécurité & Confidentialité → Plus de paramètres de sécurité → Installer depuis le stockage
3. Sélectionnez le fichier EverShelf_CA.crt téléchargé
4. Choisissez « CA » et confirmez
5. Redémarrez Chrome

Instructions pour Chrome (PC) :
1. Téléchargez le certificat ci-dessus
2. Allez dans chrome://settings/certificates
3. Onglet « Autorités » → Importer → sélectionnez le fichier
4. Cochez « Approuver ce certificat pour identifier les sites web »
5. Redémarrez Chrome" }, "tts": { "title": "🔊 Voix & TTS", "hint": "Configurez la synthèse vocale via une API REST externe. Les étapes de recette et les minuteries expirées seront envoyées à l'endpoint configuré.", "enabled": "✅ Activer la TTS", "engine_label": "⚙️ Moteur TTS", "engine_browser": "🔇 Navigateur (hors ligne, aucune configuration requise)", "engine_server": "🌐 Serveur externe (Home Assistant, API REST...)", "voice_label": "🗣️ Voix", "rate_label": "⚡ Vitesse", "pitch_label": "🎵 Tonalité", "url_label": "🌐 URL de l'endpoint", "method_label": "📡 Méthode HTTP", "auth_label": "🔐 Authentification", "auth_bearer": "Bearer Token", "auth_custom": "En-tête personnalisé", "auth_none": "Aucune", "token_label": "🔑 Bearer Token", "custom_header_name": "📋 Nom de l'en-tête", "custom_header_value": "📋 Valeur de l'en-tête", "content_type_label": "📄 Content-Type", "payload_key_label": "🗝️ Champ texte dans le payload", "payload_key_hint": "Nom du champ JSON qui contiendra le texte à lire (ex. : message, text).", "extra_fields_label": "➕ Champs supplémentaires (JSON)", "extra_fields_placeholder": "{\"entity_id\": \"media_player.salon\"}", "extra_fields_hint": "Champs supplémentaires à inclure dans le payload, en format JSON. Laissez vide si non nécessaire.", "test_btn": "🔊 Envoyer une voix de test", "voices_loading": "Chargement des voix…", "voice_not_supported": "Voix non supportée par ce navigateur", "voices_none": "Aucune voix disponible sur cet appareil", "voices_hint": "Les voix disponibles dépendent du système d'exploitation et du navigateur. Appuyez sur ↺ si la liste ne se charge pas.", "url_missing": "⚠️ URL de l'endpoint manquante.", "test_sending": "⏳ Envoi…", "test_ok": "✅ Réponse {code} — vérifiez que le haut-parleur a parlé." }, "language": { "title": "🌐 Langue", "hint": "Sélectionnez la langue de l'interface.", "label": "🌐 Langue", "restart_notice": "La page sera rechargée pour appliquer la nouvelle langue." }, "screensaver": { "label": "Activer l'économiseur d'écran", "card_title": "🌙 Économiseur d'écran", "card_hint": "Affiche une horloge avec des informations utiles après 5 minutes d'inactivité. Désactivé par défaut.", "timeout_1": "1 minute", "timeout_2": "2 minutes", "timeout_5": "5 minutes", "timeout_10": "10 minutes", "timeout_15": "15 minutes", "timeout_30": "30 minutes", "timeout_60": "1 heure", "start_after": "⏱️ Démarrer après" }, "scale": { "title": "⚖️ Balance connectée", "hint": "Connectez une balance Bluetooth via la passerelle Android pour lire automatiquement le poids.", "tab": "Balance connectée", "enabled": "✅ Activer la balance connectée", "url_label": "🌐 URL de la passerelle WebSocket", "url_placeholder": "ws://192.168.1.x:8765", "url_hint": "URL affichée par l'application Android (même réseau Wi-Fi). Ex. :", "test_btn": "🔗 Tester la connexion", "download_btn": "📥 Télécharger la passerelle Android (APK)", "download_hint": "Application Android qui connecte votre balance BLE et EverShelf.", "download_sub": "Source : evershelf-scale-gateway/ dans la racine du projet", "live_weight": "poids en temps réel", "auto_reconnect": "🔁 Reconnexion : automatique", "kiosk_title": "📡 Balance BLE intégrée dans le kiosque", "kiosk_hint": "La balance est directement gérée par la passerelle BLE interne du kiosque. Pour associer un nouvel appareil, utilisez l'assistant de configuration.", "kiosk_reconfigure": "🔄 Reconfigurer la balance BLE", "ble_protocols": "

🔌 Protocoles BLE supportés :

" }, "kiosk": { "hint": "Transformez une tablette Android en panneau EverShelf permanent avec passerelle BLE intégrée.", "download_btn": "📥 Télécharger EverShelf Kiosk (APK)", "download_sub": "Mode kiosque plein écran + passerelle de balance intégrée. Source : evershelf-kiosk/", "native_title": "Configuration du kiosque", "native_hint": "URL du serveur, balance BLE, économiseur d'écran et assistant de configuration.", "native_btn": "Ouvrir la configuration du kiosque", "native_tap_hint": "Appuyez sur le bouton engrenage en haut à droite", "native_update_hint": "Mettez à jour l'application kiosque pour utiliser cette fonctionnalité", "update_title": "Mise à jour du kiosque", "check_updates_btn": "🔍 Vérifier les mises à jour", "needs_update": "⚠️ Le kiosque installé ne supporte pas cette fonctionnalité. Mettez à jour l'application kiosque pour l'activer." }, "saved": "✅ Configuration enregistrée !", "saved_local": "✅ Configuration enregistrée localement", "saved_local_error": "⚠️ Enregistré localement, erreur serveur : {error}", "theme": { "title": "🌙 Apparence", "hint": "Choisissez le thème de l'interface.", "label": "🌙 Thème", "off": "☀️ Clair", "on": "🌙 Sombre", "auto": "🔄 Automatique (système)" } }, "expiry": { "today": "AUJOURD'HUI", "tomorrow": "Demain", "days": "{days} jours", "expired_days": "il y a {days}j", "expired_yesterday": "Hier", "expired_today": "Aujourd'hui", "badge_today": "⚠️ Expire aujourd'hui !", "badge_tomorrow": "⏰ Demain", "badge_tomorrow_long": "⏰ Expire demain", "badge_days": "⏰ {n} jours", "badge_expired_ago": "⚠️ Périmé il y a {n}j", "badge_expired": "⛔ Périmé !", "badge_stable": "✅ Stable", "badge_expiring_short": "⏰ Exp. dans {n}j", "badge_ok_still": "✅ Encore {n}j", "badge_expires_red": "🔴 Exp. dans {n}j", "badge_expires_yellow": "🟡 Exp. dans {n}j", "badge_expired_bare": "⚠️ Périmé", "badge_expires_warn": "⚠️ Exp. dans {n}j", "badge_days_left": "⏳ ~{n}j restants", "days_approx": "~{n} jours", "weeks_approx": "~{n} semaines", "months_approx": "~{n} mois", "years_approx": "~{n} ans", "expired_today_long": "Périmé aujourd'hui", "expired_ago_long": "Périmé il y a {n} jours", "expired_suffix": "— Périmé !", "expired_suffix_ok": "— Périmé (encore ok)", "expired_suffix_warning": "— Périmé (vérifier d'abord)", "opened_ago_long": "Ouvert il y a {n} jours", "opened_today_long": "Ouvert aujourd'hui", "opened_suffix": "— Ouvert depuis trop longtemps !", "opened_suffix_ok": "— Ouvert (encore ok)", "opened_suffix_warning": "— Ouvert (vérifier d'abord)", "days_compact": "{n}j", "badge_check_soon": "Vérifier prochainement" }, "status": { "ok": "OK", "check": "Vérifier", "discard": "Jeter", "tip_freezer_ok": "Au congélateur : encore sûr (~{n}j de marge)", "tip_freezer_check": "Au congélateur depuis longtemps, peut avoir perdu en qualité. Consommer rapidement", "tip_freezer_danger": "Au congélateur trop longtemps, risque de brûlure de congélation et de dégradation", "tip_highRisk_check": "Périmé récemment, vérifiez l'odeur et l'aspect avant de consommer", "tip_highRisk_danger": "Produit périssable périmé : jeter pour la sécurité", "tip_medRisk_check1": "Vérifiez l'aspect et l'odeur avant de consommer", "tip_medRisk_check2": "Périmé depuis un moment, vérifiez soigneusement avant utilisation", "tip_medRisk_danger": "Trop longtemps depuis la péremption, mieux vaut jeter", "tip_lowRisk_ok": "Produit longue conservation, encore sûr à consommer", "tip_lowRisk_check": "Périmé depuis plus d'un mois, vérifiez l'intégrité de l'emballage", "tip_lowRisk_danger": "Périmé depuis trop longtemps, mieux vaut ne pas risquer" }, "toast": { "product_saved": "Produit enregistré !", "product_created": "Produit créé !", "product_updated": "✅ Produit mis à jour !", "product_removed": "Produit supprimé", "updated": "Mis à jour !", "quantity_confirmed": "✓ Quantité confirmée", "added_to_inventory": "✅ {name} ajouté !", "removed_from_list": "✅ {name} retiré de la liste !", "removed_from_list_short": "Retiré de la liste", "added_to_shopping": "🛒 Ajouté à la liste de courses !", "removed_from_shopping": "🛒 Retiré de la liste de courses", "finished_to_bring": "🛒 Produit terminé → ajouté à Bring !", "thrown_away": "🗑️ {name} jeté !", "thrown_away_partial": "🗑️ {qty} {unit} de {name} jeté(s)", "finished_all": "📤 {name} terminé !", "product_finished_confirmed": "✅ Supprimé — ajoutez-le à nouveau lors du réapprovisionnement", "appliance_added": "Appareil ajouté", "item_added": "{name} ajouté" }, "antiwaste": { "title": "🌱 Rapport anti-gaspi", "grade_label": "Note", "you": "Vous", "avg_label": "Moy.", "better": "🎉 Vous gaspillez {diff}% de moins que la moyenne {country} !", "worse": "⚠️ Vous gaspillez plus que la moyenne {country}. Des progrès sont possibles !", "on_par": "→ Vous êtes dans la moyenne {country}. Vous pouvez faire mieux !", "saved_money": "~{amount}/mois économisé", "saved_meals": "~{n} repas sauvés", "saved_co2": "{n} kg CO₂ évités", "trend_title": "Tendance (3 derniers mois)", "months_ago_2": "-60 jours", "months_ago_1": "-30 jours", "this_month": "Maintenant", "country_it": "Moy. italienne", "country_de": "Moy. allemande", "country_en": "Moy. américaine", "source": "Sources : REDUCE, Eurostat, USDA 2021", "live_on": "Données en direct", "live_off": "Hors ligne", "meals": "repas", "annual_info": "📅 Vous ~{you} kg/an · moy. ~{avg} kg/an", "badge_rate": "taux de perte", "badge_saved_money": "économisé vs moy.", "badge_wasted": "articles perdus", "badge_better": "moins que la moy." }, "error": { "generic": "Erreur", "network": "Erreur réseau", "no_api_key": "Configurez la clé API dans les paramètres", "loading": "Erreur de chargement du produit", "not_found": "Produit introuvable", "not_found_manual": "Produit introuvable. Entrez-le manuellement.", "search": "Erreur de recherche. Réessayez.", "search_short": "Erreur de recherche", "save": "Erreur d'enregistrement", "connection": "Erreur de connexion", "camera": "Impossible d'accéder à la caméra", "bring_add": "Erreur d'ajout à Bring !", "bring_connection": "Erreur de connexion à Bring !", "identification": "Erreur d'identification", "ai_quota": "Quota IA épuisé. Réessayez dans quelques minutes.", "barcode_empty": "Entrez un code-barres", "barcode_format": "Le code-barres ne doit contenir que des chiffres (4-14 chiffres)", "min_chars": "Tapez au moins 2 caractères", "not_in_inventory": "Produit absent de l'inventaire", "appliance_exists": "L'appareil existe déjà", "already_exists": "Existe déjà", "network_retry": "Erreur de connexion. Réessayez.", "select_items": "Sélectionnez au moins un produit", "server_offline": "Connexion au serveur perdue", "server_restored": "Connexion au serveur rétablie", "server_retry": "Réessayer", "unknown": "Erreur inconnue", "prefix": "Erreur", "no_inventory_entry": "Aucune entrée d'inventaire trouvée" }, "confirm": { "remove_item": "Voulez-vous vraiment supprimer ce produit de l'inventaire ?", "kiosk_exit": "Quitter le mode kiosque ?", "cancel": "Annuler", "proceed": "Confirmer" }, "location": { "dispensa": "Garde-manger", "frigo": "Réfrigérateur", "freezer": "Congélateur" }, "edit": { "title": "Modifier {name}", "unknown_hint": "Entrez le nom du produit et les informations", "label_name": "🏷️ Nom du produit", "choose_location_title": "Quel emplacement ?", "choose_location_hint": "Choisissez l'emplacement à modifier :" }, "screensaver": { "recipe_btn": "Recettes", "scan_btn": "Scanner un produit" }, "days": { "mon": "Lundi", "tue": "Mardi", "wed": "Mercredi", "thu": "Jeudi", "fri": "Vendredi", "sat": "Samedi", "sun": "Dimanche", "mon_short": "Lun", "tue_short": "Mar", "wed_short": "Mer", "thu_short": "Jeu", "fri_short": "Ven", "sat_short": "Sam", "sun_short": "Dim" }, "meal_types": { "lunch": "Déjeuner", "dinner": "Dîner", "colazione": "Petit-déjeuner", "merenda": "Goûter", "dolce": "Dessert", "succo": "Jus de fruits", "pranzo": "Déjeuner", "cena": "Dîner" }, "scale": { "status_connected": "Balance connectée", "status_searching": "Passerelle connectée, attente de la balance…", "status_disconnected": "Passerelle de balance inaccessible", "status_error": "Erreur de connexion à la passerelle", "not_connected": "Passerelle de balance non connectée", "read_btn": "⚖️ Lire depuis la balance", "reading_title": "Lecture de la balance", "place_on_scale": "Posez le produit sur la balance…", "waiting_stable": "Le poids sera capturé automatiquement une fois la lecture stable.", "no_url": "Entrez l'URL de la passerelle", "testing": "⏳ Test de connexion…", "connected_ok": "Connexion à la passerelle réussie !", "timeout": "Délai dépassé : pas de réponse de la passerelle", "error_connect": "Impossible de se connecter à la passerelle", "tab": "Balance connectée", "low_weight": "Poids < 10 g · entrez manuellement\n(la lecture automatique nécessite au moins 10 g)", "density_hint": "(densité {density} g/ml)", "ml_hint": "(sera converti en ml)", "weight_detected": "Poids détecté — attendez 10s de stabilité…", "weight_too_low": "Poids trop faible — attente…", "stable": "✓ Stable", "auto_confirm": "✅ {val} {unit} — confirmation automatique dans 5s (appuyez pour annuler)", "cancelled_replace": "Annulé — replacez l'ingrédient sur la balance pour reprendre" }, "prediction": { "expected_qty": "Attendu : {expected} {unit}", "actual_qty": "Actuel : {actual} {unit}", "check_suggestion": "Vérifiez ou pesez la quantité restante" }, "date": { "today": "📅 Aujourd'hui", "yesterday": "📅 Hier" }, "scanner": { "title_barcode": "🔖 Scanner le code-barres", "barcode_hint": "Cadrez le code-barres du produit", "barcode_manual_placeholder": "Ou entrez manuellement...", "barcode_use_btn": "✅ Utiliser ce code", "ai_identifying": "🤖 Identification du produit...", "ai_analyzing": "🤖 Analyse IA en cours...", "product_label_hint": "Cadrez l'étiquette du produit", "expiry_label_hint": "Cadrez la date de péremption imprimée sur le produit", "capture_btn": "📸 Capturer", "capture_photo_btn": "📸 Prendre une photo", "retake_btn": "🔄 Reprendre", "camera_error_hint": "Assurez-vous d'utiliser HTTPS et d'avoir accordé les permissions caméra.
Vous pouvez entrer le code-barres manuellement ou utiliser l'identification IA.", "no_barcode": "Pas de code-barres", "save_new_btn": "🆕 Aucun de ceux-ci — enregistrer comme nouveau" }, "lowstock": { "title": "⚠️ Stock faible !", "message": "{name} est presque épuisé — il ne reste que {qty}.", "question": "Voulez-vous l'ajouter à la liste de courses ?", "yes": "🛒 Oui, ajouter à Bring !", "no": "Non, pour l'instant ça va" }, "move": { "title": "📦 Déplacer le reste ?", "question": "Voulez-vous déplacer {thing} de {name} vers un autre emplacement ?", "question_short": "Voulez-vous déplacer {thing} vers un autre emplacement ?", "thing_opened": "l'emballage ouvert", "thing_rest": "le reste", "stay_btn": "Non, rester dans {location}", "moved_toast": "📦 Emballage ouvert déplacé vers {location}", "vacuum_restore": "🫙 Restaurer sous vide", "vacuum_seal_rest": "🔒 Mettre le reste sous vide" }, "nova": { "1": "Non transformé", "2": "Ingrédient culinaire", "3": "Transformé", "4": "Ultra-transformé" }, "meal_plan_types": { "pasta": "Pâtes", "riso": "Riz", "carne": "Viande", "pesce": "Poisson", "legumi": "Légumineuses", "uova": "Œufs", "formaggio": "Fromage", "pizza": "Pizza", "affettati": "Charcuterie", "verdure": "Légumes", "zuppa": "Soupe", "insalata": "Salade", "pane": "Pain/Sandwich", "dolce": "Dessert", "libero": "Libre" }, "meal_sub": { "dolce_torta": "Gâteau", "dolce_crema": "Crème / Pudding", "dolce_crumble": "Crumble / Tarte", "dolce_biscotti": "Biscuits / Pâtisseries", "dolce_frutta": "Dessert aux fruits", "succo_dolce": "Sucré / Fruité", "succo_energizzante": "Énergisant", "succo_detox": "Détox / Vert", "succo_rinfrescante": "Rafraîchissant", "succo_vitaminico": "Vitaminé / Agrumes" }, "meal_plan": { "reset_success": "Plan hebdomadaire réinitialisé", "not_available": "non disponible dans le garde-manger", "suggested_by": "suggéré par le plan hebdomadaire" }, "nutrition": { "title": "🥗 Analyse alimentaire", "score_excellent": "😄 Excellent", "score_good": "🙂 Bien", "score_improve": "😬 Améliorable", "label_health": "🌿 Santé", "label_variety": "🎨 Variété", "label_fresh": "❄️ Frais", "source": "Basé sur {n} produits dans votre garde-manger · EverShelf", "products_count": "produits", "today_title": "🥗 Votre garde-manger aujourd'hui", "products_n": "{n} produits" }, "facts": { "greeting_morning": "Bonjour", "greeting_afternoon": "Bon après-midi", "greeting_evening": "Bonsoir", "pantry_waiting": "{greeting} ! Votre garde-manger vous attend.", "expired_one": "Vous avez 1 produit périmé dans votre garde-manger. Vérifiez-le !", "expired_many": "Vous avez {n} produits périmés dans votre garde-manger. Vérifiez-les !", "expired_list": "Produits périmés : {names}", "expired_list_more": "et {n} autres", "freezer_expired_ok": "{name} est périmé, mais étant au congélateur il peut encore être bon ! Vérifiez.", "freezer_expired_old": "{name} au congélateur est périmé depuis trop longtemps. Mieux vaut le jeter.", "fridge_expired_one": "Vous avez 1 produit périmé dans le réfrigérateur !", "fridge_expired_many": "Vous avez {n} produits périmés dans le réfrigérateur !", "expiring_today": "{name} expire aujourd'hui ! Utilisez-le immédiatement.", "expiring_tomorrow": "{name} expire demain. Planifiez !", "expiring_days": "{name} expire dans {days} jours.", "expiring_many": "Vous avez {n} produits qui expirent bientôt.", "expiring_this_week": "{n} produits expirent cette semaine. Planifiez vos repas en conséquence !", "expiring_item_loc": "{name} ({loc}) expire dans {days} {dayslabel}.", "expiring_this_month": "{n} produits expireront ce mois-ci.", "shopping_add": "Ajouter à la liste : {names} 🛒", "shopping_more": "et {n} autres", "shopping_empty": "Liste de courses vide. Tout est en stock ! ✅", "in_fridge": "Dans le réfrigérateur : {name}.", "in_freezer": "Dans le congélateur : {name}. N'oubliez pas !", "top_category": "Catégorie principale : {icon} {cat} avec {n} produits.", "cat_meat": "Vous avez {n} produits carnés. 🥩", "cat_dairy": "Vous avez {n} produits laitiers chez vous. 🥛", "cat_veggies": "Vous avez {n} types de légumes. Super pour la santé ! 🥬", "cat_fruit": "Vous avez {n} types de fruits. 🍎", "cat_drinks": "Vous avez {n} boissons disponibles. 🥤", "cat_frozen": "Vous avez {n} articles surgelés. ❄️", "cat_pasta": "Vous avez {n} types de pâtes. 🍝 Et si on faisait une carbonara ?", "cat_canned": "Vous avez {n} conserves dans le garde-manger. 🥫", "cat_snacks": "Vous avez {n} snacks. Résistez à la tentation ! 🍪", "cat_condiments": "Vous avez {n} condiments disponibles. 🧂", "item_random": "Le saviez-vous ? Vous avez {name} dans {loc}.", "item_qty": "{name} : vous en avez {qty}.", "no_expiry_count": "{n} produits n'ont pas de date de péremption.", "furthest_expiry": "Le produit avec la date de péremption la plus lointaine est {name} : {months} mois.", "high_qty": "Vous avez un beau stock de {name} : {qty} !", "low_qty_item": "{name} est presque épuisé. L'ajouter à votre liste de courses ?", "low_qty_count": "{n} produits sont presque épuisés.", "morning_bread": "Bonjour ! Vous avez du pain pour le petit-déjeuner. 🍞", "morning_milk": "Y a-t-il du lait dans le réfrigérateur pour un cappuccino ? ☕🥛", "morning_fruit": "Bonjour ! Des fruits frais sont un excellent début de journée. 🍎", "noon_pasta": "C'est l'heure du déjeuner… Et si on faisait un bon bol de pâtes ? 🍝", "noon_salad": "Une salade fraîche pour le déjeuner ? Vous avez {n} légumes ! 🥗", "evening_meat": "Pour le dîner, vous pourriez utiliser la viande que vous avez. 🥩", "evening_fish": "Et si on mangeait du poisson ce soir ? 🐟", "evening_expiring": "Vous avez {n} produits qui expirent cette semaine — utilisez-les ce soir !", "night_reminder": "Bonne nuit ! N'oubliez pas d'utiliser demain : {names}.", "weekly_balance": "Bilan hebdomadaire : +{in} ajoutés, −{out} consommés.", "weekly_added": "Vous avez ajouté {n} produits cette semaine.", "weekly_consumed": "Vous avez consommé {n} produits cette semaine. Bravo !", "tip_freezer": "💡 Les produits surgelés durent bien plus longtemps que la date de péremption.", "tip_bread": "💡 Le pain congelé garde sa fraîcheur pendant des semaines.", "tip_fifo": "💡 Pour éviter le gaspillage, utilisez en premier les produits les plus proches de la péremption (FIFO).", "tip_meat": "💡 La viande au congélateur peut se conserver jusqu'à 6 mois en toute sécurité.", "tip_no_refreeze": "💡 Ne jamais recongeler un produit décongelé. Cuisinez-le immédiatement !", "tip_fridge": "💡 Un réfrigérateur bien rangé vous fait gagner du temps et de l'argent.", "tip_canned": "💡 Les conserves ouvertes doivent aller au réfrigérateur et être consommées en quelques jours.", "top_brand": "La marque la plus courante dans votre garde-manger est {brand} avec {n} produits.", "combo_pasta": "Vous avez des pâtes et des condiments : prêt pour un premier plat ! 🍝", "combo_sandwich": "Pain et viande : un sandwich rapide est toujours une bonne idée ! 🥪", "combo_balanced": "Légumes et viande : vous avez tout pour un repas équilibré ! 🥗🥩", "pantry_empty": "Le garde-manger est vide ! Il est temps de faire les courses. 🛒", "pantry_empty_scan": "Aucun produit enregistré. Scannez quelque chose pour commencer !", "location_distribution": "Distribution : {parts}", "day": "jour", "days": "jours" }, "kiosk_session": { "first_item": "Premier article : {name} !", "items_two_four": "{n} articles — on démarre 🚀", "items_five_nine": "{n} articles — bon rythme ! 💪", "items_ten_twenty": "{n} articles — presque un record 🏆", "items_twenty_plus": "{n} articles — courses épiques ! 🛒🔥", "duplicates_one": "1 doublon (même article deux fois)", "duplicates_many": "{n} doublons (pris plusieurs fois)", "top_category": "Catégorie principale : {cat} ({count}×)", "items_fallback": "{n} article{plural} ajouté{plural}" }, "kiosk": { "check_btn": "🔍 Vérifier les mises à jour", "checking": "⏳ Vérification…", "error_check": "Erreur lors de la vérification des mises à jour", "error_start_install": "Erreur au démarrage de l'installation", "version_installed": "Installé : {v}", "update_available": "⬆️ Nouvelle version disponible : {latest} (installée : {current})", "up_to_date": "✅ Vous êtes à jour — version {v}", "too_old": "⚠️ Le kiosque installé est trop ancien pour la vérification automatique des mises à jour.
Appuyez sur le bouton ci-dessous pour télécharger et installer la nouvelle version directement.", "manual_install": "⚠️ Ce kiosque ne supporte pas l'installation automatique.
Procédure manuelle :
1. Quittez le kiosque (bouton ✕ en haut à gauche)
2. Désinstallez l'application EverShelf Kiosk
3. Téléchargez et installez le nouvel APK depuis GitHub :", "starting_download": "⏳ Démarrage du téléchargement…", "install_btn": "⬇️ Installer la mise à jour", "exit_title": "Quitter le kiosque", "refresh_title": "Actualiser la page" }, "update": { "new_version": "Nouvelle version", "btn": "Mettre à jour" }, "gemini": { "chat_title": "Discussion avec Gemini", "not_configured": "🤖 Gemini non configuré — définissez GEMINI_API_KEY dans les paramètres" }, "appliances": { "empty": "Aucun appareil ajouté" }, "about": { "title": "À propos", "version": "Version", "report_bug": "Signaler un bug", "report_bug_hint": "Quelque chose ne fonctionne pas ? Envoyez-nous un rapport directement depuis l'application.", "report_bug_modal_title": "Signaler un bug", "report_type_bug": "Bug", "report_type_feature": "Fonctionnalité", "report_type_question": "Question", "report_field_title": "Titre", "report_field_title_ph": "Brève description du problème", "report_field_desc": "Description", "report_field_desc_ph": "Décrivez le problème en détail…", "report_field_steps": "Étapes pour reproduire (optionnel)", "report_field_steps_ph": "1. Aller à…\n2. Appuyer sur…\n3. Voir l'erreur…", "report_auto_info": "Joint automatiquement : version {version}, langue {lang}.", "report_send_btn": "Envoyer le rapport", "report_bug_sending": "Envoi…", "report_bug_sent": "Rapport envoyé — merci !", "report_bug_error": "Impossible d'envoyer le rapport. Vérifiez votre connexion.", "changelog": "Journal des modifications", "github": "Dépôt GitHub" }, "export": { "title": "Exporter l'inventaire", "hint": "Téléchargez l'inventaire actuel en CSV ou ouvrez la version imprimable (PDF).", "btn_csv": "Télécharger CSV", "btn_pdf": "PDF / Imprimer", "btn_title": "Exporter" } }