Spaces:
Sleeping
Sleeping
| import * as React from 'react'; | |
| const { useState, useEffect, useRef } = React; | |
| interface ChessClockProps { | |
| isPlayerTurn: boolean; | |
| playerColor: 'white' | 'black'; | |
| gameActive: boolean; | |
| initialTimeMinutes?: number; | |
| } | |
| const ChessClock: React.FC<ChessClockProps> = ({ | |
| isPlayerTurn, | |
| playerColor, | |
| gameActive, | |
| initialTimeMinutes = 10 | |
| }) => { | |
| // Convert minutes to milliseconds | |
| const initialTime = initialTimeMinutes * 60 * 1000; | |
| // Store the initial time in a ref to access it for resets | |
| const initialTimeRef = useRef<number>(initialTime); | |
| const [whiteTime, setWhiteTime] = useState<number>(initialTime); | |
| const [blackTime, setBlackTime] = useState<number>(initialTime); | |
| const [activeClock, setActiveClock] = useState<'white' | 'black' | null>(null); | |
| // Track previous turn state to detect changes | |
| const prevTurnRef = useRef<boolean | null>(null); | |
| const prevActiveClockRef = useRef<'white' | 'black' | null>(null); | |
| const playerClockRef = useRef<'white' | 'black'>(playerColor); | |
| const aiClockRef = useRef<'white' | 'black'>(playerColor === 'white' ? 'black' : 'white'); | |
| // Update player/AI clock references when player color changes | |
| useEffect(() => { | |
| playerClockRef.current = playerColor; | |
| aiClockRef.current = playerColor === 'white' ? 'black' : 'white'; | |
| }, [playerColor]); | |
| // Reset clocks when game becomes active (new game started) | |
| useEffect(() => { | |
| if (gameActive) { | |
| setWhiteTime(initialTime); | |
| setBlackTime(initialTime); | |
| console.log('Clocks reset for new game'); | |
| } | |
| }, [gameActive, initialTime]); | |
| // Update active clock based on whose turn it is | |
| useEffect(() => { | |
| if (!gameActive) { | |
| setActiveClock(null); | |
| return; | |
| } | |
| // Determine whose turn it is based on the current player turn and player color | |
| const currentActiveClock = isPlayerTurn ? playerColor : (playerColor === 'white' ? 'black' : 'white'); | |
| // Only update if the active clock has changed | |
| if (currentActiveClock !== activeClock) { | |
| setActiveClock(currentActiveClock); | |
| console.log(`Clock switched to: ${currentActiveClock} (Player: ${playerColor}, PlayerTurn: ${isPlayerTurn})`); | |
| } | |
| }, [isPlayerTurn, playerColor, gameActive, activeClock]); | |
| // Clock tick effect | |
| useEffect(() => { | |
| if (!gameActive || !activeClock) { | |
| return; | |
| } | |
| const interval = setInterval(() => { | |
| if (activeClock === 'white') { | |
| setWhiteTime((prev) => Math.max(0, prev - 1000)); | |
| } else if (activeClock === 'black') { | |
| setBlackTime((prev) => Math.max(0, prev - 1000)); | |
| } | |
| }, 1000); | |
| return () => clearInterval(interval); | |
| }, [activeClock, gameActive]); | |
| // Format time as mm:ss | |
| const formatTime = (timeMs: number): string => { | |
| const totalSeconds = Math.floor(timeMs / 1000); | |
| const minutes = Math.floor(totalSeconds / 60); | |
| const seconds = totalSeconds % 60; | |
| return `${minutes.toString().padStart(2, '0')}:${seconds.toString().padStart(2, '0')}`; | |
| }; | |
| return ( | |
| <div className="flex justify-between items-center w-full max-w-[800px] mb-4"> | |
| <div | |
| className={`p-3 rounded-lg ${ | |
| activeClock === 'white' | |
| ? 'bg-gradio-card border-2 border-gradio-blue' | |
| : 'bg-gradio-bg' | |
| }`} | |
| > | |
| <div className="text-lg font-medium text-gradio-text">White</div> | |
| <div className={`text-2xl font-bold ${whiteTime < 60000 ? 'text-gradio-red' : 'text-gradio-text'}`}> | |
| {formatTime(whiteTime)} | |
| </div> | |
| </div> | |
| {/* Title in the middle of the timers */} | |
| <div className="bg-gradio-card py-3 px-6 rounded-lg shadow-lg"> | |
| <h2 className="text-3xl font-bold text-gradio-orange">Chess Engine</h2> | |
| </div> | |
| <div | |
| className={`p-3 rounded-lg ${ | |
| activeClock === 'black' | |
| ? 'bg-gradio-card border-2 border-gradio-blue' | |
| : 'bg-gradio-bg' | |
| }`} | |
| > | |
| <div className="text-lg font-medium text-gradio-text">Black</div> | |
| <div className={`text-2xl font-bold ${blackTime < 60000 ? 'text-gradio-red' : 'text-gradio-text'}`}> | |
| {formatTime(blackTime)} | |
| </div> | |
| </div> | |
| </div> | |
| ); | |
| }; | |
| export default ChessClock; |