Skip to content

Commit

Permalink
Add player class and test.
Browse files Browse the repository at this point in the history
  • Loading branch information
Florian Lorétan committed Feb 24, 2019
1 parent a639a84 commit 1040208
Show file tree
Hide file tree
Showing 2 changed files with 156 additions and 0 deletions.
89 changes: 89 additions & 0 deletions src/Player.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,89 @@

module.exports = class Player {
constructor({deck, pile, label = ''}) {
this.label = label;
this.hand = [];
this.deck = deck;
this.pile = pile;

for (let i = 0; i < 7; i++) {
this.hand.push(this.deck.draw());
}
}

canPlay() {
for (let card of this.hand) {
if (this.pile.canPlay({card})) {
return true;
}
}

return false;
}

play() {
// Very simple approach, play the first playable card.
for (let card of this.hand) {
if (this.pile.canPlay({card})) {
const playedCard = this.hand.splice(this.hand.indexOf(card), 1).pop();
let color;

if (playedCard.allowsPick()) {

const coloredCard = this.hand.find(c => typeof c.color !== 'undefined')
if (coloredCard) {
// Pick the color existing card on hand.
color = coloredCard.color;
}
else {
// Pick a random color.
color = Math.floor(Math.random() * 4);
}
}

this.pile.play({card: playedCard, color, label: this.label})

break;
}
}
}

draw() {
if (this.deck.cards.length === 0) {
this.deck.cards.push(...this.pile.cards.splice(0, this.pile.cards.length - 1));
this.deck.shuffle();
}

const newCard = this.deck.draw();
this.hand.push(newCard);
}

doTurn() {
// @TODO: handle adding up the penalties.
if (this.pile.currentSymbol === '+2') {
this.draw();
this.draw();
}
if (this.pile.currentSymbol === 'pickplusfour') {
this.draw();
this.draw();
this.draw();
this.draw();
}

if (this.canPlay()) {
this.play();
}
else {
console.log(this.label, 'cannot play (', this.hand.map(card => card.toString()).join('|'), '), drawing');
this.draw();
if (this.canPlay()) {
this.play();
}
}
}

hasWon() {
return this.hand.length === 0;
}
};
67 changes: 67 additions & 0 deletions test/playerTest.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@

const assert = require('assert');
const Player = require('../src/Player');
const Deck = require('../src/Deck');
const Pile = require('../src/Pile');
const Card = require('../src/Card');


describe('player test', () => {
it('player is initialized', () => {
const deck = new Deck();
const pile = new Pile({card: new Card({symbol: 0, color: 0})});
const player = new Player({deck, pile, label: 'Player 1'});

assert.strictEqual(typeof player, 'object');
assert.strictEqual(player.hand.length, 7);
});

it('player can play', () => {
const deck = new Deck();
const pile = new Pile({card: new Card({symbol: 0, color: 0})});
const player = new Player({deck, pile, label: 'Player 1'});

// Add a card that the player can play.
player.hand.length = 0;
player.hand.push(new Card({symbol: 0, color: 1}));

assert.strictEqual(player.canPlay(), true);

player.doTurn();
assert.strictEqual(player.hand.length, 0);
});

it('player cannot play and draws a card', () => {
const deck = new Deck();
const pile = new Pile({card: new Card({symbol: 0, color: 0})});
const player = new Player({deck, pile, label: 'Player 1'});

// Set the card in the deck.
deck.cards.length = 0;
deck.cards.push(new Card({symbol: 4, color: 1}));

// Add a card that the player cannot play.
player.hand.length = 0;
player.hand.push(new Card({symbol: 1, color: 1}));
player.hand.push(new Card({symbol: 2, color: 1}));
player.hand.push(new Card({symbol: 3, color: 1}));

assert.strictEqual(player.canPlay(), false);
player.doTurn();
assert.strictEqual(player.hand.length, 4);
});

it('detects winning', () => {
const deck = new Deck();
const pile = new Pile({card: new Card({symbol: 0, color: 0})});
const player = new Player({deck, pile, label: 'Player 1'});

// Add a card that the player can play.
player.hand.length = 0;
player.hand.push(new Card({symbol: 0, color: 1}));

assert.strictEqual(player.hasWon(), false);
player.doTurn();
assert.strictEqual(player.hasWon(), true);
});
});

0 comments on commit 1040208

Please sign in to comment.