From f78b0583034f116f7acefca7bfe5ed2928b6efbd Mon Sep 17 00:00:00 2001 From: cediackermann Date: Mon, 20 Apr 2026 18:27:24 +0200 Subject: [PATCH] refactor: update SL departure and clock components to respect AlwaysOn mode --- src/components/atoms/LineBadge.tsx | 22 +++--------- src/components/molecules/Clock.tsx | 40 ++++++++++++++-------- src/components/molecules/DepartureItem.tsx | 14 ++++---- src/components/organisms/DepartureList.tsx | 16 +++------ 4 files changed, 41 insertions(+), 51 deletions(-) diff --git a/src/components/atoms/LineBadge.tsx b/src/components/atoms/LineBadge.tsx index 6b67747..6a3a1f7 100644 --- a/src/components/atoms/LineBadge.tsx +++ b/src/components/atoms/LineBadge.tsx @@ -1,17 +1,5 @@ -export const LineBadge = ({ designation, mode }: { designation: string; mode: string }) => { - const getColor = (mode: string) => { - switch (mode) { - case 'METRO': return 'bg-sl-blue'; - case 'BUS': return 'bg-sl-red'; - case 'TRAM': return 'bg-sl-green'; - case 'TRAIN': return 'bg-sl-orange'; - default: return 'bg-gray-600'; - } - }; - - return ( - - {designation} - - ); -}; +export const LineBadge = ({ designation }: { designation: string; mode?: string; groupOfLines?: string }) => ( + + {designation} + +); diff --git a/src/components/molecules/Clock.tsx b/src/components/molecules/Clock.tsx index 35f4e68..ed056f5 100644 --- a/src/components/molecules/Clock.tsx +++ b/src/components/molecules/Clock.tsx @@ -1,30 +1,40 @@ import { useEffect, useState } from 'react'; +import { useAlwaysOn } from '../../contexts/AlwaysOnContext'; export const Clock = () => { + const alwaysOn = useAlwaysOn(); const [time, setTime] = useState(new Date()); useEffect(() => { - const timer = setInterval(() => setTime(new Date()), 1000); - return () => clearInterval(timer); - }, []); + if (!alwaysOn) { + const id = setInterval(() => setTime(new Date()), 1000); + return () => clearInterval(id); + } - const timeStr = time.toLocaleTimeString('en-GB', { - hour: '2-digit', - minute: '2-digit', - second: '2-digit', - hour12: false - }); + // Sync to the next full minute, then tick every 60 s + let interval: ReturnType; + const now = new Date(); + const msUntilNext = (60 - now.getSeconds()) * 1000 - now.getMilliseconds(); + const timeout = setTimeout(() => { + setTime(new Date()); + interval = setInterval(() => setTime(new Date()), 60_000); + }, msUntilNext); + + return () => { clearTimeout(timeout); clearInterval(interval); }; + }, [alwaysOn]); + + const timeStr = alwaysOn + ? time.toLocaleTimeString('en-GB', { hour: '2-digit', minute: '2-digit', hour12: false }) + : time.toLocaleTimeString('en-GB', { hour: '2-digit', minute: '2-digit', second: '2-digit', hour12: false }); const dateStr = time.toLocaleDateString('en-GB', { - weekday: 'long', - day: 'numeric', - month: 'long' + weekday: 'long', day: 'numeric', month: 'long', }); return ( -
-
{timeStr}
-
{dateStr}
+
+
{timeStr}
+
{dateStr}
); }; diff --git a/src/components/molecules/DepartureItem.tsx b/src/components/molecules/DepartureItem.tsx index 3c9281e..c778254 100644 --- a/src/components/molecules/DepartureItem.tsx +++ b/src/components/molecules/DepartureItem.tsx @@ -1,20 +1,20 @@ import { LineBadge } from '../atoms/LineBadge'; import { Departure } from '../../types'; +import { useAlwaysOn } from '../../contexts/AlwaysOnContext'; export const DepartureItem = ({ departure }: { departure: Departure }) => { + const alwaysOn = useAlwaysOn(); const depTime = new Date(departure.scheduled); const diffMin = Math.round((depTime.getTime() - Date.now()) / 60000); const timeText = diffMin <= 0 ? 'Now' : `${diffMin} min`; return ( -
-
- - {departure.destination} +
+
+ + {departure.destination}
- - {timeText} - + {timeText}
); }; diff --git a/src/components/organisms/DepartureList.tsx b/src/components/organisms/DepartureList.tsx index 7bf9549..faa2ebe 100644 --- a/src/components/organisms/DepartureList.tsx +++ b/src/components/organisms/DepartureList.tsx @@ -2,19 +2,11 @@ import { DepartureItem } from '../molecules/DepartureItem'; import { Departure } from '../../types'; export const DepartureList = ({ departures, loading }: { departures: Departure[]; loading: boolean }) => { + if (loading && departures.length === 0) return

Loading...

; + if (!loading && departures.length === 0) return

No departures.

; return ( -
- {loading && departures.length === 0 && ( -
- Fetching departures... -
- )} - {!loading && departures.length === 0 && ( -
- No upcoming departures found. -
- )} - {departures.slice(0, 5).map((dep, i) => ( +
+ {departures.map((dep, i) => ( ))}