import {useDashboardStore} from "@/store/useDashboardStore.jsx"; import VdapApi from "../../hooks/useVdapApi.js"; import useBuildUrl from "../../hooks/useBuildUrl.js"; import { Footprints, Plane, Sailboat, TrendingUp, TrendingDown } from 'lucide-react'; import {Box, Collapsible, Flex, Spinner, Text, Timeline, Center} from "@chakra-ui/react"; import { useMemo, useCallback } from "react"; export default function AlertChanges({ settings, widgetID}) { // Find this specific widgets object in the state list of active & displayed widgets const thisWidget = useDashboardStore(useCallback((state) => state.widgets.find((widget) => widget.id === widgetID), [widgetID] )); // build url, default is 7 days past const url = useBuildUrl('/api/v2/alert_changes', settings?.startDate, settings?.endDate); // call api hook to retrieve data const {data: apiData, isLoading, error} = VdapApi(url); const data = useMemo(() => { if (apiData.length === 0) return []; // .reduce() is a built-in array method used to transform an entire array into a single value (like an object) // here it returns a single massive object w/ volcano names as keys const grouped = apiData.reduce((accumulator, item) => { if (!accumulator[item.volcano]) accumulator[item.volcano] = []; accumulator[item.volcano].push(item); return accumulator; }, {}); // converts the 'grouped' object back into an array of [key, value] pairs const group_arr = Object.entries(grouped); // sort data newest to oldest within each volcano const sorted = group_arr.map((item) => [ item[0], // volcano name [...(item[1])].sort((a, b) => new Date(b.alert_start_date_local) - new Date(a.alert_start_date_local)) ] ); // volcano with most recent alert level change appears at top of list const sorted_entries = [...sorted].sort((a, b) => new Date(b[1][0].alert_start_date_local) - new Date(a[1][0].alert_start_date_local)); if (thisWidget?.size === "small") { return (sorted_entries.map((volcano) => { const domain = volcano[1].reduce((acc, curr) => { if (!acc[curr.alert_scheme_domain]) acc[curr.alert_scheme_domain] = []; acc[curr.alert_scheme_domain].push(curr); return acc; }, {}); const domain_arr = Object.entries(domain); return [volcano[0], domain_arr]; })); } return sorted_entries; }, [apiData, thisWidget]); // Alert colors are now light/dark mode responsive const alertColors = { Red: "alertRed", Orange: "alertOrange", Yellow: "alertYellow", Green: "alertGreen", }; if (isLoading) return ( ); if (error) return ( {error} ); if (data.length === 0) return ( No flight level data available for the selected dates. ); return ( // bg="transparent" to let the glass panel show through {data.map((volcano, index) => { if (thisWidget?.size === "large") return ( {(collapsible) => ( <> {volcano[0]} {volcano[1][0]?.alert_start_date_local} {volcano[1][0]?.alert_level_name} {volcano[1]?.map((object, index) => ( {object?.alert_scheme_domain === "terrestrial" && } {object?.alert_scheme_domain === "aviation" && } {object?.alert_scheme_domain === "maritime" && } {object?.change_type === "increase" ? : } {object?.alert_start_date_local} {object?.alert_level_name} Alert Scale: {(Array.from({ length: Number(object?.alert_scheme_highest) - Number(object?.alert_scheme_lowest) + 1}, (v, i) => Number(object?.alert_scheme_lowest) + i)) .map((num) => (
{num}
)) }
))}
)}
) else if (thisWidget?.size === "small") return ( volcano[1]?.map((domain, index) => ( {domain[0] === "aviation" && } {domain[0] === "terrestrial" && } {domain[0] === "maritime" && } {volcano[0] || ""} {domain[1]?.[0]?.alert_start_date_local || ""} {domain[1]?.[0]?.change_type === "increase" ? : } {domain[1]?.[0]?.alert_level_name} )) ); })}
) }