/** * Simple SGF parser for extracting moves from SGF files */ export interface SgfMove { color: 'black' | 'white'; x: number; y: number; } export interface SgfData { boardSize: number; moves: SgfMove[]; } /** * Parse SGF content and extract board size and moves */ export function parseSgf(sgfContent: string): SgfData { const moves: SgfMove[] = []; let boardSize = 19; // default // Extract board size const sizeMatch = sgfContent.match(/SZ\[(\d+)\]/); if (sizeMatch) { boardSize = parseInt(sizeMatch[1], 10); } // Extract moves - pattern like ;B[dd] or ;W[ed] const movePattern = /;([BW])\[([a-z]{0,2})\]/g; let match; while ((match = movePattern.exec(sgfContent)) !== null) { const color = match[1] === 'B' ? 'black' : 'white'; const coords = match[2]; // Empty brackets mean pass if (!coords) { continue; } // Convert SGF coordinates (aa = top-left) to 0-based x,y const x = coords.charCodeAt(0) - 97; // 'a' = 0 const y = coords.charCodeAt(1) - 97; moves.push({ color, x, y }); } return { boardSize, moves }; } /** * Load and parse an SGF file from a URL */ export async function loadSgf(url: string): Promise { const response = await fetch(url); const content = await response.text(); return parseSgf(content); }