diff options
Diffstat (limited to 'frontend')
-rw-r--r-- | frontend/src/api/model.js | 98 | ||||
-rw-r--r-- | frontend/src/api/sevenWondersApi.js | 8 | ||||
-rw-r--r-- | frontend/src/components/errors/Error404.js | 2 | ||||
-rw-r--r-- | frontend/src/index.js | 7 | ||||
-rw-r--r-- | frontend/src/routes.js | 49 | ||||
-rw-r--r-- | frontend/src/scenes/Games/index.js | 65 | ||||
-rw-r--r-- | frontend/src/scenes/Lobby/index.js | 42 | ||||
-rw-r--r-- | frontend/src/scenes/SplashScreen/components/HomeLayout.js (renamed from frontend/src/layouts/HomeLayout.js) | 2 | ||||
-rw-r--r-- | frontend/src/scenes/SplashScreen/components/background-zeus-temple.jpg (renamed from frontend/src/layouts/background-zeus-temple.jpg) | bin | 571089 -> 571089 bytes | |||
-rw-r--r-- | frontend/src/scenes/SplashScreen/components/logo-7-wonders.png (renamed from frontend/src/layouts/logo-7-wonders.png) | bin | 301442 -> 301442 bytes | |||
-rw-r--r-- | frontend/src/scenes/SplashScreen/index.js | 42 | ||||
-rw-r--r-- | frontend/src/scenes/index.js | 17 |
12 files changed, 255 insertions, 77 deletions
diff --git a/frontend/src/api/model.js b/frontend/src/api/model.js index 2f9fad37..5d1f92c6 100644 --- a/frontend/src/api/model.js +++ b/frontend/src/api/model.js @@ -1,79 +1,79 @@ // @flow export type ApiError = { - message: string; - details: ApiErrorDetail[]; -} + message: string, + details: ApiErrorDetail[] +}; export type ApiErrorDetail = { - message: string; -} + message: string +}; export type ApiGameState = "LOBBY" | "PLAYING"; export type ApiLobby = { - id: number; - name: string; - owner: ApiPlayer; - players: ApiPlayer[]; - settings: ApiSettings; - state: ApiGameState; -} + id: number, + name: string, + owner: ApiPlayer, + players: ApiPlayer[], + settings: ApiSettings, + state: ApiGameState +}; export type ApiWonderSidePickMethod = "EACH_RANDOM" | "ALL_A" | "ALL_B" | "SAME_RANDOM_FOR_ALL"; export type ApiSettings = { - randomSeedForTests: number; - timeLimitInSeconds: number; - wonderSidePickMethod: ApiWonderSidePickMethod; - initialGold: number; - discardedCardGold: number; - defaultTradingCost: number; - pointsPer3Gold: number; - lostPointsPerDefeat: number; - wonPointsPerVictoryPerAge: Map<number, number>; -} + randomSeedForTests: number, + timeLimitInSeconds: number, + wonderSidePickMethod: ApiWonderSidePickMethod, + initialGold: number, + discardedCardGold: number, + defaultTradingCost: number, + pointsPer3Gold: number, + lostPointsPerDefeat: number, + wonPointsPerVictoryPerAge: Map<number, number> +}; export type ApiPlayer = { - username: string; - displayName: string; - index: number; - ready: boolean; -} + username: string, + displayName: string, + index: number, + ready: boolean +}; -export type ApiTable = {} +export type ApiTable = {}; -export type ApiAction = {} +export type ApiAction = {}; -export type ApiHandCard = {} +export type ApiHandCard = {}; -export type ApiCard = {} +export type ApiCard = {}; -export type ApiPreparedCard = {} +export type ApiPreparedCard = {}; export type ApiPlayerTurnInfo = { - playerIndex: number; - table: ApiTable; - currentAge: number; - action: ApiAction; - hand: ApiHandCard[]; - neighbourGuildCards: ApiCard[]; - message: string; -} + playerIndex: number, + table: ApiTable, + currentAge: number, + action: ApiAction, + hand: ApiHandCard[], + neighbourGuildCards: ApiCard[], + message: string +}; export type ApiMoveType = "PLAY" | "PLAY_FREE" | "UPGRADE_WONDER" | "DISCARD" | "COPY_GUILD"; export type ApiProvider = "LEFT_NEIGHBOUR" | "RIGHT_NEIGHBOUR"; export type ApiResourceType = "WOOD" | "STONE" | "ORE" | "CLAY" | "GLASS" | "PAPYRUS" | "LOOM"; export type ApiResources = { - quantities: Map<ApiResourceType, number>; -} + quantities: Map<ApiResourceType, number> +}; export type ApiBoughtResources = { - provider: ApiProvider; - resources: ApiResources; -} + provider: ApiProvider, + resources: ApiResources +}; export type ApiPlayerMove = { - type: ApiMoveType; - cardName: string; - boughtResources: ApiBoughtResources[]; -} + type: ApiMoveType, + cardName: string, + boughtResources: ApiBoughtResources[] +}; diff --git a/frontend/src/api/sevenWondersApi.js b/frontend/src/api/sevenWondersApi.js index 058408eb..534045c8 100644 --- a/frontend/src/api/sevenWondersApi.js +++ b/frontend/src/api/sevenWondersApi.js @@ -1,6 +1,12 @@ // @flow import type { - ApiError, ApiLobby, ApiPlayer, ApiPlayerMove, ApiPlayerTurnInfo, ApiPreparedCard, ApiTable, + ApiError, + ApiLobby, + ApiPlayer, + ApiPlayerMove, + ApiPlayerTurnInfo, + ApiPreparedCard, + ApiTable, } from './model'; import type { JsonStompClient, SubscribeFn } from './websocket'; import { createJsonStompClient } from './websocket'; diff --git a/frontend/src/components/errors/Error404.js b/frontend/src/components/errors/Error404.js index 32ab8e8d..9a5e005e 100644 --- a/frontend/src/components/errors/Error404.js +++ b/frontend/src/components/errors/Error404.js @@ -1,5 +1,5 @@ import React from 'react'; -import { Link } from 'react-router'; +import { Link } from 'react-router-dom'; const Error404 = () => ( <div> diff --git a/frontend/src/index.js b/frontend/src/index.js index 2dc2442c..5441edc0 100644 --- a/frontend/src/index.js +++ b/frontend/src/index.js @@ -3,21 +3,18 @@ import 'babel-polyfill'; import React from 'react'; import ReactDOM from 'react-dom'; import { ConnectedRouter } from 'react-router-redux'; -import { Route, Switch } from 'react-router'; import { Provider } from 'react-redux'; import './global-styles.css'; import configureStore from './store'; -import HomePage from './containers/home'; +import Routes from './scenes'; const initialState = {}; const { store, history } = configureStore(initialState); ReactDOM.render( <Provider store={store}> <ConnectedRouter history={history}> - <Switch> - <Route path="/" component={HomePage} /> - </Switch> + <Routes /> </ConnectedRouter> </Provider>, document.getElementById('root') diff --git a/frontend/src/routes.js b/frontend/src/routes.js index b87977ef..60efed8d 100644 --- a/frontend/src/routes.js +++ b/frontend/src/routes.js @@ -1,23 +1,32 @@ // @flow -import { HomeLayout, LobbyLayout } from './layouts'; -import GameBrowser from './containers/gameBrowser'; -import HomePage from './containers/home'; -import Lobby from './containers/lobby'; +import React from 'react'; + +import Application from './scenes'; import Error404 from './components/errors/Error404'; -export const routes = [ - { - path: '/', - component: HomeLayout, - indexRoute: { component: HomePage }, - }, - { - path: '/', - component: LobbyLayout, - childRoutes: [{ path: '/games', component: GameBrowser }, { path: '/lobby/*', component: Lobby }], - }, - { - path: '*', - component: Error404, - }, -]; +import { Route, Switch } from 'react-router'; + +const Routes = () => ( + <Switch> + <Route path="/" component={Application} /> + <Route path="*" component={Error404} /> + </Switch> +); + +export default Routes; +// export const routes = [ +// { +// path: '/', +// component: HomeLayout, +// indexRoute: { component: HomePage }, +// }, +// { +// path: '/', +// component: LobbyLayout, +// childRoutes: [{ path: '/games', component: GameBrowser }, { path: '/lobby/*', component: Lobby }], +// }, +// { +// path: '*', +// component: Error404, +// }, +// ]; diff --git a/frontend/src/scenes/Games/index.js b/frontend/src/scenes/Games/index.js new file mode 100644 index 00000000..a2031030 --- /dev/null +++ b/frontend/src/scenes/Games/index.js @@ -0,0 +1,65 @@ +// @flow +import type { List } from 'immutable'; +import React, { Component } from 'react'; +import { connect } from 'react-redux'; +import { InlineForm, Space, Text } from 'rebass'; +import { Flex } from 'reflexbox'; +import GameList from '../../components/gameList'; +import type { Games } from '../../models/games'; +import type { Player } from '../../models/players'; +import { actions, getAllGames } from '../../redux/games'; +import { getCurrentPlayer } from '../../redux/players'; + +class GameBrowser extends Component { + props: { + currentPlayer: Player, + games: List<Games>, + createGame: (gameName: string) => void, + joinGame: (gameId: string) => void + }; + + _gameName: string | void = undefined; + + createGame = (e: SyntheticEvent): void => { + e.preventDefault(); + if (this._gameName !== undefined) { + this.props.createGame(this._gameName); + } + }; + + render() { + return ( + <div> + <Flex align="center" p={1}> + <InlineForm + buttonLabel="Create Game" + label="Game name" + name="game_name" + onChange={(e: SyntheticInputEvent) => (this._gameName = e.target.value)} + onClick={this.createGame} + /> + <Space auto /> + <Text> + <b>Username:</b> + {' '} + {this.props.currentPlayer && this.props.currentPlayer.displayName} + </Text> + <Space x={1} /> + </Flex> + <GameList games={this.props.games} joinGame={this.props.joinGame} /> + </div> + ); + } +} + +const mapStateToProps = state => ({ + currentPlayer: getCurrentPlayer(state.get('players')), + games: getAllGames(state.get('games')), +}); + +const mapDispatchToProps = { + createGame: actions.requestCreateGame, + joinGame: actions.requestJoinGame, +}; + +export default connect(mapStateToProps, mapDispatchToProps)(GameBrowser); diff --git a/frontend/src/scenes/Lobby/index.js b/frontend/src/scenes/Lobby/index.js new file mode 100644 index 00000000..1b5a11ff --- /dev/null +++ b/frontend/src/scenes/Lobby/index.js @@ -0,0 +1,42 @@ +import { List } from 'immutable'; +import React, { Component } from 'react'; +import { connect } from 'react-redux'; +import { Button } from 'rebass'; +import PlayerList from '../../components/playerList'; +import { actions, getCurrentGame } from '../../redux/games'; +import { getPlayers } from '../../redux/players'; + +class Lobby extends Component { + getTitle() { + if (this.props.currentGame) { + return this.props.currentGame.name + ' — Lobby'; + } else { + return 'What are you doing here? You haven\'t joined a game yet!'; + } + } + + render() { + return ( + <div> + <h2>{this.getTitle()}</h2> + <PlayerList players={this.props.players} /> + <Button onClick={this.props.startGame}>Start Game</Button> + </div> + ); + } +} + +const mapStateToProps = state => { + const game = getCurrentGame(state.get('games')); + console.info(game); + return { + currentGame: game, + players: game ? getPlayers(state.get('players'), game.players) : new List(), + }; +}; + +const mapDispatchToProps = { + startGame: actions.requestStartGame, +}; + +export default connect(mapStateToProps, mapDispatchToProps)(Lobby); diff --git a/frontend/src/layouts/HomeLayout.js b/frontend/src/scenes/SplashScreen/components/HomeLayout.js index f139febf..86666eb2 100644 --- a/frontend/src/layouts/HomeLayout.js +++ b/frontend/src/scenes/SplashScreen/components/HomeLayout.js @@ -2,7 +2,7 @@ import type { Children } from 'react'; import React from 'react'; import { Banner } from 'rebass'; -import ErrorToastContainer from '../components/errors/errorToastContainer'; +import ErrorToastContainer from '../../../components/errors/errorToastContainer'; import background from './background-zeus-temple.jpg'; import logo from './logo-7-wonders.png'; diff --git a/frontend/src/layouts/background-zeus-temple.jpg b/frontend/src/scenes/SplashScreen/components/background-zeus-temple.jpg Binary files differindex 5a28e933..5a28e933 100644 --- a/frontend/src/layouts/background-zeus-temple.jpg +++ b/frontend/src/scenes/SplashScreen/components/background-zeus-temple.jpg diff --git a/frontend/src/layouts/logo-7-wonders.png b/frontend/src/scenes/SplashScreen/components/logo-7-wonders.png Binary files differindex 96974d3e..96974d3e 100644 --- a/frontend/src/layouts/logo-7-wonders.png +++ b/frontend/src/scenes/SplashScreen/components/logo-7-wonders.png diff --git a/frontend/src/scenes/SplashScreen/index.js b/frontend/src/scenes/SplashScreen/index.js new file mode 100644 index 00000000..0732b1b3 --- /dev/null +++ b/frontend/src/scenes/SplashScreen/index.js @@ -0,0 +1,42 @@ +import React, { Component } from 'react'; +import { connect } from 'react-redux'; +import { Button, Container, Input } from 'rebass'; +import { actions } from '../../redux/players'; + +import HomeLayout from './components/HomeLayout'; + +class SplashScreen extends Component { + play = e => { + e.preventDefault(); + if (this._username !== undefined) { + this.props.chooseUsername(this._username); + } + }; + + render() { + return ( + <HomeLayout> + <Container> + <Input + name="username" + label="Username" + placeholder="Username" + hideLabel + onChange={e => (this._username = e.target.value)} + /> + <Button backgroundColor="primary" color="white" big onClick={this.play}> + PLAY NOW! + </Button> + </Container> + </HomeLayout> + ); + } +} + +const mapStateToProps = state => ({}); + +const mapDispatchToProps = { + chooseUsername: actions.chooseUsername, +}; + +export default connect(mapStateToProps, mapDispatchToProps)(SplashScreen); diff --git a/frontend/src/scenes/index.js b/frontend/src/scenes/index.js new file mode 100644 index 00000000..83554d48 --- /dev/null +++ b/frontend/src/scenes/index.js @@ -0,0 +1,17 @@ +import React from 'react'; +import { Route, Redirect, Switch } from 'react-router-dom'; + +import SplashScreen from './SplashScreen'; +import Games from './Games'; +import Lobby from './Lobby'; + +const Application = () => ( + <Switch> + <Route path="/splash-screen" component={SplashScreen} /> + <Route path="/games" component={Games} /> + <Route path="/lobby" component={Lobby} /> + <Redirect from="*" to="/splash-screen" /> + </Switch> +); + +export default Application; |