Cleanup mobile live

This commit is contained in:
Nicolas Mowen 2024-03-01 14:17:05 -07:00
parent 34db4900ef
commit 16bee2dd3d
2 changed files with 31 additions and 10 deletions

View File

@ -27,7 +27,7 @@ function App() {
{isMobile && <Bottombar />} {isMobile && <Bottombar />}
<div <div
id="pageRoot" id="pageRoot"
className="absolute left-0 top-2 right-0 bottom-16 md:left-16 md:bottom-8 overflow-hidden" className={`absolute top-2 right-0 overflow-hidden ${isMobile ? "left-0 bottom-16" : "left-16 bottom-8"}`}
> >
<Routes> <Routes>
<Route path="/" element={<Live />} /> <Route path="/" element={<Live />} />

View File

@ -19,7 +19,12 @@ import useKeyboardListener from "@/hooks/use-keyboard-listener";
import { CameraConfig } from "@/types/frigateConfig"; import { CameraConfig } from "@/types/frigateConfig";
import { CameraPtzInfo } from "@/types/ptz"; import { CameraPtzInfo } from "@/types/ptz";
import React, { useCallback, useMemo, useState } from "react"; import React, { useCallback, useMemo, useState } from "react";
import { isSafari } from "react-device-detect"; import {
isDesktop,
isMobile,
isSafari,
useMobileOrientation,
} from "react-device-detect";
import { BsThreeDotsVertical } from "react-icons/bs"; import { BsThreeDotsVertical } from "react-icons/bs";
import { import {
FaAngleDown, FaAngleDown,
@ -46,6 +51,7 @@ type LiveCameraViewProps = {
}; };
export default function LiveCameraView({ camera }: LiveCameraViewProps) { export default function LiveCameraView({ camera }: LiveCameraViewProps) {
const navigate = useNavigate(); const navigate = useNavigate();
const { isPortrait } = useMobileOrientation();
// camera features // camera features
@ -65,41 +71,55 @@ export default function LiveCameraView({ camera }: LiveCameraViewProps) {
const [audio, setAudio] = useState(false); const [audio, setAudio] = useState(false);
const growClassName = useMemo(() => { const growClassName = useMemo(() => {
if (camera.detect.width / camera.detect.height > 2) { if (isMobile) {
if (isPortrait) {
return "absolute left-2 right-2 top-[50%] -translate-y-[50%]";
} else {
return "absolute top-2 bottom-2 left-[50%] -translate-x-[50%]";
}
} else if (camera.detect.width / camera.detect.height > 2) {
return "absolute left-2 right-2 top-[50%] -translate-y-[50%]"; return "absolute left-2 right-2 top-[50%] -translate-y-[50%]";
} else { } else {
return "absolute top-2 bottom-2 left-[50%] -translate-x-[50%]"; return "absolute top-2 bottom-2 left-[50%] -translate-x-[50%]";
} }
}, [camera]); }, [camera, isPortrait]);
return ( return (
<div className="size-full flex flex-col"> <div className="size-full flex flex-col landscape:flex-row">
<div className="w-full h-12 flex items-center justify-between"> <div className="w-full landscape:w-min landscape:h-full h-12 flex flex-row landscape:flex-col items-center justify-between">
<Button className="rounded-lg" onClick={() => navigate(-1)}> <Button
<IoMdArrowBack className="size-5 mr-[10px]" /> className={`rounded-lg ${isMobile ? "ml-2" : "ml-0"}`}
Back size={isMobile ? "icon" : "default"}
onClick={() => navigate(-1)}
>
<IoMdArrowBack className="size-5 lg:mr-[10px]" />
{isDesktop && "Back"}
</Button> </Button>
<TooltipProvider> <TooltipProvider>
<div className="flex items-center gap-1 mr-1 *:rounded-lg"> <div className="flex flex-row landscape:flex-col items-center gap-1 mr-1 *:rounded-lg">
<CameraFeatureToggle <CameraFeatureToggle
className="p-2 md:p-0"
Icon={audio ? GiSpeaker : GiSpeakerOff} Icon={audio ? GiSpeaker : GiSpeakerOff}
isActive={audio} isActive={audio}
title={`${audio ? "Disable" : "Enable"} Camera Audio`} title={`${audio ? "Disable" : "Enable"} Camera Audio`}
onClick={() => setAudio(!audio)} onClick={() => setAudio(!audio)}
/> />
<CameraFeatureToggle <CameraFeatureToggle
className="p-2 md:p-0"
Icon={detectState == "ON" ? MdPersonSearch : MdPersonOff} Icon={detectState == "ON" ? MdPersonSearch : MdPersonOff}
isActive={detectState == "ON"} isActive={detectState == "ON"}
title={`${detectState == "ON" ? "Disable" : "Enable"} Detect`} title={`${detectState == "ON" ? "Disable" : "Enable"} Detect`}
onClick={() => sendDetect(detectState == "ON" ? "OFF" : "ON")} onClick={() => sendDetect(detectState == "ON" ? "OFF" : "ON")}
/> />
<CameraFeatureToggle <CameraFeatureToggle
className="p-2 md:p-0"
Icon={recordState == "ON" ? LuVideo : LuVideoOff} Icon={recordState == "ON" ? LuVideo : LuVideoOff}
isActive={recordState == "ON"} isActive={recordState == "ON"}
title={`${recordState == "ON" ? "Disable" : "Enable"} Recording`} title={`${recordState == "ON" ? "Disable" : "Enable"} Recording`}
onClick={() => sendRecord(recordState == "ON" ? "OFF" : "ON")} onClick={() => sendRecord(recordState == "ON" ? "OFF" : "ON")}
/> />
<CameraFeatureToggle <CameraFeatureToggle
className="p-2 md:p-0"
Icon={snapshotState == "ON" ? MdPhotoCamera : MdNoPhotography} Icon={snapshotState == "ON" ? MdPhotoCamera : MdNoPhotography}
isActive={snapshotState == "ON"} isActive={snapshotState == "ON"}
title={`${snapshotState == "ON" ? "Disable" : "Enable"} Snapshots`} title={`${snapshotState == "ON" ? "Disable" : "Enable"} Snapshots`}
@ -107,6 +127,7 @@ export default function LiveCameraView({ camera }: LiveCameraViewProps) {
/> />
{camera.audio.enabled_in_config && ( {camera.audio.enabled_in_config && (
<CameraFeatureToggle <CameraFeatureToggle
className="p-2 md:p-0"
Icon={audioState == "ON" ? LuEar : LuEarOff} Icon={audioState == "ON" ? LuEar : LuEarOff}
isActive={audioState == "ON"} isActive={audioState == "ON"}
title={`${audioState == "ON" ? "Disable" : "Enable"} Audio Detect`} title={`${audioState == "ON" ? "Disable" : "Enable"} Audio Detect`}