Pandemonium: promotion on last 2 ranks
[vchess.git] / client / src / variants / Cannibal2.js
1 import { Cannibal1Rules } from "@/variants/Cannibal1";
2
3 export class Cannibal2Rules extends Cannibal1Rules {
4
5 // Trim all non-capturing moves
6 static KeepCaptures(moves) {
7 return moves.filter(m => m.vanish.length == 2 && m.appear.length == 1);
8 }
9
10 // Stop at the first capture found (if any)
11 atLeastOneCapture() {
12 const color = this.turn;
13 const oppCol = V.GetOppCol(color);
14 for (let i = 0; i < V.size.x; i++) {
15 for (let j = 0; j < V.size.y; j++) {
16 if (
17 this.board[i][j] != V.EMPTY &&
18 this.getColor(i, j) != oppCol &&
19 this.filterValid(this.getPotentialMovesFrom([i, j])).some(m =>
20 // Warning: discard castle moves
21 m.vanish.length == 2 && m.appear.length == 1)
22 ) {
23 return true;
24 }
25 }
26 }
27 return false;
28 }
29
30 addPawnMoves([x1, y1], [x2, y2], moves) {
31 let finalPieces = [V.PAWN];
32 const color = this.turn;
33 const lastRank = (color == "w" ? 0 : V.size.x - 1);
34 if (x2 == lastRank) {
35 if (this.board[x2][y2] != V.EMPTY)
36 // Cannibal rules: no choice if capture
37 finalPieces = [this.getPiece(x2, y2)];
38 else finalPieces = V.PawnSpecs.promotions;
39 }
40 let tr = null;
41 for (let piece of finalPieces) {
42 tr = (piece != V.PAWN ? { c: color, p: piece } : null);
43 moves.push(this.getBasicMove([x1, y1], [x2, y2], tr));
44 }
45 }
46
47 getPossibleMovesFrom(sq) {
48 let moves = this.filterValid(this.getPotentialMovesFrom(sq));
49 const captureMoves = V.KeepCaptures(moves);
50 if (captureMoves.length > 0) return captureMoves;
51 if (this.atLeastOneCapture()) return [];
52 return moves;
53 }
54
55 getAllValidMoves() {
56 const moves = super.getAllValidMoves();
57 if (moves.some(m => m.vanish.length == 2 && m.appear.length == 1))
58 return V.KeepCaptures(moves);
59 return moves;
60 }
61
62 };