diff --git a/cardGen.js b/cardGen.js
index 9adaf11..80ff642 100644
--- a/cardGen.js
+++ b/cardGen.js
@@ -4,22 +4,12 @@ const database = require('./database');
const util = require('util')
-// cardClass, cardColourRequirement
-// may want to be seperate too (as well as in cardItem), so that
-// during match they can be altered by effects while keeping the OG card
-// for inspecting (and compare against new stats,reqs,etc.)
-// same with attack, cost, etc. things that will can be visually shown as
-// changed in game
-
-// Just grabbing everything from DB for now, as it's quite small at current
-// then will rejig when needed.
-// Should all cards, effects, classes etc. be loaded in on server start
-// then just load decks and decklists when needed?
+// Get the decks requested
function getDecks(deckIds = false){
// Await promise, once it's done get the data, if errors send err
const dPromise = new Promise((resolve, reject) => {
- database.dbGetDecks().then(data => {
+ database.dbGetDecks(deckIds).then(data => {
let decks = [];
@@ -48,10 +38,10 @@ function getDecks(deckIds = false){
return dPromise;
}
//getDecks();
-function getDeckList(){
+function getDeckList(deckIds = false){
const dPromise = new Promise((resolve, reject) => {
- database.dbGetDeckList().then(data => {
+ database.dbGetDeckList(deckIds).then(data => {
let deckList = [];
@@ -70,11 +60,10 @@ function getDeckList(){
});
return dPromise;
}
-//getDeckList();
-function getCards(){
+function getCards(cardIds = false){
const dPromise = new Promise((resolve, reject) => {
- database.dbGetCards().then(data => {
+ database.dbGetCards(cardIds).then(data => {
let cards = [];
@@ -97,10 +86,9 @@ function getCards(){
});
return dPromise;
}
-//getCards();
-function getCardClasses(){
+function getCardClasses(cardIds = false){
const dPromise = new Promise((resolve, reject) => {
- database.dbGetCardClasses().then(data => {
+ database.dbGetCardClasses(cardIds).then(data => {
let cardClasses = [];
@@ -118,10 +106,9 @@ function getCardClasses(){
});
return dPromise;
}
-//getCardClasses();
-function getCardColourRequirement(){
+function getCardColourRequirement(cardIds = false){
const dPromise = new Promise((resolve, reject) => {
- database.dbGetCardColourRequirement().then(data => {
+ database.dbGetCardColourRequirement(cardIds).then(data => {
let colourRequirements = [];
@@ -141,9 +128,9 @@ function getCardColourRequirement(){
});
return dPromise;
}
-function getCardManaColour(){
+function getCardManaColour(cardIds = false){
const cPromise = new Promise((resolve, reject) => {
- database.dbGetCardManaColour().then(data => {
+ database.dbGetCardManaColour(cardIds).then(data => {
let manaColours = [];
@@ -274,25 +261,9 @@ function getCardPassive(){
return cPromise;
}
-//getCardColourRequirement();
-// Then effects which will have effects with parent triggers, and unit type checks
-// colour checks, all sorts. So will be more difficult. Basic (flight, etc)
-// shouldn't be too bad
-// something like effect_basic, card_effect, effect_trigger, effect_requirement, effect_option
-// effect_stage, effect_advanced, with advanced being an id with x triggers, triggers have
-// x req, advanced as with x options, x stages to be able to fine-tune fancy stuff
-// combining all other effects, units, cards, colours, etc. Will be a lot of though,
-// but better than hard coding anything more than basic effects and effect check logic
-// TODO: effect (as above)
-
-// request a deck in the format CURRENTLY used in the game
-// decks will likely be changed around
// https://www.geeksforgeeks.org/how-to-wait-for-multiple-promises-in-javascript/
// https://medium.com/@nikolozz/using-socket-io-with-async-await-13fa8c2dc9d9
-// using last example
-// TODO: When this is functionally working, need to split up into other func/modules
-// such as: playerMod, cardMod, deckMod, miscMod ?
function requestDeck(itemData = null){
return new Promise((resolve, reject) => {
(async () => {
@@ -300,53 +271,73 @@ function requestDeck(itemData = null){
// Get the deck(s) requested.
// Not 100% on how to do two differening atm
// Besides all of playerId, and all of deckId. But 1,2/2,3 for instance
+
+ // Build array of decks to get
+ let deckIds = [];
+ for(let i = 0; i < itemData.players.length; i++){
+ let deckStuff = itemData.players[i][1].deck;
+ deckIds.push([deckStuff.playerId, deckStuff.deckId]);
+ // So should be array of [playerId, deckId] which is primary key in DB
+ }
+
+ // Get said decks, and their deckLists
const [decks, deckList] =
await Promise.all([
- getDecks(),
- getDeckList()
+ getDecks(deckIds),
+ getDeckList(deckIds)
]);
- //console.log(decks);
- //console.log(deckList);
+ /*
+ console.log('--- decks ---');
+ console.log(decks);
+ console.log('= deckLists =')
+ console.log(deckList);
+ console.log('------');
+ */
+
// Now loop the deckList for the cardIds
let deckCardIds = [];
deckList.forEach((deckItem) => {
deckCardIds.push(deckItem.cardId);
-
});
- //console.log(deckCardIds);
// Next, get the cards in the deck by their ID
// TODO: https://stackoverflow.com/a/65510676
- // Change SQL to accept for just the cards passed
// Get each cards data, colourReqs, and classes
const [cards, cardClasses, cardColourRequirements, cardManaColours, cardPassives] =
await Promise.all([
- getCards(),
- getCardClasses(),
- getCardColourRequirement(),
- getCardManaColour(),
- getCardPassive(),
+ getCards(deckCardIds),
+ getCardClasses(deckCardIds),
+ getCardColourRequirement(deckCardIds),
+ getCardManaColour(deckCardIds),
+ getCardPassive(deckCardIds),
]);
- // ^^^^ Classes async? Can pass the cardsIds, then loop classes, if the class cardId
- // matches the cardId in cards[] then push the class to cards[x].classes
+ // Return all effect data from DB
+ const [effects] =
+ await Promise.all([
+ database.dbGetEffect(deckCardIds), // Get effects
+ ]);
- // TODO: Build the card so far async for it's done alongside getting effects?
- // Then when both done add the effects to the existing cardObjects? Yep good idea me
- //console.log(cards);
- //console.info(cardClasses);
- //console.log(cardColourRequirements);
+ // Loop the effects for their effectIds to then get the steps/triggers from DB
+ let effectIds = [];
+ await effects.forEach((effect) => {
+ effectIds.push(effect.effectId);
+ });
- // Return all effect data from DB
- const [effects, effectSteps, effectTriggers] =
+ // Then pass the effectIds to get their steps/triggers
+ const [effectSteps, effectTriggers] =
await Promise.all([
- database.dbGetEffect(),
- database.dbGetEffectStep(),
- database.dbGetEffectTrigger(),
+ database.dbGetEffectStep(effectIds),
+ database.dbGetEffectTrigger(effectIds),
]);
+ /*
+ console.log('--- Effects ---');
+ console.log(effects);
+ */
+
// Build Effects
const [cardEffects] =
await Promise.all([
@@ -460,6 +451,8 @@ function requestDeck(itemData = null){
// For each new card, loop to the cardCount (how many cards in deck)
// and add to the deck
+ // TODO: Associate player to deck differently (both could be using same deck
+ // via some kind of 'try a deck' or 'use friends deck' option)
for(let i = 0; i < deckListItem.cardCount; i++){
item.push(itemCount); // Add new item to add stuff for
// ^ not using item.length incase anything in future gets deleted
diff --git a/components.js b/components.js
new file mode 100644
index 0000000..c1617b7
--- /dev/null
+++ b/components.js
@@ -0,0 +1,99 @@
+// A seperate list for components, so they're easy to recall
+
+// Done as object, so it can be added to different rooms with components = NEW component?
+const component = {
+
+ // Entity Stuff
+ //item : [],
+ //itemCount : 0,
+
+ roomId : null,
+ turn : 0,
+ playerTurn : 0,
+
+ // Card Stuff
+ cardData : {},
+ cardFace : {},
+ cardStatus : {
+ tapped : {},
+ attacking : {},
+ inspected : {},
+ },
+ cardAttack : {},
+ cardColours : {}, // Replace with colour
+ colour : {
+ white : {}, // entityId, amountOfColour
+ blue : {},
+ red : {},
+ },
+ cardManaColour : {},
+ cardEffect : {}, // TODO: Split this into effect, trigger, step, targets.
+ cardCost : {},
+ cardSprite : {}, // id, position in spritesheet [0,4] e.g.
+ //cardPlayer = {},
+
+ // Deck Stuff?
+ deckIn : {},
+ deckData : {},
+
+ // UI (so users know what's been targetted)
+ selected : {},
+ selectable : {},
+
+ // Effect (break it up?)
+ effect : {},
+ effectTrigger : {},
+ // etc, etc.
+
+ // Board Elements
+ // loop component.shield for shield items
+ boardElement : {},
+ // Replace with following
+ realDeck : {},
+ inDeck : {},
+ hand : {},
+ board : {},
+ shield : {},
+ mana : {},
+ grave : {},
+ void : {},
+
+ //
+ listPosition : {},
+ // position (clientside)
+ // size (clientside)
+
+ // Passives
+ // component.passive.flight ?
+ passive : {
+ flight : {},
+ reach : {},
+ taunt : {},
+ },
+
+ type : {
+ unit : {},
+ spell : {},
+ token : {},
+ },
+
+ classes : {
+ orc : {},
+ human : {},
+ spirit : {},
+ },
+
+
+};
+
+// For front-end
+// position, size
+
+// These should be used as such (Not 100% as yet)
+// For onBoard()... for player()... for passive.flight()...
+// Check the board, items belonging to playerX, for flight passive?
+
+module.exports = {
+ component
+}
+
diff --git a/database.js b/database.js
index 8f89c93..ece68f0 100644
--- a/database.js
+++ b/database.js
@@ -17,7 +17,7 @@ function disconnect(){
}
// My DB stuffs
-function dbGetDecks(){
+function dbGetDecks(deckIds = false){
const dPromise = new Promise((resolve, reject) => {
let cards = [];
let sql = `SELECT
@@ -25,8 +25,16 @@ function dbGetDecks(){
,playerId
,deckName
FROM deck
- LIMIT 10
- `; // TODO: Remove limit when happy/this accepts params
+ `;
+
+ // TODO: Jank, need to unjank it
+ if(deckIds){
+ for(let i = 0; i < deckIds.length; i++){
+ if(i == 0){ sql += ' WHERE '; }
+ else{ sql += ' OR '; }
+ sql += '(deckId = '+deckIds[i][1]+' AND playerId = '+deckIds[i][0]+')';
+ }
+ }
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
@@ -35,7 +43,7 @@ function dbGetDecks(){
});
return dPromise;
}
-function dbGetDeckList(){
+function dbGetDeckList(deckIds = false){
const dPromise = new Promise((resolve, reject) => {
let cards = [];
let sql = `SELECT
@@ -46,6 +54,15 @@ function dbGetDeckList(){
FROM deck_cards
`;
+ // TODO: Jank, need to unjank it
+ if(deckIds){
+ for(let i = 0; i < deckIds.length; i++){
+ if(i == 0){ sql += ' WHERE '; }
+ else{ sql += ' OR '; }
+ sql += '(deckId = '+deckIds[i][1]+' AND playerId = '+deckIds[i][0]+')';
+ }
+ }
+
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
resolve(result);
@@ -53,7 +70,7 @@ function dbGetDeckList(){
});
return dPromise;
}
-function dbGetCards(){
+function dbGetCards(cardIds = false){
// Start with basic stuff in card table
const dPromise = new Promise((resolve, reject) => {
let sql = `SELECT
@@ -65,6 +82,7 @@ function dbGetCards(){
,cardRarity
FROM card
`;
+ if(cardIds){ sql += 'WHERE card.id IN ('+cardIds+')'; }
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
@@ -73,7 +91,7 @@ function dbGetCards(){
});
return dPromise;
}
-function dbGetCardClasses(){
+function dbGetCardClasses(cardIds = false){
// Get the classes assoc. on each card
const dPromise = new Promise((resolve, reject) => {
let sql = `SELECT
@@ -81,6 +99,7 @@ function dbGetCardClasses(){
,classId
FROM card_class
`;
+ if(cardIds){ sql += 'WHERE cardId IN ('+cardIds+')'; }
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
@@ -89,7 +108,7 @@ function dbGetCardClasses(){
});
return dPromise;
}
-function dbGetCardColourRequirement(){
+function dbGetCardColourRequirement(cardIds = false){
// Get the classes assoc. on each card
const dPromise = new Promise((resolve, reject) => {
let sql = `SELECT
@@ -98,6 +117,7 @@ function dbGetCardColourRequirement(){
,cost
FROM card_colour_requirement
`;
+ if(cardIds){ sql += 'WHERE cardId IN ('+cardIds+')'; }
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
@@ -107,7 +127,7 @@ function dbGetCardColourRequirement(){
return dPromise;
}
-function dbGetCardManaColour(){
+function dbGetCardManaColour(cardIds = false){
// Get the classes assoc. on each card
const cPromise = new Promise((resolve, reject) => {
let sql = `SELECT
@@ -115,6 +135,7 @@ function dbGetCardManaColour(){
,colourId
FROM card_mana_colour
`;
+ if(cardIds){ sql += 'WHERE cardId IN ('+cardIds+')'; }
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
@@ -125,7 +146,7 @@ function dbGetCardManaColour(){
}
// Effect stuff
-function dbGetEffect(){
+function dbGetEffect(cardIds = false){
const ePromise = new Promise((resolve, reject) => {
let sql = `SELECT
cardId
@@ -136,6 +157,7 @@ function dbGetEffect(){
INNER JOIN effect
ON effect.id = card_effect.effectId
`;
+ if(cardIds){ sql += 'WHERE cardId IN ('+cardIds+')'; }
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
@@ -144,7 +166,7 @@ function dbGetEffect(){
});
return ePromise;
}
-function dbGetEffectStep(){
+function dbGetEffectStep(effectIds = false){
const ePromise = new Promise((resolve, reject) => {
let sql = `SELECT
effectId,
@@ -163,6 +185,7 @@ function dbGetEffectStep(){
effect_step_target
ON effect_step_target.effectStep = effect_step.id
`;
+ if(effectIds){ sql += 'WHERE effectId IN ('+effectIds+')'; }
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
@@ -172,7 +195,7 @@ function dbGetEffectStep(){
return ePromise;
}
// Effect Trigger stuff
-function dbGetEffectTrigger(){
+function dbGetEffectTrigger(effectIds = false){
const ePromise = new Promise((resolve, reject) => {
let sql = `SELECT
effect_trigger.id AS triggerId,
@@ -196,6 +219,7 @@ function dbGetEffectTrigger(){
effect_trigger_target
ON effect_trigger_target.effectTriggerId = effect_trigger.triggerTypeId
`;
+ if(effectIds){ sql += 'WHERE effectId IN ('+effectIds+')'; }
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
@@ -206,13 +230,14 @@ function dbGetEffectTrigger(){
}
// Passive stuff
-function dbGetPassive(){
+function dbGetPassive(cardIds = false){
const pPromise = new Promise((resolve, reject) => {
let sql = `SELECT
cardId
,passiveId
FROM card_passive
`;
+ if(cardIds){ sql += 'WHERE card.id IN ('+cardIds+')'; }
con.query(sql, function (err, result, fields) {
if (err) { throw err; reject(new Error(err)); }
diff --git a/gameMod.js b/gameMod.js
new file mode 100644
index 0000000..6d94736
--- /dev/null
+++ b/gameMod.js
@@ -0,0 +1,25 @@
+// For anything related to the actual game itself (kinda)
+// this will be split into different bits, but should be what manages a rooms
+// game states, and alladat
+// Basically here to prevent circular dependencies (where I can)
+
+
+// PlayerId is using array 0,1,2 for now, not the actual id
+// actual Id would be better, but the player should be passed correctly
+// from the client. They can edit data, but server-side validation SHOULD prevent
+// in the future
+function passTurn(roomId, playerId){
+
+ // Check playerId (not correct atm) before doing the stuff, to verify the user
+ // IS the user, and in the room
+
+ // Test alert so that different data/emits can be sent per-player
+ global.socketAlert(roomData[roomId].playerData[0].socketId, 'Pass', 'alert');
+
+}
+
+
+module.exports = {
+ passTurn
+};
+
diff --git a/public/board.js b/public/board.js
index cd51410..5286186 100644
--- a/public/board.js
+++ b/public/board.js
@@ -42,6 +42,7 @@ let cardColours = {};
let cardManaColour = {};
let cardEffect = {};
let inEvent = null;
+let roomId = null;
// To disable drawing each time something changes
let drawEachEvent = true; // For disabling draw each time and only occuring where I want to test
@@ -1298,6 +1299,7 @@ function loadBoard(data) {
cardColours = data.cardColours;
cardManaColour = data.cardManaColour;
cardEffect = data.cardEffect;
+ roomId = data.roomId;
// Passives
flight = data.flight;
diff --git a/public/index.html b/public/index.html
index 83a167a..c90e939 100644
--- a/public/index.html
+++ b/public/index.html
@@ -17,6 +17,10 @@
+
+
+
+
diff --git a/public/main.js b/public/main.js
index dbb0606..7ebcf74 100644
--- a/public/main.js
+++ b/public/main.js
@@ -182,3 +182,19 @@ socket.on('responseStartGame', function (data) {
loadBoard(data.message);
});
+// ALERTS
+socket.on('alert', function (data) {
+ console.log('<< alert');
+ alert(data.message);
+});
+
+// GAME SERVER STUFF
+// PASS TURN
+function passTurn(){
+ // TODO: Use itemData.player/itemData.room or whatnot here
+ console.log(roomId);
+ let playerId = prompt('PlayerId 0/1', 0); // TODO: very temp, will be playerId/arrayId
+ console.log('+ passTurn');
+ socket.emit('passTurn', roomId, playerId);
+}
+
diff --git a/roomMod.js b/roomMod.js
index 8223345..be7b19f 100644
--- a/roomMod.js
+++ b/roomMod.js
@@ -1,41 +1,34 @@
// Build a room, fill will players, etc.
const cardGen = require('./cardGen');
-
+const components = require('./components');
// Room should, setPlayers, add them to correct team (TODO), build their decks, and first shuffle
function startItemCount(){
+
let item = [];
let itemCount = 0;
returns = {'item': item, 'itemCount': itemCount};
return(returns);
}
-function setPlayers(playerCount = 2, itemData){
- // Add new item attribute for 'players'
- // TODO: Maybe check if exists, and add to in that case (for replacing people?)
- // Doubt that would ever make it into the game, but could still be worth
+
+function setPlayers(playerData, itemData){
+
itemData.player = {}; //let player = {}; // Player item belongs to
itemData.players = []; // List of the players (an associated playerItem?)
- //itemData.
-
- // Can be done with just referring to itemData[x], but less readable
- // Will likely redefine vars each new function. For now will keep this as-is
let playerNo = 0 + itemData['itemCount']; // Start loop from current itemCount
- playerCount = playerCount + itemData['itemCount']; // End at playerCount diff from itemCount
+ playerCount = playerData.length + itemData['itemCount']; // End at playerCount diff from itemCount
+ let i = 0;
for(playerNo; playerNo < playerCount; playerNo++){
- // REMOVED PLAYERS AS ITEM, BECAUSE THEY WERE BORKING
- // TODO: Add back at some point, or don't bother
- //itemData['item'].push(playerNo);
- //itemData['player'][itemData['itemCount']] = playerNo; // The player belongs to itself
- //itemData['itemCount']++;
- itemData['players'].push(playerNo); // Add player no to array so can be looped
+
+ itemData['players'].push([playerNo, playerData[i]]); // Add player no to array so can be looped
+ i++;
+
}
- // Return related item and item attributes
- //returns = {'item': item, 'itemCount': itemCount, 'player': player};
+
return itemData;
- //return([item, itemCount, player]);
}
// For future, when 2v2s, and 5v1 Raids, etc.
@@ -43,26 +36,72 @@ function setTeams(){
}
-function roomGeneration(playerCount, teamCount = null, playerTeams = null){
+function roomGeneration(roomId){
return new Promise((resolve, reject) => {
(async () => {
+
+ // Player's sockets
+ console.log('--- Room for generation ---');
+ console.log(io.sockets.adapter.rooms.get(roomId));
+
let itemData = startItemCount();
- // Create 2 players for the room
- itemData = setPlayers(2, itemData);
+ // Player data with Sockets
+ let playerData = [];
+ let playerOrder = {}; // Need a better name
+ let i = 1;
+ let clients = global.io.sockets.adapter.rooms.get(roomId);
+ for (const clientId of clients) {
+ const clientSocket = global.io.sockets.sockets.get(clientId);
- // TODO: Get their selected decks (will need to pass somewhere)
+ // Which order the player is? Just using the array
+ playerOrder[clientSocket.playerId] = playerData.length;
+
+ playerData.push({
+ 'playerDataId': playerData.length
+ ,'playerId': clientSocket.playerId
+ ,'deck':{'playerId':i,'deckId':1}
+ ,'socketId': clientSocket.id // TODO: ONLY FOR SERVERSIDE!!!
+ });
+
+ i++;
+
+ }
+
+
+ // Add players for the room (seperate to playerData, currently what's used)
+ // ??
+ itemData = setPlayers(playerData, itemData);
+
+ // TODO: Get their selected decks
+
+ // Add all the empty components to the room itemData
+ itemData.component = components.component;
// Generate the decks, and card within the deck cardLists
[itemData] = await Promise.all([ cardGen.requestDeck(itemData) ]);
- //console.log('deckData');
- //console.log(deckData);
+ // Some room stuff, likely change this
+ itemData.roomId = roomId;
+ itemData.turn = 0; // The turn count of the match
+ itemData.playersTurn = 0; // This means it's playerData[0] turn
+
+ // Room has just been created, so add the itemData and playerData to the room
+ // on server-side so it's easily accessible
+ roomData[roomId].itemData = itemData;
+ roomData[roomId].playerData = playerData;
+ roomData[roomId].playerOrder = playerOrder;
+
+ // Return the all the itemData to the client(s)
+ // TODO: This will need to give different data for each, or at least
+ // to differ the boardside
return resolve(itemData);
})()
});
}
+// TODO: disconnect, reconnect, resume
+
module.exports = {
startItemCount
,setPlayers
diff --git a/rooms.js b/rooms.js
new file mode 100644
index 0000000..7f3bfa5
--- /dev/null
+++ b/rooms.js
@@ -0,0 +1,229 @@
+const roomMod = require('./roomMod');
+
+// Variables for server overall
+let numRooms = 0;
+const maxRooms = 3;
+const maxPlayersPerRoom = 2;
+const maxSpectatorsPerRoom = 0;
+
+function requestRooms(socket, filter){
+ console.log('+ requestRooms recieved');
+ console.log('- filter: '+filter);
+
+ let response = getRooms(filter, dump = true);
+ global.io.to(socket.id).emit('returnRooms', response);
+
+ console.log('');
+}
+
+function getRooms(filter = 'all', dump = false){
+ console.log('+ getRooms');
+ let response = {
+ random: 'randomStuff',
+ roomData: global.roomData,
+ };
+
+ if(dump){
+ console.log(response);
+ console.log('');
+ }
+
+ return response;
+}
+
+function requestCreateRoom(socket, playerName){
+ console.log('+ createRoom recieved');
+ console.log('- requested by: '+playerName);
+
+ response = createRoom(roomId = false, dump = true);
+ global.io.to(socket.id).emit('returnCreateRoom', response);
+
+ if(response.success){
+ let response = getRooms(filter = 'all', dump = true);
+ global.io.to(socket.id).emit('returnRooms', response);
+ }
+
+ console.log('');
+}
+
+function createRoom(roomId = false, dump = true){
+ let roomName = false;
+ if(roomId == false){
+ roomId = numRooms + 1;
+ }
+ console.log(roomId);
+
+ let response = {
+ success: false,
+ message: 'No idea bossman'
+ };
+
+ // Max room limit reached
+ console.log(numRooms);
+ console.log(maxRooms);
+ if(numRooms >= maxRooms){
+ console.log('- Room limit reached');
+
+ response = {
+ success: false,
+ message: 'No space '+numRooms+' out of '+maxRooms+' created.'
+ };
+
+ // Create room
+ }else{
+ console.log('- Creating room')
+ let room = {};
+ room['id'] = roomId;
+ room['name'] = 'Room:'+room['id'];
+ roomName = room['name'];
+ room['password'] = '';
+ room['timeout'] = {};
+ room['timeout']['s'] = 10;
+ room['people'] = 0;
+ room['playerIds'] = {};
+
+ global.roomData[roomId] = room;
+ numRooms = numRooms + 1;
+
+ response = {
+ success: true,
+ message: 'Room Created: '+roomName,
+ };
+ }
+
+ if(dump){
+ console.log(response);
+ console.log('');
+ }
+ return response;
+}
+
+function requestJoinRoom(socket, playerName, roomId){
+
+ console.log('+ requestJoinRoom recieved');
+
+ let room = global.roomData[roomId];
+
+ // https://stackoverflow.com/a/18096649
+ socket.playerId = playerName;
+
+ if(room === undefined){
+ console.log('>> Room does not exist');
+ return 'error';
+ }
+
+ let roomName = 'Room_' + roomId;
+ let people = room['people'];
+
+ if(isUserInRoom(playerName, roomId)){
+ console.log('>> Already in room');
+ return 'already in room';
+ }
+
+ if (people < maxPlayersPerRoom) {
+
+ // Update people in room count
+ people = room['people'] += 1;
+
+ // Add playerId to room (playerName for now while Ids don't exist TODO)
+ room['playerIds'][playerName] = playerName;
+
+ // https://socket.io/docs/v4/rooms/
+ // https://stackoverflow.com/a/25028953
+ socket.join(roomId);
+
+ console.log('>> User ' + playerName +
+ ' connected on ' + roomName + ' (' + (people) + '/' + maxPlayersPerRoom + ')');
+
+ // Joined room (emit to the player that just joined)
+ global.io.to(socket.id).emit('responseRoom', response);
+
+ if (people >= maxPlayersPerRoom) {
+ console.log('- starting game');
+ // startGame for room
+ startGame(roomId);
+ }
+
+ }
+
+}
+
+// Will need to be different to playerName in future (in case dupes)
+// would use playerId TODO
+function isUserInRoom(playerName, roomId){
+ if(playerName in global.roomData[roomId]['playerIds']){
+ return true;
+ }
+ return false;
+}
+
+async function startGame(roomId){
+
+ console.log('>> Room: ' + roomId + ': Requesting game...');
+ let people = global.roomData[roomId].players;
+ /*
+ try {
+ //people = io.sockets.adapter.rooms.get(roomId).size;
+ } catch (e) {
+ console.log('>> Room: ' + roomId + ': No people here...');
+ return;
+ }
+ */
+
+ // For now, if there's 2 people only. Will need changing for
+ // 3v1, 5v1, 2v2, etc...
+
+ let response = {success: false, message: 'Failed requestStartGame() server.js'};
+ if(people < maxPlayersPerRoom){
+ console.log('Too few people');
+ }
+
+ console.log('>> Room: ' + roomId + ': Starting');
+
+
+ // https://stackoverflow.com/a/25028953
+ //console.log(util.inspect(io.sockets.adapter.rooms.get(roomId), true, 4, true))
+ let clients = global.io.sockets.adapter.rooms.get(roomId);
+
+ // This should return the deck data, etc. for each client
+ // ideally only returning the items that the user can/should
+ // see i.e. shouldn't give them the inDeck card list just a counter
+ // shouldn't have opponent card data/their hand shouldn't be flipped
+
+ // Not sure how to catch errors for these await alls
+ // TODO: Look into error handling for await alls
+ const [itemData] =
+ await Promise.all([
+ roomMod.roomGeneration(roomId),
+ ]);
+
+
+ // data is the 'itemData' not all the roomData
+ response.success = true;
+ response.message = itemData;
+
+ // Each player then gets sent the roomGeneration stuff
+ for (const clientId of clients) {
+
+ const clientSocket = global.io.sockets.sockets.get(clientId);
+ console.log('>> responseStartGame: '+clientSocket.playerId);
+
+ // TODO: TESTING STUFF, REMOVE WHEN SORTED
+ let message = 'You are player: '+roomData[roomId].playerOrder[clientSocket.playerId];
+ global.socketAlert(clientSocket.id, message, 'alert');
+
+ // Emit the itemData to client socket (TODO: only emit what each player should see/recieve)
+ global.io.to(clientSocket.id).emit('responseStartGame', response);
+
+ }
+
+
+}
+
+// TODO: Need a 'leave room'/disconnect
+
+module.exports = {
+ requestRooms
+ ,requestJoinRoom
+ ,requestCreateRoom
+};
diff --git a/server.js b/server.js
index c29979d..255de91 100644
--- a/server.js
+++ b/server.js
@@ -1,13 +1,21 @@
-
const express = require('express');
+
const database = require('./database');
-const cardGen = require('./cardGen');
-const roomMod = require('./roomMod');
+const rooms = require('./rooms');
+const gameMod = require('./gameMod');
+
const app = express();
const http = require('http').Server(app);
const port = process.env.PORT || 3000;
-
const io = require('socket.io')(http);
+global.io = io;
+
+// To log the player sockets, so they can be easily referred to
+// maybe jank, but can't see alternative currently
+global.playerSocket = {};
+global.roomData = {}; // Made global for now, as to not replicate. Maybe sub-optimal?
+
+
// util is what nodejs uses for console.log, but has a depth of 2 set
// so console.logs show [Array]/[Object] instead of useful info.
// This can be overridden console.log(util.inspect(LOGDATA, true, 4, true))
@@ -21,309 +29,38 @@ database.connect();
io.on('connection', onConnection);
-// Variables
-let numRooms = 0;
-let numRoomsToPreGen = 1;
-const maxRooms = 3;
-const maxPlayersPerRoom = 2;
-const maxSpectatorsPerRoom = 0;
-
-// All the room
-//let data = []; // Normal array
-let data = {}; // Object array (this one for returning to player, and JSON stringify while keeping named ids)
-let roomData = {};
-for (let roomId = 1; roomId <= numRoomsToPreGen; roomId++) {
- // Never have more rooms than max rooms!!!
- if(numRooms > maxRooms){
- break;
- }
-
- createRoom(roomId);
-}
-
function onConnection(socket){
console.log('+ User connected');
console.log('');
+ // Rooms (joining, creating, etc)
socket.on('requestRooms', function(filter) {
- requestRooms(socket, filter);
+ rooms.requestRooms(socket, filter);
});
socket.on('requestJoinRoom', function(playerName, roomId) {
- requestJoinRoom(socket, playerName, roomId);
+ rooms.requestJoinRoom(socket, playerName, roomId);
});
socket.on('requestCreateRoom', function(playerName) {
- requestCreateRoom(socket, playerName);
+ rooms.requestCreateRoom(socket, playerName);
});
-}
-
-function requestRooms(socket, filter){
- console.log('+ requestRooms recieved');
- console.log('- filter: '+filter);
-
- let response = getRooms(filter, dump = true);
- io.to(socket.id).emit('returnRooms', response);
-
- console.log('');
-}
-
-function getRooms(filter = 'all', dump = false){
- console.log('+ getRooms');
- let response = {
- random: 'randomStuff',
- roomData: roomData,
- };
-
- if(dump){
- console.log(response);
- console.log('');
- }
-
- return response;
-}
-
-function requestCreateRoom(socket, playerName){
- console.log('+ createRoom recieved');
- console.log('- requested by: '+playerName);
-
- response = createRoom(roomId = false, dump = true);
- io.to(socket.id).emit('returnCreateRoom', response);
-
- if(response.success){
- let response = getRooms(filter = 'all', dump = true);
- io.to(socket.id).emit('returnRooms', response);
- }
-
- console.log('');
-}
-
-function createRoom(roomId = false, dump = true){
- let roomName = false;
- if(roomId == false){
- roomId = numRooms + 1;
- }
- console.log(roomId);
-
- let response = {
- success: false,
- message: 'No idea bossman'
- };
-
- // Max room limit reached
- console.log(numRooms);
- console.log(maxRooms);
- if(numRooms >= maxRooms){
- console.log('- Room limit reached');
-
- response = {
- success: false,
- message: 'No space '+numRooms+' out of '+maxRooms+' created.'
- };
-
- // Create room
- }else{
- console.log('- Creating room')
- let room = {};
- room['id'] = roomId;
- room['name'] = 'Room:'+room['id'];
- roomName = room['name'];
- room['password'] = '';
- room['timeout'] = {};
- room['timeout']['s'] = 10;
- room['people'] = 0;
- room['playerIds'] = {};
-
- //room['deck'] = [];
- //room['turn'] = 0;
-
- // Removed players for now, players may be seperate
- // and back-end only with an assoc. to current room
-
- //let players = {};
- //for (let j = 0; j < maxPlayersPerRoom; j++) {
- //let p = {};
- //p['id'] = 0;
- //p['name'] = "";
- //p['hand'] = {};
- //players[j] = p;
- //}
-
- //room['players'] = players;
- roomData[roomId] = room;
- numRooms = numRooms + 1;
-
- response = {
- success: true,
- message: 'Room Created: '+roomName,
- };
- }
-
- if(dump){
- console.log(response);
- console.log('');
- }
- return response;
-}
-
-// TODO: break into requestJoinRoom, and JoinRoom?
-// Maybe not needed here? As won't be done via backend?
-// TODO: Need a 'leave room'/disconnect
-function requestJoinRoom(socket, playerName, roomId){
-
- console.log('+ requestJoinRoom recieved');
-
- let room = roomData[roomId];
-
- // Add socket for playerName so that players in room get
- // responses, etc. from the room (something like that)
-
- // Add player to socket object, so it can be referred to
- // as each socket is individual to a player, but rooms need to
- // emit to multiple players. These .player can be used in loops
-
- // https://socket.io/docs/v4/rooms/
- // https://stackoverflow.com/a/18096649
- socket.playerId = playerName;
-
- if(room === undefined){
- io.to(socket.id).emit('responseRoom', 'error');
- console.log('>> Room does not exist');
- }
-
- let roomName = 'Room_' + roomId;
- let people = room['people'];
- // people = io.sockets.adapter.rooms[roomId].length; // This gets the sockets in the room (i.e. the players)
-
- //console.log(util.inspect(io.sockets.adapter.rooms, true, 4, true))
- //console.log('- people(socket: '+io.sockets.adapter.rooms[player]+')');
- //console.log('- maxPlayersPerRoom: '+maxPlayersPerRoom);
-
- if(isUserInRoom(playerName, roomId)){
- console.log('Already in room');
- return false;
- }
-
- if (people < maxPlayersPerRoom) {
-
- // Update people in room count
- people = room['people'] += 1;
-
- // Add playerId to room (playerName for now while Ids don't exist TODO)
- room['playerIds'][playerName] = playerName;
-
- // https://socket.io/docs/v4/rooms/
- // https://stackoverflow.com/a/25028953
- socket.join(roomId);
-
- // https://stackoverflow.com/a/25028953
- //console.log(util.inspect(io.sockets.adapter.rooms.get(roomId), true, 4, true))
- /*
- let clients = io.sockets.adapter.rooms.get(roomId);
- let numClients = clients ? clients.size : 0;
- for (const clientId of clients) {
- //this is the socket of each client in the room.
- const clientSocket = io.sockets.sockets.get(clientId);
- console.log(clientSocket.playerId); // The playerId set beggining of func.
- }
- */
-
- console.log('>> User ' + playerName +
- ' connected on ' + roomName + ' (' + (people) + '/' + maxPlayersPerRoom + ')');
-
- // Joined room (emit to the player that just joined)
- io.to(socket.id).emit('responseJoinRoom', roomName);
-
- if (people >= maxPlayersPerRoom) {
- console.log('- starting game');
- // startGame for room
- startGame(roomId);
- }
-
- }
-
-}
-
-// Will need to be different to playerName in future (in case dupes)
-// would use playerId TODO
-function isUserInRoom(playerName, roomId){
- if(playerName in roomData[roomId]['playerIds']){
- return true;
- }
- return false;
-}
-
-function startGame(roomId){
-
- console.log('>> Room: ' + roomId + ': Requesting game...');
- let people = roomData[roomId].players;
- /*
- try {
- //people = io.sockets.adapter.rooms.get(roomId).size;
- } catch (e) {
- console.log('>> Room: ' + roomId + ': No people here...');
- return;
- }
- */
-
- // For now, if there's 2 people only. Will need changing for
- // 3v1, 5v1, 2v2, etc...
-
- let response = {success: false, message: 'Failed requestStartGame() server.js'};
- if(people < maxPlayersPerRoom){
- console.log('Too few people');
- }
-
- console.log('>> Room: ' + roomId + ': Starting');
-
-
- // https://stackoverflow.com/a/25028953
- //console.log(util.inspect(io.sockets.adapter.rooms.get(roomId), true, 4, true))
- let clients = io.sockets.adapter.rooms.get(roomId);
-
- /*
- for (const clientId of clients) {
- //this is the socket of each client in the room.
- const clientSocket = io.sockets.sockets.get(clientId);
- console.log(clientSocket.playerId); // The playerId set in requestJoin
-
- // Just so I know how to access stuff in future.
- console.log(roomData[roomId].playerIds[clientSocket.playerId] + 'is in the game');
- }
- */
-
- // This should return the deck data, etc. for each client
- // ideally only returning the items that the user can/should
- // see i.e. shouldn't give them the inDeck card list just a counter
- // shouldn't have opponent card data/their hand shouldn't be flipped
- roomMod.roomGeneration().then(data => {
- response.success = true;
- response.message = data;
- // Each player then gets the roomGeneration stuff
- for (const clientId of clients) {
- const clientSocket = io.sockets.sockets.get(clientId);
- console.log('>> responseStartGame: '+clientSocket.playerId);
- // Emit to client socket
- io.to(clientSocket.id).emit('responseStartGame', response);
- }
-
- })
- .catch(err => {
- response.message = err;
- // Each player then gets the error message
- for (const clientId of clients) {
- const clientSocket = io.sockets.sockets.get(clientId);
- // Emit to client socket
- io.to(clientSocket.id).emit('responseStartGame', err);
- }
+ // Game (actual things relating to the game)
+ // The socket should only be in one game, so socket.on should
+ // do this, but passing room/player anyways as it's how I've written some
+ // roomData bits. TODO: Look if I can do this better...
+ socket.on('passTurn', function(roomId, playerId) {
+ gameMod.passTurn(roomId, playerId);
});
}
-// Then do functions like this?
-function shuffleDeck(roomId, playerId){
-
+// Globals for easier clientside alerts/logs, etc.
+global.socketAlert = function(socket, message, type = 'alert'){
+ global.io.to(socket).emit(
+ type, {'message': message}
+ );
}