import { createContext, useCallback, useContext, useMemo, useState, type ReactNode, } from 'react'; type Language = 'en' | 'th' | 'ja'; type Params = Record; const strings: Record> = { en: { 'common.close': 'Close', 'tabs.home': 'Home', 'tabs.explore': 'Explore', 'tabs.onnx': 'Leaf Scan', 'tabs.setup': 'Setup', 'tabs.blog': 'Blog', 'tabs.tasks': 'Tasks', 'tabs.fields': 'Fields', 'tabs.logbook': 'Logbook', 'tabs.taskHistory': 'History', 'setup.title': 'User Setup', 'setup.profile': 'Profile', 'setup.loading': 'Loading...', 'setup.loaded': 'Loaded saved profile.', 'setup.none': 'No profile yet. Fill the form and save.', 'setup.saving': 'Saving...', 'setup.saved': 'Saved locally.', 'setup.photo': 'Profile photo', 'setup.noPhoto': 'No photo selected.', 'setup.uploadPhoto': 'Upload photo', 'setup.exportTitle': 'Export data', 'setup.exportHint': 'Download your local data as a JSON file.', 'setup.exportButton': 'Export data', 'setup.exported': 'Exported data.', 'setup.exportError': 'Export failed.', 'setup.name': 'Name', 'setup.farmName': 'Farm name', 'setup.location': 'Location', 'setup.save': 'Save locally', 'setup.saveIndicator': 'Saved!', 'setup.language': 'Language', 'setup.lang.en': 'English', 'setup.lang.th': 'Thai', 'setup.lang.ja': 'Japanese', 'setup.currency': 'Default currency', 'setup.currencyPlaceholder': 'e.g. THB', 'setup.currency.thb': 'THB', 'setup.currency.usd': 'USD', 'setup.currency.eur': 'EUR', 'setup.currency.jpy': 'JPY', 'setup.demoTitle': 'Demo Data', 'setup.demoHint': 'Insert sample fields, crops, observations, and task history.', 'setup.demoButton': 'Insert demo data', 'setup.demoInserting': 'Inserting demo data...', 'setup.demoInserted': 'Demo data inserted.', 'setup.demoExists': 'Demo data already exists.', 'setup.demoError': 'Demo insert failed.', 'setup.demoClearButton': 'Clear demo data', 'setup.demoClearing': 'Clearing demo data...', 'setup.demoCleared': 'Demo data cleared.', 'setup.demoClearError': 'Clear demo failed.', 'setup.demoClearedUndo': 'Demo data cleared.', 'setup.demoUndo': 'Undo', 'setup.demoUndoDone': 'Demo data restored.', 'setup.demoUndoError': 'Undo failed.', 'onnx.title': 'Leaf Classifier', 'onnx.howTitle': 'How to use the ONNX model', 'onnx.howBody': 'This page loads the PlantVillage MobileNetV3-Small model and runs inference on a 224x224 RGB tensor. The input is normalized to 0..1 per channel.', 'onnx.sampleTitle': 'Sample code', 'onnx.testTitle': 'Test the model', 'onnx.pickImage': 'Pick image', 'onnx.runModel': 'Run model', 'onnx.status.pick': 'Pick an image to run the model.', 'onnx.status.ready': 'Ready. Tap "Run model" to classify.', 'onnx.status.preprocessing': 'Preprocessing image...', 'onnx.status.running': 'Running PlantVillage model...', 'onnx.status.done': 'Done.', 'onnx.status.nativeMissing': 'ONNX runtime not available. Use a dev build.', 'onnx.topPredictions': 'Top predictions', 'blog.title': 'Blog Posts', 'blog.loading': 'Loading posts...', 'blog.error': 'Failed to load posts.', 'blog.empty': 'No posts found.', 'blog.loadMore': 'Load more', 'blog.loadingMore': 'Loading more...', 'blog.language': 'Language', 'blog.lang.en': 'English', 'blog.lang.th': 'Thai', 'blog.lang.ja': 'Japanese', 'blog.lang.zh': 'Chinese', 'home.badge': 'Smartfarming Lite', 'home.title': 'Track fields, crops, and observations without leaving the farm.', 'home.subtitle': 'Offline-first records for daily work, photos, and crop history.', 'home.openLogbook': 'Open Logbook', 'home.todayTasks': "Today’s Tasks", 'home.quickActions': 'Quick Actions', 'home.fields': 'Fields', 'home.fieldsHint': 'Add area, notes, photos.', 'home.crops': 'Crops', 'home.cropsHint': 'Planting and harvest dates.', 'home.observations': 'Observations', 'home.observationsHint': 'Notes, severity, images.', 'home.onnx': 'Leaf Scan', 'home.onnxHint': 'Run leaf classifier.', 'home.harvests': 'Harvests', 'home.harvestsHint': 'Yield and harvest records.', 'home.sales': 'Sales', 'home.salesHint': 'Sales records and buyers.', 'home.costs': 'Costs', 'home.costsHint': 'Record expenses.', 'home.todayTitle': 'Today', 'home.todayCardTitle': 'Log your field routine', 'home.todayCardBody': 'Capture scouting notes, attach photos, and keep a clean history for the next visit.', 'home.openTasks': 'Open Tasks', 'home.taskHistory': 'Task History', 'home.learnAnalyze': 'Learn & Analyze', 'home.blogs': 'Blogs', 'home.blogsHint': 'Latest smart farming posts.', 'home.profile': 'Profile', 'home.profileHint': 'Farm info and language.', 'home.count.tasks': 'Tasks', 'home.count.history': 'History', 'tasks.title': 'Daily Tasks', 'tasks.subtitle': 'Log today’s field routine.', 'tasks.loading': 'Loading tasks...', 'tasks.saving': 'Saving...', 'tasks.saved': 'Saved.', 'tasks.empty': 'No tasks configured yet.', 'tasks.pending': 'Pending', 'tasks.done': 'Done', 'tasks.complete': 'Mark done', 'tasks.save': 'Save', 'tasks.open': 'In progress', 'tasks.undo': 'Undo', 'tasks.notePlaceholder': 'Add notes for today...', 'tasks.photo': 'Task photo', 'tasks.addMedia': 'Add media', 'tasks.pickFromGallery': 'Pick from gallery', 'tasks.takeMedia': 'Take photo / video', 'tasks.pickPhoto': 'Pick photo', 'tasks.takePhoto': 'Take photo', 'tasks.cameraDenied': 'Camera permission denied.', 'tasks.cameraError': 'Camera is not available.', 'tasks.historyTitle': 'Task History', 'tasks.historyEmpty': 'No task history yet.', 'tasks.back': 'Back to Tasks', 'tasks.default.fieldCheck': 'Field check-in', 'tasks.default.fieldCheckDesc': 'Quick field condition and notes.', 'tasks.default.scouting': 'Pest/Disease scouting', 'tasks.default.scoutingDesc': 'Inspect leaves and record severity.', 'tasks.default.sensors': 'Sensor readings', 'tasks.default.sensorsDesc': 'Log soil moisture or weather snapshot.', 'fields.title': 'Fields', 'fields.loading': 'Loading fields...', 'fields.empty': 'No fields yet.', 'fields.nameRequired': 'Field name is required.', 'fields.areaInvalid': 'Area must be a number.', 'fields.saved': 'Saved.', 'fields.saving': 'Saving...', 'fields.name': 'Field name', 'fields.area': 'Area (ha)', 'fields.areaPlaceholder': 'e.g. 1.5', 'fields.notes': 'Notes', 'fields.notesPlaceholder': 'Soil, irrigation, landmarks...', 'fields.save': 'Save field', 'fields.update': 'Update field', 'fields.cancel': 'Cancel', 'fields.edit': 'Edit', 'fields.delete': 'Delete', 'fields.deleteTitle': 'Delete field?', 'fields.deleteMessage': 'This action cannot be undone.', 'fields.new': 'New field', 'fields.unnamed': 'Unnamed field', 'fields.areaLabel': 'Area:', 'fields.photo': 'Field photo', 'fields.addMedia': 'Add media', 'fields.pickFromGallery': 'Pick from gallery', 'fields.takeMedia': 'Take photo / video', 'fields.videoSelected': 'Video selected.', 'fields.pickPhoto': 'Pick photo', 'fields.takePhoto': 'Take photo', 'fields.noPhoto': 'No photo selected.', 'fields.updatedAt': 'Updated:', 'logbook.title': 'Logbook', 'logbook.subtitle': 'Manage your core records.', 'logbook.fields': 'Fields', 'logbook.fieldsHint': 'Land area, notes, boundaries.', 'logbook.observations': 'Observations', 'logbook.observationsHint': 'Scouting notes and severity.', 'logbook.crops': 'Crops', 'logbook.cropsHint': 'Crop info by field.', 'logbook.tasks': 'Daily Tasks', 'logbook.tasksHint': 'Notes, photos, status.', 'logbook.history': 'Task History', 'logbook.historyHint': 'Completed entries by date.', 'logbook.harvests': 'Harvests', 'logbook.harvestsHint': 'Yield and harvest details.', 'logbook.sales': 'Sales', 'logbook.salesHint': 'Sales records and buyers.', 'logbook.costs': 'Costs', 'logbook.costsHint': 'Expenses and receipts.', 'observations.title': 'Observations', 'observations.loading': 'Loading observations...', 'observations.empty': 'No observations yet.', 'observations.saved': 'Saved.', 'observations.saving': 'Saving...', 'observations.field': 'Field', 'observations.crop': 'Crop', 'observations.type': 'Type', 'observations.note': 'Note', 'observations.severity': 'Severity', 'observations.severityLabel': 'Severity:', 'observations.selectField': 'Select field', 'observations.selectCrop': 'Select crop', 'observations.typePlaceholder': 'e.g. scouting', 'observations.notePlaceholder': 'What did you observe?', 'observations.severityPlaceholder': '0-10', 'observations.fieldRequired': 'Field is required.', 'observations.severityInvalid': 'Severity must be a number.', 'observations.delete': 'Delete', 'observations.noField': 'No field', 'observations.noCrop': 'No crop', 'observations.untitled': 'Observation', 'observations.save': 'Save observation', 'observations.new': 'New observation', 'observations.cancel': 'Cancel', 'observations.edit': 'Edit observation', 'observations.update': 'Update observation', 'observations.photo': 'Observation photo', 'observations.addMedia': 'Add media', 'observations.pickFromGallery': 'Pick from gallery', 'observations.takeMedia': 'Take photo / video', 'observations.pickPhoto': 'Pick photo', 'observations.takePhoto': 'Take photo', 'observations.noPhoto': 'No photo selected.', 'harvests.title': 'Harvest Records', 'harvests.loading': 'Loading harvest records...', 'harvests.empty': 'No harvest records yet.', 'harvests.saved': 'Saved.', 'harvests.saving': 'Saving...', 'harvests.new': 'New harvest', 'harvests.field': 'Field', 'harvests.crop': 'Crop', 'harvests.selectField': 'Select field', 'harvests.selectCrop': 'Select crop', 'harvests.date': 'Harvest date', 'harvests.datePlaceholder': 'YYYY-MM-DD', 'harvests.quantity': 'Quantity', 'harvests.quantityPlaceholder': 'e.g. 120', 'harvests.unit': 'Unit', 'harvests.unitPlaceholder': 'kg', 'harvests.notes': 'Notes', 'harvests.notesPlaceholder': 'Quality, weather, labor notes...', 'harvests.photo': 'Harvest photo', 'harvests.addMedia': 'Add media', 'harvests.pickFromGallery': 'Pick from gallery', 'harvests.takeMedia': 'Take photo / video', 'harvests.pickPhoto': 'Pick photo', 'harvests.takePhoto': 'Take photo', 'harvests.noPhoto': 'No photo selected.', 'harvests.fieldRequired': 'Field is required.', 'harvests.cropRequired': 'Crop is required.', 'harvests.quantityInvalid': 'Quantity must be a number.', 'harvests.delete': 'Delete', 'harvests.deleteTitle': 'Delete harvest record?', 'harvests.deleteMessage': 'This action cannot be undone.', 'harvests.cancel': 'Cancel', 'harvests.save': 'Save harvest', 'harvests.untitled': 'Harvest', 'harvests.noField': 'No field', 'harvests.noCrop': 'No crop', 'harvests.edit': 'Edit harvest', 'harvests.update': 'Update harvest', 'units.kg': 'kg', 'units.g': 'g', 'units.ton': 'ton', 'units.pcs': 'pcs', 'sales.title': 'Sales Records', 'sales.loading': 'Loading sales records...', 'sales.empty': 'No sales records yet.', 'sales.saved': 'Saved.', 'sales.saving': 'Saving...', 'sales.new': 'New sale', 'sales.field': 'Field', 'sales.crop': 'Crop', 'sales.harvest': 'Harvest (optional)', 'sales.selectField': 'Select field', 'sales.selectCrop': 'Select crop', 'sales.selectHarvest': 'Select harvest', 'sales.noHarvest': 'No harvest records', 'sales.date': 'Sale date', 'sales.datePlaceholder': 'YYYY-MM-DD', 'sales.quantity': 'Quantity', 'sales.quantityPlaceholder': 'e.g. 50', 'sales.unit': 'Unit', 'sales.unitPlaceholder': 'kg', 'sales.price': 'Price', 'sales.pricePlaceholder': 'e.g. 35', 'sales.priceLabel': 'Price:', 'sales.buyer': 'Buyer', 'sales.buyerPlaceholder': 'e.g. Local market', 'sales.notes': 'Notes', 'sales.notesPlaceholder': 'Payment, transport, quality...', 'sales.fieldRequired': 'Field is required.', 'sales.cropRequired': 'Crop is required.', 'sales.quantityInvalid': 'Quantity must be a number.', 'sales.delete': 'Delete', 'sales.deleteTitle': 'Delete sales record?', 'sales.deleteMessage': 'This action cannot be undone.', 'sales.cancel': 'Cancel', 'sales.pickFromGallery': 'Pick from gallery', 'sales.takeMedia': 'Take photo / video', 'sales.save': 'Save sale', 'sales.untitled': 'Sale', 'sales.noField': 'No field', 'sales.noCrop': 'No crop', 'sales.edit': 'Edit sale', 'sales.update': 'Update sale', 'costs.title': 'Cost Records', 'costs.loading': 'Loading costs...', 'costs.empty': 'No cost records yet.', 'costs.saved': 'Saved.', 'costs.saving': 'Saving...', 'costs.new': 'New cost', 'costs.field': 'Field', 'costs.crop': 'Crop (optional)', 'costs.selectField': 'Select field', 'costs.selectCrop': 'Select crop', 'costs.category': 'Category', 'costs.category.seed': 'Seed', 'costs.category.fertilizer': 'Fertilizer', 'costs.category.labor': 'Labor', 'costs.category.fuel': 'Fuel', 'costs.category.equipment': 'Equipment', 'costs.category.transport': 'Transport', 'costs.category.misc': 'Misc', 'costs.categoryPlaceholder': 'e.g. Seed', 'costs.amount': 'Amount', 'costs.amountPlaceholder': 'e.g. 1200', 'costs.vendor': 'Vendor', 'costs.vendorPlaceholder': 'e.g. Local supplier', 'costs.date': 'Date', 'costs.datePlaceholder': 'YYYY-MM-DD', 'costs.notes': 'Notes', 'costs.notesPlaceholder': 'Receipt, usage, purpose...', 'costs.photo': 'Receipt photo', 'costs.addMedia': 'Add media', 'costs.pickFromGallery': 'Pick from gallery', 'costs.takeMedia': 'Take photo / video', 'costs.pickPhoto': 'Pick photo', 'costs.takePhoto': 'Take photo', 'costs.noPhoto': 'No photo selected.', 'costs.fieldRequired': 'Field is required.', 'costs.amountInvalid': 'Amount must be a number.', 'costs.delete': 'Delete', 'costs.deleteTitle': 'Delete cost record?', 'costs.deleteMessage': 'This action cannot be undone.', 'costs.cancel': 'Cancel', 'costs.save': 'Save cost', 'costs.edit': 'Edit cost', 'costs.update': 'Update cost', 'costs.untitled': 'Cost', 'costs.noField': 'No field', 'costs.noCrop': 'No crop', 'demo.field.north': 'North Field', 'demo.field.northNote': 'Loamy soil · drip irrigation', 'demo.field.river': 'River Plot', 'demo.field.riverNote': 'Lowland area near canal', 'demo.field.greenhouse': 'Greenhouse', 'demo.field.greenhouseNote': 'Shaded beds, irrigation daily', 'demo.field.orchard': 'Orchard Block', 'demo.field.orchardNote': 'Raised rows, windbreak on east side', 'demo.field.terrace': 'Terrace Plot', 'demo.field.terraceNote': 'Stepped slope with drip lines', 'demo.crop.tomato': 'Tomato', 'demo.crop.tomatoVariety': 'Cherry', 'demo.crop.rice': 'Rice', 'demo.crop.riceVariety': 'Jasmine', 'demo.crop.lettuce': 'Lettuce', 'demo.crop.lettuceVariety': 'Butterhead', 'demo.crop.chili': 'Chili', 'demo.crop.chiliVariety': 'Bird’s eye', 'demo.crop.cabbage': 'Cabbage', 'demo.crop.cabbageVariety': 'Green cabbage', 'demo.observation.scoutingNote': 'Early leaf spot found on edge rows.', 'demo.observation.diseaseNote': 'Disease patches visible after rain.', 'demo.observation.irrigationNote': 'Adjusted irrigation timing to evening.', 'demo.observation.pestNote': 'Aphids spotted on new growth.', 'demo.observation.nutrientNote': 'Lower leaves pale, applied foliar feed.', 'demo.task.note': 'Completed as scheduled.', 'demo.task.note2': 'Followed standard checklist.', 'demo.task.note3': 'Checked equipment and logged readings.', 'demo.harvest.note1': 'Morning harvest, good quality.', 'demo.harvest.note2': 'Harvested after light rain.', 'demo.harvest.note3': 'Sorted by size for market.', 'demo.sale.buyer1': 'Local market', 'demo.sale.buyer2': 'Wholesale buyer', 'demo.sale.buyer3': 'Restaurant partner', 'demo.sale.note1': 'Delivered same day.', 'demo.sale.note2': 'Paid in full.', 'demo.sale.note3': 'Requested weekly supply.', 'demo.cost.vendor1': 'Agro supply', 'demo.cost.vendor2': 'Fertilizer store', 'demo.cost.vendor3': 'Labor crew', 'demo.cost.note1': 'Tomato seeds and trays.', 'demo.cost.note2': 'Base fertilizer for rice plot.', 'demo.cost.note3': 'Harvest helpers (half day).', 'observations.type.scouting': 'Scouting', 'observations.type.pest': 'Pest', 'observations.type.disease': 'Disease', 'observations.type.irrigation': 'Irrigation', 'observations.type.weeds': 'Weeds', 'observations.type.nutrients': 'Nutrients', 'crops.title': 'Crops', 'crops.loading': 'Loading crops...', 'crops.empty': 'No crops yet.', 'crops.saved': 'Saved.', 'crops.saving': 'Saving...', 'crops.field': 'Field', 'crops.selectField': 'Select field', 'crops.name': 'Crop name', 'crops.variety': 'Variety', 'crops.planting': 'Planting date', 'crops.harvest': 'Expected harvest', 'crops.selectDate': 'Select date', 'crops.namePlaceholder': 'e.g. Tomato', 'crops.varietyPlaceholder': 'e.g. Cherry', 'crops.plantingPlaceholder': 'YYYY-MM-DD', 'crops.harvestPlaceholder': 'YYYY-MM-DD', 'crops.fieldRequired': 'Field is required.', 'crops.nameRequired': 'Crop name is required.', 'crops.delete': 'Delete', 'crops.deleteTitle': 'Delete crop?', 'crops.deleteMessage': 'This action cannot be undone.', 'crops.noField': 'No field', 'crops.untitled': 'Crop', 'crops.plantingLabel': 'Planted:', 'crops.harvestLabel': 'Harvest:', 'crops.save': 'Save crop', 'crops.new': 'New crop', 'crops.photo': 'Crop photo', 'crops.addMedia': 'Add media', 'crops.pickFromGallery': 'Pick from gallery', 'crops.takeMedia': 'Take photo / video', 'crops.pickPhoto': 'Pick photo', 'crops.takePhoto': 'Take photo', 'crops.noPhoto': 'No photo selected.', 'crops.today': 'Today', 'crops.done': 'Done', 'crops.edit': 'Edit crop', 'crops.update': 'Update crop', 'crops.cancel': 'Cancel', }, th: { 'common.close': 'ปิด', 'tabs.home': 'หน้าแรก', 'tabs.explore': 'สำรวจ', 'tabs.onnx': 'สแกนใบ', 'tabs.setup': 'ตั้งค่า', 'tabs.blog': 'บล็อก', 'tabs.tasks': 'งานประจำวัน', 'tabs.fields': 'แปลง', 'tabs.logbook': 'บันทึก', 'tabs.taskHistory': 'ประวัติ', 'setup.title': 'ตั้งค่าผู้ใช้', 'setup.profile': 'โปรไฟล์', 'setup.loading': 'กำลังโหลด...', 'setup.loaded': 'โหลดโปรไฟล์ที่บันทึกไว้แล้ว', 'setup.none': 'ยังไม่มีโปรไฟล์ กรอกข้อมูลแล้วกดบันทึก', 'setup.saving': 'กำลังบันทึก...', 'setup.saved': 'บันทึกไว้ในเครื่องแล้ว', 'setup.photo': 'รูปโปรไฟล์', 'setup.noPhoto': 'ยังไม่ได้เลือกรูป', 'setup.uploadPhoto': 'อัปโหลดรูป', 'setup.exportTitle': 'ส่งออกข้อมูล', 'setup.exportHint': 'ดาวน์โหลดข้อมูลในเครื่องเป็นไฟล์ JSON', 'setup.exportButton': 'ส่งออกข้อมูล', 'setup.exported': 'ส่งออกข้อมูลแล้ว', 'setup.exportError': 'ส่งออกข้อมูลไม่สำเร็จ', 'setup.name': 'ชื่อ', 'setup.farmName': 'ชื่อฟาร์ม', 'setup.location': 'ที่ตั้ง', 'setup.save': 'บันทึกในเครื่อง', 'setup.saveIndicator': 'บันทึกแล้ว', 'setup.language': 'ภาษา', 'setup.lang.en': 'English', 'setup.lang.th': 'ไทย', 'setup.lang.ja': '日本語', 'setup.currency': 'สกุลเงินเริ่มต้น', 'setup.currencyPlaceholder': 'เช่น THB', 'setup.currency.thb': 'บาท (THB)', 'setup.currency.usd': 'ดอลลาร์ (USD)', 'setup.currency.eur': 'ยูโร (EUR)', 'setup.currency.jpy': 'เยน (JPY)', 'setup.demoTitle': 'ข้อมูลตัวอย่าง', 'setup.demoHint': 'เพิ่มข้อมูลตัวอย่าง: แปลง พืช บันทึกสำรวจ และประวัติงาน', 'setup.demoButton': 'เพิ่มข้อมูลตัวอย่าง', 'setup.demoInserting': 'กำลังเพิ่มข้อมูลตัวอย่าง...', 'setup.demoInserted': 'เพิ่มข้อมูลตัวอย่างแล้ว', 'setup.demoExists': 'มีข้อมูลอยู่แล้ว', 'setup.demoError': 'เพิ่มข้อมูลไม่สำเร็จ', 'setup.demoClearButton': 'ลบข้อมูลตัวอย่าง', 'setup.demoClearing': 'กำลังลบข้อมูลตัวอย่าง...', 'setup.demoCleared': 'ลบข้อมูลตัวอย่างแล้ว', 'setup.demoClearError': 'ลบข้อมูลไม่สำเร็จ', 'setup.demoClearedUndo': 'ลบข้อมูลตัวอย่างแล้ว', 'setup.demoUndo': 'ย้อนกลับ', 'setup.demoUndoDone': 'กู้คืนข้อมูลตัวอย่างแล้ว', 'setup.demoUndoError': 'ย้อนกลับไม่สำเร็จ', 'onnx.title': 'จำแนกโรคใบพืช', 'onnx.howTitle': 'วิธีใช้โมเดล ONNX', 'onnx.howBody': 'หน้านี้โหลดโมเดล PlantVillage MobileNetV3-Small และรันอินเฟอเรนซ์ด้วยเทนเซอร์ RGB ขนาด 224x224 อินพุตถูกทำให้อยู่ในช่วง 0..1 ต่อช่องสี', 'onnx.sampleTitle': 'ตัวอย่างโค้ด', 'onnx.testTitle': 'ทดสอบโมเดล', 'onnx.pickImage': 'เลือกรูป', 'onnx.runModel': 'รันโมเดล', 'onnx.status.pick': 'เลือกรูปเพื่อรันโมเดล', 'onnx.status.ready': 'พร้อมแล้ว กด "รันโมเดล" เพื่อจำแนก', 'onnx.status.preprocessing': 'กำลังเตรียมรูป...', 'onnx.status.running': 'กำลังรันโมเดล PlantVillage...', 'onnx.status.done': 'เสร็จแล้ว', 'onnx.status.nativeMissing': 'ไม่พบ ONNX runtime โปรดใช้ dev build', 'onnx.topPredictions': 'ผลลัพธ์สูงสุด', 'blog.title': 'บทความล่าสุด', 'blog.loading': 'กำลังโหลดบทความ...', 'blog.error': 'โหลดบทความไม่สำเร็จ', 'blog.empty': 'ไม่พบบทความ', 'blog.loadMore': 'โหลดเพิ่มเติม', 'blog.loadingMore': 'กำลังโหลดเพิ่มเติม...', 'blog.language': 'ภาษา', 'blog.lang.en': 'English', 'blog.lang.th': 'ไทย', 'blog.lang.ja': 'ญี่ปุ่น', 'blog.lang.zh': 'จีน', 'home.badge': 'สมาร์ทฟาร์มมิ่ง ไลต์', 'home.title': 'ติดตามแปลง พืช และบันทึกสำรวจได้ทันทีในฟาร์ม', 'home.subtitle': 'บันทึกแบบออฟไลน์สำหรับงานประจำวัน รูปภาพ และประวัติพืช', 'home.openLogbook': 'เปิดบันทึก', 'home.todayTasks': 'งานวันนี้', 'home.quickActions': 'ทางลัด', 'home.fields': 'แปลง', 'home.fieldsHint': 'เพิ่มพื้นที่ บันทึก และรูปภาพ', 'home.crops': 'พืช', 'home.cropsHint': 'วันที่ปลูกและเก็บเกี่ยว', 'home.observations': 'บันทึกสำรวจ', 'home.observationsHint': 'บันทึก ความรุนแรง และรูปภาพ', 'home.onnx': 'สแกนใบ', 'home.onnxHint': 'รันโมเดลจำแนกใบพืช', 'home.harvests': 'เก็บเกี่ยว', 'home.harvestsHint': 'ผลผลิตและบันทึกการเก็บเกี่ยว', 'home.sales': 'ขายผลผลิต', 'home.salesHint': 'บันทึกการขายและผู้ซื้อ', 'home.costs': 'ต้นทุน', 'home.costsHint': 'บันทึกค่าใช้จ่าย', 'home.todayTitle': 'วันนี้', 'home.todayCardTitle': 'บันทึกงานประจำแปลง', 'home.todayCardBody': 'บันทึกการสำรวจ ถ่ายรูป และเก็บประวัติให้พร้อมสำหรับครั้งถัดไป', 'home.openTasks': 'เปิดงานประจำวัน', 'home.taskHistory': 'ประวัติงาน', 'home.learnAnalyze': 'เรียนรู้และวิเคราะห์', 'home.blogs': 'บล็อก', 'home.blogsHint': 'บทความสมาร์ทฟาร์มมิ่งล่าสุด', 'home.profile': 'โปรไฟล์', 'home.profileHint': 'ข้อมูลฟาร์มและภาษา', 'home.count.tasks': 'งาน', 'home.count.history': 'ประวัติ', 'tasks.title': 'งานประจำวัน', 'tasks.subtitle': 'บันทึกงานประจำวันของแปลงวันนี้', 'tasks.loading': 'กำลังโหลดงาน...', 'tasks.saving': 'กำลังบันทึก...', 'tasks.saved': 'บันทึกแล้ว', 'tasks.empty': 'ยังไม่มีงานที่ตั้งไว้', 'tasks.pending': 'รอดำเนินการ', 'tasks.done': 'เสร็จแล้ว', 'tasks.complete': 'ทำเสร็จแล้ว', 'tasks.save': 'บันทึก', 'tasks.open': 'กำลังดำเนินการ', 'tasks.undo': 'ย้อนกลับ', 'tasks.notePlaceholder': 'เพิ่มบันทึกสำหรับวันนี้...', 'tasks.photo': 'รูปงาน', 'tasks.addMedia': 'เพิ่มสื่อ', 'tasks.pickFromGallery': 'เลือกรูปจากแกลเลอรี', 'tasks.takeMedia': 'ถ่ายรูป / วิดีโอ', 'tasks.pickPhoto': 'เลือกรูป', 'tasks.takePhoto': 'ถ่ายรูป', 'tasks.cameraDenied': 'ไม่ได้รับอนุญาตให้ใช้กล้อง', 'tasks.cameraError': 'ไม่สามารถใช้งานกล้องได้', 'tasks.historyTitle': 'ประวัติงานประจำวัน', 'tasks.historyEmpty': 'ยังไม่มีประวัติงาน', 'tasks.back': 'กลับไปงานประจำวัน', 'tasks.default.fieldCheck': 'ตรวจแปลง', 'tasks.default.fieldCheckDesc': 'เช็คสภาพแปลงและบันทึกสั้น ๆ', 'tasks.default.scouting': 'สำรวจแมลง/โรค', 'tasks.default.scoutingDesc': 'ตรวจใบและบันทึกความรุนแรง', 'tasks.default.sensors': 'อ่านค่าจากเซนเซอร์', 'tasks.default.sensorsDesc': 'บันทึกความชื้นดินหรือสภาพอากาศ', 'fields.title': 'แปลง', 'fields.loading': 'กำลังโหลดแปลง...', 'fields.empty': 'ยังไม่มีแปลง', 'fields.nameRequired': 'ต้องระบุชื่อแปลง', 'fields.areaInvalid': 'พื้นที่ต้องเป็นตัวเลข', 'fields.saved': 'บันทึกแล้ว', 'fields.saving': 'กำลังบันทึก...', 'fields.name': 'ชื่อแปลง', 'fields.area': 'พื้นที่ (ไร่)', 'fields.areaPlaceholder': 'เช่น 1.5', 'fields.notes': 'บันทึก', 'fields.notesPlaceholder': 'ดิน น้ำ จุดสังเกต...', 'fields.save': 'บันทึกแปลง', 'fields.update': 'อัปเดตแปลง', 'fields.cancel': 'ยกเลิก', 'fields.edit': 'แก้ไข', 'fields.delete': 'ลบ', 'fields.deleteTitle': 'ลบแปลงนี้ไหม?', 'fields.deleteMessage': 'การลบไม่สามารถย้อนกลับได้', 'fields.new': 'เพิ่มแปลง', 'fields.unnamed': 'แปลงไม่มีชื่อ', 'fields.areaLabel': 'พื้นที่:', 'fields.photo': 'รูปแปลง', 'fields.addMedia': 'เพิ่มสื่อ', 'fields.pickFromGallery': 'เลือกรูปจากแกลเลอรี', 'fields.takeMedia': 'ถ่ายรูป / วิดีโอ', 'fields.videoSelected': 'เลือกวิดีโอแล้ว', 'fields.pickPhoto': 'เลือกรูป', 'fields.takePhoto': 'ถ่ายรูป', 'fields.noPhoto': 'ยังไม่ได้เลือกรูป', 'fields.updatedAt': 'อัปเดตเมื่อ:', 'logbook.title': 'บันทึก', 'logbook.subtitle': 'จัดการข้อมูลหลักของคุณ', 'logbook.fields': 'แปลง', 'logbook.fieldsHint': 'พื้นที่ บันทึก ขอบเขต', 'logbook.observations': 'บันทึกสำรวจ', 'logbook.observationsHint': 'บันทึกสำรวจและความรุนแรง', 'logbook.crops': 'พืช', 'logbook.cropsHint': 'ข้อมูลพืชตามแปลง', 'logbook.tasks': 'งานประจำวัน', 'logbook.tasksHint': 'บันทึก รูปภาพ สถานะ', 'logbook.history': 'ประวัติงาน', 'logbook.historyHint': 'รายการที่เสร็จแล้วตามวันที่', 'logbook.harvests': 'เก็บเกี่ยว', 'logbook.harvestsHint': 'ผลผลิตและรายละเอียดการเก็บเกี่ยว', 'logbook.sales': 'ขายผลผลิต', 'logbook.salesHint': 'บันทึกการขายและผู้ซื้อ', 'logbook.costs': 'ต้นทุน', 'logbook.costsHint': 'ค่าใช้จ่ายและใบเสร็จ', 'observations.title': 'บันทึกสำรวจ', 'observations.loading': 'กำลังโหลดบันทึก...', 'observations.empty': 'ยังไม่มีบันทึก', 'observations.saved': 'บันทึกแล้ว', 'observations.saving': 'กำลังบันทึก...', 'observations.field': 'แปลง', 'observations.crop': 'พืช', 'observations.type': 'ประเภท', 'observations.note': 'บันทึก', 'observations.severity': 'ความรุนแรง', 'observations.severityLabel': 'ความรุนแรง:', 'observations.selectField': 'เลือกแปลง', 'observations.selectCrop': 'เลือกพืช', 'observations.typePlaceholder': 'เช่น สำรวจโรค', 'observations.notePlaceholder': 'สังเกตอะไรบ้าง?', 'observations.severityPlaceholder': '0-10', 'observations.fieldRequired': 'ต้องเลือกแปลง', 'observations.severityInvalid': 'ความรุนแรงต้องเป็นตัวเลข', 'observations.delete': 'ลบ', 'observations.noField': 'ไม่มีแปลง', 'observations.noCrop': 'ไม่มีพืช', 'observations.untitled': 'บันทึกสำรวจ', 'observations.save': 'บันทึกข้อมูล', 'observations.new': 'เพิ่มบันทึก', 'observations.cancel': 'ยกเลิก', 'observations.edit': 'แก้ไขบันทึก', 'observations.update': 'อัปเดตบันทึก', 'observations.photo': 'รูปประกอบ', 'observations.addMedia': 'เพิ่มสื่อ', 'observations.pickFromGallery': 'เลือกรูปจากแกลเลอรี', 'observations.takeMedia': 'ถ่ายรูป / วิดีโอ', 'observations.pickPhoto': 'เลือกรูป', 'observations.takePhoto': 'ถ่ายรูป', 'observations.noPhoto': 'ยังไม่ได้เลือกรูป', 'harvests.title': 'บันทึกการเก็บเกี่ยว', 'harvests.loading': 'กำลังโหลดการเก็บเกี่ยว...', 'harvests.empty': 'ยังไม่มีบันทึกการเก็บเกี่ยว', 'harvests.saved': 'บันทึกแล้ว', 'harvests.saving': 'กำลังบันทึก...', 'harvests.new': 'เพิ่มการเก็บเกี่ยว', 'harvests.field': 'แปลง', 'harvests.crop': 'พืช', 'harvests.selectField': 'เลือกแปลง', 'harvests.selectCrop': 'เลือกพืช', 'harvests.date': 'วันที่เก็บเกี่ยว', 'harvests.datePlaceholder': 'YYYY-MM-DD', 'harvests.quantity': 'ปริมาณ', 'harvests.quantityPlaceholder': 'เช่น 120', 'harvests.unit': 'หน่วย', 'harvests.unitPlaceholder': 'กก.', 'harvests.notes': 'บันทึก', 'harvests.notesPlaceholder': 'คุณภาพ สภาพอากาศ แรงงาน...', 'harvests.photo': 'รูปการเก็บเกี่ยว', 'harvests.addMedia': 'เพิ่มสื่อ', 'harvests.pickFromGallery': 'เลือกรูปจากแกลเลอรี', 'harvests.takeMedia': 'ถ่ายรูป / วิดีโอ', 'harvests.pickPhoto': 'เลือกรูป', 'harvests.takePhoto': 'ถ่ายรูป', 'harvests.noPhoto': 'ยังไม่ได้เลือกรูป', 'harvests.fieldRequired': 'ต้องเลือกแปลง', 'harvests.cropRequired': 'ต้องเลือกพืช', 'harvests.quantityInvalid': 'ปริมาณต้องเป็นตัวเลข', 'harvests.delete': 'ลบ', 'harvests.deleteTitle': 'ลบบันทึกการเก็บเกี่ยว?', 'harvests.deleteMessage': 'การลบไม่สามารถย้อนกลับได้', 'harvests.cancel': 'ยกเลิก', 'harvests.save': 'บันทึกการเก็บเกี่ยว', 'harvests.untitled': 'เก็บเกี่ยว', 'harvests.noField': 'ไม่มีแปลง', 'harvests.noCrop': 'ไม่มีพืช', 'harvests.edit': 'แก้ไขการเก็บเกี่ยว', 'harvests.update': 'อัปเดตการเก็บเกี่ยว', 'sales.title': 'บันทึกการขาย', 'sales.loading': 'กำลังโหลดการขาย...', 'sales.empty': 'ยังไม่มีบันทึกการขาย', 'sales.saved': 'บันทึกแล้ว', 'sales.saving': 'กำลังบันทึก...', 'sales.new': 'เพิ่มการขาย', 'sales.field': 'แปลง', 'sales.crop': 'พืช', 'sales.harvest': 'เก็บเกี่ยว (ไม่บังคับ)', 'sales.selectField': 'เลือกแปลง', 'sales.selectCrop': 'เลือกพืช', 'sales.selectHarvest': 'เลือกการเก็บเกี่ยว', 'sales.noHarvest': 'ยังไม่มีการเก็บเกี่ยว', 'sales.date': 'วันที่ขาย', 'sales.datePlaceholder': 'YYYY-MM-DD', 'sales.quantity': 'ปริมาณ', 'sales.quantityPlaceholder': 'เช่น 50', 'sales.unit': 'หน่วย', 'sales.unitPlaceholder': 'กก.', 'sales.price': 'ราคา', 'sales.pricePlaceholder': 'เช่น 35', 'sales.priceLabel': 'ราคา:', 'sales.buyer': 'ผู้ซื้อ', 'sales.buyerPlaceholder': 'เช่น ตลาดท้องถิ่น', 'sales.notes': 'บันทึก', 'sales.notesPlaceholder': 'การชำระเงิน ขนส่ง คุณภาพ...', 'sales.fieldRequired': 'ต้องเลือกแปลง', 'sales.cropRequired': 'ต้องเลือกพืช', 'sales.quantityInvalid': 'ปริมาณต้องเป็นตัวเลข', 'sales.delete': 'ลบ', 'sales.deleteTitle': 'ลบบันทึกการขาย?', 'sales.deleteMessage': 'การลบไม่สามารถย้อนกลับได้', 'sales.cancel': 'ยกเลิก', 'sales.pickFromGallery': 'เลือกรูปจากแกลเลอรี', 'sales.takeMedia': 'ถ่ายรูป / วิดีโอ', 'sales.save': 'บันทึกการขาย', 'sales.untitled': 'การขาย', 'sales.noField': 'ไม่มีแปลง', 'sales.noCrop': 'ไม่มีพืช', 'sales.edit': 'แก้ไขการขาย', 'sales.update': 'อัปเดตการขาย', 'costs.title': 'บันทึกต้นทุน', 'costs.loading': 'กำลังโหลดต้นทุน...', 'costs.empty': 'ยังไม่มีบันทึกต้นทุน', 'costs.saved': 'บันทึกแล้ว', 'costs.saving': 'กำลังบันทึก...', 'costs.new': 'เพิ่มต้นทุน', 'costs.field': 'แปลง', 'costs.crop': 'พืช (ไม่บังคับ)', 'costs.selectField': 'เลือกแปลง', 'costs.selectCrop': 'เลือกพืช', 'costs.category': 'หมวดหมู่', 'costs.category.seed': 'เมล็ดพันธุ์', 'costs.category.fertilizer': 'ปุ๋ย', 'costs.category.labor': 'แรงงาน', 'costs.category.fuel': 'เชื้อเพลิง', 'costs.category.equipment': 'อุปกรณ์', 'costs.category.transport': 'ขนส่ง', 'costs.category.misc': 'อื่น ๆ', 'costs.categoryPlaceholder': 'เช่น เมล็ดพันธุ์', 'costs.amount': 'จำนวนเงิน', 'costs.amountPlaceholder': 'เช่น 1200', 'costs.vendor': 'ผู้ขาย', 'costs.vendorPlaceholder': 'เช่น ร้านวัสดุเกษตร', 'costs.date': 'วันที่', 'costs.datePlaceholder': 'YYYY-MM-DD', 'costs.notes': 'บันทึก', 'costs.notesPlaceholder': 'ใบเสร็จ การใช้งาน วัตถุประสงค์...', 'costs.photo': 'รูปใบเสร็จ', 'costs.addMedia': 'เพิ่มสื่อ', 'costs.pickFromGallery': 'เลือกรูปจากแกลเลอรี', 'costs.takeMedia': 'ถ่ายรูป / วิดีโอ', 'costs.pickPhoto': 'เลือกรูป', 'costs.takePhoto': 'ถ่ายรูป', 'costs.noPhoto': 'ยังไม่ได้เลือกรูป', 'costs.fieldRequired': 'ต้องเลือกแปลง', 'costs.amountInvalid': 'จำนวนเงินต้องเป็นตัวเลข', 'costs.delete': 'ลบ', 'costs.deleteTitle': 'ลบบันทึกต้นทุน?', 'costs.deleteMessage': 'การลบไม่สามารถย้อนกลับได้', 'costs.cancel': 'ยกเลิก', 'costs.save': 'บันทึกต้นทุน', 'costs.edit': 'แก้ไขต้นทุน', 'costs.update': 'อัปเดตต้นทุน', 'costs.untitled': 'ต้นทุน', 'costs.noField': 'ไม่มีแปลง', 'costs.noCrop': 'ไม่มีพืช', 'demo.field.north': 'แปลงเหนือ', 'demo.field.northNote': 'ดินร่วน · น้ำหยด', 'demo.field.river': 'แปลงริมน้ำ', 'demo.field.riverNote': 'พื้นที่ลุ่มใกล้คลอง', 'demo.field.greenhouse': 'โรงเรือน', 'demo.field.greenhouseNote': 'แปลงในร่ม รดน้ำทุกวัน', 'demo.field.orchard': 'แปลงสวนผลไม้', 'demo.field.orchardNote': 'ยกร่องและมีแนวกันลมด้านตะวันออก', 'demo.field.terrace': 'แปลงขั้นบันได', 'demo.field.terraceNote': 'พื้นที่ลาดชันแบ่งขั้น พร้อมน้ำหยด', 'demo.crop.tomato': 'มะเขือเทศ', 'demo.crop.tomatoVariety': 'เชอรี่', 'demo.crop.rice': 'ข้าว', 'demo.crop.riceVariety': 'หอมมะลิ', 'demo.crop.lettuce': 'ผักกาดหอม', 'demo.crop.lettuceVariety': 'บัตเตอร์เฮด', 'demo.crop.chili': 'พริก', 'demo.crop.chiliVariety': 'พริกขี้หนู', 'demo.crop.cabbage': 'กะหล่ำปลี', 'demo.crop.cabbageVariety': 'กะหล่ำปลีเขียว', 'demo.observation.scoutingNote': 'พบบางส่วนใบเป็นจุดเริ่มต้นตามขอบแปลง', 'demo.observation.diseaseNote': 'พบรอยโรคหลังฝนตก', 'demo.observation.irrigationNote': 'ปรับเวลารดน้ำเป็นช่วงเย็น', 'demo.observation.pestNote': 'พบเพลี้ยอ่อนตามยอดอ่อน', 'demo.observation.nutrientNote': 'ใบล่างซีด ให้ปุ๋ยทางใบเพิ่ม', 'demo.task.note': 'ทำงานเสร็จตามแผน', 'demo.task.note2': 'ทำตามเช็กลิสต์มาตรฐาน', 'demo.task.note3': 'ตรวจอุปกรณ์และบันทึกค่าแล้ว', 'demo.harvest.note1': 'เก็บช่วงเช้า คุณภาพดี', 'demo.harvest.note2': 'เก็บหลังฝนตกเล็กน้อย', 'demo.harvest.note3': 'คัดขนาดเพื่อขาย', 'demo.sale.buyer1': 'ตลาดท้องถิ่น', 'demo.sale.buyer2': 'ผู้ซื้อส่ง', 'demo.sale.buyer3': 'คู่ค้าร้านอาหาร', 'demo.sale.note1': 'ส่งของในวันเดียวกัน', 'demo.sale.note2': 'ชำระเงินครบถ้วน', 'demo.sale.note3': 'ขอสั่งประจำทุกสัปดาห์', 'demo.cost.vendor1': 'ร้านวัสดุเกษตร', 'demo.cost.vendor2': 'ร้านปุ๋ย', 'demo.cost.vendor3': 'ทีมแรงงาน', 'demo.cost.note1': 'เมล็ดมะเขือเทศและถาดเพาะ', 'demo.cost.note2': 'ปุ๋ยรองพื้นแปลงข้าว', 'demo.cost.note3': 'แรงงานช่วยเก็บเกี่ยว (ครึ่งวัน)', 'observations.type.scouting': 'สำรวจ', 'observations.type.pest': 'แมลง', 'observations.type.disease': 'โรค', 'observations.type.irrigation': 'ให้น้ำ', 'observations.type.weeds': 'วัชพืช', 'observations.type.nutrients': 'ธาตุอาหาร', 'crops.title': 'พืช', 'crops.loading': 'กำลังโหลดพืช...', 'crops.empty': 'ยังไม่มีพืช', 'crops.saved': 'บันทึกแล้ว', 'crops.saving': 'กำลังบันทึก...', 'crops.field': 'แปลง', 'crops.selectField': 'เลือกแปลง', 'crops.name': 'ชื่อพืช', 'crops.variety': 'สายพันธุ์', 'crops.planting': 'วันที่ปลูก', 'crops.harvest': 'คาดว่าจะเก็บเกี่ยว', 'crops.selectDate': 'เลือกวันที่', 'crops.namePlaceholder': 'เช่น มะเขือเทศ', 'crops.varietyPlaceholder': 'เช่น เชอรี่', 'crops.plantingPlaceholder': 'YYYY-MM-DD', 'crops.harvestPlaceholder': 'YYYY-MM-DD', 'crops.fieldRequired': 'ต้องเลือกแปลง', 'crops.nameRequired': 'ต้องกรอกชื่อพืช', 'crops.delete': 'ลบ', 'crops.deleteTitle': 'ลบพืชนี้ไหม?', 'crops.deleteMessage': 'การลบไม่สามารถย้อนกลับได้', 'crops.noField': 'ไม่มีแปลง', 'crops.untitled': 'พืช', 'crops.plantingLabel': 'ปลูก:', 'crops.harvestLabel': 'เก็บเกี่ยว:', 'crops.save': 'บันทึกพืช', 'crops.new': 'เพิ่มพืช', 'crops.photo': 'รูปพืช', 'crops.addMedia': 'เพิ่มสื่อ', 'crops.pickFromGallery': 'เลือกรูปจากแกลเลอรี', 'crops.takeMedia': 'ถ่ายรูป / วิดีโอ', 'crops.pickPhoto': 'เลือกรูป', 'crops.takePhoto': 'ถ่ายรูป', 'crops.noPhoto': 'ยังไม่ได้เลือกรูป', 'crops.today': 'วันนี้', 'crops.done': 'เสร็จ', 'crops.edit': 'แก้ไขพืช', 'crops.update': 'อัปเดตพืช', 'crops.cancel': 'ยกเลิก', }, ja: { 'common.close': '閉じる', 'tabs.home': 'ホーム', 'tabs.explore': '探索', 'tabs.onnx': '葉スキャン', 'tabs.setup': '設定', 'tabs.blog': 'ブログ', 'tabs.tasks': '日次タスク', 'tabs.fields': '圃場', 'tabs.logbook': 'ログブック', 'tabs.taskHistory': '履歴', 'setup.title': 'ユーザー設定', 'setup.profile': 'プロフィール', 'setup.loading': '読み込み中...', 'setup.loaded': '保存したプロフィールを読み込みました。', 'setup.none': 'プロフィールがまだありません。入力して保存してください。', 'setup.saving': '保存中...', 'setup.saved': 'ローカルに保存しました。', 'setup.photo': 'プロフィール写真', 'setup.noPhoto': '写真が選択されていません。', 'setup.uploadPhoto': '写真をアップロード', 'setup.exportTitle': 'データを書き出し', 'setup.exportHint': 'ローカルデータをJSONとしてダウンロードします。', 'setup.exportButton': 'データを書き出し', 'setup.exported': 'データを書き出しました。', 'setup.exportError': '書き出しに失敗しました。', 'setup.name': '名前', 'setup.farmName': '農場名', 'setup.location': '所在地', 'setup.save': 'ローカルに保存', 'setup.saveIndicator': '保存しました!', 'setup.language': '言語', 'setup.lang.en': 'English', 'setup.lang.th': 'ไทย', 'setup.lang.ja': '日本語', 'setup.currency': '既定の通貨', 'setup.currencyPlaceholder': '例: JPY', 'setup.currency.thb': 'THB', 'setup.currency.usd': 'USD', 'setup.currency.eur': 'EUR', 'setup.currency.jpy': 'JPY', 'setup.demoTitle': 'デモデータ', 'setup.demoHint': 'サンプルの圃場、作物、観察、履歴を挿入します。', 'setup.demoButton': 'デモデータを挿入', 'setup.demoInserting': 'デモデータを挿入中...', 'setup.demoInserted': 'デモデータを挿入しました。', 'setup.demoExists': 'デモデータは既にあります。', 'setup.demoError': 'デモデータの挿入に失敗しました。', 'setup.demoClearButton': 'デモデータを削除', 'setup.demoClearing': 'デモデータを削除中...', 'setup.demoCleared': 'デモデータを削除しました。', 'setup.demoClearError': 'デモデータの削除に失敗しました。', 'setup.demoClearedUndo': 'デモデータを削除しました。', 'setup.demoUndo': '元に戻す', 'setup.demoUndoDone': 'デモデータを復元しました。', 'setup.demoUndoError': '元に戻せませんでした。', 'onnx.title': '葉の分類', 'onnx.howTitle': 'ONNXモデルの使い方', 'onnx.howBody': 'このページはPlantVillage MobileNetV3-Smallモデルを読み込み、224x224のRGBテンソルで推論します。入力は各チャンネル0..1に正規化されます。', 'onnx.sampleTitle': 'サンプルコード', 'onnx.testTitle': 'モデルをテスト', 'onnx.pickImage': '画像を選ぶ', 'onnx.runModel': 'モデルを実行', 'onnx.status.pick': '画像を選択してモデルを実行します。', 'onnx.status.ready': '準備完了。「モデルを実行」をタップしてください。', 'onnx.status.preprocessing': '画像を前処理中...', 'onnx.status.running': 'PlantVillageモデルを実行中...', 'onnx.status.done': '完了。', 'onnx.status.nativeMissing': 'ONNX runtimeが利用できません。dev buildを使用してください。', 'onnx.topPredictions': '上位の予測', 'blog.title': 'ブログ記事', 'blog.loading': '記事を読み込み中...', 'blog.error': '記事の読み込みに失敗しました。', 'blog.empty': '記事がありません。', 'blog.loadMore': 'さらに読み込む', 'blog.loadingMore': 'さらに読み込み中...', 'blog.language': '言語', 'blog.lang.en': 'English', 'blog.lang.th': 'ไทย', 'blog.lang.ja': '日本語', 'blog.lang.zh': '中文', 'home.badge': 'Smartfarming Lite', 'home.title': '圃場・作物・観察を、農場から離れずに記録。', 'home.subtitle': '日々の作業、写真、作物履歴をオフラインで管理。', 'home.openLogbook': 'ログブックを開く', 'home.todayTasks': '今日のタスク', 'home.quickActions': 'クイック操作', 'home.fields': '圃場', 'home.fieldsHint': '面積、メモ、写真を追加。', 'home.crops': '作物', 'home.cropsHint': '定植日と収穫予定。', 'home.observations': '観察', 'home.observationsHint': 'メモ、深刻度、画像。', 'home.onnx': '葉スキャン', 'home.onnxHint': '葉の分類を実行。', 'home.harvests': '収穫', 'home.harvestsHint': '収量と収穫記録。', 'home.sales': '販売', 'home.salesHint': '販売記録と買い手。', 'home.costs': 'コスト', 'home.costsHint': '支出を記録。', 'home.todayTitle': '今日', 'home.todayCardTitle': '圃場作業を記録', 'home.todayCardBody': '観察メモを残し、写真を添付して次回のための履歴を整理。', 'home.openTasks': 'タスクを開く', 'home.taskHistory': 'タスク履歴', 'home.learnAnalyze': '学ぶ・分析する', 'home.blogs': 'ブログ', 'home.blogsHint': 'スマート農業の最新記事。', 'home.profile': 'プロフィール', 'home.profileHint': '農場情報と言語設定。', 'home.count.tasks': 'タスク', 'home.count.history': '履歴', 'tasks.title': '日次タスク', 'tasks.subtitle': '今日の圃場作業を記録。', 'tasks.loading': 'タスクを読み込み中...', 'tasks.saving': '保存中...', 'tasks.saved': '保存しました。', 'tasks.empty': 'タスクがまだありません。', 'tasks.pending': '未完了', 'tasks.done': '完了', 'tasks.complete': '完了にする', 'tasks.save': '保存', 'tasks.open': '進行中', 'tasks.undo': '元に戻す', 'tasks.notePlaceholder': '今日のメモを追加...', 'tasks.photo': 'タスク写真', 'tasks.addMedia': 'メディアを追加', 'tasks.pickFromGallery': 'ギャラリーから選ぶ', 'tasks.takeMedia': '写真 / 動画を撮る', 'tasks.pickPhoto': '写真を選ぶ', 'tasks.takePhoto': '写真を撮る', 'tasks.cameraDenied': 'カメラの権限がありません。', 'tasks.cameraError': 'カメラが利用できません。', 'tasks.historyTitle': 'タスク履歴', 'tasks.historyEmpty': 'タスク履歴がまだありません。', 'tasks.back': 'タスクに戻る', 'tasks.default.fieldCheck': '圃場チェック', 'tasks.default.fieldCheckDesc': '圃場の状態とメモを簡単に記録。', 'tasks.default.scouting': '病害虫の確認', 'tasks.default.scoutingDesc': '葉を確認して深刻度を記録。', 'tasks.default.sensors': 'センサー計測', 'tasks.default.sensorsDesc': '土壌水分や天候の記録。', 'fields.title': '圃場', 'fields.loading': '圃場を読み込み中...', 'fields.empty': '圃場がまだありません。', 'fields.nameRequired': '圃場名は必須です。', 'fields.areaInvalid': '面積は数値で入力してください。', 'fields.saved': '保存しました。', 'fields.saving': '保存中...', 'fields.name': '圃場名', 'fields.area': '面積 (ha)', 'fields.areaPlaceholder': '例: 1.5', 'fields.notes': 'メモ', 'fields.notesPlaceholder': '土壌、灌漑、目印など...', 'fields.save': '圃場を保存', 'fields.update': '圃場を更新', 'fields.cancel': 'キャンセル', 'fields.edit': '編集', 'fields.delete': '削除', 'fields.deleteTitle': '圃場を削除しますか?', 'fields.deleteMessage': 'この操作は取り消せません。', 'fields.new': '新しい圃場', 'fields.unnamed': '無名の圃場', 'fields.areaLabel': '面積:', 'fields.photo': '圃場写真', 'fields.addMedia': 'メディアを追加', 'fields.pickFromGallery': 'ギャラリーから選ぶ', 'fields.takeMedia': '写真 / 動画を撮る', 'fields.videoSelected': '動画を選択しました。', 'fields.pickPhoto': '写真を選ぶ', 'fields.takePhoto': '写真を撮る', 'fields.noPhoto': '写真が選択されていません。', 'fields.updatedAt': '更新:', 'logbook.title': 'ログブック', 'logbook.subtitle': '主要データを管理。', 'logbook.fields': '圃場', 'logbook.fieldsHint': '面積、メモ、境界。', 'logbook.observations': '観察', 'logbook.observationsHint': '観察メモと深刻度。', 'logbook.crops': '作物', 'logbook.cropsHint': '圃場ごとの作物情報。', 'logbook.tasks': '日次タスク', 'logbook.tasksHint': 'メモ、写真、状態。', 'logbook.history': 'タスク履歴', 'logbook.historyHint': '日付別の完了記録。', 'logbook.harvests': '収穫', 'logbook.harvestsHint': '収量と収穫の詳細。', 'logbook.sales': '販売', 'logbook.salesHint': '販売記録と買い手。', 'logbook.costs': 'コスト', 'logbook.costsHint': '支出と領収書。', 'observations.title': '観察', 'observations.loading': '観察を読み込み中...', 'observations.empty': '観察がまだありません。', 'observations.saved': '保存しました。', 'observations.saving': '保存中...', 'observations.field': '圃場', 'observations.crop': '作物', 'observations.type': '種類', 'observations.note': 'メモ', 'observations.severity': '深刻度', 'observations.severityLabel': '深刻度:', 'observations.selectField': '圃場を選択', 'observations.selectCrop': '作物を選択', 'observations.typePlaceholder': '例: 観察', 'observations.notePlaceholder': '観察内容を入力してください。', 'observations.severityPlaceholder': '0-10', 'observations.fieldRequired': '圃場は必須です。', 'observations.severityInvalid': '深刻度は数値で入力してください。', 'observations.delete': '削除', 'observations.noField': '圃場なし', 'observations.noCrop': '作物なし', 'observations.untitled': '観察', 'observations.save': '観察を保存', 'observations.new': '新しい観察', 'observations.cancel': 'キャンセル', 'observations.edit': '観察を編集', 'observations.update': '観察を更新', 'observations.photo': '観察写真', 'observations.addMedia': 'メディアを追加', 'observations.pickFromGallery': 'ギャラリーから選ぶ', 'observations.takeMedia': '写真 / 動画を撮る', 'observations.pickPhoto': '写真を選ぶ', 'observations.takePhoto': '写真を撮る', 'observations.noPhoto': '写真が選択されていません。', 'harvests.title': '収穫記録', 'harvests.loading': '収穫記録を読み込み中...', 'harvests.empty': '収穫記録がまだありません。', 'harvests.saved': '保存しました。', 'harvests.saving': '保存中...', 'harvests.new': '新しい収穫', 'harvests.field': '圃場', 'harvests.crop': '作物', 'harvests.selectField': '圃場を選択', 'harvests.selectCrop': '作物を選択', 'harvests.date': '収穫日', 'harvests.datePlaceholder': 'YYYY-MM-DD', 'harvests.quantity': '数量', 'harvests.quantityPlaceholder': '例: 120', 'harvests.unit': '単位', 'harvests.unitPlaceholder': 'kg', 'harvests.notes': 'メモ', 'harvests.notesPlaceholder': '品質、天候、人員メモ...', 'harvests.photo': '収穫写真', 'harvests.addMedia': 'メディアを追加', 'harvests.pickFromGallery': 'ギャラリーから選ぶ', 'harvests.takeMedia': '写真 / 動画を撮る', 'harvests.pickPhoto': '写真を選ぶ', 'harvests.takePhoto': '写真を撮る', 'harvests.noPhoto': '写真が選択されていません。', 'harvests.fieldRequired': '圃場は必須です。', 'harvests.cropRequired': '作物は必須です。', 'harvests.quantityInvalid': '数量は数値で入力してください。', 'harvests.delete': '削除', 'harvests.deleteTitle': '収穫記録を削除しますか?', 'harvests.deleteMessage': 'この操作は取り消せません。', 'harvests.cancel': 'キャンセル', 'harvests.save': '収穫を保存', 'harvests.untitled': '収穫', 'harvests.noField': '圃場なし', 'harvests.noCrop': '作物なし', 'harvests.edit': '収穫を編集', 'harvests.update': '収穫を更新', 'sales.title': '販売記録', 'sales.loading': '販売記録を読み込み中...', 'sales.empty': '販売記録がまだありません。', 'sales.saved': '保存しました。', 'sales.saving': '保存中...', 'sales.new': '新しい販売', 'sales.field': '圃場', 'sales.crop': '作物', 'sales.harvest': '収穫 (任意)', 'sales.selectField': '圃場を選択', 'sales.selectCrop': '作物を選択', 'sales.selectHarvest': '収穫を選択', 'sales.noHarvest': '収穫記録がありません', 'sales.date': '販売日', 'sales.datePlaceholder': 'YYYY-MM-DD', 'sales.quantity': '数量', 'sales.quantityPlaceholder': '例: 50', 'sales.unit': '単位', 'sales.unitPlaceholder': 'kg', 'sales.price': '価格', 'sales.pricePlaceholder': '例: 35', 'sales.priceLabel': '価格:', 'sales.buyer': '買い手', 'sales.buyerPlaceholder': '例: 地元市場', 'sales.notes': 'メモ', 'sales.notesPlaceholder': '支払い、輸送、品質...', 'sales.fieldRequired': '圃場は必須です。', 'sales.cropRequired': '作物は必須です。', 'sales.quantityInvalid': '数量は数値で入力してください。', 'sales.delete': '削除', 'sales.deleteTitle': '販売記録を削除しますか?', 'sales.deleteMessage': 'この操作は取り消せません。', 'sales.cancel': 'キャンセル', 'sales.pickFromGallery': 'ギャラリーから選ぶ', 'sales.takeMedia': '写真 / 動画を撮る', 'sales.save': '販売を保存', 'sales.untitled': '販売', 'sales.noField': '圃場なし', 'sales.noCrop': '作物なし', 'sales.edit': '販売を編集', 'sales.update': '販売を更新', 'costs.title': '費用記録', 'costs.loading': '費用を読み込み中...', 'costs.empty': '費用記録がまだありません。', 'costs.saved': '保存しました。', 'costs.saving': '保存中...', 'costs.new': '新しい費用', 'costs.field': '圃場', 'costs.crop': '作物 (任意)', 'costs.selectField': '圃場を選択', 'costs.selectCrop': '作物を選択', 'costs.category': 'カテゴリ', 'costs.category.seed': '種子', 'costs.category.fertilizer': '肥料', 'costs.category.labor': '人件費', 'costs.category.fuel': '燃料', 'costs.category.equipment': '設備', 'costs.category.transport': '輸送', 'costs.category.misc': 'その他', 'costs.categoryPlaceholder': '例: 種子', 'costs.amount': '金額', 'costs.amountPlaceholder': '例: 1200', 'costs.vendor': '仕入先', 'costs.vendorPlaceholder': '例: 地元の資材店', 'costs.date': '日付', 'costs.datePlaceholder': 'YYYY-MM-DD', 'costs.notes': 'メモ', 'costs.notesPlaceholder': '領収書、用途、目的...', 'costs.photo': '領収書写真', 'costs.addMedia': 'メディアを追加', 'costs.pickFromGallery': 'ギャラリーから選ぶ', 'costs.takeMedia': '写真 / 動画を撮る', 'costs.pickPhoto': '写真を選ぶ', 'costs.takePhoto': '写真を撮る', 'costs.noPhoto': '写真が選択されていません。', 'costs.fieldRequired': '圃場は必須です。', 'costs.amountInvalid': '金額は数値で入力してください。', 'costs.delete': '削除', 'costs.deleteTitle': '費用記録を削除しますか?', 'costs.deleteMessage': 'この操作は取り消せません。', 'costs.cancel': 'キャンセル', 'costs.save': '費用を保存', 'costs.edit': '費用を編集', 'costs.update': '費用を更新', 'costs.untitled': '費用', 'costs.noField': '圃場なし', 'costs.noCrop': '作物なし', 'units.kg': 'kg', 'units.g': 'g', 'units.ton': 't', 'units.pcs': '個', 'demo.field.north': '北圃場', 'demo.field.northNote': '壌土 · 点滴灌漑', 'demo.field.river': '川沿い区画', 'demo.field.riverNote': '水路沿いの低地', 'demo.field.greenhouse': '温室', 'demo.field.greenhouseNote': '遮光ベッド、毎日灌漑', 'demo.field.orchard': '果樹園区画', 'demo.field.orchardNote': '畝立て、東側に防風林', 'demo.field.terrace': '段々畑区画', 'demo.field.terraceNote': '段々斜面に点滴ライン', 'demo.crop.tomato': 'トマト', 'demo.crop.tomatoVariety': 'チェリー', 'demo.crop.rice': '米', 'demo.crop.riceVariety': 'ジャスミン', 'demo.crop.lettuce': 'レタス', 'demo.crop.lettuceVariety': 'バターヘッド', 'demo.crop.chili': '唐辛子', 'demo.crop.chiliVariety': 'バードアイ', 'demo.crop.cabbage': 'キャベツ', 'demo.crop.cabbageVariety': '青キャベツ', 'demo.observation.scoutingNote': '畝の端で初期の斑点を確認。', 'demo.observation.diseaseNote': '雨の後に病斑が見られました。', 'demo.observation.irrigationNote': '灌漑時間を夕方に調整。', 'demo.observation.pestNote': '新芽にアブラムシを確認。', 'demo.observation.nutrientNote': '下葉が淡く、葉面散布を実施。', 'demo.task.note': '予定通り完了。', 'demo.task.note2': '標準チェックリストを実施。', 'demo.task.note3': '機材確認と記録を完了。', 'demo.harvest.note1': '朝の収穫、品質良好。', 'demo.harvest.note2': '小雨後に収穫。', 'demo.harvest.note3': '市場向けにサイズ別選別。', 'demo.sale.buyer1': '地元市場', 'demo.sale.buyer2': '卸売業者', 'demo.sale.buyer3': 'レストラン取引先', 'demo.sale.note1': '当日配送。', 'demo.sale.note2': '全額支払い済み。', 'demo.sale.note3': '週次供給を依頼。', 'demo.cost.vendor1': '農業資材店', 'demo.cost.vendor2': '肥料店', 'demo.cost.vendor3': '作業班', 'demo.cost.note1': 'トマト種子とトレー。', 'demo.cost.note2': '水田用の元肥。', 'demo.cost.note3': '収穫補助(半日)。', 'observations.type.scouting': '観察', 'observations.type.pest': '害虫', 'observations.type.disease': '病害', 'observations.type.irrigation': '灌漑', 'observations.type.weeds': '雑草', 'observations.type.nutrients': '栄養', 'crops.title': '作物', 'crops.loading': '作物を読み込み中...', 'crops.empty': '作物がまだありません。', 'crops.saved': '保存しました。', 'crops.saving': '保存中...', 'crops.field': '圃場', 'crops.selectField': '圃場を選択', 'crops.name': '作物名', 'crops.variety': '品種', 'crops.planting': '定植日', 'crops.harvest': '収穫予定', 'crops.selectDate': '日付を選択', 'crops.namePlaceholder': '例: トマト', 'crops.varietyPlaceholder': '例: チェリー', 'crops.plantingPlaceholder': 'YYYY-MM-DD', 'crops.harvestPlaceholder': 'YYYY-MM-DD', 'crops.fieldRequired': '圃場は必須です。', 'crops.nameRequired': '作物名は必須です。', 'crops.delete': '削除', 'crops.deleteTitle': '作物を削除しますか?', 'crops.deleteMessage': 'この操作は取り消せません。', 'crops.noField': '圃場なし', 'crops.untitled': '作物', 'crops.plantingLabel': '定植:', 'crops.harvestLabel': '収穫:', 'crops.save': '作物を保存', 'crops.new': '新しい作物', 'crops.photo': '作物写真', 'crops.addMedia': 'メディアを追加', 'crops.pickFromGallery': 'ギャラリーから選ぶ', 'crops.takeMedia': '写真 / 動画を撮る', 'crops.pickPhoto': '写真を選ぶ', 'crops.takePhoto': '写真を撮る', 'crops.noPhoto': '写真が選択されていません。', 'crops.today': '今日', 'crops.done': '完了', 'crops.edit': '作物を編集', 'crops.update': '作物を更新', 'crops.cancel': 'キャンセル', }, }; export function createTranslator(language: Language) { return (key: string, params?: Params) => { const template = strings[language][key] ?? strings.en[key] ?? key; if (!params) return template; return Object.keys(params).reduce((result, paramKey) => { return result.replace( new RegExp(`{{${paramKey}}}`, 'g'), String(params[paramKey]) ); }, template); }; } function getDeviceLanguage(): Language { try { const locale = Intl.DateTimeFormat().resolvedOptions().locale; if (locale.toLowerCase().startsWith('th')) return 'th'; if (locale.toLowerCase().startsWith('ja')) return 'ja'; } catch { // fall through } return 'en'; } type LocalizationContextValue = { language: Language; setLanguage: (language: Language) => void; t: (key: string, params?: Params) => string; }; const LocalizationContext = createContext(null); export function LocalizationProvider({ children }: { children: ReactNode }) { const [language, setLanguage] = useState(getDeviceLanguage()); const t = useCallback( (key: string, params?: Params) => { const template = strings[language][key] ?? strings.en[key] ?? key; if (!params) return template; return Object.keys(params).reduce((result, paramKey) => { return result.replace( new RegExp(`{{${paramKey}}}`, 'g'), String(params[paramKey]) ); }, template); }, [language] ); const value = useMemo( () => ({ language, setLanguage, t }), [language, setLanguage, t] ); return {children}; } export function useTranslation() { const ctx = useContext(LocalizationContext); if (!ctx) { throw new Error('useTranslation must be used within LocalizationProvider'); } return ctx; }