From 623f2769ce30b64c8bb49a3b966ab33706322f7f Mon Sep 17 00:00:00 2001 From: Josh Hawkins <32435876+hawkeye217@users.noreply.github.com> Date: Fri, 27 Feb 2026 09:28:53 -0600 Subject: [PATCH] remove unused --- .../settings/CameraReviewSettingsView.tsx | 752 ------------------ 1 file changed, 752 deletions(-) delete mode 100644 web/src/views/settings/CameraReviewSettingsView.tsx diff --git a/web/src/views/settings/CameraReviewSettingsView.tsx b/web/src/views/settings/CameraReviewSettingsView.tsx deleted file mode 100644 index 9b4b818c5..000000000 --- a/web/src/views/settings/CameraReviewSettingsView.tsx +++ /dev/null @@ -1,752 +0,0 @@ -import Heading from "@/components/ui/heading"; -import { useCallback, useContext, useEffect, useMemo, useState } from "react"; -import { toast } from "sonner"; -import { Toaster } from "@/components/ui/sonner"; -import { - Form, - FormControl, - FormDescription, - FormField, - FormItem, - FormLabel, - FormMessage, -} from "@/components/ui/form"; -import { zodResolver } from "@hookform/resolvers/zod"; -import { useForm } from "react-hook-form"; -import { z } from "zod"; -import { Separator } from "@/components/ui/separator"; -import { Button } from "@/components/ui/button"; -import useSWR from "swr"; -import { FrigateConfig } from "@/types/frigateConfig"; -import { Checkbox } from "@/components/ui/checkbox"; -import ActivityIndicator from "@/components/indicators/activity-indicator"; -import { StatusBarMessagesContext } from "@/context/statusbar-provider"; -import axios from "axios"; -import { Link } from "react-router-dom"; -import { LuExternalLink } from "react-icons/lu"; -import { MdCircle } from "react-icons/md"; -import { cn } from "@/lib/utils"; -import { Trans, useTranslation } from "react-i18next"; -import { Switch } from "@/components/ui/switch"; -import { Label } from "@/components/ui/label"; -import { useDocDomain } from "@/hooks/use-doc-domain"; -import { getTranslatedLabel } from "@/utils/i18n"; -import { - useAlertsState, - useDetectionsState, - useObjectDescriptionState, - useReviewDescriptionState, -} from "@/api/ws"; -import { useCameraFriendlyName } from "@/hooks/use-camera-friendly-name"; -import { resolveZoneName } from "@/hooks/use-zone-friendly-name"; -import { formatList } from "@/utils/stringUtil"; - -type CameraReviewSettingsViewProps = { - selectedCamera: string; - setUnsavedChanges?: (hasChanges: boolean) => void; -}; - -type CameraReviewSettingsValueType = { - alerts_zones: string[]; - detections_zones: string[]; -}; - -export default function CameraReviewSettingsView({ - selectedCamera, - setUnsavedChanges, -}: CameraReviewSettingsViewProps) { - const { t } = useTranslation(["views/settings"]); - const { getLocaleDocUrl } = useDocDomain(); - - const { data: config, mutate: updateConfig } = - useSWR("config"); - - const cameraConfig = useMemo(() => { - if (config && selectedCamera) { - return config.cameras[selectedCamera]; - } - }, [config, selectedCamera]); - - const [changedValue, setChangedValue] = useState(false); - const [isLoading, setIsLoading] = useState(false); - const [selectDetections, setSelectDetections] = useState(false); - - const { addMessage, removeMessage } = useContext(StatusBarMessagesContext)!; - - const selectCameraName = useCameraFriendlyName(selectedCamera); - - // zones and labels - - const getZoneName = useCallback( - (zoneId: string, cameraId?: string) => - resolveZoneName(config, zoneId, cameraId), - [config], - ); - - const zones = useMemo(() => { - if (cameraConfig) { - return Object.entries(cameraConfig.zones).map(([name, zoneData]) => ({ - camera: cameraConfig.name, - name, - friendly_name: cameraConfig.zones[name].friendly_name, - objects: zoneData.objects, - color: zoneData.color, - })); - } - }, [cameraConfig]); - - const alertsLabels = useMemo(() => { - return cameraConfig?.review.alerts.labels - ? formatList( - cameraConfig.review.alerts.labels.map((label) => - getTranslatedLabel( - label, - cameraConfig?.audio?.listen?.includes(label) ? "audio" : "object", - ), - ), - ) - : ""; - }, [cameraConfig]); - - const detectionsLabels = useMemo(() => { - return cameraConfig?.review.detections.labels - ? formatList( - cameraConfig.review.detections.labels.map((label) => - getTranslatedLabel( - label, - cameraConfig?.audio?.listen?.includes(label) ? "audio" : "object", - ), - ), - ) - : ""; - }, [cameraConfig]); - - // form - - const formSchema = z.object({ - alerts_zones: z.array(z.string()), - detections_zones: z.array(z.string()), - }); - - const form = useForm>({ - resolver: zodResolver(formSchema), - mode: "onChange", - defaultValues: { - alerts_zones: cameraConfig?.review.alerts.required_zones || [], - detections_zones: cameraConfig?.review.detections.required_zones || [], - }, - }); - - const watchedAlertsZones = form.watch("alerts_zones"); - const watchedDetectionsZones = form.watch("detections_zones"); - - const { payload: alertsState, send: sendAlerts } = - useAlertsState(selectedCamera); - const { payload: detectionsState, send: sendDetections } = - useDetectionsState(selectedCamera); - - const { payload: objDescState, send: sendObjDesc } = - useObjectDescriptionState(selectedCamera); - const { payload: revDescState, send: sendRevDesc } = - useReviewDescriptionState(selectedCamera); - - const handleCheckedChange = useCallback( - (isChecked: boolean) => { - if (!isChecked) { - form.reset({ - alerts_zones: watchedAlertsZones, - detections_zones: [], - }); - } - setChangedValue(true); - setUnsavedChanges(true); - setSelectDetections(isChecked as boolean); - }, - // we know that these deps are correct - // eslint-disable-next-line react-hooks/exhaustive-deps - [watchedAlertsZones, setUnsavedChanges], - ); - - const saveToConfig = useCallback( - async ( - { alerts_zones, detections_zones }: CameraReviewSettingsValueType, // values submitted via the form - ) => { - const createQuery = (zones: string[], type: "alerts" | "detections") => - zones.length - ? zones - .map( - (zone) => - `&cameras.${selectedCamera}.review.${type}.required_zones=${zone}`, - ) - .join("") - : cameraConfig?.review[type]?.required_zones && - cameraConfig?.review[type]?.required_zones.length > 0 - ? `&cameras.${selectedCamera}.review.${type}.required_zones` - : ""; - - const alertQueries = createQuery(alerts_zones, "alerts"); - const detectionQueries = createQuery(detections_zones, "detections"); - - axios - .put(`config/set?${alertQueries}${detectionQueries}`, { - requires_restart: 0, - }) - .then((res) => { - if (res.status === 200) { - toast.success( - t("cameraReview.reviewClassification.toast.success"), - { - position: "top-center", - }, - ); - setChangedValue(false); - setUnsavedChanges(false); - updateConfig(); - } else { - toast.error( - t("toast.save.error.title", { - errorMessage: res.statusText, - ns: "common", - }), - { - position: "top-center", - }, - ); - } - }) - .catch((error) => { - const errorMessage = - error.response?.data?.message || - error.response?.data?.detail || - "Unknown error"; - toast.error( - t("toast.save.error.title", { - errorMessage, - ns: "common", - }), - { - position: "top-center", - }, - ); - }) - .finally(() => { - setIsLoading(false); - }); - }, - [ - updateConfig, - setIsLoading, - selectedCamera, - cameraConfig, - t, - setUnsavedChanges, - ], - ); - - const onCancel = useCallback(() => { - if (!cameraConfig) { - return; - } - - setChangedValue(false); - setUnsavedChanges?.(false); - removeMessage( - "camera_settings", - `review_classification_settings_${selectedCamera}`, - ); - form.reset({ - alerts_zones: cameraConfig?.review.alerts.required_zones ?? [], - detections_zones: cameraConfig?.review.detections.required_zones || [], - }); - setSelectDetections( - !!cameraConfig?.review.detections.required_zones?.length, - ); - // we know that these deps are correct - // eslint-disable-next-line react-hooks/exhaustive-deps - }, [removeMessage, selectedCamera, setUnsavedChanges, cameraConfig]); - - useEffect(() => { - onCancel(); - // we know that these deps are correct - // eslint-disable-next-line react-hooks/exhaustive-deps - }, [selectedCamera]); - - useEffect(() => { - if (changedValue) { - addMessage( - "camera_settings", - t("cameraReview.reviewClassification.unsavedChanges", { - camera: selectedCamera, - }), - undefined, - `review_classification_settings_${selectedCamera}`, - ); - } else { - removeMessage( - "camera_settings", - `review_classification_settings_${selectedCamera}`, - ); - } - // we know that these deps are correct - // eslint-disable-next-line react-hooks/exhaustive-deps - }, [changedValue, selectedCamera]); - - function onSubmit(values: z.infer) { - setIsLoading(true); - - saveToConfig(values as CameraReviewSettingsValueType); - } - - useEffect(() => { - document.title = t("documentTitle.cameraReview"); - }, [t]); - - if (!cameraConfig && !selectedCamera) { - return ; - } - - return ( - <> -
- -
- - {t("cameraReview.title")} - - - - cameraReview.review.title - - -
-
- { - sendAlerts(isChecked ? "ON" : "OFF"); - }} - /> -
- -
-
-
-
- { - sendDetections(isChecked ? "ON" : "OFF"); - }} - /> -
- -
-
-
- cameraReview.review.desc -
-
-
- {cameraConfig?.objects?.genai?.enabled_in_config && ( - <> - - - - - cameraReview.object_descriptions.title - - - -
-
- { - sendObjDesc(isChecked ? "ON" : "OFF"); - }} - /> -
- -
-
-
- - cameraReview.object_descriptions.desc - -
-
- - )} - - {cameraConfig?.review?.genai?.enabled_in_config && ( - <> - - - - - cameraReview.review_descriptions.title - - - -
-
- { - sendRevDesc(isChecked ? "ON" : "OFF"); - }} - /> -
- -
-
-
- - cameraReview.review_descriptions.desc - -
-
- - )} - - - - - - cameraReview.reviewClassification.title - - - -
-
-

