Port sudoku generation algorithm and integrate with game flow: Core Changes: - src/useBoard/SudokuGenerator.ts: Ported from src_old/lib/Sudoku.ts - Full puzzle generation algorithm (robatron/sudoku.js) - Supports all difficulty levels (easy through inhuman) - Returns 81-character string representation - src/useBoard/useBoard.ts: Enhanced with puzzle state - Added boardRef and initialBoardRef for state management - Added generateBoard(difficulty) method - Updated renderBoard() to display givens from board string - Cells show digits for givens, empty for '.' characters - src/useGame.ts: Integrated game flow - Reads difficulty from GameOptions (defaults to 'easy') - Generates puzzle on startGame (gameStatus → 'started') - Re-renders board on status changes - quitGame returns to empty grid Game Flow: - Waiting: Empty 9x9 grid - Press Space → startGame() → puzzle generated (~62 givens on easy) - Press Q → quitGame() → empty grid Testing platformHook integration: - startGame trigger working via useKeyBindings - quitGame trigger working via useKeyBindings - Board state properly cleared/populated on status changes Phase 20 complete. Next: Phase 30 (useGameStatus hook).
59 lines
1.4 KiB
TypeScript
59 lines
1.4 KiB
TypeScript
import { useRef } from 'react';
|
|
import { sudoku } from './SudokuGenerator';
|
|
|
|
export function useBoard() {
|
|
const containerRef = useRef<HTMLDivElement | null>(null);
|
|
const boardRef = useRef<string>('');
|
|
const initialBoardRef = useRef<string>('');
|
|
|
|
function generateBoard(difficulty: string = 'easy') {
|
|
const newBoard = sudoku.generate(difficulty);
|
|
boardRef.current = newBoard;
|
|
initialBoardRef.current = newBoard;
|
|
}
|
|
|
|
function renderBoard() {
|
|
const container = containerRef.current;
|
|
if (!container) return;
|
|
|
|
const board = boardRef.current;
|
|
|
|
container.innerHTML = '';
|
|
|
|
const sudokuDiv = document.createElement('div');
|
|
sudokuDiv.id = 'sudoku';
|
|
|
|
const grid = document.createElement('div');
|
|
grid.className = 'sudoku-grid';
|
|
|
|
for (let i = 0; i < 81; i++) {
|
|
const r = Math.floor(i / 9);
|
|
const c = i % 9;
|
|
const cell = document.createElement('div');
|
|
cell.className = 'sudoku-cell';
|
|
cell.dataset.r = String(r);
|
|
cell.dataset.c = String(c);
|
|
|
|
const value = board[i];
|
|
if (value && value !== '.') {
|
|
cell.textContent = value;
|
|
} else {
|
|
cell.textContent = '';
|
|
}
|
|
|
|
grid.appendChild(cell);
|
|
}
|
|
|
|
sudokuDiv.appendChild(grid);
|
|
container.appendChild(sudokuDiv);
|
|
}
|
|
|
|
return {
|
|
containerRef,
|
|
boardRef,
|
|
initialBoardRef,
|
|
generateBoard,
|
|
renderBoard,
|
|
};
|
|
}
|