From 2ecc39317da212a9536c599c4177855e75466b9d Mon Sep 17 00:00:00 2001 From: Toba Ojo Date: Mon, 12 Jan 2026 15:38:01 +0000 Subject: [PATCH] - Enhanced Dashboard and SystemOverview components with totalSightings prop - improved layout and loading states in VideoFeed and SightingStack components. --- src/features/dashboard/Dashboard.tsx | 18 ++++++----- .../SystemOverview/SystemOverview.tsx | 31 +++++++++++-------- .../sightingStack/SightingStack.tsx | 2 +- .../components/videoFeed/VideoFeed.tsx | 3 +- .../dashboard/hooks/useSightingList.ts | 5 ++- .../components/videofeed/VideoFeedSetup.tsx | 8 +++-- .../setup/hooks/useCreatePreviewImage.ts | 12 +++++-- 7 files changed, 50 insertions(+), 29 deletions(-) diff --git a/src/features/dashboard/Dashboard.tsx b/src/features/dashboard/Dashboard.tsx index 843a8dc..f1ea8c5 100644 --- a/src/features/dashboard/Dashboard.tsx +++ b/src/features/dashboard/Dashboard.tsx @@ -6,22 +6,24 @@ import { useCameraSettingsContext } from "../../app/context/CameraSettingsContex import SystemOverview from "./SystemOverview/SystemOverview"; const Dashboard = () => { - const { sightingList, isLoading } = useSightingList(); + const { sightingList, isLoading, totalSightings } = useSightingList(); const { state: cameraSettings } = useCameraSettingsContext(); const size = cameraSettings.imageSize; const mostRecent = sightingList[0]; return ( -
- -
-
- +
+
+ + +
+
+
-
- +
+
diff --git a/src/features/dashboard/SystemOverview/SystemOverview.tsx b/src/features/dashboard/SystemOverview/SystemOverview.tsx index 907b000..b96bfd1 100644 --- a/src/features/dashboard/SystemOverview/SystemOverview.tsx +++ b/src/features/dashboard/SystemOverview/SystemOverview.tsx @@ -5,7 +5,11 @@ import { useGetSystemHealth } from "../hooks/useGetSystemHealth"; import PlatesProcessed from "./PlatesProcessed"; import SystemStatusContent from "./SystemStatusContent"; -const SystemOverview = () => { +type SystemOverViewProps = { + totalSightings: number; +}; + +const SystemOverview = ({ totalSightings }: SystemOverViewProps) => { const { systemHealthQuery } = useGetSystemHealth(); const { storeQuery } = useGetStore(); @@ -19,23 +23,24 @@ const SystemOverview = () => { return
Loading system overview...
; } return ( -
-
- + +
+
- - -

Active Sightings

-
- +
+
+

Sightings

+

{totalSightings}

+
+
- - +
+

Up Time

{upTime}

Start Time

{startTime} - +
-
+ ); }; diff --git a/src/features/dashboard/components/sightingStack/SightingStack.tsx b/src/features/dashboard/components/sightingStack/SightingStack.tsx index 5350b99..af972e8 100644 --- a/src/features/dashboard/components/sightingStack/SightingStack.tsx +++ b/src/features/dashboard/components/sightingStack/SightingStack.tsx @@ -19,7 +19,7 @@ const SightingStack = ({ sightings }: SightingStackProps) => { return ( <> - +
{sightings.map((sighting) => ( diff --git a/src/features/dashboard/components/videoFeed/VideoFeed.tsx b/src/features/dashboard/components/videoFeed/VideoFeed.tsx index aaa44b7..9eb75e5 100644 --- a/src/features/dashboard/components/videoFeed/VideoFeed.tsx +++ b/src/features/dashboard/components/videoFeed/VideoFeed.tsx @@ -17,6 +17,7 @@ const VideoFeed = ({ mostRecentSighting, isLoading, size, modeSetting, isModal = const contextMode = cameraSettings.mode; const [localMode, setLocalMode] = useState(0); const mode = isModal ? localMode : contextMode; + console.log(mode); const { image, plateRect, plateTrack } = useCreateVideoSnapshot(mostRecentSighting); const handleModeChange = (newMode: number) => { @@ -33,7 +34,7 @@ const VideoFeed = ({ mostRecentSighting, isLoading, size, modeSetting, isModal = useEffect(() => { const updateSize = () => { - const width = window.innerWidth * 0.57; + const width = window.innerWidth * 0.48; const height = (width * 2) / 3; dispatch({ type: "SET_IMAGE_SIZE", payload: { width, height } }); }; diff --git a/src/features/dashboard/hooks/useSightingList.ts b/src/features/dashboard/hooks/useSightingList.ts index 7c5900b..d9991f3 100644 --- a/src/features/dashboard/hooks/useSightingList.ts +++ b/src/features/dashboard/hooks/useSightingList.ts @@ -4,6 +4,7 @@ import type { SightingType } from "../../../utils/types"; export const useSightingList = () => { const [sightingList, setSightingList] = useState([]); + const [totalSightings, setTotalSightings] = useState(0); const { videoFeedQuery } = useVideoFeed(); const latestSighting = videoFeedQuery?.data; const lastProcessedRef = useRef(-1); @@ -11,6 +12,8 @@ export const useSightingList = () => { useEffect(() => { if (!latestSighting || latestSighting.ref === undefined || latestSighting.ref === -1) return; + // eslint-disable-next-line react-hooks/set-state-in-effect + setTotalSightings((prev) => (latestSighting.ref! > prev ? latestSighting.ref! : prev)); if (latestSighting.ref !== lastProcessedRef.current) { lastProcessedRef.current = latestSighting.ref; @@ -23,5 +26,5 @@ export const useSightingList = () => { }); } }, [latestSighting, latestSighting?.ref]); - return { sightingList, isLoading }; + return { sightingList, isLoading, totalSightings }; }; diff --git a/src/features/setup/components/videofeed/VideoFeedSetup.tsx b/src/features/setup/components/videofeed/VideoFeedSetup.tsx index f0c6ec7..9336dfd 100644 --- a/src/features/setup/components/videofeed/VideoFeedSetup.tsx +++ b/src/features/setup/components/videofeed/VideoFeedSetup.tsx @@ -13,7 +13,8 @@ const cols = 40; const gap = 0; const VideoFeedSetup = () => { - const { latestBitmapRef, isLoading } = useCreateVideoPreviewSnapshot(); + const { latestBitmapRef, isPreviewLoading } = useCreateVideoPreviewSnapshot(); + const { state, dispatch } = useCameraSettingsContext(); const cameraMode = state.cameraMode; const paintedCells = state.regionPainter.paintedCells; @@ -84,9 +85,10 @@ const VideoFeedSetup = () => { updateSize(); window.addEventListener("resize", updateSize); return () => window.removeEventListener("resize", updateSize); - }, []); + }, [dispatch]); + + if (isPreviewLoading) return <>Loading Preview...; - if (isLoading) return <>Loading...; return (
diff --git a/src/features/setup/hooks/useCreatePreviewImage.ts b/src/features/setup/hooks/useCreatePreviewImage.ts index 1f753fe..a23afd2 100644 --- a/src/features/setup/hooks/useCreatePreviewImage.ts +++ b/src/features/setup/hooks/useCreatePreviewImage.ts @@ -6,7 +6,9 @@ export const useCreateVideoPreviewSnapshot = () => { const { state } = useCameraSettingsContext(); const { videoPreviewQuery, targetDetectionFeedQuery } = useVideoPreview(state.cameraMode); const latestBitmapRef = useRef(null); - const isLoading = videoPreviewQuery?.isPending || targetDetectionFeedQuery?.isPending; + const isPreviewLoading = videoPreviewQuery?.isPending; + const isTargetDetectionLoading = targetDetectionFeedQuery?.isPending; + let snapshot; if (state.cameraMode === 0) { snapshot = videoPreviewQuery?.data; @@ -20,6 +22,7 @@ export const useCreateVideoPreviewSnapshot = () => { try { const bitmap = await createImageBitmap(imageBlob); + latestBitmapRef.current = bitmap; } catch (error) { console.log(error); @@ -28,5 +31,10 @@ export const useCreateVideoPreviewSnapshot = () => { createImageBitmapFromBlob(); }, [imageBlob]); - return { latestBitmapRef, isLoading, imageURL: imageBlob ? URL.createObjectURL(imageBlob) : null }; + return { + latestBitmapRef, + isPreviewLoading, + isTargetDetectionLoading, + imageURL: imageBlob ? URL.createObjectURL(imageBlob) : null, + }; };