Add Chinese translations for medication management and personal settings

- Introduced new translation files for medication, personal, and weight management in Chinese.
- Updated the main index file to include the new translation modules.
- Enhanced the medication type definitions to include 'ointment'.
- Refactored workout type labels to utilize i18n for better localization support.
- Improved sleep quality descriptions and recommendations with i18n integration.
This commit is contained in:
richarjiang
2025-11-28 17:29:51 +08:00
parent fbe0c92f0f
commit bca6670390
42 changed files with 7972 additions and 6632 deletions

303
i18n/en/challenge.ts Normal file
View File

@@ -0,0 +1,303 @@
export const challengeDetail = {
title: 'Challenge Details',
notFound: 'Challenge not found, please try again later.',
loading: 'Loading challenge details…',
retry: 'Reload',
share: {
generating: 'Generating share card...',
failed: 'Share failed, please try again later',
messageJoined: 'I\'m participating in "{{title}}" challenge, completed {{completed}}/{{target}} days! Join me!',
messageNotJoined: 'Found an amazing challenge "{{title}}", let\'s join together!',
},
dateRange: {
format: '{{start}} - {{end}}',
monthDay: 'Month {{month}} Day {{day}}',
ongoing: 'Ongoing updates',
},
participants: {
count: '{{count}} participants',
ongoing: 'Ongoing updates',
more: 'More',
},
detail: {
requirement: 'Daily check-in auto accumulates',
viewAllRanking: 'View All',
},
checkIn: {
title: 'Challenge Check-in',
todayChecked: 'Checked in today',
subtitle: 'Daily check-ins accumulate progress towards goal',
subtitleChecked: 'Today\'s progress recorded, keep it up tomorrow',
button: {
checkIn: 'Check In Now',
checking: 'Checking in…',
checked: 'Checked in today',
notJoined: 'Join to check in',
upcoming: 'Not started yet',
expired: 'Challenge ended',
},
toast: {
alreadyChecked: 'Already checked in today',
notStarted: 'Challenge not started yet, check in after it begins',
expired: 'Challenge has ended, cannot check in',
mustJoin: 'Join the challenge to check in',
success: 'Check-in successful, keep going!',
failed: 'Check-in failed, please try again',
},
},
cta: {
join: 'Join Challenge',
joining: 'Joining…',
leave: 'Leave Challenge',
leaving: 'Leaving…',
delete: 'Delete Challenge',
deleting: 'Deleting…',
upcoming: 'Starting Soon',
expired: 'Challenge Ended',
},
highlight: {
join: {
title: 'Join Challenge Now',
subtitle: 'Invite friends to persist together, achieve more easily',
},
leave: {
title: 'Don\'t leave just yet',
subtitle: 'Keep going, the next milestone is around the corner',
},
upcoming: {
title: 'Challenge Starting Soon',
subtitle: 'Starts on {{date}}, stay tuned',
subtitleFallback: 'Challenge coming soon, stay tuned',
},
expired: {
title: 'Challenge Ended',
subtitle: 'Ended on {{date}}, look forward to the next one',
subtitleFallback: 'This round has ended, look forward to the next challenge',
},
},
alert: {
leaveConfirm: {
title: 'Confirm leaving challenge?',
message: 'You will need to rejoin to continue.',
cancel: 'Cancel',
confirm: 'Leave Challenge',
},
joinFailed: 'Failed to join challenge',
leaveFailed: 'Failed to leave challenge',
archiveConfirm: {
title: 'Delete this challenge?',
message: 'This cannot be undone and participants will lose access.',
cancel: 'Cancel',
confirm: 'Delete Challenge',
},
archiveFailed: 'Failed to delete challenge',
archiveSuccess: 'Challenge deleted',
},
ranking: {
title: 'Leaderboard',
description: '',
empty: 'Leaderboard opening soon, grab your spot.',
today: 'Today',
todayGoal: 'Today\'s Goal',
hour: 'hrs',
},
leaderboard: {
title: 'Leaderboard',
loading: 'Loading leaderboard…',
notFound: 'Challenge not found.',
loadFailed: 'Unable to load leaderboard, please try again later.',
empty: 'Leaderboard opening soon, grab your spot.',
loadMore: 'Loading more…',
loadMoreFailed: 'Failed to load more, pull to refresh and retry',
},
shareCard: {
footer: 'Out Live · Beyond Life',
progress: {
label: 'My Progress',
days: '{{completed}} / {{target}} days',
completed: '🎉 Challenge Completed!',
remaining: '{{remaining}} days to complete',
},
info: {
checkInDaily: 'Daily check-in',
joinUs: 'Join us!',
},
shareCode: {
copied: 'Share code copied',
},
},
shareCode: {
copied: 'Share code copied',
},
};
export const badges = {
title: 'Badge Gallery',
subtitle: 'Celebrate every effort',
hero: {
highlight: 'Keep checking in to unlock rarer badges.',
earnedLabel: 'Earned',
totalLabel: 'Total',
progressLabel: 'Progress',
},
categories: {
all: 'All',
sleep: 'Sleep',
exercise: 'Exercise',
diet: 'Nutrition',
challenge: 'Challenge',
social: 'Social',
special: 'Special',
},
rarities: {
common: 'Common',
uncommon: 'Uncommon',
rare: 'Rare',
epic: 'Epic',
legendary: 'Legendary',
},
status: {
earned: 'Unlocked',
locked: 'Locked',
earnedAt: 'Unlocked on {{date}}',
},
legend: 'Rarity legend',
filterLabel: 'Badge categories',
empty: {
title: 'No badges yet',
description: 'Complete sleep, workout, or challenge tasks to earn your first badge.',
action: 'Explore plans',
},
};
export const challenges = {
title: 'Challenges',
subtitle: 'Join challenges to stay consistent',
loading: 'Loading challenges…',
loadFailed: 'Failed to load challenges, please try again later.',
retry: 'Retry',
empty: 'No challenges yet. Join one to get started.',
customChallenges: 'Custom Challenges',
officialChallengesTitle: 'Official Challenges',
officialChallenges: 'Official challenges launching soon.',
join: 'Join',
joined: 'Joined',
invalidInviteCode: 'Please enter a valid invite code',
joinSuccess: 'Joined challenge successfully',
joinFailed: 'Failed to join challenge',
joinModal: {
title: 'Join via invite code',
description: 'Enter the invite code to join a challenge',
confirm: 'Join',
joining: 'Joining…',
cancel: 'Cancel',
placeholder: 'Enter invite code',
},
statusLabels: {
upcoming: 'Upcoming',
ongoing: 'Ongoing',
expired: 'Ended',
},
createCustom: {
title: 'Create Challenge',
editTitle: 'Edit Challenge',
yourChallenge: 'Your challenge',
basicInfo: 'Basic Info',
challengeSettings: 'Challenge Settings',
displayInteraction: 'Display & Interaction',
durationDays: '{{days}} days',
durationDaysChallenge: '{{days}}-day challenge',
dayUnit: 'days',
defaultTitle: 'Custom Challenge',
rankingDescription: 'Leaderboard updates daily',
typeLabels: {
water: 'Hydration',
exercise: 'Exercise',
diet: 'Diet',
sleep: 'Sleep',
mood: 'Mood',
weight: 'Weight',
custom: 'Custom',
},
fields: {
title: 'Challenge title',
titlePlaceholder: 'e.g., 21-day hydration',
coverImage: 'Cover image',
uploadCover: 'Upload cover',
challengeDescription: 'Challenge description',
descriptionPlaceholder: 'Describe the goal and check-in rules',
challengeType: 'Challenge type',
challengeTypeHelper: 'Pick the category closest to your goal',
timeRange: 'Time range',
start: 'Start date',
end: 'End date',
duration: 'Duration',
periodLabel: 'Period label',
periodLabelPlaceholder: 'e.g., 21-day sprint',
dailyTargetAndUnit: 'Daily target & unit',
dailyTargetPlaceholder: 'Daily target value',
unitPlaceholder: 'Unit (cups / mins / steps...)',
unitHelper: 'Optional, shown after the daily target',
minimumCheckInDays: 'Minimum check-in days',
minimumCheckInDaysPlaceholder: 'Cannot exceed total duration',
maxParticipants: 'Max participants',
noLimit: 'No limit',
isPublic: 'Allow public join',
publicDescription: 'Others can join with the invite code when enabled.',
},
floatingCTA: {
title: 'Generate invite code',
subtitle: 'Create a challenge and share it with friends',
editTitle: 'Save changes',
editSubtitle: 'Update the challenge for all participants',
},
buttons: {
createAndGenerateCode: 'Create & generate code',
creating: 'Creating…',
updateAndSave: 'Save changes',
updating: 'Saving…',
},
datePicker: {
confirm: 'Confirm',
cancel: 'Cancel',
},
alerts: {
titleRequired: 'Please enter a challenge title',
endTimeError: 'End date must be after start date',
targetValueError: 'Daily target must be between 1 and 1000',
minimumDaysError: 'Minimum check-in days must be between 1 and 365',
minimumDaysExceedError: 'Minimum check-in days cannot exceed total duration',
participantsError: 'Participants must be between 2 and 10000 or leave empty',
createFailed: 'Failed to create challenge',
createSuccess: 'Challenge created',
updateSuccess: 'Challenge updated',
},
imageUpload: {
selectSource: 'Choose cover',
selectMessage: 'Take a photo or pick from album',
camera: 'Camera',
album: 'Album',
cancel: 'Cancel',
cameraPermission: 'Camera permission required',
cameraPermissionMessage: 'Enable camera access to take a photo.',
albumPermissionMessage: 'Enable photo access to choose from library.',
cameraFailed: 'Failed to open camera',
cameraFailedMessage: 'Please try again or choose from album.',
selectFailed: 'Selection failed',
selectFailedMessage: 'Could not select an image, please try again.',
uploadFailed: 'Upload failed',
uploadFailedMessage: 'Cover upload failed, please retry.',
uploading: 'Uploading…',
clear: 'Remove cover',
helper: 'Use a 16:9 cover under 2MB for better results.',
},
shareModal: {
title: 'Invite code generated',
subtitle: 'Share this code so others can join your challenge',
generatingCode: 'Generating…',
copyCode: 'Copy code',
viewChallenge: 'View challenge',
later: 'Share later',
},
},
};

