feat : set depth & multipv

This commit is contained in:
GuillaumeSD
2024-02-24 01:20:39 +01:00
parent 89ca7d8f13
commit 6156e4a228
13 changed files with 318 additions and 142 deletions

View File

@@ -0,0 +1,111 @@
import { Stockfish } from "@/lib/engine/stockfish";
import { Icon } from "@iconify/react";
import { Grid } from "@mui/material";
import { useEffect, useState } from "react";
import {
engineDepthAtom,
engineMultiPvAtom,
gameAtom,
gameEvalAtom,
} from "../states";
import { useAtomValue, useSetAtom } from "jotai";
import { getFens } from "@/lib/chess";
import { useGameDatabase } from "@/hooks/useGameDatabase";
import { LoadingButton } from "@mui/lab";
import Slider from "@/components/slider";
export default function AnalyzePanel() {
const [engine, setEngine] = useState<Stockfish | null>(null);
const [evaluationInProgress, setEvaluationInProgress] = useState(false);
const engineDepth = useAtomValue(engineDepthAtom);
const engineMultiPv = useAtomValue(engineMultiPvAtom);
const { setGameEval, gameFromUrl } = useGameDatabase();
const setEval = useSetAtom(gameEvalAtom);
const game = useAtomValue(gameAtom);
useEffect(() => {
const engine = new Stockfish();
engine.init().then(() => {
setEngine(engine);
});
return () => {
engine.shutdown();
};
}, []);
const readyToAnalyse =
engine?.isReady() && game.history().length > 0 && !evaluationInProgress;
const handleAnalyze = async () => {
const gameFens = getFens(game);
if (!engine?.isReady() || gameFens.length === 0 || evaluationInProgress)
return;
setEvaluationInProgress(true);
const newGameEval = await engine.evaluateGame(
gameFens,
engineDepth,
engineMultiPv
);
setEval(newGameEval);
setEvaluationInProgress(false);
if (gameFromUrl) {
setGameEval(gameFromUrl.id, newGameEval);
}
};
return (
<Grid
item
container
xs={12}
justifyContent="center"
alignItems="center"
rowGap={4}
>
<Slider label="Maximum depth" atom={engineDepthAtom} min={10} max={30} />
<Slider
label="Number of lines"
atom={engineMultiPvAtom}
min={1}
max={6}
xs={6}
/>
<Grid
item
container
xs={12}
justifyContent="center"
alignItems="center"
marginTop={1}
>
<LoadingButton
variant="contained"
size="large"
startIcon={
!evaluationInProgress && (
<Icon icon="streamline:magnifying-glass-solid" />
)
}
onClick={handleAnalyze}
disabled={!readyToAnalyse}
loading={evaluationInProgress}
loadingPosition={evaluationInProgress ? "end" : undefined}
endIcon={
evaluationInProgress && (
<Icon icon="streamline:magnifying-glass-solid" />
)
}
>
{evaluationInProgress ? "Analyzing..." : "Analyze"}
</LoadingButton>
</Grid>
</Grid>
);
}

View File

@@ -0,0 +1,35 @@
import { Icon } from "@iconify/react";
import { Grid, Typography } from "@mui/material";
import LoadGame from "./loadGame";
import AnalyzePanel from "./analyzePanel";
export default function ReviewPanelHeader() {
return (
<Grid
item
container
justifyContent="center"
alignItems="center"
xs={12}
gap={3}
>
<Grid
item
container
xs={12}
justifyContent="center"
alignItems="center"
columnGap={1}
>
<Icon icon="ph:file-magnifying-glass-fill" height={40} />
<Typography variant="h4" align="center">
Game Report
</Typography>
</Grid>
<LoadGame />
<AnalyzePanel />
</Grid>
);
}

View File

@@ -0,0 +1,55 @@
import { Grid } from "@mui/material";
import LoadGameButton from "../../loadGame/loadGameButton";
import { useCallback, useEffect } from "react";
import { useChessActions } from "@/hooks/useChess";
import {
boardAtom,
boardOrientationAtom,
gameAtom,
gameEvalAtom,
} from "../states";
import { useGameDatabase } from "@/hooks/useGameDatabase";
import { useAtomValue, useSetAtom } from "jotai";
import { Chess } from "chess.js";
export default function LoadGame() {
const game = useAtomValue(gameAtom);
const gameActions = useChessActions(gameAtom);
const boardActions = useChessActions(boardAtom);
const { gameFromUrl } = useGameDatabase();
const setEval = useSetAtom(gameEvalAtom);
const setBoardOrientation = useSetAtom(boardOrientationAtom);
const resetAndSetGamePgn = useCallback(
(pgn: string) => {
boardActions.reset();
setEval(undefined);
setBoardOrientation(true);
gameActions.setPgn(pgn);
},
[boardActions, gameActions, setEval, setBoardOrientation]
);
useEffect(() => {
const loadGame = async () => {
if (!gameFromUrl) return;
const gamefromDbChess = new Chess();
gamefromDbChess.loadPgn(gameFromUrl.pgn);
if (game.history().join() === gamefromDbChess.history().join()) return;
resetAndSetGamePgn(gameFromUrl.pgn);
setEval(gameFromUrl.eval);
};
loadGame();
}, [gameFromUrl, game, resetAndSetGamePgn, setEval]);
if (gameFromUrl) return null;
return (
<Grid item container xs={12} justifyContent="center" alignItems="center">
<LoadGameButton setGame={(game) => resetAndSetGamePgn(game.pgn())} />
</Grid>
);
}