import { ThemedText } from '@/components/ThemedText'; import { useThemeColor } from '@/hooks/useThemeColor'; import { DietRecord } from '@/services/dietRecords'; import { Ionicons } from '@expo/vector-icons'; import dayjs from 'dayjs'; import React, { useMemo } from 'react'; import { Image, StyleSheet, TouchableOpacity, View } from 'react-native'; export type NutritionRecordCardProps = { record: DietRecord; onPress?: () => void; showTimeline?: boolean; isFirst?: boolean; isLast?: boolean; }; const MEAL_TYPE_LABELS = { breakfast: '早餐', lunch: '午餐', dinner: '晚餐', snack: '加餐', other: '其他', } as const; const MEAL_TYPE_ICONS = { breakfast: 'sunny-outline', lunch: 'partly-sunny-outline', dinner: 'moon-outline', snack: 'cafe-outline', other: 'restaurant-outline', } as const; const MEAL_TYPE_COLORS = { breakfast: '#FFB366', lunch: '#4ECDC4', dinner: '#5D5FEF', snack: '#FF6B6B', other: '#9AA3AE', } as const; export function NutritionRecordCard({ record, onPress, showTimeline = false, isFirst = false, isLast = false }: NutritionRecordCardProps) { const surfaceColor = useThemeColor({}, 'surface'); const textColor = useThemeColor({}, 'text'); const textSecondaryColor = useThemeColor({}, 'textSecondary'); const primaryColor = useThemeColor({}, 'primary'); // 营养数据统计 const nutritionStats = useMemo(() => { return [ { label: '热量', value: record.estimatedCalories ? `${Math.round(record.estimatedCalories)} 千卡` : '-', icon: 'flame-outline' as const, color: '#FF6B6B' }, { label: '蛋白质', value: record.proteinGrams ? `${record.proteinGrams.toFixed(1)} g` : '-', icon: 'fitness-outline' as const, color: '#4ECDC4' }, { label: '碳水', value: record.carbohydrateGrams ? `${record.carbohydrateGrams.toFixed(1)} g` : '-', icon: 'leaf-outline' as const, color: '#45B7D1' }, { label: '脂肪', value: record.fatGrams ? `${record.fatGrams.toFixed(1)} g` : '-', icon: 'water-outline' as const, color: '#FFA07A' }, ]; }, [record]); const mealTypeColor = MEAL_TYPE_COLORS[record.mealType]; const mealTypeIcon = MEAL_TYPE_ICONS[record.mealType]; const mealTypeLabel = MEAL_TYPE_LABELS[record.mealType]; return ( {/* 时间轴 */} {showTimeline && ( {record.createdAt ? dayjs(record.createdAt).format('HH:mm') : '--:--'} {!isLast && ( )} )} {/* 卡片内容 */} {/* 主要内容区域 */} {/* 左侧:食物图片 */} {record.imageUrl ? ( ) : ( )} {/* 右侧:食物信息 */} {/* 餐次和操作按钮 */} {mealTypeLabel} {!showTimeline && ( {record.mealTime ? dayjs(record.mealTime).format('HH:mm') : '时间未设置'} )} {/* 食物名称和分量 */} {record.foodName} {(record.weightGrams || record.portionDescription) && ( {record.portionDescription || `${record.weightGrams}g`} )} {/* 营养信息网格 */} {nutritionStats.map((stat) => ( {stat.label} {stat.value} ))} {/* 备注信息 */} {record.notes && ( {record.notes} )} ); } const styles = StyleSheet.create({ timelineContainer: { flexDirection: 'row', marginBottom: 12, }, timelineColumn: { width: 64, alignItems: 'center', paddingTop: 8, }, timeContainer: { marginBottom: 8, }, timeText: { fontSize: 12, fontWeight: '600', textAlign: 'center', }, timelineNode: { alignItems: 'center', flex: 1, }, timelineDot: { width: 24, height: 24, borderRadius: 12, justifyContent: 'center', alignItems: 'center', shadowColor: '#000', shadowOffset: { width: 0, height: 2 }, shadowOpacity: 0.1, shadowRadius: 4, elevation: 2, }, timelineLine: { width: 2, flex: 1, marginTop: 8, opacity: 0.3, }, card: { flex: 1, borderRadius: 16, padding: 16, shadowColor: '#000', shadowOffset: { width: 0, height: 2 }, shadowOpacity: 0.06, shadowRadius: 8, elevation: 2, }, cardWithTimeline: { marginLeft: 8, }, mainContent: { flexDirection: 'row', }, foodImageContainer: { width: 80, height: 80, borderRadius: 16, marginRight: 16, overflow: 'hidden', }, foodImage: { width: '100%', height: '100%', }, foodImagePlaceholder: { backgroundColor: '#F8F9FA', justifyContent: 'center', alignItems: 'center', }, foodInfoContainer: { flex: 1, }, headerRow: { flexDirection: 'row', justifyContent: 'space-between', alignItems: 'flex-start', marginBottom: 8, }, mealTypeContainer: { flex: 1, }, mealTypeBadge: { alignSelf: 'flex-start', paddingHorizontal: 8, paddingVertical: 4, borderRadius: 8, marginBottom: 4, }, mealTypeText: { fontSize: 12, fontWeight: '600', }, mealTime: { fontSize: 11, fontWeight: '500', }, moreButton: { padding: 4, marginLeft: 8, }, foodNameSection: { marginBottom: 12, }, foodName: { fontSize: 18, fontWeight: '700', lineHeight: 24, marginBottom: 2, }, portionInfo: { fontSize: 14, fontWeight: '500', }, nutritionGrid: { flexDirection: 'row', flexWrap: 'wrap', marginBottom: 8, }, nutritionItem: { width: '50%', marginBottom: 8, paddingRight: 8, }, nutritionItemHeader: { flexDirection: 'row', alignItems: 'center', marginBottom: 2, }, nutritionLabel: { fontSize: 12, fontWeight: '500', marginLeft: 4, }, nutritionValue: { fontSize: 14, fontWeight: '700', }, notesSection: { marginTop: 8, paddingTop: 12, borderTopWidth: 1, borderTopColor: 'rgba(0,0,0,0.06)', }, notesText: { fontSize: 13, fontWeight: '500', lineHeight: 18, fontStyle: 'italic', }, });