myheats

Live heats, scoring and leaderboard for sport events
git clone https://git.in0rdr.ch/myheats.git
Log | Files | Refs | Pull requests | README | LICENSE

commit 336249f26ac25d56f358cfd53320c6c67d4ff558
parent e2f243718ec2cdb04267fba22b2167d02dba0bcc
Author: Andreas Gruhler <andreas.gruhler@adfinis.com>
Date:   Wed,  5 Apr 2023 00:27:39 +0200

feat(leaderboard): loading indicator

Diffstat:
Msrc/Heats.js | 2+-
Msrc/Leaderboard.js | 19+++++++++++++++----
2 files changed, 16 insertions(+), 5 deletions(-)

diff --git a/src/Heats.js b/src/Heats.js @@ -25,7 +25,7 @@ function HeatForm({session}) { const heatList = await supabase.from('heats').select() if (heatList.error === null) setHeats(heatList.data) - setLoading(false) + setLoading(false) })(); }, []) diff --git a/src/Leaderboard.js b/src/Leaderboard.js @@ -134,6 +134,7 @@ async function newHeatFromLeaderboard(e, leaderboard, rankingComp, selectHeatRef } function Leaderboard() { + const [loading, setLoading] = useState(false) const [leaderboard, setLeaderboard] = useState([]) const [heatSelection, setHeatSelection] = useState([]) const [heats, setHeats] = useState([]) @@ -192,38 +193,48 @@ function Leaderboard() { useEffect(() => { (async () => { + setLoading(true) + + // load initial list of heats const heatList = await supabase.from('heats').select() setHeats(heatList.data) + setLoading(false) })(); }, []); useEffect(() => { (async () => { + setLoading(true) + // reload entire leaderboard when heat selection is changed const ratingSummary = await getRatingSummary(heatSelection.map(h => h.value)) setLeaderboard(ratingSummary) + setLoading(false) })(); }, [heatSelection]); useEffect(() => { // subscribe to ratings from judges and - const ratingsChannel = supabase.channel('ratings') - ratingsChannel.on( + const channel = supabase.channel('ratings') + channel.on( 'postgres_changes', { event: '*', table: 'ratings', }, async (payload) => { + setLoading(true) + // todo: reload only required ratings const ratingSummary = await getRatingSummary(heatSelection.map(h => h.value)) setLeaderboard(ratingSummary) + setLoading(false) } ).subscribe() // remove subscription return function cleanup() { - supabase.removeChannel(ratingsChannel) + supabase.removeChannel(channel) } }, [heatSelection]); @@ -266,7 +277,7 @@ function Leaderboard() { )}>Create</button> </form> </div> - <h1>Leaderboard</h1> + <h1>Leaderboard <button disabled={!loading}>{loading ? '🔄 loading' : ''}</button></h1> </header> <table className='leaderboard'> <thead>