diff --git a/src/app/context/CameraSettingsContext.ts b/src/app/context/CameraSettingsContext.ts new file mode 100644 index 0000000..4ee294b --- /dev/null +++ b/src/app/context/CameraSettingsContext.ts @@ -0,0 +1,16 @@ +import { createContext, useContext } from "react"; +import type { CameraSettings, CameraSettingsAction } from "../../utils/types"; + +type CameraSettingsContextType = { + state: CameraSettings; + dispatch: (state: CameraSettingsAction) => void; +}; +export const CameraSettingsContext = createContext(null); + +export const useCameraSettingsContext = () => { + const context = useContext(CameraSettingsContext); + if (!context) { + throw new Error("useCameraSettingsContext must be used within a CameraSettingsProvider"); + } + return context; +}; diff --git a/src/app/providers/AppProviders.tsx b/src/app/providers/AppProviders.tsx index 212fdd3..9018fbf 100644 --- a/src/app/providers/AppProviders.tsx +++ b/src/app/providers/AppProviders.tsx @@ -1,8 +1,13 @@ import { type PropsWithChildren } from "react"; import { QueryProvider } from "./QueryProvider"; +import CameraSettingsProvider from "./CameraSettingsProvider"; const AppProviders = ({ children }: PropsWithChildren) => { - return {children}; + return ( + + {children} + + ); }; export default AppProviders; diff --git a/src/app/providers/CameraSettingsProvider.tsx b/src/app/providers/CameraSettingsProvider.tsx new file mode 100644 index 0000000..f33ee72 --- /dev/null +++ b/src/app/providers/CameraSettingsProvider.tsx @@ -0,0 +1,11 @@ +import { CameraSettingsContext } from "../context/CameraSettingsContext"; +import { useReducer, type ReactNode } from "react"; +import { initialState, cameraSettingsReducer } from "../reducers/cameraSettingsReducer"; + +const CameraSettingsProvider = ({ children }: { children: ReactNode }) => { + const [state, dispatch] = useReducer(cameraSettingsReducer, initialState); + + return {children}; +}; + +export default CameraSettingsProvider; diff --git a/src/app/reducers/cameraSettingsReducer.ts b/src/app/reducers/cameraSettingsReducer.ts new file mode 100644 index 0000000..d2573c7 --- /dev/null +++ b/src/app/reducers/cameraSettingsReducer.ts @@ -0,0 +1,17 @@ +import type { CameraSettings, CameraSettingsAction } from "../../utils/types"; + +export const initialState: CameraSettings = { + mode: 0, +}; + +export const cameraSettingsReducer = (state: CameraSettings, action: CameraSettingsAction) => { + switch (action.type) { + case "SET_MODE": + return { + ...state, + mode: action.payload, + }; + default: + return state; + } +}; diff --git a/src/features/dashboard/components/platePatch/NumberPlate.tsx b/src/features/dashboard/components/platePatch/NumberPlate.tsx index 2f986cb..0a485bc 100644 --- a/src/features/dashboard/components/platePatch/NumberPlate.tsx +++ b/src/features/dashboard/components/platePatch/NumberPlate.tsx @@ -41,7 +41,7 @@ const NumberPlate = ({ vrm, motion, size }: NumberPlateProps) => { return (
diff --git a/src/features/dashboard/components/sightingStack/SightingItem.tsx b/src/features/dashboard/components/sightingStack/SightingItem.tsx index 8ec0d3c..0c29b49 100644 --- a/src/features/dashboard/components/sightingStack/SightingItem.tsx +++ b/src/features/dashboard/components/sightingStack/SightingItem.tsx @@ -10,10 +10,10 @@ const SightingItem = ({ sighting }: SightingItemProps) => { return (
-
Ref: {sighting.ref}
-
vrm: {sighting.vrm}
+
+ VRM: {sighting.vrm} +
-
); diff --git a/src/features/dashboard/components/sightingStack/SightingStack.tsx b/src/features/dashboard/components/sightingStack/SightingStack.tsx index 15fcad5..6c8d94d 100644 --- a/src/features/dashboard/components/sightingStack/SightingStack.tsx +++ b/src/features/dashboard/components/sightingStack/SightingStack.tsx @@ -8,11 +8,13 @@ type SightingStackProps = { }; const SightingStack = ({ sightings }: SightingStackProps) => { return ( - - - {sightings.map((sighting) => ( - - ))} + + +
+ {sightings.map((sighting) => ( + + ))} +
); }; diff --git a/src/features/dashboard/components/videoFeed/VideoButton.tsx b/src/features/dashboard/components/videoFeed/VideoButton.tsx new file mode 100644 index 0000000..4b0a4db --- /dev/null +++ b/src/features/dashboard/components/videoFeed/VideoButton.tsx @@ -0,0 +1,42 @@ +import { useState } from "react"; +import { Text, Group, Rect } from "react-konva"; + +type VideoButtonProps = { + x?: number; + y?: number; + onClick?: () => void; + text?: string; +}; + +const VideoButton = ({ x, y, onClick, text }: VideoButtonProps) => { + const [isHovered, setIsHovered] = useState(false); + return ( + { + setIsHovered(true); + const container = e.target.getStage()?.container(); + if (container) container.style.cursor = "pointer"; + }} + onMouseLeave={(e) => { + setIsHovered(false); + const container = e.target.getStage()?.container(); + if (container) container.style.cursor = "default"; + }} + > + + + + ); +}; + +export default VideoButton; diff --git a/src/features/dashboard/components/videoFeed/VideoFeed.tsx b/src/features/dashboard/components/videoFeed/VideoFeed.tsx index 2c85705..28e22b6 100644 --- a/src/features/dashboard/components/videoFeed/VideoFeed.tsx +++ b/src/features/dashboard/components/videoFeed/VideoFeed.tsx @@ -2,6 +2,7 @@ import { Stage, Layer, Image, Rect } from "react-konva"; import type { SightingType } from "../../../../utils/types"; import { useCreateVideoSnapshot } from "../../hooks/useCreateVideoSnapshot"; import { useEffect, useState } from "react"; +import { useCameraSettingsContext } from "../../../../app/context/CameraSettingsContext"; type VideoFeedProps = { mostRecentSighting: SightingType; @@ -9,13 +10,16 @@ type VideoFeedProps = { }; const VideoFeed = ({ mostRecentSighting, isLoading }: VideoFeedProps) => { + const { state: cameraSettings, dispatch } = useCameraSettingsContext(); + + const mode = cameraSettings.mode; const [size, setSize] = useState<{ width: number; height: number }>({ width: 1280, height: 960 }); - const [mode, setMode] = useState(0); + const { image, plateRect, plateTrack } = useCreateVideoSnapshot(mostRecentSighting); const handleModeChange = (newMode: number) => { - if (newMode > 2) setMode(0); - else setMode(newMode); + if (newMode > 2) dispatch({ type: "SET_MODE", payload: 0 }); + else dispatch({ type: "SET_MODE", payload: newMode }); }; useEffect(() => { diff --git a/src/utils/types.ts b/src/utils/types.ts index c518fa3..b0f29c1 100644 --- a/src/utils/types.ts +++ b/src/utils/types.ts @@ -51,3 +51,11 @@ export type NpedJSON = { vrm: string; "INSURANCE STATUS": string; }; + +export type CameraSettings = { + mode: number; +}; +export type CameraSettingsAction = { + type: "SET_MODE"; + payload: number; +};