zchess 0.1.7-alpha.0 → 0.1.8-alpha.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -21,6 +21,29 @@ brew install --formula https://github.com/kennylwx/zchess/releases/latest/downlo
21
21
  Stockfish runs locally. Plain-English move descriptions need the Chess server;
22
22
  SAN and UCI moves work offline.
23
23
 
24
+ Terminal graphics default to `--graphics auto`: the CLI probes the active terminal
25
+ for Kitty graphics support only when identified as Kitty or Ghostty. Unknown
26
+ emulators stay on text without receiving APC queries, because QTerminal 2.1.0
27
+ was observed to leak query payloads into shell scrollback. A known identifier
28
+ only permits probing; a successful runtime reply is still required. Names alone do not
29
+ enable images. Unsupported terminals, redirected streams, tmux, screen and Konsole use the
30
+ text board. `--graphics text` skips probing; `--graphics kitty` explicitly forces
31
+ the protocol on an interactive terminal (use only if you know it supports it).
32
+
33
+ Konsole defaults to text because testing in 25.04.2 found that it acknowledged
34
+ Kitty queries but ignored the requested image sizing, clipping the board over
35
+ the input field. Forced Kitty mode can still exhibit this issue in Konsole.
36
+
37
+ The CLI queries cell pixel dimensions at startup and on image-board resize, then
38
+ specifies only one image dimension so the PNG stays square. If cell size is not
39
+ reported, sizing uses an approximate 2:1 cell ratio; image aspect is still preserved,
40
+ but available-space estimates can be less accurate with unusual fonts. The text
41
+ board also uses approximate proportions and depends on the terminal font.
42
+
43
+ Help, returning to menus and exit delete the board image. If the native PNG
44
+ renderer cannot load, play continues with the text board. A protocol response
45
+ establishes capability, not visual correctness in every terminal/version.
46
+
24
47
  When you start an interactive session, Chess checks npm for a newer version and
25
48
  shows the command to install it in the main menu. Alpha installations also check
26
49
  the alpha channel; stable installations only check stable releases. Homebrew
@@ -28,3 +51,11 @@ installations show a command to reinstall the latest release formula instead.
28
51
  The check times out after 800 ms and failures are silent, so you can still play
29
52
  offline. Set `ZCHESS_NO_UPDATE_CHECK=1` to disable it. Help and noninteractive
30
53
  sessions do not check for updates. Updates are never installed automatically.
