
Fix load resize callbackk issue Signed-off-by: James Ketrenos <james_eikona@ketrenos.com>
182 lines
5.7 KiB
JavaScript
182 lines
5.7 KiB
JavaScript
import React, { useState, useEffect, useContext, useRef, useMemo, useCallback } from "react";
|
|
import Paper from '@material-ui/core/Paper';
|
|
import Button from '@material-ui/core/Button';
|
|
import equal from "fast-deep-equal";
|
|
|
|
import "./Actions.css";
|
|
import { PlayerName } from './PlayerName.js';
|
|
import { GlobalContext } from "./GlobalContext.js";
|
|
|
|
const Actions = ({buildActive, setBuildActive}) => {
|
|
const { ws, gameId, name } = useContext(GlobalContext);
|
|
const [state, setState] = useState('lobby');
|
|
const [color, setColor] = useState(undefined);
|
|
const [priv, setPriv] = useState(undefined);
|
|
const [turn, setTurn] = useState({});
|
|
const [edit, setEdit] = useState(name);
|
|
const [active, setActive] = useState(0);
|
|
|
|
const fields = useMemo(() => [
|
|
'state', 'turn', 'private', 'active', 'color'
|
|
], []);
|
|
|
|
const onWsMessage = (event) => {
|
|
const data = JSON.parse(event.data);
|
|
switch (data.type) {
|
|
case 'game-update':
|
|
console.log(`actions - game update`, data.update);
|
|
if ('private' in data.update && !equal(data.update.private, priv)) {
|
|
setPriv(data.update.private);
|
|
}
|
|
if ('state' in data.update && data.update.state !== state) {
|
|
setState(data.update.state);
|
|
}
|
|
if ('color' in data.update && data.update.color !== color) {
|
|
setColor(data.update.color);
|
|
}
|
|
if ('name' in data.update && data.update.name !== edit) {
|
|
setEdit(data.update.name);
|
|
}
|
|
if ('turn' in data.update && !equal(data.update.turn, turn)) {
|
|
setTurn(data.update.turn);
|
|
}
|
|
if ('active' in data.update && data.update.active !== active) {
|
|
setActive(data.update.active);
|
|
}
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
};
|
|
const refWsMessage = useRef(onWsMessage);
|
|
useEffect(() => { refWsMessage.current = onWsMessage; });
|
|
useEffect(() => {
|
|
if (!ws) { return; }
|
|
const cbMessage = e => refWsMessage.current(e);
|
|
ws.addEventListener('message', cbMessage);
|
|
return () => {
|
|
ws.removeEventListener('message', cbMessage);
|
|
}
|
|
}, [ws, refWsMessage]);
|
|
useEffect(() => {
|
|
if (!ws) { return; }
|
|
ws.send(JSON.stringify({
|
|
type: 'get',
|
|
fields
|
|
}));
|
|
}, [ws, fields]);
|
|
|
|
const sendMessage = useCallback((data) => {
|
|
if (!ws) {
|
|
console.warn(`No socket`);
|
|
} else {
|
|
ws.send(JSON.stringify(data));
|
|
}
|
|
}, [ws]);
|
|
|
|
const buildClicked = () => {
|
|
setBuildActive(!buildActive);
|
|
};
|
|
|
|
const setName = (update) => {
|
|
if (update !== name) {
|
|
sendMessage({ type: 'player-name', name: update });
|
|
}
|
|
setEdit(name);
|
|
if (buildActive) setBuildActive(false);
|
|
}
|
|
|
|
const changeNameClick = () => {
|
|
setEdit("");
|
|
if (buildActive) setBuildActive(false);
|
|
}
|
|
|
|
const discardClick = () => {
|
|
const nodes = document.querySelectorAll('.Hand .Resource.Selected'),
|
|
discards = { wheat: 0, brick: 0, sheep: 0, stone: 0, wood: 0 };
|
|
|
|
for (let i = 0; i < nodes.length; i++) {
|
|
discards[nodes[i].getAttribute("data-type")]++;
|
|
nodes[i].classList.remove('Selected');
|
|
}
|
|
|
|
sendMessage({ type: 'discard', discards });
|
|
if (buildActive) setBuildActive(false);
|
|
}
|
|
|
|
const newTableClick = () => {
|
|
sendMessage({ type: 'shuffle' });
|
|
if (buildActive) setBuildActive(false);
|
|
};
|
|
|
|
const tradeClick = () => {
|
|
sendMessage({ type: 'trade' });
|
|
if (buildActive) setBuildActive(false);
|
|
}
|
|
|
|
const rollClick = () => {
|
|
sendMessage({ type: 'roll' });
|
|
if (buildActive) setBuildActive(false);
|
|
}
|
|
|
|
const passClick = () => {
|
|
sendMessage({ type: 'pass' });
|
|
if (buildActive) setBuildActive(false);
|
|
}
|
|
|
|
const startClick = () => {
|
|
sendMessage({
|
|
type: 'set',
|
|
field: 'state',
|
|
value: 'game-order'
|
|
});
|
|
if (buildActive) setBuildActive(false);
|
|
};
|
|
|
|
if (!gameId) {
|
|
return (<Paper className="Actions"/>);
|
|
}
|
|
|
|
const inLobby = state === 'lobby',
|
|
inGame = state === 'normal',
|
|
inGameOrder = state === 'game-order',
|
|
hasGameOrderRolled = (priv && priv.orderRoll) ? true : false,
|
|
hasRolled = (turn && turn.roll) ? true : false,
|
|
isTurn = (turn && turn.color === color) ? true : false,
|
|
robberActions = (turn && turn.robberInAction),
|
|
haveResources = priv ? priv.resources !== 0 : false,
|
|
placement = (state === 'initial-placement' || (turn && turn.active === 'road-building')),
|
|
placeRoad = placement && turn && turn.actions && turn.actions.indexOf('place-road') !== -1;
|
|
|
|
return (
|
|
<Paper className="Actions">
|
|
{ edit === "" && <PlayerName name={name} setName={setName}/> }
|
|
<div className="Buttons">
|
|
{ name && inLobby && <>
|
|
<Button disabled={(color && active >= 2) ? false : true } onClick={startClick}>Start game</Button>
|
|
<Button disabled={color ? false : true} onClick={newTableClick}>New table</Button>
|
|
<Button disabled={color ? true : false} onClick={changeNameClick}>Change name</Button>
|
|
</> }
|
|
{ name && !inLobby && <>
|
|
<Button disabled={
|
|
robberActions ||
|
|
(inGame && (!isTurn || hasRolled)) ||
|
|
(inGameOrder && hasGameOrderRolled) ||
|
|
(!inGame && !inGameOrder)
|
|
} onClick={rollClick}>Roll Dice</Button>
|
|
<Button disabled={placeRoad || robberActions || !isTurn || !hasRolled || !haveResources} onClick={tradeClick}>Trade</Button>
|
|
<Button disabled={placeRoad || robberActions || !isTurn || !hasRolled || !haveResources} onClick={buildClicked}>Build</Button>
|
|
<Button disabled={!(turn && turn.roll === 7 && priv && priv.mustDiscard > 0)}onClick={discardClick}>Discard</Button>
|
|
<Button disabled={placeRoad || robberActions || !isTurn || !hasRolled} onClick={passClick}>Done</Button>
|
|
</> }
|
|
{ /* inLobby &&
|
|
<Button onClick={quitClick}>Quit</Button>
|
|
*/ }
|
|
</div>
|
|
</Paper>
|
|
);
|
|
}
|
|
|
|
export { Actions };
|
|
|