5
i18n/en/common.ts Normal file
View File

@@ -0,0 +1,5 @@
export const dateSelector = {
backToToday: 'Back to Today',
cancel: 'Cancel',
confirm: 'Confirm',
};

551
i18n/en/diet.ts Normal file
View File

@@ -0,0 +1,551 @@
export const nutritionRecords = {
title: 'Nutrition Records',
listTitle: 'Today\'s Meals',
recordCount: '{{count}} records',
empty: {
title: 'No records today',
action: 'Add Record',
},
footer: {
end: '- No more records -',
loadMore: 'Load More',
},
delete: {
title: 'Confirm Delete',
message: 'Are you sure you want to delete this nutrition record? This action cannot be undone.',
cancel: 'Cancel',
confirm: 'Delete',
},
mealTypes: {
breakfast: 'Breakfast',
lunch: 'Lunch',
dinner: 'Dinner',
snack: 'Snack',
other: 'Other',
},
nutrients: {
protein: 'Protein',
fat: 'Fat',
carbs: 'Carbs',
unit: 'g',
caloriesUnit: 'kcal',
},
overlay: {
title: 'Record Method',
scan: 'AI Scan',
foodLibrary: 'Food Library',
voiceRecord: 'Voice Log',
},
chart: {
remaining: 'Remaining',
formula: 'Remaining = Metabolism + Exercise - Diet',
metabolism: 'Metabolism',
exercise: 'Exercise',
diet: 'Diet',
},
};
export const foodCamera = {
title: 'Food Camera',
hint: 'Keep food within the frame',
permission: {
title: 'Camera Permission Required',
description: 'Camera access is needed to capture food for AI recognition',
button: 'Allow Access',
},
guide: {
title: 'Shooting Guide',
description: 'Please upload or take clear photos of food to improve recognition accuracy',
button: 'Got it',
good: 'Good lighting, clear subject',
bad: 'Blurry, poor lighting',
},
buttons: {
album: 'Album',
capture: 'Capture',
help: 'Help',
},
alerts: {
captureFailed: {
title: 'Capture Failed',
message: 'Please try again',
},
pickFailed: {
title: 'Selection Failed',
message: 'Please try again',
},
},
};
export const foodRecognition = {
title: 'Food Recognition',
header: {
confirm: 'Confirm Food',
recognizing: 'AI Recognizing',
},
errors: {
noImage: 'Image not found',
generic: 'Food recognition failed, please try again',
unknown: 'Unknown error',
noFoodDetected: 'Recognition failed: No food detected',
processError: 'Error during recognition process',
},
logs: {
uploading: '📤 Uploading image to cloud...',
uploadSuccess: '✅ Image upload completed',
analyzing: '🤖 AI model analyzing...',
analysisSuccess: '✅ AI analysis completed',
confidence: '🎯 Confidence: {{value}}%',
itemsFound: '🍽️ Detected {{count}} food items',
failed: '❌ Recognition failed: No food detected',
error: '❌ Error during recognition process',
},
status: {
idle: {
title: 'Ready',
subtitle: 'Please wait...',
},
uploading: {
title: 'Uploading Image',
subtitle: 'Uploading image to cloud server...',
},
recognizing: {
title: 'AI Analyzing',
subtitle: 'AI model is analyzing food ingredients...',
},
completed: {
title: 'Success',
subtitle: 'Redirecting to analysis results...',
},
failed: {
title: 'Failed',
subtitle: 'Please check network or try again later',
},
processing: {
title: 'Processing...',
subtitle: 'Please wait...',
},
},
mealTypes: {
breakfast: 'Breakfast',
lunch: 'Lunch',
dinner: 'Dinner',
snack: 'Snack',
unknown: 'Unknown',
},
info: {
title: 'Smart Food Recognition',
description: 'AI will analyze the photo, identify food types, estimate nutrition, and generate a detailed report.',
},
actions: {
start: 'Start Recognition',
retry: 'Retry',
logs: 'Process Logs',
logsPlaceholder: 'Ready to start...',
},
alerts: {
recognizing: {
title: 'Recognition in progress',
message: 'Recognition is not complete. Are you sure you want to go back?',
continue: 'Continue',
back: 'Go Back',
},
},
};
export const foodAnalysisResult = {
title: 'Analysis Result',
error: {
notFound: 'Image or recognition result not found',
},
placeholder: 'Nutrition Record',
nutrients: {
caloriesUnit: 'kcal',
protein: 'Protein',
fat: 'Fat',
carbs: 'Carbs',
unit: 'g',
},
sections: {
recognitionResult: 'Recognition Result',
foodIntake: 'Food Intake',
},
nonFood: {
title: 'No Food Detected',
suggestions: {
title: 'Suggestions:',
item1: '• Ensure food is in the frame',
item2: '• Try a clearer angle',
item3: '• Avoid blur or poor lighting',
},
},
actions: {
retake: 'Retake',
record: 'Record',
close: 'Close',
},
mealSelector: {
title: 'Select Meal',
},
editModal: {
title: 'Edit Food Info',
fields: {
name: 'Food Name',
namePlaceholder: 'Enter food name',
amount: 'Weight (g)',
amountPlaceholder: 'Enter weight',
calories: 'Calories (kcal)',
caloriesPlaceholder: 'Enter calories',
},
actions: {
cancel: 'Cancel',
save: 'Save',
},
},
confidence: 'Confidence: {{value}}%',
dateFormats: {
today: 'MMM D, YYYY',
full: 'MMM D, YYYY HH:mm',
},
};
export const foodLibrary = {
title: 'Food Library',
custom: 'Custom',
search: {
placeholder: 'Search food...',
loading: 'Searching...',
empty: 'No relevant food found',
noData: 'No food data',
},
loading: 'Loading food library...',
retry: 'Retry',
mealTypes: {
breakfast: 'Breakfast',
lunch: 'Lunch',
dinner: 'Dinner',
snack: 'Snack',
},
actions: {
record: 'Record',
selectMeal: 'Select Meal',
},
alerts: {
deleteFailed: {
title: 'Delete Failed',
message: 'Error occurred while deleting food, please try again later',
},
createFailed: {
title: 'Create Failed',
message: 'Error occurred while creating custom food, please try again later',
},
},
};
export const createCustomFood = {
title: 'Create Custom Food',
save: 'Save',
preview: {
title: 'Preview',
defaultName: 'Food Name',
},
basicInfo: {
title: 'Basic Info',
name: 'Food Name',
namePlaceholder: 'e.g. Hamburger',
defaultAmount: 'Default Amount',
calories: 'Calories',
},
optionalInfo: {
title: 'Optional Info',
photo: 'Photo',
addPhoto: 'Add Photo',
protein: 'Protein',
fat: 'Fat',
carbohydrate: 'Carbs',
},
units: {
kcal: 'kcal',
g: 'g',
gram: 'g',
},
alerts: {
permissionDenied: {
title: 'Permission Denied',
message: 'Photo library permission is required to select photos',
},
uploadFailed: {
title: 'Upload Failed',
message: 'Photo upload failed, please try again',
},
error: {
title: 'Error',
message: 'Failed to select photo, please try again',
},
validation: {
title: 'Notice',
nameRequired: 'Please enter food name',
caloriesRequired: 'Please enter valid calories',
},
},
};
export const voiceRecord = {
title: 'Voice Log',
intro: {
description: 'Describe your meal with voice, AI will intelligently analyze nutrition and calories',
},
status: {
idle: 'Tap microphone to start recording',
listening: 'Listening... Please start speaking...',
processing: 'AI is processing voice content...',
analyzing: 'AI model is deeply analyzing nutritional components...',
result: 'Voice recognition completed, please confirm the result',
},
hints: {
listening: 'Tell us about the food you want to record',
},
examples: {
title: 'Recording Examples:',
items: [
'This morning I had two fried eggs, a slice of whole wheat bread and a glass of milk',
'For lunch I had about 150g of braised pork, a small bowl of rice and a serving of vegetables',
'For dinner I had steamed egg custard, seaweed egg drop soup and a bowl of millet porridge',
],
},
analysis: {
progress: 'Analysis Progress: {{progress}}%',
hint: 'AI is deeply analyzing your food description...',
},
result: {
label: 'Recognition Result:',
},
actions: {
retry: 'Retry Recording',
confirm: 'Confirm & Use',
},
alerts: {
noVoiceInput: 'No voice input detected, please try again',
networkError: 'Network connection error, please check network and try again',
voiceError: 'Voice recognition problem occurred, please try again',
noValidContent: 'No valid content recognized, please record again',
pleaseRecordFirst: 'Please perform voice recognition first',
recordingFailed: 'Recording Failed',
recordingPermissionError: 'Unable to start voice recognition, please check microphone permission settings',
analysisFailed: 'Analysis Failed',
},
};
export const nutritionLabelAnalysis = {
title: 'Nutrition Label Analysis',
camera: {
permissionDenied: 'Permission Denied',
permissionMessage: 'Camera permission is required to take nutrition label photos',
},
actions: {
takePhoto: 'Take Photo',
selectFromAlbum: 'Select from Album',
startAnalysis: 'Start Analysis',
close: 'Close',
},
placeholder: {
text: 'Take or select a nutrition label photo',
},
status: {
uploading: 'Uploading image...',
analyzing: 'Analyzing nutrition label...',
},
errors: {
analysisFailed: {
title: 'Analysis Failed',
message: 'Error occurred while analyzing the image, please try again',
defaultMessage: 'Analysis service is temporarily unavailable',
},
cannotRecognize: 'Unable to recognize nutrition label, please try taking a clearer photo',
cameraPermissionDenied: 'Camera permission is required to take nutrition label photos',
},
results: {
title: 'Detailed Nutrition Analysis',
detailedAnalysis: 'Detailed Nutrition Analysis',
},
imageViewer: {
close: 'Close',
dateFormat: 'MMM D, YYYY HH:mm',
},
};
export const nutritionAnalysisHistory = {
title: 'History',
dateFormat: 'MMM D, YYYY HH:mm',
recognized: 'Recognized {{count}} nutrients',
loadingMore: 'Loading more...',
loading: 'Loading history...',
filter: {
all: 'All',
},
filters: {
all: 'All',
success: 'Success',
failed: 'Failed',
},
status: {
success: 'Success',
failed: 'Failed',
processing: 'Processing',
unknown: 'Unknown',
},
nutrients: {
energy: 'Energy',
protein: 'Protein',
carbs: 'Carbs',
fat: 'Fat',
},
delete: {
confirmTitle: 'Confirm Delete',
confirmMessage: 'Are you sure you want to delete this record?',
cancel: 'Cancel',
delete: 'Delete',
successTitle: 'Deleted Successfully',
successMessage: 'Record has been deleted successfully',
},
actions: {
expand: 'Expand Details',
collapse: 'Collapse Details',
expandDetails: 'Expand Details',
collapseDetails: 'Collapse Details',
confirmDelete: 'Confirm Delete',
delete: 'Delete',
cancel: 'Cancel',
retry: 'Retry',
},
empty: {
title: 'No History Records',
subtitle: 'Start recognizing nutrition labels',
},
errors: {
error: 'Error',
loadFailed: 'Load Failed',
unknownError: 'Unknown Error',
fetchFailed: 'Failed to fetch history records',
fetchFailedRetry: 'Failed to fetch history records, please retry',
deleteFailed: 'Delete failed, please try again later',
},
loadingState: {
records: 'Loading history...',
more: 'Loading more...',
},
details: {
title: 'Detailed Nutrition Information',
nutritionDetails: 'Detailed Nutrition Information',
aiModel: 'AI Model',
provider: 'Service Provider',
serviceProvider: 'Service Provider',
},
records: {
nutritionCount: 'Recognized {{count}} nutrients',
},
imageViewer: {
close: 'Close',
},
};
export const waterDetail = {
title: 'Water Details',
waterRecord: 'Water Records',
today: 'Today',
total: 'Total: ',
goal: 'Goal: ',
noRecords: 'No water records',
noRecordsSubtitle: 'Tap "Add Record" to start tracking water intake',
deleteConfirm: {
title: 'Confirm Delete',
message: 'Are you sure you want to delete this water record? This action cannot be undone.',
cancel: 'Cancel',
confirm: 'Delete',
},
deleteButton: 'Delete',
water: 'Water',
loadingUserPreferences: 'Failed to load user preferences',
};
export const waterSettings = {
title: 'Water Settings',
sections: {
dailyGoal: 'Daily Water Goal',
quickAdd: 'Quick Add Default',
reminder: 'Water Reminder',
},
descriptions: {
quickAdd: 'Set the default water amount when clicking the "+" button',
reminder: 'Set periodic reminders to replenish water',
},
labels: {
ml: 'ml',
disabled: 'Disabled',
},
alerts: {
goalSuccess: {
title: 'Settings Saved',
message: 'Daily water goal has been set to {{amount}}ml',
},
quickAddSuccess: {
title: 'Settings Saved',
message: 'Quick add default has been set to {{amount}}ml',
},
quickAddFailed: {
title: 'Save Failed',
message: 'Unable to save quick add default, please try again',
},
},
buttons: {
cancel: 'Cancel',
confirm: 'Confirm',
},
status: {
reminderEnabled: '{{startTime}}-{{endTime}}, every {{interval}} minutes',
},
};
export const waterReminderSettings = {
title: 'Water Reminder',
sections: {
notifications: 'Push Notifications',
timeRange: 'Reminder Time Range',
interval: 'Reminder Interval',
},
descriptions: {
notifications: 'Enable to receive periodic water reminders during specified time periods',
timeRange: 'Only send reminders during specified time periods to avoid disturbing your rest',
interval: 'Choose the reminder frequency, recommended 30-120 minutes',
},
labels: {
startTime: 'Start Time',
endTime: 'End Time',
interval: 'Reminder Interval',
saveSettings: 'Save Settings',
hours: 'Hours',
timeRangePreview: 'Time Range Preview',
minutes: 'Minutes',
},
alerts: {
timeValidation: {
title: 'Time Setting Tip',
startTimeInvalid: 'Start time cannot be later than or equal to end time, please select again',
endTimeInvalid: 'End time cannot be earlier than or equal to start time, please select again',
},
success: {
enabled: 'Settings Saved',
enabledMessage: 'Water reminder has been enabled\n\nTime range: {{timeRange}}\nReminder interval: {{interval}}\n\nWe will periodically remind you to drink water during the specified time period',
disabled: 'Settings Saved',
disabledMessage: 'Water reminder has been disabled',
},
error: {
title: 'Save Failed',
message: 'Unable to save water reminder settings, please try again',
},
},
buttons: {
confirm: 'Confirm',
cancel: 'Cancel',
},
};

