Massive collaborative workshop 23/03/2022
Co-authored-by: SgtPodding <SgtPodding@users.noreply.github.com> Co-authored-by: Felix Albrigtsen <felixalbrigtsen@gmail.com> Co-authored-by: krloer <krloer@users.noreply.github.com>
This commit is contained in:
parent
9056d10117
commit
189a047bd2
File diff suppressed because it is too large
Load Diff
|
@ -31,15 +31,5 @@
|
||||||
<body>
|
<body>
|
||||||
<noscript>You need to enable JavaScript to run this app.</noscript>
|
<noscript>You need to enable JavaScript to run this app.</noscript>
|
||||||
<div id="root"></div>
|
<div id="root"></div>
|
||||||
<!--
|
|
||||||
This HTML file is a template.
|
|
||||||
If you open it directly in the browser, you will see an empty page.
|
|
||||||
|
|
||||||
You can add webfonts, meta tags, or analytics to this file.
|
|
||||||
The build step will place the bundled scripts into the <body> tag.
|
|
||||||
|
|
||||||
To begin the development, run `npm start` or `yarn start`.
|
|
||||||
To create a production bundle, use `npm run build` or `yarn build`.
|
|
||||||
-->
|
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|
|
@ -1,18 +1,35 @@
|
||||||
import * as React from "react";
|
import * as React from "react";
|
||||||
import { AppBar, Typography, Toolbar } from "@mui/material";
|
import { AppBar, Typography, Toolbar, CssBaseline, Button, Box, IconButton } from "@mui/material"
|
||||||
|
import Menu from '@mui/icons-material/Menu'
|
||||||
import HomeImage from "./homeimage";
|
import HomeImage from "./homeimage";
|
||||||
import CssBaseline from '@mui/material/CssBaseline'
|
|
||||||
|
|
||||||
export default function Appbar() {
|
export default function Appbar() {
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<CssBaseline />
|
<CssBaseline />
|
||||||
<AppBar position="relative" color="primary">
|
<Box sx={{ flexGrow: 1 }}>
|
||||||
|
<AppBar position="static">
|
||||||
<Toolbar>
|
<Toolbar>
|
||||||
<HomeImage />
|
<HomeImage />
|
||||||
<Typography>This is an Appbar</Typography>
|
<Typography variant="h6" component="div" sx={{
|
||||||
|
flexGrow: 1,
|
||||||
|
marginLeft: '2vw'
|
||||||
|
}}>
|
||||||
|
Asura Tournaments
|
||||||
|
</Typography>
|
||||||
|
<IconButton
|
||||||
|
size="large"
|
||||||
|
edge="start"
|
||||||
|
color="inherit"
|
||||||
|
aria-label="menu"
|
||||||
|
sx={{ mr: 2 }}
|
||||||
|
>
|
||||||
|
<Menu />
|
||||||
|
</IconButton>
|
||||||
|
{/* <Button color="inherit">Login</Button> */}
|
||||||
</Toolbar>
|
</Toolbar>
|
||||||
</AppBar>
|
</AppBar>
|
||||||
|
</Box>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,7 +5,7 @@ import Button from "@mui/material/Button";
|
||||||
|
|
||||||
export default function ManageButton(props) {
|
export default function ManageButton(props) {
|
||||||
return (
|
return (
|
||||||
<Link to="/tournament/manage" style={{textDecoration:'none'}}>
|
<Link to={`/tournament/${props.tournamentId}/manage`} style={{textDecoration:'none'}}>
|
||||||
<Button className="ManageButton" variant="contained" color="primary">Manage Tournament</Button>
|
<Button className="ManageButton" variant="contained" color="primary">Manage Tournament</Button>
|
||||||
</Link>
|
</Link>
|
||||||
);
|
);
|
||||||
|
|
|
@ -6,7 +6,7 @@ import Button from "@mui/material/Button";
|
||||||
export default function SaveButton(props) {
|
export default function SaveButton(props) {
|
||||||
return (
|
return (
|
||||||
<Link to="/" style={{textDecoration:'none'}}>
|
<Link to="/" style={{textDecoration:'none'}}>
|
||||||
<Button>Save and Exit</Button>
|
<Button variant="outlined" color="primary">Save and Exit</Button>
|
||||||
</Link>
|
</Link>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,52 +2,153 @@ import * as React from "react";
|
||||||
import { BrowserRouter as Router, Link, Route, Routes } from "react-router-dom";
|
import { BrowserRouter as Router, Link, Route, Routes } from "react-router-dom";
|
||||||
import Appbar from "./components/appbar";
|
import Appbar from "./components/appbar";
|
||||||
|
|
||||||
function CreateButton(props) {
|
import { Button, TextField, MenuItem, InputLabel, Select, Container, Slider } from '@mui/material'
|
||||||
return (
|
|
||||||
<Link to="/">
|
function submitTournament(event) {
|
||||||
<button>Create Tournament!</button>
|
event.preventDefault();
|
||||||
</Link>
|
//TODO use refs to get values
|
||||||
);
|
let tournamentName = document.getElementById("nameInput").value;
|
||||||
|
let tournamentDescription = document.getElementById("descriptionInput").value;
|
||||||
|
let tournamentImageFile = document.getElementById("editImage").files[0];
|
||||||
|
let tournamentStartDate = document.getElementById("startDatePicker").value;
|
||||||
|
let tournamentEndDate = document.getElementById("endDatePicker").value;
|
||||||
|
let tournamentMaxTeams = document.getElementById("max-teams-select").value;
|
||||||
|
|
||||||
|
if (!tournamentName || tournamentName == "") {
|
||||||
|
alert("Tournament name cannot be empty");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!tournamentDescription || tournamentDescription == "") {
|
||||||
|
alert("Tournament description cannot be empty");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!tournamentStartDate || tournamentStartDate == "") {
|
||||||
|
alert("Tournament start date cannot be empty");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!tournamentEndDate || tournamentEndDate == "") {
|
||||||
|
alert("Tournament end date cannot be empty");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!tournamentMaxTeams || isNaN(tournamentMaxTeams) || tournamentMaxTeams < 2) {
|
||||||
|
alert("Tournament max teams cannot be empty");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (tournamentStartDate > tournamentEndDate) {
|
||||||
|
alert("Tournament start date cannot be after end date");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
let today = new Date();
|
||||||
|
if (tournamentStartDate < today || tournamentEndDate < today) {
|
||||||
|
alert("Tournament start and end date must be after today");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let formData = new FormData();
|
||||||
|
formData.append("name", tournamentName);
|
||||||
|
formData.append("description", tournamentDescription);
|
||||||
|
// formData.append("image", tournamentImageFile);
|
||||||
|
formData.append("startDate", tournamentStartDate);
|
||||||
|
formData.append("endDate", tournamentEndDate);
|
||||||
|
formData.append("teamLimit", tournamentMaxTeams);
|
||||||
|
let body = new URLSearchParams(formData);
|
||||||
|
|
||||||
|
fetch("http://10.24.1.213:3000/api/tournament/create", {
|
||||||
|
method: "POST",
|
||||||
|
body: body
|
||||||
|
})
|
||||||
|
.then(response => response.json())
|
||||||
|
.then(data => {
|
||||||
|
if (data.status == "OK") {
|
||||||
|
alert("Tournament created successfully");
|
||||||
|
window.location.href = "/";
|
||||||
|
} else {
|
||||||
|
showError(data.data)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(error => showError(error));
|
||||||
|
|
||||||
|
}
|
||||||
|
function showError(error) {
|
||||||
|
alert("Something went wrong. \n" + error);
|
||||||
|
console.error(error);
|
||||||
}
|
}
|
||||||
|
|
||||||
function ParticipantLimit(props) {
|
function TournamentForm(props) {
|
||||||
return (
|
|
||||||
<div>
|
|
||||||
Participant Limit:
|
|
||||||
<select>
|
|
||||||
<option value="4">4</option>
|
|
||||||
<option value="8">8</option>
|
|
||||||
<option value="16">16</option>
|
|
||||||
<option value="16">32</option>
|
|
||||||
<option value="64">64</option>
|
|
||||||
<option value="128">128</option>
|
|
||||||
<option value="256">256</option>
|
|
||||||
</select>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
function CreateForm(props) {
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<form>
|
<form>
|
||||||
<label for="name">Tournament Name: <input type="text" id="name" /></label>
|
<Container maxWidth="md">
|
||||||
|
<InputLabel htmlFor="nameInput">Tournament Name: </InputLabel>
|
||||||
|
<TextField type="text" id="nameInput" variant="filled" label="Tournament Name" />
|
||||||
|
<InputLabel htmlFor="descriptionInput">Description: </InputLabel>
|
||||||
|
<TextField type="text" id="descriptionInput" variant="filled" label="Description"/>
|
||||||
|
<InputLabel htmlFor="editImage">
|
||||||
|
Tournament Image:
|
||||||
<br />
|
<br />
|
||||||
<label for="description">Description:</label>
|
<Button variant="outlined" component="span" color="primary">
|
||||||
<input type="text" id="description" />
|
Upload
|
||||||
<br />
|
</Button>
|
||||||
<label for="image">Tournament Image:</label>
|
</InputLabel>
|
||||||
<input
|
<input
|
||||||
type="file"
|
type="file"
|
||||||
id="image"
|
id="editImage"
|
||||||
accept="image/png, image/jpeg, image/jpg"
|
accept="image/png, image/jpeg, image/jpg, image/gif, image/svg"
|
||||||
|
style={{ display: 'none' }}
|
||||||
/>
|
/>
|
||||||
<br />
|
<InputLabel htmlFor="startDatePicker">Start Time:</InputLabel>
|
||||||
<label for="date">Start Date:</label>
|
<TextField type="datetime-local" id="startDatePicker" />
|
||||||
<input type="date" id="date" />
|
|
||||||
<input type="time" id="time" />
|
<InputLabel htmlFor="endDatePicker">End Time:</InputLabel>
|
||||||
<br />
|
<TextField type="datetime-local" id="endDatePicker" />
|
||||||
|
|
||||||
|
<InputLabel id="max-teams-label">Maximum number of teams</InputLabel>
|
||||||
|
{/* <Select
|
||||||
|
labelId="max-teams-label"
|
||||||
|
id="max-teams-select"
|
||||||
|
onChange={(event) => {
|
||||||
|
console.log(event.target.value);
|
||||||
|
} }
|
||||||
|
value={8}
|
||||||
|
label="Max Teams"
|
||||||
|
>
|
||||||
|
<MenuItem value={2}>2</MenuItem>
|
||||||
|
<MenuItem value={4}>4</MenuItem>
|
||||||
|
<MenuItem value={8}>8</MenuItem>
|
||||||
|
<MenuItem value={16}>16</MenuItem>
|
||||||
|
<MenuItem value={32}>32</MenuItem>
|
||||||
|
<MenuItem value={64}>64</MenuItem>
|
||||||
|
<MenuItem value={128}>128</MenuItem>
|
||||||
|
</Select> */}
|
||||||
|
<select id="max-teams-select">
|
||||||
|
<option value={2}>2</option>
|
||||||
|
<option value={4}>4</option>
|
||||||
|
<option value={8}>8</option>
|
||||||
|
<option value={16}>16</option>
|
||||||
|
<option value={32}>32</option>
|
||||||
|
<option value={64}>64</option>
|
||||||
|
<option value={128}>128</option>
|
||||||
|
</select>
|
||||||
|
<Slider
|
||||||
|
aria-label="Teams"
|
||||||
|
defaultValue={1}
|
||||||
|
// value={value}
|
||||||
|
// onChange={console.log(value)}
|
||||||
|
valueLabelDisplay="auto"
|
||||||
|
step={1}
|
||||||
|
marks
|
||||||
|
min={1}
|
||||||
|
max={7}
|
||||||
|
id="max-teams-slider"
|
||||||
|
>
|
||||||
|
</Slider>
|
||||||
|
|
||||||
|
{/* go brrrr */}
|
||||||
|
<br /><br />
|
||||||
|
|
||||||
|
<Button type="submit" variant="contained" onClick={submitTournament} color="primary">Create Tournament!</Button>
|
||||||
|
</Container>
|
||||||
</form>
|
</form>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
@ -57,9 +158,7 @@ export default function CreateTournament(props) {
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<Appbar />
|
<Appbar />
|
||||||
<CreateForm />
|
<TournamentForm />
|
||||||
<ParticipantLimit />
|
|
||||||
<CreateButton />
|
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,18 +9,21 @@ import TournamentMatches from "./tournamentmatches";
|
||||||
import TeamEditor from "./teameditor";
|
import TeamEditor from "./teameditor";
|
||||||
import Appbar from './components/appbar';
|
import Appbar from './components/appbar';
|
||||||
|
|
||||||
import Button from "@mui/material/Button";
|
import { Button, Container, Typography, Grid, Box } from "@mui/material";
|
||||||
import Container from "@mui/material/Container";
|
import { Card, CardActions,CardACtionsArea, CardContent, CardHeader, CardMedia, Collapse, Paper } from "@mui/material";
|
||||||
import CssBaseline from "@mui/material/CssBaseline";
|
import AddCircleIcon from '@mui/icons-material/AddCircle';
|
||||||
import Typography from "@mui/material/Typography";
|
import { maxWidth } from "@mui/system";
|
||||||
import Grid from "@mui/material/Grid";
|
|
||||||
import Box from "@mui/material/Box";
|
|
||||||
|
|
||||||
function CreateButton(props) {
|
function CreateButton(props) {
|
||||||
return (
|
return (
|
||||||
<Link to="/create" style={{ textDecoration: "none" }}>
|
<Link to="/create" style={{ textDecoration: "none" }}>
|
||||||
<Button variant="contained" color="primary">
|
<Button variant="contained" color="success" style={{ margin: '2.5% 0 0 0'}}>
|
||||||
|
<Box sx={{
|
||||||
|
marginRight: '2%',
|
||||||
|
}}>
|
||||||
Create Tournament
|
Create Tournament
|
||||||
|
</Box>
|
||||||
|
<AddCircleIcon />
|
||||||
</Button>
|
</Button>
|
||||||
</Link>
|
</Link>
|
||||||
);
|
);
|
||||||
|
@ -36,38 +39,92 @@ function OverviewButton(props) {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function ListElement(props) {
|
function TournamentListItem(props) {
|
||||||
return (
|
return (
|
||||||
<Container maxWidth="lg" align="start">
|
<Container maxWidth="lg" align="start" sx={{
|
||||||
<Grid container spacing={2}>
|
margin:'2.5% 0'
|
||||||
<Grid item xs={5}>
|
}}>
|
||||||
<Typography noWrap>
|
<Paper elevation={8}>
|
||||||
{props.name}, {props.competitors} competitors, Date: {props.date}
|
<Card>
|
||||||
|
<CardMedia
|
||||||
|
component="img"
|
||||||
|
alt="tournament image"
|
||||||
|
height="140"
|
||||||
|
image="https://source.unsplash.com/random"
|
||||||
|
/>
|
||||||
|
<CardContent>
|
||||||
|
<Typography variant="h3" component="div" align="center">
|
||||||
|
{props.tournament.name}
|
||||||
</Typography>
|
</Typography>
|
||||||
</Grid>
|
<Typography variant="h5" color="text.primary">
|
||||||
<Grid item>
|
{props.tournament.description}
|
||||||
<ManageButton />
|
</Typography>
|
||||||
</Grid>
|
<Typography variant="body2" color="text.secondary">
|
||||||
<Grid item>
|
Start: {props.tournament.startTime.toLocaleString()}
|
||||||
|
</Typography>
|
||||||
|
<Typography variant="body2" color="text.secondary">
|
||||||
|
End: {props.tournament.endTime.toLocaleString()}
|
||||||
|
</Typography>
|
||||||
|
<Typography variant="h5" color="text.primary" gutterBottom>
|
||||||
|
Players todo / {props.tournament.teamLimit}
|
||||||
|
</Typography>
|
||||||
|
<Box sx={{
|
||||||
|
margin: 'auto',
|
||||||
|
display: 'flex',
|
||||||
|
flexDirection: 'row',
|
||||||
|
justifyContent: 'center',
|
||||||
|
}} component="span">
|
||||||
|
<Box sx={{
|
||||||
|
margin: '0 2% 0 2'
|
||||||
|
}}>
|
||||||
|
<ManageButton tournamentId={props.tournament.id}/>
|
||||||
|
</Box>
|
||||||
|
<Box sx={{
|
||||||
|
margin: '0 2% 0 2%'
|
||||||
|
}}>
|
||||||
<OverviewButton />
|
<OverviewButton />
|
||||||
</Grid>
|
</Box>
|
||||||
</Grid>
|
</Box>
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
</Paper>
|
||||||
</Container>
|
</Container>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function TournamentList() {
|
function TournamentList() {
|
||||||
let [data, setData] = React.useState(null);
|
let [data, setData] = React.useState(null);
|
||||||
|
let [tournamentList, setTournamentList] = React.useState([]);
|
||||||
|
|
||||||
React.useEffect(() => {
|
React.useEffect(() => {
|
||||||
fetch("https://jsonplaceholder.typicode.com/todos/1")
|
fetch("http://10.24.1.213:3000/api/tournament/getTournaments")
|
||||||
.then((res) => res.json())
|
.then(res => res.json())
|
||||||
.then((data) => {
|
.then(data => {
|
||||||
setData(data.data);
|
|
||||||
|
if (data.status != "OK") {
|
||||||
|
// Do your error thing
|
||||||
|
console.error(data);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let tournaments = Object.values(data.data);
|
||||||
|
for (let i = 0; i < tournaments.length; i++) {
|
||||||
|
tournaments[i].startTime = new Date(tournaments[i].startTime);
|
||||||
|
tournaments[i].endTime = new Date(tournaments[i].endTime);
|
||||||
|
}
|
||||||
|
|
||||||
|
setTournamentList(tournaments);
|
||||||
})
|
})
|
||||||
.catch((err) => console.log(err.message));
|
.catch((err) => console.log(err.message));
|
||||||
}, []);
|
}, []);
|
||||||
return <div>{data && data.map((data, i) => <div>{i}</div>)}</div>;
|
|
||||||
|
return <>
|
||||||
|
{/* {tournamentList && tournamentList.map((tournamentObject, i) => <TournamentListItem key={tournamentObject.id.toString()} name={tournamentObject.name} description={tournamentObject.description} startDate={tournamentObject.startTime} endDate={tournamentObject.endTime} teamLimit={tournamentObject.teamLimit} />)} */}
|
||||||
|
{tournamentList && tournamentList.map((tournamentObject) => <TournamentListItem key={tournamentObject.id.toString()} tournament={tournamentObject} />)}
|
||||||
|
|
||||||
|
</>;
|
||||||
}
|
}
|
||||||
|
|
||||||
//<ListElement name={data[i].name} competitors={data[i].teamLimit} date={data[i].startTime}/>
|
//<ListElement name={data[i].name} competitors={data[i].teamLimit} date={data[i].startTime}/>
|
||||||
|
|
||||||
function Home() {
|
function Home() {
|
||||||
|
@ -75,10 +132,12 @@ function Home() {
|
||||||
<React.StrictMode>
|
<React.StrictMode>
|
||||||
<Appbar />
|
<Appbar />
|
||||||
<main>
|
<main>
|
||||||
<Container>
|
<Container align="center">
|
||||||
<Box>
|
|
||||||
<CreateButton />
|
<CreateButton />
|
||||||
</Box>
|
<Typography variant="h2" style={{margin:'2% 0'}}>
|
||||||
|
Tournaments
|
||||||
|
</Typography>
|
||||||
|
<TournamentList />
|
||||||
{/* <ListElement
|
{/* <ListElement
|
||||||
name="Weekend Warmup"
|
name="Weekend Warmup"
|
||||||
competitors="16"
|
competitors="16"
|
||||||
|
@ -94,7 +153,7 @@ function Home() {
|
||||||
competitors="64"
|
competitors="64"
|
||||||
date="01.05.2022"
|
date="01.05.2022"
|
||||||
/> */}
|
/> */}
|
||||||
<TournamentList />
|
|
||||||
</Container>
|
</Container>
|
||||||
</main>
|
</main>
|
||||||
<footer className="footer"></footer>
|
<footer className="footer"></footer>
|
||||||
|
@ -108,8 +167,8 @@ export default function App() {
|
||||||
<Routes>
|
<Routes>
|
||||||
<Route path="/" element={<Home />} />
|
<Route path="/" element={<Home />} />
|
||||||
<Route path="/create" element={<CreateTournament />} />
|
<Route path="/create" element={<CreateTournament />} />
|
||||||
<Route path="/tournament" element={<TournamentOverview />} />
|
<Route path="/tournament/" element={<TournamentOverview />} />
|
||||||
<Route path="/tournament/manage" element={<TournamentManager />} />
|
<Route path="/tournament/:id/manage" element={<TournamentManager />} />
|
||||||
<Route path="/tournament/teams" element={<TeamEditor />} />
|
<Route path="/tournament/teams" element={<TeamEditor />} />
|
||||||
<Route path="/tournament/matches" element={<TournamentMatches />} />
|
<Route path="/tournament/matches" element={<TournamentMatches />} />
|
||||||
<Route
|
<Route
|
||||||
|
|
|
@ -19,6 +19,13 @@ code {
|
||||||
}
|
}
|
||||||
|
|
||||||
.mainIcon{
|
.mainIcon{
|
||||||
height: 40px;
|
height: 60px;
|
||||||
width: 40px;
|
width: 60px;
|
||||||
|
border-radius: 50%;
|
||||||
|
/* border: 5px dotted salmon; */
|
||||||
|
border: 3px solid darkslateblue;
|
||||||
|
background-color: white;
|
||||||
|
margin: 5px;
|
||||||
|
margin-bottom: 0;
|
||||||
|
/* margin: 50% calc(2vw + 50%) 50% 50%; */
|
||||||
}
|
}
|
|
@ -3,29 +3,58 @@ import { BrowserRouter as Router, Link, Route, Routes } from "react-router-dom";
|
||||||
import { AlertContainer, alert } from "react-custom-alert";
|
import { AlertContainer, alert } from "react-custom-alert";
|
||||||
import Appbar from './components/appbar';
|
import Appbar from './components/appbar';
|
||||||
import SaveButton from "./components/savebutton";
|
import SaveButton from "./components/savebutton";
|
||||||
|
import { useParams } from 'react-router-dom'
|
||||||
|
|
||||||
|
import { Button, TextField, MenuItem, InputLabel, Select, Container, Slider } from '@mui/material'
|
||||||
|
|
||||||
function ManageTournament(props) {
|
function ManageTournament(props) {
|
||||||
|
const { id } = useParams()
|
||||||
|
let [tournamentInfo, setTournamentInfo] = React.useState([]);
|
||||||
|
|
||||||
|
React.useEffect(() => {
|
||||||
|
fetch(`http://10.24.1.213:3000/api/tournament/${id}`)
|
||||||
|
.then(res => res.json())
|
||||||
|
.then(data => {
|
||||||
|
|
||||||
|
if (data.status != "OK") {
|
||||||
|
// Do your error thing
|
||||||
|
console.error(data.data);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
setTournamentInfo(data.data);
|
||||||
|
document.getElementById("editName").value = data.data.name;
|
||||||
|
})
|
||||||
|
.catch((err) => console.log(err.message));
|
||||||
|
}, []);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<form>
|
<form>
|
||||||
<label>Edit name: </label>
|
<Container>
|
||||||
<input type="text" id="editName" />
|
<InputLabel htmlFor="editName">Edit name: </InputLabel>
|
||||||
|
<TextField type="text" id="editName" />
|
||||||
|
<InputLabel htmlFor="editDesc">Edit description: </InputLabel>
|
||||||
|
<TextField type="text" id="editDesc" />
|
||||||
|
<InputLabel htmlFor="editImage">
|
||||||
|
Edit image:
|
||||||
<br />
|
<br />
|
||||||
<label>Edit description: </label>
|
<Button variant="outlined" component="span" color="primary">
|
||||||
<input type="text" id="editDesc" />
|
Upload
|
||||||
<br />
|
</Button>
|
||||||
<label>Edit image: </label>
|
</InputLabel>
|
||||||
<input
|
<input
|
||||||
type="file"
|
type="file"
|
||||||
id="editImage"
|
id="editImage"
|
||||||
accept="image/png, image/jpeg, image/jpg"
|
accept="image/png, image/jpeg, image/jpg, image/gif, image/svg"
|
||||||
|
style={{ display: 'none' }}
|
||||||
/>
|
/>
|
||||||
<br />
|
<InputLabel htmlFor="editStartDate">Edit Start Time:</InputLabel>
|
||||||
<label>Edit start time: </label>
|
<TextField type="datetime-local" id="editStartDate" />
|
||||||
<input type="date" id="editDate" />
|
|
||||||
<input type="time" id="editTime" />
|
<InputLabel htmlFor="editEndDate">Edit End Time:</InputLabel>
|
||||||
<br />
|
<TextField type="datetime-local" id="editEndDate" />
|
||||||
<br />
|
</Container>
|
||||||
</form>
|
</form>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
@ -34,7 +63,7 @@ function ManageTournament(props) {
|
||||||
function AnnounceButton(props) {
|
function AnnounceButton(props) {
|
||||||
return (
|
return (
|
||||||
<Link to="/tournament/manage/announcement">
|
<Link to="/tournament/manage/announcement">
|
||||||
<button id="sendAnnon">Send Tournament Announcement</button>
|
<Button id="sendAnnon" variant="outlined" color="primary">Send Tournament Announcement</Button>
|
||||||
</Link>
|
</Link>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -50,14 +79,13 @@ function InviteButton(props) {
|
||||||
const alertSuccess = () =>
|
const alertSuccess = () =>
|
||||||
alert({ message: "Copied to clipboard.", type: "success" });
|
alert({ message: "Copied to clipboard.", type: "success" });
|
||||||
return (
|
return (
|
||||||
<button id="createInvLink" onClick={event}>
|
<Button id="createInvLink" onClick={event} variant="outlined" color="primary">
|
||||||
Copy Invite Link
|
Copy Invite Link
|
||||||
</button>
|
</Button>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
//navigator.clipboard.writeText("discord.gg/asura")
|
export default function TournamentManager(props) {
|
||||||
export default function TournamentManager() {
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<Appbar />
|
<Appbar />
|
||||||
|
|
|
@ -1,11 +1,37 @@
|
||||||
import * as React from "react";
|
import * as React from "react";
|
||||||
import { BrowserRouter as Router, Link, Route, Routes } from "react-router-dom";
|
import { BrowserRouter as Router, Link, Route, Routes } from "react-router-dom";
|
||||||
import Appbar from './components/appbar';
|
import Appbar from './components/appbar';
|
||||||
|
import { Button, TextField, MenuItem, InputLabel, Select, Container, Slider } from '@mui/material'
|
||||||
|
|
||||||
|
function TeamList() {
|
||||||
|
let teams = {"team 1": ["tom", "eric", "gustav"], "team 2": ["emma", "mari", "ida"],"team 3": ["ola", "ole", "ost"],"team 4": ["christine", "kristine", "kristhine"]}
|
||||||
|
return (<div>
|
||||||
|
<ul>
|
||||||
|
{Object.entries(teams).map(([team, players]) => <li key={team} ><button>{team}</button></li>)}
|
||||||
|
</ul>
|
||||||
|
</div>)
|
||||||
|
}
|
||||||
|
|
||||||
|
function TeamChanger() {
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<form>
|
||||||
|
<InputLabel htmlFor="teamInput">Team Name: </InputLabel>
|
||||||
|
<TextField type="text" id="teamInput" variant="filled" label="Team Name:" />
|
||||||
|
<InputLabel htmlFor="membersInput">Team Members: </InputLabel>
|
||||||
|
<TextField type="text" id="membersInput" variant="filled" label="Members:"/>
|
||||||
|
</form>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
export default function TeamEditor() {
|
export default function TeamEditor() {
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<Appbar />
|
<Appbar />
|
||||||
|
<TeamChanger />
|
||||||
|
<TeamList />
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,10 +2,18 @@ import * as React from "react";
|
||||||
import { BrowserRouter as Router, Link, Route, Routes } from "react-router-dom";
|
import { BrowserRouter as Router, Link, Route, Routes } from "react-router-dom";
|
||||||
import Appbar from './components/appbar';
|
import Appbar from './components/appbar';
|
||||||
|
|
||||||
|
function MatchHistory() {
|
||||||
|
|
||||||
|
return(
|
||||||
|
`Hei`
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
export default function TournamentMatches() {
|
export default function TournamentMatches() {
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<Appbar />
|
<Appbar />
|
||||||
|
<MatchHistory />
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,38 +3,54 @@ import { BrowserRouter as Router, Link, Route, Routes } from "react-router-dom";
|
||||||
import ManageButton from "./components/managebutton";
|
import ManageButton from "./components/managebutton";
|
||||||
import Appbar from './components/appbar';
|
import Appbar from './components/appbar';
|
||||||
|
|
||||||
function RenderBrackets() {
|
// Test data
|
||||||
|
// {"status":"OK","data":
|
||||||
|
// [
|
||||||
|
// {"id":1,
|
||||||
|
// "tournamentId":1,
|
||||||
|
// "parentMatchId":null,
|
||||||
|
// "team1Id":null,
|
||||||
|
// "team2Id":null,
|
||||||
|
// "winnerId":null}
|
||||||
|
|
||||||
|
function RenderBrackets(params) {
|
||||||
|
let teams = 16;
|
||||||
|
let groups = Math.log2(teams);
|
||||||
|
// Number of matches, python equivalent: sum([2**groupNumber for groupNumber in range(groups)])
|
||||||
|
let matches = [...Array(groups).keys()].map(num => Math.pow(2, num)).reduce((a, b) => a + b);
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
brackets = []
|
{new Array(groups).map((group, i) => {
|
||||||
knownTeams = [2,4,8,16,32,64,128,256]
|
return (
|
||||||
|
<div>Group {i}</div>
|
||||||
|
);
|
||||||
|
})}
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function ViewTournament(params) {
|
function OverviewButtons(params) {
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<div id="touOverview"></div>
|
<div id="touOverview"></div>
|
||||||
<Link to="/tournament/teams">
|
<Link to="/tournament/teams">
|
||||||
<button id="manageTeams">Manage Teams </button>
|
<button id="manageTeams">Manage Teams </button>
|
||||||
</Link>
|
</Link>
|
||||||
<Link to="/tournament/matches">
|
{/* <Link to="/tournament/matches">
|
||||||
<button id="touMaches">Tournament Matches</button>
|
<button id="touMatches">Tournament Matches</button>
|
||||||
</Link>
|
</Link> */}
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
export default function TournamentOverview(props) {
|
export default function TournamentOverview(props) {
|
||||||
|
// Use-effect hook here
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<Appbar />
|
<Appbar />
|
||||||
<ManageButton />
|
<ManageButton />
|
||||||
<ViewTournament />
|
<RenderBrackets />
|
||||||
|
<OverviewButtons />
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue