// // Copyright 2026 James Pace // // This Source Code Form is subject to the terms of the Mozilla Public // License, v. 2.0. If a copy of the MPL was not distributed with this // file, You can obtain one at https://mozilla.org/MPL/2.0/. // // This Source Code Form is "Incompatible With Secondary Licenses", as // defined by the Mozilla Public License, v. 2.0. // import { AppNav, Footer } from "./AppNav.tsx"; import { Container, Row, Col, Image, Card } from "react-bootstrap"; import { atom, useAtomValue } from "jotai"; import { atomWithQuery } from "jotai-tanstack-query"; const costmapImageQuery = async () => { const resp = await fetch("api/costmap_image"); if (!resp.ok) { throw new Error("Network response was not ok"); } const blob = await resp.blob(); return URL.createObjectURL(blob); }; const costmapImageQueryAtom = atomWithQuery(() => ({ queryKey: ["costmap_image"], queryFn: costmapImageQuery, refetchInterval: 1000, // 1s })); const costmapImageAtom = atom((get) => { const response = get(costmapImageQueryAtom); if (response.isPending) { return

"Loading..."

; } if (response.isError) { return

"Error loading!"

; } const costmapStyle = { minHeight: "65svb", }; return ; }); const statusStringQuery = async () => { const resp = await fetch("api/status"); if (!resp.ok) { throw new Error("Network response was not ok"); } return resp.json(); }; const statusStringQueryAtom = atomWithQuery(() => ({ queryKey: ["status_string"], queryFn: statusStringQuery, refetchInterval: 500, // 0.5s })); const statusStringAtom = atom((get) => { const response = get(statusStringQueryAtom); if (response.isPending || response.isError || !response.data.status) { return "N/A"; } return response.data.message; }); const latLongQuery = async () => { const resp = await fetch("api/position"); if (!resp.ok) { throw new Error("Network response was not ok"); } return resp.json(); }; const latLongQueryAtom = atomWithQuery(() => ({ queryKey: ["latlong"], queryFn: latLongQuery, refetchInterval: 500, // 0.5s })); const latLongAtom = atom((get) => { const response = get(latLongQueryAtom); if (response.isPending || response.isError || !response.data.status) { return "N/A"; } return `(${response.data.latitude}, ${response.data.longitude})`; }); export function Autonomy() { const costmapImage = useAtomValue(costmapImageAtom); const statusString = useAtomValue(statusStringAtom); const latLong = useAtomValue(latLongAtom); return (
{costmapImage}

Status:

{statusString}

Latitude, Longitude:

{latLong}
); }