- Add product search screen (/products/search) as primary add flow; "Add" button on products list opens search, manual entry remains as fallback - Add to shelf bottom sheet with AnimatedSwitcher success view (green checkmark) and SnackBar confirmation on the search screen via onAdded callback - Manual add (AddProductScreen) shows SnackBar on success before popping back - Extend AddProductScreen with optional nutrition fields (calories, protein, fat, carbs, fiber); auto-fills from catalog selection and auto-expands section - Auto-upsert catalog product on backend when nutrition data is provided without a primary_product_id, linking the user product to the catalog - Add fiber_per_100g field to CatalogProduct model and CreateRequest - Add 16 new L10n keys across all 12 locales (addProduct, addManually, searchProducts, quantity, storageDays, addToShelf, nutritionOptional, calories, protein, fat, carbs, fiber, productAddedToShelf, etc.) Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
204 lines
6.6 KiB
Plaintext
204 lines
6.6 KiB
Plaintext
{
|
|
"@@locale": "en",
|
|
"appTitle": "FoodAI",
|
|
"greetingMorning": "Good morning",
|
|
"greetingAfternoon": "Good afternoon",
|
|
"greetingEvening": "Good evening",
|
|
"caloriesUnit": "kcal",
|
|
"gramsUnit": "g",
|
|
"goalLabel": "goal:",
|
|
"consumed": "Consumed",
|
|
"remaining": "Remaining",
|
|
"exceeded": "Exceeded",
|
|
"proteinLabel": "Protein",
|
|
"fatLabel": "Fat",
|
|
"carbsLabel": "Carbs",
|
|
"today": "Today",
|
|
"yesterday": "Yesterday",
|
|
"mealsSection": "Meals",
|
|
"addDish": "Add dish",
|
|
"scanDish": "Scan",
|
|
"menu": "Menu",
|
|
"dishHistory": "Dish history",
|
|
"recommendCook": "We recommend cooking",
|
|
"camera": "Camera",
|
|
"gallery": "Gallery",
|
|
"analyzingPhoto": "Analyzing photo...",
|
|
"inQueue": "You are in queue",
|
|
"queuePosition": "Position {position}",
|
|
"@queuePosition": {
|
|
"placeholders": {
|
|
"position": {
|
|
"type": "int"
|
|
}
|
|
}
|
|
},
|
|
"processing": "Processing...",
|
|
"upgradePrompt": "Skip the queue? Upgrade →",
|
|
"recognitionFailed": "Recognition failed. Try again.",
|
|
"dishRecognition": "Dish recognition",
|
|
"all": "All",
|
|
"dishRecognized": "Dish recognized",
|
|
"recognizing": "Recognizing…",
|
|
"recognitionError": "Recognition error",
|
|
"dishResultTitle": "Dish recognized",
|
|
"selectDish": "Select dish",
|
|
"dishNotRecognized": "Dish not recognized",
|
|
"tryAgain": "Try again",
|
|
"nutritionApproximate": "Nutrition is approximate — estimated from photo.",
|
|
"portion": "Portion",
|
|
"mealType": "Meal type",
|
|
"dateLabel": "Date",
|
|
"addToJournal": "Add to journal",
|
|
"addFailed": "Failed to add. Try again.",
|
|
"historyTitle": "Recognition history",
|
|
"historyLoadError": "Failed to load history",
|
|
"retry": "Retry",
|
|
"noHistory": "No recognitions yet",
|
|
"profileTitle": "Profile",
|
|
"edit": "Edit",
|
|
"bodyParams": "BODY PARAMS",
|
|
"goalActivity": "GOAL & ACTIVITY",
|
|
"nutrition": "NUTRITION",
|
|
"settings": "SETTINGS",
|
|
"height": "Height",
|
|
"weight": "Weight",
|
|
"age": "Age",
|
|
"gender": "Gender",
|
|
"genderMale": "Male",
|
|
"genderFemale": "Female",
|
|
"goalLoss": "Weight loss",
|
|
"goalMaintain": "Maintenance",
|
|
"goalGain": "Muscle gain",
|
|
"activityLow": "Low",
|
|
"activityMedium": "Medium",
|
|
"activityHigh": "High",
|
|
"calorieGoal": "Calorie goal",
|
|
"mealTypes": "Meal types",
|
|
"formulaNote": "Calculated using the Mifflin-St Jeor formula",
|
|
"language": "Language",
|
|
"notSet": "Not set",
|
|
"calorieHint": "Enter body params to calculate calorie goal",
|
|
"logout": "Log out",
|
|
"editProfile": "Edit profile",
|
|
"cancel": "Cancel",
|
|
"save": "Save",
|
|
"nameLabel": "Name",
|
|
"heightCm": "Height (cm)",
|
|
"weightKg": "Weight (kg)",
|
|
"birthDate": "Date of birth",
|
|
"nameRequired": "Enter name",
|
|
"profileUpdated": "Profile updated",
|
|
"profileSaveFailed": "Failed to save",
|
|
"mealTypeBreakfast": "Breakfast",
|
|
"mealTypeSecondBreakfast": "Second breakfast",
|
|
"mealTypeLunch": "Lunch",
|
|
"mealTypeAfternoonSnack": "Afternoon snack",
|
|
"mealTypeDinner": "Dinner",
|
|
"mealTypeSnack": "Snack",
|
|
"navHome": "Home",
|
|
"navProducts": "Products",
|
|
"navRecipes": "Recipes",
|
|
"addFromReceiptOrPhoto": "Add from receipt or photo",
|
|
"chooseMethod": "Choose method",
|
|
"photoReceipt": "Photo of receipt",
|
|
"photoReceiptSubtitle": "Recognize all items from a receipt",
|
|
"photoProducts": "Photo of products",
|
|
"photoProductsSubtitle": "Fridge, table, shelf — up to 3 photos",
|
|
"addPackagedFood": "Add packaged food",
|
|
"scanBarcode": "Scan barcode",
|
|
"portionWeightG": "Portion weight (g)",
|
|
"productNotFound": "Product not found",
|
|
"enterManually": "Enter manually",
|
|
"perHundredG": "per 100 g",
|
|
"searchFoodHint": "Search products and dishes...",
|
|
"recentlyUsedLabel": "Recently used",
|
|
"productsSection": "Products",
|
|
"dishesSection": "Dishes",
|
|
"noResultsForQuery": "Nothing found for \"{query}\"",
|
|
"@noResultsForQuery": {
|
|
"placeholders": {
|
|
"query": {
|
|
"type": "String"
|
|
}
|
|
}
|
|
},
|
|
"servingsLabel": "Servings",
|
|
"addToDiary": "Add to diary",
|
|
"scanDishPhoto": "Scan photo",
|
|
"planningForDate": "Planning for {date}",
|
|
"@planningForDate": {
|
|
"placeholders": {
|
|
"date": {
|
|
"type": "String"
|
|
}
|
|
}
|
|
},
|
|
"markAsEaten": "Mark as eaten",
|
|
"plannedMealLabel": "Planned",
|
|
"generateWeekLabel": "Plan the week",
|
|
"generateWeekSubtitle": "AI will create a menu with breakfast, lunch and dinner for the whole week",
|
|
"generatingMenu": "Generating menu...",
|
|
"dayPlannedLabel": "Day planned",
|
|
"planMenuButton": "Plan meals",
|
|
"planMenuTitle": "What to plan?",
|
|
"planOptionSingleMeal": "Single meal",
|
|
"planOptionSingleMealDesc": "Choose a day and meal type",
|
|
"planOptionDay": "One day",
|
|
"planOptionDayDesc": "All meals for one day",
|
|
"planOptionDays": "Several days",
|
|
"planOptionDaysDesc": "Custom date range",
|
|
"planOptionWeek": "A week",
|
|
"planOptionWeekDesc": "7 days at once",
|
|
"planSelectDate": "Select date",
|
|
"planSelectMealType": "Meal type",
|
|
"planSelectRange": "Select period",
|
|
"planGenerateButton": "Plan",
|
|
"planGenerating": "Generating plan…",
|
|
"planSuccess": "Menu planned!",
|
|
"planProductsTitle": "Products for the menu",
|
|
"planProductsSubtitle": "AI will take the selected products into account when generating recipes",
|
|
"planProductsEmpty": "No products added",
|
|
"planProductsEmptyMessage": "Add products you have at home — AI will suggest recipes from what you already have",
|
|
"planProductsAddProducts": "Add products",
|
|
"planProductsContinue": "Continue",
|
|
"planProductsSkip": "Skip product selection",
|
|
"planProductsSkipNoProducts": "Plan without products",
|
|
"planProductsSelectAll": "Select all",
|
|
"planProductsDeselectAll": "Deselect all",
|
|
"recentScans": "Recent scans",
|
|
"seeAllScans": "See all",
|
|
"productJobHistoryTitle": "Scan history",
|
|
"jobTypeReceipt": "Receipt",
|
|
"jobTypeProducts": "Products",
|
|
"scanSubmitting": "Submitting...",
|
|
"processingProducts": "Processing...",
|
|
"clearAllProducts": "Clear all",
|
|
"clearAllConfirmTitle": "Clear all products?",
|
|
"clearAllConfirmMessage": "All products will be permanently deleted.",
|
|
"addManually": "Manually",
|
|
"scan": "Scan",
|
|
"addProduct": "Add",
|
|
"searchProducts": "Search products",
|
|
"searchProductsHint": "Type a product name to search or add manually",
|
|
"noSearchResults": "No results for \"{query}\"",
|
|
"@noSearchResults": {
|
|
"placeholders": {
|
|
"query": {
|
|
"type": "String"
|
|
}
|
|
}
|
|
},
|
|
"quantity": "Quantity",
|
|
"storageDays": "Storage days",
|
|
"addToShelf": "Add to pantry",
|
|
"errorGeneric": "Something went wrong",
|
|
"nutritionOptional": "Nutrition per 100g (optional)",
|
|
"calories": "Calories",
|
|
"protein": "Protein",
|
|
"fat": "Fat",
|
|
"carbs": "Carbohydrates",
|
|
"fiber": "Fiber",
|
|
"productAddedToShelf": "Added to pantry"
|
|
}
|