Skip to content

Commit 72f3684

Browse files
feat: clean up broadcast page
1 parent a2629cd commit 72f3684

1 file changed

Lines changed: 76 additions & 52 deletions

File tree

src/pages/broadcast/index.tsx

Lines changed: 76 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -9,24 +9,38 @@ import { AuthenticatedWrapper } from 'src/components/Common/AuthenticatedWrapper
99
import { useBroadcastController } from 'src/hooks/useBroadcastController'
1010
import { Broadcast } from 'src/types'
1111

12+
const fadeInUp = {
13+
initial: { opacity: 0, y: 15 },
14+
animate: { opacity: 1, y: 0 },
15+
transition: { duration: 0.3, ease: 'easeOut' },
16+
}
17+
18+
const staggerContainer = {
19+
animate: {
20+
transition: {
21+
staggerChildren: 0.05,
22+
},
23+
},
24+
}
25+
1226
const BroadcastsPage: NextPage = () => {
1327
const router = useRouter()
14-
const broadcastController = useBroadcastController()
28+
const { broadcastSections, broadcastState, loadBroadcasts } =
29+
useBroadcastController()
1530
const [loading, setLoading] = useState(true)
1631

1732
useEffect(() => {
1833
const loadData = async () => {
1934
try {
20-
await broadcastController.loadBroadcasts()
35+
await loadBroadcasts()
2136
} catch (error) {
2237
console.error('Error loading broadcasts:', error)
2338
} finally {
2439
setLoading(false)
2540
}
2641
}
27-
2842
loadData()
29-
}, [])
43+
}, [loadBroadcasts])
3044

3145
const handleSelectBroadcast = (broadcast: Broadcast) => {
3246
const defaultRound =
@@ -47,32 +61,6 @@ const BroadcastsPage: NextPage = () => {
4761
})
4862
}
4963

