"use client";

import { motion } from "motion/react";
import { ChartFrame } from "./chart-frame";
import { linearScale, niceTicks, catColor } from "@/lib/chart-utils";

export type Bubble = { x: number; y: number; size: number; label?: string };

type BubbleChartProps = {
  data: Bubble[];
  /** Max bubble radius in drawing units. Default 34. */
  maxRadius?: number;
  width?: number;
  height?: number;
  className?: string;
};

const M = { top: 24, right: 28, bottom: 34, left: 44 };

/** BubbleChart — scatter with radius mapped to `size`; bubbles inflate (scale 0→1), staggered. */
export function BubbleChart({ data, maxRadius = 34, width = 600, height = 400, className }: BubbleChartProps) {
  const xs = data.map((d) => d.x);
  const ys = data.map((d) => d.y);
  const sizes = data.map((d) => d.size);
  const maxSize = Math.max(...sizes, 1);
  const sx = linearScale([Math.min(...xs), Math.max(...xs)], [M.left, width - M.right]);
  const sy = linearScale([Math.min(0, ...ys), Math.max(...ys)], [height - M.bottom, M.top]);
  const r = (s: number) => 6 + Math.sqrt(s / maxSize) * (maxRadius - 6);
  const yticks = niceTicks(Math.min(0, ...ys), Math.max(...ys), 4);

  return (
    <ChartFrame width={width} height={height} label="Gráfica de burbujas" className={className}>
      {({ inView, reduce }) => (
        <>
          {yticks.map((t) => (
            <line key={t} x1={M.left} x2={width - M.right} y1={sy(t)} y2={sy(t)} stroke="var(--ink-100)" />
          ))}
          {data.map((d, i) => {
            const cx = sx(d.x);
            const cy = sy(d.y);
            return (
              <g key={i}>
                <motion.circle
                  cx={cx}
                  cy={cy}
                  r={r(d.size)}
                  fill={catColor(i)}
                  fillOpacity={0.22}
                  stroke={catColor(i)}
                  strokeWidth={1.5}
                  initial={reduce ? false : { opacity: 0, scale: 0 }}
                  animate={inView ? { opacity: 1, scale: 1 } : { opacity: 0, scale: 0 }}
                  transition={{ duration: 0.6, delay: 0.1 + i * 0.08, ease: [0.22, 1, 0.36, 1] }}
                  style={{ transformOrigin: `${cx}px ${cy}px` }}
                />
                {d.label && (
                  <motion.text
                    x={cx}
                    y={cy}
                    textAnchor="middle"
                    dominantBaseline="middle"
                    fontSize={11}
                    fontWeight={700}
                    fill="var(--ink-800)"
                    initial={{ opacity: 0 }}
                    animate={inView ? { opacity: 1 } : { opacity: 0 }}
                    transition={{ duration: 0.3, delay: 0.1 + i * 0.08 + 0.45 }}
                  >
                    {d.label}
                  </motion.text>
                )}
              </g>
            );
          })}
        </>
      )}
    </ChartFrame>
  );
}
