X-Git-Url: https://git.auder.net/?a=blobdiff_plain;f=client%2Fsrc%2Fvariants%2FEightpieces.js;h=dc7580b32a63e806eb2eb6a6737e5ec7c9ab0bd9;hb=abbda16dbd485dfc43ee502bbef67045b1aecc59;hp=c380610c159c25f5fde4b013a9e18f67ebb47b66;hpb=f52671e5b5b50b1421474f27dc9c18f701b559f3;p=vchess.git diff --git a/client/src/variants/Eightpieces.js b/client/src/variants/Eightpieces.js index c380610c..dc7580b3 100644 --- a/client/src/variants/Eightpieces.js +++ b/client/src/variants/Eightpieces.js @@ -1,4 +1,4 @@ -import { randInt } from "@/utils/alea"; +import { randInt, sample } from "@/utils/alea"; import { ChessRules, PiPo, Move } from "@/base_rules"; export class EightpiecesRules extends ChessRules { @@ -167,58 +167,54 @@ export class EightpiecesRules extends ChessRules { } } - static GenRandInitFen(randomness) { - if (randomness == 0) + static GenRandInitFen(options) { + if (options.randomness == 0) return "jfsqkbnr/pppppppp/8/8/8/8/PPPPPPPP/JDSQKBNR w 0 ahah - -"; - const baseFen = ChessRules.GenRandInitFen(randomness); + const baseFen = ChessRules.GenRandInitFen(options); const fenParts = baseFen.split(' '); const posParts = fenParts[0].split('/'); // Replace one bishop by sentry, so that sentries on different colors // Also replace one random rook by jailer, // and one random knight by lancer (facing north/south) - - // "replaced" array contains -2 initially, then either -1 if skipped, - // or (eventually) the index of replacement: - let newPos = { 0: "", 7: "" }; - let sentryOddity = -1; - for (let rank of [0, 7]) { - let replaced = { 'b': -2, 'n': -2, 'r': -2 }; - for (let i = 0; i < 8; i++) { - const curChar = posParts[rank].charAt(i).toLowerCase(); - if (['b', 'n', 'r'].includes(curChar)) { - if ( - replaced[curChar] == -1 || - (curChar == 'b' && rank == 7 && i % 2 == sentryOddity) || - ( - (curChar != 'b' || rank == 0) && - replaced[curChar] == -2 && - randInt(2) == 0 - ) - ) { - replaced[curChar] = i; - if (curChar == 'b') { - if (sentryOddity < 0) sentryOddity = i % 2; - newPos[rank] += 's'; - } - else if (curChar == 'r') newPos[rank] += 'j'; - else - // Lancer: orientation depends on side - newPos[rank] += (rank == 0 ? 'g' : 'c'); - } - else { - if (replaced[curChar] == -2) replaced[curChar]++; - newPos[rank] += curChar; - } - } - else newPos[rank] += curChar; + let pieceLine = { b: posParts[0], w: posParts[7].toLowerCase() }; + let posBlack = { r: -1, n: -1, b: -1 }; + const mapP = { r: 'j', n: 'l', b: 's' }; + ['w', 'b'].forEach(c => { + ['r', 'n', 'b'].forEach(p => { + let pl = pieceLine[c]; + let pos = -1; + if (options.randomness == 2 || c == 'b') + pos = (randInt(2) == 0 ? pl.indexOf(p) : pl.lastIndexOf(p)); + else pos = posBlack[p]; + pieceLine[c] = + pieceLine[c].substr(0, pos) + mapP[p] + pieceLine[c].substr(pos+1); + if (options.randomness == 1 && c == 'b') posBlack[p] = pos; + }); + }); + // Rename 'l' into 'g' (black) or 'c' (white) + pieceLine['w'] = pieceLine['w'].replace('l', 'c'); + pieceLine['b'] = pieceLine['b'].replace('l', 'g'); + if (options.randomness == 2) { + const ws = pieceLine['w'].indexOf('s'); + const bs = pieceLine['b'].indexOf('s'); + if (ws % 2 != bs % 2) { + // Fix sentry: should be on different colors. + // => move sentry on other bishop for random color + const c = sample(['w', 'b'], 1); + pieceLine[c] = pieceLine[c] + .replace('b', 't'); //tmp + .replace('s', 'b'); + .replace('t', 's'); } } return ( - newPos[0] + "/" + posParts.slice(1, 7).join('/') + "/" + - newPos[7].toUpperCase() + " " + fenParts.slice(1, 5).join(' ') + " -" + pieceLine['b'] + "/" + + posParts.slice(1, 7).join('/') + "/" + + pieceLine['w'].toUpperCase() + " " + + fenParts.slice(1, 5).join(' ') + " -" ); } @@ -671,10 +667,7 @@ export class EightpiecesRules extends ChessRules { getPotentialKingMoves(sq) { const moves = this.getSlideNJumpMoves( - sq, - V.steps[V.ROOK].concat(V.steps[V.BISHOP]), - "oneStep" - ); + sq, V.steps[V.ROOK].concat(V.steps[V.BISHOP]), 1); return ( this.subTurn == 1 ? moves.concat(this.getCastleMoves(sq)) @@ -824,8 +817,8 @@ export class EightpiecesRules extends ChessRules { const oppCol = V.GetOppCol(color); const sliderAttack = (allowedSteps, lancer) => { const deltaX = x2 - x1, - absDeltaX = Math.abs(deltaX); - const deltaY = y2 - y1, + deltaY = y2 - y1; + const absDeltaX = Math.abs(deltaX), absDeltaY = Math.abs(deltaY); const step = [ deltaX / absDeltaX || 0, deltaY / absDeltaY || 0 ]; if ( @@ -837,12 +830,18 @@ export class EightpiecesRules extends ChessRules { } let sq = [ x1 + step[0], y1 + step[1] ]; while (sq[0] != x2 || sq[1] != y2) { - if ( - // NOTE: no need to check OnBoard in this special case - (!lancer && this.board[sq[0]][sq[1]] != V.EMPTY) || - (!!lancer && this.getColor(sq[0], sq[1]) == oppCol) - ) { - return false; + // NOTE: no need to check OnBoard in this special case + if (this.board[sq[0]][sq[1]] != V.EMPTY) { + const p = this.getPiece(sq[0], sq[1]); + const pc = this.getColor(sq[0], sq[1]); + if ( + // Enemy sentry on the way will be gone: + (p != V.SENTRY || pc != oppCol) && + // Lancer temporarily "changed color": + (!lancer || pc == color) + ) { + return false; + } } sq[0] += step[0]; sq[1] += step[1];