import { useMemo } from 'react'; import { Chart, ChartProps } from './Chart'; export interface LineChartData { label: string; value: number; } export interface LineChartProps extends Omit { data: LineChartData[]; xAxisLabel?: string; yAxisLabel?: string; color?: string; showGrid?: boolean; showDots?: boolean; } /** * Composant LineChart pour visualisation de données en ligne. */ export function LineChart({ data, xAxisLabel, yAxisLabel, color = '#3b82f6', showGrid = true, showDots = true, height = 300, className, ...chartProps }: LineChartProps) { const { normalizedData, padding } = useMemo(() => { if (data.length === 0) { return { normalizedData: [], padding: 40 }; } const values = data.map((d) => d.value); const max = Math.max(...values, 0); const min = Math.min(...values, 0); const range = max - min || 1; const padding = 40; const chartHeight = height - padding * 2; const chartWidth = 100 - (padding / 10) * 2; const normalizedData = data.map((item, index) => { const x = (index / (data.length - 1 || 1)) * chartWidth + padding / 10; const y = chartHeight - ((item.value - min) / range) * chartHeight + padding / 10; return { ...item, x, y: y / 10, // Convert to percentage }; }); return { normalizedData, padding }; }, [data, height]); if (data.length === 0) { return (
Aucune donnée disponible
); } const pathData = normalizedData .map((point, index) => `${index === 0 ? 'M' : 'L'} ${point.x} ${point.y}`) .join(' '); const strokeWidth = 2; const dotRadius = 4; return ( {/* Grid lines */} {showGrid && ( {[0, 25, 50, 75, 100].map((y) => ( ))} )} {/* Y-axis labels */} {yAxisLabel && ( {yAxisLabel} )} {/* X-axis labels */} {xAxisLabel && ( {xAxisLabel} )} {/* Line */} {/* Dots */} {showDots && normalizedData.map((point, index) => ( {point.label}: {data[index].value} ))} ); }