WIP: Attack

TODO: finaliseAttack(), do the attack, do fight/GY
and tap/destroy shield
feature/clientSideSimplify
Nathan Steel 1 year ago
parent fee1a3988e
commit 63d6056fe1

@ -29,6 +29,7 @@ const component = {
tapped : {},
attacking : {},
inspected : {},
targetable : {},
},
cardAttack : {},
cardColours : {}, // Replace with colour

@ -47,8 +47,46 @@ function moveElementPositions(roomId, player, direction, element, position){
}
function canAttack(roomId, playerId, cardId){
if(cardId in global.roomData[roomId].itemData.component.cardStatus.tapped){
return false;
}
return true;
}
function getTargetableCards(roomId, playerId, cardId){
// i.e. If no flight/reach, you cant attack flight, if not all shield tapped, cant attack tapped shield
// TODO: The above, for now just letting all units/shields targetable
let targetable = {};
// Board
for (const [key, value] of Object.entries(global.roomData[roomId].itemData.component.board)) {
// If not the players card (for now, will need better checks in future)
if(global.roomData[roomId].itemData.player[key] !== playerId){
targetable[key] = key;
}
}
// Shield
for (const [key, value] of Object.entries(global.roomData[roomId].itemData.component.shield)) {
// If not the players card (for now, will need better checks in future)
if(global.roomData[roomId].itemData.player[key] !== playerId){
//if(!(key in global.roomData[roomId].itemData.player[playerId])){
targetable[key] = key;
}
}
console.log(targetable);
return targetable;
}
module.exports = {
setCardPosition
,canAttack
,getTargetableCards
};

