import { useMemo, useState, type ReactNode } from 'react' import { Box, Collapse, Typography } from '@mui/material' import { ExpandMore as ExpandMoreIcon } from '@mui/icons-material' import { SmartTooltip } from '../../../components/smart-tooltip/smart-tooltip' import { selectLayerCollapsible, useLegendId, useLegendShallow, useLegendStore, } from '../../stores' import { accordionKeyDown } from '../a11y' import { LegendRowContext, type LegendRowContextValue, useLegendGroupId, } from '../contexts' import { partitionLegendChildren } from '../legend-actions/legend-actions' import { LEGEND_GROUP_HEADER_HEIGHT } from '../legend-group/styles' import { useLegendSortable } from '../legend-sortable/contexts' import { SortableEntity, type SortableEntityRenderProps, } from '../legend-sortable/sortable-entity' import { styles } from './styles' export interface LegendRowProps { layerId: string /** * `` in the sticky header; body children + `helperText` footer. * Place `` first in the body. */ children?: ReactNode } /** * Store-connected layer row. Provides row context for actions; hidden layers * force-collapse the body. * * @experimental This API is new and may change in a future release. */ export function LegendRow({ layerId, children }: LegendRowProps) { const id = useLegendId() const layer = useLegendShallow(id, (s) => s.layers[layerId]) const setCollapsed = useLegendShallow(id, (s) => s.setCollapsed) const collapsible = useLegendStore(id, (s) => selectLayerCollapsible(s, layerId), ) const inGroup = useLegendGroupId() !== null const sortable = useLegendSortable() const [opacityOpen, setOpacityOpen] = useState(false) // Hidden rows derive opacityOpen=false so menu `.active` never pins while hidden. const visible = layer?.visible ?? true const rowContext = useMemo( () => ({ layerId, opacityOpen: opacityOpen && visible, setOpacityOpen }), [layerId, opacityOpen, visible], ) if (!layer) return null const { actions, body } = partitionLegendChildren(children) const effectivelyCollapsed = !layer.visible || layer.collapsed const stickyTop = inGroup ? LEGEND_GROUP_HEADER_HEIGHT : 0 const canToggle = layer.visible && collapsible const toggle = () => setCollapsed(layerId, !layer.collapsed) const renderRow = (sortableProps?: SortableEntityRenderProps) => ( {sortableProps?.handle} {({ ref }) => ( {layer.name} )} {canToggle && ( )} {layer.subtitle && !effectivelyCollapsed && ( {layer.subtitle} )} {actions} {body} {layer.helperText && ( {typeof layer.helperText === 'string' ? ( {layer.helperText} ) : ( layer.helperText )} )} ) return sortable ? ( ) : ( renderRow() ) }