507
i18n/en/health.ts Normal file
View File

@@ -0,0 +1,507 @@
export const healthPermissions = {
title: 'Health data disclosure',
subtitle: 'We integrate with Apple Health through HealthKit and CareKit to deliver precise training, recovery, and reminder experiences.',
cards: {
usage: {
title: 'Data we read or write',
items: [
'Activity: steps, active energy, and workouts fuel performance charts and rings.',
'Body metrics: height, weight, and body fat keep plans and nutrition tips personalized.',
'Sleep & recovery: duration and stages unlock recovery advice and reminders.',
'Hydration: we read and write water intake so Health and the app stay in sync.',
],
},
purpose: {
title: 'Why we need it',
items: [
'Generate adaptive training plans, challenges, and recovery nudges.',
'Display long-term trends so you can understand progress at a glance.',
'Reduce manual input by syncing reminders and challenge progress automatically.',
],
},
control: {
title: 'Your control',
items: [
'Permissions are granted inside Apple Health; change them anytime under iOS Settings > Health > Data Access & Devices.',
'We never access data you do not authorize, and cached values are removed if you revoke access.',
'Core functionality keeps working and offers manual input alternatives.',
],
},
privacy: {
title: 'Storage & privacy',
items: [
'Health data stays on your device — we do not upload it or share it with third parties.',
'Only aggregated, anonymized stats are synced when absolutely necessary.',
"We follow Apple's review requirements and will notify you before any changes.",
],
},
},
callout: {
title: 'What if I skip authorization?',
items: [
'The related modules will ask for permission and provide manual logging options.',
'Declining does not break other areas of the app that do not rely on Health data.',
],
},
contact: {
title: 'Need help?',
description: 'Questions about HealthKit or CareKit? Reach out via email or the in-app feedback form:',
email: 'richardwei1995@gmail.com',
},
};
export const statistics = {
title: 'Out Live',
sections: {
bodyMetrics: 'Body Metrics',
},
components: {
diet: {
title: 'Diet Analysis',
loading: 'Loading...',
updated: 'Updated: {{time}}',
remaining: 'Can Still Eat',
calories: 'Calories',
protein: 'Protein',
carb: 'Carbs',
fat: 'Fat',
fiber: 'Fiber',
sodium: 'Sodium',
basal: 'Basal',
exercise: 'Exercise',
diet: 'Diet',
kcal: 'kcal',
aiRecognition: 'AI Scan',
foodLibrary: 'Food Library',
voiceRecord: 'Voice Log',
nutritionLabel: 'Nutrition Label',
},
fitness: {
kcal: 'kcal',
minutes: 'min',
hours: 'hrs',
},
steps: {
title: 'Steps',
},
mood: {
title: 'Mood',
empty: 'Tap to record mood',
},
stress: {
title: 'Stress',
unit: 'ms',
},
water: {
title: 'Water',
unit: 'ml',
addButton: '+ {{amount}}ml',
},
metabolism: {
title: 'Basal Metabolism',
loading: 'Loading...',
unit: 'kcal/day',
status: {
high: 'High',
normal: 'Normal',
low: 'Low',
veryLow: 'Very Low',
unknown: 'Unknown',
},
},
sleep: {
title: 'Sleep',
loading: 'Loading...',
},
oxygen: {
title: 'Blood Oxygen',
},
circumference: {
title: 'Circumference (cm)',
setTitle: 'Set {{label}}',
confirm: 'Confirm',
measurements: {
chest: 'Chest',
waist: 'Waist',
hip: 'Hip',
arm: 'Arm',
thigh: 'Thigh',
calf: 'Calf',
},
},
workout: {
title: 'Recent Workout',
minutes: 'min',
kcal: 'kcal',
noData: 'No workout data',
syncing: 'Syncing...',
sourceWaiting: 'Source: Syncing...',
sourceUnknown: 'Source: Unknown',
sourceFormat: 'Source: {{source}}',
sourceFormatMultiple: 'Source: {{source}} et al.',
lastWorkout: 'Latest Workout',
updated: 'Updated',
},
weight: {
title: 'Weight Records',
addButton: 'Record Weight',
bmi: 'BMI',
weight: 'Weight',
days: 'days',
range: 'Range',
unit: 'kg',
bmiModal: {
title: 'BMI Index Explanation',
description: 'BMI (Body Mass Index) is an internationally recognized health indicator for assessing weight relative to height',
formula: 'Formula: weight(kg) ÷ height²(m)',
classificationTitle: 'BMI Classification Standards',
healthTipsTitle: 'Health Tips',
tips: {
nutrition: 'Maintain a balanced diet and control calorie intake',
exercise: 'At least 150 minutes of moderate-intensity exercise per week',
sleep: 'Ensure 7-9 hours of adequate sleep',
monitoring: 'Regularly monitor weight changes and adjust promptly',
},
disclaimer: 'BMI is for reference only and cannot reflect muscle mass, bone density, etc. If you have health concerns, please consult a professional doctor.',
continueButton: 'Continue',
},
},
fitnessRings: {
title: 'Fitness Rings',
activeCalories: 'Active Calories',
exerciseMinutes: 'Exercise Minutes',
standHours: 'Stand Hours',
goal: '/{{goal}}',
ringLabels: {
active: 'Active',
exercise: 'Exercise',
stand: 'Stand',
},
},
},
tabs: {
health: 'Health',
medications: 'Meds',
fasting: 'Fasting',
challenges: 'Challenges',
personal: 'Me',
},
activityHeatMap: {
subtitle: 'Active {{days}} days in the last 6 months',
activeRate: '{{rate}}%',
popover: {
title: 'Accumulated energy can be redeemed for AI-related benefits',
subtitle: 'How to earn',
rules: {
login: '1. Daily login earns energy +1',
mood: '2. Daily mood record earns energy +1',
diet: '3. Diet record earns energy +1',
goal: '4. Complete a goal earns energy +1',
},
},
months: {
1: 'Jan',
2: 'Feb',
3: 'Mar',
4: 'Apr',
5: 'May',
6: 'Jun',
7: 'Jul',
8: 'Aug',
9: 'Sep',
10: 'Oct',
11: 'Nov',
12: 'Dec',
},
legend: {
less: 'Less',
more: 'More',
},
},
};
export const sleepDetail = {
title: 'Sleep Details',
loading: 'Loading sleep data...',
today: 'Today',
sleepScore: 'Sleep Score',
noData: 'No sleep data available',
noDataRecommendation: 'Please ensure you are running on a real iOS device with authorized health data access, or wait until you have sleep data to view.',
sleepDuration: 'Sleep Duration',
sleepQuality: 'Sleep Quality',
sleepStages: 'Sleep Stages',
learnMore: 'Learn More',
awake: 'Awake',
rem: 'REM',
core: 'Core Sleep',
deep: 'Deep Sleep',
unknown: 'Unknown',
rawData: 'Raw Data',
rawDataDescription: 'Contains {{count}} HealthKit sleep sample records',
infoModalTitles: {
sleepTime: 'Sleep Time',
sleepQuality: 'Sleep Quality',
},
sleepGrades: {
low: 'Low',
normal: 'Normal',
good: 'Good',
excellent: 'Excellent',
poor: 'Poor',
fair: 'Fair',
},
sleepTimeDescription: 'Sleep is most important - it accounts for more than half of your sleep score. Longer sleep can reduce sleep debt, but regular sleep times are crucial for quality rest.',
sleepQualityDescription: 'Sleep quality comprehensively evaluates multiple indicators such as your sleep efficiency, deep sleep duration, REM sleep ratio, etc. High-quality sleep depends not only on duration but also on sleep continuity and balance of sleep stages.',
sleepStagesInfo: {
title: 'Understand Your Sleep Stages',
description: 'People have many misconceptions about sleep stages and sleep quality. Some people may need more deep sleep, while others may not. Scientists and doctors are still exploring the role of different sleep stages and their effects on the body. By tracking sleep stages and paying attention to how you feel each morning, you may gain deeper insights into your own sleep.',
awake: {
title: 'Awake Time',
description: 'During a sleep period, you may wake up several times. Occasional waking is normal. You may fall back asleep immediately and not remember waking up during the night.',
},
rem: {
title: 'REM Sleep',
description: 'This sleep stage may have some impact on learning and memory. During this stage, your muscles are most relaxed and your eyes move rapidly left and right. This is also the stage where most of your dreams occur.',
},
core: {
title: 'Core Sleep',
description: 'This stage is sometimes called light sleep and is as important as other stages. This stage usually occupies most of your sleep time each night. Brain waves that are crucial for cognition are generated during this stage.',
},
deep: {
title: 'Deep Sleep',
description: 'Due to the characteristics of brain waves, this stage is also called slow-wave sleep. During this stage, body tissues are repaired and important hormones are released. It usually occurs in the first half of sleep and lasts longer. During deep sleep, the body is very relaxed, so you may find it harder to wake up during this stage compared to other stages.',
},
},
};
export const sleepQuality = {
excellent: {
description: 'You feel refreshed and energized',
recommendation: 'Congratulations on getting quality sleep! If you feel energized, consider moderate exercise to maintain a healthy lifestyle and further reduce stress for optimal sleep.'
},
good: {
description: 'Good sleep quality, decent mental state',
recommendation: 'Your sleep quality is decent but has room for improvement.建议 maintaining regular sleep schedules, avoiding electronic devices before bed, and creating a quiet, comfortable sleep environment.'
},
fair: {
description: 'Fair sleep quality, may affect daytime performance',
recommendation: 'Your sleep needs improvement.建议 establishing a fixed bedtime routine, limiting caffeine intake, ensuring appropriate bedroom temperature, and considering light exercise to improve sleep quality.'
},
poor: {
description: 'Poor sleep quality, attention to sleep health recommended',
recommendation: 'Your sleep quality needs serious attention.建议 consulting a doctor or sleep specialist to check for sleep disorders, while improving sleep environment and habits, avoiding stimulating activities before bed.'
}
};
export const stepsDetail = {
title: 'Steps Details',
loading: 'Loading...',
stats: {
totalSteps: 'Total Steps',
averagePerHour: 'Average Per Hour',
mostActiveTime: 'Most Active Time',
},
chart: {
title: 'Hourly Steps Distribution',
averageLabel: 'Average {{steps}} steps',
},
activityLevel: {
currentActivity: 'Your activity level today is',
levels: {
inactive: 'Inactive',
light: 'Lightly Active',
moderate: 'Moderately Active',
very_active: 'Very Active',
},
progress: {
current: 'Current',
nextLevel: 'Next: {{level}}',
highestLevel: 'Highest Level',
},
},
timeLabels: {
midnight: '0:00',
noon: '12:00',
nextDay: '24:00',
},
};
export const fitnessRingsDetail = {
title: 'Fitness Rings Detail',
loading: 'Loading...',
weekDays: {
monday: 'Mon',
tuesday: 'Tue',
wednesday: 'Wed',
thursday: 'Thu',
friday: 'Fri',
saturday: 'Sat',
sunday: 'Sun',
},
cards: {
activeCalories: {
title: 'Active Calories',
unit: 'kcal',
},
exerciseMinutes: {
title: 'Exercise Minutes',
unit: 'minutes',
info: {
title: 'Exercise Minutes:',
description: 'Exercise at an intensity of at least "brisk walking" will accumulate corresponding exercise minutes.',
recommendation: 'WHO recommends adults to maintain at least 30 minutes of moderate to high-intensity exercise daily.',
knowButton: 'Got it',
},
},
standHours: {
title: 'Stand Hours',
unit: 'hours',
},
},
stats: {
weeklyClosedRings: 'Weekly Closed Rings',
daysUnit: 'days',
},
datePicker: {
cancel: 'Cancel',
confirm: 'Confirm',
},
errors: {
loadExerciseInfoPreference: 'Failed to load exercise minutes info preference',
saveExerciseInfoPreference: 'Failed to save exercise minutes info preference',
},
};
export const circumferenceDetail = {
title: 'Circumference Statistics',
loading: 'Loading...',
error: 'Loading failed',
retry: 'Retry',
noData: 'No data available',
noDataSelected: 'Please select circumference data to display',
tabs: {
week: 'By Week',
month: 'By Month',
year: 'By Year',
},
measurements: {
chest: 'Chest',
waist: 'Waist',
upperHip: 'Upper Hip',
arm: 'Arm',
thigh: 'Thigh',
calf: 'Calf',
},
modal: {
title: 'Set {{label}}',
defaultTitle: 'Set Circumference',
confirm: 'Confirm',
},
chart: {
weekLabel: 'Week {{week}}',
monthLabel: '{{month}}',
empty: 'No data available',
noSelection: 'Please select circumference data to display',
},
};
export const basalMetabolismDetail = {
title: 'Basal Metabolism',
currentData: {
title: '{{date}} Basal Metabolism',
unit: 'kcal',
normalRange: 'Normal range: {{min}}-{{max}} kcal',
noData: '--',
},
stats: {
title: 'Basal Metabolism Statistics',
tabs: {
week: 'By Week',
month: 'By Month',
},
},
chart: {
loading: 'Loading...',
loadingText: 'Loading...',
error: {
text: 'Loading failed: {{error}}',
retry: 'Retry',
fetchFailed: 'Failed to fetch data',
},
empty: 'No data available',
yAxisSuffix: 'kcal',
weekLabel: 'Week {{week}}',
},
modal: {
title: 'Basal Metabolism',
closeButton: '×',
description: 'Basal metabolism, also known as Basal Metabolic Rate (BMR), refers to the minimum energy consumption required for the human body to maintain basic life functions (heartbeat, breathing, body temperature regulation, etc.) in a completely resting state, usually measured in calories.',
sections: {
importance: {
title: 'Why is it important?',
content: 'Basal metabolism accounts for 60-75% of total energy consumption and is the foundation of energy balance. Understanding your basal metabolism helps develop scientific nutrition plans, optimize weight management strategies, and assess metabolic health status.',
},
normalRange: {
title: 'Normal Range',
formulas: {
male: 'Male: BMR = 10 × weight(kg) + 6.25 × height(cm) - 5 × age + 5',
female: 'Female: BMR = 10 × weight(kg) + 6.25 × height(cm) - 5 × age - 161',
},
userRange: 'Your normal range: {{min}}-{{max}} kcal/day',
rangeNote: '(Within 15% above or below the calculated value is considered normal)',
userInfo: 'Based on your information: {{gender}}, {{age}} years old, {{height}}cm, {{weight}}kg',
incompleteInfo: 'Please complete basic information to calculate your metabolic rate',
},
strategies: {
title: 'Strategies to Boost Metabolism',
subtitle: 'Scientific research supports the following methods:',
items: [
'1. Increase muscle mass (2-3 strength training sessions per week)',
'2. High-intensity interval training (HIIT)',
'3. Adequate protein intake (1.6-2.2g per kg of body weight)',
'4. Ensure adequate sleep (7-9 hours per night)',
'5. Avoid excessive calorie restriction (not less than 80% of BMR)',
],
},
},
},
gender: {
male: 'Male',
female: 'Female',
},
comments: {
reloadData: 'Reload data',
},
};
export const workoutHistory = {
title: 'Workout Summary',
loading: 'Loading workout records...',
error: {
permissionDenied: 'Health data permission not granted',
loadFailed: 'Failed to load workout records, please try again later',
detailLoadFailed: 'Failed to load workout details, please try again later',
},
retry: 'Retry',
monthlyStats: {
title: 'Workout Time',
periodText: 'Statistics period: 1st - {{day}} (This month)',
overviewWithStats: 'As of {{date}}, you have completed {{count}} workouts, totaling {{duration}}.',
overviewEmpty: 'No workout records this month yet, start moving to collect your first one!',
emptyData: 'No workout data this month',
},
intensity: {
low: 'Low Intensity',
medium: 'Medium Intensity',
high: 'High Intensity',
},
historyCard: {
calories: '{{calories}} kcal · {{minutes}} min',
activityTime: '{{activity}}, {{time}}',
},
empty: {
title: 'No Workout Records',
subtitle: 'Complete a workout to view detailed history here',
},
monthOccurrence: 'This is your {{index}} {{activity}} in {{month}}.',
};

