]> git.localhorst.tv Git - alttp.git/blob - resources/js/components/pages/Tournament.js
server calculated scoring
[alttp.git] / resources / js / components / pages / Tournament.js
1 import axios from 'axios';
2 import React, { useEffect, useState } from 'react';
3 import { useParams } from 'react-router-dom';
4
5 import ErrorBoundary from '../common/ErrorBoundary';
6 import ErrorMessage from '../common/ErrorMessage';
7 import Loading from '../common/Loading';
8 import NotFound from '../pages/NotFound';
9 import Detail from '../tournament/Detail';
10 import {
11         patchParticipant,
12         patchResult,
13         patchRound,
14         patchUser,
15         sortParticipants,
16 } from '../../helpers/Tournament';
17
18 const Tournament = () => {
19         const params = useParams();
20         const { id } = params;
21
22         const [error, setError] = useState(null);
23         const [loading, setLoading] = useState(true);
24         const [tournament, setTournament] = useState(null);
25
26         useEffect(() => {
27                 setLoading(true);
28                 axios
29                         .get(`/api/tournaments/${id}`)
30                         .then(response => {
31                                 setError(null);
32                                 setLoading(false);
33                                 setTournament(sortParticipants(response.data));
34                         })
35                         .catch(error => {
36                                 setError(error);
37                                 setLoading(false);
38                                 setTournament(null);
39                         });
40         }, [id]);
41
42         useEffect(() => {
43                 window.Echo.channel(`Tournament.${id}`)
44                         .listen('ParticipantChanged', e => {
45                                 if (e.participant) {
46                                         setTournament(tournament => patchParticipant(tournament, e.participant));
47                                 }
48                         })
49                         .listen('ResultChanged', e => {
50                                 if (e.result) {
51                                         setTournament(tournament => patchResult(tournament, e.result));
52                                 }
53                         })
54                         .listen('RoundAdded', e => {
55                                 if (e.round) {
56                                         setTournament(tournament => ({
57                                                 ...tournament,
58                                                 rounds: [e.round, ...tournament.rounds],
59                                         }));
60                                 }
61                         })
62                         .listen('RoundChanged', e => {
63                                 if (e.round) {
64                                         setTournament(tournament => patchRound(tournament, e.round));
65                                 }
66                         })
67                         .listen('TournamentChanged', e => {
68                                 if (e.tournament) {
69                                         setTournament(tournament => ({ ...tournament, ...e.tournament }));
70                                 }
71                         });
72                 return () => {
73                         window.Echo.leave(`Tournament.${id}`);
74                 };
75         }, [id]);
76
77         useEffect(() => {
78                 const cb = (e) => {
79                         if (e.user) {
80                                 setTournament(tournament => patchUser(tournament, e.user));
81                         }
82                 };
83                 window.Echo.channel('App.Control')
84                         .listen('UserChanged', cb);
85                 return () => {
86                         window.Echo.channel('App.Control')
87                                 .stopListening('UserChanged', cb);
88                 };
89         }, []);
90
91         if (loading) {
92                 return <Loading />;
93         }
94
95         if (error) {
96                 return <ErrorMessage error={error} />;
97         }
98
99         if (!tournament) {
100                 return <NotFound />;
101         }
102
103         const addRound = async () => {
104                 await axios.post('/api/rounds', { tournament_id: tournament.id });
105         };
106
107         return <ErrorBoundary>
108                 <Detail addRound={addRound} tournament={tournament} />
109         </ErrorBoundary>;
110 };
111
112 export default Tournament;