import { useState } from 'react'
import styles from './AreaChart.module.css'
import {
  computeYScale,
  computeXScale,
  seriesPoints,
  seriesPath,
  formatAxisLabel,
  CHART_COLORS,
  type ChartSeries,
} from '../_chart-utils'

interface Threshold {
  value: number
  label: string
}

interface AreaChartProps {
  series: ChartSeries[]
  xLabel?: string
  yLabel?: string
  threshold?: Threshold
  height?: number
  width?: number
  className?: string
}

const Y_TICK_COUNT = 4
const DIMS = {
  paddingTop: 12,
  paddingRight: 16,
  paddingBottom: 28,
  paddingLeft: 48,
}

export function AreaChart({
  series,
  xLabel,
  yLabel,
  threshold,
  height = 200,
  width = 400,
  className,
}: AreaChartProps) {
  const [tooltip, setTooltip] = useState<{
    x: number
    y: number
    values: { label: string; value: number; color: string }[]
  } | null>(null)

  const dims = { ...DIMS, width, height }
  const allData = series.flatMap((s) => s.data)

  if (allData.length === 0) {
    return <div className={`${styles.empty} ${className ?? ''}`}>No data</div>
  }

  const { max, toY } = computeYScale(series, dims, threshold?.value)
  const { toX } = computeXScale(series, dims)
  const plotH = height - dims.paddingTop - dims.paddingBottom
  const plotW = width - dims.paddingLeft - dims.paddingRight
  const bottomY = dims.paddingTop + plotH

  // Y-axis ticks
  const yTicks = Array.from({ length: Y_TICK_COUNT + 1 }, (_, i) =>
    Math.round((max / Y_TICK_COUNT) * i),
  )

  // X-axis ticks (first, middle, last)
  const firstSeries = series[0]
  const xSamples =
    firstSeries && firstSeries.data.length > 0
      ? [
          firstSeries.data[0].x,
          firstSeries.data[Math.floor(firstSeries.data.length / 2)]?.x,
          firstSeries.data[firstSeries.data.length - 1].x,
        ].filter(Boolean)
      : []

  function handleMouseMove(e: React.MouseEvent<SVGSVGElement>) {
    const rect = e.currentTarget.getBoundingClientRect()
    const mx = e.clientX - rect.left
    const my = e.clientY - rect.top

    // Find closest x value
    const pctX = (mx - dims.paddingLeft) / plotW
    const values = series.map((s, i) => {
      const idx = Math.round(pctX * (s.data.length - 1))
      const clamped = Math.max(0, Math.min(s.data.length - 1, idx))
      const pt = s.data[clamped]
      return {
        label: s.label,
        value: pt?.y ?? 0,
        color: s.color ?? CHART_COLORS[i % CHART_COLORS.length],
      }
    })

    setTooltip({ x: mx, y: my, values })
  }

  return (
    <div className={`${styles.wrapper} ${className ?? ''}`}>
      {yLabel && <div className={styles.yLabel}>{yLabel}</div>}
      <svg
        width={width}
        height={height}
        viewBox={`0 0 ${width} ${height}`}
        className={styles.svg}
        onMouseMove={handleMouseMove}
        onMouseLeave={() => setTooltip(null)}
        aria-label="Area chart"
        role="img"
      >
        {/* Grid lines */}
        {yTicks.map((val) => {
          const y = toY(val)
          return (
            <g key={val}>
              <line
                x1={dims.paddingLeft}
                y1={y}
                x2={width - dims.paddingRight}
                y2={y}
                className={styles.gridLine}
              />
              <text x={dims.paddingLeft - 6} y={y + 4} className={styles.axisLabel} textAnchor="end">
                {formatAxisLabel(val)}
              </text>
            </g>
          )
        })}

        {/* X-axis labels */}
        {xSamples.map((xVal, i) => {
          const xPos = toX(xVal)
          const xv = xVal instanceof Date ? xVal : new Date(xVal as number)
          const label =
            xVal instanceof Date || (typeof xVal === 'number' && xVal > 1e10)
              ? xv.toLocaleTimeString([], { hour: '2-digit', minute: '2-digit' })
              : formatAxisLabel(xVal as number)
          const anchor = i === 0 ? 'start' : i === xSamples.length - 1 ? 'end' : 'middle'
          return (
            <text
              key={i}
              x={xPos}
              y={height - dims.paddingBottom + 16}
              className={styles.axisLabel}
              textAnchor={anchor}
            >
              {label}
            </text>
          )
        })}

        {/* SLA threshold line */}
        {threshold && (
          <g>
            <line
              x1={dims.paddingLeft}
              y1={toY(threshold.value)}
              x2={width - dims.paddingRight}
              y2={toY(threshold.value)}
              className={styles.thresholdLine}
            />
            <text
              x={width - dims.paddingRight - 4}
              y={toY(threshold.value) - 4}
              className={styles.thresholdLabel}
              textAnchor="end"
            >
              {threshold.label}
            </text>
          </g>
        )}

        {/* Area fills */}
        {series.map((s, i) => {
          const color = s.color ?? CHART_COLORS[i % CHART_COLORS.length]
          const areaD = seriesPath(s, toX, toY, bottomY)
          return (
            <path
              key={`area-${i}`}
              d={areaD}
              fill={color}
              className={styles.area}
            />
          )
        })}

        {/* Lines */}
        {series.map((s, i) => {
          const color = s.color ?? CHART_COLORS[i % CHART_COLORS.length]
          const pts = seriesPoints(s, toX, toY)
          return (
            <polyline
              key={`line-${i}`}
              points={pts}
              fill="none"
              stroke={color}
              className={styles.line}
            />
          )
        })}

        {/* Crosshair */}
        {tooltip && (
          <line
            x1={tooltip.x}
            y1={dims.paddingTop}
            x2={tooltip.x}
            y2={bottomY}
            className={styles.crosshair}
          />
        )}
      </svg>

      {/* Tooltip */}
      {tooltip && (
        <div
          className={styles.tooltip}
          style={{
            left: tooltip.x + 12,
            top: tooltip.y,
          }}
        >
          {tooltip.values.map((v) => (
            <div key={v.label} className={styles.tooltipRow}>
              <span className={styles.tooltipDot} style={{ background: v.color }} />
              <span className={styles.tooltipLabel}>{v.label}:</span>
              <span className={styles.tooltipValue}>{formatAxisLabel(v.value)}</span>
            </div>
          ))}
        </div>
      )}

      {/* Legend */}
      {series.length > 1 && (
        <div className={styles.legend}>
          {series.map((s, i) => (
            <div key={s.label} className={styles.legendItem}>
              <span
                className={styles.legendDot}
                style={{ background: s.color ?? CHART_COLORS[i % CHART_COLORS.length] }}
              />
              <span className={styles.legendLabel}>{s.label}</span>
            </div>
          ))}
        </div>
      )}

      {xLabel && <div className={styles.xLabel}>{xLabel}</div>}
    </div>
  )
}
