import { Dispatch } from 'react'; import { Map as Map_2 } from 'maplibre-gl'; import { SetStateAction } from 'react'; /** * A layer that has been added to the map through the control. */ export declare interface AddedLayer { /** Unique identifier for this entry */ id: string; /** MapLibre source id */ sourceId: string; /** MapLibre layer id */ layerId: string; /** The EnviroAtlas service the layer comes from */ service: ServiceRef; /** Sublayer id when a single MapServer sublayer was added */ sublayerId?: number; /** Display label shown in the added layers list */ label: string; /** Whether the layer is currently visible */ visible: boolean; /** Current raster opacity (0 to 1) */ opacity: number; /** Geographic bounds of the service data, when known */ bounds?: LngLatBoundsArray; } /** * An ArcGIS extent object (subset). */ declare interface ArcGISExtent { xmin: number; ymin: number; xmax: number; ymax: number; spatialReference?: { wkid?: number; latestWkid?: number; wkt?: string; wkt2?: string; }; } /** * Event types emitted by the EnviroAtlas control */ export declare type EnviroAtlasControlEvent = 'collapse' | 'expand' | 'statechange' | 'layeradd' | 'layerremove' | 'layerchange' | 'error'; /** * Payload passed to event handlers. */ export declare interface EnviroAtlasControlEventData { /** The event type */ type: EnviroAtlasControlEvent; /** A snapshot of the control state */ state: EnviroAtlasState; /** The affected layer for layer events */ layer?: AddedLayer; /** The error for 'error' events */ error?: Error; } /** * Event handler function type */ export declare type EnviroAtlasControlEventHandler = (event: EnviroAtlasControlEventData) => void; /** * Options for configuring the EnviroAtlasControl */ export declare interface EnviroAtlasControlOptions { /** * Whether the control panel should start collapsed (showing only the toggle button) * @default true */ collapsed?: boolean; /** * Position of the control on the map * @default 'top-right' */ position?: 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right'; /** * Title displayed in the control header * @default 'US EPA EnviroAtlas' */ title?: string; /** * Width of the control panel in pixels (capped to the viewport on small screens) * @default 360 */ panelWidth?: number; /** * Custom CSS class name for the control container */ className?: string; /** * Color theme for the control UI * @default 'auto' */ theme?: EnviroAtlasTheme; /** * ArcGIS REST services root to browse * @default 'https://enviroatlas.epa.gov/arcgis/rest/services' */ servicesUrl?: string; /** * Catalog folders to hide from browsing and search * @default ['test_services', 'Utilities', 'monitor'] */ excludedFolders?: string[]; /** * Initial opacity for newly added layers (0 to 1) * @default 1 */ defaultOpacity?: number; /** * How added layers are rendered. * * - `'image'` (default): one export request covers the visible map * area and refreshes when the view settles. Dynamic ArcGIS * services render each request server-side, so a single * viewport-sized request is much faster and more reliable than * dozens of tile requests. * - `'tiles'`: a raster tile source requesting one export per tile. * @default 'image' */ renderMode?: 'image' | 'tiles'; /** * Raster tile size in pixels (tiles render mode) * @default 256 */ tileSize?: number; /** * ArcGIS export image format * @default 'png32' */ imageFormat?: string; /** * Attribution string attached to added raster sources * @default 'U.S. EPA EnviroAtlas' */ attribution?: string; /** * Id of an existing map layer to insert added layers before * (e.g. a label layer so EnviroAtlas rasters render below labels). * When omitted or not found, layers are added on top. */ beforeId?: string; /** * Debounce delay for the search input in milliseconds * @default 250 */ searchDebounceMs?: number; /** * Whether to zoom the map to a layer's extent when it is added * @default true */ fitBoundsOnAdd?: boolean; /** * Whether to keep transient EnviroAtlas tile failures out of the * console. The EPA server occasionally answers tile requests * without CORS headers or with gateway timeouts; with this enabled * the control handles the map's error events for EnviroAtlas URLs * (emitting its own 'error' event instead) and logs all other map * errors as MapLibre would by default. * @default true */ quietTileErrors?: boolean; } /** * React wrapper component for EnviroAtlasControl. * * This component manages the lifecycle of an EnviroAtlasControl * instance, adding it to the map on mount and removing it on unmount. * * @example * ```tsx * import { EnviroAtlasControlReact } from 'maplibre-gl-enviroatlas/react'; * * function MyMap() { * const [map, setMap] = useState(null); * * return ( * <> *
* {map && ( * console.log('Added', layer.label)} * /> * )} * * ); * } * ``` * * @param props - Component props including map instance and control options * @returns null - This component renders nothing directly */ export declare function EnviroAtlasControlReact({ map, onStateChange, onLayerAdd, onLayerRemove, onError, ...options }: EnviroAtlasControlReactProps): null; /** * Props for the React wrapper component */ export declare interface EnviroAtlasControlReactProps extends EnviroAtlasControlOptions { /** * MapLibre GL map instance */ map: Map_2; /** * Callback fired when the control state changes */ onStateChange?: (state: EnviroAtlasState) => void; /** * Callback fired when a layer is added to the map */ onLayerAdd?: (layer: AddedLayer) => void; /** * Callback fired when a layer is removed from the map */ onLayerRemove?: (layer: AddedLayer) => void; /** * Callback fired when a catalog or network error occurs */ onError?: (error: Error) => void; } /** * Internal state of the EnviroAtlas control */ export declare interface EnviroAtlasState { /** * Whether the control panel is currently collapsed */ collapsed: boolean; /** * Current panel width in pixels */ panelWidth: number; /** * Current color theme */ theme: EnviroAtlasTheme; /** * Current search query */ query: string; /** * Layers added to the map through the control */ addedLayers: AddedLayer[]; /** * Any custom state data */ data?: Record; } /** * Color theme for the control UI. * * - `'light'` and `'dark'` force a palette. * - `'auto'` follows the user's `prefers-color-scheme` setting. */ export declare type EnviroAtlasTheme = 'light' | 'dark' | 'auto'; /** * Legend information for one layer of a service. */ export declare interface LayerLegend { /** The layer id within the service */ layerId: number; /** The layer name */ layerName: string; /** Legend swatches for the layer */ legend: LegendEntry[]; } /** * A single legend swatch entry for a layer. */ export declare interface LegendEntry { /** Legend label text */ label: string; /** Base64-encoded PNG image data */ imageData: string; /** Image content type (e.g. "image/png") */ contentType: string; /** Swatch width in pixels */ width: number; /** Swatch height in pixels */ height: number; } /** * Converts ArcGIS service extents to geographic (EPSG:4326) bounds. * * EnviroAtlas services publish extents in Web Mercator, geographic * coordinates, or one of several Albers Equal Area projections (the * server's GeometryServer project endpoint is unavailable, so the * inverse projection is computed client-side with a spherical * approximation, then padded). The resulting bounds are used both to * limit raster tile requests (the server times out with a 504 on * far-out-of-extent exports) and to zoom the map to newly added layers. */ /** Geographic bounds as [west, south, east, north] */ declare type LngLatBoundsArray = [number, number, number, number]; /** * A search result entry. Either a whole service or a single * sublayer within a MapServer service. */ export declare type SearchResult = { kind: 'service'; service: ServiceRef; } | { kind: 'sublayer'; service: ServiceRef; layer: ServiceLayer; }; /** * A single layer inside a MapServer service. */ export declare interface ServiceLayer { /** Numeric layer id used in `layers=show:{id}` export requests */ id: number; /** Human readable layer name */ name: string; /** Parent layer id, -1 for root layers */ parentLayerId: number; /** Child layer ids when this is a group layer */ subLayerIds: number[] | null; } /** * Metadata for a MapServer or ImageServer service (subset of the * ArcGIS JSON response). */ export declare interface ServiceMetadata { /** Display name reported by the server */ mapName?: string; /** Service description */ description?: string; /** Flat list of layers (empty for ImageServers) */ layers: ServiceLayer[]; /** Service extent (fullExtent for MapServers, extent for ImageServers) */ extent?: ArcGISExtent; } /** * A reference to a single ArcGIS service in the catalog. */ export declare interface ServiceRef { /** Folder the service lives in (e.g. "Communities") */ folder: string; /** Short service name without the folder prefix (e.g. "Community_BGmetrics") */ name: string; /** Full service name as returned by the server (e.g. "Communities/Community_BGmetrics") */ fullName: string; /** The ArcGIS service type */ type: ServiceType; } /** * The kind of ArcGIS service exposed by the EnviroAtlas server. */ export declare type ServiceType = 'MapServer' | 'ImageServer'; /** * Custom hook for tracking EnviroAtlas control state in React apps. * * @example * ```tsx * function MyComponent() { * const { state, setState, toggle } = useEnviroAtlas({ collapsed: false }); * * return ( *
* * *
* ); * } * ``` * * @param initialState - Optional initial state values * @returns Object containing state and update functions */ export declare function useEnviroAtlas(initialState?: Partial): { state: EnviroAtlasState; setState: Dispatch>; setCollapsed: (collapsed: boolean) => void; setPanelWidth: (panelWidth: number) => void; setTheme: (theme: EnviroAtlasTheme) => void; setData: (data: Record) => void; reset: () => void; toggle: () => void; }; export { }