diff --git a/src/lib/chess/types.ts b/src/lib/chess/types.ts index 44e147d..dde6bce 100644 --- a/src/lib/chess/types.ts +++ b/src/lib/chess/types.ts @@ -1,3 +1,6 @@ +import { Game } from "./utils"; +export type GameListener = (board: Game) => void; + export enum Piece { EMPTY = 0, KING = 1, diff --git a/src/lib/chess/utils.ts b/src/lib/chess/utils.ts index 90acea8..33a99e3 100644 --- a/src/lib/chess/utils.ts +++ b/src/lib/chess/utils.ts @@ -1,8 +1,8 @@ -import { CHAR_TO_PIECE, Piece } from "./types"; +import { CHAR_TO_PIECE, Piece, PIECE_TO_CHAR, type GameListener } from "./types"; export const startFEN = "rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0"; -export class Board { +export class Game { public board = new Int8Array(8 ** 2); public details = { whiteTurn: true, @@ -14,11 +14,22 @@ export class Board { halfMove: 0, fullMove: 0, }; + + private listeners = new Set(); constructor() { this.loadFEN(); } + private notify() { + for (const listener of this.listeners) listener(this); + } + + subscribe(listener: GameListener): () => void { + this.listeners.add(listener); + return () => this.listeners.delete(listener); + } + loadFEN(fen = startFEN) { const [position, turn, castling, enPassant, halfMove, fullMove] = fen.split(" "); @@ -43,9 +54,20 @@ export class Board { this.details.halfMove = parseInt(halfMove); this.details.fullMove = parseInt(fullMove); + + this.notify(); } } +export function boardToAscii(board: Int8Array): string { + let ascii = ''; + board.forEach((piece, i) => { + if (i % 8 === 0 && i !== 0) ascii += '\n'; + ascii += PIECE_TO_CHAR[piece]; + }); + return ascii; +} + function algebraicToIndex(algebraic: string): number { const FILE_TO_INDEX: Record = { a: 0, b: 1, c: 2, d: 3, e: 4, f: 5, g: 6, h: 7, diff --git a/src/routes/+page.svelte b/src/routes/+page.svelte index 3ac01ec..ea6797a 100644 --- a/src/routes/+page.svelte +++ b/src/routes/+page.svelte @@ -1,20 +1,25 @@
- {#each boardView as square, index} + {#each board as square, index}
@@ -24,6 +29,37 @@ {/each}
+
{ascii}
+
    + {#each Object.entries(game.details).filter(([k]) => k !== "castling") as [key, val]} +
  • + {key}: + {val.toString()} +
  • + {/each} + + + + + + + + + + + + + + + + + + + + +
    CastlingKingQueen
    White{game.details.castling.white.king}{game.details.castling.white.queen}
    Black{game.details.castling.black.king}{game.details.castling.black.queen}
    +
+
\ No newline at end of file diff --git a/src/routes/layout.css b/src/routes/layout.css index 46b5600..6e343a7 100644 --- a/src/routes/layout.css +++ b/src/routes/layout.css @@ -3,4 +3,8 @@ html, body { @apply h-full; } body { @apply bg-gray-900 text-gray-100; } -input, button { @apply bg-stone-200 text-stone-800 px-2 py-1 m-1 rounded; } \ No newline at end of file +input, button { @apply bg-stone-200 text-stone-800 px-2 py-1 m-1 rounded; } + +table { @apply w-full border-collapse; } +th, td { @apply border border-gray-700 px-2 py-1 text-center } +th { @apply font-bold; }