"use client";

// JARVIS orb. Pure SVG so it's perfectly crisp on retina and doesn't carry
// a canvas runtime cost. The orb has four rings:
//   - core: onyx fill (#0F0F11) with subtle gradient
//   - inner pulse: bone (#DCDCD8) opacity-modulated by audio level
//   - middle halo: graphite (#4A4A4D) rotating slowly when live
//   - outer crown: mars red (#C2452A) — visible only on speaking + approval

import { useEffect, useState } from 'react';

export default function VoiceOrb({ state = 'idle', audioLevel = 0, size = 220, muted = false }) {
  const [phase, setPhase] = useState(0);
  useEffect(() => {
    if (state === 'idle') return;
    let raf = 0;
    let last = performance.now();
    const tick = (now) => {
      const dt = (now - last) / 1000;
      last = now;
      const speed = state === 'live' ? 1 : state === 'connecting' ? 2.4 : 0.6;
      setPhase(p => (p + dt * speed) % (Math.PI * 2));
      raf = requestAnimationFrame(tick);
    };
    raf = requestAnimationFrame(tick);
    return () => cancelAnimationFrame(raf);
  }, [state]);

  // Audio level → 1.0 ring scale. Idle has a tiny breath so the orb is alive.
  const breath = state === 'idle' ? 0 : 0.04 * Math.sin(phase * 2);
  const drive = state === 'live' ? Math.max(audioLevel, 0.08) : state === 'connecting' ? 0.16 : 0.04;
  const innerR = 56 + drive * 28;
  const middleR = 80 + (drive * 0.6 + breath) * 22;
  const outerR = 96 + (drive * 0.35 + breath) * 14;
  const rotation = (phase * 180) / Math.PI;

  const showMars = state === 'live' && audioLevel > 0.42;
  const showApproval = state === 'approval';
  const showError = state === 'error';

  return (
    <div className={`voice-orb voice-orb--${state}` + (muted ? ' voice-orb--muted' : '')} aria-hidden="true">
      <svg width={size} height={size} viewBox="0 0 220 220">
        <defs>
          <radialGradient id="orbCore" cx="50%" cy="40%" r="62%">
            <stop offset="0%" stopColor="#ffffff" />
            <stop offset="42%" stopColor="#fff5f0" />
            <stop offset="100%" stopColor="#fbe5e0" />
          </radialGradient>
          <radialGradient id="orbInner" cx="50%" cy="50%" r="50%">
            <stop offset="0%" stopColor="#ffffff" stopOpacity="0.75" />
            <stop offset="60%" stopColor="#ffffff" stopOpacity="0.18" />
            <stop offset="100%" stopColor="#ffffff" stopOpacity="0" />
          </radialGradient>
          <radialGradient id="orbMars" cx="50%" cy="50%" r="50%">
            <stop offset="0%" stopColor="#C2452A" stopOpacity="0.65" />
            <stop offset="100%" stopColor="#C2452A" stopOpacity="0" />
          </radialGradient>
          <radialGradient id="orbError" cx="50%" cy="50%" r="50%">
            <stop offset="0%" stopColor="#b91c1c" stopOpacity="0.55" />
            <stop offset="100%" stopColor="#b91c1c" stopOpacity="0" />
          </radialGradient>
        </defs>

        {/* Outer crown — ivory when speaking strongly, soft ivory otherwise */}
        <circle
          cx="110"
          cy="110"
          r={outerR}
          fill="none"
          stroke={showError ? '#fff' : '#ffffff'}
          strokeOpacity={showMars ? 0.80 : 0.30}
          strokeWidth="1.25"
          style={{ transformOrigin: '110px 110px', transform: `rotate(${rotation}deg)` }}
        />

        {/* Middle halo */}
        <circle
          cx="110"
          cy="110"
          r={middleR}
          fill="none"
          stroke="#ffffff"
          strokeOpacity="0.35"
          strokeWidth="1"
          strokeDasharray="2 4"
          style={{ transformOrigin: '110px 110px', transform: `rotate(${-rotation * 0.7}deg)` }}
        />

        {/* Approval / waiting pulse — only when an approval banner is up */}
        {showApproval && (
          <circle
            cx="110"
            cy="110"
            r={outerR + 6}
            fill="none"
            stroke="#ffffff"
            strokeOpacity={0.55 + 0.25 * Math.sin(phase * 4)}
            strokeWidth="1.5"
          />
        )}

        {/* Inner glow tied to audio level */}
        <circle cx="110" cy="110" r={innerR + 18} fill="url(#orbInner)" />
        {showError && <circle cx="110" cy="110" r={innerR + 24} fill="url(#orbError)" />}
        {showMars && <circle cx="110" cy="110" r={innerR + 12} fill="url(#orbMars)" />}

        {/* Core orb */}
        <circle cx="110" cy="110" r={innerR} fill="url(#orbCore)" />

        {/* Highlight to give the orb dimension */}
        <ellipse cx="92" cy="92" rx={innerR * 0.55} ry={innerR * 0.25} fill="#fff" fillOpacity="0.55" />

        {/* madarX brand mark centered on the core. Scale stays fixed against
            the base core radius (56) so the X doesn't breathe with the audio
            meter — the orb pulses, the brand mark stays still. */}
        {(() => {
          const scale = (innerR * 0.62) / 50;
          const offset = 110 - 50 * scale;
          const strokeW = 3 / scale;
          return (
            <g transform={`translate(${offset} ${offset}) scale(${scale})`} opacity={showError ? 0.55 : 0.92}>
              <path
                d="M 85.32 31.22 A 40 40 0 1 1 78.78 22.20"
                stroke="#0F0F11"
                strokeWidth={strokeW}
                fill="none"
              />
              <line x1="21.72" y1="21.72" x2="78.28" y2="78.28" stroke="#0F0F11" strokeWidth={strokeW} strokeLinecap="round" />
              <line x1="21.72" y1="78.28" x2="78.28" y2="21.72" stroke="#0F0F11" strokeWidth={strokeW} strokeLinecap="round" />
              <circle cx="82.36" cy="26.49" r="5" fill="#C2452A" />
            </g>
          );
        })()}

        {/* Muted overlay — diagonal stroke across the orb */}
        {muted && (
          <line
            x1={110 - innerR * 0.7}
            y1={110 - innerR * 0.7}
            x2={110 + innerR * 0.7}
            y2={110 + innerR * 0.7}
            stroke="#7c2b19"
            strokeOpacity="0.85"
            strokeWidth="3.5"
            strokeLinecap="round"
          />
        )}
      </svg>
    </div>
  );
}