@ -539,6 +539,27 @@ function untapCard(roomId, playerId, cardId){
}
function startAttack(roomId, playerId, cardId){
console.log('start attack');
if(!gameHelper.canAttack){
return false;
}
// Set the card to 'attacking'
global.roomData[roomId].itemData.component.cardStatus.attacking[cardId] = cardId;
// TODO: Maybe set targetable as component and return that
global.roomData[roomId].itemData.component.cardStatus.targetable = gameHelper.getTargetableCards(roomId, playerId, cardId);
// Return the available targets (give them a border in UI)
global.socketResponseUpdateTargetable(roomId, playerId,
global.roomData[roomId].itemData.component.cardStatus.targetable
);
}
// DATA RETURNER DUDES
// TODO: Where to put this? Kind of a helper, kind of functionality. Hmmmmm
// maybe do a dataHelper? then anything to return data can be included there?
@ -599,6 +620,7 @@ module.exports = {
,playManaFromHand
,acceptResolveStack
,gameStart
,startAttack
// TEMP
,tapCard
,untapCard

@ -22,6 +22,7 @@
<button onclick="requestDrawACard()">Draw Card</button>
<button onclick="requestShuffleDeck()">Shuffle Deck</button>
<button onclick="requestResolveStack()">Resolve Stack</button>
<button onclick="requestFinaliseAttack()">Finalise Attack</button>
<br><br>
<hr>

@ -350,13 +350,15 @@ function drawCardInHand(entity){
// TODO: Change card colour based on its colours
// Draw the card shape
let strokeStyle = '#AAA';
if(entity in gameData.cardStatus.targetable){ strokeStyle = '#222'; }
let shape = new Shape({
x: gameData.position[entity][0],
y: gameData.position[entity][1],
width: gameData.size[entity][0],
height: gameData.size[entity][1],
fillStyle: '#EEE',
strokeStyle: '#AAA',
strokeStyle: strokeStyle,
});
shape.draw();
@ -370,7 +372,9 @@ function drawCardOnBoard(entity){
// TODO: Passives, flight, etc. effects
let strokeStyle = '#AAA';
if(entity in gameData.cardStatus.tapped){ strokeStyle = '#555'; }
if(entity in gameData.cardStatus.tapped){ strokeStyle = '#6D0202'; }
if(entity in gameData.cardStatus.targetable){ strokeStyle = '#FF9A00'; }
if(entity in gameData.cardStatus.targetted){ strokeStyle = '#EC5300'; }
// Draw the card shape
let shape = new Shape({
x: gameData.position[entity][0],
@ -392,6 +396,7 @@ function drawShield(entity){
let strokeStyle = '#AAA';
if(entity in gameData.cardStatus.tapped){ strokeStyle = '#555'; }
if(entity in gameData.cardStatus.targetable){ strokeStyle = '#222'; }
// Draw the card shape
let shape = new Shape({
x: gameData.position[entity][0],
@ -416,6 +421,7 @@ function drawMana(entity){
let strokeStyle = '#AAA';
if(entity in gameData.cardStatus.tapped){ strokeStyle = '#555'; }
if(entity in gameData.cardStatus.targetable){ strokeStyle = '#222'; }
// Draw the card shape
let shape = new Shape({
x: gameData.position[entity][0],

@ -35,6 +35,18 @@ function openInteractionMenu(entity){
// Interact
// Attack
// Start Attack
if(entity in gameData.board && !(entity in gameData.cardStatus.tapped)){
// TODO: Make the object within each interationOption a function to return instead of duping
gameData.interactionOption['Attack'] = {
x: gameData.position[entity][0] + gameData.size[entity][0]*.1/2,
y: gameData.position[entity][1] + gameData.size[entity][1] - (35 * (Object.entries(gameData.interactionOption).length + 1)),
width: gameData.size[entity][0]*.9,
height: 30
}
}
// Target Attack Target
// Tap
// TAP (TEMP TODO: remove or add in a statement to hide)
@ -77,6 +89,28 @@ function openInteractionMenu(entity){
}
// If selectable, give option to select. If selected, deselect
if(gameData.cardStatus.targetable[entity] !== undefined){
gameData.interactionOption['Target'] = {
x: gameData.position[entity][0] + gameData.size[entity][0]*.1/2,
y: gameData.position[entity][1] + gameData.size[entity][1] - (35 * (Object.entries(gameData.interactionOption).length + 1)),
width: gameData.size[entity][0]*.9,
height: 30
}
}
if(gameData.cardStatus.targetable[entity] !== undefined && gameData.cardStatus.targetted[entity] !== undefined){
gameData.interactionOption['Untarget'] = {
x: gameData.position[entity][0] + gameData.size[entity][0]*.1/2,
y: gameData.position[entity][1] + gameData.size[entity][1] - (35 * (Object.entries(gameData.interactionOption).length + 1)),
width: gameData.size[entity][0]*.9,
height: 30
}
}
drawGameBoard();
}
@ -117,6 +151,19 @@ function doiMenuPressed(iMenuKey){
iMenuUntap();
}
// Attack
// Start Attack (Card that's to attack)
if(iMenuKey == 'Attack'){
iMenuStartAttack();
}
// Target
if(iMenuKey == 'Target'){
iMenuTarget();
}
if(iMenuKey == 'Untarget'){
iMenuUntarget();
}
}
function iMenuPlayToBoard(){
@ -143,4 +190,16 @@ function iMenuUntap(){
console.log(Object.keys(gameData.inInteractionMenu)[0]);
requestUntapCard(gameData.inInteractionMenu[Object.keys(gameData.inInteractionMenu)[0]]);
}
function iMenuStartAttack(){
requestStartAttack(Object.keys(gameData.inInteractionMenu)[0]);
}
function iMenuTarget(){
gameData.cardStatus.targetted[Object.keys(gameData.inInteractionMenu)[0]] = Object.keys(gameData.inInteractionMenu)[0];
clearInteractionMenu(); // Clears and redraws the board
console.log('target');
}
function iMenuUntarget(){
delete(gameData.cardStatus.targetted[Object.keys(gameData.inInteractionMenu)[0]]);
console.log('UNtarget');
}

@ -34,6 +34,8 @@ let gameData = {
tapped : {},
attacking : {},
inspected : {},
targetable : {},
targetted : {},
},

@ -104,6 +104,13 @@ function updateTapped(data){
gameData.cardStatus.tapped = data;
console.log(gameData.cardStatus.tapped);
}
// Targetable
function updateTargetable(data){
console.log(data);
// Clear targetable if null returned
if(data == null){ gameData.cardStatus.targetable = {}; }
gameData.cardStatus.targetable = data;
}
// To prevent typical functionality (draw, etc.)
// if there's a stack in play.

@ -121,6 +121,19 @@ socket.on('responseUntapped', function (data) {
});
function requestStartAttack(card){
console.log('>> startAttack');
socket.emit('requestStartAttack', gameData.roomId, gameData.playerId, card);
}
socket.on('responseTargetable', function (data) {
// The playerId that played it for animations
console.log('<< responseTargetable');
console.log(data);
updateTargetable(data);
drawGameBoard();
});
// Stack
socket.on('responseAddToStack', function (data) {
console.log('<< addToStack');
@ -148,7 +161,6 @@ function requestResolveStack(){
socket.emit('requestResolveStack', gameData.roomId, gameData.playerId);
}
// Functions like this would be elsewhere, do client-side
// validation THEN request stuff from the server?
// This is here for now, as it's used by the button

@ -84,6 +84,10 @@ function onConnection(socket){
gameMod.untapCard(roomId, playerId, card);
});
socket.on('requestStartAttack', function(roomId, playerId, card) {
gameMod.startAttack(roomId, playerId, card);
});
}
global.getPlayerSocketFromRoom = function(playerId, roomId){
@ -246,6 +250,22 @@ global.socketResponseUntapped = function(roomId, card){
global.sendToEachSocket(roomId, 'responseUntapped', data);
}
/*
global.socketResponseStartAttack = function(roomId, playerId, targetable){
global.socketResponseUpdateTargetable(roomId, playerId, targetable);
}
*/
global.socketResponseUpdateTargetable = function(roomId, playerId, targetable){
global.io.to(global.getPlayerSocketFromRoom(playerId, roomId)).emit(
'responseTargetable'
,targetable
);
}
// Attack (return the attacking and 'defending' card and allow for interactions/stack
// Stack
global.socketResponseAddToStack = function(roomId){
global.sendToEachSocket(roomId, 'responseAddToStack', 'testData');

Loading…
Cancel
Save