const { useEffect, useRef, useState } = React;

/* ---------- Portal — escapes transformed ancestors so fixed overlays anchor to the viewport ---------- */
const Portal = ({ children }) => {
  const elRef = useRef(null);
  if (!elRef.current) elRef.current = document.createElement('div');
  useEffect(() => {
    const el = elRef.current;
    document.body.appendChild(el);
    return () => { document.body.removeChild(el); };
  }, []);
  return ReactDOM.createPortal(children, elRef.current);
};

/* ---------- Icon (lucide bridge) ---------- */
const Icon = ({ name, className, onClick }) => {
  const spanRef = useRef(null);

  useEffect(() => {
    if (spanRef.current && window.lucide) {
      spanRef.current.innerHTML = `<i data-lucide="${name}" class="${className || ''}"></i>`;
      try { window.lucide.createIcons(); } catch (err) {}
    }
  }, [name, className]);

  return (
    <span
      ref={spanRef}
      onClick={onClick}
      className={`inline-flex items-center justify-center shrink-0 ${onClick ? 'cursor-pointer' : 'pointer-events-none'}`}
    />
  );
};

/* ---------- Badge ---------- */
const Badge = ({ children, variant = 'default', className = '' }) => {
  const variants = {
    default: "bg-slate-900 text-slate-50",
    secondary: "bg-slate-100 text-slate-700 border border-slate-200",
    outline: "text-slate-600 border border-slate-200 bg-white shadow-sm",
    gold: "bg-brand-50 text-brand-700 border border-brand-200",
    destructive: "bg-red-50 text-red-700 border border-red-200",
    success: "bg-emerald-50 text-emerald-700 border border-emerald-200",
    warning: "bg-amber-50 text-amber-700 border border-amber-200"
  };

  return (
    <span className={`inline-flex items-center rounded-md px-2 py-0.5 text-[11px] font-bold tracking-wide transition-colors ${variants[variant]} ${className}`}>
      {children}
    </span>
  );
};

/* ---------- Section kicker — uppercase tracked label with gold tick ---------- */
const Kicker = ({ children, className = '' }) => (
  <div className={`flex items-center gap-2.5 ${className}`}>
    <span className="h-[14px] w-[3px] rounded-full bg-gold" />
    <span className="text-[11px] font-bold uppercase tracking-kicker text-slate-500">{children}</span>
  </div>
);

/* ---------- Brandmark ---------- */
const Brandmark = ({ size = 38 }) => (
  <div
    className="relative rounded-xl flex items-center justify-center text-slate-50 shrink-0 ink-panel shadow-md"
    style={{ width: size, height: size }}
  >
    <Icon name="hexagon" className="w-1/2 h-1/2 text-brand-300" />
    <span className="absolute inset-0 rounded-xl ring-1 ring-inset ring-white/10" />
  </div>
);

/* ---------- Status dot (pulsing) ---------- */
const LiveDot = ({ tone = 'emerald' }) => {
  const map = { emerald: 'bg-emerald-500', gold: 'bg-brand-500', red: 'bg-red-500' };
  return (
    <span className="relative flex h-2 w-2">
      <span className={`animate-ping absolute inline-flex h-full w-full rounded-full opacity-60 ${map[tone]}`} />
      <span className={`relative inline-flex rounded-full h-2 w-2 ${map[tone]}`} />
    </span>
  );
};

/* ---------- Animated count-up number ---------- */
const CountUp = ({ value, decimals = 0, duration = 1100, prefix = '', suffix = '' }) => {
  const [display, setDisplay] = useState(0);
  const raf = useRef(null);

  useEffect(() => {
    const start = performance.now();
    const from = 0;
    const ease = (t) => 1 - Math.pow(1 - t, 3);
    const tick = (now) => {
      const p = Math.min(1, (now - start) / duration);
      setDisplay(from + (value - from) * ease(p));
      if (p < 1) raf.current = requestAnimationFrame(tick);
    };
    raf.current = requestAnimationFrame(tick);
    return () => cancelAnimationFrame(raf.current);
  }, [value, duration]);

  const formatted = Number(display).toLocaleString('en-US', {
    minimumFractionDigits: decimals,
    maximumFractionDigits: decimals
  });
  return <span className="tnum">{prefix}{formatted}{suffix}</span>;
};

/* ---------- Delta chip ---------- */
const Delta = ({ value, tone = 'pos' }) => {
  const up = value >= 0;
  const good = tone === 'pos' ? up : !up;
  return (
    <span className={`inline-flex items-center gap-1 text-[11px] font-bold tnum ${good ? 'text-emerald-600' : 'text-red-600'}`}>
      <Icon name={up ? 'trending-up' : 'trending-down'} className="w-3 h-3" />
      {up ? '+' : ''}{value}%
    </span>
  );
};

