import type { FlexProps } from '@chakra-ui/react'; import { Flex, Icon } from '@chakra-ui/react'; import { range } from 'es-toolkit'; import React, { useRef } from 'react'; import type { AxesConfigFn, TimeChartData } from './types'; import RepeatIcon from 'icons/repeat.svg'; import { IconButton } from '../../chakra/icon-button'; import { Link } from '../../chakra/link'; import { Skeleton } from '../../chakra/skeleton'; import { Tooltip } from '../../chakra/tooltip'; import { ChartWidgetContent } from './ChartWidgetContent'; import { ChartLegend } from './parts/ChartLegend'; import type { ChartMenuItemId } from './parts/ChartMenu'; import ChartMenu from './parts/ChartMenu'; import { useChartZoom } from './utils/useChartZoom'; export interface ChartWidgetProps extends FlexProps { charts: TimeChartData; title: string; description?: string; isLoading: boolean; isError: boolean; emptyText?: string; noAnimation?: boolean; href?: string; chartUrl?: string; axesConfig?: AxesConfigFn; menuItemIds?: Array; noWatermark?: boolean; }; export const ChartWidget = React.memo(({ charts, title, description, isLoading, isError, emptyText, noAnimation, href, chartUrl, axesConfig, menuItemIds, noWatermark, ...rest }: ChartWidgetProps) => { const ref = useRef(null); const { zoomRange, handleZoom, handleZoomReset } = useChartZoom(); const [ selectedCharts, setSelectedCharts ] = React.useState>( range(charts.length), ); React.useEffect(() => { if (charts.length > 0) { setSelectedCharts(range(charts.length)); } }, [ charts.length ]); const handleLegendItemClick = React.useCallback((index: number) => { setSelectedCharts((prev) => { if (prev.includes(index)) { return prev.filter((item) => item !== index); } return [ ...prev, index ]; }); }, []); const displayedCharts = React.useMemo(() => { return charts.filter((_, index) => selectedCharts.includes(index)); }, [ charts, selectedCharts ]); const hasNonEmptyCharts = charts.some(({ items }) => items && items.length > 2); const hasMenu = (() => { const hasIds = !(menuItemIds && menuItemIds.length === 0); if (!hasIds) { return false; } if (isError) { return false; } if (!hasNonEmptyCharts) { return false; } return true; })(); const content = ( ); const chartHeader = ( { title } { description && ( { description } ) } ); return ( { href ? ( { chartHeader } ) : chartHeader } { hasMenu && ( ) } { content } { charts.length > 1 && ( ) } ); });