add Game.currentState to indicate whether games are won/lost

This commit is contained in:
Thorsten Rausch 2021-06-18 13:03:25 +02:00
parent 60adfc1e49
commit 494109de79
3 changed files with 92 additions and 53 deletions

View File

@ -1,45 +1,58 @@
const Player = require('./Player');
const Hunter = require("./Hunter");
class Game {
static MAX_PLAYERS = 4;
static STATUS = {
SETTING_UP: 0,
ONGOING: 1,
IS_DRAW: 2,
IS_WON: 3
}
constructor() {
this.currentStatus = Game.STATUS.SETTING_UP;
this.players = [];
this.currentPlayerIndex = 0;
this.started = false;
this.winnerIndex = 0;
this.round = 0;
this.hunter = new Hunter();
}
finish_turn() {
let move_to_next_round = false;
// move on to next player; skip dead players
do {
if (this.players.length === 0) break;
this.update_game_status();
if (this.currentStatus !== Game.STATUS.ONGOING) return;
if (!this.players.some(player => player.isAlive === true)) return;
let roundIsOver = false;
do {
this.currentPlayerIndex++;
if (this.currentPlayerIndex >= this.players.length) {
this.currentPlayerIndex = 0;
move_to_next_round = true;
roundIsOver = true;
}
} while (!this.players[this.currentPlayerIndex].isAlive); // skip dead players
this.finish_round();
if (roundIsOver) this.#finish_round();
}
finish_round() {
#finish_round() {
this.round++;
// kill players with hunter
if (this.round >= 5) {
this.hunter.move_by(1);
this.hunter.hunt(this.players);
}
// check if all players are dead
if (!this.players.some(player => player.isAlive === true)) {
// todo: end game (all players are dead)
}
this.update_game_status();
}
add_player(name) {
this.players.push(new Player(name));
let canAddPlayer = this.players.length < Game.MAX_PLAYERS;
if (canAddPlayer) this.players.push(new Player(name));
return canAddPlayer;
}
remove_player(name) {
@ -52,6 +65,7 @@ class Game {
}
current_player_is(name) {
if (this.players[this.currentPlayerIndex] === undefined) return false;
return this.players[this.currentPlayerIndex].name === name;
}
@ -61,7 +75,19 @@ class Game {
move_player(name, amount) {
let index = this.get_player_index(name);
if (index === -1) return;
this.players[index].move_by(amount);
this.update_game_status();
}
update_game_status() {
if (!this.players.some(player => player.isAlive === true)) this.currentStatus = Game.STATUS.IS_DRAW;
let index = this.players.findIndex(player => player.position > 15);
if (index !== -1) {
this.currentStatus = Game.STATUS.IS_WON;
this.winnerIndex = index;
}
}
}

View File

@ -8,9 +8,6 @@ class Player {
move_by(amount) {
this.position += amount;
//todo: move by 1 only on the last 3 fields
if (this.position >= 16) {
// todo: win
}
}
}

View File

@ -9,7 +9,7 @@ const {Server} = require("socket.io");
const io = new Server(server);
let cards = JSON.parse(fs.readFileSync(__dirname + '/../data/fragen_10_06_21_final_new_format.json'));
let gameState = {};
let game = {};
let port = 5000;
server.listen(port, function () {
@ -44,12 +44,12 @@ io.on('connection', socket => {
socket.username = data.username;
socket.room = data.room_name;
if (gameState[socket.room] === undefined) {
gameState[socket.room] = new Game();
if (game[socket.room] === undefined) {
game[socket.room] = new Game();
}
if (gameState[socket.room].players.length < 4 && !gameState[socket.room].started) {
gameState[socket.room].add_player(socket.username);
if (game[socket.room].add_player(socket.username)) {
addedUser = true;
socket.emit('login');
@ -64,7 +64,7 @@ io.on('connection', socket => {
});
socket.on('new message', function (data) {
if (gameState[socket.room] !== undefined && addedUser) {
if (game[socket.room] !== undefined && addedUser) {
socket.broadcast.to(socket.room).emit('new message', {
username: socket.username,
message: data
@ -75,15 +75,15 @@ io.on('connection', socket => {
});
socket.on('disconnect', function () {
if (gameState[socket.room] !== undefined && addedUser) {
if (game[socket.room] !== undefined && addedUser) {
socket.broadcast.to(socket.room).emit('user left', socket.username);
gameState[socket.room].remove_player(socket.username);
game[socket.room].remove_player(socket.username);
// TODO Close card if card is opened and active player left
socket.leave(socket.room);
if (gameState[socket.room].players.length === 0) delete gameState[socket.room];
if (game[socket.room].players.length === 0) delete game[socket.room];
}
generate_log_message(socket.room, socket.username, "LEFT", "");
@ -91,51 +91,67 @@ io.on('connection', socket => {
// Game
socket.on('roll dice', function () {
if (gameState[socket.room] !== undefined && addedUser) {
if (gameState[socket.room].current_player_is(socket.username)) {
gameState[socket.room].started = true;
let sides = 3;
let randomNumber = Math.floor(Math.random() * sides) + 1;
if (game[socket.room] === undefined || !addedUser) return;
io.in(socket.room).emit('dice', randomNumber);
if (game[socket.room].current_player_is(socket.username)) {
game[socket.room].currentStatus = Game.STATUS.ONGOING;
let sides = 3;
let randomNumber = Math.floor(Math.random() * sides) + 1;
generate_log_message(socket.room, socket.username, "DICE", randomNumber);
} else {
io.to(socket.id).emit('error', 'It\'s not your turn');
}
io.in(socket.room).emit('dice', randomNumber);
generate_log_message(socket.room, socket.username, "DICE", randomNumber);
} else {
io.to(socket.id).emit('error', 'It\'s not your turn');
}
});
socket.on('get card', function (difficulty) {
if (gameState[socket.room] !== undefined && addedUser) {
if (gameState[socket.room].current_player_is(socket.username)) {
io.in(socket.room).emit('card', {'username': socket.username, 'card': getRandomCard(difficulty)});
if (game[socket.room] === undefined || !addedUser) return;
if (game[socket.room].currentStatus !== Game.STATUS.ONGOING) return;
generate_log_message(socket.room, socket.username, "CARD", difficulty);
} else {
io.to(socket.id).emit('error', 'It\'s not your turn');
}
if (game[socket.room].current_player_is(socket.username)) {
io.in(socket.room).emit('card', {'username': socket.username, 'card': getRandomCard(difficulty)});
generate_log_message(socket.room, socket.username, "CARD", difficulty);
} else {
io.to(socket.id).emit('error', 'It\'s not your turn');
}
});
socket.on('card finished', function (difficulty, answerIsCorrect) {
if (gameState[socket.room] !== undefined && addedUser) {
if (answerIsCorrect) {
gameState[socket.room].move_player(socket.username, difficulty);
generate_log_message(socket.room, socket.username, "MOVE", difficulty);
}
io.in(socket.room).emit('card destroyed');
gameState[socket.room].finish_turn();
if (game[socket.room] === undefined || !addedUser) return;
if (game[socket.room].currentStatus !== Game.STATUS.ONGOING) return;
let index = gameState[socket.room].get_player_index(socket.username);
let next_player = gameState[socket.room].players[gameState[socket.room].currentPlayerIndex].name;
io.in(socket.room).emit('card destroyed');
if (answerIsCorrect) {
game[socket.room].move_player(socket.username, difficulty);
generate_log_message(socket.room, socket.username, "MOVE", difficulty);
let index = game[socket.room].get_player_index(socket.username);
let next_player = game[socket.room].players[game[socket.room].currentPlayerIndex].name;
io.in(socket.room).emit('player moved', {
"next_player": next_player,
"player": index,
"position": gameState[socket.room].players[index].position
"position": game[socket.room].players[index].position
});
}
game[socket.room].finish_turn();
switch (game[socket.room].currentStatus) {
case Game.STATUS.IS_WON:
//TODO show clients the winner
break;
case Game.STATUS.IS_DRAW:
//TODO show clients that nobody wins
break;
default:
break;
}
});
});