"use client" import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card" import { ResponsiveContainer, ScatterChart, Scatter, XAxis, YAxis, Tooltip, CartesianGrid } from "recharts" import { format } from "date-fns" import { Badge } from "@/components/ui/badge" import { TrendingUp, Info } from "lucide-react" interface Performance { id: number show_date: string avg_rating: number venue_name: string venue_city: string venue_state: string | null show_id: number } interface SongEvolutionChartProps { performances: Performance[] title?: string } const CustomTooltip = ({ active, payload }: { active?: boolean; payload?: any[] }) => { if (active && payload && payload.length) { const data = payload[0].payload return ( {format(new Date(data.date), "MMM d, yyyy")} {data.venue} Rating: Rating: {data.rating.toFixed(1)} ) } return null } export function SongEvolutionChart({ performances, title = "Rating Evolution" }: SongEvolutionChartProps) { // Filter out unrated performances to keep chart clean? // Or keep them as 0? Usually 0 skews the chart. Let's filter > 0 for "Evolution of Quality". const ratedPerfs = performances .filter(p => p.avg_rating > 0) .map(p => ({ id: p.id, date: new Date(p.show_date).getTime(), rating: p.avg_rating, venue: `${p.venue_name}, ${p.venue_city}`, fullDate: p.show_date })) .sort((a, b) => a.date - b.date) if (ratedPerfs.length < 2) { return null } // Calculate trend? Simple linear/avg for now. const average = ratedPerfs.reduce((acc, curr) => acc + curr.rating, 0) / ratedPerfs.length return ( {title} {ratedPerfs.length > 5 && ( Avg: {average.toFixed(1)} )} format(new Date(unixTime), "yyyy")} stroke="hsl(var(--muted-foreground))" fontSize={12} tickLine={false} axisLine={false} dy={10} /> } cursor={{ strokeDasharray: '3 3' }} /> ) }