UNPKG

binmat

Version:
144 lines (143 loc) 6.08 kB
import { doMoveCombat } from "./doMoveCombat.js" import { doMoveDiscard } from "./doMoveDiscard.js" import { doMoveDraw } from "./doMoveDraw.js" import { doMovePass } from "./doMovePass.js" import { doMovePlay } from "./doMovePlay.js" import { doMovePlayFaceUp } from "./doMovePlayFaceUp.js" import { MoveKind, StatusCode, AttackerDeck } from "./shared.js" import "./doCombat.js" import "@samual/lib/shuffle" import "@samual/lib/assert" function doMove(state, move) { const turn = String(state.turn).padStart(3, "0"), roleTurn = state.turn % 2 ? "a" : "d" switch (move.kind) { case MoveKind.Draw: { const deckIsEmpty = !(move.deck == AttackerDeck ? state.attackerDeck : state.laneDecks[move.deck]).length, result = doMoveDraw(state, move.deck), deck = move.deck == AttackerDeck ? "a" : move.deck if (result.status == StatusCode.AttackerWin) return { status: StatusCode.AttackerWin, binlog: [`\`V${turn}\` \`n------\``, `${roleTurn}0 d${deck}`] } if (result.status == StatusCode.Ok || result.status == StatusCode.DefenderWin) { const card = move.deck < 3 || move.deck == AttackerDeck || deckIsEmpty ? "X" : result.cardDrawn return { status: result.status, binlog: [`\`V${turn}\` \`n------\``, `${roleTurn}0 d${deck} / ${card} h${roleTurn}0 `] } } return { status: result.status } } case MoveKind.Play: { const result = doMovePlay(state, move.card, move.lane) return result.status == StatusCode.Ok || result.status == StatusCode.DefenderWin ? { status: result.status, binlog: [`\`V${turn}\` \`n------\``, `${roleTurn}0 pX${move.lane} / X ${roleTurn}${move.lane}`] } : { status: result.status } } case MoveKind.PlayFaceUp: { const result = doMovePlayFaceUp(state, move.card, move.lane) if ( result.status == StatusCode.Ok || result.status == StatusCode.AttackerWin || result.status == StatusCode.DefenderWin ) { const binlog = [ `\`V${turn}\` \`n------\``, `${roleTurn}0 u${result.cardPlayed[0]}${move.lane} / ${result.cardPlayed} ${roleTurn}${move.lane}` ] return ( result.combat && pushCombatBinlog(binlog, result.combat, move.lane, result.cardPlayed), { status: result.status, binlog: binlog } ) } return { status: result.status } } case MoveKind.Combat: { const result = doMoveCombat(state, move.lane) if ( result.status == StatusCode.Ok || result.status == StatusCode.DefenderWin || result.status == StatusCode.AttackerWin ) { const binlog = [`\`V${turn}\` \`n------\``, `${roleTurn}0 c${move.lane}`] return pushCombatBinlog(binlog, result, move.lane), { status: result.status, binlog: binlog } } return { status: result.status } } case MoveKind.Discard: { const result = doMoveDiscard(state, move.card, move.discardPile) if (result.status == StatusCode.Ok || result.status == StatusCode.DefenderWin) { const discardPile = move.discardPile == AttackerDeck ? "a" : move.discardPile return { status: result.status, binlog: [ `\`V${turn}\` \`n------\``, `${roleTurn}0 x${result.cardDiscarded[0]}${discardPile} / ${result.cardDiscarded} x${discardPile}` ] } } return { status: result.status } } case MoveKind.Pass: { const status = doMovePass(state) return status == StatusCode.MadeMoveOnFinishedGame ? { status: status } : { status: status, binlog: [`\`V${turn}\` \`n------\``, `${roleTurn}0 \`n--\``] } } } function pushCombatBinlog(binlog, combatData, lane, cardIsPlayedFaceUp) { const { attackerAttackPower: attackerAttackPower, attackerStack: attackerStack, defenderAttackPower: defenderAttackPower, defenderStack: defenderStack, attackerCardsTrapped: attackerCardsTrapped, defenderCardsTrapped: defenderCardsTrapped, attackerBouncesDiscarded: attackerBouncesDiscarded, defenderBouncesDiscarded: defenderBouncesDiscarded, damageValue: damageValue, defenderStackWasFaceUp: defenderStackWasFaceUp } = combatData, attackerSide = "a" == roleTurn && cardIsPlayedFaceUp && attackerStack.length ? `${attackerStack.join(" ")}u` : attackerStack.join(" "), defenderSide = defenderStackWasFaceUp ? defenderStack.map(card => `${card}u`).join(" ") : defenderStack.join(" ") binlog.push(`\`n--\` c${lane} / ${attackerSide} / ${defenderSide}`), "d" == roleTurn ? (attackerCardsTrapped.length && binlog.push(`\`n--\` d@ / ${attackerCardsTrapped.join(" ")} x${lane}`), defenderCardsTrapped.length && binlog.push(`\`n--\` a@ / ${defenderCardsTrapped.join(" ")} xa`)) : (defenderCardsTrapped.length && binlog.push(`\`n--\` a@ / ${defenderCardsTrapped.join(" ")} xa`), attackerCardsTrapped.length && binlog.push(`\`n--\` d@ / ${attackerCardsTrapped.join(" ")} x${lane}`)), attackerBouncesDiscarded.length && binlog.push(`\`n--\` a? / ${attackerBouncesDiscarded.join(" ")} x${lane}`), defenderBouncesDiscarded.length && binlog.push(`\`n--\` d? / ${defenderBouncesDiscarded.join(" ")} xa`) const attackerStackDiscarded = "a" == roleTurn && cardIsPlayedFaceUp && combatData.attackerStackDiscarded.at(-1) == cardIsPlayedFaceUp ? `${combatData.attackerStackDiscarded.join(" ")}u` : combatData.attackerStackDiscarded.join(" ") if (damageValue) { const cardsDrawnToDiscard = combatData.cardsDrawnToDiscard.length ? ` / ${combatData.cardsDrawnToDiscard.join(" ")} xa` : "" let cardsDrawn ;(cardsDrawn = combatData.cardsDrawn.length ? lane < 3 ? ` / ${"X ".repeat(combatData.cardsDrawn.length)}ha0 ` : ` / ${combatData.cardsDrawn.join(" ")} ha0 ` : ""), binlog.push( `\`n--\` ${attackerAttackPower} ${defenderAttackPower} ${damageValue} / ${attackerStackDiscarded} xa${cardsDrawnToDiscard}${cardsDrawn}` ) } else attackerAttackPower || defenderAttackPower ? binlog.push( `\`n--\` ${attackerAttackPower} ${defenderAttackPower} - / ${attackerStackDiscarded} x${lane}` ) : binlog.push(`\`n--\` 0 0 0 / ${attackerStackDiscarded} xa`) } } export { doMove }