import { useCallback, useRef, useState } from 'react';

import type {
  Match3DClickItemRequest,
  Match3DRunSnapshot,
} from '../packages/shared/src/contracts/match3dRuntime';
import { Match3DRuntimeShell } from './components/match3d-runtime';
import {
  confirmLocalMatch3DClick,
  resolveLocalMatch3DTimer,
  startLocalMatch3DRun,
} from './services/match3d-runtime';

function buildInitialRun() {
  const params = new URLSearchParams(window.location.search);
  const clearCountParam = params.get('clearCount') ?? params.get('count');
  const clearCount =
    clearCountParam === null ? 12 : Number.parseInt(clearCountParam, 10);
  return startLocalMatch3DRun(
    Number.isFinite(clearCount) && clearCount > 0 ? clearCount : 12,
  );
}

export default function Match3DPlaygroundApp() {
  const [run, setRun] = useState<Match3DRunSnapshot>(buildInitialRun);
  const authorityRunRef = useRef(run);

  const syncRun = useCallback((nextRun: Match3DRunSnapshot) => {
    setRun(nextRun);
  }, []);

  const handleClickItem = useCallback(async (payload: Match3DClickItemRequest) => {
    const result = await confirmLocalMatch3DClick(authorityRunRef.current, payload);
    authorityRunRef.current = result.run;
    setRun(result.run);
    return result;
  }, []);

  const handleRestart = useCallback(() => {
    const nextRun = buildInitialRun();
    authorityRunRef.current = nextRun;
    setRun(nextRun);
  }, []);

  const handleExit = useCallback(() => {
    window.location.assign('/');
  }, []);

  const handleTimeExpired = useCallback(() => {
    const nextRun = resolveLocalMatch3DTimer(authorityRunRef.current);
    authorityRunRef.current = nextRun;
    setRun(nextRun);
  }, []);

  return (
    <Match3DRuntimeShell
      run={run}
      onBack={handleExit}
      onRestart={handleRestart}
      onOptimisticRunChange={syncRun}
      onClickItem={handleClickItem}
      onTimeExpired={handleTimeExpired}
      error={null}
      isBusy={false}
    />
  );
}
