Fix Titan (king tracking)
[vchess.git] / client / src / variants / Titan.js
index aadc3e7..427eecd 100644 (file)
@@ -120,69 +120,31 @@ export class TitanRules extends ChessRules {
     }
   }
 
-  // If piece not in usual list, bishop or knight appears.
-  getPotentialMovesFrom([x, y]) {
-    if (this.movesCount <= 3) {
-      // Setup stage
-      const color = this.getColor(x, y);
-      const firstRank = (color == 'w' ? 7 : 0);
-      if (x != firstRank || V.AUGMENTED_PIECES.includes(this.board[x][y][1]))
-        return [];
-      const piece = this.getPiece(x, y);
-      const move = new Move({
-        appear: [
-          new PiPo({ x: x, y: y, c: color, p: this.getAugmented(piece) })
-        ],
-        vanish: [
-          new PiPo({ x: x, y: y, c: color, p: piece })
-        ],
-        start: { x: x, y: y },
-        end: { x: x, y: y }
-      });
-      return [move];
-    }
-    let moves = super.getPotentialMovesFrom([x, y]);
-    const initialPiece = this.getPiece(x, y);
-    const color = this.turn;
-    if (
-      V.AUGMENTED_PIECES.includes(this.board[x][y][1]) &&
-      ((color == 'w' && x == 7) || (color == "b" && x == 0))
-    ) {
-      const newPiece = this.getExtraPiece(this.board[x][y][1]);
-      moves.forEach(m => {
-        m.appear[0].p = initialPiece;
-        m.appear.push(
-          new PiPo({
-            p: newPiece,
-            c: color,
-            x: x,
-            y: y
-          })
-        );
-      });
-    }
-    moves.forEach(m => {
-      if (m.vanish.length <= 1) return;
-      const [vx, vy] = [m.vanish[1].x, m.vanish[1].y];
-      if (
-        m.appear.length >= 2 && //3 if the king was also augmented
-        m.vanish.length == 2 &&
-        m.vanish[1].c == color &&
-        V.AUGMENTED_PIECES.includes(this.board[vx][vy][1])
-      ) {
-        // Castle, rook is an "augmented piece"
-        m.appear[1].p = V.ROOK;
-        m.appear.push(
-          new PiPo({
-            p: this.getExtraPiece(this.board[vx][vy][1]),
-            c: color,
-            x: vx,
-            y: vy
-          })
-        );
-      }
-    });
-    return moves;
+  canIplay(side, [x, y]) {
+    if (this.movesCount >= 4) return super.canIplay(side, [x, y]);
+    return (
+      this.turn == side &&
+      (
+        (side == 'w' && x == 7) ||
+        (side == 'b' && x == 0)
+      )
+    );
+  }
+
+  hoverHighlight([x, y]) {
+    const c = this.turn;
+    return (
+      this.movesCount <= 3 &&
+      ((c == 'w' && x == 7) || (c == 'b' && x == 0))
+    );
+  }
+
+  onlyClick([x, y]) {
+    return (
+      this.movesCount <= 3 ||
+      // TODO: next line theoretically shouldn't be required...
+      (this.movesCount == 4 && this.getColor(x, y) != this.turn)
+    );
   }
 
   // Special case of move 1 = choose squares, knight first, then bishop
@@ -214,12 +176,73 @@ export class TitanRules extends ChessRules {
     });
   }
 
+  // If piece not in usual list, bishop or knight appears.
+  getPotentialMovesFrom([x, y]) {
+    if (this.movesCount <= 3) {
+      // Setup stage
+      const move = this.doClick([x, y]);
+      return (!move ? [] : [move]);
+    }
+    let moves = super.getPotentialMovesFrom([x, y]);
+    const initialPiece = this.getPiece(x, y);
+    const color = this.turn;
+    if (
+      ((color == 'w' && x == 7) || (color == "b" && x == 0)) &&
+      V.AUGMENTED_PIECES.includes(this.board[x][y][1])
+    ) {
+      const newPiece = this.getExtraPiece(this.board[x][y][1]);
+      moves.forEach(m => {
+        m.appear[0].p = initialPiece;
+        m.appear.push(
+          new PiPo({
+            p: newPiece,
+            c: color,
+            x: x,
+            y: y
+          })
+        );
+      });
+      moves.forEach(m => {
+        if (m.vanish.length <= 1) return;
+        const [vx, vy] = [m.vanish[1].x, m.vanish[1].y];
+        if (
+          m.appear.length >= 2 && //3 if the king was also augmented
+          m.vanish.length == 2 &&
+          m.vanish[1].c == color &&
+          V.AUGMENTED_PIECES.includes(this.board[vx][vy][1])
+        ) {
+          // Castle, rook is an "augmented piece"
+          m.appear[1].p = V.ROOK;
+          m.appear.push(
+            new PiPo({
+              p: this.getExtraPiece(this.board[vx][vy][1]),
+              c: color,
+              x: vx,
+              y: vy
+            })
+          );
+        }
+      });
+    }
+    return moves;
+  }
+
   postPlay(move) {
-    if (this.movesCount > 4) super.postPlay(move);
+    if (this.movesCount > 4) {
+      let piece = move.vanish[0].p;
+      if (['j', 'l'].includes(piece)) piece = V.KING;
+      if (piece == V.KING && move.appear.length > 0)
+        this.kingPos[c] = [move.appear[0].x, move.appear[0].y];
+      this.updateCastleFlags(move, piece);
+    }
   }
 
   postUndo(move) {
-    if (this.movesCount >= 4) super.postUndo(move);
+    if (this.movesCount >= 4) {
+      const c = this.getColor(move.start.x, move.start.y);
+      if (['j', 'k', 'l'].includes(this.getPiece(move.start.x, move.start.y)))
+        this.kingPos[c] = [move.start.x, move.start.y];
+    }
   }
 
   evalPosition() {
@@ -249,6 +272,7 @@ export class TitanRules extends ChessRules {
       if (
         V.AUGMENTED_PIECES.includes(move.vanish[0].p) ||
         (
+          move.appear.length >= 2 &&
           move.vanish.length >= 2 &&
           V.AUGMENTED_PIECES.includes(move.vanish[1].p)
         )