UNPKG

hathora-et-labora-game

Version:

Plays Uwe Rosenberg's Ora et Labora for the Hathora engine. It reduces a list of moves into a board game state.

69 lines 3.36 kB
import { match, P } from 'ts-pattern'; import { GameCommandEnum, } from './types'; import { parseResourceParam } from './board/resource'; import { build, commit, config, convert, cutPeat, fellTrees, settle, start, use, withLaybrother, withPrior, buyPlot, buyDistrict, workContract, } from './commands'; const PPlot = P.union('MOUNTAIN', 'COAST'); const PDistrict = P.union('HILLS', 'PLAINS'); const PPlayerCount = P.union('1', '2', '3', '4'); const PCountry = P.union('ireland', 'france'); const PLength = P.union('short', 'long'); export const reducer = (state, [command, ...params]) => { return match([command, params]) .with([GameCommandEnum.COMMIT, []], () => commit(state)) .with([GameCommandEnum.USE, P.array(P.string)], ([_command, [building, ...params]]) => use(building, params)(state)) .with([GameCommandEnum.BUILD, P.array(P.string)], ([_, [building, col, row]]) => build({ building: building, col: Number.parseInt(col, 10), row: Number.parseInt(row, 10), })(state)) .with([GameCommandEnum.CUT_PEAT, P.array(P.string)], ([_, [col, row, useJoker]]) => cutPeat({ col: Number.parseInt(col, 10), row: Number.parseInt(row, 10), useJoker: useJoker === 'Jo', })(state)) .with([GameCommandEnum.FELL_TREES, P.array(P.string)], ([_, [col, row, useJoker]]) => fellTrees({ col: Number.parseInt(col, 10), row: Number.parseInt(row !== null && row !== void 0 ? row : '', 10), useJoker: useJoker === 'Jo', })(state)) .with([GameCommandEnum.WORK_CONTRACT, P.array(P.string)], ([_, [building, paymentGift, withPrior]]) => workContract(building, paymentGift, withPrior === 'WITH_PRIOR')(state)) .with([GameCommandEnum.WITH_PRIOR, []], () => withPrior(state)) .with([GameCommandEnum.WITH_LAYBROTHER, []], () => withLaybrother(state)) .with([GameCommandEnum.BUY_PLOT, [P._, PPlot]], ([_, [y, side]]) => buyPlot({ y: Number.parseInt(y, 10), side: side, })(state)) .with([GameCommandEnum.BUY_DISTRICT, [P._, PDistrict]], ([_, [y, side]]) => buyDistrict({ y: Number.parseInt(y, 10), side: side, })(state)) .with([GameCommandEnum.CONVERT, [P.select('resources')]], ({ resources }) => convert(parseResourceParam(resources))(state)) .with([GameCommandEnum.SETTLE, P.array(P.string)], ([_, [settlement, col, row, resources]]) => settle({ settlement: settlement, col: Number.parseInt(col, 10), row: Number.parseInt(row, 10), resources, })(state)) .with([GameCommandEnum.CONFIG, [PPlayerCount, PCountry, PLength]], ([_, [players, country, length]]) => config({ players: Number.parseInt(players, 10), length: length, country: country, })(state)) .with([GameCommandEnum.START, P.array(P.string)], ([_, params]) => { const seed = Number.parseInt(params[0], 10); if (Number.isNaN(seed)) { return start(state, { seed: undefined, colors: params, }); } return start(state, { seed, colors: params.slice(1), }); }) .otherwise((command) => { throw new Error(`Unable to parse [${command.join(',')}]`); }); }; //# sourceMappingURL=reducer.js.map