50-
const containerVariants = {
51-
hidden: { opacity: 0 },
52-
visible: {
53-
opacity: 1,
54-
transition: {
55-
duration: 0.3,
56-
staggerChildren: 0.1,
57-
},
58-
},
59-
}
60-
61-
const itemVariants = {
62-
hidden: {
63-
opacity: 0,
64-
y: 20,
65-
},
66-
visible: {
67-
opacity: 1,
68-
y: 0,
69-
transition: {
70-
duration: 0.4,
71-
ease: [0.25, 0.46, 0.45, 0.94],
72-
},
73-
},
74-
}
75-
7664
if (loading) {
7765
return (
7866
<>
@@ -97,7 +85,7 @@ const BroadcastsPage: NextPage = () => {
9785
)
9886
}
9987

100-
if (broadcastController.broadcastState.error) {
88+
if (broadcastState.error) {
10189
return (
10290
<>
10391
<Head>
@@ -106,16 +94,20 @@ const BroadcastsPage: NextPage = () => {
10694
<div className="flex min-h-screen items-center justify-center bg-backdrop">
10795
<div className="rounded-lg border border-white/10 bg-background-1 p-6 text-center">
10896
<h2 className="mb-4 text-xl font-semibold text-red-400">
109-
Error Loading Broadcasts
97+
Failed to Load Broadcasts
11098
</h2>
11199
<p className="mb-4 text-secondary">
112-
{broadcastController.broadcastState.error}
100+
Unable to connect to Lichess. Please check your internet
101+
connection and try again.
113102
</p>
114103
<button
115-
onClick={() => window.location.reload()}
104+
onClick={() => {
105+
setLoading(true)
106+
loadBroadcasts().finally(() => setLoading(false))
107+
}}
116108
className="rounded border border-human-4/30 bg-human-4 px-4 py-2 text-white transition-all duration-200 hover:border-human-4/50 hover:bg-human-4/80"
117109
>
118-
Try Again
110+
Retry
119111
</button>
120112
</div>
121113
</div>
@@ -141,13 +133,14 @@ const BroadcastsPage: NextPage = () => {
141133
'radial-gradient(ellipse 75% 60% at center top, rgba(239, 68, 68, 0.08) 0%, transparent 60%)',
142134
}}
143135
/>
136+
144137
<motion.div
145138
className="container relative mx-auto px-6 py-8"
146-
variants={containerVariants}
147-
initial="hidden"
148-
animate="visible"
139+
initial="initial"
140+
animate="animate"
141+
variants={staggerContainer}
149142
>
150-
<motion.div variants={itemVariants} className="mb-8 text-center">
143+
<motion.div className="mb-8 text-center" variants={fadeInUp}>
151144
<h1 className="mb-2 text-3xl font-bold text-white">
152145
Live Broadcasts
153146
</h1>
@@ -156,10 +149,10 @@ const BroadcastsPage: NextPage = () => {
156149
</p>
157150
</motion.div>
158151

159-
{broadcastController.broadcastSections.length === 0 ? (
152+
{broadcastSections.length === 0 ? (
160153
<motion.div
161-
variants={itemVariants}
162154
className="flex flex-col items-center justify-center py-16 text-center"
155+
variants={fadeInUp}
163156
>
164157
<span className="material-symbols-outlined mb-4 !text-6xl text-white/60">
165158
live_tv
@@ -171,19 +164,33 @@ const BroadcastsPage: NextPage = () => {
171164
There are currently no ongoing tournaments available.
172165
</p>
173166
<button
174-
onClick={() => broadcastController.loadBroadcasts()}
167+
onClick={() => {
168+
setLoading(true)
169+
loadBroadcasts().finally(() => setLoading(false))
170+
}}
175171
className="mt-4 rounded border border-human-4/30 bg-human-4 px-4 py-2 text-white transition-all duration-200 hover:border-human-4/50 hover:bg-human-4/80"
176172
>
177173
Refresh
178174
</button>
179175
</motion.div>
180176
) : (
181-
<div className="space-y-6">
182-
{broadcastController.broadcastSections.map((section) => (
177+
<motion.div className="space-y-6" variants={staggerContainer}>
178+
{broadcastSections.map((section, sectionIndex) => (
183179
<motion.div
184180
key={section.type}
185-
variants={itemVariants}
186181
className="space-y-3"
182+
variants={{
183+
initial: { opacity: 0, y: 15 },
184+
animate: {
185+
opacity: 1,
186+
y: 0,
187+
transition: {
188+
duration: 0.25,
189+
ease: 'easeOut',
190+
delay: sectionIndex * 0.2,
191+
},
192+
},
193+
}}
187194
>
188195
<h2 className="flex items-center gap-2 text-xl font-semibold text-white">
189196
{section.title}
@@ -198,12 +205,22 @@ const BroadcastsPage: NextPage = () => {
198205
)}
199206
</h2>
200207

201-
<div
208+
<motion.div
202209
className={
203210
section.type === 'official-active'
204211
? 'flex flex-wrap gap-4'
205212
: 'grid gap-4 sm:grid-cols-2 md:grid-cols-3 lg:grid-cols-4 xl:grid-cols-5'
206213
}
214+
initial="initial"
215+
animate="animate"
216+
variants={{
217+
animate: {
218+
transition: {
219+
staggerChildren: 0.03,
220+
delayChildren: sectionIndex * 0.2 + 0.15,
221+
},
222+
},
223+
}}
207224
>
208225
{section.broadcasts.map((broadcast) => {
209226
const ongoingRounds = broadcast.rounds.filter(
@@ -218,12 +235,19 @@ const BroadcastsPage: NextPage = () => {
218235
return (
219236
<motion.div
220237
key={broadcast.tour.id}
221-
variants={itemVariants}
222238
className={`from-white/8 to-white/4 hover:from-white/12 hover:to-white/6 group relative flex flex-col overflow-hidden rounded-lg border border-white/10 bg-gradient-to-br backdrop-blur-md transition-all duration-300 hover:border-white/20 ${
223239
section.type === 'official-active'
224240
? 'w-[280px]'
225241
: ''
226242
}`}
243+
variants={{
244+
initial: { opacity: 0, y: 15 },
245+
animate: {
246+
opacity: 1,
247+
y: 0,
248+
transition: { duration: 0.2, ease: 'easeOut' },
249+
},
250+
}}
227251
>
228252
<div className="flex flex-1 flex-col gap-3 p-4">
229253
<div className="flex items-start justify-between gap-3">
@@ -267,7 +291,7 @@ const BroadcastsPage: NextPage = () => {
267291
<button
268292
onClick={() => handleSelectBroadcast(broadcast)}
269293
disabled={!hasOngoingRounds && !isPast}
270-
className={`border-t py-2 text-sm font-medium transition-all duration-300 ${
294+
className={`border-t py-2 text-sm font-medium tracking-wide transition-all duration-300 ${
271295
hasOngoingRounds
272296
? 'border-red-500/30 bg-red-500/20 text-red-400 group-hover:bg-red-500/30'
273297
: isPast
@@ -284,18 +308,18 @@ const BroadcastsPage: NextPage = () => {
284308
</motion.div>
285309
)
286310
})}
287-
</div>
311+
</motion.div>
288312
</motion.div>
289313
))}
290-
</div>
314+
</motion.div>
291315
)}
292316

293317
<motion.div
294-
variants={itemVariants}
295318
className="mt-8 text-center text-xs text-white/60"
319+
variants={fadeInUp}
296320
>
297321
<p>
298-
Broadcasts powered by{' '}
322+
Broadcasts streamed from{' '}
299323
<a
300324
href="https://lichess.org"
301325
target="_blank"

0 commit comments

Comments
 (0)