// Animated connector lines + flow dots. Used to make scenes feel "alive" —
// lines drawing between elements, particles traveling along the paths.

// ── ConnectorPath ───────────────────────────────────────────────────────────
// Renders an animated SVG path between two points with a "drawing" stroke
// (dash-offset reveal) and optional flow dots moving along the path.
//
// Props:
//   from, to: {x, y}     anchor points (absolute coords in the stage)
//   curvature: 0..1      how curved (S-shape) the path is
//   bend: number         which axis to bend on ('y' for horizontal-ish, 'x' for vertical-ish)
//   draw: 0..1           path reveal progress
//   color, width         stroke style
//   dotted: bool         dashed style
//   dotsCount: int       number of flow dots
//   dotProgress: 0..1    base time fraction for dot motion (multiplied per dot)
//   dotColor: string
function ConnectorPath({
  from, to,
  curvature = 0.35,
  bend = 'auto',
  draw = 1,
  color = AKDMI.violet,
  width = 1.5,
  dashed = false,
  dotsCount = 0,
  dotProgress = 0,
  dotColor = null,
  dotSize = 5,
  opacity = 1,
  glow = false,
}) {
  const dx = to.x - from.x;
  const dy = to.y - from.y;
  const len = Math.sqrt(dx * dx + dy * dy);
  // Decide bend axis: if more horizontal, bend in Y. If vertical, bend in X.
  const useY = bend === 'auto' ? Math.abs(dx) > Math.abs(dy) : bend === 'y';
  const midX = (from.x + to.x) / 2;
  const midY = (from.y + to.y) / 2;
  // Control points for cubic Bezier
  let c1x, c1y, c2x, c2y;
  if (useY) {
    const off = len * curvature;
    c1x = from.x + dx * 0.33;
    c1y = from.y - off;
    c2x = from.x + dx * 0.66;
    c2y = to.y - off;
  } else {
    const off = len * curvature;
    c1x = from.x + off;
    c1y = from.y + dy * 0.33;
    c2x = to.x + off;
    c2y = from.y + dy * 0.66;
  }
  const d = `M ${from.x} ${from.y} C ${c1x} ${c1y}, ${c2x} ${c2y}, ${to.x} ${to.y}`;

  // Approximate path length for dash offset
  const approxLen = len * (1 + curvature * 0.4);
  const dash = dashed ? `${width * 4} ${width * 4}` : undefined;

  // Compute dot positions along Bezier curve
  function bezierPoint(t) {
    const u = 1 - t;
    const bx = u*u*u*from.x + 3*u*u*t*c1x + 3*u*t*t*c2x + t*t*t*to.x;
    const by = u*u*u*from.y + 3*u*u*t*c1y + 3*u*t*t*c2y + t*t*t*to.y;
    return { x: bx, y: by };
  }

  return (
    <svg
      width={STAGE_W} height={STAGE_H}
      style={{
        position: 'absolute',
        left: 0, top: 0,
        pointerEvents: 'none',
        opacity,
        overflow: 'visible',
      }}
    >
      {glow && (
        <path
          d={d}
          fill="none"
          stroke={color}
          strokeWidth={width * 4}
          strokeOpacity="0.18"
          strokeLinecap="round"
          strokeDasharray={dash}
          style={{
            strokeDasharray: dashed ? dash : approxLen,
            strokeDashoffset: dashed ? 0 : approxLen * (1 - draw),
          }}
        />
      )}
      <path
        d={d}
        fill="none"
        stroke={color}
        strokeWidth={width}
        strokeLinecap="round"
        strokeDasharray={dashed ? dash : approxLen}
        strokeDashoffset={dashed ? 0 : approxLen * (1 - draw)}
      />
      {Array.from({ length: dotsCount }).map((_, i) => {
        // Each dot lags behind by spacing
        const phase = (dotProgress + i / dotsCount) % 1;
        const p = bezierPoint(phase);
        // Fade dots at the ends to look like a pulse trail
        const fade = phase < 0.05 ? phase / 0.05 : phase > 0.95 ? (1 - phase) / 0.05 : 1;
        return (
          <circle
            key={i}
            cx={p.x} cy={p.y}
            r={dotSize}
            fill={dotColor || color}
            opacity={fade * draw}
          />
        );
      })}
    </svg>
  );
}

// ── NetworkBurst ────────────────────────────────────────────────────────────
// Lines radiating outward from a center point. Used for accent moments
// (logo reveal, AI generation).
function NetworkBurst({
  center, radius = 200, count = 12,
  startAngle = 0,
  progress = 0,  // 0..1 how far lines have extended
  color = AKDMI.orange,
  width = 1.5,
  opacity = 1,
}) {
  return (
    <svg
      width={STAGE_W} height={STAGE_H}
      style={{
        position: 'absolute', left: 0, top: 0,
        pointerEvents: 'none', opacity, overflow: 'visible',
      }}
    >
      {Array.from({ length: count }).map((_, i) => {
        const a = startAngle + (i / count) * Math.PI * 2;
        const length = radius * progress;
        const ex = center.x + Math.cos(a) * length;
        const ey = center.y + Math.sin(a) * length;
        return (
          <line
            key={i}
            x1={center.x} y1={center.y}
            x2={ex} y2={ey}
            stroke={color}
            strokeWidth={width}
            strokeLinecap="round"
            strokeOpacity={1 - progress * 0.3}
          />
        );
      })}
    </svg>
  );
}

// ── ParticleFountain ────────────────────────────────────────────────────────
// Tiny particles ejecting from a point along random trajectories. Used for
// AI burst, completion celebrations.
function ParticleFountain({
  center, count = 18, spread = 200, age = 0, color = AKDMI.orange,
}) {
  // age: 0..1 how far the particles have traveled
  return (
    <svg
      width={STAGE_W} height={STAGE_H}
      style={{
        position: 'absolute', left: 0, top: 0,
        pointerEvents: 'none', overflow: 'visible',
      }}
    >
      {Array.from({ length: count }).map((_, i) => {
        // Deterministic pseudo-random per index
        const seed = Math.sin(i * 13.37) * 10000;
        const r = ((seed - Math.floor(seed)) * 2 - 1) * spread;
        const angle = (i / count) * Math.PI * 2 + (seed - Math.floor(seed));
        const dist = (0.4 + Math.abs(r) / spread) * spread * age;
        const x = center.x + Math.cos(angle) * dist;
        const y = center.y + Math.sin(angle) * dist;
        return (
          <circle
            key={i}
            cx={x} cy={y}
            r={3 * (1 - age * 0.6)}
            fill={color}
            opacity={(1 - age) * 0.9}
          />
        );
      })}
    </svg>
  );
}

// ── PulsingDot ──────────────────────────────────────────────────────────────
// A node anchor that pulses — used at line endpoints.
function PulsingDot({ x, y, color = AKDMI.violet, size = 10, pulseT = 0 }) {
  const pulseScale = 1 + Math.sin(pulseT * 6) * 0.15;
  return (
    <div style={{
      position: 'absolute',
      left: x - size / 2, top: y - size / 2,
      width: size, height: size,
      borderRadius: '50%',
      background: color,
      boxShadow: `0 0 0 ${size * 0.6}px ${color}22, 0 0 0 ${size * 1.2}px ${color}11`,
      transform: `scale(${pulseScale})`,
    }} />
  );
}

Object.assign(window, {
  ConnectorPath, NetworkBurst, ParticleFountain, PulsingDot,
});
