From 2fbfd28f3a13773d05cf791231427625385bded9 Mon Sep 17 00:00:00 2001 From: Chris Karle Date: Sun, 10 May 2020 21:54:54 -0400 Subject: [PATCH] app, CardTable, Lobby: revised join/sit/stand/exit UI updates to change to new game initial state, where coming to table starts user in is_spectator always, no more force-rejoin. Add call to leave_table when table exit chosen. Add left corner menu with Stand and Exit after game has started. Change the seat display after game starts to offer "Sit" button if any seat becomes unoccupied - visible to all spectators. If a seated player wishes to move to the empty seat they must first Stand, so also becoming a spectator. --- assets/app.js | 27 +++++++++++++-------------- assets/components/CardTable.js | 216 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++--------------------------------------------------------------------- assets/components/Lobby.js | 10 +--------- 3 files changed, 161 insertions(+), 92 deletions(-) diff --git a/assets/app.js b/assets/app.js index 30f66ed..6e4ead7 100644 --- a/assets/app.js +++ b/assets/app.js @@ -87,6 +87,18 @@ class App extends React.Component { } } } + + exitTable = () => { + client.onmessage = (event) => this.processResponse(event); + this.setState({ + tableName: '', + showTable: false + }, () => { + client.send(JSON.stringify({ + action:'leave_table' + })); + }); + } chooseTable = tableName => { if (!tableName || tableName == ''){ @@ -109,18 +121,6 @@ class App extends React.Component { }); } - forceJoin = () => { - // console.log('send force rejoin'); - // should only be calling this on unique error and user wants force rejoin - // so all other state should be correct - client.send(JSON.stringify({ - action:'join_table', - player_name: this.state.playerName, - table: this.state.tableName, - force: true - })); - } - setFakeGame = (initialName, initialTable) => { client.send(JSON.stringify({ action:'join_table', player_name: initialName, table: initialTable })); fc1.send(JSON.stringify({ action:'join_table', player_name: 'Betty', table: initialTable })); @@ -141,12 +141,11 @@ class App extends React.Component { chooseTable={this.chooseTable} name={playerName} uniqueError={uniqueError} - forceJoin={this.forceJoin} /> )} {showTable && ( this.processResponse(event); const welcomeMsg = 'Welcome to the ' + tableName + ' table, ' + name + '!'; if (firstMsg) { - this.processFirstMessage(firstMsg); + this.processPlayerChange(firstMsg); } this.setState({ bannerMsg: welcomeMsg @@ -76,43 +75,82 @@ export default class CardTable extends React.Component { componentDidUpdate (prevProps) { const {firstMsg} = this.props; if (firstMsg && !prevProps.firstMsg) { - this.processFirstMessage(firstMsg); + this.processPlayerChange(firstMsg); } } processResponse = (event) => { + const { playerNames} = this.state; let msg = JSON.parse(event.data); if ('pong' != msg.msg_type) { console.log(msg); } if ('game_state' == msg.msg_type) { - if (msg.game) { - switch (msg.game.phase) { - case 'lobby': - this.processLobby(msg); - break; - case 'vote': - this.processVote(msg); - break; - case 'dealer_swap': - this.processSwap(msg); - break; - case 'play': - this.processPlay(msg); - break; - case 'pause': - this.processPause(msg); - break; - case 'end': - this.processEnd(msg); - break; - default: - break; + if (msg.game.phase != 'lobby') { + if (!_.isEqual(playerNames, msg.game.players)){ + this.processPlayerChange(msg); + } else { + this.processResponseSwitch(msg); } + } else { + this.processLobby(msg); } }; }; + processResponseSwitch = msg => { + switch (msg.game.phase) { + case 'lobby': + this.processLobby(msg); + break; + case 'vote': + this.processVote(msg); + break; + case 'dealer_swap': + this.processSwap(msg); + break; + case 'play': + this.processPlay(msg); + break; + case 'pause': + this.processPause(msg); + break; + case 'end': + this.processEnd(msg); + break; + default: + break; + } + } + + processPlayerChange = msg => { + const {amSpectator} = this.state; + console.log('Player update!!'); + const newSpectator = msg.is_spectator > 0; + if (!amSpectator && !newSpectator) { + // I'm already a player, update the name set and continue + this.setState({ + playerNames: msg.game.players + }, () => { + this.processResponseSwitch(msg); + }); + } else if (!amSpectator && newSpectator) { + // I was playing and just stood up - reset me to spectator mode + this.processFirstMessage(msg); + } else if (amSpectator && !newSpectator) { + // I was spectator and just took a seat + this.processFirstMessage(msg); + } else { + // was and still am spectator - update names and continue + this.setState({ + playerNames: msg.game.players, + }, () => { + this.processResponseSwitch(msg); + }); + } + + } + processFirstMessage = msg => { console.log('processFirstMessage, msg:\n', msg); // in cases of forceRejoin, the firstMsg could be lobby, vote, play @@ -179,28 +217,19 @@ export default class CardTable extends React.Component { }; initMySeat = msg => { + const {name} = this.props; + const newSpec = msg.is_spectator > 0; if (msg.game.players) { const plAr = msg.game.players; - let mySeat = plAr.findIndex( x => x == this.props.name ); - // if mySeat=-1 & msg.is_spec - // set activeGameSpectator ags true, set mySeat=3 - // write my-name as playerNames[3] for bottom display - let myName = 'You'; - let ags = false; - if (mySeat == -1){ - const emptySeat = plAr.findIndex( x => x == 'Empty'); - if (emptySeat == -1) { - ags = true; - myName = plAr[3]; - mySeat = 3; - } - } - console.log('calc ags = ', ags); + let mySeat = plAr.findIndex( x => x == name ); + console.log('initMySeat.mySeat=', mySeat); + if (newSpec && msg.game.phase != 'lobby'){ + mySeat = 3; + }; this.setState({ playerNames: plAr, mySeat: mySeat, - myName: myName, - activeGameSpectator: ags + amSpectator: newSpec }); }; } @@ -321,13 +350,14 @@ export default class CardTable extends React.Component { } processEnd = msg => { - const {playerNames, myName, leftSeat, partnerSeat, rightSeat, activeGameSpectator} = this.state; + const {playerNames, leftSeat, partnerSeat, rightSeat, amSpectator} = this.state; // arrangeScore[0] us, [1] them const finalScore = this.arrangeScore(msg.game.score); + const myName = amSpectator ? playerNames[3] : 'You'; const winMsg = finalScore[0] > finalScore[1] ? myName + ' and ' + playerNames[partnerSeat] + ' win the game!!' : playerNames[leftSeat] + ' and ' + playerNames[rightSeat] + ' win this one...'; - const innerWin = activeGameSpectator ? 'Game Over...' : + const innerWin = amSpectator ? 'Game Over...' : finalScore[0] > finalScore[1] ? 'You Win!!' : 'You lost...'; this.setState({ phase: 'end', @@ -458,6 +488,10 @@ export default class CardTable extends React.Component { // console.log('start game, dealer = ', startDealer); }; + sendExit = () => { + this.props.exitTable(); + }; + sendVote = (voteObject) => { const voteString = JSON.stringify(voteObject); // console.log('sendVote:', voteString); @@ -485,9 +519,9 @@ export default class CardTable extends React.Component { } genGameOver = () => { - const {innerWinMsg, activeGameSpectator} = this.state; + const {innerWinMsg, amSpectator} = this.state; let retVal = []; - const instMsg = activeGameSpectator ? 'You can take a seat if one becomes empty, or you can return to the lobby...' + const instMsg = amSpectator ? 'You can take a seat if one becomes empty, or you can return to the lobby...' : 'You can play again at this table, or return to the lobby to change your table or player name...'; retVal.push(
@@ -499,10 +533,10 @@ export default class CardTable extends React.Component { - {!activeGameSpectator && ( + {!amSpectator && ( + )} +
); + } + return retVal; + } + render () { - const { playerNames, mySeat, myName, phase, myCards, myHandInfo, myTurnInfo, activeGameSpectator, - partnerName, partnerHandInfo, partnerTurnInfo, partnerSeat, leftName, leftTurnInfo, leftHandInfo, leftSeat, - rightName, rightHandInfo, rightTurnInfo, rightSeat, trumpPlace, trumpNom, turnSeat, + const { playerNames, mySeat, phase, myCards, myTurnInfo, amSpectator, + partnerHandInfo, partnerTurnInfo, partnerSeat, leftTurnInfo, leftHandInfo, leftSeat, + rightHandInfo, rightTurnInfo, rightSeat, trumpPlace, trumpNom, turnSeat, dealSeat, trump, handLengths, score, trickWinner, bannerMsg, noPick, onlyAlone } = this.state; const showSeatPicker = phase == 'lobby'; const showGameOver = phase == 'end'; const showTrump = (phase == 'vote') || (phase == 'vote2') || (phase == 'swap'); const showTrumpPicker = showTrump && (turnSeat == mySeat); const showSwap = (phase == 'swap') && (dealSeat == mySeat); - const showInfo = !showSeatPicker && !showTrumpPicker && !showSwap; + const showBottomInfo = !showSeatPicker && (amSpectator || (!showTrumpPicker && !showSwap)); const tcp = "trump__holder " + trumpPlace; const trumpImage = (phase != 'vote2') ? 'cards/' + trumpNom + '.svg' : 'cards/1B.svg'; const trumpMsg = phase == 'play' ? suit[trump] + ' are trump' : ''; const trickDisplay = (phase == 'play' || phase == 'pause') ? this.genTrick() : []; const gameOverDisplay = (phase == 'end') ? this.genGameOver() : []; + const usLabel = amSpectator ? playerNames[1] + ' & ' + playerNames[3] + ': ' : 'Us: '; + const themLabel = amSpectator ? playerNames[0] + ' & ' + playerNames[2] + ': ' : 'Them: '; return (
@@ -608,7 +671,7 @@ export default class CardTable extends React.Component {
@@ -616,11 +679,26 @@ export default class CardTable extends React.Component { )} + {!showSeatPicker && ( +
+ + + + +
+ )}
{!showSeatPicker && (
-
{partnerName}
+
{this.genNameDisplay(partnerSeat)}
{partnerHandInfo}
{partnerTurnInfo}
@@ -632,8 +710,8 @@ export default class CardTable extends React.Component { {(phase != 'lobby') && (
-
Us: {score[0]}
-
Them: {score[1]}
+
{usLabel}{score[0]}
+
{themLabel}{score[1]}
{trickWinner}
)}
@@ -642,7 +720,7 @@ export default class CardTable extends React.Component { {!showSeatPicker && (
-
{leftName}
+
{this.genNameDisplay(leftSeat)}
{leftHandInfo}
{leftTurnInfo}
)} { showTrump && ( @@ -678,7 +756,7 @@ export default class CardTable extends React.Component { {!showSeatPicker && (
-
{rightName}
+
{this.genNameDisplay(rightSeat)}
{rightHandInfo}
{rightTurnInfo}
- {(showInfo || activeGameSpectator) && ( + {showBottomInfo && (
-
{myName}: {myHandInfo}
+
{this.genNameDisplay(mySeat)}
{myTurnInfo}
{trumpMsg}
)} - {showTrumpPicker && !activeGameSpectator && ( + {showTrumpPicker && !amSpectator && ( )} - {showSwap && !activeGameSpectator && ( + {showSwap && !amSpectator && (
Click a card to discard:
)}
- {!showSeatPicker && !activeGameSpectator && ( + {!showSeatPicker && !amSpectator && ( )} - {!showSeatPicker && activeGameSpectator && ( + {!showSeatPicker && amSpectator && ( )} @@ -732,7 +810,7 @@ export default class CardTable extends React.Component { } CardTable.propTypes = { - chooseTable: PropTypes.func, + exitTable: PropTypes.func, name: PropTypes.string, tableName: PropTypes.string, firstMsg: PropTypes.object, diff --git a/assets/components/Lobby.js b/assets/components/Lobby.js index 4ae005b..36f3cdb 100644 --- a/assets/components/Lobby.js +++ b/assets/components/Lobby.js @@ -114,13 +114,6 @@ export default class Lobby extends React.Component {

Hmm, a player named {name} is at the table...

You need a unique player name, which you can change in the top input above.

-

OR if you lost your connection and want to re-join the - game as player "{name}" from this page, press the REJOIN button below

-
)}
@@ -132,6 +125,5 @@ Lobby.propTypes = { setName: PropTypes.func, chooseTable: PropTypes.func, name: PropTypes.string, - uniqueError: PropTypes.bool, - forceJoin: PropTypes.func + uniqueError: PropTypes.bool } \ No newline at end of file -- libgit2 1.1.1