diff --git a/src/components/panels/analysis/BestMoves.tsx b/src/components/panels/analysis/BestMoves.tsx index 037c0790..d221e8da 100644 --- a/src/components/panels/analysis/BestMoves.tsx +++ b/src/components/panels/analysis/BestMoves.tsx @@ -34,6 +34,7 @@ import { useContext, useEffect, useMemo, + useRef, useState, } from "react"; import { match } from "ts-pattern"; @@ -86,12 +87,18 @@ export default function BestMovesComponent({ .with({ t: "Infinite" }, () => 99.9) .otherwise(() => 0); const theme = useMantineTheme(); + const listeners = useRef<(() => void)[]>([]); + + const isGameOver = useMemo(() => { + const chess = new Chess(fen); + return chess.isGameOver(); + }, [fen]); useEffect(() => { async function waitForMove() { const unlisten = await events.bestMovesPayload.listen(({ payload }) => { const ev = payload.bestLines; - if (payload.engine === engine.path && payload.tab === activeTab) { + if (payload.engine === engine.path && payload.tab === activeTab && settings.enabled && !isGameOver) { startTransition(() => { setEngineVariation(ev); dispatch({ @@ -108,24 +115,20 @@ export default function BestMovesComponent({ }); } }); - return () => { - unlisten(); - }; + listeners.current.push(unlisten); } waitForMove(); - }, [activeTab, dispatch, engine.path, id, setArrows]); - - const isGameOver = useMemo(() => { - const chess = new Chess(fen); - return chess.isGameOver(); - }, [fen]); + return () => { + listeners.current.forEach((unlisten) => unlisten()); + }; + }, [activeTab, dispatch, engine.path, id, setArrows, settings.enabled, isGameOver]); useThrottledEffect( () => { if (settings.enabled) { const chess = new Chess(fen); if (chess.isGameOver()) { - setSettings((prev) => ({ ...prev, enabled: false })); + commands.stopEngine(engine.path, activeTab!); setEngineVariation([]); } else { commands @@ -166,7 +169,6 @@ export default function BestMovesComponent({ onClick={() => { setSettings((prev) => ({ ...prev, enabled: !prev.enabled })); }} - disabled={isGameOver} ml={12} > {settings.enabled ? ( @@ -183,46 +185,48 @@ export default function BestMovesComponent({ {engine.name} - {settings.enabled && engineVariations.length === 0 && ( + {settings.enabled && !isGameOver && engineVariations.length === 0 && ( Loading... )} {progress < 100 && settings.enabled && - engineVariations.length > 0 && ( + !isGameOver && engineVariations.length > 0 && ( {nps}k nodes/s )} - {engineVariations.length > 0 && ( - - - Eval - - - {formatScore(engineVariations[0].score, 1) ?? 0} - - + {!isGameOver && engineVariations.length > 0 && ( + <> + + + Eval + + + {formatScore(engineVariations[0].score, 1) ?? 0} + + + + + Depth + + + {depth} + + + )} - - - Depth - - - {depth} - - @@ -247,8 +251,8 @@ export default function BestMovesComponent({ /> - {engineVariations.length === 0 && + {isGameOver && + + } + {!isGameOver && engineVariations.length === 0 && (settings.enabled ? ( [...Array(settings.numberLines)].map((_, i) => ( @@ -275,7 +286,7 @@ export default function BestMovesComponent({ ))} - {engineVariations.map((engineVariation, index) => { + {!isGameOver && engineVariations.map((engineVariation, index) => { return (
+ + {"Game is over"} + +