17
i18n/en/index.ts Normal file
View File

@@ -0,0 +1,17 @@
import * as Challenge from './challenge';
import * as Common from './common';
import * as Diet from './diet';
import * as Health from './health';
import * as Medication from './medication';
import * as Personal from './personal';
import * as Weight from './weight';
export default {
...Personal,
...Health,
...Diet,
...Medication,
...Weight,
...Challenge,
...Common,
};

472
i18n/en/medication.ts Normal file
View File

@@ -0,0 +1,472 @@
export const medications = {
greeting: 'Hello, {{name}}',
welcome: 'Welcome to Medication Assistant!',
todayMedications: 'Today\'s Medications',
filters: {
all: 'All',
taken: 'Taken',
missed: 'Missed',
},
emptyState: {
title: 'No medications scheduled for today',
subtitle: 'No medication plans added yet. Let\'s add some.',
},
stack: {
completed: 'Completed ({{count}})',
},
dateFormats: {
today: 'Today, {{date}}',
other: '{{date}}',
},
// MedicationCard
card: {
status: {
missed: 'Missed',
timeToTake: 'Time to take',
remaining: '{{time}} remaining',
},
action: {
takeNow: 'Take Now',
taken: 'Taken',
skipped: 'Skipped',
skip: 'Skip',
submitting: 'Submitting...',
},
skipAlert: {
title: 'Confirm Skip',
message: 'Are you sure you want to skip this medication?\n\nIt will not be recorded as taken.',
cancel: 'Cancel',
confirm: 'Confirm Skip',
},
earlyTakeAlert: {
title: 'Not yet time to take medication',
message: 'This medication is scheduled for {{time}}, which is more than 1 hour from now.\n\nHave you already taken this medication?',
cancel: 'Cancel',
confirm: 'Confirm Taken',
},
takeError: {
title: 'Operation Failed',
message: 'An error occurred while recording medication, please try again later',
confirm: 'OK',
},
skipError: {
title: 'Operation Failed',
message: 'Skip operation failed, please try again later',
confirm: 'OK',
},
},
// Add Medication Page
add: {
title: 'Add Medication',
steps: {
name: 'Medication Name',
dosage: 'Dosage & Form',
frequency: 'Frequency',
time: 'Reminder Time',
note: 'Notes',
},
descriptions: {
name: 'Name the medication and upload package photo for easy identification',
dosage: 'Select tablet type and fill in dosage per administration',
frequency: 'Set medication frequency and daily times',
time: 'Add and manage daily reminder times',
note: 'Fill in notes or doctor instructions (optional)',
},
name: {
placeholder: 'Enter or search medication name',
},
photo: {
title: 'Upload Medication Photo',
subtitle: 'Take a photo or select from album to help identify medication packaging',
selectTitle: 'Select Image',
selectMessage: 'Please select image source',
camera: 'Camera',
album: 'From Album',
cancel: 'Cancel',
retake: 'Retake',
uploading: 'Uploading...',
uploadingText: 'Uploading',
remove: 'Remove',
cameraPermission: 'Camera permission is required to take medication photos',
albumPermission: 'Album permission is required to select medication photos',
uploadFailed: 'Upload Failed',
uploadFailedMessage: 'Image upload failed, please try again later',
cameraFailed: 'Camera Failed',
cameraFailedMessage: 'Unable to open camera, please try again later',
selectFailed: 'Selection Failed',
selectFailedMessage: 'Unable to open album, please try again later',
},
dosage: {
label: 'Dosage per administration',
placeholder: '0.5',
type: 'Type',
unitSelector: 'Select dosage unit',
},
frequency: {
label: 'Times per day',
value: '{{count}} times/day',
period: 'Medication period',
start: 'Start',
end: 'End',
longTerm: 'Long-term',
startDateInvalid: 'Invalid date',
startDateInvalidMessage: 'Start date cannot be earlier than today',
endDateInvalid: 'Invalid date',
endDateInvalidMessage: 'End date cannot be earlier than start date',
},
time: {
label: 'Daily reminder times',
addTime: 'Add Time',
editTime: 'Edit Reminder Time',
addTimeButton: 'Add Time',
},
note: {
label: 'Notes',
placeholder: 'Record precautions, doctor instructions or custom reminders',
voiceNotSupported: 'Voice-to-text is not supported on this device, you can type notes directly',
voiceError: 'Voice recognition unavailable',
voiceErrorMessage: 'Unable to use voice input, please check permission settings and try again',
voiceStartError: 'Unable to start voice input',
voiceStartErrorMessage: 'Please check microphone and voice recognition permissions and try again',
},
actions: {
previous: 'Previous',
next: 'Next',
complete: 'Complete',
},
success: {
title: 'Added Successfully',
message: 'Successfully added medication "{{name}}"',
confirm: 'OK',
},
error: {
title: 'Add Failed',
message: 'An error occurred while creating medication, please try again later',
confirm: 'OK',
},
datePickers: {
startDate: 'Select Start Date',
endDate: 'Select End Date',
time: 'Select Time',
cancel: 'Cancel',
confirm: 'Confirm',
},
pickers: {
timesPerDay: 'Select Times Per Day',
dosageUnit: 'Select Dosage Unit',
cancel: 'Cancel',
confirm: 'Confirm',
},
},
// Medication Management Page
manage: {
title: 'Medication Management',
subtitle: 'Manage status and reminders for all medications',
filters: {
all: 'All',
active: 'Active',
inactive: 'Inactive',
},
loading: 'Loading medication information...',
empty: {
title: 'No Medications',
subtitle: 'No medication records yet, click the top right to add',
},
deactivate: {
title: 'Deactivate {{name}}?',
description: 'After deactivation, medication plans generated for the day will be deleted and cannot be recovered.',
confirm: 'Confirm Deactivation',
cancel: 'Cancel',
error: {
title: 'Operation Failed',
message: 'An error occurred while deactivating medication, please try again later.',
},
},
toggleError: {
title: 'Operation Failed',
message: 'An error occurred while toggling medication status, please try again later.',
},
formLabels: {
capsule: 'Capsule',
pill: 'Tablet',
tablet: 'Tablet',
injection: 'Injection',
spray: 'Spray',
drop: 'Drops',
syrup: 'Syrup',
other: 'Other',
ointment: 'Ointment',
},
frequency: {
daily: 'Daily',
weekly: 'Weekly',
custom: 'Custom',
},
cardMeta: 'Started {{date}} Reminder: {{reminder}}',
reminderNotSet: 'Not set',
unknownDate: 'Unknown date',
},
// Medication Detail Page
detail: {
title: 'Medication Details',
notFound: {
title: 'Medication information not found',
subtitle: 'Please re-enter this page from the medication list.',
},
loading: 'Loading...',
error: {
title: 'Unable to retrieve medication information at this time, please try again later.',
subtitle: 'Please check your network and try again, or return to the previous page.',
},
sections: {
plan: 'Medication Plan',
dosage: 'Dosage & Form',
note: 'Notes',
overview: 'Medication Overview',
aiAnalysis: 'AI Medication Analysis',
},
plan: {
period: 'Medication Period',
time: 'Medication Time',
frequency: 'Frequency',
expiryDate: 'Expiry Date',
longTerm: 'Long-term',
periodMessage: 'Start date: {{startDate}}\n{{endDateInfo}}',
longTermPlan: 'Medication plan: Long-term medication',
timeMessage: 'Set times: {{times}}',
dateFormat: 'MMM D, YYYY',
periodRange: 'From {{startDate}} to {{endDate}}',
periodLongTerm: 'From {{startDate}} until indefinitely',
expiryStatus: {
notSet: 'Not set',
expired: 'Expired',
expiresToday: 'Expires today',
expiresInDays: 'Expires in {{days}} days',
},
},
dosage: {
label: 'Dosage per administration',
form: 'Form',
selectDosage: 'Select Dosage',
selectForm: 'Select Form',
dosageValue: 'Dosage Value',
unit: 'Unit',
},
note: {
label: 'Medication Notes',
placeholder: 'Record precautions, doctor instructions or custom reminders',
edit: 'Edit Notes',
noNote: 'No notes',
voiceNotSupported: 'Voice-to-text is not supported on this device, you can type notes directly',
save: 'Save',
saveError: {
title: 'Save Failed',
message: 'An error occurred while submitting notes, please try again later.',
},
},
overview: {
calculating: 'Calculating...',
takenCount: 'Taken {{count}} times in total',
calculatingDays: 'Calculating adherence days',
startedDays: 'Adhered for {{days}} days',
startDate: 'Started {{date}}',
noStartDate: 'No start date',
},
aiAnalysis: {
analyzing: 'Analyzing medication information...',
analyzingButton: 'Analyzing...',
reanalyzeButton: 'Reanalyze',
getAnalysisButton: 'Get AI Analysis',
button: 'AI Analysis',
status: {
generated: 'Generated',
memberExclusive: 'Member Exclusive',
pending: 'Pending',
},
title: 'Analysis Results',
recommendation: 'AI Recommended',
placeholder: 'Get AI analysis to quickly understand suitable populations, ingredient safety, and usage recommendations.',
categories: {
suitableFor: 'Suitable For',
unsuitableFor: 'Unsuitable For',
sideEffects: 'Possible Side Effects',
storageAdvice: 'Storage Advice',
healthAdvice: 'Health/Usage Advice',
},
membershipCard: {
title: 'Member Exclusive AI In-depth Analysis',
subtitle: 'Unlock complete medication analysis and unlimited usage',
},
error: {
title: 'Analysis Failed',
message: 'AI analysis failed, please try again later',
networkError: 'Failed to initiate analysis request, please check network connection',
unauthorized: 'Please log in first',
forbidden: 'No access to this medication',
notFound: 'Medication not found',
},
},
aiDraft: {
reshoot: 'Reshoot',
saveAndCreate: 'Save & Create',
saveError: {
title: 'Save Failed',
message: 'An error occurred while creating medication, please try again later',
},
},
status: {
enabled: 'Reminders Enabled',
disabled: 'Reminders Disabled',
},
delete: {
title: 'Delete {{name}}?',
description: 'After deletion, reminders and history related to this medication will be cleared and cannot be recovered.',
confirm: 'Delete',
cancel: 'Cancel',
error: {
title: 'Delete Failed',
message: 'An error occurred while removing this medication, please try again later.',
},
},
deactivate: {
title: 'Deactivate {{name}}?',
description: 'After deactivation, medication plans generated for the day will be deleted and cannot be recovered.',
confirm: 'Confirm Deactivation',
cancel: 'Cancel',
error: {
title: 'Operation Failed',
message: 'An error occurred while deactivating medication, please try again later.',
},
},
toggleError: {
title: 'Operation Failed',
message: 'An error occurred while toggling reminder status, please try again later.',
},
updateErrors: {
dosage: 'Update Failed',
dosageMessage: 'An error occurred while updating dosage, please try again later.',
form: 'Update Failed',
formMessage: 'An error occurred while updating form, please try again later.',
expiryDate: 'Update Failed',
expiryDateMessage: 'Failed to update expiry date, please try again later.',
},
imageViewer: {
close: 'Close',
},
pickers: {
cancel: 'Cancel',
confirm: 'Confirm',
},
},
// Edit Frequency Page
editFrequency: {
title: 'Edit Medication Frequency',
missingParams: 'Missing required parameters',
medicationName: 'Editing: {{name}}',
sections: {
frequency: 'Medication Frequency',
frequencyDescription: 'Set daily medication frequency',
time: 'Daily Reminder Times',
timeDescription: 'Add and manage daily reminder times',
},
frequency: {
repeatPattern: 'Repeat Pattern',
timesPerDay: 'Times Per Day',
daily: 'Daily',
weekly: 'Weekly',
custom: 'Custom',
timesLabel: '{{count}} times',
summary: '{{pattern}} {{count}} times',
},
time: {
addTime: 'Add Time',
editTime: 'Edit Reminder Time',
addTimeButton: 'Add Time',
},
actions: {
save: 'Save Changes',
},
error: {
title: 'Update Failed',
message: 'An error occurred while updating medication frequency, please try again later.',
},
pickers: {
cancel: 'Cancel',
confirm: 'Confirm',
},
},
aiProgress: {
title: 'Analyzing',
steps: {
analyzing_product: 'Analyzing product...',
analyzing_suitability: 'Checking suitability...',
analyzing_ingredients: 'Evaluating ingredients...',
analyzing_effects: 'Generating safety advice...',
completed: 'Completed, loading details...',
},
errors: {
default: 'Recognition failed, please retake photo',
queryFailed: 'Query failed, please try again later',
},
modal: {
title: 'Retake Required',
retry: 'Retake Photo',
},
},
aiCamera: {
title: 'AI Scan',
steps: {
front: {
title: 'Front',
subtitle: 'Ensure medication name is clearly visible',
},
side: {
title: 'Back',
subtitle: 'Include specs and ingredients info',
},
aux: {
title: 'Side',
subtitle: 'Add more details to improve accuracy',
},
stepProgress: 'Step {{current}} / {{total}}',
optional: '(Optional)',
notTaken: 'Empty',
},
buttons: {
flip: 'Flip',
capture: 'Snap',
complete: 'Done',
album: 'Album',
},
permission: {
title: 'Camera Permission Required',
description: 'Allow access to capture medication packaging for automatic recognition',
button: 'Allow Camera Access',
},
alerts: {
pickFailed: {
title: 'Selection Failed',
message: 'Please try again or choose another image',
},
captureFailed: {
title: 'Capture Failed',
message: 'Please try again',
},
insufficientPhotos: {
title: 'Photos Missing',
message: 'Please capture at least front and back sides',
},
taskFailed: {
title: 'Task Creation Failed',
defaultMessage: 'Please check network and try again',
},
},
guideModal: {
badge: 'Guide',
title: 'Keep Photos Clear',
description1: 'Please capture the product name and description on the front/back of the medication.',
description2: 'Ensure good lighting, avoid glare, and keep text legible. Photo clarity affects recognition accuracy.',
button: 'Got it!',
},
},
};

