diff --git a/index.html b/index.html index e0d1c84..552fde0 100644 --- a/index.html +++ b/index.html @@ -4,7 +4,7 @@ - Vite + React + TS + Splendor (clone by Mikayla Dobson)
diff --git a/package-lock.json b/package-lock.json index df21d6d..d391950 100644 --- a/package-lock.json +++ b/package-lock.json @@ -10,6 +10,7 @@ "dependencies": { "react": "^18.2.0", "react-dom": "^18.2.0", + "react-router-dom": "^6.3.0", "uuid": "^8.3.2" }, "devDependencies": { @@ -378,6 +379,17 @@ "@babel/core": "^7.0.0-0" } }, + "node_modules/@babel/runtime": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.18.9.tgz", + "integrity": "sha512-lkqXDcvlFT5rvEjiu6+QYO+1GXrEHRo2LOtS7E4GtX5ESIZOgepqsZBVIj6Pv+a6zqsya9VCgiK1KAK4BvJDAw==", + "dependencies": { + "regenerator-runtime": "^0.13.4" + }, + "engines": { + "node": ">=6.9.0" + } + }, "node_modules/@babel/template": { "version": "7.18.6", "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.18.6.tgz", @@ -1087,6 +1099,14 @@ "node": ">=4" } }, + "node_modules/history": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/history/-/history-5.3.0.tgz", + "integrity": "sha512-ZqaKwjjrAYUYfLG+htGaIIZ4nioX2L70ZUMIFysS3xvBsSG4x/n1V6TXV3N8ZYNuFGlDirFg32T7B6WOUPDYcQ==", + "dependencies": { + "@babel/runtime": "^7.7.6" + } + }, "node_modules/is-core-module": { "version": "2.9.0", "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.9.0.tgz", @@ -1243,6 +1263,35 @@ "node": ">=0.10.0" } }, + "node_modules/react-router": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/react-router/-/react-router-6.3.0.tgz", + "integrity": "sha512-7Wh1DzVQ+tlFjkeo+ujvjSqSJmkt1+8JO+T5xklPlgrh70y7ogx75ODRW0ThWhY7S+6yEDks8TYrtQe/aoboBQ==", + "dependencies": { + "history": "^5.2.0" + }, + "peerDependencies": { + "react": ">=16.8" + } + }, + "node_modules/react-router-dom": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-6.3.0.tgz", + "integrity": "sha512-uaJj7LKytRxZNQV8+RbzJWnJ8K2nPsOOEuX7aQstlMZKQT0164C+X2w6bnkqU3sjtLvpd5ojrezAyfZ1+0sStw==", + "dependencies": { + "history": "^5.2.0", + "react-router": "6.3.0" + }, + "peerDependencies": { + "react": ">=16.8", + "react-dom": ">=16.8" + } + }, + "node_modules/regenerator-runtime": { + "version": "0.13.9", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.9.tgz", + "integrity": "sha512-p3VT+cOEgxFsRRA9X4lkI1E+k2/CtnKtU4gcxyaCUreilL/vqI6CdZ3wxVUx3UOUg+gnUOQQcRI7BmSI656MYA==" + }, "node_modules/resolve": { "version": "1.22.1", "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.1.tgz", @@ -1692,6 +1741,14 @@ "@babel/helper-plugin-utils": "^7.18.6" } }, + "@babel/runtime": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.18.9.tgz", + "integrity": "sha512-lkqXDcvlFT5rvEjiu6+QYO+1GXrEHRo2LOtS7E4GtX5ESIZOgepqsZBVIj6Pv+a6zqsya9VCgiK1KAK4BvJDAw==", + "requires": { + "regenerator-runtime": "^0.13.4" + } + }, "@babel/template": { "version": "7.18.6", "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.18.6.tgz", @@ -2125,6 +2182,14 @@ "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", "dev": true }, + "history": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/history/-/history-5.3.0.tgz", + "integrity": "sha512-ZqaKwjjrAYUYfLG+htGaIIZ4nioX2L70ZUMIFysS3xvBsSG4x/n1V6TXV3N8ZYNuFGlDirFg32T7B6WOUPDYcQ==", + "requires": { + "@babel/runtime": "^7.7.6" + } + }, "is-core-module": { "version": "2.9.0", "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.9.0.tgz", @@ -2232,6 +2297,28 @@ "integrity": "sha512-wViHqhAd8OHeLS/IRMJjTSDHF3U9eWi62F/MledQGPdJGDhodXJ9PBLNGr6WWL7qlH12Mt3TyTpbS+hGXMjCzQ==", "dev": true }, + "react-router": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/react-router/-/react-router-6.3.0.tgz", + "integrity": "sha512-7Wh1DzVQ+tlFjkeo+ujvjSqSJmkt1+8JO+T5xklPlgrh70y7ogx75ODRW0ThWhY7S+6yEDks8TYrtQe/aoboBQ==", + "requires": { + "history": "^5.2.0" + } + }, + "react-router-dom": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-6.3.0.tgz", + "integrity": "sha512-uaJj7LKytRxZNQV8+RbzJWnJ8K2nPsOOEuX7aQstlMZKQT0164C+X2w6bnkqU3sjtLvpd5ojrezAyfZ1+0sStw==", + "requires": { + "history": "^5.2.0", + "react-router": "6.3.0" + } + }, + "regenerator-runtime": { + "version": "0.13.9", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.9.tgz", + "integrity": "sha512-p3VT+cOEgxFsRRA9X4lkI1E+k2/CtnKtU4gcxyaCUreilL/vqI6CdZ3wxVUx3UOUg+gnUOQQcRI7BmSI656MYA==" + }, "resolve": { "version": "1.22.1", "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.1.tgz", diff --git a/package.json b/package.json index 18ba0f6..c8dd376 100644 --- a/package.json +++ b/package.json @@ -11,6 +11,7 @@ "dependencies": { "react": "^18.2.0", "react-dom": "^18.2.0", + "react-router-dom": "^6.3.0", "uuid": "^8.3.2" }, "devDependencies": { diff --git a/src/App.tsx b/src/App.tsx index 52d0edd..3afb7c7 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -1,36 +1,27 @@ +import { BrowserRouter, Routes, Route } from 'react-router-dom' import Gameboard from './components/Gameboard/Gameboard' import './App.css' -import { useCallback, useEffect, useState } from 'react' +import { useCallback, useContext, useEffect, useState } from 'react' +import { appState, Context } from './context/Context' +import AvailableChips from './components/Resources/AvailableChips'; +import GameConstructor from './util/GameConstructor'; +import { PlayerData } from './util/types'; function App() { - const [state, setState] = useState({ - gameboard: null, - store: null, - players: null, - round: 0 - }) - - useEffect(() => { - if (!state.players) { - console.log('no players!'); - } - }, []); - - const getGameboard = useCallback(() => { - - }, []) + let AppContext = useContext(Context); + let { players } = AppContext; return (
- - {/* - - < INVENTORY /> - < PLAYERS /> - - */} +

SPLENDOR

+ + + } /> + } /> + +
- ) + ); } export default App diff --git a/src/components/Card/Card.tsx b/src/components/Card/Card.tsx index f4b2f6f..1e73bb3 100644 --- a/src/components/Card/Card.tsx +++ b/src/components/Card/Card.tsx @@ -1,4 +1,5 @@ import { CardData } from '../../util/types'; +import { v4 } from 'uuid'; type CardProps = { data: CardData @@ -14,7 +15,7 @@ export default function Card({ data }: CardProps) { { Object.keys(data.resourceCost).map((key, value) => { return ( // @ts-ignore -

{key}: {data.resourceCost[key]}

+

{key}: {data.resourceCost[key]}

) }) } diff --git a/src/components/Gameboard/Gameboard.tsx b/src/components/Gameboard/Gameboard.tsx index 6ddd277..0911c2b 100644 --- a/src/components/Gameboard/Gameboard.tsx +++ b/src/components/Gameboard/Gameboard.tsx @@ -1,48 +1,37 @@ -import { useEffect, useState } from 'react'; -import { CardData, NobleData } from '../../util/types'; +import { useContext, useEffect, useState } from 'react'; +import { Context } from '../../context/Context'; +import GameConstructor from '../../util/GameConstructor'; +import { NobleData } from '../../util/types'; +import AvailableChips from '../Resources/AvailableChips'; import CardRow from './CardRow'; -import CardDeck from '../../data/cards.json'; -import Nobles from '../../data/nobles.json'; export default function Gameboard() { - const [state, setState] = useState({ - deck: CardDeck, - nobles: Nobles.nobles, - cardRows: { - tierOne: new Array, - tierTwo: new Array, - tierThree: new Array - }, - tradingResources: { - ruby: 7, - sapphire: 7, - emerald: 7, - diamond: 7, - onyx: 7, - gold: 5 - } - }) - + let AppContext = useContext(Context); + let { gameboard, players } = AppContext; const [view, setView] = useState(

Loading...

) useEffect(() => { initializeBoard(); - console.log(state); }, []) useEffect(() => { - setView( - <> - - - - - ) - }, [state.cardRows]); + if (!players.length) { + setView(); + } else { + setView( +
+ + + + +
+ ) + } + }, [players]); const shuffleDeck = () => { - if (!state.deck) return; - let newDeck = state.deck; + if (!gameboard.deck) return; + let newDeck = gameboard.deck; for (const [key, value] of Object.entries(newDeck)) { for (let i = value.length - 1; i > 0; i--) { @@ -53,11 +42,12 @@ export default function Gameboard() { } } - setState({ ...state, deck: newDeck }); + gameboard.deck = newDeck; + // setState({ ...gameboard, deck: newDeck }); } const setNobles = () => { - let newNobles = state.nobles; + let newNobles = gameboard.nobles; let shuffledNobles = new Array; while (shuffledNobles.length < 4) { @@ -66,16 +56,17 @@ export default function Gameboard() { shuffledNobles.push(randNoble); } - setState({ ...state, nobles: shuffledNobles }); + // setState({ ...gameboard, nobles: shuffledNobles }); + gameboard.nobles = shuffledNobles; } const initializeBoard = () => { shuffleDeck(); setNobles(); - let newState = state; + let newState = gameboard; - for (const [key, value] of Object.entries(state.deck)) { + for (const [key, value] of Object.entries(gameboard.deck)) { // @ts-ignore while (newState.cardRows[key].length < 4) { const nextCard = value.shift(); @@ -84,13 +75,8 @@ export default function Gameboard() { } } - setState(newState); + gameboard = newState; } - return ( -
-

SPLENDOR

- { view } -
- ) + return view; } \ No newline at end of file diff --git a/src/components/Player/AllPlayers.tsx b/src/components/Player/AllPlayers.tsx new file mode 100644 index 0000000..f42adcb --- /dev/null +++ b/src/components/Player/AllPlayers.tsx @@ -0,0 +1,11 @@ +import { useContext } from "react" +import { Context } from "../../context/Context" + +export default function AllPlayers() { + const AppContext = useContext(Context); + + return ( + <> + + ) +} \ No newline at end of file diff --git a/src/components/Resources/AvailableChips.tsx b/src/components/Resources/AvailableChips.tsx new file mode 100644 index 0000000..25c649c --- /dev/null +++ b/src/components/Resources/AvailableChips.tsx @@ -0,0 +1,22 @@ +import { useContext } from "react" +import { Context } from "../../context/Context" +import { v4 } from "uuid"; + +export default function AvailableChips() { + const { gameboard } = useContext(Context); + + return ( +
+ { + Object.keys(gameboard.tradingResources).map((key: string) => { + return ( +
+ {/* @ts-ignore */} +

{key}: {gameboard.tradingResources[key]}

+
+ ) + }) + } +
+ ) +} \ No newline at end of file diff --git a/src/context/Context.ts b/src/context/Context.ts new file mode 100644 index 0000000..1ec607e --- /dev/null +++ b/src/context/Context.ts @@ -0,0 +1,28 @@ +import { CardData, NobleData, PlayerData } from '../util/types'; +import CardDeck from '../data/cards.json'; +import { createContext } from 'react'; +import { AppState } from './types'; + +export const appState: AppState = { + gameboard: { + nobles: new Array, + cardRows: { + tierOne: new Array, + tierTwo: new Array, + tierThree: new Array, + }, + tradingResources: { + ruby: 7, + sapphire: 7, + emerald: 7, + diamond: 7, + onyx: 7, + gold: 5 + }, + deck: CardDeck, + }, + round: 0, + players: new Array, +} + +export const Context = createContext(appState); \ No newline at end of file diff --git a/src/context/types.d.ts b/src/context/types.d.ts new file mode 100644 index 0000000..4b67105 --- /dev/null +++ b/src/context/types.d.ts @@ -0,0 +1,16 @@ +import { CardData, FullDeck, NobleData, PlayerData, ResourceCost } from "../util/types" + +export interface AppState { + gameboard: { + nobles: Array, + cardRows: { + tierOne: Array + tierTwo: Array + tierThree: Array + }, + tradingResources: ResourceCost + deck: FullDeck, + }, + round: number, + players: Array +} \ No newline at end of file diff --git a/src/util/GameConstructor.tsx b/src/util/GameConstructor.tsx new file mode 100644 index 0000000..75a0b87 --- /dev/null +++ b/src/util/GameConstructor.tsx @@ -0,0 +1,70 @@ +import { useContext, useState } from "react" +import { useNavigate } from "react-router-dom" +import { Context } from "../context/Context"; +import { CardData, NobleData, PlayerData } from "./types"; + +export default function GameConstructor() { + const AppContext = useContext(Context); + const navigate = useNavigate(); + + const [input, setInput] = useState({ + playerOne: '', + playerTwo: '', + playerThree: '', + playerFour: '', + }) + + const newGame = () => { + if (!input.playerOne || !input.playerTwo) return; + if (input.playerFour && !input.playerThree) return; + + const newPlayers = Object.values(input).map((name: string): PlayerData => { + return { + name: name, + starter: false, + points: 0, + nobles: new Array, + cards: new Array, + inventory: { + ruby: 0, + sapphire: 0, + emerald: 0, + diamond: 0, + onyx: 0, + gold: 0 + } + } + }) + + for (let player of newPlayers) { + if (!player.name) newPlayers.splice(newPlayers.indexOf(player)); + } + + AppContext.players = newPlayers; + + console.log(AppContext) + navigate('/game'); + } + + return ( +
+

Configure a new game:

+ +
+ + setInput({ ...input, playerOne: e.target.value})}> + + setInput({ ...input, playerTwo: e.target.value})}> +
+ +
+ + setInput({ ...input, playerThree: e.target.value})}> + + setInput({ ...input, playerFour: e.target.value})}> +
+ + +
+ ) +} \ No newline at end of file diff --git a/src/util/types.ts b/src/util/types.d.ts similarity index 100% rename from src/util/types.ts rename to src/util/types.d.ts