54
+
55
+
56
+ Unicode text boards require a terminal font containing chess symbols. The XTerm
57
+ 398 Unicode check used DejaVu Sans Mono 11; its default bitmap font showed missing
58
+ glyph boxes. For fonts without chess symbols, use `chess --graphics ascii`.
59
+ This disables image probing and uses uppercase `KQRBNP` for white, lowercase
60
+ `kqrbnp` for black, and ASCII board labels/markers. It changes the board only;
61
+ other CLI messages can still contain Unicode. Font support is not auto-detected.
@@ -60,7 +60,7 @@ async function checkForUpdate(installed, options = {}) {
60
60
 
61
61
  // src/cli.ts
62
62
  import { createInterface as createInterface2 } from "node:readline/promises";
63
- import { stdin, stdout as stdout2 } from "node:process";
63
+ import { stdin as stdin2, stdout as stdout3 } from "node:process";
64
64
 
65
65
  // ../../packages/chess/dist/index.js
66
66
  var START_FEN = "rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0 1";
@@ -593,40 +593,40 @@ var PIECES = {
593
593
  };
594
594
  var OUTLINES = { K: "\u2654", Q: "\u2655", R: "\u2656", B: "\u2657", N: "\u2658", P: "\u2659" };
595
595
  var RESET = "\x1B[0m";
596
- function render(chess, { perspective = "w", last = null, color: color2 = Boolean(process.stdout.isTTY), compact = false } = {}) {
596
+ function render(chess, { perspective = "w", last = null, color: color2 = Boolean(process.stdout.isTTY), compact = false, ascii = false } = {}) {
597
597
  const rows = perspective === "w" ? [0, 1, 2, 3, 4, 5, 6, 7] : [7, 6, 5, 4, 3, 2, 1, 0];
598
598
  const files = perspective === "w" ? [0, 1, 2, 3, 4, 5, 6, 7] : [7, 6, 5, 4, 3, 2, 1, 0];
599
- const cellWidth = Math.max(6, Math.min(8, Math.floor(((process.stdout.columns || 80) - 8) / 8)));
599
+ const cellWidth = Math.max(1, Math.min(compact ? 2 : 6, Math.floor(((process.stdout.columns || 80) - 8) / 8)));
600
600
  const cell = (content = "") => {
601
601
  const left = Math.floor((cellWidth - 1) / 2);
602
602
  return `${" ".repeat(left)}${content}${" ".repeat(cellWidth - left - (content ? 1 : 0))}`;
603
603
  };
604
- const green = (text) => color2 ? `\x1B[38;5;114m${text}${RESET}` : text;
605
- const border = green(` +${"-".repeat(cellWidth * 8)}+`);
604
+ const defaultText = (text) => color2 ? `\x1B[39m${text}${RESET}` : text;
605
+ const border = defaultText(` +${"-".repeat(cellWidth * 8)}+`);
606
606
  const output = [border];
607
607
  for (const rank of rows) {
608
608
  for (const line of compact ? [1] : [0, 1, 2]) {
609
- let row = green(`${line === 1 ? ` ${8 - rank} ` : " "}|`);
609
+ let row = defaultText(`${line === 1 ? ` ${8 - rank} ` : " "}|`);
610
610
  for (const file of files) {
611
611
  const index = rank * 8 + file;
612
612
  const piece = chess.board[index];
613
613
  const white = piece !== null && piece === piece.toUpperCase();
614
- const glyph = piece ? !color2 && white ? OUTLINES[piece] : PIECES[piece] : " ";
614
+ const glyph = piece ? ascii ? piece : !color2 && white ? OUTLINES[piece] : PIECES[piece] : " ";
615
615
  let square = cell(line === 1 ? glyph : "");
616
616
  if (color2) {
617
617
  const background = last?.includes(index) ? 107 : (rank + file) % 2 ? 65 : 108;
618
618
  square = `\x1B[1;48;5;${background};38;5;${white ? 231 : 16}m${square}${RESET}`;
619
619
  } else if (!piece && line === 1) {
620
- square = cell((rank + file) % 2 ? "\xB7" : "");
620
+ square = cell((rank + file) % 2 ? ascii ? "." : "\xB7" : "");
621
621
  }
622
622
  row += square;
623
623
  }
624
- output.push(row + green("|"));
624
+ output.push(row + defaultText("|"));
625
625
  }
626
626
  }
627
627
  output.push(border);
628
- output.push(green(" " + files.map((file) => cell("abcdefgh"[file])).join("")));
629
- output.push(color2 ? ` \x1B[1;38;5;231m\u265A White${RESET} ${green("\u265A Black \xB7 dark pieces")}` : " \u2654 White \u265A Black");
628
+ output.push(defaultText(" " + files.map((file) => cell("abcdefgh"[file])).join("")));
629
+ output.push(ascii ? defaultText(" White: KQRBNP Black: kqrbnp") : color2 ? defaultText(" \u2654 White \u265A Black \xB7 dark pieces") : " \u2654 White \u265A Black");
630
630
  return output.join("\n") + "\n";
631
631
  }
632
632
 
@@ -649,15 +649,103 @@ var pieces_default = {
649
649
  R: '<g id="white-rook" class="white rook" fill="#fff" fill-rule="evenodd" stroke="#000" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"><path d="M9 39h27v-3H9v3zM12 36v-4h21v4H12zM11 14V9h4v2h5V9h5v2h5V9h4v5" stroke-linecap="butt"/><path d="M34 14l-3 3H14l-3-3"/><path d="M31 17v12.5H14V17" stroke-linecap="butt" stroke-linejoin="miter"/><path d="M31 29.5l1.5 2.5h-20l1.5-2.5"/><path d="M11 14h23" fill="none" stroke-linejoin="miter"/></g>'
650
650
  };
651
651
 
652
+ // src/terminal.ts
653
+ import { stdin, stdout } from "node:process";
654
+ var QUERY_ID = 73192;
655
+ function blocksAutoGraphics(env) {
656
+ const candidate = env.TERM === "xterm-kitty" || env.TERM === "xterm-ghostty" || ["kitty", "ghostty"].includes(env.TERM_PROGRAM?.toLowerCase() ?? "");
657
+ return Boolean(!candidate || env.TMUX || env.STY || env.TERM === "dumb" || env.KONSOLE_VERSION || env.TERM_PROGRAM?.toLowerCase() === "konsole");
658
+ }
659
+ function supportsGraphics(mode, tty = Boolean(stdout.isTTY && stdin.isTTY), env = process.env, confirmed = false) {
660
+ if (!tty || (mode === "text" || mode === "ascii")) return false;
661
+ if (mode === "kitty") return true;
662
+ if (blocksAutoGraphics(env)) return false;
663
+ return confirmed;
664
+ }
665
+ async function detectGraphics(mode, input = stdin, output = stdout, env = process.env, timeout = 300, onCellAspect) {
666
+ const tty = Boolean(input.isTTY && output.isTTY);
667
+ if (mode === "text" || mode === "ascii" || !tty || env.TMUX || env.STY || env.TERM === "dumb" || mode === "auto" && blocksAutoGraphics(env)) {
668
+ return supportsGraphics(mode, tty, env);
669
+ }
670
+ const previous = input.listeners("data");
671
+ previous.forEach((listener) => input.off("data", listener));
672
+ const wasRaw = input.isRaw;
673
+ const wasFlowing = input.readableFlowing === true;
674
+ let pending = "";
675
+ let keyboard = "";
676
+ let confirmed = mode === "kitty";
677
+ return await new Promise((resolve, reject) => {
678
+ let finished = false;
679
+ const finish = (error) => {
680
+ if (finished) return;
681
+ finished = true;
682
+ clearTimeout(timer);
683
+ input.pause();
684
+ input.off("data", onData);
685
+ input.off("end", onEnd);
686
+ input.off("error", onError);
687
+ input.setRawMode(Boolean(wasRaw));
688
+ previous.forEach((listener) => input.on("data", listener));
689
+ if (keyboard) input.unshift(Buffer.from(keyboard, "latin1"));
690
+ if (wasFlowing) input.resume();
691
+ if (error) reject(error);
692
+ else resolve(confirmed);
693
+ };
694
+ const onEnd = () => finish();
695
+ const onError = (error) => finish(error);
696
+ const onData = (chunk) => {
697
+ pending += (typeof chunk === "string" ? Buffer.from(chunk) : chunk).toString("latin1");
698
+ while (pending) {
699
+ if (pending[0] !== "\x1B") {
700
+ keyboard += pending[0];
701
+ pending = pending.slice(1);
702
+ continue;
703
+ }
704
+ const reply = pending.match(/^\x1b_G([^;]*);([^\x1b]*)\x1b\\/);
705
+ if (reply) {
706
+ if (mode === "auto" && reply[1].split(",").includes(`i=${QUERY_ID}`)) confirmed = reply[2] === "OK";
707
+ pending = pending.slice(reply[0].length);
708
+ continue;
709
+ }
710
+ const cellSize = pending.match(/^\x1b\[6;(\d+);(\d+)t/);
711
+ if (cellSize) {
712
+ const height = Number(cellSize[1]), width = Number(cellSize[2]);
713
+ if (height > 0 && width > 0 && height <= 1e3 && width <= 1e3) onCellAspect?.(height / width);
714
+ pending = pending.slice(cellSize[0].length);
715
+ continue;
716
+ }
717
+ const attributes = pending.match(/^\x1b\[\?[\d;]*c/);
718
+ if (attributes) {
719
+ keyboard += pending.slice(attributes[0].length);
720
+ pending = "";
721
+ finish();
722
+ return;
723
+ }
724
+ if ("\x1B_G".startsWith(pending) || pending.startsWith("\x1B_G") || "\x1B[?".startsWith(pending) || /^\x1b\[(?:\?[\d;]*|6[;\d]*)$/.test(pending)) break;
725
+ keyboard += pending[0];
726
+ pending = pending.slice(1);
727
+ }
728
+ };
729
+ const timer = setTimeout(() => finish(), timeout);
730
+ input.on("data", onData);
731
+ input.once("end", onEnd);
732
+ input.once("error", onError);
733
+ try {
734
+ input.setRawMode(true);
735
+ input.resume();
736
+ output.write(`\x1B_Gi=${QUERY_ID},s=1,v=1,a=q,t=d,f=24;AAAA\x1B\\\x1B[16t\x1B[c`);
737
+ } catch (error) {
738
+ finish(error);
739
+ }
740
+ });
741
+ }
742
+
652
743
  // src/graphics.ts
653
744
  var require2 = createRequire(import.meta.url);
654
745
  var pieces = pieces_default;
655
746
  var IMAGE_ID = 73191;
656
- function supportsGraphics(mode, tty = Boolean(process.stdout.isTTY), env = process.env) {
657
- if (!tty || mode === "text") return false;
658
- if (mode === "kitty") return true;
659
- if (env.TMUX || env.STY) return false;
660
- return env.TERM_PROGRAM === "ghostty" || env.TERM === "xterm-ghostty" || env.TERM === "xterm-kitty";
747
+ function clearGraphics() {
748
+ return `\x1B_Ga=d,d=I,i=${IMAGE_ID},q=2;\x1B\\`;
661
749
  }
662
750
  function boardSvg(chess, perspective, last) {
663
751
  const order = perspective === "w" ? [0, 1, 2, 3, 4, 5, 6, 7] : [7, 6, 5, 4, 3, 2, 1, 0];
@@ -686,19 +774,20 @@ function boardPng(chess, perspective, last) {
686
774
  const { Resvg } = require2("@resvg/resvg-js");
687
775
  return new Resvg(boardSvg(chess, perspective, last)).render().asPng();
688
776
  }
689
- function renderGraphics(chess, perspective, last, fixed = false) {
690
- const columnsPerRow = 2.2;
691
- const availableRows = Math.max(1, (process.stdout.rows || 40) - (fixed ? 8 : 7));
692
- const availableColumns = Math.max(2, (process.stdout.columns || 80) - 2);
693
- const rows = Math.max(1, Math.min(32, availableRows, Math.floor(availableColumns / columnsPerRow)));
694
- const columns = Math.min(availableColumns, Math.round(rows * columnsPerRow));
777
+ function renderGraphics(chess, perspective, last, fixed = false, columnsPerRow = 2) {
778
+ const availableRows = Math.max(1, Math.min(32, (process.stdout.rows || 40) - (fixed ? 8 : 7)));
779
+ const availableColumns = Math.max(1, (process.stdout.columns || 80) - 2);
780
+ const ratio = Number.isFinite(columnsPerRow) && columnsPerRow > 0 ? columnsPerRow : 2;
781
+ const widthLimited = availableColumns / ratio < availableRows;
782
+ const rows = widthLimited ? Math.ceil(availableColumns / ratio) : availableRows;
783
+ const placement = widthLimited ? `c=${availableColumns}` : `r=${rows}`;
695
784
  const data = boardPng(chess, perspective, last).toString("base64");
696
- let output = `\x1B_Ga=d,d=I,i=${IMAGE_ID},q=2;\x1B\\`;
785
+ let output = clearGraphics();
697
786
  if (!fixed) output += "\n".repeat(rows) + `\x1B[${rows}A\r`;
698
787
  for (let offset = 0; offset < data.length; offset += 4096) {
699
788
  const chunk = data.slice(offset, offset + 4096);
700
789
  const more = offset + 4096 < data.length ? 1 : 0;
701
- const control = offset === 0 ? `a=T,f=100,t=d,i=${IMAGE_ID},c=${columns},r=${rows},C=1,q=2,` : "";
790
+ const control = offset === 0 ? `a=T,f=100,t=d,i=${IMAGE_ID},${placement},C=1,q=2,` : "";
702
791
  output += `\x1B_G${control}m=${more};${chunk}\x1B\\`;
703
792
  }
704
793
  return output + `\x1B[${rows}B\r`;
@@ -761,9 +850,9 @@ go depth ${depth}
761
850
  }
762
851
 
763
852
  // src/screen.ts
764
- import { stdout } from "node:process";
853
+ import { stdout as stdout2 } from "node:process";
765
854
  var GameScreen = class {
766
- constructor(active, output = stdout, manageScreen = true) {
855
+ constructor(active, output = stdout2, manageScreen = true) {
767
856
  this.active = active;
768
857
  this.output = output;
769
858
  this.manageScreen = manageScreen;
@@ -791,14 +880,14 @@ ${status}
791
880
  }
792
881
  const width = Math.max(1, (this.output.columns || 80) - 1);
793
882
  const fit = (text) => [...text.replace(/[\x00-\x1f\x7f]/g, " ")].slice(0, width).join("");
794
- const title = `\x1B[38;2;224;242;215m${fit(header).padEnd(width)}\x1B[0m`;
795
- const history = `\x1B[38;2;190;221;173m${fit(moves).padEnd(width)}\x1B[0m`;
883
+ const title = `\x1B[39m${fit(header).padEnd(width)}\x1B[0m`;
884
+ const history = `\x1B[39m${fit(moves).padEnd(width)}\x1B[0m`;
796
885
  const horizontalPadding = Math.min(1, Math.floor((width - 1) / 2));
797
886
  const innerWidth = Math.max(1, width - horizontalPadding * 2);
798
887
  const controls = "/help";
799
888
  const visibleControls = controls.slice(-Math.min(innerWidth, controls.length));
800
889
  const statusWidth = Math.max(0, innerWidth - visibleControls.length);
801
- const footer = `\x1B[38;2;224;242;215m${" ".repeat(horizontalPadding)}${fit(status).slice(0, statusWidth).padEnd(statusWidth)}${visibleControls}${" ".repeat(horizontalPadding + 1)}\x1B[0m`;
890
+ const footer = `\x1B[39m${" ".repeat(horizontalPadding)}${fit(status).slice(0, statusWidth).padEnd(statusWidth)}${visibleControls}${" ".repeat(horizontalPadding + 1)}\x1B[0m`;
802
891
  const bottom = Math.max(6, this.output.rows || 40);
803
892
  this.output.write(`\x1B[?2026h\x1B[H\x1B[2J${title}\r
804
893
  ${history}\r
@@ -837,7 +926,7 @@ ${board}\x1B[${bottom - 4};1H${footer}` + this.inputFrame("", "Type any moves e.
837
926
  }
838
927
  };
839
928
  var MenuScreen = class {
840
- constructor(active, output = stdout) {
929
+ constructor(active, output = stdout2) {
841
930
  this.active = active;
842
931
  this.output = output;
843
932
  }
@@ -860,9 +949,9 @@ ${footer}
860
949
  `);
861
950
  return;
862
951
  }
863
- const title = `\x1B[38;2;224;242;215m${fit(header).padEnd(width)}\x1B[0m`;
952
+ const title = `\x1B[39m${fit(header).padEnd(width)}\x1B[0m`;
864
953
  const horizontalPadding = Math.min(2, Math.floor((width - 1) / 2));
865
- const status = `\x1B[38;2;210;225;202m${" ".repeat(horizontalPadding)}${fit(footer).slice(0, width - horizontalPadding * 2).padEnd(width - horizontalPadding * 2)}${" ".repeat(horizontalPadding)}\x1B[0m`;
954
+ const status = `\x1B[39m${" ".repeat(horizontalPadding)}${fit(footer).slice(0, width - horizontalPadding * 2).padEnd(width - horizontalPadding * 2)}${" ".repeat(horizontalPadding)}\x1B[0m`;
866
955
  const body = content.split("\n").map((line) => fit(line)).join("\r\n");
867
956
  this.output.write(`\x1B[?25l\x1B[?2026h\x1B[H\x1B[2J${title}\r
868
957
  \r
@@ -944,7 +1033,7 @@ var GameStore = class {
944
1033
  var HELP = `chess \u2014 terminal chess
945
1034
 
946
1035
  Usage: chess [--elo 1500] [--color white|black] [--fen FEN]
947
- [--server URL] [--depth 12] [--graphics auto|kitty|text]
1036
+ [--server URL] [--depth 12] [--graphics auto|kitty|text|ascii]
948
1037
 
949
1038
  Run "chess" with no options to open the Play / Load game menu.
950
1039
  Moves accept UCI (e2e4), SAN (Nf3), or free text ("move the queen up by 1").
@@ -972,7 +1061,7 @@ function editGameInput(value, text, key) {
972
1061
  if (!key?.ctrl && !key?.meta && text && !/[\x00-\x1f\x7f]/.test(text)) return value + text;
973
1062
  return value;
974
1063
  }
975
- var promptColor = "\x1B[38;2;190;221;173m";
1064
+ var promptColor = "\x1B[39m";
976
1065
  var reset = "\x1B[0m";
977
1066
  var ELO_PRESETS = [
978
1067
  { label: "Beginner", elo: 1320 },
@@ -991,13 +1080,17 @@ async function run(args, installation) {
991
1080
  return index < 0 ? fallback : args[index + 1] ?? fallback;
992
1081
  };
993
1082
  const graphics = get("--graphics", "auto");
994
- if (!["auto", "kitty", "text"].includes(graphics)) throw new Error("Graphics must be auto, kitty, or text.");
1083
+ if (!["auto", "kitty", "text", "ascii"].includes(graphics)) throw new Error("Graphics must be auto, kitty, text, or ascii.");
995
1084
  const depth = Number(get("--depth", "12"));
996
1085
  if (!Number.isInteger(depth) || depth < 1 || depth > 30) throw new Error("Depth must be an integer from 1 to 30.");
997
- const update = installation && stdin.isTTY && stdout2.isTTY && process.env.ZCHESS_NO_UPDATE_CHECK !== "1" ? await checkForUpdate(installation.version, { homebrew: installation.homebrew }) : void 0;
1086
+ let cellAspect = 2;
1087
+ const useGraphics = await detectGraphics(graphics, stdin2, stdout3, process.env, 300, (ratio) => {
1088
+ cellAspect = ratio;
1089
+ });
1090
+ const update = installation && stdin2.isTTY && stdout3.isTTY && process.env.ZCHESS_NO_UPDATE_CHECK !== "1" ? await checkForUpdate(installation.version, { homebrew: installation.homebrew }) : void 0;
998
1091
  const store = new GameStore(get("--db", void 0));
999
1092
  const direct = args.some((arg) => arg.startsWith("--"));
1000
- const interactiveMenu = !direct && stdin.isTTY && stdout2.isTTY;
1093
+ const interactiveMenu = !direct && stdin2.isTTY && stdout3.isTTY;
1001
1094
  const menuScreen = interactiveMenu ? new MenuScreen(true) : void 0;
1002
1095
  menuScreen?.open();
1003
1096
  if (update && !interactiveMenu) console.log(`Update available: ${installation.version} \u2192 ${update.version}
@@ -1007,7 +1100,7 @@ Run: ${update.command}`);
1007
1100
  let returnToSavedGames = false;
1008
1101
  while (keepGoing) {
1009
1102
  let config;
1010
- if (direct || !stdin.isTTY || !stdout2.isTTY) {
1103
+ if (direct || !stdin2.isTTY || !stdout3.isTTY) {
1011
1104
  const elo = Number(get("--elo", "1500"));
1012
1105
  if (!Number.isInteger(elo) || elo < 1320 || elo > 3190) throw new Error("ELO must be an integer from 1320 to 3190 (Stockfish UCI range).");
1013
1106
  config = { elo, human: get("--color", "white").toLowerCase().startsWith("b") ? "b" : "w", fen: get("--fen", void 0) };
@@ -1019,7 +1112,7 @@ Run: ${update.command}`);
1019
1112
  config = choice;
1020
1113
  }
1021
1114
  if (config) {
1022
- const again = await playGame(config, { graphics, depth, serverUrl: get("--server", process.env.ZCHESS_SERVER_URL || "http://localhost:8000"), store, sharedScreen: interactiveMenu });
1115
+ const again = await playGame(config, { useGraphics, ascii: graphics === "ascii", cellAspect, depth, serverUrl: get("--server", process.env.ZCHESS_SERVER_URL || "http://localhost:8000"), store, sharedScreen: interactiveMenu });
1023
1116
  if (again && config.saved) returnToSavedGames = true;
1024
1117
  if (direct || !again) keepGoing = false;
1025
1118
  }
@@ -1030,7 +1123,7 @@ Run: ${update.command}`);
1030
1123
  }
1031
1124
  }
1032
1125
  async function mainMenu(store, screen, openSavedGames = false, update, installed) {
1033
- const rl = createInterface2({ input: stdin, output: stdout2 });
1126
+ const rl = createInterface2({ input: stdin2, output: stdout3 });
1034
1127
  try {
1035
1128
  while (true) {
1036
1129
  if (openSavedGames) {
@@ -1146,7 +1239,7 @@ function menuText(prompt) {
1146
1239
  }
1147
1240
  if (key?.name === "backspace") {
1148
1241
  value = value.slice(0, -1);
1149
- stdout2.write("\b \b");
1242
+ stdout3.write("\b \b");
1150
1243
  return;
1151
1244
  }
1152
1245
  if (key?.name === "return" || key?.name === "enter") {
@@ -1156,29 +1249,29 @@ function menuText(prompt) {
1156
1249
  const character = text ?? "";
1157
1250
  if (key?.ctrl || !character) return;
1158
1251
  value += character;
1159
- stdout2.write(character);
1252
+ stdout3.write(character);
1160
1253
  });
1161
1254
  }
1162
1255
  function rawPrompt(prompt, onKey) {
1163
- const stream = stdin;
1256
+ const stream = stdin2;
1164
1257
  if (!stream.isTTY || !stream.setRawMode) return Promise.reject(new Error("Menu selection requires an interactive terminal."));
1165
- const previous = stdin.listeners("keypress");
1166
- previous.forEach((listener) => stdin.removeListener("keypress", listener));
1167
- stdout2.write(`${promptColor}${prompt}${reset}`);
1258
+ const previous = stdin2.listeners("keypress");
1259
+ previous.forEach((listener) => stdin2.removeListener("keypress", listener));
1260
+ stdout3.write(`${promptColor}${prompt}${reset}`);
1168
1261
  stream.setRawMode(true);
1169
1262
  return new Promise((resolve) => {
1170
1263
  let finished = false;
1171
1264
  const finish = (value) => {
1172
1265
  if (finished) return;
1173
1266
  finished = true;
1174
- stdin.removeListener("keypress", listener);
1267
+ stdin2.removeListener("keypress", listener);
1175
1268
  stream.setRawMode(false);
1176
- [...previous].reverse().forEach((listener2) => stdin.prependListener("keypress", listener2));
1177
- stdout2.write("\r\n");
1269
+ [...previous].reverse().forEach((listener2) => stdin2.prependListener("keypress", listener2));
1270
+ stdout3.write("\r\n");
1178
1271
  resolve(value);
1179
1272
  };
1180
1273
  const listener = (text, key) => onKey(text, key, finish);
1181
- stdin.on("keypress", listener);
1274
+ stdin2.on("keypress", listener);
1182
1275
  });
1183
1276
  }
1184
1277
  async function playGame(config, options) {
@@ -1188,9 +1281,9 @@ async function playGame(config, options) {
1188
1281
  if (saved) for (const move of saved.moves) chess.play(move);
1189
1282
  const abort = new AbortController();
1190
1283
  const server = new ChessServerClient(options.serverUrl, abort.signal);
1191
- const rl = createInterface2({ input: stdin, output: stdout2 });
1192
- const screen = new GameScreen(Boolean(stdout2.isTTY && stdin.isTTY), stdout2, !options.sharedScreen);
1193
- const useGraphics = supportsGraphics(options.graphics);
1284
+ const rl = createInterface2({ input: stdin2, output: stdout3 });
1285
+ const screen = new GameScreen(Boolean(stdout3.isTTY && stdin2.isTTY), stdout3, !options.sharedScreen);
1286
+ let useGraphics = options.useGraphics;
1194
1287
  let stopped = false;
1195
1288
  let redrawInput;
1196
1289
  let last = null;
@@ -1204,12 +1297,21 @@ async function playGame(config, options) {
1204
1297
  const persist = () => {
1205
1298
  gameId = options.store.save({ elo, color: human, startFen, fen: chess.fen(), moves: chess.history.map((entry) => entry.san), status: chess.status() ?? "In progress" }, gameId);
1206
1299
  };
1207
- const draw = () => screen.draw(
1208
- header,
1209
- showingHelp ? commandHelp() : useGraphics ? renderGraphics(chess, human, last, screen.active) : render(chess, { perspective: human, last, compact: screen.active && (stdout2.rows || 40) < 36 }),
1210
- notice,
1211
- showingHelp ? "" : moveHistory(chess, Math.max(1, (stdout2.columns || 80) - 1))
1212
- );
1300
+ const draw = () => {
1301
+ let board;
1302
+ if (showingHelp) board = (useGraphics ? clearGraphics() : "") + commandHelp();
1303
+ else {
1304
+ try {
1305
+ board = useGraphics ? renderGraphics(chess, human, last, screen.active, options.cellAspect) : "";
1306
+ } catch {
1307
+ stdout3.write(clearGraphics());
1308
+ useGraphics = false;
1309
+ board = "";
1310
+ }
1311
+ if (!useGraphics) board = render(chess, { ascii: options.ascii, perspective: human, last, compact: screen.active && (stdout3.rows || 40) < 36 });
1312
+ }
1313
+ screen.draw(header, board, notice, showingHelp ? "" : moveHistory(chess, Math.max(1, (stdout3.columns || 80) - 1)));
1314
+ };
1213
1315
  const takeBack = () => {
1214
1316
  notice = undoTurn(chess, human) ? "Took back your last move and any Stockfish reply." : "No move to undo yet.";
1215
1317
  const move = chess.history.at(-1)?.move;
@@ -1228,18 +1330,30 @@ async function playGame(config, options) {
1228
1330
  abort.abort();
1229
1331
  search?.abort();
1230
1332
  };
1333
+ let resizeTask;
1231
1334
  const resize = () => {
1232
- if (!stopped) {
1233
- draw();
1234
- redrawInput?.();
1235
- }
1335
+ if (stopped || resizeTask) return;
1336
+ resizeTask = (async () => {
1337
+ try {
1338
+ if (useGraphics) await detectGraphics("kitty", stdin2, stdout3, process.env, 300, (ratio) => {
1339
+ options.cellAspect = ratio;
1340
+ });
1341
+ if (!stopped) {
1342
+ draw();
1343
+ redrawInput?.();
1344
+ }
1345
+ } catch {
1346
+ }
1347
+ })().finally(() => {
1348
+ resizeTask = void 0;
1349
+ });
1236
1350
  };
1237
1351
  const question = async (placeholder) => {
1238
1352
  if (!screen.active) return await rl.question(`${promptColor}${placeholder} \u203A ${reset}`, { signal: abort.signal });
1239
- const stream = stdin;
1353
+ const stream = stdin2;
1240
1354
  const previousRaw = stream.isRaw;
1241
- const previous = stdin.listeners("keypress");
1242
- previous.forEach((listener) => stdin.removeListener("keypress", listener));
1355
+ const previous = stdin2.listeners("keypress");
1356
+ previous.forEach((listener) => stdin2.removeListener("keypress", listener));
1243
1357
  stream.setRawMode?.(true);
1244
1358
  return new Promise((resolve) => {
1245
1359
  let value = "";
@@ -1248,9 +1362,9 @@ async function playGame(config, options) {
1248
1362
  const finish = (answer) => {
1249
1363
  if (done) return;
1250
1364
  done = true;
1251
- stdin.removeListener("keypress", onKey);
1365
+ stdin2.removeListener("keypress", onKey);
1252
1366
  abort.signal.removeEventListener("abort", onAbort);
1253
- previous.forEach((listener) => stdin.on("keypress", listener));
1367
+ previous.forEach((listener) => stdin2.on("keypress", listener));
1254
1368
  stream.setRawMode?.(previousRaw);
1255
1369
  redrawInput = void 0;
1256
1370
  screen.input("", placeholder);
@@ -1271,17 +1385,17 @@ async function playGame(config, options) {
1271
1385
  redraw();
1272
1386
  };
1273
1387
  redrawInput = redraw;
1274
- stdin.on("keypress", onKey);
1388
+ stdin2.on("keypress", onKey);
1275
1389
  abort.signal.addEventListener("abort", onAbort, { once: true });
1276
1390
  redraw();
1277
1391
  });
1278
1392
  };
1279
- stdin.on("keypress", shortcut);
1393
+ stdin2.on("keypress", shortcut);
1280
1394
  rl.on("SIGINT", stop);
1281
1395
  rl.on("close", stop);
1282
1396
  process.on("SIGINT", stop);
1283
1397
  process.on("SIGTERM", stop);
1284
- stdout2.on("resize", resize);
1398
+ stdout3.on("resize", resize);
1285
1399
  screen.open();
1286
1400
  persist();
1287
1401
  try {
@@ -1396,12 +1510,14 @@ async function playGame(config, options) {
1396
1510
  } catch (error) {
1397
1511
  if (!stopped) throw error;
1398
1512
  } finally {
1513
+ await resizeTask;
1399
1514
  returnToMenu = screen.active && !stopped;
1400
- stdin.off("keypress", shortcut);
1401
- stdout2.off("resize", resize);
1515
+ stdin2.off("keypress", shortcut);
1516
+ stdout3.off("resize", resize);
1402
1517
  process.off("SIGINT", stop);
1403
1518
  process.off("SIGTERM", stop);
1404
1519
  rl.close();
1520
+ if (useGraphics) stdout3.write(clearGraphics());
1405
1521
  screen.close();
1406
1522
  }
1407
1523
  return returnToMenu || screen.active && returnToMenuRequested;
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
- "sources": ["../src/update.ts", "../src/cli.ts", "../../../packages/chess/src/index.ts", "../../../packages/chess/src/resolution.ts", "../../../packages/chess/src/legality.ts", "../../../packages/chess/src/suggestions.ts", "../../../packages/chess/src/input.ts", "../../../packages/chess/src/history.ts", "../src/api.ts", "../src/ui.ts", "../src/graphics.ts", "../../../packages/chess/assets/pieces.json", "../src/engine.ts", "../src/screen.ts", "../src/store.ts"],
4
- "sourcesContent": ["export interface UpdateNotice { version: string; command: string }\n\ninterface Version { core: bigint[]; prerelease: string[] }\nfunction parseVersion(value: unknown): Version | undefined {\n if (typeof value !== 'string') return;\n const match = /^(0|[1-9]\\d*)\\.(0|[1-9]\\d*)\\.(0|[1-9]\\d*)(?:-([\\da-zA-Z-]+(?:\\.[\\da-zA-Z-]+)*))?(?:\\+[\\da-zA-Z-]+(?:\\.[\\da-zA-Z-]+)*)?$/.exec(value);\n if (!match) return;\n const prerelease = match[4]?.split('.') || [];\n if (prerelease.some(part => /^0\\d+$/.test(part))) return;\n return { core: match.slice(1, 4).map(BigInt), prerelease };\n}\n\nexport function isNewerVersion(candidate: string, installed: string): boolean {\n const a = parseVersion(candidate), b = parseVersion(installed);\n if (!a || !b) return false;\n for (let i = 0; i < 3; i++) if (a.core[i] !== b.core[i]) return a.core[i] > b.core[i];\n if (!a.prerelease.length || !b.prerelease.length) return a.prerelease.length === 0 && b.prerelease.length > 0;\n for (let i = 0; i < Math.max(a.prerelease.length, b.prerelease.length); i++) {\n const x = a.prerelease[i], y = b.prerelease[i];\n if (x === undefined || y === undefined) return x !== undefined;\n if (x === y) continue;\n const xn = /^\\d+$/.test(x), yn = /^\\d+$/.test(y);\n if (xn && yn) return BigInt(x) > BigInt(y);\n if (xn !== yn) return !xn;\n return x > y;\n }\n return false;\n}\n\n/** An optional startup hint: network or registry problems must never prevent play. */\nexport async function checkForUpdate(installed: string, options: {\n fetch?: typeof fetch;\n timeoutMs?: number;\n homebrew?: boolean;\n} = {}): Promise<UpdateNotice | undefined> {\n const current = parseVersion(installed);\n if (!current) return;\n const controller = new AbortController();\n let timer: ReturnType<typeof setTimeout> | undefined;\n try {\n const lookup = async (): Promise<UpdateNotice | undefined> => {\n const response = await (options.fetch || fetch)('https://registry.npmjs.org/-/package/zchess/dist-tags', { signal: controller.signal });\n if (!response.ok) return;\n const tags = await response.json() as Record<string, unknown> | null;\n if (!tags || typeof tags !== 'object') return;\n const candidates = [tags.latest];\n if (current.prerelease.length && !options.homebrew) candidates.push(tags[current.prerelease[0]]);\n let version = installed;\n for (const candidate of candidates) {\n if (typeof candidate === 'string' && isNewerVersion(candidate, version)) version = candidate;\n }\n if (version === installed) return;\n return { version, command: options.homebrew\n ? `brew reinstall --formula \\\\\n https://github.com/kennylwx/zchess/releases/latest/download/zchess.rb`\n : `npm install --global zchess@${version}` };\n };\n const timeout = new Promise<undefined>(resolve => {\n timer = setTimeout(() => { controller.abort(); resolve(undefined); }, options.timeoutMs ?? 800);\n });\n return await Promise.race([lookup(), timeout]);\n } catch { return; }\n finally { if (timer) clearTimeout(timer); }\n}\n", "import { checkForUpdate, type UpdateNotice } from './update.js';\nimport { createInterface } from 'node:readline/promises';\nimport { stdin, stdout } from 'node:process';\nimport { Chess, START_FEN } from '@zchess/chess';\nimport { modelInput } from './input.js';\nimport { ChessServerClient } from './api.js';\nimport { render } from './ui.js';\nimport { renderGraphics, supportsGraphics, type GraphicsMode } from './graphics.js';\nimport { engineMove } from './engine.js';\nimport { GameScreen, MenuScreen } from './screen.js';\nimport { moveHistory, undoTurn } from './history.js';\nimport { GameStore, type SavedGame } from './store.js';\nimport type { Key } from 'node:readline';\n\nconst HELP = `chess \u2014 terminal chess\n\nUsage: chess [--elo 1500] [--color white|black] [--fen FEN]\n [--server URL] [--depth 12] [--graphics auto|kitty|text]\n\nRun \"chess\" with no options to open the Play / Load game menu.\nMoves accept UCI (e2e4), SAN (Nf3), or free text (\"move the queen up by 1\").\nStockfish is included and runs locally. Only free text requires the Chess server.\nGames are saved automatically in ~/.local/share/zchess/games.sqlite.\nCommands: /fen, /fen <position>, /undo, /help, /back, /quit`;\n\nexport function commandHelp(): string {\n return [\n 'COMMANDS',\n '/help Show this list',\n '/undo Take back a turn',\n '/fen Show the current position',\n '/fen <FEN> Load a position',\n '/back Return to the previous screen',\n '/quit Quit Chess',\n '',\n 'SHORTCUTS',\n 'Ctrl+C Quit',\n 'Ctrl+U Clear input',\n ].join('\\n');\n}\n\nexport function editGameInput(value: string, text: string, key: Key): string {\n if ((key?.ctrl && key.name === 'u') || (key?.meta && key.name === 'backspace')) return '';\n if (key?.name === 'backspace') return [...value].slice(0, -1).join('');\n if (!key?.ctrl && !key?.meta && text && !/[\\x00-\\x1f\\x7f]/.test(text)) return value + text;\n return value;\n}\n\nconst promptColor = '\\x1b[38;2;190;221;173m';\nconst reset = '\\x1b[0m';\nconst ELO_PRESETS = [\n { label: 'Beginner', elo: 1320 },\n { label: 'Intermediate', elo: 1500 },\n { label: 'Advanced', elo: 1800 },\n { label: 'Expert', elo: 2200 },\n { label: 'Master', elo: 3190 },\n];\ninterface GameConfig { elo: number; human: 'w' | 'b'; saved?: SavedGame; fen?: string }\n\nexport async function run(args: string[], installation?: { version: string; homebrew?: boolean }): Promise<void> {\n if (args.includes('--help') || args.includes('-h')) { console.log(HELP); return; }\n const get = (name: string, fallback: string | undefined): string | undefined => {\n const index = args.indexOf(name);\n return index < 0 ? fallback : (args[index + 1] ?? fallback);\n };\n const graphics = get('--graphics', 'auto') as GraphicsMode;\n if (!['auto', 'kitty', 'text'].includes(graphics)) throw new Error('Graphics must be auto, kitty, or text.');\n const depth = Number(get('--depth', '12'));\n if (!Number.isInteger(depth) || depth < 1 || depth > 30) throw new Error('Depth must be an integer from 1 to 30.');\n const update = installation && stdin.isTTY && stdout.isTTY && process.env.ZCHESS_NO_UPDATE_CHECK !== '1'\n ? await checkForUpdate(installation.version, { homebrew: installation.homebrew }) : undefined;\n const store = new GameStore(get('--db', undefined));\n const direct = args.some(arg => arg.startsWith('--'));\n const interactiveMenu = !direct && stdin.isTTY && stdout.isTTY;\n const menuScreen = interactiveMenu ? new MenuScreen(true) : undefined;\n menuScreen?.open();\n if (update && !interactiveMenu) console.log(`Update available: ${installation!.version} \u2192 ${update.version}\\nRun: ${update.command}`);\n\n try {\n let keepGoing = true;\n let returnToSavedGames = false;\n while (keepGoing) {\n let config: GameConfig | undefined;\n if (direct || !stdin.isTTY || !stdout.isTTY) {\n const elo = Number(get('--elo', '1500'));\n if (!Number.isInteger(elo) || elo < 1320 || elo > 3190) throw new Error('ELO must be an integer from 1320 to 3190 (Stockfish UCI range).');\n config = { elo, human: get('--color', 'white')!.toLowerCase().startsWith('b') ? 'b' : 'w', fen: get('--fen', undefined) };\n keepGoing = false;\n } else {\n const choice = await mainMenu(store, menuScreen!, returnToSavedGames, update, installation?.version);\n returnToSavedGames = false;\n if (choice === 'quit') break;\n config = choice;\n }\n if (config) {\n const again = await playGame(config, { graphics, depth, serverUrl: get('--server', process.env.ZCHESS_SERVER_URL || 'http://localhost:8000')!, store, sharedScreen: interactiveMenu });\n if (again && config.saved) returnToSavedGames = true;\n if (direct || !again) keepGoing = false;\n }\n }\n } finally { menuScreen?.close(); store.close(); }\n}\n\nasync function mainMenu(store: GameStore, screen: MenuScreen, openSavedGames = false, update?: UpdateNotice, installed?: string): Promise<GameConfig | 'quit'> {\n const rl = createInterface({ input: stdin, output: stdout });\n try {\n while (true) {\n if (openSavedGames) {\n openSavedGames = false;\n const game = await savedGamesMenu(store, screen);\n if (game === 'quit') return 'quit';\n if (game) return game;\n continue;\n }\n const notice = update ? `\\n\\nUpdate available: ${installed} \u2192 ${update.version}\\nRun: ${update.command}` : '';\n screen.draw('ZCHESS / LOCAL STOCKFISH', ' 1 Play\\n 2 Load a saved game\\n 3 Quit' + notice, '');\n const choice = await menuKey('Select \u203A ', ['1', '2', '3']);\n if (choice === 'q') return 'quit';\n if (choice === 'b') continue;\n if (choice === '3') return 'quit';\n if (choice === '1') {\n const game = await newGameMenu(screen);\n if (game === 'quit') return 'quit';\n if (game) return game;\n }\n if (choice === '2' || choice === 'load') {\n const game = await savedGamesMenu(store, screen);\n if (game === 'quit') return 'quit';\n if (game) return game;\n }\n }\n } finally { rl.close(); }\n}\n\nasync function savedGamesMenu(store: GameStore, screen: MenuScreen): Promise<GameConfig | 'quit' | null> {\n const games = store.list();\n if (!games.length) {\n screen.draw('LOAD A SAVED GAME', 'No saved games yet.\\n\\n 1 Back\\n 2 Quit', '');\n const action = await menuKey('Select \u203A ', ['1', '2']);\n return action === '2' || action === 'q' ? 'quit' : null;\n }\n const recent = games.slice(0, 7);\n const lines = recent.map((game, index) => ` ${index + 1} ${game.updatedAt.slice(0, 16).replace('T', ' ')} \u00B7 ${game.elo} ELO \u00B7 ${game.moves.length ? game.moves.join(' ') : 'New game'} \u00B7 ${game.status}`);\n if (games.length > recent.length) lines.push(' Showing the 7 most recent games.');\n const backChoice = recent.length + 1;\n const quitChoice = recent.length + 2;\n lines.push(` ${backChoice} Back`, ` ${quitChoice} Quit`);\n screen.draw('LOAD A SAVED GAME', lines.join('\\n'), '');\n const selection = await menuKey('Choose a game \u203A ', Array.from({ length: quitChoice }, (_, index) => String(index + 1)));\n if (selection === 'q') return 'quit';\n if (Number(selection) === backChoice) return null;\n if (Number(selection) === quitChoice) return 'quit';\n const game = recent[Number(selection) - 1];\n return game ? { elo: game.elo, human: game.color, saved: game } : null;\n}\n\nasync function newGameMenu(screen: MenuScreen): Promise<GameConfig | null | 'quit'> {\n const choices = ELO_PRESETS.map(({ label, elo }, index) => ` ${index + 1} ${label} \u00B7 ${elo} ELO`);\n choices.push(' 6 Custom ELO');\n choices.push(' 7 Back', ' 8 Quit');\n screen.draw('NEW GAME / STOCKFISH STRENGTH', `${choices.join('\\n')}\\n\\nAvailable range: 1320\u20133190 ELO`, '');\n const selection = await menuKey('ELO \u203A ', ['1', '2', '3', '4', '5', '6', '7', '8']);\n if (selection === 'q') return 'quit';\n if (selection === '7') return null;\n if (selection === '8') return 'quit';\n let elo = ELO_PRESETS[Number(selection) - 1]?.elo;\n if (selection === '6') {\n let custom: number;\n while (true) {\n screen.draw('NEW GAME / CUSTOM ELO', 'Enter any ELO from 1320 to 3190.\\n\\n 0 Back\\n 00 Quit', '');\n const value = await menuText('ELO \u203A ');\n if (value === 'q') return 'quit';\n if (value === 'b' || value === null) return await newGameMenu(screen);\n custom = Number(value);\n if (Number.isInteger(custom) && custom >= 1320 && custom <= 3190) break;\n screen.draw('NEW GAME / CUSTOM ELO', 'Enter an ELO from 1320 to 3190.\\nThat value is outside the range.\\n\\n 0 Back\\n 00 Quit', '');\n }\n elo = custom;\n }\n if (elo === undefined) return null;\n while (true) {\n screen.draw('NEW GAME / CHOOSE SIDE', `Stockfish ${elo} ELO\\n\\n 1 White\\n 2 Black\\n 3 Random\\n 4 Back\\n 5 Quit`, '');\n const side = await menuKey('Side \u203A ', ['1', '2', '3', '4', '5']);\n if (side === 'q') return 'quit';\n if (side === '4') return await newGameMenu(screen);\n if (side === '5') return 'quit';\n const human: 'w' | 'b' = side === '1' ? 'w' : side === '2' ? 'b' : Math.random() < 0.5 ? 'w' : 'b';\n return { elo, human };\n }\n}\n\nfunction menuKey(prompt: string, choices: string[]): Promise<string> {\n return rawPrompt(prompt, (text, key, finish) => {\n if (key?.ctrl && key.name === 'c') { finish('q'); return; }\n const character = (text ?? '').toLowerCase();\n if (!key?.ctrl && choices.includes(character)) finish(character);\n });\n}\n\nfunction menuText(prompt: string): Promise<string | 'b' | 'q' | null> {\n let value = '';\n return rawPrompt(prompt, (text, key, finish) => {\n if (key?.ctrl && key.name === 'c') { finish('q'); return; }\n if (key?.name === 'backspace') {\n value = value.slice(0, -1);\n stdout.write('\\b \\b');\n return;\n }\n if (key?.name === 'return' || key?.name === 'enter') {\n finish(value === '0' ? 'b' : value === '00' ? 'q' : value);\n return;\n }\n const character = text ?? '';\n if (key?.ctrl || !character) return;\n value += character;\n stdout.write(character);\n });\n}\n\nfunction rawPrompt<T>(prompt: string, onKey: (text: string, key: Key, finish: (value: T) => void) => void): Promise<T> {\n const stream = stdin as typeof stdin & { setRawMode?: (mode: boolean) => void };\n if (!stream.isTTY || !stream.setRawMode) return Promise.reject(new Error('Menu selection requires an interactive terminal.'));\n const previous = stdin.listeners('keypress') as Array<(...args: any[]) => void>;\n previous.forEach(listener => stdin.removeListener('keypress', listener));\n stdout.write(`${promptColor}${prompt}${reset}`);\n stream.setRawMode(true);\n return new Promise(resolve => {\n let finished = false;\n const finish = (value: T): void => {\n if (finished) return;\n finished = true;\n stdin.removeListener('keypress', listener);\n stream.setRawMode(false);\n [...previous].reverse().forEach(listener => stdin.prependListener('keypress', listener));\n stdout.write('\\r\\n');\n resolve(value);\n };\n const listener = (text: string, key: Key): void => onKey(text, key, finish);\n stdin.on('keypress', listener);\n });\n}\n\nasync function playGame(config: GameConfig, options: { graphics: GraphicsMode; depth: number; serverUrl: string; store: GameStore; sharedScreen: boolean }): Promise<boolean> {\n const { elo, human, saved } = config;\n let startFen = saved?.startFen ?? config.fen ?? START_FEN;\n const chess = new Chess(startFen);\n if (saved) for (const move of saved.moves) chess.play(move);\n const abort = new AbortController();\n const server = new ChessServerClient(options.serverUrl, abort.signal);\n const rl = createInterface({ input: stdin, output: stdout });\n const screen = new GameScreen(Boolean(stdout.isTTY && stdin.isTTY), stdout, !options.sharedScreen);\n const useGraphics = supportsGraphics(options.graphics);\n let stopped = false;\n let redrawInput: (() => void) | undefined;\n let last: number[] | null = null;\n let showingHelp = false;\n let returnToMenu = false;\n let returnToMenuRequested = false;\n let search: AbortController | undefined;\n let notice = 'Your move';\n let gameId = saved?.id;\n const header = `CHESS / ${human === 'w' ? 'White' : 'Black'} / Stockfish ${elo} ELO`;\n const persist = (): void => {\n gameId = options.store.save({ elo, color: human, startFen, fen: chess.fen(), moves: chess.history.map(entry => entry.san), status: chess.status() ?? 'In progress' }, gameId);\n };\n const draw = (): void => screen.draw(header,\n showingHelp ? commandHelp()\n : useGraphics ? renderGraphics(chess, human, last, screen.active)\n : render(chess, { perspective: human, last, compact: screen.active && (stdout.rows || 40) < 36 }),\n notice, showingHelp ? '' : moveHistory(chess, Math.max(1, (stdout.columns || 80) - 1)));\n const takeBack = (): void => {\n notice = undoTurn(chess, human) ? 'Took back your last move and any Stockfish reply.' : 'No move to undo yet.';\n const move = chess.history.at(-1)?.move;\n last = move ? [move.from, move.to] : null;\n persist();\n };\n const shortcut = (text: string, key: Key): void => {\n if (stopped || returnToMenuRequested) return;\n if (key?.ctrl && key.name === 'c') { stop(); return; }\n };\n const stop = (): void => { stopped = true; abort.abort(); search?.abort(); };\n const resize = (): void => { if (!stopped) { draw(); redrawInput?.(); } };\n const question = async (placeholder: string): Promise<string> => {\n if (!screen.active) return await rl.question(`${promptColor}${placeholder} \u203A ${reset}`, { signal: abort.signal });\n const stream = stdin as typeof stdin & { setRawMode?: (mode: boolean) => void };\n const previousRaw = stream.isRaw;\n const previous = stdin.listeners('keypress') as Array<(text: string, key: Key) => void>;\n previous.forEach(listener => stdin.removeListener('keypress', listener));\n stream.setRawMode?.(true);\n return new Promise(resolve => {\n let value = '';\n let done = false;\n const redraw = (): void => screen.input(value, placeholder);\n const finish = (answer: string): void => {\n if (done) return;\n done = true;\n stdin.removeListener('keypress', onKey);\n abort.signal.removeEventListener('abort', onAbort);\n previous.forEach(listener => stdin.on('keypress', listener));\n stream.setRawMode?.(previousRaw);\n redrawInput = undefined;\n screen.input('', placeholder);\n resolve(answer);\n };\n const onAbort = (): void => finish('');\n const onKey = (text: string, key: Key): void => {\n if (key?.ctrl && key.name === 'c') { stop(); finish(''); return; }\n if (key?.name === 'return' || key?.name === 'enter') { finish(value); return; }\n value = editGameInput(value, text, key);\n redraw();\n };\n redrawInput = redraw;\n stdin.on('keypress', onKey);\n abort.signal.addEventListener('abort', onAbort, { once: true });\n redraw();\n });\n };\n stdin.on('keypress', shortcut);\n rl.on('SIGINT', stop);\n rl.on('close', stop);\n process.on('SIGINT', stop);\n process.on('SIGTERM', stop);\n stdout.on('resize', resize);\n screen.open();\n persist();\n\n try {\n while (!stopped && !returnToMenuRequested) {\n const status = chess.status();\n if (status) {\n notice = status;\n persist();\n draw();\n if (screen.active) {\n const command = await question('Type /undo, /back, or /quit \u00B7 Ctrl+C quit');\n if (command.trim().toLowerCase() === '/undo') { takeBack(); continue; }\n if (/^\\/(quit|exit)$/.test(command.trim().toLowerCase())) { stop(); break; }\n break;\n }\n console.log(status);\n break;\n }\n if (chess.turn !== human) {\n notice = 'Stockfish is thinking\u2026';\n draw();\n search = new AbortController();\n let move: string;\n try { move = await engineMove(chess.fen(), elo, options.depth, search.signal); }\n catch (error) {\n if (returnToMenuRequested) break;\n throw error;\n } finally { search = undefined; }\n const side = chess.turn;\n const san = chess.play(move);\n const played = chess.history.at(-1)!.move;\n last = [played.from, played.to];\n notice = `${side === 'w' ? 'White' : 'Black'} plays ${san}`;\n persist();\n continue;\n }\n\n draw();\n let raw: string;\n try { raw = await question(showingHelp ? 'Type /back to return to the game' : 'Type any moves e.g. e4 or e pawn up 2'); }\n catch (error) { if (returnToMenuRequested) break; throw error; }\n const wasShowingHelp = showingHelp;\n showingHelp = false;\n if (wasShowingHelp && /^\\/back$/i.test(raw.trim())) { notice = 'Your move'; continue; }\n let intent;\n try { intent = await modelInput(raw, chess, server); }\n catch (error) { notice = message(error); continue; }\n if (stopped) break;\n if (intent.type === 'quit') { stop(); break; }\n if (intent.type === 'help') { notice = 'Available commands'; showingHelp = true; continue; }\n if (intent.type === 'back') { returnToMenuRequested = true; break; }\n if (intent.type === 'show-fen') { notice = chess.fen(); continue; }\n if (intent.type === 'load-fen') {\n try { chess.load(intent.value); startFen = intent.value; last = null; notice = 'Position loaded.'; persist(); }\n catch (error) { notice = message(error); }\n continue;\n }\n if (intent.type === 'undo') { takeBack(); continue; }\n if (intent.type === 'empty') continue;\n try {\n const san = chess.play(intent.value);\n const move = chess.history.at(-1)!.move;\n last = [move.from, move.to];\n notice = intent.source === 'jev' ? `JEV chose ${san}` : `You played ${san}`;\n persist();\n } catch (error) { notice = `${message(error)}. Try e2e4, Nf3, or describe the move.`; }\n }\n } catch (error) { if (!stopped) throw error; }\n finally {\n returnToMenu = screen.active && !stopped;\n stdin.off('keypress', shortcut);\n stdout.off('resize', resize);\n process.off('SIGINT', stop);\n process.off('SIGTERM', stop);\n rl.close();\n screen.close();\n }\n return returnToMenu || screen.active && returnToMenuRequested;\n}\n\nexport { HELP };\nconst message = (error: unknown): string => error instanceof Error ? error.message : String(error);\n", "export const START_FEN = 'rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0 1';\nconst FILES = 'abcdefgh';\nconst KNIGHT: Direction[] = [[1,2],[2,1],[2,-1],[1,-2],[-1,-2],[-2,-1],[-2,1],[-1,2]];\nconst KING: Direction[] = [[1,0],[-1,0],[0,1],[0,-1],[1,1],[1,-1],[-1,1],[-1,-1]];\ntype Side = 'w' | 'b';\ntype Piece = 'P'|'N'|'B'|'R'|'Q'|'K'|'p'|'n'|'b'|'r'|'q'|'k';\ntype Direction = [number, number];\nexport interface Move { from:number; to:number; promotion:string|null; flags:string }\nexport interface PositionSnapshot { board:(Piece|null)[]; turn:Side; castling:string; ep:number; halfmove:number; fullmove:number }\nexport interface HistoryEntry { move:Move; san:string; before:PositionSnapshot }\n\nexport const squareName = (i:number):string => FILES[i % 8] + (8 - Math.floor(i / 8));\nexport const squareIndex = (s:string):number => /^[a-h][1-8]$/i.test(s) ? (8 - Number(s[1])) * 8 + FILES.indexOf(s[0].toLowerCase()) : -1;\nconst color = (p:Piece|null):Side|null => p ? (p === p.toUpperCase() ? 'w' : 'b') : null;\n\nexport class Chess {\n board:(Piece|null)[]=[]; turn:Side='w'; castling=''; ep=-1; halfmove=0; fullmove=1; history:HistoryEntry[]=[];\n constructor(fen:string = START_FEN) { this.load(fen); }\n load(fen:string):this {\n const [placement, turn, castling = '-', ep = '-', half = '0', full = '1'] = fen.trim().split(/\\s+/);\n const ranks = placement?.split('/');\n if (!ranks || ranks.length !== 8 || !/^[wb]$/.test(turn)) throw new Error('Invalid FEN');\n this.board = [];\n for (const rank of ranks) {\n for (const c of rank) {\n if (/\\d/.test(c)) this.board.push(...Array(Number(c)).fill(null));\n else if (/[prnbqkPRNBQK]/.test(c)) this.board.push(c as Piece);\n else throw new Error('Invalid FEN');\n }\n }\n if (this.board.length !== 64) throw new Error('Invalid FEN');\n this.turn = turn as Side; this.castling = castling === '-' ? '' : castling; this.ep = ep === '-' ? -1 : squareIndex(ep);\n this.halfmove = Number(half); this.fullmove = Number(full); this.history = [];\n if (this.ep < -1 || !Number.isFinite(this.halfmove) || !Number.isFinite(this.fullmove)) throw new Error('Invalid FEN');\n return this;\n }\n fen():string {\n let out = '';\n for (let r=0;r<8;r++) { let empty=0; for(let f=0;f<8;f++){ const p=this.board[r*8+f]; if(!p) empty++; else {if(empty){out+=empty;empty=0;} out+=p;} } if(empty)out+=empty; if(r<7)out+='/'; }\n return `${out} ${this.turn} ${this.castling || '-'} ${this.ep < 0 ? '-' : squareName(this.ep)} ${this.halfmove} ${this.fullmove}`;\n }\n attacked(sq:number, by:Side):boolean {\n const r=Math.floor(sq/8), f=sq%8;\n const pawn = by==='w'?'P':'p', pawnRow = r + (by==='w'?1:-1);\n for(const df of [-1,1]) if(pawnRow>=0&&pawnRow<8&&f+df>=0&&f+df<8&&this.board[pawnRow*8+f+df]===pawn)return true;\n for(const [df,dr] of KNIGHT){const rr=r+dr,ff=f+df;if(rr>=0&&rr<8&&ff>=0&&ff<8&&this.board[rr*8+ff]===(by==='w'?'N':'n'))return true;}\n for(const [df,dr] of KING){const rr=r+dr,ff=f+df;if(rr>=0&&rr<8&&ff>=0&&ff<8&&this.board[rr*8+ff]===(by==='w'?'K':'k'))return true;}\n for(const [df,dr,types] of [[1,0,'RQ'],[-1,0,'RQ'],[0,1,'RQ'],[0,-1,'RQ'],[1,1,'BQ'],[-1,1,'BQ'],[1,-1,'BQ'],[-1,-1,'BQ']] as [number,number,string][]) {\n let rr=r+dr,ff=f+df; while(rr>=0&&rr<8&&ff>=0&&ff<8){const p=this.board[rr*8+ff];if(p){if(color(p)===by&&types.includes(p.toUpperCase()))return true;break;}rr+=dr;ff+=df;\n }} return false;\n }\n inCheck(side:Side=this.turn):boolean { const king=this.board.indexOf(side==='w'?'K':'k'); return king<0 || this.attacked(king,side==='w'?'b':'w'); }\n pseudo():Move[] {\n const moves:Move[]=[];\n const add=(from:number,to:number,promotion:string|null=null,flags='')=>moves.push({from,to,promotion,flags});\n for(let from=0;from<64;from++){const p=this.board[from];if(!p||color(p)!==this.turn)continue;const type=p.toUpperCase(),r=Math.floor(from/8),f=from%8;\n if(type==='P'){const dir=this.turn==='w'?-1:1, home=this.turn==='w'?6:1, last=this.turn==='w'?0:7;const one=(r+dir)*8+f;\n if(r+dir>=0&&r+dir<8&&!this.board[one]){if(r+dir===last)for(const q of 'qrbn')add(from,one,q,'p');else add(from,one);const two=(r+2*dir)*8+f;if(r===home&&!this.board[two])add(from,two,null,'d');}\n for(const df of [-1,1]){const rr=r+dir,ff=f+df;if(rr<0||rr>7||ff<0||ff>7)continue;const to=rr*8+ff;if((this.board[to]&&color(this.board[to])!==this.turn)||to===this.ep){if(rr===last)for(const q of 'qrbn')add(from,to,q,to===this.ep?'ep':'cp');else add(from,to,null,to===this.ep?'e':'c');}}\n } else if(type==='N'||type==='K'){for(const [df,dr] of type==='N'?KNIGHT:KING){const rr=r+dr,ff=f+df;if(rr>=0&&rr<8&&ff>=0&&ff<8&&color(this.board[rr*8+ff])!==this.turn)add(from,rr*8+ff,null,this.board[rr*8+ff]?'c':'');}\n if(type==='K')this.castleMoves(from,add);\n } else {const dirs=type==='B'?KING.slice(4):type==='R'?KING.slice(0,4):KING;for(const[df,dr]of dirs){let rr=r+dr,ff=f+df;while(rr>=0&&rr<8&&ff>=0&&ff<8){const to=rr*8+ff;if(color(this.board[to])===this.turn)break;add(from,to,null,this.board[to]?'c':'');if(this.board[to])break;rr+=dr;ff+=df;}}}\n } return moves;\n }\n castleMoves(from:number, add:(from:number,to:number,promotion?:string|null,flags?:string)=>void):void {\n const white=this.turn==='w', base=white?60:4, enemy=white?'b':'w'; if(from!==base||this.inCheck())return;\n const king=white?'K':'k', rook=white?'R':'r'; if(this.board[from]!==king)return;\n if(this.castling.includes(white?'K':'k')&&this.board[base+3]===rook&&!this.board[base+1]&&!this.board[base+2]&&!this.attacked(base+1,enemy)&&!this.attacked(base+2,enemy))add(from,base+2,null,'k');\n if(this.castling.includes(white?'Q':'q')&&this.board[base-4]===rook&&!this.board[base-1]&&!this.board[base-2]&&!this.board[base-3]&&!this.attacked(base-1,enemy)&&!this.attacked(base-2,enemy))add(from,base-2,null,'q');\n }\n moves():Move[] { return this.pseudo().filter(m=>{const snapshot=this.snapshot();this.apply(m);const bad=this.inCheck(this.turn==='w'?'b':'w');this.restore(snapshot);return !bad;}); }\n snapshot():PositionSnapshot{return {board:[...this.board],turn:this.turn,castling:this.castling,ep:this.ep,halfmove:this.halfmove,fullmove:this.fullmove};}\n restore(s:PositionSnapshot):void{Object.assign(this,s);}\n apply(m:Move):void{const p=this.board[m.from]! as Piece, side=this.turn, captured=this.board[m.to];this.board[m.to]=(m.promotion?(side==='w'?m.promotion.toUpperCase():m.promotion):p) as Piece;this.board[m.from]=null;\n if(m.flags.includes('e'))this.board[m.to+(side==='w'?8:-8)]=null;\n if(m.flags==='k'){this.board[m.to-1]=this.board[m.to+1];this.board[m.to+1]=null;} if(m.flags==='q'){this.board[m.to+1]=this.board[m.to-2];this.board[m.to-2]=null;}\n const rights:Record<number,string>={0:'q',4:'kq',7:'k',56:'Q',60:'KQ',63:'K'};for(const sq of [m.from,m.to])if(rights[sq])for(const x of rights[sq])this.castling=this.castling.replace(x,'');\n this.ep=m.flags==='d'?(m.from+m.to)/2:-1;this.halfmove=(p.toUpperCase()==='P'||captured||m.flags.includes('e'))?0:this.halfmove+1;if(side==='b')this.fullmove++;this.turn=side==='w'?'b':'w';\n }\n san(m:Move, legal:Move[]=this.moves()):string {const p=this.board[m.from]!, type=p.toUpperCase();if(m.flags==='k')return'O-O';if(m.flags==='q')return'O-O-O';let s=type==='P'?'':type;\n if(type!=='P'){const same=legal.filter(x=>x!==m&&x.to===m.to&&this.board[x.from]?.toUpperCase()===type);if(same.length){if(same.every(x=>x.from%8!==m.from%8))s+=FILES[m.from%8];else if(same.every(x=>Math.floor(x.from/8)!==Math.floor(m.from/8)))s+=8-Math.floor(m.from/8);else s+=squareName(m.from);}}\n if(m.flags.includes('c')||m.flags.includes('e'))s+=(type==='P'?FILES[m.from%8]:'')+'x';s+=squareName(m.to);if(m.promotion)s+='='+m.promotion.toUpperCase();const snap=this.snapshot();this.apply(m);if(this.inCheck()){s+=this.moves().length?'#'.replace('#','+'):'#';}this.restore(snap);return s;\n }\n play(input:string):string {const legal=this.moves(), normalized=input.trim().replace(/[!?+#]/g,'').replace(/0/g,'O');let move=legal.find(m=>`${squareName(m.from)}${squareName(m.to)}${m.promotion||''}`===normalized.toLowerCase());if(!move)move=legal.find(m=>this.san(m,legal).replace(/[+#]/g,'')===normalized);if(!move)throw new Error(`Illegal or unrecognized move: ${input}`);const san=this.san(move,legal), before=this.snapshot();this.apply(move);this.history.push({move,san,before});return san;}\n undo():HistoryEntry|undefined{const h=this.history.pop();if(h)this.restore(h.before);return h;}\n status():string|null{const moves=this.moves();if(!moves.length)return this.inCheck()?(this.turn==='w'?'Black':'White')+' wins by checkmate':'Draw by stalemate';if(this.halfmove>=100)return'Draw by fifty-move rule';return null;}\n}\n", "import type { Chess } from './index.js';\nexport interface MoveResult { move: string; fen: string; explanation: string }\nexport interface MoveResolver { resolve(text: string, chess: Chess): Promise<MoveResult> }\nexport class ResolutionError extends Error {\n constructor(message: string, readonly status: number) { super(message); }\n}\n", "import { Chess, squareName } from './index.js';\n\nconst names: Record<string, string> = { P: 'Pawn', N: 'Knight', B: 'Bishop', R: 'Rook', Q: 'Queen', K: 'King' };\n\n/** Explain a recognizable move rejected for king safety, without changing the game. */\nexport function illegalMoveReason(input: string, chess: Chess): string | undefined {\n const text = input.trim();\n const uci = /^([a-h][1-8])([a-h][1-8])([qrbn])?$/.exec(text);\n const san = /^([KQRBN])?([a-h])?([1-8])?(x)?([a-h][1-8])(?:=([QRBN]))?[+#]?$/.exec(text);\n const words = text.toLowerCase();\n const squares = words.match(/[a-h][1-8]/g) || [];\n const named = words.match(/\\bwith (?:my |the |a )?(pawn|knight|bishop|rook|queen|king)\\b/)?.[1]\n || words.match(/\\b(pawn|knight|bishop|rook|queen|king)\\b/)?.[1];\n const kind = uci ? undefined : san ? san[1] || 'P'\n : Object.keys(names).find(key => names[key].toLowerCase() === named);\n const from = uci?.[1] || (squares.length > 1 ? squares[0] : undefined);\n const to = uci?.[2] || san?.[5] || squares.at(-1);\n if (!to || (!uci && !san && !kind && !from)) return;\n const capture = san ? Boolean(san[4]) : /\\b(take|takes|taking|capture|captures|capturing)\\b/.test(words);\n const candidates = chess.pseudo().filter(move => {\n if (squareName(move.to) !== to) return false;\n if (from && squareName(move.from) !== from) return false;\n if (kind && chess.board[move.from]!.toUpperCase() !== kind) return false;\n if (san?.[2] && squareName(move.from)[0] !== san[2]) return false;\n if (san?.[3] && squareName(move.from)[1] !== san[3]) return false;\n if (capture && !/[ce]/.test(move.flags)) return false;\n return true;\n });\n const legal = chess.moves();\n // A legal interpretation or multiple possible pieces needs clarification, not a pin claim.\n if (candidates.length !== 1 || legal.some(move => move.from === candidates[0].from && move.to === candidates[0].to)) return;\n const move = candidates[0];\n const copy = new Chess(chess.fen());\n copy.apply(move);\n if (!copy.inCheck(chess.turn)) return;\n const piece = chess.board[move.from]!.toUpperCase();\n if (piece === 'K') return `King cannot move to ${to}: that square is attacked.`;\n if (chess.inCheck()) return 'You are in check; this move would leave your king in check.';\n\n const king = chess.board.indexOf(chess.turn === 'w' ? 'K' : 'k');\n const dr = Math.floor(move.from / 8) - Math.floor(king / 8);\n const df = move.from % 8 - king % 8;\n if (dr === 0 || df === 0 || Math.abs(dr) === Math.abs(df)) {\n const stepR = Math.sign(dr), stepF = Math.sign(df);\n let rank = Math.floor(king / 8) + stepR, file = king % 8 + stepF;\n let passedPiece = false;\n while (rank >= 0 && rank < 8 && file >= 0 && file < 8) {\n const index = rank * 8 + file;\n const blocker = chess.board[index];\n if (index === move.from) passedPiece = true;\n else if (blocker) {\n const enemy = (blocker === blocker.toUpperCase() ? 'w' : 'b') !== chess.turn;\n const slider = (dr === 0 || df === 0 ? 'RQ' : 'BQ').includes(blocker.toUpperCase());\n if (passedPiece && enemy && slider) {\n return `${names[piece]} ${squareName(move.from)} is pinned by ${names[blocker.toUpperCase()].toLowerCase()} ${squareName(index)}; moving it exposes your king.`;\n }\n break;\n }\n rank += stepR;\n file += stepF;\n }\n }\n return `${names[piece]} ${squareName(move.from)} cannot move to ${to}: it would expose your king to check.`;\n}\n", "import { squareName, type Chess } from './index.js';\n\nconst names: Record<string, string> = { king: 'K', queen: 'Q', rook: 'R', bishop: 'B', knight: 'N', pawn: 'P' };\nexport function normalizeNotation(text: string): string {\n const symbols: Record<string, string> = { '\u2654':'K', '\u265A':'K', '\u2655':'Q', '\u265B':'Q', '\u2656':'R', '\u265C':'R', '\u2657':'B', '\u265D':'B', '\u2658':'N', '\u265E':'N', '\u2659':'', '\u265F':'' };\n return text.trim().replace(/[\u2654\u265A\u2655\u265B\u2656\u265C\u2657\u265D\u2658\u265E\u2659\u265F]/g, symbol => symbols[symbol])\n .replace(/\u00D7/g, 'x').replace(/([a-h][1-8])\\s*(?:\u2192|->|-)\\s*(?=[a-h][1-8])/g, '$1').replace(/0/g, 'O');\n}\n\nexport const looksLikeNotation = (text: string): boolean => !/\\s/.test(text) && (/\\d/.test(text) || /^[O0]-[O0]/.test(text));\n\nfunction distance(a: string, b: string): number {\n let row = Array.from({ length: b.length + 1 }, (_, i) => i);\n for (let i = 0; i < a.length; i++) {\n const next = [i + 1];\n for (let j = 0; j < b.length; j++) next.push(Math.min(next[j] + 1, row[j + 1] + 1, row[j] + Number(a[i] !== b[j])));\n row = next;\n }\n return row[b.length];\n}\n\n/** Prefer matching legal moves, then offer explicitly labeled legal alternatives. */\nexport function suggestMoves(input: string, chess: Chess): string[] {\n const text = normalizeNotation(input);\n const lower = text.toLowerCase();\n const notation = looksLikeNotation(text);\n const squares = lower.match(/[a-h][1-8]/g) || [];\n const destination = squares.at(-1);\n const source = squares.length > 1 ? squares[0] : undefined;\n const named = lower.match(/\\bwith (?:my |the |a )?(king|queen|rook|bishop|knight|pawn)\\b/)?.[1]\n || lower.match(/\\b(king|queen|rook|bishop|knight|pawn)\\b/)?.[1];\n const piece = named ? names[named] : notation && !/^[a-h][1-8][a-h][1-8]/.test(text)\n ? (/^[KQRBN]/.exec(text)?.[0] || (/^[a-h]/.test(text) ? 'P' : undefined)) : undefined;\n const capture = notation ? text.includes('x') : /\\b(take|takes|taking|capture|captures|capturing)\\b/.test(lower);\n const castle = /\\bcastl/.test(lower) || /^[O0]-[O0]/.test(text);\n const legal = chess.moves();\n const matches = legal.map(move => {\n const san = chess.san(move, legal);\n const from = squareName(move.from), to = squareName(move.to);\n const kind = chess.board[move.from]!.toUpperCase();\n if (piece && kind !== piece) return null;\n if (source && from !== source) return null;\n if (capture && !san.includes('x')) return null;\n if (castle && !san.startsWith('O-O')) return null;\n if (!notation && destination && to !== destination) return null;\n const uci = from + to + (move.promotion || '');\n const difference = Math.min(distance(text, san), distance(lower, uci));\n if (notation && difference > 2 && to !== destination) return null;\n return { san, score: (to === destination ? 20 : 0) + (from === source ? 10 : 0) - difference };\n }).filter((entry): entry is { san: string; score: number } => entry !== null)\n .sort((a, b) => b.score - a.score || a.san.localeCompare(b.san)).slice(0, 5).map(entry => entry.san);\n return matches.length ? matches : legal.map(move => chess.san(move, legal)).sort().slice(0, 5);\n}\n\nexport function suggestionMessage(input: string, chess: Chess): string {\n const moves = suggestMoves(input, chess);\n return moves.length ? `No exact match. Try: ${moves.join(' \u00B7 ')} (legal alternatives; confirm your intended move).` : 'No legal moves are available.';\n}\n", "import { squareName } from './index.js';\nimport type { Chess } from './index.js';\nimport { ResolutionError, type MoveResolver } from './resolution.js';\nimport { illegalMoveReason } from './legality.js';\nimport { looksLikeNotation, normalizeNotation, suggestionMessage } from './suggestions.js';\n\nexport type InputIntent =\n | { type:'empty' }\n | { type:'quit' }\n | { type:'help' }\n | { type:'undo' }\n | { type:'back' }\n | { type:'show-fen' }\n | { type:'load-fen'; value:string }\n | { type:'move'; value:string; source:'notation'|'jev'; fen?:string; explanation?:string };\n\n/** Parse local commands/notation; delegate all genuinely free-form text to JEV. */\nexport async function modelInput(raw:string, chess:Chess, server?:MoveResolver):Promise<InputIntent> {\n const text = String(raw).trim();\n const lower = text.toLowerCase();\n if (!text) return { type: 'empty' };\n if (/^\\/(quit|exit)$/.test(lower)) return { type: 'quit' };\n if (lower === '/help') return { type: 'help' };\n if (lower === '/undo') return { type: 'undo' };\n if (/^\\/(back|menu)$/.test(lower)) return { type: 'back' };\n if (/^\\/(fen|position)$/.test(lower)) return { type: 'show-fen' };\n if (/^\\/(fen|position)\\s+/.test(lower)) return { type: 'load-fen', value: text.replace(/^\\/(?:fen|position)\\s+/i, '').trim() };\n if (lower.startsWith('/')) throw new Error(`Unknown command: ${text}. Type /help to see commands.`);\n\n const legal = chess.moves();\n const normalized = normalizeNotation(text);\n const exact = legal.find(move => {\n const uci = squareName(move.from) + squareName(move.to) + (move.promotion || '');\n return uci === normalized || chess.san(move, legal) === normalized;\n });\n if (exact) return { type: 'move', value: squareName(exact.from) + squareName(exact.to) + (exact.promotion || ''), source: 'notation' };\n\n const reason = illegalMoveReason(text, chess);\n if (reason) throw new Error(`${reason} ${suggestionMessage(text, chess)}`);\n if (looksLikeNotation(text)) throw new Error(suggestionMessage(text, chess));\n\n if (!server) throw new Error(`Chess server is required for natural-language input. ${suggestionMessage(text, chess)}`);\n let result;\n try { result = await server.resolve(text, chess); }\n catch (error) {\n if (error instanceof ResolutionError && error.status === 422) throw new Error(suggestionMessage(text, chess));\n if (error instanceof Error && error.name === 'AbortError') throw error;\n const detail = error instanceof Error ? error.message : String(error);\n throw new Error(`${detail}. ${suggestionMessage(text, chess)}`);\n }\n return { type: 'move', value: result.move, fen: result.fen, explanation: result.explanation, source: 'jev' };\n}\n", "import type { Chess } from './index.js';\n\n/** Undo through the player's most recent move, including any engine reply. */\nexport function undoTurn(chess: Chess, human: 'w' | 'b'): boolean {\n let index = chess.history.length - 1;\n while (index >= 0 && chess.history[index].before.turn !== human) index--;\n if (index < 0) return false;\n while (chess.history.length > index) chess.undo();\n return true;\n}\n\nexport function moveHistory(chess: Chess, width = 80): string {\n const groups: string[] = [];\n for (const entry of chess.history) {\n const { fullmove, turn } = entry.before;\n if (turn === 'w') groups.push(`${fullmove}. ${entry.san}`);\n else if (groups.length) groups[groups.length - 1] += ` ${entry.san}`;\n else groups.push(`${fullmove}\u2026 ${entry.san}`);\n }\n if (!groups.length) return 'Moves: \u2014';\n let clipped = false;\n while (groups.length > 1 && `Moves: ${clipped ? '\u2026 ' : ''}${groups.join(' ')}`.length > width) {\n groups.shift();\n clipped = true;\n }\n return `Moves: ${clipped ? '\u2026 ' : ''}${groups.join(' ')}`;\n}\n", "import type { Chess } from '@zchess/chess';\nimport { ResolutionError, type MoveResult } from '@zchess/chess/interaction';\nexport { ResolutionError, type MoveResult } from '@zchess/chess/interaction';\nexport class ChessServerClient {\n constructor(private readonly baseUrl=process.env.ZCHESS_SERVER_URL||'http://localhost:8000', private readonly signal?:AbortSignal){}\n async resolve(text:string,chess:Chess):Promise<MoveResult>{return this.post('/api/resolve',{instruction:text,fen:chess.fen()});}\n private async post(path:string,body:unknown):Promise<MoveResult>{const response=await fetch(this.baseUrl.replace(/\\/$/,'')+path,{method:'POST',headers:{'content-type':'application/json'},body:JSON.stringify(body),signal:this.signal});if(!response.ok){\n const body = await response.json().catch(() => ({})) as {detail?:unknown};\n throw new ResolutionError(typeof body.detail === 'string' ? body.detail : `Chess server failed (${response.status})`, response.status);\n }return response.json() as Promise<MoveResult>;}\n}\n", "import type { Chess } from '@zchess/chess';\n\nconst PIECES: Record<string, string> = {\n K: '\u265A', Q: '\u265B', R: '\u265C', B: '\u265D', N: '\u265E', P: '\u265F',\n k: '\u265A', q: '\u265B', r: '\u265C', b: '\u265D', n: '\u265E', p: '\u265F',\n};\nconst OUTLINES: Record<string, string> = { K: '\u2654', Q: '\u2655', R: '\u2656', B: '\u2657', N: '\u2658', P: '\u2659' };\nconst RESET = '\\x1b[0m';\ninterface RenderOptions { perspective?: 'w' | 'b'; last?: number[] | null; color?: boolean; compact?: boolean }\n\nexport function render(chess: Chess, { perspective = 'w', last = null, color = Boolean(process.stdout.isTTY), compact = false }: RenderOptions = {}): string {\n const rows = perspective === 'w' ? [0, 1, 2, 3, 4, 5, 6, 7] : [7, 6, 5, 4, 3, 2, 1, 0];\n const files = perspective === 'w' ? [0, 1, 2, 3, 4, 5, 6, 7] : [7, 6, 5, 4, 3, 2, 1, 0];\n const cellWidth = Math.max(6, Math.min(8, Math.floor(((process.stdout.columns || 80) - 8) / 8)));\n const cell = (content = ''): string => {\n const left = Math.floor((cellWidth - 1) / 2);\n return `${' '.repeat(left)}${content}${' '.repeat(cellWidth - left - (content ? 1 : 0))}`;\n };\n const green = (text: string): string => color ? `\\x1b[38;5;114m${text}${RESET}` : text;\n const border = green(` +${'-'.repeat(cellWidth * 8)}+`);\n const output = [border];\n\n for (const rank of rows) {\n for (const line of compact ? [1] : [0, 1, 2]) {\n let row = green(`${line === 1 ? ` ${8 - rank} ` : ' '}|`);\n for (const file of files) {\n const index = rank * 8 + file;\n const piece = chess.board[index];\n const white = piece !== null && piece === piece.toUpperCase();\n const glyph = piece ? (!color && white ? OUTLINES[piece] : PIECES[piece]) : ' ';\n let square = cell(line === 1 ? glyph : '');\n if (color) {\n const background = last?.includes(index) ? 107 : (rank + file) % 2 ? 65 : 108;\n square = `\\x1b[1;48;5;${background};38;5;${white ? 231 : 16}m${square}${RESET}`;\n } else if (!piece && line === 1) {\n square = cell((rank + file) % 2 ? '\u00B7' : '');\n }\n row += square;\n }\n output.push(row + green('|'));\n }\n }\n output.push(border);\n output.push(green(' ' + files.map(file => cell('abcdefgh'[file])).join('')));\n output.push(color\n ? ` \\x1b[1;38;5;231m\u265A White${RESET} ${green('\u265A Black \u00B7 dark pieces')}`\n : ' \u2654 White \u265A Black');\n return output.join('\\n') + '\\n';\n}\n", "import { createRequire } from 'node:module';\nimport type { Chess } from '@zchess/chess';\nimport piecesData from '@zchess/chess/pieces' with { type: 'json' };\n\nconst require = createRequire(import.meta.url);\nconst pieces = piecesData as Record<string, string>;\nconst IMAGE_ID = 73191;\nexport type GraphicsMode = 'auto' | 'kitty' | 'text';\n\nexport function supportsGraphics(mode: GraphicsMode, tty = Boolean(process.stdout.isTTY), env = process.env): boolean {\n if (!tty || mode === 'text') return false;\n if (mode === 'kitty') return true;\n if (env.TMUX || env.STY) return false;\n return env.TERM_PROGRAM === 'ghostty' || env.TERM === 'xterm-ghostty' || env.TERM === 'xterm-kitty';\n}\n\nexport function boardSvg(chess: Chess, perspective: 'w' | 'b', last: number[] | null): string {\n const order = perspective === 'w' ? [0, 1, 2, 3, 4, 5, 6, 7] : [7, 6, 5, 4, 3, 2, 1, 0];\n const svg = ['<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"768\" height=\"768\" viewBox=\"0 0 768 768\">',\n '<rect width=\"768\" height=\"768\" rx=\"12\" fill=\"#14291f\"/>'];\n for (const [y, rank] of order.entries()) {\n for (const [x, file] of order.entries()) {\n const index = rank * 8 + file;\n const left = 24 + x * 90, top = 24 + y * 90;\n const fill = last?.includes(index) ? '#b4cf68' : (rank + file) % 2 ? '#64916d' : '#d5e5cb';\n svg.push(`<rect x=\"${left}\" y=\"${top}\" width=\"90\" height=\"90\" fill=\"${fill}\"/>`);\n const piece = chess.board[index];\n if (piece) svg.push(`<g transform=\"translate(${left} ${top}) scale(2)\">${pieces[piece]}</g>`);\n }\n svg.push(`<text x=\"12\" y=\"${24 + y * 90 + 50}\" text-anchor=\"middle\" font-size=\"16\" font-family=\"sans-serif\" fill=\"#d5e5cb\">${8 - rank}</text>`);\n }\n for (const [x, file] of order.entries()) {\n svg.push(`<text x=\"${24 + x * 90 + 45}\" y=\"762\" text-anchor=\"middle\" font-size=\"16\" font-family=\"sans-serif\" fill=\"#d5e5cb\">${'abcdefgh'[file]}</text>`);\n }\n svg.push('</svg>');\n return svg.join('');\n}\n\nexport function boardPng(chess: Chess, perspective: 'w' | 'b', last: number[] | null): Buffer {\n const { Resvg } = require('@resvg/resvg-js') as typeof import('@resvg/resvg-js');\n return new Resvg(boardSvg(chess, perspective, last)).render().asPng();\n}\n\nexport function renderGraphics(chess: Chess, perspective: 'w' | 'b', last: number[] | null, fixed = false): string {\n // The supplied Ghostty screenshot shows that this terminal's cells are a\n // little narrower than the usual 2:1 estimate. Use a 2.2:1 placement so the\n // rendered board squares do not appear tall.\n const columnsPerRow = 2.2;\n const availableRows = Math.max(1, (process.stdout.rows || 40) - (fixed ? 8 : 7));\n const availableColumns = Math.max(2, (process.stdout.columns || 80) - 2);\n const rows = Math.max(1, Math.min(32, availableRows, Math.floor(availableColumns / columnsPerRow)));\n const columns = Math.min(availableColumns, Math.round(rows * columnsPerRow));\n const data = boardPng(chess, perspective, last).toString('base64');\n // Reserve room first: images anchored near the bottom must not cover the prompt.\n let output = `\\x1b_Ga=d,d=I,i=${IMAGE_ID},q=2;\\x1b\\\\`;\n if (!fixed) output += '\\n'.repeat(rows) + `\\x1b[${rows}A\\r`;\n for (let offset = 0; offset < data.length; offset += 4096) {\n const chunk = data.slice(offset, offset + 4096);\n const more = offset + 4096 < data.length ? 1 : 0;\n const control = offset === 0 ? `a=T,f=100,t=d,i=${IMAGE_ID},c=${columns},r=${rows},C=1,q=2,` : '';\n output += `\\x1b_G${control}m=${more};${chunk}\\x1b\\\\`;\n }\n return output + `\\x1b[${rows}B\\r`;\n}\n", "{\n \"b\": \"<g id=\\\"black-bishop\\\" class=\\\"black bishop\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M9 36c3.39-.97 10.11.43 13.5-2 3.39 2.43 10.11 1.03 13.5 2 0 0 1.65.54 3 2-.68.97-1.65.99-3 .5-3.39-.97-10.11.46-13.5-1-3.39 1.46-10.11.03-13.5 1-1.354.49-2.323.47-3-.5 1.354-1.94 3-2 3-2zm6-4c2.5 2.5 12.5 2.5 15 0 .5-1.5 0-2 0-2 0-2.5-2.5-4-2.5-4 5.5-1.5 6-11.5-5-15.5-11 4-10.5 14-5 15.5 0 0-2.5 1.5-2.5 4 0 0-.5.5 0 2zM25 8a2.5 2.5 0 1 1-5 0 2.5 2.5 0 1 1 5 0z\\\" fill=\\\"#000\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M17.5 26h10M15 30h15m-7.5-14.5v5M20 18h5\\\" stroke=\\\"#fff\\\" stroke-linejoin=\\\"miter\\\"/></g>\",\n \"k\": \"<g id=\\\"black-king\\\" class=\\\"black king\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M22.5 11.63V6\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M22.5 25s4.5-7.5 3-10.5c0 0-1-2.5-3-2.5s-3 2.5-3 2.5c-1.5 3 3 10.5 3 10.5\\\" fill=\\\"#000\\\" stroke-linecap=\\\"butt\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M11.5 37c5.5 3.5 15.5 3.5 21 0v-7s9-4.5 6-10.5c-4-6.5-13.5-3.5-16 4V27v-3.5c-3.5-7.5-13-10.5-16-4-3 6 5 10 5 10V37z\\\" fill=\\\"#000\\\"/><path d=\\\"M20 8h5\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M32 29.5s8.5-4 6.03-9.65C34.15 14 25 18 22.5 24.5l.01 2.1-.01-2.1C20 18 9.906 14 6.997 19.85c-2.497 5.65 4.853 9 4.853 9M11.5 30c5.5-3 15.5-3 21 0m-21 3.5c5.5-3 15.5-3 21 0m-21 3.5c5.5-3 15.5-3 21 0\\\" stroke=\\\"#fff\\\"/></g>\",\n \"n\": \"<g id=\\\"black-knight\\\" class=\\\"black knight\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M 22,10 C 32.5,11 38.5,18 38,39 L 15,39 C 15,30 25,32.5 23,18\\\" style=\\\"fill:#000000; stroke:#000000;\\\"/><path d=\\\"M 24,18 C 24.38,20.91 18.45,25.37 16,27 C 13,29 13.18,31.34 11,31 C 9.958,30.06 12.41,27.96 11,28 C 10,28 11.19,29.23 10,30 C 9,30 5.997,31 6,26 C 6,24 12,14 12,14 C 12,14 13.89,12.1 14,10.5 C 13.27,9.506 13.5,8.5 13.5,7.5 C 14.5,6.5 16.5,10 16.5,10 L 18.5,10 C 18.5,10 19.28,8.008 21,7 C 22,7 22,10 22,10\\\" style=\\\"fill:#000000; stroke:#000000;\\\"/><path d=\\\"M 9.5 25.5 A 0.5 0.5 0 1 1 8.5,25.5 A 0.5 0.5 0 1 1 9.5 25.5 z\\\" style=\\\"fill:#ececec; stroke:#ececec;\\\"/><path d=\\\"M 15 15.5 A 0.5 1.5 0 1 1 14,15.5 A 0.5 1.5 0 1 1 15 15.5 z\\\" transform=\\\"matrix(0.866,0.5,-0.5,0.866,9.693,-5.173)\\\" style=\\\"fill:#ececec; stroke:#ececec;\\\"/><path d=\\\"M 24.55,10.4 L 24.1,11.85 L 24.6,12 C 27.75,13 30.25,14.49 32.5,18.75 C 34.75,23.01 35.75,29.06 35.25,39 L 35.2,39.5 L 37.45,39.5 L 37.5,39 C 38,28.94 36.62,22.15 34.25,17.66 C 31.88,13.17 28.46,11.02 25.06,10.5 L 24.55,10.4 z \\\" style=\\\"fill:#ececec; stroke:none;\\\"/></g>\",\n \"p\": \"<g id=\\\"black-pawn\\\" class=\\\"black pawn\\\"><path d=\\\"M22.5 9c-2.21 0-4 1.79-4 4 0 .89.29 1.71.78 2.38C17.33 16.5 16 18.59 16 21c0 2.03.94 3.84 2.41 5.03-3 1.06-7.41 5.55-7.41 13.47h23c0-7.92-4.41-12.41-7.41-13.47 1.47-1.19 2.41-3 2.41-5.03 0-2.41-1.33-4.5-3.28-5.62.49-.67.78-1.49.78-2.38 0-2.21-1.79-4-4-4z\\\" fill=\\\"#000\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\"/></g>\",\n \"q\": \"<g id=\\\"black-queen\\\" class=\\\"black queen\\\" fill=\\\"#000\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><g fill=\\\"#000\\\" stroke=\\\"none\\\"><circle cx=\\\"6\\\" cy=\\\"12\\\" r=\\\"2.75\\\"/><circle cx=\\\"14\\\" cy=\\\"9\\\" r=\\\"2.75\\\"/><circle cx=\\\"22.5\\\" cy=\\\"8\\\" r=\\\"2.75\\\"/><circle cx=\\\"31\\\" cy=\\\"9\\\" r=\\\"2.75\\\"/><circle cx=\\\"39\\\" cy=\\\"12\\\" r=\\\"2.75\\\"/></g><path d=\\\"M9 26c8.5-1.5 21-1.5 27 0l2.5-12.5L31 25l-.3-14.1-5.2 13.6-3-14.5-3 14.5-5.2-13.6L14 25 6.5 13.5 9 26zM9 26c0 2 1.5 2 2.5 4 1 1.5 1 1 .5 3.5-1.5 1-1.5 2.5-1.5 2.5-1.5 1.5.5 2.5.5 2.5 6.5 1 16.5 1 23 0 0 0 1.5-1 0-2.5 0 0 .5-1.5-1-2.5-.5-2.5-.5-2 .5-3.5 1-2 2.5-2 2.5-4-8.5-1.5-18.5-1.5-27 0z\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M11 38.5a35 35 1 0 0 23 0\\\" fill=\\\"none\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M11 29a35 35 1 0 1 23 0M12.5 31.5h20M11.5 34.5a35 35 1 0 0 22 0M10.5 37.5a35 35 1 0 0 24 0\\\" fill=\\\"none\\\" stroke=\\\"#fff\\\"/></g>\",\n \"r\": \"<g id=\\\"black-rook\\\" class=\\\"black rook\\\" fill=\\\"#000\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M9 39h27v-3H9v3zM12.5 32l1.5-2.5h17l1.5 2.5h-20zM12 36v-4h21v4H12z\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M14 29.5v-13h17v13H14z\\\" stroke-linecap=\\\"butt\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M14 16.5L11 14h23l-3 2.5H14zM11 14V9h4v2h5V9h5v2h5V9h4v5H11z\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M12 35.5h21M13 31.5h19M14 29.5h17M14 16.5h17M11 14h23\\\" fill=\\\"none\\\" stroke=\\\"#fff\\\" stroke-width=\\\"1\\\" stroke-linejoin=\\\"miter\\\"/></g>\",\n \"B\": \"<g id=\\\"white-bishop\\\" class=\\\"white bishop\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><g fill=\\\"#fff\\\" stroke-linecap=\\\"butt\\\"><path d=\\\"M9 36c3.39-.97 10.11.43 13.5-2 3.39 2.43 10.11 1.03 13.5 2 0 0 1.65.54 3 2-.68.97-1.65.99-3 .5-3.39-.97-10.11.46-13.5-1-3.39 1.46-10.11.03-13.5 1-1.354.49-2.323.47-3-.5 1.354-1.94 3-2 3-2zM15 32c2.5 2.5 12.5 2.5 15 0 .5-1.5 0-2 0-2 0-2.5-2.5-4-2.5-4 5.5-1.5 6-11.5-5-15.5-11 4-10.5 14-5 15.5 0 0-2.5 1.5-2.5 4 0 0-.5.5 0 2zM25 8a2.5 2.5 0 1 1-5 0 2.5 2.5 0 1 1 5 0z\\\"/></g><path d=\\\"M17.5 26h10M15 30h15m-7.5-14.5v5M20 18h5\\\" stroke-linejoin=\\\"miter\\\"/></g>\",\n \"K\": \"<g id=\\\"white-king\\\" class=\\\"white king\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M22.5 11.63V6M20 8h5\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M22.5 25s4.5-7.5 3-10.5c0 0-1-2.5-3-2.5s-3 2.5-3 2.5c-1.5 3 3 10.5 3 10.5\\\" fill=\\\"#fff\\\" stroke-linecap=\\\"butt\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M11.5 37c5.5 3.5 15.5 3.5 21 0v-7s9-4.5 6-10.5c-4-6.5-13.5-3.5-16 4V27v-3.5c-3.5-7.5-13-10.5-16-4-3 6 5 10 5 10V37z\\\" fill=\\\"#fff\\\"/><path d=\\\"M11.5 30c5.5-3 15.5-3 21 0m-21 3.5c5.5-3 15.5-3 21 0m-21 3.5c5.5-3 15.5-3 21 0\\\"/></g>\",\n \"N\": \"<g id=\\\"white-knight\\\" class=\\\"white knight\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M 22,10 C 32.5,11 38.5,18 38,39 L 15,39 C 15,30 25,32.5 23,18\\\" style=\\\"fill:#ffffff; stroke:#000000;\\\"/><path d=\\\"M 24,18 C 24.38,20.91 18.45,25.37 16,27 C 13,29 13.18,31.34 11,31 C 9.958,30.06 12.41,27.96 11,28 C 10,28 11.19,29.23 10,30 C 9,30 5.997,31 6,26 C 6,24 12,14 12,14 C 12,14 13.89,12.1 14,10.5 C 13.27,9.506 13.5,8.5 13.5,7.5 C 14.5,6.5 16.5,10 16.5,10 L 18.5,10 C 18.5,10 19.28,8.008 21,7 C 22,7 22,10 22,10\\\" style=\\\"fill:#ffffff; stroke:#000000;\\\"/><path d=\\\"M 9.5 25.5 A 0.5 0.5 0 1 1 8.5,25.5 A 0.5 0.5 0 1 1 9.5 25.5 z\\\" style=\\\"fill:#000000; stroke:#000000;\\\"/><path d=\\\"M 15 15.5 A 0.5 1.5 0 1 1 14,15.5 A 0.5 1.5 0 1 1 15 15.5 z\\\" transform=\\\"matrix(0.866,0.5,-0.5,0.866,9.693,-5.173)\\\" style=\\\"fill:#000000; stroke:#000000;\\\"/></g>\",\n \"P\": \"<g id=\\\"white-pawn\\\" class=\\\"white pawn\\\"><path d=\\\"M22.5 9c-2.21 0-4 1.79-4 4 0 .89.29 1.71.78 2.38C17.33 16.5 16 18.59 16 21c0 2.03.94 3.84 2.41 5.03-3 1.06-7.41 5.55-7.41 13.47h23c0-7.92-4.41-12.41-7.41-13.47 1.47-1.19 2.41-3 2.41-5.03 0-2.41-1.33-4.5-3.28-5.62.49-.67.78-1.49.78-2.38 0-2.21-1.79-4-4-4z\\\" fill=\\\"#fff\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\"/></g>\",\n \"Q\": \"<g id=\\\"white-queen\\\" class=\\\"white queen\\\" fill=\\\"#fff\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M8 12a2 2 0 1 1-4 0 2 2 0 1 1 4 0zM24.5 7.5a2 2 0 1 1-4 0 2 2 0 1 1 4 0zM41 12a2 2 0 1 1-4 0 2 2 0 1 1 4 0zM16 8.5a2 2 0 1 1-4 0 2 2 0 1 1 4 0zM33 9a2 2 0 1 1-4 0 2 2 0 1 1 4 0z\\\"/><path d=\\\"M9 26c8.5-1.5 21-1.5 27 0l2-12-7 11V11l-5.5 13.5-3-15-3 15-5.5-14V25L7 14l2 12zM9 26c0 2 1.5 2 2.5 4 1 1.5 1 1 .5 3.5-1.5 1-1.5 2.5-1.5 2.5-1.5 1.5.5 2.5.5 2.5 6.5 1 16.5 1 23 0 0 0 1.5-1 0-2.5 0 0 .5-1.5-1-2.5-.5-2.5-.5-2 .5-3.5 1-2 2.5-2 2.5-4-8.5-1.5-18.5-1.5-27 0z\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M11.5 30c3.5-1 18.5-1 22 0M12 33.5c6-1 15-1 21 0\\\" fill=\\\"none\\\"/></g>\",\n \"R\": \"<g id=\\\"white-rook\\\" class=\\\"white rook\\\" fill=\\\"#fff\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M9 39h27v-3H9v3zM12 36v-4h21v4H12zM11 14V9h4v2h5V9h5v2h5V9h4v5\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M34 14l-3 3H14l-3-3\\\"/><path d=\\\"M31 17v12.5H14V17\\\" stroke-linecap=\\\"butt\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M31 29.5l1.5 2.5h-20l1.5-2.5\\\"/><path d=\\\"M11 14h23\\\" fill=\\\"none\\\" stroke-linejoin=\\\"miter\\\"/></g>\"\n}\n", "import { spawn } from 'node:child_process';\nimport { createRequire } from 'node:module';\nimport { createInterface } from 'node:readline';\nimport { Chess } from '@zchess/chess';\n\nconst require = createRequire(import.meta.url);\nconst stockfish = require('stockfish') as { findEngine(flavor: string): string };\n\n/** Run the bundled engine in a separate process so search never blocks the CLI. */\nexport async function engineMove(fen: string, elo: number, depth: number, signal?: AbortSignal): Promise<string> {\n if (!Number.isInteger(elo) || elo < 1320 || elo > 3190) throw new Error('ELO must be an integer from 1320 to 3190.');\n if (!Number.isInteger(depth) || depth < 1 || depth > 30) throw new Error('Depth must be an integer from 1 to 30.');\n signal?.throwIfAborted();\n const position = new Chess(fen);\n if (position.status()) throw new Error('The game is over.');\n\n return new Promise((resolve, reject) => {\n const child = spawn(process.execPath, [stockfish.findEngine('single')], { stdio: ['pipe', 'pipe', 'ignore'] });\n const lines = createInterface({ input: child.stdout });\n let settled = false;\n const finish = (error?: Error, move?: string): void => {\n if (settled) return;\n settled = true;\n clearTimeout(timer);\n signal?.removeEventListener('abort', cancel);\n lines.close();\n child.kill();\n if (error) reject(error);\n else resolve(move!);\n };\n const timer = setTimeout(() => finish(new Error('Stockfish timed out. Try a lower --depth.')), 60_000);\n const cancel = (): void => finish(new Error('Stockfish search cancelled.'));\n signal?.addEventListener('abort', cancel, { once: true });\n child.on('error', error => finish(new Error(`Could not start bundled Stockfish: ${error.message}`)));\n child.stdin.on('error', error => finish(error));\n child.on('exit', () => finish(new Error('Stockfish exited before returning a move.')));\n lines.on('line', line => {\n if (line === 'uciok') {\n child.stdin.write(`setoption name UCI_LimitStrength value true\\nsetoption name UCI_Elo value ${elo}\\nisready\\n`);\n } else if (line === 'readyok') {\n child.stdin.write(`position fen ${fen}\\ngo depth ${depth}\\n`);\n } else if (line.startsWith('bestmove ')) {\n const move = line.split(/\\s+/)[1];\n try {\n position.play(move);\n finish(undefined, move);\n } catch {\n finish(new Error('Stockfish returned an invalid move.'));\n }\n }\n });\n child.stdin.write('uci\\n');\n });\n}\n", "import { stdout } from 'node:process';\n\ninterface Output {\n columns?: number;\n rows?: number;\n write(text: string): unknown;\n}\n\n/** Keep game frames out of shell scrollback and restore the shell on exit. */\nexport class GameScreen {\n private opened = false;\n private cursorStyled = false;\n constructor(readonly active: boolean, private readonly output: Output = stdout, private readonly manageScreen = true) {}\n\n open(): void {\n if (this.active && this.manageScreen && !this.opened) {\n this.output.write('\\x1b[?1049h');\n this.opened = true;\n }\n }\n\n draw(header: string, board: string, status: string, moves = ''): void {\n if (!this.active) {\n this.output.write(`${header}\\n${moves}\\n\\n${board}\\n${status}\\n`);\n return;\n }\n const width = Math.max(1, (this.output.columns || 80) - 1);\n const fit = (text: string): string => [...text.replace(/[\\x00-\\x1f\\x7f]/g, ' ')].slice(0, width).join('');\n // Synchronized output prevents a visible blank frame between positions.\n const title = `\\x1b[38;2;224;242;215m${fit(header).padEnd(width)}\\x1b[0m`;\n const history = `\\x1b[38;2;190;221;173m${fit(moves).padEnd(width)}\\x1b[0m`;\n const horizontalPadding = Math.min(1, Math.floor((width - 1) / 2));\n const innerWidth = Math.max(1, width - horizontalPadding * 2);\n const controls = '/help';\n const visibleControls = controls.slice(-Math.min(innerWidth, controls.length));\n const statusWidth = Math.max(0, innerWidth - visibleControls.length);\n const footer = `\\x1b[38;2;224;242;215m${' '.repeat(horizontalPadding)}${fit(status).slice(0, statusWidth).padEnd(statusWidth)}${visibleControls}${' '.repeat(horizontalPadding + 1)}\\x1b[0m`;\n const bottom = Math.max(6, this.output.rows || 40);\n this.output.write('\\x1b[?2026h\\x1b[H\\x1b[2J' +\n `${title}\\r\\n${history}\\r\\n\\r\\n${board}\\x1b[${bottom - 4};1H${footer}` +\n this.inputFrame('', 'Type any moves e.g. e4 or e pawn up 2') + '\\x1b[?2026l');\n }\n\n input(value: string, placeholder = 'Type any moves e.g. e4 or e pawn up 2'): void {\n if (this.active) this.output.write(this.inputFrame(value, placeholder));\n }\n\n private inputFrame(value: string, placeholder: string): string {\n const width = Math.max(1, (this.output.columns || 80) - 1);\n const bottom = Math.max(6, this.output.rows || 40);\n const visible = [...value].slice(-Math.max(0, width - 4)).join('');\n const foreground = value ? '\\x1b[38;2;235;248;226m' : '\\x1b[38;2;139;168;144m';\n const horizontalPadding = 1;\n const fieldTextWidth = Math.max(0, width - horizontalPadding - 2);\n const shown = value\n ? [...visible].slice(-fieldTextWidth).join('')\n : [...placeholder].slice(0, Math.max(0, fieldTextWidth - 1)).join('');\n const prefix = ' ';\n const displayed = value ? shown : ` ${shown}`;\n const background = '\\x1b[48;2;12;42;34m';\n const paddingRow = `${background}${' '.repeat(width + 1)}\\x1b[0m`;\n const row = `${background}\\x1b[38;2;190;221;173m${prefix}${foreground}${displayed}${' '.repeat(Math.max(0, width + 1 - prefix.length - [...displayed].length))}\\x1b[0m`;\n const cursor = value ? Math.min(width, prefix.length + [...shown].length + 1) : 2;\n this.cursorStyled = true;\n return `\\x1b[${bottom - 2};1H${paddingRow}` +\n `\\x1b[${bottom - 1};1H${row}` +\n `\\x1b[${bottom};1H${paddingRow}\\x1b[${bottom - 1};${cursor}H\\x1b[5 q\\x1b[?25h`;\n }\n\n close(): void {\n if (this.cursorStyled) {\n this.output.write('\\x1b[0 q');\n this.cursorStyled = false;\n }\n if (this.opened) {\n this.output.write('\\x1b[?2026l\\x1b[?25h\\x1b[?1049l');\n this.opened = false;\n }\n }\n}\n\n/** Full-screen start and load menus that replace one another without scrollback. */\nexport class MenuScreen {\n private opened = false;\n constructor(readonly active: boolean, private readonly output: Output = stdout) {}\n\n open(): void {\n if (this.active && !this.opened) {\n this.output.write('\\x1b[?1049h\\x1b[?25l');\n this.opened = true;\n }\n }\n\n draw(header: string, content: string, footer: string): void {\n const width = Math.max(1, (this.output.columns || 80) - 1);\n const fit = (text: string): string => [...text.replace(/[\\x00-\\x1f\\x7f]/g, ' ')].slice(0, width).join('');\n if (!this.active) {\n this.output.write(`${header}\\n${content}\\n${footer}\\n`);\n return;\n }\n const title = `\\x1b[38;2;224;242;215m${fit(header).padEnd(width)}\\x1b[0m`;\n const horizontalPadding = Math.min(2, Math.floor((width - 1) / 2));\n const status = `\\x1b[38;2;210;225;202m${' '.repeat(horizontalPadding)}${fit(footer).slice(0, width - horizontalPadding * 2).padEnd(width - horizontalPadding * 2)}${' '.repeat(horizontalPadding)}\\x1b[0m`;\n const body = content.split('\\n').map(line => fit(line)).join('\\r\\n');\n this.output.write(`\\x1b[?25l\\x1b[?2026h\\x1b[H\\x1b[2J${title}\\r\\n\\r\\n${body}\\r\\n\\r\\n${status}\\r\\n\\x1b[?2026l`);\n }\n\n close(): void {\n if (this.opened) {\n this.output.write('\\x1b[?25h\\x1b[?1049l');\n this.opened = false;\n }\n }\n}\n", "import { DatabaseSync } from 'node:sqlite';\nimport { mkdirSync } from 'node:fs';\nimport { dirname, join } from 'node:path';\nimport { homedir } from 'node:os';\n\nexport interface SavedGame {\n id: number;\n createdAt: string;\n updatedAt: string;\n elo: number;\n color: 'w' | 'b';\n startFen: string;\n fen: string;\n moves: string[];\n status: string;\n}\n\nexport class GameStore {\n private readonly db: DatabaseSync;\n\n constructor(path = process.env.ZCHESS_DB_PATH || join(process.env.XDG_DATA_HOME || join(homedir(), '.local', 'share'), 'zchess', 'games.sqlite')) {\n mkdirSync(dirname(path), { recursive: true });\n this.db = new DatabaseSync(path);\n this.db.exec(`\n PRAGMA journal_mode = WAL;\n CREATE TABLE IF NOT EXISTS games (\n id INTEGER PRIMARY KEY,\n created_at TEXT NOT NULL,\n updated_at TEXT NOT NULL,\n elo INTEGER NOT NULL,\n color TEXT NOT NULL CHECK (color IN ('w', 'b')),\n start_fen TEXT NOT NULL,\n fen TEXT NOT NULL,\n moves TEXT NOT NULL,\n status TEXT NOT NULL\n );\n `);\n }\n\n save(game: Omit<SavedGame, 'id' | 'createdAt' | 'updatedAt'>, id?: number): number {\n const now = new Date().toISOString();\n if (id === undefined) {\n const result = this.db.prepare(`INSERT INTO games (created_at, updated_at, elo, color, start_fen, fen, moves, status)\n VALUES (?, ?, ?, ?, ?, ?, ?, ?)`).run(now, now, game.elo, game.color, game.startFen, game.fen, JSON.stringify(game.moves), game.status);\n return Number(result.lastInsertRowid);\n }\n this.db.prepare(`UPDATE games SET updated_at = ?, elo = ?, color = ?, start_fen = ?, fen = ?, moves = ?, status = ? WHERE id = ?`)\n .run(now, game.elo, game.color, game.startFen, game.fen, JSON.stringify(game.moves), game.status, id);\n return id;\n }\n\n list(): SavedGame[] {\n const rows = this.db.prepare('SELECT * FROM games ORDER BY updated_at DESC').all() as Array<Record<string, unknown>>;\n return rows.map(row => this.decode(row));\n }\n\n get(id: number): SavedGame | undefined {\n const row = this.db.prepare('SELECT * FROM games WHERE id = ?').get(id) as Record<string, unknown> | undefined;\n return row ? this.decode(row) : undefined;\n }\n\n close(): void { this.db.close(); }\n\n private decode(row: Record<string, unknown>): SavedGame {\n return {\n id: Number(row.id), createdAt: String(row.created_at), updatedAt: String(row.updated_at),\n elo: Number(row.elo), color: row.color === 'b' ? 'b' : 'w', startFen: String(row.start_fen), fen: String(row.fen),\n moves: JSON.parse(String(row.moves)) as string[], status: String(row.status),\n };\n }\n}\n"],
5
- "mappings": "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",
6
- "names": ["createInterface", "stdout", "message", "move", "names", "body", "color", "require", "createRequire", "require", "createRequire", "stdout", "createInterface", "game", "elo", "listener"]
3
+ "sources": ["../src/update.ts", "../src/cli.ts", "../../../packages/chess/src/index.ts", "../../../packages/chess/src/resolution.ts", "../../../packages/chess/src/legality.ts", "../../../packages/chess/src/suggestions.ts", "../../../packages/chess/src/input.ts", "../../../packages/chess/src/history.ts", "../src/api.ts", "../src/ui.ts", "../src/graphics.ts", "../../../packages/chess/assets/pieces.json", "../src/terminal.ts", "../src/engine.ts", "../src/screen.ts", "../src/store.ts"],
4
+ "sourcesContent": ["export interface UpdateNotice { version: string; command: string }\n\ninterface Version { core: bigint[]; prerelease: string[] }\nfunction parseVersion(value: unknown): Version | undefined {\n if (typeof value !== 'string') return;\n const match = /^(0|[1-9]\\d*)\\.(0|[1-9]\\d*)\\.(0|[1-9]\\d*)(?:-([\\da-zA-Z-]+(?:\\.[\\da-zA-Z-]+)*))?(?:\\+[\\da-zA-Z-]+(?:\\.[\\da-zA-Z-]+)*)?$/.exec(value);\n if (!match) return;\n const prerelease = match[4]?.split('.') || [];\n if (prerelease.some(part => /^0\\d+$/.test(part))) return;\n return { core: match.slice(1, 4).map(BigInt), prerelease };\n}\n\nexport function isNewerVersion(candidate: string, installed: string): boolean {\n const a = parseVersion(candidate), b = parseVersion(installed);\n if (!a || !b) return false;\n for (let i = 0; i < 3; i++) if (a.core[i] !== b.core[i]) return a.core[i] > b.core[i];\n if (!a.prerelease.length || !b.prerelease.length) return a.prerelease.length === 0 && b.prerelease.length > 0;\n for (let i = 0; i < Math.max(a.prerelease.length, b.prerelease.length); i++) {\n const x = a.prerelease[i], y = b.prerelease[i];\n if (x === undefined || y === undefined) return x !== undefined;\n if (x === y) continue;\n const xn = /^\\d+$/.test(x), yn = /^\\d+$/.test(y);\n if (xn && yn) return BigInt(x) > BigInt(y);\n if (xn !== yn) return !xn;\n return x > y;\n }\n return false;\n}\n\n/** An optional startup hint: network or registry problems must never prevent play. */\nexport async function checkForUpdate(installed: string, options: {\n fetch?: typeof fetch;\n timeoutMs?: number;\n homebrew?: boolean;\n} = {}): Promise<UpdateNotice | undefined> {\n const current = parseVersion(installed);\n if (!current) return;\n const controller = new AbortController();\n let timer: ReturnType<typeof setTimeout> | undefined;\n try {\n const lookup = async (): Promise<UpdateNotice | undefined> => {\n const response = await (options.fetch || fetch)('https://registry.npmjs.org/-/package/zchess/dist-tags', { signal: controller.signal });\n if (!response.ok) return;\n const tags = await response.json() as Record<string, unknown> | null;\n if (!tags || typeof tags !== 'object') return;\n const candidates = [tags.latest];\n if (current.prerelease.length && !options.homebrew) candidates.push(tags[current.prerelease[0]]);\n let version = installed;\n for (const candidate of candidates) {\n if (typeof candidate === 'string' && isNewerVersion(candidate, version)) version = candidate;\n }\n if (version === installed) return;\n return { version, command: options.homebrew\n ? `brew reinstall --formula \\\\\n https://github.com/kennylwx/zchess/releases/latest/download/zchess.rb`\n : `npm install --global zchess@${version}` };\n };\n const timeout = new Promise<undefined>(resolve => {\n timer = setTimeout(() => { controller.abort(); resolve(undefined); }, options.timeoutMs ?? 800);\n });\n return await Promise.race([lookup(), timeout]);\n } catch { return; }\n finally { if (timer) clearTimeout(timer); }\n}\n", "import { checkForUpdate, type UpdateNotice } from './update.js';\nimport { createInterface } from 'node:readline/promises';\nimport { stdin, stdout } from 'node:process';\nimport { Chess, START_FEN } from '@zchess/chess';\nimport { modelInput } from './input.js';\nimport { ChessServerClient } from './api.js';\nimport { render } from './ui.js';\nimport { clearGraphics, renderGraphics, type GraphicsMode } from './graphics.js';\nimport { detectGraphics } from './terminal.js';\nimport { engineMove } from './engine.js';\nimport { GameScreen, MenuScreen } from './screen.js';\nimport { moveHistory, undoTurn } from './history.js';\nimport { GameStore, type SavedGame } from './store.js';\nimport type { Key } from 'node:readline';\n\nconst HELP = `chess \u2014 terminal chess\n\nUsage: chess [--elo 1500] [--color white|black] [--fen FEN]\n [--server URL] [--depth 12] [--graphics auto|kitty|text|ascii]\n\nRun \"chess\" with no options to open the Play / Load game menu.\nMoves accept UCI (e2e4), SAN (Nf3), or free text (\"move the queen up by 1\").\nStockfish is included and runs locally. Only free text requires the Chess server.\nGames are saved automatically in ~/.local/share/zchess/games.sqlite.\nCommands: /fen, /fen <position>, /undo, /help, /back, /quit`;\n\nexport function commandHelp(): string {\n return [\n 'COMMANDS',\n '/help Show this list',\n '/undo Take back a turn',\n '/fen Show the current position',\n '/fen <FEN> Load a position',\n '/back Return to the previous screen',\n '/quit Quit Chess',\n '',\n 'SHORTCUTS',\n 'Ctrl+C Quit',\n 'Ctrl+U Clear input',\n ].join('\\n');\n}\n\nexport function editGameInput(value: string, text: string, key: Key): string {\n if ((key?.ctrl && key.name === 'u') || (key?.meta && key.name === 'backspace')) return '';\n if (key?.name === 'backspace') return [...value].slice(0, -1).join('');\n if (!key?.ctrl && !key?.meta && text && !/[\\x00-\\x1f\\x7f]/.test(text)) return value + text;\n return value;\n}\n\nconst promptColor = '\\x1b[39m';\nconst reset = '\\x1b[0m';\nconst ELO_PRESETS = [\n { label: 'Beginner', elo: 1320 },\n { label: 'Intermediate', elo: 1500 },\n { label: 'Advanced', elo: 1800 },\n { label: 'Expert', elo: 2200 },\n { label: 'Master', elo: 3190 },\n];\ninterface GameConfig { elo: number; human: 'w' | 'b'; saved?: SavedGame; fen?: string }\n\nexport async function run(args: string[], installation?: { version: string; homebrew?: boolean }): Promise<void> {\n if (args.includes('--help') || args.includes('-h')) { console.log(HELP); return; }\n const get = (name: string, fallback: string | undefined): string | undefined => {\n const index = args.indexOf(name);\n return index < 0 ? fallback : (args[index + 1] ?? fallback);\n };\n const graphics = get('--graphics', 'auto') as GraphicsMode;\n if (!['auto', 'kitty', 'text', 'ascii'].includes(graphics)) throw new Error('Graphics must be auto, kitty, text, or ascii.');\n const depth = Number(get('--depth', '12'));\n if (!Number.isInteger(depth) || depth < 1 || depth > 30) throw new Error('Depth must be an integer from 1 to 30.');\n let cellAspect = 2;\n const useGraphics = await detectGraphics(graphics, stdin, stdout, process.env, 300, ratio => { cellAspect = ratio; });\n\n const update = installation && stdin.isTTY && stdout.isTTY && process.env.ZCHESS_NO_UPDATE_CHECK !== '1'\n ? await checkForUpdate(installation.version, { homebrew: installation.homebrew }) : undefined;\n const store = new GameStore(get('--db', undefined));\n const direct = args.some(arg => arg.startsWith('--'));\n const interactiveMenu = !direct && stdin.isTTY && stdout.isTTY;\n const menuScreen = interactiveMenu ? new MenuScreen(true) : undefined;\n menuScreen?.open();\n if (update && !interactiveMenu) console.log(`Update available: ${installation!.version} \u2192 ${update.version}\\nRun: ${update.command}`);\n\n try {\n let keepGoing = true;\n let returnToSavedGames = false;\n while (keepGoing) {\n let config: GameConfig | undefined;\n if (direct || !stdin.isTTY || !stdout.isTTY) {\n const elo = Number(get('--elo', '1500'));\n if (!Number.isInteger(elo) || elo < 1320 || elo > 3190) throw new Error('ELO must be an integer from 1320 to 3190 (Stockfish UCI range).');\n config = { elo, human: get('--color', 'white')!.toLowerCase().startsWith('b') ? 'b' : 'w', fen: get('--fen', undefined) };\n keepGoing = false;\n } else {\n const choice = await mainMenu(store, menuScreen!, returnToSavedGames, update, installation?.version);\n returnToSavedGames = false;\n if (choice === 'quit') break;\n config = choice;\n }\n if (config) {\n const again = await playGame(config, { useGraphics, ascii: graphics === 'ascii', cellAspect, depth, serverUrl: get('--server', process.env.ZCHESS_SERVER_URL || 'http://localhost:8000')!, store, sharedScreen: interactiveMenu });\n if (again && config.saved) returnToSavedGames = true;\n if (direct || !again) keepGoing = false;\n }\n }\n } finally { menuScreen?.close(); store.close(); }\n}\n\nasync function mainMenu(store: GameStore, screen: MenuScreen, openSavedGames = false, update?: UpdateNotice, installed?: string): Promise<GameConfig | 'quit'> {\n const rl = createInterface({ input: stdin, output: stdout });\n try {\n while (true) {\n if (openSavedGames) {\n openSavedGames = false;\n const game = await savedGamesMenu(store, screen);\n if (game === 'quit') return 'quit';\n if (game) return game;\n continue;\n }\n const notice = update ? `\\n\\nUpdate available: ${installed} \u2192 ${update.version}\\nRun: ${update.command}` : '';\n screen.draw('ZCHESS / LOCAL STOCKFISH', ' 1 Play\\n 2 Load a saved game\\n 3 Quit' + notice, '');\n const choice = await menuKey('Select \u203A ', ['1', '2', '3']);\n if (choice === 'q') return 'quit';\n if (choice === 'b') continue;\n if (choice === '3') return 'quit';\n if (choice === '1') {\n const game = await newGameMenu(screen);\n if (game === 'quit') return 'quit';\n if (game) return game;\n }\n if (choice === '2' || choice === 'load') {\n const game = await savedGamesMenu(store, screen);\n if (game === 'quit') return 'quit';\n if (game) return game;\n }\n }\n } finally { rl.close(); }\n}\n\nasync function savedGamesMenu(store: GameStore, screen: MenuScreen): Promise<GameConfig | 'quit' | null> {\n const games = store.list();\n if (!games.length) {\n screen.draw('LOAD A SAVED GAME', 'No saved games yet.\\n\\n 1 Back\\n 2 Quit', '');\n const action = await menuKey('Select \u203A ', ['1', '2']);\n return action === '2' || action === 'q' ? 'quit' : null;\n }\n const recent = games.slice(0, 7);\n const lines = recent.map((game, index) => ` ${index + 1} ${game.updatedAt.slice(0, 16).replace('T', ' ')} \u00B7 ${game.elo} ELO \u00B7 ${game.moves.length ? game.moves.join(' ') : 'New game'} \u00B7 ${game.status}`);\n if (games.length > recent.length) lines.push(' Showing the 7 most recent games.');\n const backChoice = recent.length + 1;\n const quitChoice = recent.length + 2;\n lines.push(` ${backChoice} Back`, ` ${quitChoice} Quit`);\n screen.draw('LOAD A SAVED GAME', lines.join('\\n'), '');\n const selection = await menuKey('Choose a game \u203A ', Array.from({ length: quitChoice }, (_, index) => String(index + 1)));\n if (selection === 'q') return 'quit';\n if (Number(selection) === backChoice) return null;\n if (Number(selection) === quitChoice) return 'quit';\n const game = recent[Number(selection) - 1];\n return game ? { elo: game.elo, human: game.color, saved: game } : null;\n}\n\nasync function newGameMenu(screen: MenuScreen): Promise<GameConfig | null | 'quit'> {\n const choices = ELO_PRESETS.map(({ label, elo }, index) => ` ${index + 1} ${label} \u00B7 ${elo} ELO`);\n choices.push(' 6 Custom ELO');\n choices.push(' 7 Back', ' 8 Quit');\n screen.draw('NEW GAME / STOCKFISH STRENGTH', `${choices.join('\\n')}\\n\\nAvailable range: 1320\u20133190 ELO`, '');\n const selection = await menuKey('ELO \u203A ', ['1', '2', '3', '4', '5', '6', '7', '8']);\n if (selection === 'q') return 'quit';\n if (selection === '7') return null;\n if (selection === '8') return 'quit';\n let elo = ELO_PRESETS[Number(selection) - 1]?.elo;\n if (selection === '6') {\n let custom: number;\n while (true) {\n screen.draw('NEW GAME / CUSTOM ELO', 'Enter any ELO from 1320 to 3190.\\n\\n 0 Back\\n 00 Quit', '');\n const value = await menuText('ELO \u203A ');\n if (value === 'q') return 'quit';\n if (value === 'b' || value === null) return await newGameMenu(screen);\n custom = Number(value);\n if (Number.isInteger(custom) && custom >= 1320 && custom <= 3190) break;\n screen.draw('NEW GAME / CUSTOM ELO', 'Enter an ELO from 1320 to 3190.\\nThat value is outside the range.\\n\\n 0 Back\\n 00 Quit', '');\n }\n elo = custom;\n }\n if (elo === undefined) return null;\n while (true) {\n screen.draw('NEW GAME / CHOOSE SIDE', `Stockfish ${elo} ELO\\n\\n 1 White\\n 2 Black\\n 3 Random\\n 4 Back\\n 5 Quit`, '');\n const side = await menuKey('Side \u203A ', ['1', '2', '3', '4', '5']);\n if (side === 'q') return 'quit';\n if (side === '4') return await newGameMenu(screen);\n if (side === '5') return 'quit';\n const human: 'w' | 'b' = side === '1' ? 'w' : side === '2' ? 'b' : Math.random() < 0.5 ? 'w' : 'b';\n return { elo, human };\n }\n}\n\nfunction menuKey(prompt: string, choices: string[]): Promise<string> {\n return rawPrompt(prompt, (text, key, finish) => {\n if (key?.ctrl && key.name === 'c') { finish('q'); return; }\n const character = (text ?? '').toLowerCase();\n if (!key?.ctrl && choices.includes(character)) finish(character);\n });\n}\n\nfunction menuText(prompt: string): Promise<string | 'b' | 'q' | null> {\n let value = '';\n return rawPrompt(prompt, (text, key, finish) => {\n if (key?.ctrl && key.name === 'c') { finish('q'); return; }\n if (key?.name === 'backspace') {\n value = value.slice(0, -1);\n stdout.write('\\b \\b');\n return;\n }\n if (key?.name === 'return' || key?.name === 'enter') {\n finish(value === '0' ? 'b' : value === '00' ? 'q' : value);\n return;\n }\n const character = text ?? '';\n if (key?.ctrl || !character) return;\n value += character;\n stdout.write(character);\n });\n}\n\nfunction rawPrompt<T>(prompt: string, onKey: (text: string, key: Key, finish: (value: T) => void) => void): Promise<T> {\n const stream = stdin as typeof stdin & { setRawMode?: (mode: boolean) => void };\n if (!stream.isTTY || !stream.setRawMode) return Promise.reject(new Error('Menu selection requires an interactive terminal.'));\n const previous = stdin.listeners('keypress') as Array<(...args: any[]) => void>;\n previous.forEach(listener => stdin.removeListener('keypress', listener));\n stdout.write(`${promptColor}${prompt}${reset}`);\n stream.setRawMode(true);\n return new Promise(resolve => {\n let finished = false;\n const finish = (value: T): void => {\n if (finished) return;\n finished = true;\n stdin.removeListener('keypress', listener);\n stream.setRawMode(false);\n [...previous].reverse().forEach(listener => stdin.prependListener('keypress', listener));\n stdout.write('\\r\\n');\n resolve(value);\n };\n const listener = (text: string, key: Key): void => onKey(text, key, finish);\n stdin.on('keypress', listener);\n });\n}\n\nasync function playGame(config: GameConfig, options: { useGraphics: boolean; ascii: boolean; cellAspect: number; depth: number; serverUrl: string; store: GameStore; sharedScreen: boolean }): Promise<boolean> {\n const { elo, human, saved } = config;\n let startFen = saved?.startFen ?? config.fen ?? START_FEN;\n const chess = new Chess(startFen);\n if (saved) for (const move of saved.moves) chess.play(move);\n const abort = new AbortController();\n const server = new ChessServerClient(options.serverUrl, abort.signal);\n const rl = createInterface({ input: stdin, output: stdout });\n const screen = new GameScreen(Boolean(stdout.isTTY && stdin.isTTY), stdout, !options.sharedScreen);\n let useGraphics = options.useGraphics;\n let stopped = false;\n let redrawInput: (() => void) | undefined;\n let last: number[] | null = null;\n let showingHelp = false;\n let returnToMenu = false;\n let returnToMenuRequested = false;\n let search: AbortController | undefined;\n let notice = 'Your move';\n let gameId = saved?.id;\n const header = `CHESS / ${human === 'w' ? 'White' : 'Black'} / Stockfish ${elo} ELO`;\n const persist = (): void => {\n gameId = options.store.save({ elo, color: human, startFen, fen: chess.fen(), moves: chess.history.map(entry => entry.san), status: chess.status() ?? 'In progress' }, gameId);\n };\n const draw = (): void => {\n let board: string;\n if (showingHelp) board = (useGraphics ? clearGraphics() : '') + commandHelp();\n else {\n try { board = useGraphics ? renderGraphics(chess, human, last, screen.active, options.cellAspect) : ''; }\n catch {\n // A missing native rasterizer must not prevent playing a text game.\n stdout.write(clearGraphics());\n useGraphics = false;\n board = '';\n }\n if (!useGraphics) board = render(chess, { ascii: options.ascii, perspective: human, last, compact: screen.active && (stdout.rows || 40) < 36 });\n }\n screen.draw(header, board, notice, showingHelp ? '' : moveHistory(chess, Math.max(1, (stdout.columns || 80) - 1)));\n };\n const takeBack = (): void => {\n notice = undoTurn(chess, human) ? 'Took back your last move and any Stockfish reply.' : 'No move to undo yet.';\n const move = chess.history.at(-1)?.move;\n last = move ? [move.from, move.to] : null;\n persist();\n };\n const shortcut = (text: string, key: Key): void => {\n if (stopped || returnToMenuRequested) return;\n if (key?.ctrl && key.name === 'c') { stop(); return; }\n };\n const stop = (): void => { stopped = true; abort.abort(); search?.abort(); };\n let resizeTask: Promise<void> | undefined;\n const resize = (): void => {\n if (stopped || resizeTask) return;\n resizeTask = (async () => {\n try {\n if (useGraphics) await detectGraphics('kitty', stdin, stdout, process.env, 300, ratio => { options.cellAspect = ratio; });\n if (!stopped) { draw(); redrawInput?.(); }\n } catch { /* Keep the previous geometry if the terminal stops responding. */ }\n })().finally(() => { resizeTask = undefined; });\n };\n const question = async (placeholder: string): Promise<string> => {\n if (!screen.active) return await rl.question(`${promptColor}${placeholder} \u203A ${reset}`, { signal: abort.signal });\n const stream = stdin as typeof stdin & { setRawMode?: (mode: boolean) => void };\n const previousRaw = stream.isRaw;\n const previous = stdin.listeners('keypress') as Array<(text: string, key: Key) => void>;\n previous.forEach(listener => stdin.removeListener('keypress', listener));\n stream.setRawMode?.(true);\n return new Promise(resolve => {\n let value = '';\n let done = false;\n const redraw = (): void => screen.input(value, placeholder);\n const finish = (answer: string): void => {\n if (done) return;\n done = true;\n stdin.removeListener('keypress', onKey);\n abort.signal.removeEventListener('abort', onAbort);\n previous.forEach(listener => stdin.on('keypress', listener));\n stream.setRawMode?.(previousRaw);\n redrawInput = undefined;\n screen.input('', placeholder);\n resolve(answer);\n };\n const onAbort = (): void => finish('');\n const onKey = (text: string, key: Key): void => {\n if (key?.ctrl && key.name === 'c') { stop(); finish(''); return; }\n if (key?.name === 'return' || key?.name === 'enter') { finish(value); return; }\n value = editGameInput(value, text, key);\n redraw();\n };\n redrawInput = redraw;\n stdin.on('keypress', onKey);\n abort.signal.addEventListener('abort', onAbort, { once: true });\n redraw();\n });\n };\n stdin.on('keypress', shortcut);\n rl.on('SIGINT', stop);\n rl.on('close', stop);\n process.on('SIGINT', stop);\n process.on('SIGTERM', stop);\n stdout.on('resize', resize);\n screen.open();\n persist();\n\n try {\n while (!stopped && !returnToMenuRequested) {\n const status = chess.status();\n if (status) {\n notice = status;\n persist();\n draw();\n if (screen.active) {\n const command = await question('Type /undo, /back, or /quit \u00B7 Ctrl+C quit');\n if (command.trim().toLowerCase() === '/undo') { takeBack(); continue; }\n if (/^\\/(quit|exit)$/.test(command.trim().toLowerCase())) { stop(); break; }\n break;\n }\n console.log(status);\n break;\n }\n if (chess.turn !== human) {\n notice = 'Stockfish is thinking\u2026';\n draw();\n search = new AbortController();\n let move: string;\n try { move = await engineMove(chess.fen(), elo, options.depth, search.signal); }\n catch (error) {\n if (returnToMenuRequested) break;\n throw error;\n } finally { search = undefined; }\n const side = chess.turn;\n const san = chess.play(move);\n const played = chess.history.at(-1)!.move;\n last = [played.from, played.to];\n notice = `${side === 'w' ? 'White' : 'Black'} plays ${san}`;\n persist();\n continue;\n }\n\n draw();\n let raw: string;\n try { raw = await question(showingHelp ? 'Type /back to return to the game' : 'Type any moves e.g. e4 or e pawn up 2'); }\n catch (error) { if (returnToMenuRequested) break; throw error; }\n const wasShowingHelp = showingHelp;\n showingHelp = false;\n if (wasShowingHelp && /^\\/back$/i.test(raw.trim())) { notice = 'Your move'; continue; }\n let intent;\n try { intent = await modelInput(raw, chess, server); }\n catch (error) { notice = message(error); continue; }\n if (stopped) break;\n if (intent.type === 'quit') { stop(); break; }\n if (intent.type === 'help') { notice = 'Available commands'; showingHelp = true; continue; }\n if (intent.type === 'back') { returnToMenuRequested = true; break; }\n if (intent.type === 'show-fen') { notice = chess.fen(); continue; }\n if (intent.type === 'load-fen') {\n try { chess.load(intent.value); startFen = intent.value; last = null; notice = 'Position loaded.'; persist(); }\n catch (error) { notice = message(error); }\n continue;\n }\n if (intent.type === 'undo') { takeBack(); continue; }\n if (intent.type === 'empty') continue;\n try {\n const san = chess.play(intent.value);\n const move = chess.history.at(-1)!.move;\n last = [move.from, move.to];\n notice = intent.source === 'jev' ? `JEV chose ${san}` : `You played ${san}`;\n persist();\n } catch (error) { notice = `${message(error)}. Try e2e4, Nf3, or describe the move.`; }\n }\n } catch (error) { if (!stopped) throw error; }\n finally {\n await resizeTask;\n returnToMenu = screen.active && !stopped;\n stdin.off('keypress', shortcut);\n stdout.off('resize', resize);\n process.off('SIGINT', stop);\n process.off('SIGTERM', stop);\n rl.close();\n if (useGraphics) stdout.write(clearGraphics());\n screen.close();\n }\n return returnToMenu || screen.active && returnToMenuRequested;\n}\n\nexport { HELP };\nconst message = (error: unknown): string => error instanceof Error ? error.message : String(error);\n", "export const START_FEN = 'rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0 1';\nconst FILES = 'abcdefgh';\nconst KNIGHT: Direction[] = [[1,2],[2,1],[2,-1],[1,-2],[-1,-2],[-2,-1],[-2,1],[-1,2]];\nconst KING: Direction[] = [[1,0],[-1,0],[0,1],[0,-1],[1,1],[1,-1],[-1,1],[-1,-1]];\ntype Side = 'w' | 'b';\ntype Piece = 'P'|'N'|'B'|'R'|'Q'|'K'|'p'|'n'|'b'|'r'|'q'|'k';\ntype Direction = [number, number];\nexport interface Move { from:number; to:number; promotion:string|null; flags:string }\nexport interface PositionSnapshot { board:(Piece|null)[]; turn:Side; castling:string; ep:number; halfmove:number; fullmove:number }\nexport interface HistoryEntry { move:Move; san:string; before:PositionSnapshot }\n\nexport const squareName = (i:number):string => FILES[i % 8] + (8 - Math.floor(i / 8));\nexport const squareIndex = (s:string):number => /^[a-h][1-8]$/i.test(s) ? (8 - Number(s[1])) * 8 + FILES.indexOf(s[0].toLowerCase()) : -1;\nconst color = (p:Piece|null):Side|null => p ? (p === p.toUpperCase() ? 'w' : 'b') : null;\n\nexport class Chess {\n board:(Piece|null)[]=[]; turn:Side='w'; castling=''; ep=-1; halfmove=0; fullmove=1; history:HistoryEntry[]=[];\n constructor(fen:string = START_FEN) { this.load(fen); }\n load(fen:string):this {\n const [placement, turn, castling = '-', ep = '-', half = '0', full = '1'] = fen.trim().split(/\\s+/);\n const ranks = placement?.split('/');\n if (!ranks || ranks.length !== 8 || !/^[wb]$/.test(turn)) throw new Error('Invalid FEN');\n this.board = [];\n for (const rank of ranks) {\n for (const c of rank) {\n if (/\\d/.test(c)) this.board.push(...Array(Number(c)).fill(null));\n else if (/[prnbqkPRNBQK]/.test(c)) this.board.push(c as Piece);\n else throw new Error('Invalid FEN');\n }\n }\n if (this.board.length !== 64) throw new Error('Invalid FEN');\n this.turn = turn as Side; this.castling = castling === '-' ? '' : castling; this.ep = ep === '-' ? -1 : squareIndex(ep);\n this.halfmove = Number(half); this.fullmove = Number(full); this.history = [];\n if (this.ep < -1 || !Number.isFinite(this.halfmove) || !Number.isFinite(this.fullmove)) throw new Error('Invalid FEN');\n return this;\n }\n fen():string {\n let out = '';\n for (let r=0;r<8;r++) { let empty=0; for(let f=0;f<8;f++){ const p=this.board[r*8+f]; if(!p) empty++; else {if(empty){out+=empty;empty=0;} out+=p;} } if(empty)out+=empty; if(r<7)out+='/'; }\n return `${out} ${this.turn} ${this.castling || '-'} ${this.ep < 0 ? '-' : squareName(this.ep)} ${this.halfmove} ${this.fullmove}`;\n }\n attacked(sq:number, by:Side):boolean {\n const r=Math.floor(sq/8), f=sq%8;\n const pawn = by==='w'?'P':'p', pawnRow = r + (by==='w'?1:-1);\n for(const df of [-1,1]) if(pawnRow>=0&&pawnRow<8&&f+df>=0&&f+df<8&&this.board[pawnRow*8+f+df]===pawn)return true;\n for(const [df,dr] of KNIGHT){const rr=r+dr,ff=f+df;if(rr>=0&&rr<8&&ff>=0&&ff<8&&this.board[rr*8+ff]===(by==='w'?'N':'n'))return true;}\n for(const [df,dr] of KING){const rr=r+dr,ff=f+df;if(rr>=0&&rr<8&&ff>=0&&ff<8&&this.board[rr*8+ff]===(by==='w'?'K':'k'))return true;}\n for(const [df,dr,types] of [[1,0,'RQ'],[-1,0,'RQ'],[0,1,'RQ'],[0,-1,'RQ'],[1,1,'BQ'],[-1,1,'BQ'],[1,-1,'BQ'],[-1,-1,'BQ']] as [number,number,string][]) {\n let rr=r+dr,ff=f+df; while(rr>=0&&rr<8&&ff>=0&&ff<8){const p=this.board[rr*8+ff];if(p){if(color(p)===by&&types.includes(p.toUpperCase()))return true;break;}rr+=dr;ff+=df;\n }} return false;\n }\n inCheck(side:Side=this.turn):boolean { const king=this.board.indexOf(side==='w'?'K':'k'); return king<0 || this.attacked(king,side==='w'?'b':'w'); }\n pseudo():Move[] {\n const moves:Move[]=[];\n const add=(from:number,to:number,promotion:string|null=null,flags='')=>moves.push({from,to,promotion,flags});\n for(let from=0;from<64;from++){const p=this.board[from];if(!p||color(p)!==this.turn)continue;const type=p.toUpperCase(),r=Math.floor(from/8),f=from%8;\n if(type==='P'){const dir=this.turn==='w'?-1:1, home=this.turn==='w'?6:1, last=this.turn==='w'?0:7;const one=(r+dir)*8+f;\n if(r+dir>=0&&r+dir<8&&!this.board[one]){if(r+dir===last)for(const q of 'qrbn')add(from,one,q,'p');else add(from,one);const two=(r+2*dir)*8+f;if(r===home&&!this.board[two])add(from,two,null,'d');}\n for(const df of [-1,1]){const rr=r+dir,ff=f+df;if(rr<0||rr>7||ff<0||ff>7)continue;const to=rr*8+ff;if((this.board[to]&&color(this.board[to])!==this.turn)||to===this.ep){if(rr===last)for(const q of 'qrbn')add(from,to,q,to===this.ep?'ep':'cp');else add(from,to,null,to===this.ep?'e':'c');}}\n } else if(type==='N'||type==='K'){for(const [df,dr] of type==='N'?KNIGHT:KING){const rr=r+dr,ff=f+df;if(rr>=0&&rr<8&&ff>=0&&ff<8&&color(this.board[rr*8+ff])!==this.turn)add(from,rr*8+ff,null,this.board[rr*8+ff]?'c':'');}\n if(type==='K')this.castleMoves(from,add);\n } else {const dirs=type==='B'?KING.slice(4):type==='R'?KING.slice(0,4):KING;for(const[df,dr]of dirs){let rr=r+dr,ff=f+df;while(rr>=0&&rr<8&&ff>=0&&ff<8){const to=rr*8+ff;if(color(this.board[to])===this.turn)break;add(from,to,null,this.board[to]?'c':'');if(this.board[to])break;rr+=dr;ff+=df;}}}\n } return moves;\n }\n castleMoves(from:number, add:(from:number,to:number,promotion?:string|null,flags?:string)=>void):void {\n const white=this.turn==='w', base=white?60:4, enemy=white?'b':'w'; if(from!==base||this.inCheck())return;\n const king=white?'K':'k', rook=white?'R':'r'; if(this.board[from]!==king)return;\n if(this.castling.includes(white?'K':'k')&&this.board[base+3]===rook&&!this.board[base+1]&&!this.board[base+2]&&!this.attacked(base+1,enemy)&&!this.attacked(base+2,enemy))add(from,base+2,null,'k');\n if(this.castling.includes(white?'Q':'q')&&this.board[base-4]===rook&&!this.board[base-1]&&!this.board[base-2]&&!this.board[base-3]&&!this.attacked(base-1,enemy)&&!this.attacked(base-2,enemy))add(from,base-2,null,'q');\n }\n moves():Move[] { return this.pseudo().filter(m=>{const snapshot=this.snapshot();this.apply(m);const bad=this.inCheck(this.turn==='w'?'b':'w');this.restore(snapshot);return !bad;}); }\n snapshot():PositionSnapshot{return {board:[...this.board],turn:this.turn,castling:this.castling,ep:this.ep,halfmove:this.halfmove,fullmove:this.fullmove};}\n restore(s:PositionSnapshot):void{Object.assign(this,s);}\n apply(m:Move):void{const p=this.board[m.from]! as Piece, side=this.turn, captured=this.board[m.to];this.board[m.to]=(m.promotion?(side==='w'?m.promotion.toUpperCase():m.promotion):p) as Piece;this.board[m.from]=null;\n if(m.flags.includes('e'))this.board[m.to+(side==='w'?8:-8)]=null;\n if(m.flags==='k'){this.board[m.to-1]=this.board[m.to+1];this.board[m.to+1]=null;} if(m.flags==='q'){this.board[m.to+1]=this.board[m.to-2];this.board[m.to-2]=null;}\n const rights:Record<number,string>={0:'q',4:'kq',7:'k',56:'Q',60:'KQ',63:'K'};for(const sq of [m.from,m.to])if(rights[sq])for(const x of rights[sq])this.castling=this.castling.replace(x,'');\n this.ep=m.flags==='d'?(m.from+m.to)/2:-1;this.halfmove=(p.toUpperCase()==='P'||captured||m.flags.includes('e'))?0:this.halfmove+1;if(side==='b')this.fullmove++;this.turn=side==='w'?'b':'w';\n }\n san(m:Move, legal:Move[]=this.moves()):string {const p=this.board[m.from]!, type=p.toUpperCase();if(m.flags==='k')return'O-O';if(m.flags==='q')return'O-O-O';let s=type==='P'?'':type;\n if(type!=='P'){const same=legal.filter(x=>x!==m&&x.to===m.to&&this.board[x.from]?.toUpperCase()===type);if(same.length){if(same.every(x=>x.from%8!==m.from%8))s+=FILES[m.from%8];else if(same.every(x=>Math.floor(x.from/8)!==Math.floor(m.from/8)))s+=8-Math.floor(m.from/8);else s+=squareName(m.from);}}\n if(m.flags.includes('c')||m.flags.includes('e'))s+=(type==='P'?FILES[m.from%8]:'')+'x';s+=squareName(m.to);if(m.promotion)s+='='+m.promotion.toUpperCase();const snap=this.snapshot();this.apply(m);if(this.inCheck()){s+=this.moves().length?'#'.replace('#','+'):'#';}this.restore(snap);return s;\n }\n play(input:string):string {const legal=this.moves(), normalized=input.trim().replace(/[!?+#]/g,'').replace(/0/g,'O');let move=legal.find(m=>`${squareName(m.from)}${squareName(m.to)}${m.promotion||''}`===normalized.toLowerCase());if(!move)move=legal.find(m=>this.san(m,legal).replace(/[+#]/g,'')===normalized);if(!move)throw new Error(`Illegal or unrecognized move: ${input}`);const san=this.san(move,legal), before=this.snapshot();this.apply(move);this.history.push({move,san,before});return san;}\n undo():HistoryEntry|undefined{const h=this.history.pop();if(h)this.restore(h.before);return h;}\n status():string|null{const moves=this.moves();if(!moves.length)return this.inCheck()?(this.turn==='w'?'Black':'White')+' wins by checkmate':'Draw by stalemate';if(this.halfmove>=100)return'Draw by fifty-move rule';return null;}\n}\n", "import type { Chess } from './index.js';\nexport interface MoveResult { move: string; fen: string; explanation: string }\nexport interface MoveResolver { resolve(text: string, chess: Chess): Promise<MoveResult> }\nexport class ResolutionError extends Error {\n constructor(message: string, readonly status: number) { super(message); }\n}\n", "import { Chess, squareName } from './index.js';\n\nconst names: Record<string, string> = { P: 'Pawn', N: 'Knight', B: 'Bishop', R: 'Rook', Q: 'Queen', K: 'King' };\n\n/** Explain a recognizable move rejected for king safety, without changing the game. */\nexport function illegalMoveReason(input: string, chess: Chess): string | undefined {\n const text = input.trim();\n const uci = /^([a-h][1-8])([a-h][1-8])([qrbn])?$/.exec(text);\n const san = /^([KQRBN])?([a-h])?([1-8])?(x)?([a-h][1-8])(?:=([QRBN]))?[+#]?$/.exec(text);\n const words = text.toLowerCase();\n const squares = words.match(/[a-h][1-8]/g) || [];\n const named = words.match(/\\bwith (?:my |the |a )?(pawn|knight|bishop|rook|queen|king)\\b/)?.[1]\n || words.match(/\\b(pawn|knight|bishop|rook|queen|king)\\b/)?.[1];\n const kind = uci ? undefined : san ? san[1] || 'P'\n : Object.keys(names).find(key => names[key].toLowerCase() === named);\n const from = uci?.[1] || (squares.length > 1 ? squares[0] : undefined);\n const to = uci?.[2] || san?.[5] || squares.at(-1);\n if (!to || (!uci && !san && !kind && !from)) return;\n const capture = san ? Boolean(san[4]) : /\\b(take|takes|taking|capture|captures|capturing)\\b/.test(words);\n const candidates = chess.pseudo().filter(move => {\n if (squareName(move.to) !== to) return false;\n if (from && squareName(move.from) !== from) return false;\n if (kind && chess.board[move.from]!.toUpperCase() !== kind) return false;\n if (san?.[2] && squareName(move.from)[0] !== san[2]) return false;\n if (san?.[3] && squareName(move.from)[1] !== san[3]) return false;\n if (capture && !/[ce]/.test(move.flags)) return false;\n return true;\n });\n const legal = chess.moves();\n // A legal interpretation or multiple possible pieces needs clarification, not a pin claim.\n if (candidates.length !== 1 || legal.some(move => move.from === candidates[0].from && move.to === candidates[0].to)) return;\n const move = candidates[0];\n const copy = new Chess(chess.fen());\n copy.apply(move);\n if (!copy.inCheck(chess.turn)) return;\n const piece = chess.board[move.from]!.toUpperCase();\n if (piece === 'K') return `King cannot move to ${to}: that square is attacked.`;\n if (chess.inCheck()) return 'You are in check; this move would leave your king in check.';\n\n const king = chess.board.indexOf(chess.turn === 'w' ? 'K' : 'k');\n const dr = Math.floor(move.from / 8) - Math.floor(king / 8);\n const df = move.from % 8 - king % 8;\n if (dr === 0 || df === 0 || Math.abs(dr) === Math.abs(df)) {\n const stepR = Math.sign(dr), stepF = Math.sign(df);\n let rank = Math.floor(king / 8) + stepR, file = king % 8 + stepF;\n let passedPiece = false;\n while (rank >= 0 && rank < 8 && file >= 0 && file < 8) {\n const index = rank * 8 + file;\n const blocker = chess.board[index];\n if (index === move.from) passedPiece = true;\n else if (blocker) {\n const enemy = (blocker === blocker.toUpperCase() ? 'w' : 'b') !== chess.turn;\n const slider = (dr === 0 || df === 0 ? 'RQ' : 'BQ').includes(blocker.toUpperCase());\n if (passedPiece && enemy && slider) {\n return `${names[piece]} ${squareName(move.from)} is pinned by ${names[blocker.toUpperCase()].toLowerCase()} ${squareName(index)}; moving it exposes your king.`;\n }\n break;\n }\n rank += stepR;\n file += stepF;\n }\n }\n return `${names[piece]} ${squareName(move.from)} cannot move to ${to}: it would expose your king to check.`;\n}\n", "import { squareName, type Chess } from './index.js';\n\nconst names: Record<string, string> = { king: 'K', queen: 'Q', rook: 'R', bishop: 'B', knight: 'N', pawn: 'P' };\nexport function normalizeNotation(text: string): string {\n const symbols: Record<string, string> = { '\u2654':'K', '\u265A':'K', '\u2655':'Q', '\u265B':'Q', '\u2656':'R', '\u265C':'R', '\u2657':'B', '\u265D':'B', '\u2658':'N', '\u265E':'N', '\u2659':'', '\u265F':'' };\n return text.trim().replace(/[\u2654\u265A\u2655\u265B\u2656\u265C\u2657\u265D\u2658\u265E\u2659\u265F]/g, symbol => symbols[symbol])\n .replace(/\u00D7/g, 'x').replace(/([a-h][1-8])\\s*(?:\u2192|->|-)\\s*(?=[a-h][1-8])/g, '$1').replace(/0/g, 'O');\n}\n\nexport const looksLikeNotation = (text: string): boolean => !/\\s/.test(text) && (/\\d/.test(text) || /^[O0]-[O0]/.test(text));\n\nfunction distance(a: string, b: string): number {\n let row = Array.from({ length: b.length + 1 }, (_, i) => i);\n for (let i = 0; i < a.length; i++) {\n const next = [i + 1];\n for (let j = 0; j < b.length; j++) next.push(Math.min(next[j] + 1, row[j + 1] + 1, row[j] + Number(a[i] !== b[j])));\n row = next;\n }\n return row[b.length];\n}\n\n/** Prefer matching legal moves, then offer explicitly labeled legal alternatives. */\nexport function suggestMoves(input: string, chess: Chess): string[] {\n const text = normalizeNotation(input);\n const lower = text.toLowerCase();\n const notation = looksLikeNotation(text);\n const squares = lower.match(/[a-h][1-8]/g) || [];\n const destination = squares.at(-1);\n const source = squares.length > 1 ? squares[0] : undefined;\n const named = lower.match(/\\bwith (?:my |the |a )?(king|queen|rook|bishop|knight|pawn)\\b/)?.[1]\n || lower.match(/\\b(king|queen|rook|bishop|knight|pawn)\\b/)?.[1];\n const piece = named ? names[named] : notation && !/^[a-h][1-8][a-h][1-8]/.test(text)\n ? (/^[KQRBN]/.exec(text)?.[0] || (/^[a-h]/.test(text) ? 'P' : undefined)) : undefined;\n const capture = notation ? text.includes('x') : /\\b(take|takes|taking|capture|captures|capturing)\\b/.test(lower);\n const castle = /\\bcastl/.test(lower) || /^[O0]-[O0]/.test(text);\n const legal = chess.moves();\n const matches = legal.map(move => {\n const san = chess.san(move, legal);\n const from = squareName(move.from), to = squareName(move.to);\n const kind = chess.board[move.from]!.toUpperCase();\n if (piece && kind !== piece) return null;\n if (source && from !== source) return null;\n if (capture && !san.includes('x')) return null;\n if (castle && !san.startsWith('O-O')) return null;\n if (!notation && destination && to !== destination) return null;\n const uci = from + to + (move.promotion || '');\n const difference = Math.min(distance(text, san), distance(lower, uci));\n if (notation && difference > 2 && to !== destination) return null;\n return { san, score: (to === destination ? 20 : 0) + (from === source ? 10 : 0) - difference };\n }).filter((entry): entry is { san: string; score: number } => entry !== null)\n .sort((a, b) => b.score - a.score || a.san.localeCompare(b.san)).slice(0, 5).map(entry => entry.san);\n return matches.length ? matches : legal.map(move => chess.san(move, legal)).sort().slice(0, 5);\n}\n\nexport function suggestionMessage(input: string, chess: Chess): string {\n const moves = suggestMoves(input, chess);\n return moves.length ? `No exact match. Try: ${moves.join(' \u00B7 ')} (legal alternatives; confirm your intended move).` : 'No legal moves are available.';\n}\n", "import { squareName } from './index.js';\nimport type { Chess } from './index.js';\nimport { ResolutionError, type MoveResolver } from './resolution.js';\nimport { illegalMoveReason } from './legality.js';\nimport { looksLikeNotation, normalizeNotation, suggestionMessage } from './suggestions.js';\n\nexport type InputIntent =\n | { type:'empty' }\n | { type:'quit' }\n | { type:'help' }\n | { type:'undo' }\n | { type:'back' }\n | { type:'show-fen' }\n | { type:'load-fen'; value:string }\n | { type:'move'; value:string; source:'notation'|'jev'; fen?:string; explanation?:string };\n\n/** Parse local commands/notation; delegate all genuinely free-form text to JEV. */\nexport async function modelInput(raw:string, chess:Chess, server?:MoveResolver):Promise<InputIntent> {\n const text = String(raw).trim();\n const lower = text.toLowerCase();\n if (!text) return { type: 'empty' };\n if (/^\\/(quit|exit)$/.test(lower)) return { type: 'quit' };\n if (lower === '/help') return { type: 'help' };\n if (lower === '/undo') return { type: 'undo' };\n if (/^\\/(back|menu)$/.test(lower)) return { type: 'back' };\n if (/^\\/(fen|position)$/.test(lower)) return { type: 'show-fen' };\n if (/^\\/(fen|position)\\s+/.test(lower)) return { type: 'load-fen', value: text.replace(/^\\/(?:fen|position)\\s+/i, '').trim() };\n if (lower.startsWith('/')) throw new Error(`Unknown command: ${text}. Type /help to see commands.`);\n\n const legal = chess.moves();\n const normalized = normalizeNotation(text);\n const exact = legal.find(move => {\n const uci = squareName(move.from) + squareName(move.to) + (move.promotion || '');\n return uci === normalized || chess.san(move, legal) === normalized;\n });\n if (exact) return { type: 'move', value: squareName(exact.from) + squareName(exact.to) + (exact.promotion || ''), source: 'notation' };\n\n const reason = illegalMoveReason(text, chess);\n if (reason) throw new Error(`${reason} ${suggestionMessage(text, chess)}`);\n if (looksLikeNotation(text)) throw new Error(suggestionMessage(text, chess));\n\n if (!server) throw new Error(`Chess server is required for natural-language input. ${suggestionMessage(text, chess)}`);\n let result;\n try { result = await server.resolve(text, chess); }\n catch (error) {\n if (error instanceof ResolutionError && error.status === 422) throw new Error(suggestionMessage(text, chess));\n if (error instanceof Error && error.name === 'AbortError') throw error;\n const detail = error instanceof Error ? error.message : String(error);\n throw new Error(`${detail}. ${suggestionMessage(text, chess)}`);\n }\n return { type: 'move', value: result.move, fen: result.fen, explanation: result.explanation, source: 'jev' };\n}\n", "import type { Chess } from './index.js';\n\n/** Undo through the player's most recent move, including any engine reply. */\nexport function undoTurn(chess: Chess, human: 'w' | 'b'): boolean {\n let index = chess.history.length - 1;\n while (index >= 0 && chess.history[index].before.turn !== human) index--;\n if (index < 0) return false;\n while (chess.history.length > index) chess.undo();\n return true;\n}\n\nexport function moveHistory(chess: Chess, width = 80): string {\n const groups: string[] = [];\n for (const entry of chess.history) {\n const { fullmove, turn } = entry.before;\n if (turn === 'w') groups.push(`${fullmove}. ${entry.san}`);\n else if (groups.length) groups[groups.length - 1] += ` ${entry.san}`;\n else groups.push(`${fullmove}\u2026 ${entry.san}`);\n }\n if (!groups.length) return 'Moves: \u2014';\n let clipped = false;\n while (groups.length > 1 && `Moves: ${clipped ? '\u2026 ' : ''}${groups.join(' ')}`.length > width) {\n groups.shift();\n clipped = true;\n }\n return `Moves: ${clipped ? '\u2026 ' : ''}${groups.join(' ')}`;\n}\n", "import type { Chess } from '@zchess/chess';\nimport { ResolutionError, type MoveResult } from '@zchess/chess/interaction';\nexport { ResolutionError, type MoveResult } from '@zchess/chess/interaction';\nexport class ChessServerClient {\n constructor(private readonly baseUrl=process.env.ZCHESS_SERVER_URL||'http://localhost:8000', private readonly signal?:AbortSignal){}\n async resolve(text:string,chess:Chess):Promise<MoveResult>{return this.post('/api/resolve',{instruction:text,fen:chess.fen()});}\n private async post(path:string,body:unknown):Promise<MoveResult>{const response=await fetch(this.baseUrl.replace(/\\/$/,'')+path,{method:'POST',headers:{'content-type':'application/json'},body:JSON.stringify(body),signal:this.signal});if(!response.ok){\n const body = await response.json().catch(() => ({})) as {detail?:unknown};\n throw new ResolutionError(typeof body.detail === 'string' ? body.detail : `Chess server failed (${response.status})`, response.status);\n }return response.json() as Promise<MoveResult>;}\n}\n", "import type { Chess } from '@zchess/chess';\n\nconst PIECES: Record<string, string> = {\n K: '\u265A', Q: '\u265B', R: '\u265C', B: '\u265D', N: '\u265E', P: '\u265F',\n k: '\u265A', q: '\u265B', r: '\u265C', b: '\u265D', n: '\u265E', p: '\u265F',\n};\nconst OUTLINES: Record<string, string> = { K: '\u2654', Q: '\u2655', R: '\u2656', B: '\u2657', N: '\u2658', P: '\u2659' };\nconst RESET = '\\x1b[0m';\ninterface RenderOptions { perspective?: 'w' | 'b'; last?: number[] | null; color?: boolean; compact?: boolean; ascii?: boolean }\n\nexport function render(chess: Chess, { perspective = 'w', last = null, color = Boolean(process.stdout.isTTY), compact = false, ascii = false }: RenderOptions = {}): string {\n const rows = perspective === 'w' ? [0, 1, 2, 3, 4, 5, 6, 7] : [7, 6, 5, 4, 3, 2, 1, 0];\n const files = perspective === 'w' ? [0, 1, 2, 3, 4, 5, 6, 7] : [7, 6, 5, 4, 3, 2, 1, 0];\n // Typical terminal cells are about twice as tall as they are wide. Keep\n // compact ranks proportional too, and allow narrow windows to shrink.\n const cellWidth = Math.max(1, Math.min(compact ? 2 : 6, Math.floor(((process.stdout.columns || 80) - 8) / 8)));\n const cell = (content = ''): string => {\n const left = Math.floor((cellWidth - 1) / 2);\n return `${' '.repeat(left)}${content}${' '.repeat(cellWidth - left - (content ? 1 : 0))}`;\n };\n const defaultText = (text: string): string => color ? `\\x1b[39m${text}${RESET}` : text;\n const border = defaultText(` +${'-'.repeat(cellWidth * 8)}+`);\n const output = [border];\n\n for (const rank of rows) {\n for (const line of compact ? [1] : [0, 1, 2]) {\n let row = defaultText(`${line === 1 ? ` ${8 - rank} ` : ' '}|`);\n for (const file of files) {\n const index = rank * 8 + file;\n const piece = chess.board[index];\n const white = piece !== null && piece === piece.toUpperCase();\n const glyph = piece ? (ascii ? piece : !color && white ? OUTLINES[piece] : PIECES[piece]) : ' ';\n let square = cell(line === 1 ? glyph : '');\n if (color) {\n const background = last?.includes(index) ? 107 : (rank + file) % 2 ? 65 : 108;\n square = `\\x1b[1;48;5;${background};38;5;${white ? 231 : 16}m${square}${RESET}`;\n } else if (!piece && line === 1) {\n square = cell((rank + file) % 2 ? (ascii ? '.' : '\u00B7') : '');\n }\n row += square;\n }\n output.push(row + defaultText('|'));\n }\n }\n output.push(border);\n output.push(defaultText(' ' + files.map(file => cell('abcdefgh'[file])).join('')));\n output.push(ascii ? defaultText(' White: KQRBNP Black: kqrbnp') : color\n ? defaultText(' \u2654 White \u265A Black \u00B7 dark pieces')\n : ' \u2654 White \u265A Black');\n return output.join('\\n') + '\\n';\n}\n", "import { createRequire } from 'node:module';\nimport type { Chess } from '@zchess/chess';\nimport piecesData from '@zchess/chess/pieces' with { type: 'json' };\n\nconst require = createRequire(import.meta.url);\nconst pieces = piecesData as Record<string, string>;\nconst IMAGE_ID = 73191;\nexport { supportsGraphics, type GraphicsMode } from './terminal.js';\n\nexport function clearGraphics(): string {\n return `\\x1b_Ga=d,d=I,i=${IMAGE_ID},q=2;\\x1b\\\\`;\n}\n\nexport function boardSvg(chess: Chess, perspective: 'w' | 'b', last: number[] | null): string {\n const order = perspective === 'w' ? [0, 1, 2, 3, 4, 5, 6, 7] : [7, 6, 5, 4, 3, 2, 1, 0];\n const svg = ['<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"768\" height=\"768\" viewBox=\"0 0 768 768\">',\n '<rect width=\"768\" height=\"768\" rx=\"12\" fill=\"#14291f\"/>'];\n for (const [y, rank] of order.entries()) {\n for (const [x, file] of order.entries()) {\n const index = rank * 8 + file;\n const left = 24 + x * 90, top = 24 + y * 90;\n const fill = last?.includes(index) ? '#b4cf68' : (rank + file) % 2 ? '#64916d' : '#d5e5cb';\n svg.push(`<rect x=\"${left}\" y=\"${top}\" width=\"90\" height=\"90\" fill=\"${fill}\"/>`);\n const piece = chess.board[index];\n if (piece) svg.push(`<g transform=\"translate(${left} ${top}) scale(2)\">${pieces[piece]}</g>`);\n }\n svg.push(`<text x=\"12\" y=\"${24 + y * 90 + 50}\" text-anchor=\"middle\" font-size=\"16\" font-family=\"sans-serif\" fill=\"#d5e5cb\">${8 - rank}</text>`);\n }\n for (const [x, file] of order.entries()) {\n svg.push(`<text x=\"${24 + x * 90 + 45}\" y=\"762\" text-anchor=\"middle\" font-size=\"16\" font-family=\"sans-serif\" fill=\"#d5e5cb\">${'abcdefgh'[file]}</text>`);\n }\n svg.push('</svg>');\n return svg.join('');\n}\n\nexport function boardPng(chess: Chess, perspective: 'w' | 'b', last: number[] | null): Buffer {\n const { Resvg } = require('@resvg/resvg-js') as typeof import('@resvg/resvg-js');\n return new Resvg(boardSvg(chess, perspective, last)).render().asPng();\n}\n\nexport function renderGraphics(chess: Chess, perspective: 'w' | 'b', last: number[] | null, fixed = false, columnsPerRow = 2): string {\n // A single placement dimension preserves PNG aspect even in terminals that\n // stretch images when both c and r are supplied. Use measured cell pixels to\n // select the limiting dimension and reserve the corresponding rows.\n const availableRows = Math.max(1, Math.min(32, (process.stdout.rows || 40) - (fixed ? 8 : 7)));\n const availableColumns = Math.max(1, (process.stdout.columns || 80) - 2);\n const ratio = Number.isFinite(columnsPerRow) && columnsPerRow > 0 ? columnsPerRow : 2;\n const widthLimited = availableColumns / ratio < availableRows;\n const rows = widthLimited ? Math.ceil(availableColumns / ratio) : availableRows;\n const placement = widthLimited ? `c=${availableColumns}` : `r=${rows}`;\n const data = boardPng(chess, perspective, last).toString('base64');\n // Reserve room first: images anchored near the bottom must not cover the prompt.\n let output = clearGraphics();\n if (!fixed) output += '\\n'.repeat(rows) + `\\x1b[${rows}A\\r`;\n for (let offset = 0; offset < data.length; offset += 4096) {\n const chunk = data.slice(offset, offset + 4096);\n const more = offset + 4096 < data.length ? 1 : 0;\n const control = offset === 0 ? `a=T,f=100,t=d,i=${IMAGE_ID},${placement},C=1,q=2,` : '';\n output += `\\x1b_G${control}m=${more};${chunk}\\x1b\\\\`;\n }\n return output + `\\x1b[${rows}B\\r`;\n}\n", "{\n \"b\": \"<g id=\\\"black-bishop\\\" class=\\\"black bishop\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M9 36c3.39-.97 10.11.43 13.5-2 3.39 2.43 10.11 1.03 13.5 2 0 0 1.65.54 3 2-.68.97-1.65.99-3 .5-3.39-.97-10.11.46-13.5-1-3.39 1.46-10.11.03-13.5 1-1.354.49-2.323.47-3-.5 1.354-1.94 3-2 3-2zm6-4c2.5 2.5 12.5 2.5 15 0 .5-1.5 0-2 0-2 0-2.5-2.5-4-2.5-4 5.5-1.5 6-11.5-5-15.5-11 4-10.5 14-5 15.5 0 0-2.5 1.5-2.5 4 0 0-.5.5 0 2zM25 8a2.5 2.5 0 1 1-5 0 2.5 2.5 0 1 1 5 0z\\\" fill=\\\"#000\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M17.5 26h10M15 30h15m-7.5-14.5v5M20 18h5\\\" stroke=\\\"#fff\\\" stroke-linejoin=\\\"miter\\\"/></g>\",\n \"k\": \"<g id=\\\"black-king\\\" class=\\\"black king\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M22.5 11.63V6\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M22.5 25s4.5-7.5 3-10.5c0 0-1-2.5-3-2.5s-3 2.5-3 2.5c-1.5 3 3 10.5 3 10.5\\\" fill=\\\"#000\\\" stroke-linecap=\\\"butt\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M11.5 37c5.5 3.5 15.5 3.5 21 0v-7s9-4.5 6-10.5c-4-6.5-13.5-3.5-16 4V27v-3.5c-3.5-7.5-13-10.5-16-4-3 6 5 10 5 10V37z\\\" fill=\\\"#000\\\"/><path d=\\\"M20 8h5\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M32 29.5s8.5-4 6.03-9.65C34.15 14 25 18 22.5 24.5l.01 2.1-.01-2.1C20 18 9.906 14 6.997 19.85c-2.497 5.65 4.853 9 4.853 9M11.5 30c5.5-3 15.5-3 21 0m-21 3.5c5.5-3 15.5-3 21 0m-21 3.5c5.5-3 15.5-3 21 0\\\" stroke=\\\"#fff\\\"/></g>\",\n \"n\": \"<g id=\\\"black-knight\\\" class=\\\"black knight\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M 22,10 C 32.5,11 38.5,18 38,39 L 15,39 C 15,30 25,32.5 23,18\\\" style=\\\"fill:#000000; stroke:#000000;\\\"/><path d=\\\"M 24,18 C 24.38,20.91 18.45,25.37 16,27 C 13,29 13.18,31.34 11,31 C 9.958,30.06 12.41,27.96 11,28 C 10,28 11.19,29.23 10,30 C 9,30 5.997,31 6,26 C 6,24 12,14 12,14 C 12,14 13.89,12.1 14,10.5 C 13.27,9.506 13.5,8.5 13.5,7.5 C 14.5,6.5 16.5,10 16.5,10 L 18.5,10 C 18.5,10 19.28,8.008 21,7 C 22,7 22,10 22,10\\\" style=\\\"fill:#000000; stroke:#000000;\\\"/><path d=\\\"M 9.5 25.5 A 0.5 0.5 0 1 1 8.5,25.5 A 0.5 0.5 0 1 1 9.5 25.5 z\\\" style=\\\"fill:#ececec; stroke:#ececec;\\\"/><path d=\\\"M 15 15.5 A 0.5 1.5 0 1 1 14,15.5 A 0.5 1.5 0 1 1 15 15.5 z\\\" transform=\\\"matrix(0.866,0.5,-0.5,0.866,9.693,-5.173)\\\" style=\\\"fill:#ececec; stroke:#ececec;\\\"/><path d=\\\"M 24.55,10.4 L 24.1,11.85 L 24.6,12 C 27.75,13 30.25,14.49 32.5,18.75 C 34.75,23.01 35.75,29.06 35.25,39 L 35.2,39.5 L 37.45,39.5 L 37.5,39 C 38,28.94 36.62,22.15 34.25,17.66 C 31.88,13.17 28.46,11.02 25.06,10.5 L 24.55,10.4 z \\\" style=\\\"fill:#ececec; stroke:none;\\\"/></g>\",\n \"p\": \"<g id=\\\"black-pawn\\\" class=\\\"black pawn\\\"><path d=\\\"M22.5 9c-2.21 0-4 1.79-4 4 0 .89.29 1.71.78 2.38C17.33 16.5 16 18.59 16 21c0 2.03.94 3.84 2.41 5.03-3 1.06-7.41 5.55-7.41 13.47h23c0-7.92-4.41-12.41-7.41-13.47 1.47-1.19 2.41-3 2.41-5.03 0-2.41-1.33-4.5-3.28-5.62.49-.67.78-1.49.78-2.38 0-2.21-1.79-4-4-4z\\\" fill=\\\"#000\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\"/></g>\",\n \"q\": \"<g id=\\\"black-queen\\\" class=\\\"black queen\\\" fill=\\\"#000\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><g fill=\\\"#000\\\" stroke=\\\"none\\\"><circle cx=\\\"6\\\" cy=\\\"12\\\" r=\\\"2.75\\\"/><circle cx=\\\"14\\\" cy=\\\"9\\\" r=\\\"2.75\\\"/><circle cx=\\\"22.5\\\" cy=\\\"8\\\" r=\\\"2.75\\\"/><circle cx=\\\"31\\\" cy=\\\"9\\\" r=\\\"2.75\\\"/><circle cx=\\\"39\\\" cy=\\\"12\\\" r=\\\"2.75\\\"/></g><path d=\\\"M9 26c8.5-1.5 21-1.5 27 0l2.5-12.5L31 25l-.3-14.1-5.2 13.6-3-14.5-3 14.5-5.2-13.6L14 25 6.5 13.5 9 26zM9 26c0 2 1.5 2 2.5 4 1 1.5 1 1 .5 3.5-1.5 1-1.5 2.5-1.5 2.5-1.5 1.5.5 2.5.5 2.5 6.5 1 16.5 1 23 0 0 0 1.5-1 0-2.5 0 0 .5-1.5-1-2.5-.5-2.5-.5-2 .5-3.5 1-2 2.5-2 2.5-4-8.5-1.5-18.5-1.5-27 0z\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M11 38.5a35 35 1 0 0 23 0\\\" fill=\\\"none\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M11 29a35 35 1 0 1 23 0M12.5 31.5h20M11.5 34.5a35 35 1 0 0 22 0M10.5 37.5a35 35 1 0 0 24 0\\\" fill=\\\"none\\\" stroke=\\\"#fff\\\"/></g>\",\n \"r\": \"<g id=\\\"black-rook\\\" class=\\\"black rook\\\" fill=\\\"#000\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M9 39h27v-3H9v3zM12.5 32l1.5-2.5h17l1.5 2.5h-20zM12 36v-4h21v4H12z\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M14 29.5v-13h17v13H14z\\\" stroke-linecap=\\\"butt\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M14 16.5L11 14h23l-3 2.5H14zM11 14V9h4v2h5V9h5v2h5V9h4v5H11z\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M12 35.5h21M13 31.5h19M14 29.5h17M14 16.5h17M11 14h23\\\" fill=\\\"none\\\" stroke=\\\"#fff\\\" stroke-width=\\\"1\\\" stroke-linejoin=\\\"miter\\\"/></g>\",\n \"B\": \"<g id=\\\"white-bishop\\\" class=\\\"white bishop\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><g fill=\\\"#fff\\\" stroke-linecap=\\\"butt\\\"><path d=\\\"M9 36c3.39-.97 10.11.43 13.5-2 3.39 2.43 10.11 1.03 13.5 2 0 0 1.65.54 3 2-.68.97-1.65.99-3 .5-3.39-.97-10.11.46-13.5-1-3.39 1.46-10.11.03-13.5 1-1.354.49-2.323.47-3-.5 1.354-1.94 3-2 3-2zM15 32c2.5 2.5 12.5 2.5 15 0 .5-1.5 0-2 0-2 0-2.5-2.5-4-2.5-4 5.5-1.5 6-11.5-5-15.5-11 4-10.5 14-5 15.5 0 0-2.5 1.5-2.5 4 0 0-.5.5 0 2zM25 8a2.5 2.5 0 1 1-5 0 2.5 2.5 0 1 1 5 0z\\\"/></g><path d=\\\"M17.5 26h10M15 30h15m-7.5-14.5v5M20 18h5\\\" stroke-linejoin=\\\"miter\\\"/></g>\",\n \"K\": \"<g id=\\\"white-king\\\" class=\\\"white king\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M22.5 11.63V6M20 8h5\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M22.5 25s4.5-7.5 3-10.5c0 0-1-2.5-3-2.5s-3 2.5-3 2.5c-1.5 3 3 10.5 3 10.5\\\" fill=\\\"#fff\\\" stroke-linecap=\\\"butt\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M11.5 37c5.5 3.5 15.5 3.5 21 0v-7s9-4.5 6-10.5c-4-6.5-13.5-3.5-16 4V27v-3.5c-3.5-7.5-13-10.5-16-4-3 6 5 10 5 10V37z\\\" fill=\\\"#fff\\\"/><path d=\\\"M11.5 30c5.5-3 15.5-3 21 0m-21 3.5c5.5-3 15.5-3 21 0m-21 3.5c5.5-3 15.5-3 21 0\\\"/></g>\",\n \"N\": \"<g id=\\\"white-knight\\\" class=\\\"white knight\\\" fill=\\\"none\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M 22,10 C 32.5,11 38.5,18 38,39 L 15,39 C 15,30 25,32.5 23,18\\\" style=\\\"fill:#ffffff; stroke:#000000;\\\"/><path d=\\\"M 24,18 C 24.38,20.91 18.45,25.37 16,27 C 13,29 13.18,31.34 11,31 C 9.958,30.06 12.41,27.96 11,28 C 10,28 11.19,29.23 10,30 C 9,30 5.997,31 6,26 C 6,24 12,14 12,14 C 12,14 13.89,12.1 14,10.5 C 13.27,9.506 13.5,8.5 13.5,7.5 C 14.5,6.5 16.5,10 16.5,10 L 18.5,10 C 18.5,10 19.28,8.008 21,7 C 22,7 22,10 22,10\\\" style=\\\"fill:#ffffff; stroke:#000000;\\\"/><path d=\\\"M 9.5 25.5 A 0.5 0.5 0 1 1 8.5,25.5 A 0.5 0.5 0 1 1 9.5 25.5 z\\\" style=\\\"fill:#000000; stroke:#000000;\\\"/><path d=\\\"M 15 15.5 A 0.5 1.5 0 1 1 14,15.5 A 0.5 1.5 0 1 1 15 15.5 z\\\" transform=\\\"matrix(0.866,0.5,-0.5,0.866,9.693,-5.173)\\\" style=\\\"fill:#000000; stroke:#000000;\\\"/></g>\",\n \"P\": \"<g id=\\\"white-pawn\\\" class=\\\"white pawn\\\"><path d=\\\"M22.5 9c-2.21 0-4 1.79-4 4 0 .89.29 1.71.78 2.38C17.33 16.5 16 18.59 16 21c0 2.03.94 3.84 2.41 5.03-3 1.06-7.41 5.55-7.41 13.47h23c0-7.92-4.41-12.41-7.41-13.47 1.47-1.19 2.41-3 2.41-5.03 0-2.41-1.33-4.5-3.28-5.62.49-.67.78-1.49.78-2.38 0-2.21-1.79-4-4-4z\\\" fill=\\\"#fff\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\"/></g>\",\n \"Q\": \"<g id=\\\"white-queen\\\" class=\\\"white queen\\\" fill=\\\"#fff\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M8 12a2 2 0 1 1-4 0 2 2 0 1 1 4 0zM24.5 7.5a2 2 0 1 1-4 0 2 2 0 1 1 4 0zM41 12a2 2 0 1 1-4 0 2 2 0 1 1 4 0zM16 8.5a2 2 0 1 1-4 0 2 2 0 1 1 4 0zM33 9a2 2 0 1 1-4 0 2 2 0 1 1 4 0z\\\"/><path d=\\\"M9 26c8.5-1.5 21-1.5 27 0l2-12-7 11V11l-5.5 13.5-3-15-3 15-5.5-14V25L7 14l2 12zM9 26c0 2 1.5 2 2.5 4 1 1.5 1 1 .5 3.5-1.5 1-1.5 2.5-1.5 2.5-1.5 1.5.5 2.5.5 2.5 6.5 1 16.5 1 23 0 0 0 1.5-1 0-2.5 0 0 .5-1.5-1-2.5-.5-2.5-.5-2 .5-3.5 1-2 2.5-2 2.5-4-8.5-1.5-18.5-1.5-27 0z\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M11.5 30c3.5-1 18.5-1 22 0M12 33.5c6-1 15-1 21 0\\\" fill=\\\"none\\\"/></g>\",\n \"R\": \"<g id=\\\"white-rook\\\" class=\\\"white rook\\\" fill=\\\"#fff\\\" fill-rule=\\\"evenodd\\\" stroke=\\\"#000\\\" stroke-width=\\\"1.5\\\" stroke-linecap=\\\"round\\\" stroke-linejoin=\\\"round\\\"><path d=\\\"M9 39h27v-3H9v3zM12 36v-4h21v4H12zM11 14V9h4v2h5V9h5v2h5V9h4v5\\\" stroke-linecap=\\\"butt\\\"/><path d=\\\"M34 14l-3 3H14l-3-3\\\"/><path d=\\\"M31 17v12.5H14V17\\\" stroke-linecap=\\\"butt\\\" stroke-linejoin=\\\"miter\\\"/><path d=\\\"M31 29.5l1.5 2.5h-20l1.5-2.5\\\"/><path d=\\\"M11 14h23\\\" fill=\\\"none\\\" stroke-linejoin=\\\"miter\\\"/></g>\"\n}\n", "import { stdin, stdout } from 'node:process';\n\nexport type GraphicsMode = 'auto' | 'kitty' | 'text' | 'ascii';\nconst QUERY_ID = 73192;\n\nfunction blocksAutoGraphics(env: NodeJS.ProcessEnv): boolean {\n // Konsole 25.04.2 acknowledges Kitty queries but was observed to ignore our\n // single-dimension placement, clipping the board over the input field.\n // Keep auto conservative until its placement is empirically validated.\n const candidate = env.TERM === 'xterm-kitty' || env.TERM === 'xterm-ghostty' ||\n ['kitty', 'ghostty'].includes(env.TERM_PROGRAM?.toLowerCase() ?? '');\n // Unknown emulators can print APC payloads into shell scrollback (observed\n // in QTerminal 2.1.0). A hint permits probing; only an OK reply enables images.\n return Boolean(!candidate || env.TMUX || env.STY || env.TERM === 'dumb' ||\n env.KONSOLE_VERSION || env.TERM_PROGRAM?.toLowerCase() === 'konsole');\n}\n\n/** Environment variables can disable probing, but cannot prove graphics support. */\nexport function supportsGraphics(mode: GraphicsMode, tty = Boolean(stdout.isTTY && stdin.isTTY), env = process.env, confirmed = false): boolean {\n if (!tty || (mode === 'text' || mode === 'ascii')) return false;\n if (mode === 'kitty') return true;\n if (blocksAutoGraphics(env)) return false;\n return confirmed;\n}\n\n/** Isolate protocol replies from readline. Queries do not store or display images. */\nexport async function detectGraphics(mode: GraphicsMode, input = stdin, output = stdout, env = process.env, timeout = 300, onCellAspect?: (ratio: number) => void): Promise<boolean> {\n const tty = Boolean(input.isTTY && output.isTTY);\n if ((mode === 'text' || mode === 'ascii') || !tty || env.TMUX || env.STY || env.TERM === 'dumb' ||\n (mode === 'auto' && blocksAutoGraphics(env))) {\n return supportsGraphics(mode, tty, env);\n }\n const previous = input.listeners('data') as Array<(chunk: Buffer | string) => void>;\n previous.forEach(listener => input.off('data', listener));\n const wasRaw = input.isRaw;\n const wasFlowing = input.readableFlowing === true;\n let pending = '';\n let keyboard = '';\n let confirmed = mode === 'kitty';\n return await new Promise<boolean>((resolve, reject) => {\n let finished = false;\n const finish = (error?: Error): void => {\n if (finished) return;\n finished = true;\n clearTimeout(timer);\n input.pause();\n input.off('data', onData);\n input.off('end', onEnd);\n input.off('error', onError);\n input.setRawMode(Boolean(wasRaw));\n previous.forEach(listener => input.on('data', listener));\n // Replay original bytes, including any partial UTF-8 character. The\n // downstream decoder owns completion across this handoff and EOF.\n if (keyboard) input.unshift(Buffer.from(keyboard, 'latin1'));\n if (wasFlowing) input.resume();\n if (error) reject(error); else resolve(confirmed);\n };\n const onEnd = (): void => finish();\n const onError = (error: Error): void => finish(error);\n const onData = (chunk: Buffer | string): void => {\n // Latin-1 is a reversible byte mapping here, not a text encoding choice.\n // Protocol delimiters are ASCII; decoding keyboard UTF-8 here would\n // corrupt characters whose continuation arrives after the probe ends.\n pending += (typeof chunk === 'string' ? Buffer.from(chunk) : chunk).toString('latin1');\n while (pending) {\n if (pending[0] !== '\\x1b') {\n keyboard += pending[0];\n pending = pending.slice(1);\n continue;\n }\n const reply = pending.match(/^\\x1b_G([^;]*);([^\\x1b]*)\\x1b\\\\/);\n if (reply) {\n if (mode === 'auto' && reply[1].split(',').includes(`i=${QUERY_ID}`)) confirmed = reply[2] === 'OK';\n pending = pending.slice(reply[0].length);\n continue;\n }\n const cellSize = pending.match(/^\\x1b\\[6;(\\d+);(\\d+)t/);\n if (cellSize) {\n const height = Number(cellSize[1]), width = Number(cellSize[2]);\n if (height > 0 && width > 0 && height <= 1000 && width <= 1000) onCellAspect?.(height / width);\n pending = pending.slice(cellSize[0].length);\n continue;\n }\n const attributes = pending.match(/^\\x1b\\[\\?[\\d;]*c/);\n if (attributes) {\n keyboard += pending.slice(attributes[0].length);\n pending = '';\n finish();\n return;\n }\n // Buffer fragmented responses, preserving unrelated escape keys.\n if ('\\x1b_G'.startsWith(pending) || pending.startsWith('\\x1b_G') ||\n '\\x1b[?'.startsWith(pending) || /^\\x1b\\[(?:\\?[\\d;]*|6[;\\d]*)$/.test(pending)) break;\n keyboard += pending[0];\n pending = pending.slice(1);\n }\n };\n const timer = setTimeout(() => finish(), timeout);\n input.on('data', onData);\n input.once('end', onEnd);\n input.once('error', onError);\n try {\n input.setRawMode(true);\n input.resume();\n output.write(`\\x1b_Gi=${QUERY_ID},s=1,v=1,a=q,t=d,f=24;AAAA\\x1b\\\\\\x1b[16t\\x1b[c`);\n } catch (error) { finish(error as Error); }\n });\n}\n", "import { spawn } from 'node:child_process';\nimport { createRequire } from 'node:module';\nimport { createInterface } from 'node:readline';\nimport { Chess } from '@zchess/chess';\n\nconst require = createRequire(import.meta.url);\nconst stockfish = require('stockfish') as { findEngine(flavor: string): string };\n\n/** Run the bundled engine in a separate process so search never blocks the CLI. */\nexport async function engineMove(fen: string, elo: number, depth: number, signal?: AbortSignal): Promise<string> {\n if (!Number.isInteger(elo) || elo < 1320 || elo > 3190) throw new Error('ELO must be an integer from 1320 to 3190.');\n if (!Number.isInteger(depth) || depth < 1 || depth > 30) throw new Error('Depth must be an integer from 1 to 30.');\n signal?.throwIfAborted();\n const position = new Chess(fen);\n if (position.status()) throw new Error('The game is over.');\n\n return new Promise((resolve, reject) => {\n const child = spawn(process.execPath, [stockfish.findEngine('single')], { stdio: ['pipe', 'pipe', 'ignore'] });\n const lines = createInterface({ input: child.stdout });\n let settled = false;\n const finish = (error?: Error, move?: string): void => {\n if (settled) return;\n settled = true;\n clearTimeout(timer);\n signal?.removeEventListener('abort', cancel);\n lines.close();\n child.kill();\n if (error) reject(error);\n else resolve(move!);\n };\n const timer = setTimeout(() => finish(new Error('Stockfish timed out. Try a lower --depth.')), 60_000);\n const cancel = (): void => finish(new Error('Stockfish search cancelled.'));\n signal?.addEventListener('abort', cancel, { once: true });\n child.on('error', error => finish(new Error(`Could not start bundled Stockfish: ${error.message}`)));\n child.stdin.on('error', error => finish(error));\n child.on('exit', () => finish(new Error('Stockfish exited before returning a move.')));\n lines.on('line', line => {\n if (line === 'uciok') {\n child.stdin.write(`setoption name UCI_LimitStrength value true\\nsetoption name UCI_Elo value ${elo}\\nisready\\n`);\n } else if (line === 'readyok') {\n child.stdin.write(`position fen ${fen}\\ngo depth ${depth}\\n`);\n } else if (line.startsWith('bestmove ')) {\n const move = line.split(/\\s+/)[1];\n try {\n position.play(move);\n finish(undefined, move);\n } catch {\n finish(new Error('Stockfish returned an invalid move.'));\n }\n }\n });\n child.stdin.write('uci\\n');\n });\n}\n", "import { stdout } from 'node:process';\n\ninterface Output {\n columns?: number;\n rows?: number;\n write(text: string): unknown;\n}\n\n/** Keep game frames out of shell scrollback and restore the shell on exit. */\nexport class GameScreen {\n private opened = false;\n private cursorStyled = false;\n constructor(readonly active: boolean, private readonly output: Output = stdout, private readonly manageScreen = true) {}\n\n open(): void {\n if (this.active && this.manageScreen && !this.opened) {\n this.output.write('\\x1b[?1049h');\n this.opened = true;\n }\n }\n\n draw(header: string, board: string, status: string, moves = ''): void {\n if (!this.active) {\n this.output.write(`${header}\\n${moves}\\n\\n${board}\\n${status}\\n`);\n return;\n }\n const width = Math.max(1, (this.output.columns || 80) - 1);\n const fit = (text: string): string => [...text.replace(/[\\x00-\\x1f\\x7f]/g, ' ')].slice(0, width).join('');\n // Synchronized output prevents a visible blank frame between positions.\n const title = `\\x1b[39m${fit(header).padEnd(width)}\\x1b[0m`;\n const history = `\\x1b[39m${fit(moves).padEnd(width)}\\x1b[0m`;\n const horizontalPadding = Math.min(1, Math.floor((width - 1) / 2));\n const innerWidth = Math.max(1, width - horizontalPadding * 2);\n const controls = '/help';\n const visibleControls = controls.slice(-Math.min(innerWidth, controls.length));\n const statusWidth = Math.max(0, innerWidth - visibleControls.length);\n const footer = `\\x1b[39m${' '.repeat(horizontalPadding)}${fit(status).slice(0, statusWidth).padEnd(statusWidth)}${visibleControls}${' '.repeat(horizontalPadding + 1)}\\x1b[0m`;\n const bottom = Math.max(6, this.output.rows || 40);\n this.output.write('\\x1b[?2026h\\x1b[H\\x1b[2J' +\n `${title}\\r\\n${history}\\r\\n\\r\\n${board}\\x1b[${bottom - 4};1H${footer}` +\n this.inputFrame('', 'Type any moves e.g. e4 or e pawn up 2') + '\\x1b[?2026l');\n }\n\n input(value: string, placeholder = 'Type any moves e.g. e4 or e pawn up 2'): void {\n if (this.active) this.output.write(this.inputFrame(value, placeholder));\n }\n\n private inputFrame(value: string, placeholder: string): string {\n const width = Math.max(1, (this.output.columns || 80) - 1);\n const bottom = Math.max(6, this.output.rows || 40);\n const visible = [...value].slice(-Math.max(0, width - 4)).join('');\n const foreground = value ? '\\x1b[38;2;235;248;226m' : '\\x1b[38;2;139;168;144m';\n const horizontalPadding = 1;\n const fieldTextWidth = Math.max(0, width - horizontalPadding - 2);\n const shown = value\n ? [...visible].slice(-fieldTextWidth).join('')\n : [...placeholder].slice(0, Math.max(0, fieldTextWidth - 1)).join('');\n const prefix = ' ';\n const displayed = value ? shown : ` ${shown}`;\n const background = '\\x1b[48;2;12;42;34m';\n const paddingRow = `${background}${' '.repeat(width + 1)}\\x1b[0m`;\n const row = `${background}\\x1b[38;2;190;221;173m${prefix}${foreground}${displayed}${' '.repeat(Math.max(0, width + 1 - prefix.length - [...displayed].length))}\\x1b[0m`;\n const cursor = value ? Math.min(width, prefix.length + [...shown].length + 1) : 2;\n this.cursorStyled = true;\n return `\\x1b[${bottom - 2};1H${paddingRow}` +\n `\\x1b[${bottom - 1};1H${row}` +\n `\\x1b[${bottom};1H${paddingRow}\\x1b[${bottom - 1};${cursor}H\\x1b[5 q\\x1b[?25h`;\n }\n\n close(): void {\n if (this.cursorStyled) {\n this.output.write('\\x1b[0 q');\n this.cursorStyled = false;\n }\n if (this.opened) {\n this.output.write('\\x1b[?2026l\\x1b[?25h\\x1b[?1049l');\n this.opened = false;\n }\n }\n}\n\n/** Full-screen start and load menus that replace one another without scrollback. */\nexport class MenuScreen {\n private opened = false;\n constructor(readonly active: boolean, private readonly output: Output = stdout) {}\n\n open(): void {\n if (this.active && !this.opened) {\n this.output.write('\\x1b[?1049h\\x1b[?25l');\n this.opened = true;\n }\n }\n\n draw(header: string, content: string, footer: string): void {\n const width = Math.max(1, (this.output.columns || 80) - 1);\n const fit = (text: string): string => [...text.replace(/[\\x00-\\x1f\\x7f]/g, ' ')].slice(0, width).join('');\n if (!this.active) {\n this.output.write(`${header}\\n${content}\\n${footer}\\n`);\n return;\n }\n const title = `\\x1b[39m${fit(header).padEnd(width)}\\x1b[0m`;\n const horizontalPadding = Math.min(2, Math.floor((width - 1) / 2));\n const status = `\\x1b[39m${' '.repeat(horizontalPadding)}${fit(footer).slice(0, width - horizontalPadding * 2).padEnd(width - horizontalPadding * 2)}${' '.repeat(horizontalPadding)}\\x1b[0m`;\n const body = content.split('\\n').map(line => fit(line)).join('\\r\\n');\n this.output.write(`\\x1b[?25l\\x1b[?2026h\\x1b[H\\x1b[2J${title}\\r\\n\\r\\n${body}\\r\\n\\r\\n${status}\\r\\n\\x1b[?2026l`);\n }\n\n close(): void {\n if (this.opened) {\n this.output.write('\\x1b[?25h\\x1b[?1049l');\n this.opened = false;\n }\n }\n}\n", "import { DatabaseSync } from 'node:sqlite';\nimport { mkdirSync } from 'node:fs';\nimport { dirname, join } from 'node:path';\nimport { homedir } from 'node:os';\n\nexport interface SavedGame {\n id: number;\n createdAt: string;\n updatedAt: string;\n elo: number;\n color: 'w' | 'b';\n startFen: string;\n fen: string;\n moves: string[];\n status: string;\n}\n\nexport class GameStore {\n private readonly db: DatabaseSync;\n\n constructor(path = process.env.ZCHESS_DB_PATH || join(process.env.XDG_DATA_HOME || join(homedir(), '.local', 'share'), 'zchess', 'games.sqlite')) {\n mkdirSync(dirname(path), { recursive: true });\n this.db = new DatabaseSync(path);\n this.db.exec(`\n PRAGMA journal_mode = WAL;\n CREATE TABLE IF NOT EXISTS games (\n id INTEGER PRIMARY KEY,\n created_at TEXT NOT NULL,\n updated_at TEXT NOT NULL,\n elo INTEGER NOT NULL,\n color TEXT NOT NULL CHECK (color IN ('w', 'b')),\n start_fen TEXT NOT NULL,\n fen TEXT NOT NULL,\n moves TEXT NOT NULL,\n status TEXT NOT NULL\n );\n `);\n }\n\n save(game: Omit<SavedGame, 'id' | 'createdAt' | 'updatedAt'>, id?: number): number {\n const now = new Date().toISOString();\n if (id === undefined) {\n const result = this.db.prepare(`INSERT INTO games (created_at, updated_at, elo, color, start_fen, fen, moves, status)\n VALUES (?, ?, ?, ?, ?, ?, ?, ?)`).run(now, now, game.elo, game.color, game.startFen, game.fen, JSON.stringify(game.moves), game.status);\n return Number(result.lastInsertRowid);\n }\n this.db.prepare(`UPDATE games SET updated_at = ?, elo = ?, color = ?, start_fen = ?, fen = ?, moves = ?, status = ? WHERE id = ?`)\n .run(now, game.elo, game.color, game.startFen, game.fen, JSON.stringify(game.moves), game.status, id);\n return id;\n }\n\n list(): SavedGame[] {\n const rows = this.db.prepare('SELECT * FROM games ORDER BY updated_at DESC').all() as Array<Record<string, unknown>>;\n return rows.map(row => this.decode(row));\n }\n\n get(id: number): SavedGame | undefined {\n const row = this.db.prepare('SELECT * FROM games WHERE id = ?').get(id) as Record<string, unknown> | undefined;\n return row ? this.decode(row) : undefined;\n }\n\n close(): void { this.db.close(); }\n\n private decode(row: Record<string, unknown>): SavedGame {\n return {\n id: Number(row.id), createdAt: String(row.created_at), updatedAt: String(row.updated_at),\n elo: Number(row.elo), color: row.color === 'b' ? 'b' : 'w', startFen: String(row.start_fen), fen: String(row.fen),\n moves: JSON.parse(String(row.moves)) as string[], status: String(row.status),\n };\n }\n}\n"],
5
+ "mappings": "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",
6
+ "names": ["createInterface", "stdin", "stdout", "message", "move", "names", "body", "color", "require", "createRequire", "require", "createRequire", "stdout", "stdin", "stdout", "createInterface", "game", "elo", "listener"]
7
7
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "zchess",
3
- "version": "0.1.7-alpha.0",
3
+ "version": "0.1.8-alpha.0",
4
4
  "type": "module",
5
5
  "engines": {
6
6
  "node": ">=22.13.0"