import { useEffect, useRef } from 'react';

interface Props {
  onKiraReady?: (model: any) => void;
  onReady?: () => void;
  isSpeaking?: boolean;
}

/**
 * Single full-viewport Live2D stage. One WebGL context, two models:
 *   - Kira (center)
 *   - Mochi the cat (bottom-right, PetZone area)
 *
 * The canvas sits behind the UI panels (z-0, pointer-events: none).
 */
export default function Live2DStage({ onKiraReady, onReady, isSpeaking }: Props) {
  const canvasRef = useRef<HTMLCanvasElement>(null);

  useEffect(() => {
    let mounted = true;
    const canvas = canvasRef.current;
    if (!canvas) return;

    let app: any = null;
    let kiraModel: any = null;
    let catModel: any = null;

    const init = async () => {
      try {
        await loadScript('/live2d/cubism/live2dcubismcore.min.js');
        const { Application, Ticker } = await import('pixi.js');
        const { Live2DModel } = await import('pixi-live2d-display/cubism4');
        (Live2DModel as any).registerTicker(Ticker as any);

        // Full viewport canvas
        const w = window.innerWidth;
        const h = window.innerHeight;

        app = new Application({
          view: canvas,
          width: w,
          height: h,
          antialias: true,
          resolution: Math.min(window.devicePixelRatio || 1, 2),
          backgroundAlpha: 0,
          autoDensity: true,
        });
        if (!mounted) { app.destroy(true); return; }

        // Resize handler
        const onResize = () => {
          app.renderer.resize(window.innerWidth, window.innerHeight);
          if (kiraModel) {
            const sw = app.screen.width;
            const sh = app.screen.height;
            const centerX = sw * 0.42; // center column offset
            const centerY = sh * 0.48;
            const s = Math.min((sw * 0.28) / kiraModel.width, (sh * 0.7) / kiraModel.height);
            kiraModel.scale.set(s);
            kiraModel.anchor.set(0.5, 0.5);
            kiraModel.position.set(centerX, centerY);
          }
          if (catModel) {
            const sw = app.screen.width;
            const sh = app.screen.height;
            // Position in right sidebar area
            const catX = sw * 0.88;
            const catY = sh * 0.88;
            const cs = Math.min((sw * 0.08) / catModel.width, (sh * 0.12) / catModel.height);
            catModel.scale.set(cs);
            catModel.anchor.set(0.5, 0.5);
            catModel.position.set(catX, catY);
          }
        };
        window.addEventListener('resize', onResize);

        // Load Kira
        kiraModel = await Live2DModel.from('/live2d/models/kira/kira.model3.json', {
          autoInteract: false,
        });
        if (!mounted) { app.destroy(true); return; }

        const sw = app.screen.width;
        const sh = app.screen.height;
        const centerX = sw * 0.42;
        const centerY = sh * 0.48;
        const s = Math.min((sw * 0.28) / kiraModel.width, (sh * 0.7) / kiraModel.height);
        kiraModel.scale.set(s);
        kiraModel.anchor.set(0.5, 0.5);
        kiraModel.position.set(centerX, centerY);
        (kiraModel as any).isInteractive = () => false;

        app.stage.addChild(kiraModel as any);
        try { kiraModel.motion('Idle'); } catch {}
        try { kiraModel.expression('Normal'); } catch {}

        if (onKiraReady && mounted) onKiraReady(kiraModel);

        // Load Mochi the cat
        try {
          catModel = await Live2DModel.from('/live2d/models/little-cat/LittleCat.model3.json', {
            autoInteract: false,
          });
          if (!mounted) return;

          const catX = sw * 0.88;
          const catY = sh * 0.88;
          const cs = Math.min((sw * 0.08) / catModel.width, (sh * 0.12) / catModel.height);
          catModel.scale.set(cs);
          catModel.anchor.set(0.5, 0.5);
          catModel.position.set(catX, catY);
          (catModel as any).isInteractive = () => false;

          app.stage.addChild(catModel as any);
          try { catModel.motion('Idle'); } catch {}
        } catch (e) {
          console.warn('[Live2DStage] cat load failed:', e);
        }

        if (mounted && onReady) onReady();

      } catch (e) {
        console.warn('[Live2DStage]', e);
      }
    };

    init();

    return () => {
      mounted = false;
      if (app) { app.destroy(true, { children: true }); }
    };
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, []);

  // Lip sync for Kira
  const kiraRef = useRef<any>(null);
  const lipSyncRef = useRef<number>(0);

  useEffect(() => {
    // Store kira model from onKiraReady callback
    // We need to capture the model for lip sync
  }, []);

  return (
    <canvas
      ref={canvasRef}
      className="fixed inset-0 w-full h-full"
      style={{ zIndex: 0, pointerEvents: 'none' }}
    />
  );
}

function loadScript(src: string): Promise<void> {
  return new Promise((resolve, reject) => {
    if (document.querySelector(`script[src="${src}"]`)) { resolve(); return; }
    const s = document.createElement('script');
    s.src = src;
    s.onload = () => resolve();
    s.onerror = () => reject(new Error('Failed ' + src));
    document.head.appendChild(s);
  });
}