- - cameraReview.reviewClassification.desc - -

-
- - {t("readTheDocumentation", { ns: "common" })} - - -
-
-
- -
- -
0 && - "grid items-start gap-5 md:grid-cols-2", - )} - > - ( - - {zones && zones?.length > 0 ? ( - <> -
- - - camera.review.alerts - - - - - - cameraReview.reviewClassification.selectAlertsZones - - -
-
- {zones?.map((zone) => ( - ( - - - { - setChangedValue(true); - setUnsavedChanges(true); - return checked - ? field.onChange([ - ...field.value, - zone.name, - ]) - : field.onChange( - field.value?.filter( - (value) => - value !== zone.name, - ), - ); - }} - /> - - - {zone.friendly_name || zone.name} - - - )} - /> - ))} -
- - ) : ( -
- - cameraReview.reviewClassification.noDefinedZones - -
- )} - -
- {watchedAlertsZones && watchedAlertsZones.length > 0 - ? t( - "cameraReview.reviewClassification.zoneObjectAlertsTips", - { - alertsLabels, - zone: formatList( - watchedAlertsZones.map((zone) => - getZoneName(zone), - ), - ), - cameraName: selectCameraName, - }, - ) - : t( - "cameraReview.reviewClassification.objectAlertsTips", - { - alertsLabels, - cameraName: selectCameraName, - }, - )} -
-
- )} - /> - - ( - - {zones && zones?.length > 0 && ( - <> -
- - - camera.review.detections - - - - {selectDetections && ( - - - cameraReview.reviewClassification.selectDetectionsZones - - - )} -
- - {selectDetections && ( -
- {zones?.map((zone) => ( - ( - - - { - setChangedValue(true); - setUnsavedChanges(true); - return checked - ? field.onChange([ - ...field.value, - zone.name, - ]) - : field.onChange( - field.value?.filter( - (value) => - value !== zone.name, - ), - ); - }} - /> - - - {zone.friendly_name || zone.name} - - - )} - /> - ))} -
- )} - - -
- -
- -
-
- - )} - -
- {watchedDetectionsZones && - watchedDetectionsZones.length > 0 ? ( - !selectDetections ? ( - - getZoneName(zone), - ), - ), - cameraName: selectCameraName, - }} - ns="views/settings" - /> - ) : ( - - getZoneName(zone), - ), - ), - cameraName: selectCameraName, - }} - ns="views/settings" - /> - ) - ) : ( - - )} -
-
- )} - /> -
- -
- - -
-
- -
-
- - - ); -}