{"version":3,"file":"react.mjs","names":[],"sources":["../src/lib/core/EnviroAtlasControlReact.tsx","../src/lib/hooks/useEnviroAtlas.ts"],"sourcesContent":["import { useEffect, useRef } from \"react\";\nimport { EnviroAtlasControl } from \"./EnviroAtlasControl\";\nimport type { EnviroAtlasControlReactProps } from \"./types\";\n\n/**\n * React wrapper component for EnviroAtlasControl.\n *\n * This component manages the lifecycle of an EnviroAtlasControl\n * instance, adding it to the map on mount and removing it on unmount.\n *\n * @example\n * ```tsx\n * import { EnviroAtlasControlReact } from 'maplibre-gl-enviroatlas/react';\n *\n * function MyMap() {\n *   const [map, setMap] = useState<Map | null>(null);\n *\n *   return (\n *     <>\n *       <div ref={mapContainer} />\n *       {map && (\n *         <EnviroAtlasControlReact\n *           map={map}\n *           collapsed={false}\n *           theme=\"auto\"\n *           onLayerAdd={(layer) => console.log('Added', layer.label)}\n *         />\n *       )}\n *     </>\n *   );\n * }\n * ```\n *\n * @param props - Component props including map instance and control options\n * @returns null - This component renders nothing directly\n */\nexport function EnviroAtlasControlReact({\n  map,\n  onStateChange,\n  onLayerAdd,\n  onLayerRemove,\n  onError,\n  ...options\n}: EnviroAtlasControlReactProps): null {\n  const controlRef = useRef<EnviroAtlasControl | null>(null);\n\n  // Keep latest callbacks without re-creating the control\n  const callbacksRef = useRef({ onStateChange, onLayerAdd, onLayerRemove, onError });\n  callbacksRef.current = { onStateChange, onLayerAdd, onLayerRemove, onError };\n\n  useEffect(() => {\n    if (!map) return;\n\n    // Create the control instance\n    const control = new EnviroAtlasControl(options);\n    controlRef.current = control;\n\n    control.on(\"statechange\", (event) => {\n      callbacksRef.current.onStateChange?.(event.state);\n    });\n    control.on(\"layeradd\", (event) => {\n      if (event.layer) callbacksRef.current.onLayerAdd?.(event.layer);\n    });\n    control.on(\"layerremove\", (event) => {\n      if (event.layer) callbacksRef.current.onLayerRemove?.(event.layer);\n    });\n    control.on(\"error\", (event) => {\n      if (event.error) callbacksRef.current.onError?.(event.error);\n    });\n\n    // Add control to map\n    map.addControl(control, options.position || \"top-right\");\n\n    // Cleanup on unmount\n    return () => {\n      if (map.hasControl(control)) {\n        map.removeControl(control);\n      }\n      controlRef.current = null;\n    };\n  }, [map]);\n\n  // Update collapsed state when the prop changes\n  useEffect(() => {\n    if (controlRef.current && options.collapsed !== undefined) {\n      const currentState = controlRef.current.getState();\n      if (options.collapsed !== currentState.collapsed) {\n        if (options.collapsed) {\n          controlRef.current.collapse();\n        } else {\n          controlRef.current.expand();\n        }\n      }\n    }\n  }, [options.collapsed]);\n\n  // Update theme when the prop changes\n  useEffect(() => {\n    if (controlRef.current && options.theme !== undefined) {\n      if (controlRef.current.getState().theme !== options.theme) {\n        controlRef.current.setTheme(options.theme);\n      }\n    }\n  }, [options.theme]);\n\n  // Update panel width when the prop changes\n  useEffect(() => {\n    if (controlRef.current && options.panelWidth !== undefined) {\n      if (controlRef.current.getState().panelWidth !== options.panelWidth) {\n        controlRef.current.setPanelWidth(options.panelWidth);\n      }\n    }\n  }, [options.panelWidth]);\n\n  return null;\n}\n","import { useState, useCallback } from 'react';\nimport type { EnviroAtlasState, EnviroAtlasTheme } from '../core/types';\n\n/**\n * Default initial state for the EnviroAtlas control\n */\nconst DEFAULT_STATE: EnviroAtlasState = {\n  collapsed: true,\n  panelWidth: 360,\n  theme: 'auto',\n  query: '',\n  addedLayers: [],\n  data: {},\n};\n\n/**\n * Custom hook for tracking EnviroAtlas control state in React apps.\n *\n * @example\n * ```tsx\n * function MyComponent() {\n *   const { state, setState, toggle } = useEnviroAtlas({ collapsed: false });\n *\n *   return (\n *     <div>\n *       <button onClick={toggle}>\n *         {state.collapsed ? 'Expand' : 'Collapse'}\n *       </button>\n *       <EnviroAtlasControlReact\n *         map={map}\n *         collapsed={state.collapsed}\n *         onStateChange={setState}\n *       />\n *     </div>\n *   );\n * }\n * ```\n *\n * @param initialState - Optional initial state values\n * @returns Object containing state and update functions\n */\nexport function useEnviroAtlas(initialState?: Partial<EnviroAtlasState>) {\n  const [state, setState] = useState<EnviroAtlasState>({\n    ...DEFAULT_STATE,\n    ...initialState,\n  });\n\n  /**\n   * Sets the collapsed state\n   */\n  const setCollapsed = useCallback((collapsed: boolean) => {\n    setState((prev) => ({ ...prev, collapsed }));\n  }, []);\n\n  /**\n   * Sets the panel width\n   */\n  const setPanelWidth = useCallback((panelWidth: number) => {\n    setState((prev) => ({ ...prev, panelWidth }));\n  }, []);\n\n  /**\n   * Sets the color theme\n   */\n  const setTheme = useCallback((theme: EnviroAtlasTheme) => {\n    setState((prev) => ({ ...prev, theme }));\n  }, []);\n\n  /**\n   * Sets custom data in the state\n   */\n  const setData = useCallback((data: Record<string, unknown>) => {\n    setState((prev) => ({ ...prev, data: { ...prev.data, ...data } }));\n  }, []);\n\n  /**\n   * Resets the state to default values\n   */\n  const reset = useCallback(() => {\n    setState({ ...DEFAULT_STATE, ...initialState });\n  }, [initialState]);\n\n  /**\n   * Toggles the collapsed state\n   */\n  const toggle = useCallback(() => {\n    setState((prev) => ({ ...prev, collapsed: !prev.collapsed }));\n  }, []);\n\n  return {\n    state,\n    setState,\n    setCollapsed,\n    setPanelWidth,\n    setTheme,\n    setData,\n    reset,\n    toggle,\n  };\n}\n"],"mappings":"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"}