'use client'; import { useState, useEffect } from 'react'; import { Box, Typography, Button, Paper, TextField, FormControl, InputLabel, Select, MenuItem, IconButton, Alert, CircularProgress, Card, CardContent, Dialog, DialogTitle, DialogContent, DialogContentText, DialogActions, Chip, Snackbar, ToggleButtonGroup, ToggleButton, FormLabel, } from '@mui/material'; import { ArrowBack, Refresh, Save, Delete, BabyChangingStation, Warning, CheckCircle, } from '@mui/icons-material'; import { useRouter } from 'next/navigation'; import { AppShell } from '@/components/layouts/AppShell/AppShell'; import { ProtectedRoute } from '@/components/common/ProtectedRoute'; import { useAuth } from '@/lib/auth/AuthContext'; import { trackingApi, Activity } from '@/lib/api/tracking'; import { childrenApi, Child } from '@/lib/api/children'; import { motion } from 'framer-motion'; import { formatDistanceToNow, format } from 'date-fns'; interface DiaperData { diaperType: 'wet' | 'dirty' | 'both' | 'dry'; conditions: string[]; hasRash: boolean; rashSeverity?: 'mild' | 'moderate' | 'severe'; } export default function DiaperTrackPage() { const router = useRouter(); const { user } = useAuth(); const [children, setChildren] = useState([]); const [selectedChild, setSelectedChild] = useState(''); // Diaper state const [timestamp, setTimestamp] = useState( format(new Date(), "yyyy-MM-dd'T'HH:mm") ); const [diaperType, setDiaperType] = useState<'wet' | 'dirty' | 'both' | 'dry'>('wet'); const [conditions, setConditions] = useState(['normal']); const [hasRash, setHasRash] = useState(false); const [rashSeverity, setRashSeverity] = useState<'mild' | 'moderate' | 'severe'>('mild'); // Common state const [notes, setNotes] = useState(''); const [recentDiapers, setRecentDiapers] = useState([]); const [loading, setLoading] = useState(false); const [childrenLoading, setChildrenLoading] = useState(true); const [diapersLoading, setDiapersLoading] = useState(false); const [error, setError] = useState(null); const [successMessage, setSuccessMessage] = useState(null); // Delete confirmation dialog const [deleteDialogOpen, setDeleteDialogOpen] = useState(false); const [activityToDelete, setActivityToDelete] = useState(null); const familyId = user?.families?.[0]?.familyId; const availableConditions = [ 'normal', 'soft', 'hard', 'watery', 'mucus', 'blood', ]; // Load children useEffect(() => { if (familyId) { loadChildren(); } }, [familyId]); // Load recent diapers when child is selected useEffect(() => { if (selectedChild) { loadRecentDiapers(); } }, [selectedChild]); const loadChildren = async () => { if (!familyId) return; try { setChildrenLoading(true); const childrenData = await childrenApi.getChildren(familyId); setChildren(childrenData); if (childrenData.length > 0) { setSelectedChild(childrenData[0].id); } } catch (err: any) { console.error('Failed to load children:', err); setError(err.response?.data?.message || 'Failed to load children'); } finally { setChildrenLoading(false); } }; const loadRecentDiapers = async () => { if (!selectedChild) return; try { setDiapersLoading(true); const activities = await trackingApi.getActivities(selectedChild, 'diaper'); // Sort by timestamp descending and take last 10 const sorted = activities.sort((a, b) => new Date(b.timestamp).getTime() - new Date(a.timestamp).getTime() ).slice(0, 10); setRecentDiapers(sorted); } catch (err: any) { console.error('Failed to load recent diapers:', err); } finally { setDiapersLoading(false); } }; const setTimeNow = () => { setTimestamp(format(new Date(), "yyyy-MM-dd'T'HH:mm")); }; const handleConditionToggle = (condition: string) => { setConditions((prev) => { if (prev.includes(condition)) { // Remove condition, but ensure at least one remains if (prev.length === 1) return prev; return prev.filter((c) => c !== condition); } else { return [...prev, condition]; } }); }; const handleSubmit = async () => { if (!selectedChild) { setError('Please select a child'); return; } // Validation if (!timestamp) { setError('Please enter timestamp'); return; } if (conditions.length === 0) { setError('Please select at least one condition'); return; } try { setLoading(true); setError(null); const data: DiaperData = { diaperType, conditions, hasRash, }; if (hasRash) { data.rashSeverity = rashSeverity; } await trackingApi.createActivity(selectedChild, { type: 'diaper', timestamp, data, notes: notes || undefined, }); setSuccessMessage('Diaper change logged successfully!'); // Reset form resetForm(); // Reload recent diapers await loadRecentDiapers(); } catch (err: any) { console.error('Failed to save diaper:', err); setError(err.response?.data?.message || 'Failed to save diaper change'); } finally { setLoading(false); } }; const resetForm = () => { setTimestamp(format(new Date(), "yyyy-MM-dd'T'HH:mm")); setDiaperType('wet'); setConditions(['normal']); setHasRash(false); setRashSeverity('mild'); setNotes(''); }; const handleDeleteClick = (activityId: string) => { setActivityToDelete(activityId); setDeleteDialogOpen(true); }; const handleDeleteConfirm = async () => { if (!activityToDelete) return; try { setLoading(true); await trackingApi.deleteActivity(activityToDelete); setSuccessMessage('Diaper change deleted successfully'); setDeleteDialogOpen(false); setActivityToDelete(null); await loadRecentDiapers(); } catch (err: any) { console.error('Failed to delete diaper:', err); setError(err.response?.data?.message || 'Failed to delete diaper change'); } finally { setLoading(false); } }; const getDiaperTypeColor = (type: string) => { switch (type) { case 'wet': return '#2196f3'; // blue case 'dirty': return '#795548'; // brown case 'both': return '#ff9800'; // orange case 'dry': return '#4caf50'; // green default: return '#757575'; // grey } }; const getDiaperTypeIcon = (type: string) => { switch (type) { case 'wet': return '💧'; case 'dirty': return '💩'; case 'both': return '💧💩'; case 'dry': return '✨'; default: return '🍼'; } }; const getDiaperDetails = (activity: Activity) => { const data = activity.data as DiaperData; const typeLabel = data.diaperType.charAt(0).toUpperCase() + data.diaperType.slice(1); const conditionsLabel = data.conditions.join(', '); let details = `${typeLabel} - ${conditionsLabel}`; if (data.hasRash) { details += ` - Rash (${data.rashSeverity})`; } return details; }; const getRashSeverityColor = (severity: string) => { switch (severity) { case 'mild': return 'warning'; case 'moderate': return 'error'; case 'severe': return 'error'; default: return 'default'; } }; if (childrenLoading) { return ( ); } if (!familyId || children.length === 0) { return ( Please add a child first before tracking diaper changes. ); } return ( router.back()} sx={{ mr: 2 }}> Track Diaper Change {error && ( setError(null)}> {error} )} {/* Child Selector */} {children.length > 1 && ( Select Child )} {/* Main Form */} {/* Icon Header */} {/* Timestamp */} Time setTimestamp(e.target.value)} InputLabelProps={{ shrink: true }} /> {/* Diaper Type */} Diaper Type { if (value !== null) { setDiaperType(value); } }} fullWidth > 💧 Wet 💩 Dirty 💧💩 Both Dry {/* Condition Selector */} Condition (select all that apply) {availableConditions.map((condition) => ( handleConditionToggle(condition)} color={conditions.includes(condition) ? 'primary' : 'default'} variant={conditions.includes(condition) ? 'filled' : 'outlined'} sx={{ cursor: 'pointer' }} /> ))} {/* Rash Indicator */} Diaper Rash? {/* Rash Severity */} {hasRash && ( Diaper rash detected. Consider applying diaper rash cream and consulting your pediatrician if it persists. Rash Severity )} {/* Notes Field */} setNotes(e.target.value)} sx={{ mb: 3 }} placeholder="Color, consistency, or any concerns..." /> {/* Submit Button */} {/* Recent Diapers */} Recent Diaper Changes {diapersLoading ? ( ) : recentDiapers.length === 0 ? ( No diaper changes yet ) : ( {recentDiapers.map((activity, index) => { const data = activity.data as DiaperData; return ( {getDiaperTypeIcon(data.diaperType)} Diaper Change {data.hasRash && ( } label={`Rash: ${data.rashSeverity}`} size="small" color={getRashSeverityColor(data.rashSeverity || 'mild') as any} /> )} {getDiaperDetails(activity)} {activity.notes && ( {activity.notes} )} handleDeleteClick(activity.id)} disabled={loading} > ); })} )} {/* Delete Confirmation Dialog */} setDeleteDialogOpen(false)} > Delete Diaper Change? Are you sure you want to delete this diaper change? This action cannot be undone. {/* Success Snackbar */} setSuccessMessage(null)} message={successMessage} /> ); }