import { useEffect, useRef } from 'react'; interface Props { app: any; className?: string; } export default function Live2DCat({ app, className }: Props) { const modelRef = useRef(null); useEffect(() => { if (!app) return; let mounted = true; const init = async () => { try { const { Live2DModel } = await import('pixi-live2d-display/cubism4'); const model = await Live2DModel.from('/live2d/models/little-cat/LittleCat.model3.json', { autoInteract: false, }); if (!mounted) return; // Scale to fit ~120x120 area on the shared stage const sw = app.screen.width; const sh = app.screen.height; const targetW = 120; const targetH = 120; const s = Math.min(targetW / model.width, targetH / model.height); model.scale.set(s); model.anchor.set(0.5, 0.5); // Position near top-left corner with some padding model.position.set(80, 80); app.stage.addChild(model as any); (model as any).isInteractive = () => false; modelRef.current = model; try { model.motion('Idle'); } catch { /* */ } } catch (e) { console.warn('[Live2DCat]', e); } }; init(); return () => { mounted = false; if (modelRef.current) { app.stage.removeChild(modelRef.current); modelRef.current.destroy?.(); modelRef.current = null; } }; }, [app]); // Live2DCat no longer renders its own canvas — it shares the KiraAvatar canvas return null; }