'use client'; import React, { useState } from 'react'; import { Card, CardContent, CardHeader, CardTitle } from '@/components/ui/card'; import { Badge } from '@/components/ui/badge'; import { Progress } from '@/components/ui/progress'; import { Tabs, TabsContent, TabsList, TabsTrigger } from '@/components/ui/tabs'; import { Alert, AlertDescription } from '@/components/ui/alert'; import { LineChart, Line, XAxis, YAxis, CartesianGrid, Tooltip, Legend, ResponsiveContainer, ReferenceLine, Area, AreaChart, } from 'recharts'; import { Ruler, Weight, TrendingUp, Baby, AlertCircle, ChevronUp, ChevronDown, Minus, } from 'lucide-react'; import { GrowthAnalysis, GrowthPercentile } from '@/lib/api/analytics'; import { format } from 'date-fns'; interface GrowthPercentileChartProps { data: GrowthAnalysis | null; loading?: boolean; error?: Error | null; } export function GrowthPercentileChart({ data, loading, error }: GrowthPercentileChartProps) { const [selectedMetric, setSelectedMetric] = useState<'weight' | 'height' | 'headCircumference'>('weight'); if (loading) { return (
Loading growth analysis...
); } if (error) { return ( Error loading growth data ); } if (!data) { return null; } const getPercentileColor = (percentile: number) => { if (percentile < 5 || percentile > 95) return 'text-red-600'; if (percentile < 15 || percentile > 85) return 'text-yellow-600'; return 'text-green-600'; }; const getPercentileBadge = (percentile: number) => { if (percentile < 5 || percentile > 95) return 'bg-red-100 text-red-800'; if (percentile < 15 || percentile > 85) return 'bg-yellow-100 text-yellow-800'; return 'bg-green-100 text-green-800'; }; const getVelocityIcon = (value: number) => { if (value > 0) return ; if (value < 0) return ; return ; }; const formatMeasurement = (value: number | undefined, metric: string) => { if (!value) return 'N/A'; switch (metric) { case 'weight': return `${value.toFixed(1)} kg`; case 'height': return `${value.toFixed(1)} cm`; case 'headCircumference': return `${value.toFixed(1)} cm`; default: return value.toFixed(1); } }; // Prepare chart data const chartData = data.growthCurve.measurements.map(m => ({ date: format(m.date, 'MMM dd'), weight: m.weight, height: m.height, headCircumference: m.headCircumference, p3: data.growthCurve.percentileCurves[selectedMetric]?.p3?.[0], p15: data.growthCurve.percentileCurves[selectedMetric]?.p15?.[0], p50: data.growthCurve.percentileCurves[selectedMetric]?.p50?.[0], p85: data.growthCurve.percentileCurves[selectedMetric]?.p85?.[0], p97: data.growthCurve.percentileCurves[selectedMetric]?.p97?.[0], })); return ( Growth Analysis {data.alerts.length > 0 && ( {data.alerts.length} Alert{data.alerts.length > 1 ? 's' : ''} )} {/* Current Percentiles */} {data.currentPercentiles && (
{data.currentPercentiles.weight && (
Weight

{data.currentPercentiles.weight.value.toFixed(1)} kg

{Math.round(data.currentPercentiles.weight.percentile)}th percentile

{data.currentPercentiles.weight.interpretation}

)} {data.currentPercentiles.height && (
Height

{data.currentPercentiles.height.value.toFixed(1)} cm

{Math.round(data.currentPercentiles.height.percentile)}th percentile

{data.currentPercentiles.height.interpretation}

)} {data.currentPercentiles.headCircumference && (
Head Circ.

{data.currentPercentiles.headCircumference.value.toFixed(1)} cm

{Math.round(data.currentPercentiles.headCircumference.percentile)}th percentile

{data.currentPercentiles.headCircumference.interpretation}

)}
)} {/* Growth Velocity */} {data.growthVelocity && (

Growth Velocity

{data.growthVelocity.weightVelocity && (
Weight Gain
{getVelocityIcon(data.growthVelocity.weightVelocity.value)} {data.growthVelocity.weightVelocity.value.toFixed(2)} {data.growthVelocity.weightVelocity.unit}
)} {data.growthVelocity.heightVelocity && (
Height Growth
{getVelocityIcon(data.growthVelocity.heightVelocity.value)} {data.growthVelocity.heightVelocity.value.toFixed(2)} {data.growthVelocity.heightVelocity.unit}
)}

{data.growthVelocity.interpretation}

)} {/* Growth Chart */} setSelectedMetric(v as any)}> Weight Height Head Circ. {/* Percentile reference lines */} {/* Child's measurements */} {/* Alerts */} {data.alerts.length > 0 && (

Growth Alerts

{data.alerts.map((alert, index) => (

{alert.message}

{alert.action}

))}
)} {/* Recommendations */} {data.recommendations.length > 0 && (

Recommendations

    {data.recommendations.map((rec, index) => (
  • {rec}
  • ))}
)}
); }