diff --git a/create_game.html b/create_game.html
index 7f88328..63a3fc5 100644
--- a/create_game.html
+++ b/create_game.html
@@ -27,6 +27,7 @@
diff --git a/package-lock.json b/package-lock.json
index f345d98..5a6480e 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -126,6 +126,14 @@
"resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz",
"integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw="
},
+ "cron": {
+ "version": "1.7.1",
+ "resolved": "https://registry.npmjs.org/cron/-/cron-1.7.1.tgz",
+ "integrity": "sha512-gmMB/pJcqUVs/NklR1sCGlNYM7TizEw+1gebz20BMc/8bTm/r7QUp3ZPSPlG8Z5XRlvb7qhjEjq/+bdIfUCL2A==",
+ "requires": {
+ "moment-timezone": "^0.5.x"
+ }
+ },
"debug": {
"version": "2.6.9",
"resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz",
@@ -379,6 +387,19 @@
"mime-db": "1.40.0"
}
},
+ "moment": {
+ "version": "2.24.0",
+ "resolved": "https://registry.npmjs.org/moment/-/moment-2.24.0.tgz",
+ "integrity": "sha512-bV7f+6l2QigeBBZSM/6yTNq4P2fNpSWj/0e7jQcy87A8e7o2nAfP/34/2ky5Vw4B9S446EtIhodAzkFCcR4dQg=="
+ },
+ "moment-timezone": {
+ "version": "0.5.26",
+ "resolved": "https://registry.npmjs.org/moment-timezone/-/moment-timezone-0.5.26.tgz",
+ "integrity": "sha512-sFP4cgEKTCymBBKgoxZjYzlSovC20Y6J7y3nanDc5RoBIXKlZhoYwBoZGe3flwU6A372AcRwScH8KiwV6zjy1g==",
+ "requires": {
+ "moment": ">= 2.9.0"
+ }
+ },
"ms": {
"version": "2.0.0",
"resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz",
diff --git a/package.json b/package.json
index 898f2ed..e0a0652 100644
--- a/package.json
+++ b/package.json
@@ -9,6 +9,7 @@
"author": "",
"license": "ISC",
"dependencies": {
+ "cron": "^1.7.1",
"express": "^4.17.1",
"socket.io": "^2.2.0"
}
diff --git a/server.js b/server.js
index a7e8665..c85357d 100644
--- a/server.js
+++ b/server.js
@@ -6,8 +6,18 @@ const app = express();
const server = http.Server(app);
const io = socketIO(server);
+// cron job for periodically clearing finished games
+const CronJob = require('cron').CronJob;
+
var activeGames = {};
+const job = new CronJob('* * 2 * * *', function() {
+ activeGames = activeGames.filter((game) => game.state !== "ended");
+ console.log("Games pruned at: " + (new Date()).toDateString());
+});
+console.log("cron job created");
+job.start();
+
app.set('port', 5000);
app.use('/static', express.static(__dirname + '/static')); // Routing
app.use('/assets', express.static(__dirname + '/assets')); // Routing
@@ -32,16 +42,6 @@ server.listen(process.env.PORT || 5000, function() {
console.log('Starting server on port 5000');
});
-function didVillageWin(game) {
- let liveCount = 0;
- for (const player of game.players) {
- if (player.card.role === "Werewolf" && !player.dead) {
- return false;
- }
- }
- return true;
-}
-
function teamWon(game) {
let wolvesAlive = 0;
let villagersAlive = 0;
@@ -124,6 +124,12 @@ io.on('connection', function(socket) {
game.endTime = newDate.toJSON();
io.to(code).emit('state', game);
});
+ socket.on("timerExpired", function(code) {
+ let game = activeGames[Object.keys(activeGames).find((key) => key === code)];
+ game.winningTeam = "wolf";
+ game.state = "ended";
+ io.to(code).emit('state', game);
+ });
socket.on('killPlayer', function(id, code) {
let game = activeGames[Object.keys(activeGames).find((key) => key === code)];
let player = game.players.find((player) => player.id === id);
diff --git a/static/game.js b/static/game.js
index 41988cf..8985cbb 100644
--- a/static/game.js
+++ b/static/game.js
@@ -187,8 +187,7 @@ function renderClock() {
clearInterval(clock);
}
if (delta <= 0) {
- clearInterval(clock);
- endGame(true);
+ endGameDueToTimeExpired();
} else {
let minutes = Math.floor((delta % (1000 * 60 * 60)) / (1000 * 60));
let seconds = Math.floor((delta % (1000 * 60)) / 1000);
@@ -198,9 +197,10 @@ function renderClock() {
}, 1000);
}
-function endGame(timeExpired) {
- if (timeExpired) {
- }
+function endGameDueToTimeExpired() {
+ clearInterval(clock);
+ console.log("expired!");
+ socket.emit("timerExpired", currentGame.accessCode);
}
function killPlayer() {
diff --git a/static/setup.js b/static/setup.js
index dff44c5..8d53297 100644
--- a/static/setup.js
+++ b/static/setup.js
@@ -30,7 +30,7 @@ class Game {
var fullDeck = [];
var gameSize = 0;
-var time = null;
+var atLeastOnePlayer = false;
// register event listeners on buttons
@@ -66,6 +66,12 @@ function updateGameSize() {
gameSize += card.quantity;
}
document.getElementById("game-size").innerText = gameSize + " Players";
+ if (gameSize > 0) {
+ atLeastOnePlayer = true;
+ } else {
+ atLeastOnePlayer = false;
+ }
+ return gameSize;
}
function resetCardQuantities() {
@@ -91,7 +97,7 @@ function buildDeckFromQuantities() {
}
function createGame() {
- if (document.getElementById("name").value.length > 0) {
+ if (document.getElementById("name").value.length > 0 && atLeastOnePlayer) {
// generate 6 digit access code
let code = "";
let charPool = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
@@ -120,6 +126,13 @@ function createGame() {
window.location.replace('/' + code);
});
} else {
+ if (!atLeastOnePlayer) {
+ document.getElementById("game-size").classList.add("error");
+ document.getElementById("size-error").innerText = "Add at least one card";
+ } else {
+ document.getElementById("game-size").classList.remove("error");
+ document.getElementById("size-error").innerText = "";
+ }
document.getElementById("name").classList.add("error");
document.getElementById("name-error").innerText = "Name is required.";
}
diff --git a/static/styles.css b/static/styles.css
index 9a2b497..cb28171 100644
--- a/static/styles.css
+++ b/static/styles.css
@@ -127,7 +127,7 @@ button {
background-color: rgba(189, 42, 42, 0.1) !important;
}
-#join-error, #name-error {
+#join-error, #name-error, #size-error {
color: #bd2a2a;
font-size: 0.9em;
height: 2em;
@@ -256,6 +256,12 @@ button {
margin: 3em 1em;
}
+#game-size {
+ border-radius: 5px;
+ padding: 0.3em 0.5em;
+ margin-right: 0.5em !important;
+}
+
#create-game-container, #lobby-container, #join-game-container, #game-container, #launch, #message-box {
animation: fadein 0.8s ease-in;
}
@@ -470,7 +476,7 @@ label {
.killed-btn {
border-radius: 5px;
width: 13em;
- font-size: 1.2em;
+ font-size: 1em;
margin: 0
}