408
i18n/en/personal.ts Normal file
View File

@@ -0,0 +1,408 @@
export const personal = {
edit: 'Edit',
login: 'Log in',
memberNumber: 'Member ID: {{number}}',
aiUsage: 'Free AI credits: {{value}}',
aiUsageUnlimited: 'Unlimited',
fishRecord: 'Energy log',
badgesPreview: {
title: 'My badges',
subtitle: 'Celebrate every milestone',
cta: 'View all',
loading: 'Syncing your badges…',
empty: 'Complete sleep or challenge tasks to unlock your first badge.',
lockedHint: 'Keep building the habit to unlock more.',
},
stats: {
height: 'Height',
weight: 'Weight',
age: 'Age',
ageSuffix: ' yrs',
},
membership: {
badge: 'Premium member',
planFallback: 'VIP Membership',
expiryLabel: 'Valid until',
changeButton: 'Change plan',
validForever: 'No expiry',
dateFormat: 'YYYY-MM-DD',
},
sections: {
notifications: 'Notifications',
developer: 'Developer',
other: 'Other',
account: 'Account & Security',
language: 'Language',
healthData: 'Health data permissions',
medicalSources: 'Medical Advice Sources',
customization: 'Customization',
},
menu: {
notificationSettings: 'Notification settings',
developerOptions: 'Developer options',
pushSettings: 'Push notification settings',
privacyPolicy: 'Privacy policy',
feedback: 'Feedback',
userAgreement: 'User agreement',
logout: 'Log out',
deleteAccount: 'Delete account',
healthDataPermissions: 'Health data disclosure',
whoSource: 'World Health Organization (WHO)',
tabBarConfig: 'Tab Bar Settings',
},
language: {
title: 'Language',
menuTitle: 'Display language',
modalTitle: 'Choose language',
modalSubtitle: 'Your selection applies immediately',
cancel: 'Cancel',
options: {
zh: {
label: 'Chinese',
description: 'Use the Chinese interface',
},
en: {
label: 'English',
description: 'Use the app in English',
},
},
},
tabBarConfig: {
title: 'Tab Bar Settings',
subtitle: 'Customize your bottom navigation',
description: 'Use toggles to show or hide tabs',
resetButton: 'Reset',
cannotDisable: 'Cannot be disabled',
resetConfirm: {
title: 'Reset to Default?',
message: 'This will reset all tab bar settings and visibility',
cancel: 'Cancel',
confirm: 'Confirm',
},
resetSuccess: 'Settings reset to default',
},
};
export const editProfile = {
title: 'Edit Profile',
fields: {
name: 'Nickname',
gender: 'Gender',
height: 'Height',
weight: 'Weight',
activityLevel: 'Activity Level',
birthDate: 'Birth Date',
maxHeartRate: 'Max Heart Rate',
},
gender: {
male: 'Male',
female: 'Female',
notSet: 'Not set',
},
height: {
unit: 'cm',
placeholder: '170cm',
},
weight: {
unit: 'kg',
placeholder: '55kg',
},
activityLevels: {
1: 'Sedentary',
2: 'Lightly active',
3: 'Moderately active',
4: 'Very active',
descriptions: {
1: 'Rarely exercise',
2: 'Exercise 1-3 times per week',
3: 'Exercise 3-5 times per week',
4: 'Exercise 6-7 times per week',
},
},
birthDate: {
placeholder: 'January 1, 1995',
format: '{{month}} {{day}}, {{year}}',
},
maxHeartRate: {
unit: 'bpm',
notAvailable: 'Not available',
alert: {
title: 'Notice',
message: 'Max heart rate data is automatically retrieved from Health app',
},
},
alerts: {
notLoggedIn: {
title: 'Not logged in',
message: 'Please log in before trying to save',
},
saveFailed: {
title: 'Save failed',
message: 'Please try again later',
},
avatarPermissions: {
title: 'Insufficient permissions',
message: 'Photo album permission is required to select avatar',
},
avatarUploadFailed: {
title: 'Upload failed',
message: 'Avatar upload failed, please try again',
},
avatarError: {
title: 'Error occurred',
message: 'Failed to select avatar, please try again',
},
avatarSuccess: {
title: 'Success',
message: 'Avatar updated successfully',
},
},
modals: {
cancel: 'Cancel',
confirm: 'Confirm',
save: 'Save',
input: {
namePlaceholder: 'Enter nickname',
weightPlaceholder: 'Enter weight',
weightUnit: 'kg',
},
selectHeight: 'Select Height',
selectGender: 'Select Gender',
selectActivityLevel: 'Select Activity Level',
female: 'Female',
male: 'Male',
},
defaultValues: {
name: 'TonightEatMeat',
height: 170,
weight: 55,
birthDate: '1995-01-01',
activityLevel: 1,
},
};
export const login = {
title: 'Log In',
subtitle: 'Healthy living, freedom through self-discipline',
appleLogin: 'Sign in with Apple',
loggingIn: 'Logging in...',
agreement: {
readAndAgree: 'I have read and agree to ',
privacyPolicy: 'Privacy Policy',
and: ' and ',
userAgreement: 'User Agreement',
alert: {
title: 'Please read and agree',
message: 'Please read and check the "Privacy Policy" and "User Agreement" before continuing. Clicking "Agree and Continue" will automatically check the box and proceed.',
cancel: 'Cancel',
confirm: 'Agree and Continue',
},
},
errors: {
appleIdentityTokenMissing: 'Failed to get Apple identity token',
loginFailed: 'Login failed, please try again later',
loginFailedTitle: 'Login Failed',
},
success: {
loginSuccess: 'Login Successful',
},
};
export const authGuard = {
logout: {
error: 'Logout Failed',
errorMessage: 'Failed to logout, please try again later',
},
confirmLogout: {
title: 'Confirm Logout',
message: 'Are you sure you want to logout of your current account?',
cancelButton: 'Cancel',
confirmButton: 'Confirm',
},
deleteAccount: {
successTitle: 'Account Deleted',
successMessage: 'Your account has been successfully deleted',
confirmButton: 'OK',
errorTitle: 'Deletion Failed',
errorMessage: 'Failed to delete account, please try again later',
},
confirmDeleteAccount: {
title: 'Confirm Account Deletion',
message: 'This action cannot be undone. Your account and all related data will be permanently deleted. Are you sure you want to continue?',
cancelButton: 'Cancel',
confirmButton: 'Confirm Deletion',
},
};
export const membershipModal = {
plans: {
lifetime: {
title: 'Lifetime',
subtitle: 'Lifetime companion, witnessing every health transformation',
},
quarterly: {
title: 'Quarterly',
subtitle: '3-month scientific plan, making health a habit',
},
weekly: {
title: 'Weekly',
subtitle: '7-day trial, experience the power of professional guidance',
},
unknown: 'Unknown Plan',
tag: 'Best Value',
},
benefits: {
title: 'Benefits Comparison',
subtitle: 'Core benefits at a glance, choose with confidence',
table: {
benefit: 'Benefit',
vip: 'VIP',
regular: 'Regular',
},
items: {
aiCalories: {
title: 'AI Calorie Tracking',
description: 'Photo recognition for automatic calorie tracking',
},
aiNutrition: {
title: 'AI Nutrition Label',
description: 'Identify nutrition facts from food packaging',
},
healthReminder: {
title: 'Daily Health Reminder',
description: 'Personalized health reminders based on goals',
},
aiMedication: {
title: 'AI Medication Manager',
description: 'Deep analysis of interactions & personalized schedules',
},
customChallenge: {
title: 'Unlimited Custom Challenges',
description: 'Create exclusive challenges & invite friends to join the journey',
},
},
permissions: {
unlimited: 'Unlimited',
limited: 'Limited',
dailyLimit: '{{count}} times/day',
fullSupport: 'Full Support',
basicSupport: 'Basic',
smartReminder: 'Smart',
fullAnalysis: 'Deep Analysis',
createUnlimited: 'Unlimited',
notSupported: 'Not Supported',
},
},
sectionTitle: {
plans: 'Membership Plans',
plansSubtitle: 'Flexible choices, improve at your own pace',
},
actions: {
subscribe: 'Subscribe Now',
processing: 'Processing...',
restore: 'Restore Purchase',
restoring: 'Restoring...',
back: 'Back',
close: 'Close membership modal',
selectPlan: 'Select {{plan}} plan',
purchaseHint: 'Click to purchase {{plan}} membership',
},
agreements: {
prefix: 'By subscribing, you agree to',
userAgreement: 'User Agreement',
membershipAgreement: 'Membership Agreement',
autoRenewalAgreement: 'Auto-Renewal Agreement',
alert: {
title: 'Please read and agree',
message: 'Please agree to User Agreement, Membership Agreement and Auto-Renewal Agreement before purchasing',
confirm: 'OK',
},
},
errors: {
noProducts: 'No membership products found. Please configure iOS products in RevenueCat and sync to current Offering.',
purchaseCancelled: 'Purchase cancelled',
alreadyPurchased: 'You already own this item',
networkError: 'Network connection failed',
paymentPending: 'Payment is processing',
invalidCredentials: 'Account verification failed',
purchaseFailed: 'Purchase failed',
restoreSuccess: 'Restore successful',
restoreFailed: 'Restore failed',
restoreCancelled: 'Restore cancelled',
restorePartialFailed: 'Restore partially failed',
noPurchasesFound: 'No purchase records found',
selectPlan: 'Please select a plan',
},
loading: {
products: 'Loading membership plans, please wait',
purchase: 'Purchase in progress, please wait',
},
success: {
purchase: 'Membership activated successfully',
},
};
export const notificationSettings = {
title: 'Notification Settings',
loading: 'Loading...',
sections: {
notifications: 'Notification Settings',
medicationReminder: 'Medication Reminder',
nutritionReminder: 'Nutrition Reminder',
moodReminder: 'Mood Reminder',
description: 'Description',
},
items: {
pushNotifications: {
title: 'Push Notifications',
description: 'Receive app notifications when enabled',
},
medicationReminder: {
title: 'Medication Reminder',
description: 'Receive reminder notifications at medication time',
},
nutritionReminder: {
title: 'Nutrition Record Reminder',
description: 'Receive nutrition record reminders at meal times',
},
moodReminder: {
title: 'Mood Record Reminder',
description: 'Receive mood record reminders in the evening',
},
},
description: {
text: '• Push notifications is the master switch for all notifications\n• Various reminders require push notifications to be enabled\n• You can manage notification permissions in system settings\n• Disabling push notifications will stop all app notifications',
},
alerts: {
permissionDenied: {
title: 'Permission Denied',
message: 'Please enable notification permission in system settings, then try to enable push notifications',
cancel: 'Cancel',
goToSettings: 'Go to Settings',
},
error: {
title: 'Error',
message: 'Failed to request notification permission',
saveFailed: 'Failed to save settings',
medicationReminderFailed: 'Failed to set medication reminder',
nutritionReminderFailed: 'Failed to set nutrition reminder',
moodReminderFailed: 'Failed to set mood reminder',
},
notificationsEnabled: {
title: 'Notifications Enabled',
body: 'You will receive app notifications and reminders',
},
medicationReminderEnabled: {
title: 'Medication Reminder Enabled',
body: 'You will receive reminder notifications at medication time',
},
nutritionReminderEnabled: {
title: 'Nutrition Reminder Enabled',
body: 'You will receive nutrition record reminders at meal times',
},
moodReminderEnabled: {
title: 'Mood Reminder Enabled',
body: 'You will receive mood record reminders in the evening',
},
},
};

31
i18n/en/weight.ts Normal file
View File

@@ -0,0 +1,31 @@
export const weightRecords = {
title: 'Weight Records',
pageSubtitle: 'Track your weight progress and trends',
loadingHistory: 'Failed to load weight history',
history: 'Records',
historyMonthFormat: '{{year}}.{{month}}',
stats: {
currentWeight: 'Current Weight',
initialWeight: 'Starting Weight',
targetWeight: 'Target Weight',
},
empty: {
title: 'No weight records',
subtitle: 'Tap the + button to add your first record.',
},
modal: {
recordWeight: 'Record Weight',
editInitialWeight: 'Edit Starting Weight',
editTargetWeight: 'Edit Target Weight',
editRecord: 'Edit Record',
inputPlaceholder: 'Enter weight',
unit: 'kg',
quickSelection: 'Quick pick',
confirm: 'Save',
},
alerts: {
deleteFailed: 'Failed to delete record',
invalidWeight: 'Please enter a valid weight between 0 and 500 kg',
saveFailed: 'Failed to save weight, please try again',
},
};