/* ---------- Sparkline — fluid width, never collides with the value it sits beside ---------- */
const Sparkline = ({ data, height = 32, tone = '#b9842a' }) => {
  const W = 120, H = height;
  const min = Math.min(...data), max = Math.max(...data);
  const span = max - min || 1;
  const pts = data.map((d, i) => [
    (i / (data.length - 1)) * W,
    H - 3 - ((d - min) / span) * (H - 6)
  ]);
  const line = pts.map((p, i) => `${i === 0 ? 'M' : 'L'}${p[0].toFixed(1)} ${p[1].toFixed(1)}`).join(' ');
  const area = `${line} L${W} ${H} L0 ${H} Z`;
  const id = 'sp' + Math.random().toString(36).slice(2, 7);
  return (
    <svg viewBox={`0 0 ${W} ${H}`} width="100%" height={H} preserveAspectRatio="none" className="block w-full" style={{ height: H }}>
      <defs>
        <linearGradient id={id} x1="0" y1="0" x2="0" y2="1">
          <stop offset="0%" stopColor={tone} stopOpacity="0.20" />
          <stop offset="100%" stopColor={tone} stopOpacity="0" />
        </linearGradient>
      </defs>
      <path d={area} fill={`url(#${id})`} />
      <path d={line} fill="none" stroke={tone} strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" vectorEffect="non-scaling-stroke" className="draw-line" />
      <circle cx={pts[pts.length - 1][0]} cy={pts[pts.length - 1][1]} r="2.4" fill={tone} vectorEffect="non-scaling-stroke" />
    </svg>
  );
};

/* ---------- Donut / ring chart ---------- */
const Donut = ({ segments, size = 168, stroke = 20 }) => {
  const r = (size - stroke) / 2;
  const c = 2 * Math.PI * r;
  const total = segments.reduce((s, x) => s + x.value, 0);
  let offset = 0;
  return (
    <svg width={size} height={size} viewBox={`0 0 ${size} ${size}`} className="-rotate-90">
      <circle cx={size / 2} cy={size / 2} r={r} fill="none" stroke="#efece4" strokeWidth={stroke} />
      {segments.map((seg, i) => {
        const len = (seg.value / total) * c;
        const dash = `${len} ${c - len}`;
        const el = (
          <circle
            key={i}
            cx={size / 2} cy={size / 2} r={r}
            fill="none" stroke={seg.color} strokeWidth={stroke}
            strokeDasharray={dash} strokeDashoffset={-offset}
            strokeLinecap="butt"
            style={{ transition: 'stroke-dasharray 0.9s cubic-bezier(0.16,1,0.3,1)' }}
          />
        );
        offset += len;
        return el;
      })}
    </svg>
  );
};

/* ---------- Trend chart (area + line, dual series) ---------- */
const TrendChart = ({ labels, primary, secondary, height = 200 }) => {
  const W = 640, H = height, padX = 16, padY = 22;
  const max = Math.max(...primary, ...secondary) * 1.12;
  const x = (i) => padX + (i / (labels.length - 1)) * (W - padX * 2);
  const y = (v) => H - padY - (v / max) * (H - padY * 2);
  const toPath = (arr) => arr.map((v, i) => `${i === 0 ? 'M' : 'L'}${x(i).toFixed(1)} ${y(v).toFixed(1)}`).join(' ');
  const areaPath = `${toPath(primary)} L${x(primary.length - 1)} ${H - padY} L${x(0)} ${H - padY} Z`;

  return (
    <svg viewBox={`0 0 ${W} ${H}`} className="w-full" style={{ height }} preserveAspectRatio="none">
      <defs>
        <linearGradient id="trendFill" x1="0" y1="0" x2="0" y2="1">
          <stop offset="0%" stopColor="#b9842a" stopOpacity="0.20" />
          <stop offset="100%" stopColor="#b9842a" stopOpacity="0" />
        </linearGradient>
      </defs>
      {[0.25, 0.5, 0.75, 1].map((g, i) => (
        <line key={i} x1={padX} x2={W - padX} y1={padY + g * (H - padY * 2)} y2={padY + g * (H - padY * 2)} stroke="#e3ddd0" strokeWidth="1" strokeDasharray="2 4" />
      ))}
      <path d={areaPath} fill="url(#trendFill)" />
      <path d={toPath(secondary)} fill="none" stroke="#cfc7b5" strokeWidth="2" strokeDasharray="4 4" className="draw-line" />
      <path d={toPath(primary)} fill="none" stroke="#b9842a" strokeWidth="2.6" strokeLinecap="round" strokeLinejoin="round" className="draw-line" />
      {primary.map((v, i) => <circle key={i} cx={x(i)} cy={y(v)} r="3" fill="#fff" stroke="#b9842a" strokeWidth="2" />)}
      {labels.map((l, i) => (
        <text key={i} x={x(i)} y={H - 4} textAnchor="middle" fontSize="10" fill="#a99f8b" fontFamily="JetBrains Mono">{l}</text>
      ))}
    </svg>
  );
};

/* ---------- Horizontal bar meter ---------- */
const BarMeter = ({ value, max = 100, tone = 'gold' }) => {
  const map = { gold: 'bg-brand-500', risk: 'bg-red-500', warn: 'bg-amber-500', muted: 'bg-slate-300', ink: 'bg-slate-900' };
  return (
    <div className="h-2 w-full rounded-full bg-slate-100 overflow-hidden">
      <div
        className={`h-full rounded-full ${map[tone] || map.gold}`}
        style={{ width: `${(value / max) * 100}%`, transition: 'width 0.9s cubic-bezier(0.16,1,0.3,1)' }}
      />
    </div>
  );
};

/* ---------- Vertical edge connector ---------- */
const VerticalEdge = ({ height = 'h-6' }) => (
  <div className="flex justify-center w-full">
    <div className={`w-[2px] bg-slate-300 ${height} arrow-down relative z-0`} />
  </div>
);
