{"version":3,"file":"PlanetaryComputerControl-8tNQxMX0.cjs","sources":["../src/lib/api/stac-client.ts","../src/lib/api/titiler-client.ts","../src/lib/api/sas-token.ts","../src/lib/api/render-presets.ts","../src/lib/utils/helpers.ts","../src/lib/core/LayerManager.ts","../src/lib/core/PlanetaryComputerControl.ts"],"sourcesContent":["import type {\n  STACCollection,\n  STACCollectionsResponse,\n  STACItem,\n  STACItemCollection,\n  STACSearchParams,\n} from './types';\n\nconst DEFAULT_STAC_URL = 'https://planetarycomputer.microsoft.com/api/stac/v1';\n\n/**\n * Client for interacting with the Planetary Computer STAC API.\n * Provides methods for browsing collections, searching items, and fetching metadata.\n */\nexport class STACClient {\n  private baseUrl: string;\n  private abortController: AbortController | null = null;\n\n  /**\n   * Creates a new STAC API client.\n   *\n   * @param baseUrl - Base URL for the STAC API.\n   */\n  constructor(baseUrl: string = DEFAULT_STAC_URL) {\n    this.baseUrl = baseUrl.replace(/\\/$/, '');\n  }\n\n  /**\n   * Fetches all available collections.\n   *\n   * @returns Promise resolving to array of collections.\n   */\n  async getCollections(): Promise<STACCollection[]> {\n    const response = await this.fetch<STACCollectionsResponse>('/collections');\n    return response.collections;\n  }\n\n  /**\n   * Fetches a single collection by ID.\n   *\n   * @param collectionId - Collection identifier.\n   * @returns Promise resolving to collection metadata.\n   */\n  async getCollection(collectionId: string): Promise<STACCollection> {\n    return this.fetch<STACCollection>(`/collections/${encodeURIComponent(collectionId)}`);\n  }\n\n  /**\n   * Searches for items matching the given parameters.\n   *\n   * @param params - Search parameters (bbox, datetime, collections, etc.).\n   * @returns Promise resolving to array of matching items.\n   */\n  async search(params: STACSearchParams): Promise<STACItem[]> {\n    // Cancel any pending search\n    this.abortController?.abort();\n    this.abortController = new AbortController();\n\n    const response = await this.fetch<STACItemCollection>('/search', {\n      method: 'POST',\n      headers: { 'Content-Type': 'application/json' },\n      body: JSON.stringify(params),\n      signal: this.abortController.signal,\n    });\n\n    return response.features;\n  }\n\n  /**\n   * Searches for items and returns the full response with context.\n   *\n   * @param params - Search parameters.\n   * @returns Promise resolving to the full item collection response.\n   */\n  async searchWithContext(params: STACSearchParams): Promise<STACItemCollection> {\n    this.abortController?.abort();\n    this.abortController = new AbortController();\n\n    return this.fetch<STACItemCollection>('/search', {\n      method: 'POST',\n      headers: { 'Content-Type': 'application/json' },\n      body: JSON.stringify(params),\n      signal: this.abortController.signal,\n    });\n  }\n\n  /**\n   * Fetches items from a specific collection.\n   *\n   * @param collectionId - Collection identifier.\n   * @param limit - Maximum number of items to return.\n   * @returns Promise resolving to array of items.\n   */\n  async getCollectionItems(collectionId: string, limit: number = 50): Promise<STACItem[]> {\n    const response = await this.fetch<STACItemCollection>(\n      `/collections/${encodeURIComponent(collectionId)}/items?limit=${limit}`\n    );\n    return response.features;\n  }\n\n  /**\n   * Fetches a single item by collection and item ID.\n   *\n   * @param collectionId - Collection identifier.\n   * @param itemId - Item identifier.\n   * @returns Promise resolving to item metadata.\n   */\n  async getItem(collectionId: string, itemId: string): Promise<STACItem> {\n    return this.fetch<STACItem>(\n      `/collections/${encodeURIComponent(collectionId)}/items/${encodeURIComponent(itemId)}`\n    );\n  }\n\n  /**\n   * Cancels any pending requests.\n   */\n  cancelPending(): void {\n    this.abortController?.abort();\n    this.abortController = null;\n  }\n\n  /**\n   * Gets the base URL of the STAC API.\n   *\n   * @returns The base URL.\n   */\n  getBaseUrl(): string {\n    return this.baseUrl;\n  }\n\n  /**\n   * Internal fetch wrapper with error handling.\n   *\n   * @param path - API path.\n   * @param options - Fetch options.\n   * @returns Promise resolving to parsed JSON response.\n   */\n  private async fetch<T>(path: string, options?: RequestInit): Promise<T> {\n    const url = `${this.baseUrl}${path}`;\n\n    try {\n      const response = await fetch(url, options);\n\n      if (!response.ok) {\n        const errorText = await response.text();\n        throw new Error(`STAC API error: ${response.status} ${response.statusText} - ${errorText}`);\n      }\n\n      return response.json();\n    } catch (error) {\n      if (error instanceof Error && error.name === 'AbortError') {\n        throw new Error('Request was cancelled');\n      }\n      throw error;\n    }\n  }\n}\n","import type {\n  PointValueResponse,\n  StatisticsParams,\n  TileJSONMetadata,\n  TileParams,\n  STACSearchParams,\n} from './types';\n\nconst DEFAULT_TILER_URL = 'https://planetarycomputer.microsoft.com/api/data/v1';\n\n/**\n * Client for interacting with the Planetary Computer TiTiler API.\n * Provides methods for generating tile URLs for visualization.\n */\nexport class TiTilerClient {\n  private baseUrl: string;\n\n  /**\n   * Creates a new TiTiler API client.\n   *\n   * @param baseUrl - Base URL for the TiTiler API.\n   */\n  constructor(baseUrl: string = DEFAULT_TILER_URL) {\n    this.baseUrl = baseUrl.replace(/\\/$/, '');\n  }\n\n  /**\n   * Generates a tile URL template for a single STAC item.\n   *\n   * @param collectionId - Collection identifier.\n   * @param itemId - Item identifier.\n   * @param params - Tile rendering parameters.\n   * @returns Tile URL template with {z}/{x}/{y} placeholders.\n   */\n  getItemTileUrl(collectionId: string, itemId: string, params: TileParams = {}): string {\n    const queryString = this.buildQueryString(params);\n    const scale = params.tile_scale || 1;\n    const format = params.tile_format ? `.${params.tile_format}` : '';\n    return `${this.baseUrl}/item/tiles/WebMercatorQuad/{z}/{x}/{y}@${scale}x${format}?collection=${encodeURIComponent(collectionId)}&item=${encodeURIComponent(itemId)}${queryString ? '&' + queryString : ''}`;\n  }\n\n  /**\n   * Generates a tile URL for a collection mosaic.\n   *\n   * @param collectionId - Collection identifier.\n   * @param params - Tile rendering parameters.\n   * @param searchParams - Optional STAC search parameters for filtering the mosaic.\n   * @returns Tile URL template with {z}/{x}/{y} placeholders.\n   */\n  getCollectionTileUrl(\n    collectionId: string,\n    params: TileParams = {},\n    searchParams?: Partial<STACSearchParams>\n  ): string {\n    const tileParams = this.buildQueryString(params);\n    const searchStr = searchParams ? this.buildSearchParams(searchParams) : '';\n\n    const allParams = [\n      `collection=${encodeURIComponent(collectionId)}`,\n      tileParams,\n      searchStr,\n    ]\n      .filter(Boolean)\n      .join('&');\n\n    const scale = params.tile_scale || 1;\n    const format = params.tile_format ? `.${params.tile_format}` : '';\n    return `${this.baseUrl}/mosaic/tiles/WebMercatorQuad/{z}/{x}/{y}@${scale}x${format}?${allParams}`;\n  }\n\n  /**\n   * Fetches TileJSON metadata for a STAC item.\n   *\n   * @param collectionId - Collection identifier.\n   * @param itemId - Item identifier.\n   * @param params - Tile rendering parameters.\n   * @returns Promise resolving to TileJSON metadata.\n   */\n  async getItemTileJSON(\n    collectionId: string,\n    itemId: string,\n    params: TileParams = {}\n  ): Promise<TileJSONMetadata> {\n    const queryString = this.buildQueryString(params);\n    const response = await fetch(\n      `${this.baseUrl}/item/WebMercatorQuad/tilejson.json?collection=${encodeURIComponent(collectionId)}&item=${encodeURIComponent(itemId)}${queryString ? '&' + queryString : ''}`\n    );\n\n    if (!response.ok) {\n      throw new Error(`Failed to get item TileJSON: ${response.statusText}`);\n    }\n\n    return response.json();\n  }\n\n  /**\n   * Gets the TileJSON URL for a STAC item.\n   *\n   * @param collectionId - Collection identifier.\n   * @param itemId - Item identifier.\n   * @param params - Tile rendering parameters.\n   * @returns TileJSON URL.\n   */\n  getItemTileJSONUrl(collectionId: string, itemId: string, params: TileParams = {}): string {\n    const queryString = this.buildQueryString(params);\n    return `${this.baseUrl}/item/WebMercatorQuad/tilejson.json?collection=${encodeURIComponent(collectionId)}&item=${encodeURIComponent(itemId)}${queryString ? '&' + queryString : ''}`;\n  }\n\n  /**\n   * Fetches TileJSON metadata for a collection mosaic.\n   *\n   * @param collectionId - Collection identifier.\n   * @param params - Tile rendering parameters.\n   * @param searchParams - Optional STAC search parameters for filtering the mosaic.\n   * @returns Promise resolving to TileJSON metadata.\n   */\n  async getCollectionTileJSON(\n    collectionId: string,\n    params: TileParams = {},\n    searchParams?: Partial<STACSearchParams>\n  ): Promise<TileJSONMetadata> {\n    const tileParams = this.buildQueryString(params);\n    const searchStr = searchParams ? this.buildSearchParams(searchParams) : '';\n    const query = [\n      `collection=${encodeURIComponent(collectionId)}`,\n      tileParams,\n      searchStr,\n    ]\n      .filter(Boolean)\n      .join('&');\n    const response = await fetch(`${this.baseUrl}/mosaic/WebMercatorQuad/tilejson.json?${query}`);\n\n    if (!response.ok) {\n      throw new Error(`Failed to get collection TileJSON: ${response.statusText}`);\n    }\n\n    return response.json();\n  }\n\n  /**\n   * Registers a custom search mosaic and returns the tile URL.\n   *\n   * @param searchParams - STAC search parameters for the mosaic.\n   * @param tileParams - Tile rendering parameters.\n   * @returns Promise resolving to mosaic info including tile URL and search ID.\n   */\n  async registerMosaic(\n    searchParams: STACSearchParams,\n    tileParams: TileParams = {}\n  ): Promise<{ searchId: string; tileUrl: string }> {\n    const response = await fetch(`${this.baseUrl}/mosaic/register`, {\n      method: 'POST',\n      headers: { 'Content-Type': 'application/json' },\n      body: JSON.stringify({\n        collections: searchParams.collections,\n        filter: searchParams.filter,\n        'filter-lang': searchParams['filter-lang'] || 'cql2-json',\n        sortby: searchParams.sortby,\n      }),\n    });\n\n    if (!response.ok) {\n      throw new Error(`Failed to register mosaic: ${response.statusText}`);\n    }\n\n    const data = await response.json();\n    const searchId = data.id || data.searchid;\n    const queryString = this.buildQueryString(tileParams);\n\n    return {\n      searchId,\n      tileUrl: `${this.baseUrl}/mosaic/tiles/WebMercatorQuad/{z}/{x}/{y}@1x?searchid=${searchId}${queryString ? '&' + queryString : ''}`,\n    };\n  }\n\n  /**\n   * Fetches metadata for a STAC item (bounds, statistics, etc.).\n   *\n   * @param collectionId - Collection identifier.\n   * @param itemId - Item identifier.\n   * @param assets - Asset names to include.\n   * @returns Promise resolving to item info.\n   */\n  async getItemInfo(\n    collectionId: string,\n    itemId: string,\n    assets?: string[]\n  ): Promise<Record<string, unknown>> {\n    const assetParam = assets?.length ? `&assets=${assets.join(',')}` : '';\n    const response = await fetch(\n      `${this.baseUrl}/item/info?collection=${encodeURIComponent(collectionId)}&item=${encodeURIComponent(itemId)}${assetParam}`\n    );\n\n    if (!response.ok) {\n      throw new Error(`Failed to get item info: ${response.statusText}`);\n    }\n\n    return response.json();\n  }\n\n  /**\n   * Fetches available statistics for an item.\n   *\n   * @param collectionId - Collection identifier.\n   * @param itemId - Item identifier.\n   * @param assets - Asset names.\n   * @returns Promise resolving to statistics.\n   */\n  async getItemStatistics(\n    collectionId: string,\n    itemId: string,\n    params: StatisticsParams = {}\n  ): Promise<Record<string, unknown>> {\n    const queryString = this.buildQueryString(params);\n    const query = queryString ? `&${queryString}` : '';\n    const response = await fetch(\n      `${this.baseUrl}/item/statistics?collection=${encodeURIComponent(collectionId)}&item=${encodeURIComponent(itemId)}${query}`\n    );\n\n    if (!response.ok) {\n      throw new Error(`Failed to get item statistics: ${response.statusText}`);\n    }\n\n    return response.json();\n  }\n\n  /**\n   * Gets pixel values for a STAC item at a coordinate.\n   *\n   * @param collectionId - Collection identifier.\n   * @param itemId - Item identifier.\n   * @param lon - Longitude.\n   * @param lat - Latitude.\n   * @param params - Rendering parameters.\n   * @returns Promise resolving to point values.\n   */\n  async getItemPoint(\n    collectionId: string,\n    itemId: string,\n    lon: number,\n    lat: number,\n    params: TileParams = {}\n  ): Promise<PointValueResponse> {\n    const queryString = this.buildQueryString(params);\n    const query = queryString ? `&${queryString}` : '';\n    const response = await fetch(\n      `${this.baseUrl}/item/point/${lon},${lat}?collection=${encodeURIComponent(collectionId)}&item=${encodeURIComponent(itemId)}${query}`\n    );\n\n    if (!response.ok) {\n      throw new Error(await this.getErrorMessage(response, 'Failed to get point values'));\n    }\n\n    return response.json();\n  }\n\n  /**\n   * Builds an informative error message from an API response.\n   */\n  private async getErrorMessage(response: Response, fallback: string): Promise<string> {\n    let detail = '';\n\n    try {\n      const contentType = response.headers.get('content-type') || '';\n      if (contentType.includes('application/json')) {\n        const body = await response.json();\n        const rawDetail = body.detail || body.message || body.error;\n        detail = Array.isArray(rawDetail) ? rawDetail.map((entry) => entry.msg || String(entry)).join('; ') : String(rawDetail || '');\n      } else {\n        detail = await response.text();\n      }\n    } catch {\n      detail = '';\n    }\n\n    const status = response.statusText || `HTTP ${response.status}`;\n    return [fallback, detail || status].filter(Boolean).join(': ');\n  }\n\n  /**\n   * Gets a rendered preview URL for a STAC item.\n   *\n   * @param collectionId - Collection identifier.\n   * @param itemId - Item identifier.\n   * @param params - Rendering parameters.\n   * @param format - Output image format.\n   * @returns Preview image URL.\n   */\n  getItemPreviewUrl(\n    collectionId: string,\n    itemId: string,\n    params: TileParams = {},\n    format: 'png' | 'jpg' | 'jpeg' | 'webp' = 'png'\n  ): string {\n    const queryString = this.buildQueryString(params);\n    return `${this.baseUrl}/item/preview.${format}?collection=${encodeURIComponent(collectionId)}&item=${encodeURIComponent(itemId)}${queryString ? '&' + queryString : ''}`;\n  }\n\n  /**\n   * Gets a rendered bbox image URL for a STAC item.\n   *\n   * @param collectionId - Collection identifier.\n   * @param itemId - Item identifier.\n   * @param bbox - Bounding box [west, south, east, north].\n   * @param size - Output image size.\n   * @param params - Rendering parameters.\n   * @param format - Output image format.\n   * @returns Bbox image URL.\n   */\n  getItemBboxImageUrl(\n    collectionId: string,\n    itemId: string,\n    bbox: [number, number, number, number],\n    size: { width: number; height: number } = { width: 768, height: 512 },\n    params: TileParams = {},\n    format: 'png' | 'jpg' | 'jpeg' | 'webp' = 'png'\n  ): string {\n    const queryString = this.buildQueryString(params);\n    return `${this.baseUrl}/item/bbox/${bbox.join(',')}/${size.width}x${size.height}.${format}?collection=${encodeURIComponent(collectionId)}&item=${encodeURIComponent(itemId)}${queryString ? '&' + queryString : ''}`;\n  }\n\n  /**\n   * Gets a legend image URL for a named colormap.\n   *\n   * @param colormapName - Named colormap.\n   * @param size - Legend image size.\n   * @returns Legend image URL.\n   */\n  getColormapLegendUrl(\n    colormapName: string,\n    size: { width: number; height: number } = { width: 220, height: 30 }\n  ): string {\n    return `${this.baseUrl}/legend/colormap/${encodeURIComponent(colormapName)}?width=${size.width}&height=${size.height}`;\n  }\n\n  /**\n   * Gets the base URL of the TiTiler API.\n   *\n   * @returns The base URL.\n   */\n  getBaseUrl(): string {\n    return this.baseUrl;\n  }\n\n  /**\n   * Builds query string from tile parameters.\n   *\n   * @param params - Tile parameters.\n   * @returns URL query string.\n   */\n  private buildQueryString(params: TileParams): string {\n    const searchParams = new URLSearchParams();\n\n    if (params.assets?.length) {\n      params.assets.forEach((asset) => searchParams.append('assets', asset));\n    }\n    if (params.bidx?.length) {\n      params.bidx.forEach((bidx) => searchParams.append('bidx', String(bidx)));\n    }\n    if (params.expression) {\n      searchParams.set('expression', params.expression);\n    }\n    if (params.rescale) {\n      searchParams.set('rescale', params.rescale);\n    }\n    if (params.colormap_name) {\n      searchParams.set('colormap_name', params.colormap_name);\n    }\n    if (params.colormap) {\n      searchParams.set('colormap', JSON.stringify(params.colormap));\n    }\n    if (params.nodata !== undefined) {\n      searchParams.set('nodata', String(params.nodata));\n    }\n    if (params.resampling) {\n      searchParams.set('resampling', params.resampling);\n    }\n    if (params.return_mask !== undefined) {\n      searchParams.set('return_mask', String(params.return_mask));\n    }\n    if (params.unscale !== undefined) {\n      searchParams.set('unscale', String(params.unscale));\n    }\n    if (params.color_formula) {\n      searchParams.set('color_formula', params.color_formula);\n    }\n    if (params.asset_as_band !== undefined) {\n      searchParams.set('asset_as_band', String(params.asset_as_band));\n    }\n    if (params.algorithm) {\n      searchParams.set('algorithm', params.algorithm);\n    }\n    if (params.algorithm_params) {\n      searchParams.set('algorithm_params', params.algorithm_params);\n    }\n    if (params.buffer !== undefined) {\n      searchParams.set('buffer', String(params.buffer));\n    }\n    if (params.tile_format) {\n      searchParams.set('tile_format', params.tile_format);\n    }\n    if (params.tile_scale) {\n      searchParams.set('tile_scale', String(params.tile_scale));\n    }\n    if (params.minzoom !== undefined) {\n      searchParams.set('minzoom', String(params.minzoom));\n    }\n    if (params.maxzoom !== undefined) {\n      searchParams.set('maxzoom', String(params.maxzoom));\n    }\n    if (params.tile_size) {\n      searchParams.set('tile_size', String(params.tile_size));\n    }\n    if (params.asset_bidx) {\n      Object.entries(params.asset_bidx).forEach(([asset, bidx]) => {\n        searchParams.append('asset_bidx', `${asset}|${bidx}`);\n      });\n    }\n    const statisticsParams = params as StatisticsParams;\n    if (statisticsParams.max_size !== undefined) {\n      searchParams.set('max_size', String(statisticsParams.max_size));\n    }\n    if (statisticsParams.height !== undefined) {\n      searchParams.set('height', String(statisticsParams.height));\n    }\n    if (statisticsParams.width !== undefined) {\n      searchParams.set('width', String(statisticsParams.width));\n    }\n    if (statisticsParams.categorical !== undefined) {\n      searchParams.set('categorical', String(statisticsParams.categorical));\n    }\n    if (statisticsParams.c?.length) {\n      statisticsParams.c.forEach((value) => searchParams.append('c', String(value)));\n    }\n    if (statisticsParams.p?.length) {\n      statisticsParams.p.forEach((value) => searchParams.append('p', String(value)));\n    }\n    if (statisticsParams.histogram_bins !== undefined) {\n      searchParams.set('histogram_bins', String(statisticsParams.histogram_bins));\n    }\n    if (statisticsParams.histogram_range) {\n      searchParams.set('histogram_range', statisticsParams.histogram_range.join(','));\n    }\n\n    return searchParams.toString();\n  }\n\n  /**\n   * Builds search parameters for mosaic requests.\n   *\n   * @param params - STAC search parameters.\n   * @returns URL query string.\n   */\n  private buildSearchParams(params: Partial<STACSearchParams>): string {\n    const parts: string[] = [];\n\n    if (params.datetime) {\n      parts.push(`datetime=${encodeURIComponent(params.datetime)}`);\n    }\n    if (params.bbox) {\n      parts.push(`bbox=${params.bbox.join(',')}`);\n    }\n\n    return parts.join('&');\n  }\n}\n","import type { SASTokenResponse } from './types';\n\nconst SAS_TOKEN_URL = 'https://planetarycomputer.microsoft.com/api/sas/v1/token';\n\ninterface TokenCache {\n  token: string;\n  expiry: Date;\n}\n\n/**\n * Manages SAS tokens for accessing Planetary Computer assets.\n * Implements token caching to minimize API calls.\n */\nexport class SASTokenManager {\n  private cache: Map<string, TokenCache> = new Map();\n  private bufferMs: number;\n\n  /**\n   * Creates a new SAS token manager.\n   *\n   * @param bufferMs - Buffer time before expiry to refresh token (default: 5 min).\n   */\n  constructor(bufferMs: number = 5 * 60 * 1000) {\n    this.bufferMs = bufferMs;\n  }\n\n  /**\n   * Gets a valid SAS token for the given collection.\n   *\n   * @param collectionId - Collection identifier.\n   * @returns Promise resolving to SAS token string.\n   */\n  async getToken(collectionId: string): Promise<string> {\n    const cached = this.cache.get(collectionId);\n    const now = new Date();\n\n    // Return cached token if still valid\n    if (cached && cached.expiry.getTime() - now.getTime() > this.bufferMs) {\n      return cached.token;\n    }\n\n    // Fetch new token\n    const response = await fetch(`${SAS_TOKEN_URL}/${encodeURIComponent(collectionId)}`);\n\n    if (!response.ok) {\n      throw new Error(`Failed to get SAS token for ${collectionId}: ${response.statusText}`);\n    }\n\n    const data: SASTokenResponse = await response.json();\n    const token = data.token;\n    const expiry = new Date(data['msft:expiry']);\n\n    // Cache the token\n    this.cache.set(collectionId, { token, expiry });\n\n    return token;\n  }\n\n  /**\n   * Signs a URL with a SAS token.\n   *\n   * @param url - URL to sign.\n   * @param collectionId - Collection identifier for token lookup.\n   * @returns Promise resolving to signed URL.\n   */\n  async signUrl(url: string, collectionId: string): Promise<string> {\n    const token = await this.getToken(collectionId);\n    const separator = url.includes('?') ? '&' : '?';\n    return `${url}${separator}${token}`;\n  }\n\n  /**\n   * Checks if a token is cached and valid for a collection.\n   *\n   * @param collectionId - Collection identifier.\n   * @returns True if a valid token is cached.\n   */\n  hasValidToken(collectionId: string): boolean {\n    const cached = this.cache.get(collectionId);\n    if (!cached) return false;\n\n    const now = new Date();\n    return cached.expiry.getTime() - now.getTime() > this.bufferMs;\n  }\n\n  /**\n   * Clears the token cache.\n   */\n  clearCache(): void {\n    this.cache.clear();\n  }\n\n  /**\n   * Clears the cached token for a specific collection.\n   *\n   * @param collectionId - Collection identifier.\n   */\n  clearToken(collectionId: string): void {\n    this.cache.delete(collectionId);\n  }\n}\n","import type { CollectionRenderConfig, RenderPreset } from './types';\n\n/**\n * Render presets for Sentinel-2 L2A collection.\n */\nconst sentinel2L2aPresets: RenderPreset[] = [\n  {\n    name: 'true-color',\n    label: 'True Color',\n    description: 'Natural color composite (RGB)',\n    params: {\n      assets: ['visual'],\n    },\n  },\n  {\n    name: 'false-color',\n    label: 'False Color (Vegetation)',\n    description: 'NIR-Red-Green composite for vegetation analysis',\n    params: {\n      assets: ['B08', 'B04', 'B03'],\n      rescale: '0,3000',\n    },\n  },\n  {\n    name: 'ndvi',\n    label: 'NDVI',\n    description: 'Normalized Difference Vegetation Index',\n    params: {\n      expression: '(B08-B04)/(B08+B04)',\n      rescale: '-1,1',\n      colormap_name: 'rdylgn',\n    },\n  },\n  {\n    name: 'ndwi',\n    label: 'NDWI',\n    description: 'Normalized Difference Water Index',\n    params: {\n      expression: '(B03-B08)/(B03+B08)',\n      rescale: '-1,1',\n      colormap_name: 'blues',\n    },\n  },\n  {\n    name: 'swir',\n    label: 'SWIR Composite',\n    description: 'SWIR-NIR-Red for geology and moisture',\n    params: {\n      assets: ['B12', 'B08', 'B04'],\n      rescale: '0,3000',\n    },\n  },\n];\n\n/**\n * Render presets for Landsat Collection 2 Level-2.\n */\nconst landsatC2L2Presets: RenderPreset[] = [\n  {\n    name: 'true-color',\n    label: 'True Color',\n    description: 'Natural color composite (RGB)',\n    params: {\n      assets: ['red', 'green', 'blue'],\n      rescale: '0,20000',\n    },\n  },\n  {\n    name: 'false-color',\n    label: 'False Color (Vegetation)',\n    description: 'NIR-Red-Green composite',\n    params: {\n      assets: ['nir08', 'red', 'green'],\n      rescale: '0,20000',\n    },\n  },\n  {\n    name: 'ndvi',\n    label: 'NDVI',\n    description: 'Normalized Difference Vegetation Index',\n    params: {\n      expression: '(nir08-red)/(nir08+red)',\n      rescale: '-1,1',\n      colormap_name: 'rdylgn',\n    },\n  },\n  {\n    name: 'thermal',\n    label: 'Thermal',\n    description: 'Land surface temperature',\n    params: {\n      assets: ['lwir11'],\n      rescale: '290,320',\n      colormap_name: 'magma',\n    },\n  },\n];\n\n/**\n * Render presets for NAIP imagery.\n */\nconst naipPresets: RenderPreset[] = [\n  {\n    name: 'rgb',\n    label: 'RGB',\n    description: 'Natural color',\n    params: {\n      assets: ['image'],\n      asset_bidx: { image: '1,2,3' },\n    },\n  },\n  {\n    name: 'cir',\n    label: 'Color Infrared',\n    description: 'NIR-Red-Green composite',\n    params: {\n      assets: ['image'],\n      asset_bidx: { image: '4,1,2' },\n    },\n  },\n  {\n    name: 'ndvi',\n    label: 'NDVI',\n    description: 'Vegetation index from NAIP',\n    params: {\n      expression: '(image_b4-image_b1)/(image_b4+image_b1)',\n      rescale: '-1,1',\n      colormap_name: 'rdylgn',\n    },\n  },\n];\n\n/**\n * Render presets for Copernicus DEM.\n */\nconst demPresets: RenderPreset[] = [\n  {\n    name: 'elevation',\n    label: 'Elevation',\n    description: 'Color-coded elevation',\n    params: {\n      assets: ['data'],\n      colormap_name: 'terrain',\n      rescale: '0,4000',\n    },\n  },\n  {\n    name: 'hillshade',\n    label: 'Hillshade',\n    description: 'Shaded relief visualization',\n    params: {\n      assets: ['data'],\n      colormap_name: 'gray',\n      rescale: '0,255',\n    },\n  },\n];\n\n/**\n * Default render configurations for common collections.\n */\nexport const RENDER_CONFIGS: CollectionRenderConfig[] = [\n  {\n    collectionId: 'sentinel-2-l2a',\n    defaultPreset: 'true-color',\n    presets: sentinel2L2aPresets,\n  },\n  {\n    collectionId: 'landsat-c2-l2',\n    defaultPreset: 'true-color',\n    presets: landsatC2L2Presets,\n  },\n  {\n    collectionId: 'naip',\n    defaultPreset: 'rgb',\n    presets: naipPresets,\n  },\n  {\n    collectionId: 'cop-dem-glo-30',\n    defaultPreset: 'elevation',\n    presets: demPresets,\n  },\n  {\n    collectionId: 'cop-dem-glo-90',\n    defaultPreset: 'elevation',\n    presets: demPresets,\n  },\n];\n\n/**\n * Gets render configuration for a collection.\n *\n * @param collectionId - Collection identifier.\n * @returns Render configuration or undefined if not found.\n */\nexport function getRenderConfig(collectionId: string): CollectionRenderConfig | undefined {\n  return RENDER_CONFIGS.find((config) => config.collectionId === collectionId);\n}\n\n/**\n * Gets available presets for a collection.\n *\n * @param collectionId - Collection identifier.\n * @returns Array of render presets.\n */\nexport function getPresetsForCollection(collectionId: string): RenderPreset[] {\n  const config = getRenderConfig(collectionId);\n  return config?.presets ?? [];\n}\n\n/**\n * Gets the default preset for a collection.\n *\n * @param collectionId - Collection identifier.\n * @returns Default render preset or undefined.\n */\nexport function getDefaultPreset(collectionId: string): RenderPreset | undefined {\n  const config = getRenderConfig(collectionId);\n  if (!config) return undefined;\n  return config.presets.find((p) => p.name === config.defaultPreset);\n}\n\n/**\n * Gets a specific preset by name for a collection.\n *\n * @param collectionId - Collection identifier.\n * @param presetName - Preset name.\n * @returns Render preset or undefined.\n */\nexport function getPreset(collectionId: string, presetName: string): RenderPreset | undefined {\n  const config = getRenderConfig(collectionId);\n  return config?.presets.find((p) => p.name === presetName);\n}\n","/**\n * Generates a unique ID with optional prefix.\n *\n * @param prefix - Optional prefix for the ID.\n * @returns Unique identifier string.\n */\nexport function generateId(prefix: string = ''): string {\n  const timestamp = Date.now().toString(36);\n  const randomPart = Math.random().toString(36).substring(2, 8);\n  return prefix ? `${prefix}-${timestamp}-${randomPart}` : `${timestamp}-${randomPart}`;\n}\n\n/**\n * Debounces a function call.\n *\n * @param fn - Function to debounce.\n * @param delay - Delay in milliseconds.\n * @returns Debounced function.\n */\nexport function debounce<T extends (...args: unknown[]) => void>(\n  fn: T,\n  delay: number\n): (...args: Parameters<T>) => void {\n  let timeoutId: ReturnType<typeof setTimeout>;\n\n  return (...args: Parameters<T>) => {\n    clearTimeout(timeoutId);\n    timeoutId = setTimeout(() => fn(...args), delay);\n  };\n}\n\n/**\n * Throttles a function call.\n *\n * @param fn - Function to throttle.\n * @param limit - Time limit in milliseconds.\n * @returns Throttled function.\n */\nexport function throttle<T extends (...args: unknown[]) => void>(\n  fn: T,\n  limit: number\n): (...args: Parameters<T>) => void {\n  let inThrottle = false;\n\n  return (...args: Parameters<T>) => {\n    if (!inThrottle) {\n      fn(...args);\n      inThrottle = true;\n      setTimeout(() => {\n        inThrottle = false;\n      }, limit);\n    }\n  };\n}\n\n/**\n * Clamps a value between min and max.\n *\n * @param value - Value to clamp.\n * @param min - Minimum value.\n * @param max - Maximum value.\n * @returns Clamped value.\n */\nexport function clamp(value: number, min: number, max: number): number {\n  return Math.min(Math.max(value, min), max);\n}\n\n/**\n * Formats a date string for display.\n *\n * @param dateStr - ISO date string.\n * @returns Formatted date string.\n */\nexport function formatDate(dateStr: string | null | undefined): string {\n  if (!dateStr) return 'Unknown';\n  try {\n    return new Date(dateStr).toLocaleDateString();\n  } catch {\n    return dateStr;\n  }\n}\n\n/**\n * Gets the best available date from STAC item properties.\n * Checks datetime, start_datetime, and end_datetime in order.\n *\n * @param properties - STAC item properties.\n * @returns Date string or null.\n */\nexport function getItemDate(properties: Record<string, unknown>): string | null {\n  return (\n    (properties.datetime as string | null) ||\n    (properties.start_datetime as string | undefined) ||\n    (properties.end_datetime as string | undefined) ||\n    null\n  );\n}\n\n/**\n * Formats a datetime string for display.\n *\n * @param dateStr - ISO datetime string.\n * @returns Formatted datetime string.\n */\nexport function formatDateTime(dateStr: string | null | undefined): string {\n  if (!dateStr) return 'Unknown';\n  try {\n    return new Date(dateStr).toLocaleString();\n  } catch {\n    return dateStr;\n  }\n}\n\n/**\n * Truncates a string to a maximum length.\n *\n * @param text - String to truncate.\n * @param maxLength - Maximum length.\n * @returns Truncated string.\n */\nexport function truncate(text: string, maxLength: number): string {\n  if (text.length <= maxLength) return text;\n  return text.substring(0, maxLength) + '...';\n}\n\n/**\n * Formats a bounding box for display.\n *\n * @param bbox - Bounding box [west, south, east, north].\n * @returns Formatted bbox string.\n */\nexport function formatBbox(bbox: [number, number, number, number]): string {\n  const [w, s, e, n] = bbox;\n  return `${w.toFixed(2)}, ${s.toFixed(2)}, ${e.toFixed(2)}, ${n.toFixed(2)}`;\n}\n\n/**\n * Builds CSS class string from conditions.\n *\n * @param classes - Object mapping class names to boolean conditions.\n * @returns Space-separated class string.\n */\nexport function classNames(classes: Record<string, boolean>): string {\n  return Object.entries(classes)\n    .filter(([, condition]) => condition)\n    .map(([className]) => className)\n    .join(' ');\n}\n\n/**\n * Checks if a value is a valid bbox.\n *\n * @param bbox - Value to check.\n * @returns True if valid bbox.\n */\nexport function isValidBbox(\n  bbox: unknown\n): bbox is [number, number, number, number] {\n  if (!Array.isArray(bbox) || bbox.length !== 4) return false;\n  return bbox.every((v) => typeof v === 'number' && isFinite(v));\n}\n\n/**\n * Formats file size for display.\n *\n * @param bytes - Size in bytes.\n * @returns Formatted size string.\n */\nexport function formatFileSize(bytes: number): string {\n  if (bytes === 0) return '0 Bytes';\n  const k = 1024;\n  const sizes = ['Bytes', 'KB', 'MB', 'GB', 'TB'];\n  const i = Math.floor(Math.log(bytes) / Math.log(k));\n  return parseFloat((bytes / Math.pow(k, i)).toFixed(2)) + ' ' + sizes[i];\n}\n","import type { Map as MapLibreMap } from 'maplibre-gl';\nimport type { STACItem, STACCollection, TileParams } from '../api/types';\nimport type { ActiveLayer } from './types';\nimport { TiTilerClient } from '../api/titiler-client';\nimport { getDefaultPreset } from '../api/render-presets';\nimport { generateId } from '../utils/helpers';\n\n/**\n * Manages raster layers on the MapLibre map.\n * Handles adding, removing, and updating tile layers from Planetary Computer.\n */\nexport class LayerManager {\n  private map: MapLibreMap;\n  private tilerClient: TiTilerClient;\n  private layers: Map<string, ActiveLayer> = new Map();\n\n  /**\n   * Creates a new layer manager.\n   *\n   * @param map - MapLibre GL map instance.\n   * @param tilerClient - TiTiler API client.\n   */\n  constructor(map: MapLibreMap, tilerClient: TiTilerClient) {\n    this.map = map;\n    this.tilerClient = tilerClient;\n  }\n\n  /**\n   * Adds a STAC item as a raster tile layer.\n   *\n   * @param item - STAC item to visualize.\n   * @param options - Layer options.\n   * @returns The created active layer configuration.\n   */\n  addItemLayer(\n    item: STACItem,\n    options?: {\n      assets?: string[];\n      renderParams?: TileParams;\n      presetName?: string;\n    }\n  ): ActiveLayer {\n    // Use item ID as layer name, sanitized for use as layer ID\n    const sanitizedItemId = item.id.replace(/[^a-zA-Z0-9-_]/g, '-').slice(0, 50);\n    const layerId = `${sanitizedItemId}-${generateId().slice(-6)}`;\n    const sourceId = `${layerId}-source`;\n    const collectionId = item.collection || '';\n\n    // Get render params from preset or options\n    let renderParams: TileParams = options?.renderParams || {};\n    let presetName = options?.presetName;\n\n    if (!options?.renderParams && !options?.assets && collectionId) {\n      const defaultPreset = getDefaultPreset(collectionId);\n      if (defaultPreset) {\n        renderParams = defaultPreset.params;\n        presetName = defaultPreset.name;\n      }\n    }\n\n    // Determine assets to use\n    const assets = options?.assets || renderParams.assets || this.getDefaultAssets(item);\n    renderParams = { ...renderParams, assets };\n\n    // Generate TileJSON URL\n    const tileJsonUrl = this.tilerClient.getItemTileJSONUrl(collectionId, item.id, renderParams);\n\n    // Add source\n    this.map.addSource(sourceId, {\n      type: 'raster',\n      url: tileJsonUrl,\n      tileSize: renderParams.tile_size || 256,\n      bounds: item.bbox as [number, number, number, number],\n      attribution: 'Microsoft Planetary Computer',\n    });\n\n    // Add layer\n    this.map.addLayer({\n      id: layerId,\n      type: 'raster',\n      source: sourceId,\n      paint: {\n        'raster-opacity': 1,\n      },\n    });\n\n    const layer: ActiveLayer = {\n      id: layerId,\n      type: 'item',\n      sourceId,\n      item,\n      collection: undefined,\n      visible: true,\n      opacity: 1,\n      assets,\n      renderParams,\n      presetName,\n    };\n\n    this.layers.set(layerId, layer);\n    return layer;\n  }\n\n  /**\n   * Adds a collection mosaic as a raster tile layer.\n   *\n   * @param collection - STAC collection.\n   * @param options - Layer options.\n   * @returns The created active layer configuration.\n   */\n  addCollectionLayer(\n    collection: STACCollection,\n    options?: {\n      assets?: string[];\n      renderParams?: TileParams;\n      bbox?: [number, number, number, number];\n      presetName?: string;\n    }\n  ): ActiveLayer {\n    // Use collection title or ID as layer name\n    const collectionName = (collection.title || collection.id).replace(/[^a-zA-Z0-9-_]/g, '-').slice(0, 50);\n    const layerId = `${collectionName}-${generateId().slice(-6)}`;\n    const sourceId = `${layerId}-source`;\n\n    // Get render params from preset or options\n    let renderParams: TileParams = options?.renderParams || {};\n    let presetName = options?.presetName;\n\n    if (!options?.renderParams && !options?.assets) {\n      const defaultPreset = getDefaultPreset(collection.id);\n      if (defaultPreset) {\n        renderParams = defaultPreset.params;\n        presetName = defaultPreset.name;\n      }\n    }\n\n    // Determine assets\n    const assets =\n      options?.assets || renderParams.assets || this.getDefaultCollectionAssets(collection);\n    renderParams = { ...renderParams, assets };\n\n    // Generate tile URL\n    const tileUrl = this.tilerClient.getCollectionTileUrl(collection.id, renderParams);\n\n    // Get bounds\n    const bounds = options?.bbox || this.getCollectionBounds(collection);\n\n    // Add source\n    this.map.addSource(sourceId, {\n      type: 'raster',\n      tiles: [tileUrl],\n      tileSize: 256,\n      bounds,\n      attribution: 'Microsoft Planetary Computer',\n    });\n\n    // Add layer\n    this.map.addLayer({\n      id: layerId,\n      type: 'raster',\n      source: sourceId,\n      paint: {\n        'raster-opacity': 1,\n      },\n    });\n\n    const layer: ActiveLayer = {\n      id: layerId,\n      type: 'collection',\n      sourceId,\n      collection,\n      visible: true,\n      opacity: 1,\n      assets,\n      renderParams,\n      presetName,\n    };\n\n    this.layers.set(layerId, layer);\n    return layer;\n  }\n\n  /**\n   * Removes a layer from the map.\n   *\n   * @param layerId - Layer identifier.\n   */\n  removeLayer(layerId: string): void {\n    const layer = this.layers.get(layerId);\n    if (!layer) return;\n\n    // Remove layer from map\n    if (this.map.getLayer(layerId)) {\n      this.map.removeLayer(layerId);\n    }\n\n    // Remove source from map\n    if (this.map.getSource(layer.sourceId)) {\n      this.map.removeSource(layer.sourceId);\n    }\n\n    this.layers.delete(layerId);\n  }\n\n  /**\n   * Updates layer properties.\n   *\n   * @param layerId - Layer identifier.\n   * @param updates - Properties to update.\n   */\n  updateLayer(layerId: string, updates: Partial<ActiveLayer>): void {\n    const layer = this.layers.get(layerId);\n    if (!layer) return;\n\n    // Update visibility\n    if (updates.visible !== undefined) {\n      this.map.setLayoutProperty(layerId, 'visibility', updates.visible ? 'visible' : 'none');\n    }\n\n    // Update opacity\n    if (updates.opacity !== undefined) {\n      this.map.setPaintProperty(layerId, 'raster-opacity', updates.opacity);\n    }\n\n    // Update render params (requires recreating the source)\n    if (updates.renderParams || updates.assets) {\n      this.updateLayerSource(layerId, updates);\n    }\n\n    // Update internal state\n    this.layers.set(layerId, { ...layer, ...updates });\n  }\n\n  /**\n   * Gets a layer by ID.\n   *\n   * @param layerId - Layer identifier.\n   * @returns The layer configuration or undefined.\n   */\n  getLayer(layerId: string): ActiveLayer | undefined {\n    return this.layers.get(layerId);\n  }\n\n  /**\n   * Gets all active layers.\n   *\n   * @returns Array of active layers.\n   */\n  getLayers(): ActiveLayer[] {\n    return Array.from(this.layers.values());\n  }\n\n  /**\n   * Removes all layers managed by this instance.\n   */\n  removeAllLayers(): void {\n    for (const layerId of this.layers.keys()) {\n      this.removeLayer(layerId);\n    }\n  }\n\n  /**\n   * Zooms the map to a layer's bounds.\n   *\n   * @param layerId - Layer identifier.\n   */\n  zoomToLayer(layerId: string): void {\n    const layer = this.layers.get(layerId);\n    if (!layer) return;\n\n    let bounds: [number, number, number, number] | undefined;\n\n    if (layer.item?.bbox) {\n      bounds = layer.item.bbox as [number, number, number, number];\n    } else if (layer.collection) {\n      bounds = this.getCollectionBounds(layer.collection);\n    }\n\n    if (bounds) {\n      this.map.fitBounds(\n        [\n          [bounds[0], bounds[1]],\n          [bounds[2], bounds[3]],\n        ],\n        { padding: 50 }\n      );\n    }\n  }\n\n  /**\n   * Gets the map instance.\n   *\n   * @returns The MapLibre GL map.\n   */\n  getMap(): MapLibreMap {\n    return this.map;\n  }\n\n  /**\n   * Updates a layer's tile source with new render params.\n   *\n   * @param layerId - Layer identifier.\n   * @param updates - Updates including new render params.\n   */\n  private updateLayerSource(layerId: string, updates: Partial<ActiveLayer>): void {\n    const layer = this.layers.get(layerId);\n    if (!layer) return;\n\n    const newParams = { ...layer.renderParams, ...updates.renderParams };\n    const newAssets = updates.assets || layer.assets;\n\n    let tileUrl: string;\n\n    if (layer.type === 'item' && layer.item) {\n      const collectionId = layer.item.collection || '';\n      tileUrl = this.tilerClient.getItemTileJSONUrl(collectionId, layer.item.id, {\n        ...newParams,\n        assets: newAssets,\n      });\n    } else if (layer.type === 'collection' && layer.collection) {\n      tileUrl = this.tilerClient.getCollectionTileUrl(layer.collection.id, {\n        ...newParams,\n        assets: newAssets,\n      });\n    } else {\n      return;\n    }\n\n    // Get current layer state\n    const visibility = this.map.getLayoutProperty(layerId, 'visibility');\n    const opacity = this.map.getPaintProperty(layerId, 'raster-opacity');\n\n    // Remove old layer and source\n    this.map.removeLayer(layerId);\n    this.map.removeSource(layer.sourceId);\n\n    // Get bounds\n    const bounds = layer.item?.bbox || (layer.collection ? this.getCollectionBounds(layer.collection) : undefined);\n\n    // Add new source\n    this.map.addSource(layer.sourceId, {\n      type: 'raster',\n      ...(layer.type === 'item' ? { url: tileUrl } : { tiles: [tileUrl] }),\n      tileSize: newParams.tile_size || 256,\n      bounds: bounds as [number, number, number, number] | undefined,\n      attribution: 'Microsoft Planetary Computer',\n    });\n\n    // Add new layer\n    this.map.addLayer({\n      id: layerId,\n      type: 'raster',\n      source: layer.sourceId,\n      layout: {\n        visibility: visibility as 'visible' | 'none' | undefined,\n      },\n      paint: {\n        'raster-opacity': (opacity as number) ?? 1,\n      },\n    });\n  }\n\n  /**\n   * Gets default assets for a STAC item.\n   *\n   * @param item - STAC item.\n   * @returns Array of asset names.\n   */\n  private getDefaultAssets(item: STACItem): string[] {\n    // Prioritize common renderable assets\n    const preferredAssets = ['visual', 'data', 'image', 'cog_default'];\n    for (const asset of preferredAssets) {\n      if (item.assets[asset]) return [asset];\n    }\n    // Look for any COG or data asset\n    for (const [key, asset] of Object.entries(item.assets)) {\n      const type = asset.type || '';\n      if (type.includes('tiff') || type.includes('geotiff') || type.includes('cog')) {\n        return [key];\n      }\n    }\n    // Return first asset (excluding thumbnail/overview/metadata)\n    const excludePatterns = ['thumbnail', 'overview', 'metadata', 'tilejson', 'rendered_preview'];\n    const dataAsset = Object.keys(item.assets).find(\n      (key) => !excludePatterns.some((p) => key.toLowerCase().includes(p))\n    );\n    return dataAsset ? [dataAsset] : [];\n  }\n\n  /**\n   * Gets default assets for a collection.\n   *\n   * @param collection - STAC collection.\n   * @returns Array of asset names.\n   */\n  private getDefaultCollectionAssets(collection: STACCollection): string[] {\n    const itemAssets = collection.item_assets || {};\n    // Prioritize common renderable assets\n    const preferredAssets = ['visual', 'data', 'image', 'cog_default'];\n    for (const asset of preferredAssets) {\n      if (itemAssets[asset]) return [asset];\n    }\n    // Look for any COG or data asset\n    for (const [key, asset] of Object.entries(itemAssets)) {\n      const type = asset.type || '';\n      if (type.includes('tiff') || type.includes('geotiff') || type.includes('cog')) {\n        return [key];\n      }\n    }\n    // Return first asset (excluding thumbnail/overview/metadata)\n    const excludePatterns = ['thumbnail', 'overview', 'metadata', 'tilejson', 'rendered_preview'];\n    const dataAsset = Object.keys(itemAssets).find(\n      (key) => !excludePatterns.some((p) => key.toLowerCase().includes(p))\n    );\n    return dataAsset ? [dataAsset] : [];\n  }\n\n  /**\n   * Gets bounds from a collection's extent.\n   *\n   * @param collection - STAC collection.\n   * @returns Bounding box or undefined.\n   */\n  private getCollectionBounds(\n    collection: STACCollection\n  ): [number, number, number, number] | undefined {\n    const bbox = collection.extent?.spatial?.bbox?.[0];\n    if (bbox && bbox.length >= 4) {\n      return [bbox[0], bbox[1], bbox[2], bbox[3]];\n    }\n    return undefined;\n  }\n}\n","import type {\n  GeoJSONSource,\n  IControl,\n  Map as MapLibreMap,\n  MapLayerMouseEvent,\n  MapMouseEvent,\n} from 'maplibre-gl';\nimport type { Feature, FeatureCollection, Geometry, Polygon } from 'geojson';\nimport type {\n  PlanetaryComputerOptions,\n  PlanetaryComputerState,\n  PlanetaryComputerEvent,\n  PlanetaryComputerEventHandler,\n  ActiveLayer,\n  PanelView,\n} from './types';\nimport type {\n  BandStatistics,\n  PointValueResponse,\n  STACCollection,\n  STACItem,\n  STACSearchParams,\n  TileParams,\n} from '../api/types';\nimport { STACClient } from '../api/stac-client';\nimport { TiTilerClient } from '../api/titiler-client';\nimport { SASTokenManager } from '../api/sas-token';\nimport { LayerManager } from './LayerManager';\nimport { truncate, formatDate, formatBbox, getItemDate } from '../utils/helpers';\nimport { getPresetsForCollection } from '../api/render-presets';\n\n/**\n * Default options for the control.\n */\nconst DEFAULT_OPTIONS: Required<PlanetaryComputerOptions> = {\n  collapsed: true,\n  position: 'top-right',\n  title: 'Planetary Computer',\n  panelWidth: 380,\n  maxHeight: 500,\n  className: '',\n  stacApiUrl: 'https://planetarycomputer.microsoft.com/api/stac/v1',\n  tilerApiUrl: 'https://planetarycomputer.microsoft.com/api/data/v1',\n  defaultCollections: [],\n  enableBboxSelector: true,\n  maxSearchResults: 50,\n  autoLoadCollections: true,\n};\n\nconst FOOTPRINT_SOURCE_ID = 'pc-search-footprints';\nconst FOOTPRINT_FILL_LAYER_ID = 'pc-search-footprints-fill';\nconst FOOTPRINT_OUTLINE_LAYER_ID = 'pc-search-footprints-outline';\nconst FOOTPRINT_SELECTED_FILL_LAYER_ID = 'pc-search-footprints-selected-fill';\nconst FOOTPRINT_SELECTED_OUTLINE_LAYER_ID = 'pc-search-footprints-selected-outline';\n\n/**\n * Event handlers map type.\n */\ntype EventHandlersMap = globalThis.Map<PlanetaryComputerEvent, Set<PlanetaryComputerEventHandler>>;\n\ntype ScreenPoint = {\n  x: number;\n  y: number;\n};\n\ntype InspectorResult = {\n  layerId: string;\n  lon: number;\n  lat: number;\n  loading: boolean;\n  data?: PointValueResponse;\n  error?: string;\n};\n\ntype FootprintFeature = Feature<Geometry | Polygon, { itemId: string; title: string }>;\n\n/**\n * MapLibre GL control for browsing and visualizing Planetary Computer data.\n *\n * @example\n * ```typescript\n * const control = new PlanetaryComputerControl({\n *   title: 'Earth Data',\n *   collapsed: false,\n * });\n * map.addControl(control, 'top-right');\n *\n * control.on('layer:add', (event) => {\n *   console.log('Layer added:', event.data);\n * });\n * ```\n */\nexport class PlanetaryComputerControl implements IControl {\n  private _map?: MapLibreMap;\n  private _mapContainer?: HTMLElement;\n  private _container?: HTMLElement;\n  private _panel?: HTMLElement;\n  private _contentEl?: HTMLElement;\n  private _options: Required<PlanetaryComputerOptions>;\n  private _state: PlanetaryComputerState;\n  private _eventHandlers: EventHandlersMap = new globalThis.Map();\n\n  // API clients\n  private _stacClient: STACClient;\n  private _tilerClient: TiTilerClient;\n  private _sasManager: SASTokenManager;\n  private _layerManager?: LayerManager;\n\n  // Event handlers for cleanup\n  private _resizeHandler: (() => void) | null = null;\n  private _mapResizeHandler: (() => void) | null = null;\n  private _clickOutsideHandler: ((e: MouseEvent) => void) | null = null;\n  private _bboxPointerDownHandler: ((e: PointerEvent) => void) | null = null;\n  private _bboxPointerMoveHandler: ((e: PointerEvent) => void) | null = null;\n  private _bboxPointerUpHandler: ((e: PointerEvent) => void) | null = null;\n  private _bboxKeyDownHandler: ((e: KeyboardEvent) => void) | null = null;\n  private _bboxOverlay?: HTMLElement;\n  private _bboxBox?: HTMLElement;\n  private _bboxStartPoint: ScreenPoint | null = null;\n  private _bboxDragPanWasEnabled = false;\n  private _bboxBoxZoomWasEnabled = false;\n  private _ignoreNextDocumentClick = false;\n  private _inspectClickHandler: ((e: MapMouseEvent) => void) | null = null;\n  private _inspectorLayerId: string | null = null;\n  private _inspectorResult: InspectorResult | null = null;\n  private _footprintClickHandler: ((e: MapLayerMouseEvent) => void) | null = null;\n  private _footprintMouseEnterHandler: (() => void) | null = null;\n  private _footprintMouseLeaveHandler: (() => void) | null = null;\n\n  /**\n   * Creates a new PlanetaryComputerControl instance.\n   *\n   * @param options - Configuration options for the control.\n   */\n  constructor(options?: Partial<PlanetaryComputerOptions>) {\n    this._options = { ...DEFAULT_OPTIONS, ...options };\n    this._state = this._getInitialState();\n\n    // Initialize API clients\n    this._stacClient = new STACClient(this._options.stacApiUrl);\n    this._tilerClient = new TiTilerClient(this._options.tilerApiUrl);\n    this._sasManager = new SASTokenManager();\n  }\n\n  /**\n   * Called when the control is added to the map.\n   *\n   * @param map - The MapLibre GL map instance.\n   * @returns The control's container element.\n   */\n  onAdd(map: MapLibreMap): HTMLElement {\n    this._map = map;\n    this._mapContainer = map.getContainer();\n    this._layerManager = new LayerManager(map, this._tilerClient);\n\n    this._container = this._createContainer();\n    this._panel = this._createPanel();\n    this._mapContainer.appendChild(this._panel);\n\n    this._setupEventListeners();\n\n    if (!this._state.collapsed) {\n      this._panel.classList.add('expanded');\n      requestAnimationFrame(() => this._updatePanelPosition());\n    }\n\n    // Load collections if auto-load is enabled\n    if (this._options.autoLoadCollections) {\n      this._loadCollections();\n    }\n\n    return this._container;\n  }\n\n  /**\n   * Called when the control is removed from the map.\n   */\n  onRemove(): void {\n    this._stopBboxDraw(false);\n    this._stopInspector(false);\n    this._clearSearchFootprints(false);\n\n    // Remove event listeners\n    if (this._resizeHandler) {\n      window.removeEventListener('resize', this._resizeHandler);\n      this._resizeHandler = null;\n    }\n    if (this._mapResizeHandler && this._map) {\n      this._map.off('resize', this._mapResizeHandler);\n      this._mapResizeHandler = null;\n    }\n    if (this._clickOutsideHandler) {\n      document.removeEventListener('click', this._clickOutsideHandler);\n      this._clickOutsideHandler = null;\n    }\n\n    // Cleanup API clients\n    this._stacClient.cancelPending();\n    this._sasManager.clearCache();\n\n    // Remove layers from map\n    this._layerManager?.removeAllLayers();\n\n    // Remove DOM elements\n    this._panel?.parentNode?.removeChild(this._panel);\n    this._container?.parentNode?.removeChild(this._container);\n\n    this._map = undefined;\n    this._eventHandlers.clear();\n  }\n\n  // ============ Public API Methods ============\n\n  /**\n   * Gets the current state of the control.\n   *\n   * @returns The current plugin state.\n   */\n  getState(): PlanetaryComputerState {\n    return { ...this._state };\n  }\n\n  /**\n   * Toggles the collapsed state of the control panel.\n   */\n  toggle(): void {\n    if (!this._state.collapsed) {\n      this._stopBboxDraw(false);\n    }\n\n    this._state.collapsed = !this._state.collapsed;\n    this._updatePanelVisibility();\n    this._emit(this._state.collapsed ? 'collapse' : 'expand');\n    this._emit('statechange');\n  }\n\n  /**\n   * Expands the control panel.\n   */\n  expand(): void {\n    if (this._state.collapsed) this.toggle();\n  }\n\n  /**\n   * Collapses the control panel.\n   */\n  collapse(): void {\n    if (!this._state.collapsed) this.toggle();\n  }\n\n  /**\n   * Loads all available collections.\n   *\n   * @returns Promise resolving to array of collections.\n   */\n  async loadCollections(): Promise<STACCollection[]> {\n    return this._loadCollections();\n  }\n\n  /**\n   * Performs a search with the given parameters.\n   *\n   * @param params - Search parameters.\n   * @returns Promise resolving to array of matching items.\n   */\n  async search(params?: Partial<STACSearchParams>): Promise<STACItem[]> {\n    const searchParams: STACSearchParams = {\n      ...this._state.searchParams,\n      ...params,\n      limit: this._options.maxSearchResults,\n    };\n\n    this._state.searchParams = searchParams;\n    this._state.searchLoading = true;\n    this._state.error = null;\n    this._emit('search:start');\n    this._emit('statechange');\n    this._renderContent();\n\n    try {\n      const results = await this._stacClient.search(searchParams);\n      this._state.searchResults = results;\n      this._state.selectedSearchResultId = null;\n      this._state.activeView = 'results';\n      this._showSearchFootprints(results);\n      this._emit('search:complete');\n      this._emit('search');\n      return results;\n    } catch (error) {\n      const errorMessage = error instanceof Error ? error.message : 'Search failed';\n      this._state.error = errorMessage;\n      this._emit('search:error');\n      this._emit('error');\n      throw error;\n    } finally {\n      this._state.searchLoading = false;\n      this._emit('statechange');\n      this._renderContent();\n    }\n  }\n\n  /**\n   * Adds a STAC item as a raster layer on the map.\n   *\n   * @param item - STAC item to visualize.\n   * @param options - Layer options.\n   * @returns The created active layer.\n   */\n  addItemLayer(\n    item: STACItem,\n    options?: { assets?: string[]; renderParams?: TileParams; presetName?: string }\n  ): ActiveLayer {\n    if (!this._layerManager) throw new Error('Control not added to map');\n\n    const layer = this._layerManager.addItemLayer(item, options);\n    layer.showControls = false;\n    this._state.activeLayers.push(layer);\n    this._emit('layer:add');\n    this._emit('statechange');\n    this._renderContent();\n    return layer;\n  }\n\n  /**\n   * Adds a collection mosaic as a raster layer.\n   *\n   * @param collection - STAC collection.\n   * @param options - Layer options.\n   * @returns The created active layer.\n   */\n  addCollectionLayer(\n    collection: STACCollection,\n    options?: {\n      assets?: string[];\n      renderParams?: TileParams;\n      bbox?: [number, number, number, number];\n      presetName?: string;\n    }\n  ): ActiveLayer {\n    if (!this._layerManager) throw new Error('Control not added to map');\n\n    const layer = this._layerManager.addCollectionLayer(collection, options);\n    layer.showControls = false;\n    this._state.activeLayers.push(layer);\n    this._emit('layer:add');\n    this._emit('statechange');\n    this._renderContent();\n    return layer;\n  }\n\n  /**\n   * Removes a layer from the map.\n   *\n   * @param layerId - Layer identifier.\n   */\n  removeLayer(layerId: string): void {\n    if (this._inspectorLayerId === layerId) {\n      this._stopInspector(false);\n    }\n    this._layerManager?.removeLayer(layerId);\n    this._state.activeLayers = this._state.activeLayers.filter((l) => l.id !== layerId);\n    this._emit('layer:remove');\n    this._emit('statechange');\n    this._renderContent();\n  }\n\n  /**\n   * Updates layer properties.\n   *\n   * @param layerId - Layer identifier.\n   * @param updates - Properties to update.\n   */\n  updateLayer(layerId: string, updates: Partial<ActiveLayer>): void {\n    this._layerManager?.updateLayer(layerId, updates);\n    const layerIndex = this._state.activeLayers.findIndex((l) => l.id === layerId);\n    if (layerIndex >= 0) {\n      this._state.activeLayers[layerIndex] = {\n        ...this._state.activeLayers[layerIndex],\n        ...updates,\n      };\n    }\n    this._emit('layer:update');\n    this._emit('statechange');\n  }\n\n  /**\n   * Zooms the map to a layer's bounds.\n   *\n   * @param layerId - Layer identifier.\n   */\n  zoomToLayer(layerId: string): void {\n    this._layerManager?.zoomToLayer(layerId);\n  }\n\n  /**\n   * Gets download URL for an asset with SAS token.\n   *\n   * @param item - STAC item.\n   * @param assetKey - Asset key.\n   * @returns Promise resolving to signed download URL.\n   */\n  async getDownloadUrl(item: STACItem, assetKey: string): Promise<string> {\n    const asset = item.assets[assetKey];\n    if (!asset) throw new Error(`Asset '${assetKey}' not found`);\n\n    const collectionId = item.collection || '';\n    return this._sasManager.signUrl(asset.href, collectionId);\n  }\n\n  /**\n   * Selects a collection for searching.\n   *\n   * @param collection - Collection to select.\n   */\n  selectCollection(collection: STACCollection | null): void {\n    this._stopBboxDraw(false);\n    this._clearSearchFootprints(false);\n    this._state.selectedCollection = collection;\n    this._state.searchParams = collection ? { collections: [collection.id] } : {};\n    this._state.activeView = collection ? 'search' : 'collections';\n    this._state.searchResults = [];\n    this._state.selectedItem = null;\n    this._state.selectedSearchResultId = null;\n    this._emit('collection:select');\n    this._emit('statechange');\n    this._renderContent();\n  }\n\n  /**\n   * Selects an item for detail view.\n   *\n   * @param item - Item to select.\n   */\n  selectItem(item: STACItem | null): void {\n    this._state.selectedItem = item;\n    this._state.selectedSearchResultId = item?.id || null;\n    this._updateSelectedFootprint();\n    this._state.activeView = item ? 'item' : 'results';\n    this._emit('item:select');\n    this._emit('statechange');\n    this._renderContent();\n  }\n\n  /**\n   * Sets the current view.\n   *\n   * @param view - View to display.\n   */\n  setView(view: PanelView): void {\n    this._state.activeView = view;\n    this._emit('statechange');\n    this._renderContent();\n  }\n\n  /**\n   * Registers an event handler.\n   *\n   * @param event - Event type.\n   * @param handler - Event handler function.\n   */\n  on(event: PlanetaryComputerEvent, handler: PlanetaryComputerEventHandler): void {\n    if (!this._eventHandlers.has(event)) {\n      this._eventHandlers.set(event, new Set());\n    }\n    this._eventHandlers.get(event)!.add(handler);\n  }\n\n  /**\n   * Removes an event handler.\n   *\n   * @param event - Event type.\n   * @param handler - Event handler function.\n   */\n  off(event: PlanetaryComputerEvent, handler: PlanetaryComputerEventHandler): void {\n    this._eventHandlers.get(event)?.delete(handler);\n  }\n\n  /**\n   * Gets the map instance.\n   *\n   * @returns The MapLibre GL map instance.\n   */\n  getMap(): MapLibreMap | undefined {\n    return this._map;\n  }\n\n  /**\n   * Gets the control container element.\n   *\n   * @returns The container element.\n   */\n  getContainer(): HTMLElement | undefined {\n    return this._container;\n  }\n\n  // ============ Private Methods ============\n\n  /**\n   * Gets the initial state.\n   */\n  private _getInitialState(): PlanetaryComputerState {\n    return {\n      collapsed: this._options.collapsed,\n      panelWidth: this._options.panelWidth,\n      activeView: 'collections',\n      collections: [],\n      collectionsLoading: false,\n      selectedCollection: null,\n      searchParams: {},\n      searchResults: [],\n      searchLoading: false,\n      selectedItem: null,\n      selectedSearchResultId: null,\n      activeLayers: [],\n      error: null,\n      bboxSelectorActive: false,\n      drawnBbox: null,\n    };\n  }\n\n  /**\n   * Emits an event.\n   */\n  private _emit(event: PlanetaryComputerEvent, data?: unknown): void {\n    const handlers = this._eventHandlers.get(event);\n    if (handlers) {\n      const eventData = { type: event, state: this.getState(), data };\n      handlers.forEach((handler) => handler(eventData));\n    }\n  }\n\n  /**\n   * Creates the control container.\n   */\n  private _createContainer(): HTMLElement {\n    const container = document.createElement('div');\n    container.className = `maplibregl-ctrl maplibregl-ctrl-group pc-control${\n      this._options.className ? ` ${this._options.className}` : ''\n    }`;\n\n    const toggleBtn = document.createElement('button');\n    toggleBtn.className = 'pc-control-toggle';\n    toggleBtn.type = 'button';\n    toggleBtn.setAttribute('aria-label', this._options.title);\n    toggleBtn.innerHTML = `\n      <span class=\"pc-control-icon\">\n        <svg viewBox=\"0 0 23 23\" width=\"22\" height=\"22\">\n          <rect x=\"1\" y=\"1\" width=\"10\" height=\"10\" fill=\"#666\"/>\n          <rect x=\"12\" y=\"1\" width=\"10\" height=\"10\" fill=\"#888\"/>\n          <rect x=\"1\" y=\"12\" width=\"10\" height=\"10\" fill=\"#999\"/>\n          <rect x=\"12\" y=\"12\" width=\"10\" height=\"10\" fill=\"#777\"/>\n        </svg>\n      </span>\n    `;\n    toggleBtn.addEventListener('click', () => this.toggle());\n\n    container.appendChild(toggleBtn);\n    return container;\n  }\n\n  /**\n   * Creates the panel element.\n   */\n  private _createPanel(): HTMLElement {\n    const panel = document.createElement('div');\n    panel.className = 'pc-control-panel';\n    panel.style.width = `${this._options.panelWidth}px`;\n    panel.style.maxHeight = `${this._options.maxHeight}px`;\n\n    // Prevent clicks inside the panel from triggering the click-outside handler\n    panel.addEventListener('click', (e) => e.stopPropagation());\n\n    // Header\n    const header = document.createElement('div');\n    header.className = 'pc-control-header';\n\n    const title = document.createElement('span');\n    title.className = 'pc-control-title';\n    title.textContent = this._options.title;\n\n    const closeBtn = document.createElement('button');\n    closeBtn.className = 'pc-control-close';\n    closeBtn.type = 'button';\n    closeBtn.innerHTML = '&times;';\n    closeBtn.addEventListener('click', () => this.collapse());\n\n    header.appendChild(title);\n    header.appendChild(closeBtn);\n\n    // Navigation tabs\n    const nav = document.createElement('div');\n    nav.className = 'pc-control-nav';\n    nav.innerHTML = `\n      <button type=\"button\" class=\"pc-nav-btn active\" data-view=\"collections\">Collections</button>\n      <button type=\"button\" class=\"pc-nav-btn\" data-view=\"layers\">Layers (0)</button>\n    `;\n    nav.addEventListener('click', (e) => {\n      const target = e.target as HTMLElement;\n      if (target.dataset.view) {\n        this.setView(target.dataset.view as PanelView);\n      }\n    });\n\n    // Content area\n    const content = document.createElement('div');\n    content.className = 'pc-control-content';\n    this._contentEl = content;\n\n    panel.appendChild(header);\n    panel.appendChild(nav);\n    panel.appendChild(content);\n\n    return panel;\n  }\n\n  /**\n   * Renders content based on current view.\n   */\n  private _renderContent(): void {\n    if (!this._contentEl) return;\n\n    // Update nav tabs\n    this._updateNavTabs();\n\n    switch (this._state.activeView) {\n      case 'collections':\n        this._renderCollections();\n        break;\n      case 'search':\n        this._renderSearch();\n        break;\n      case 'results':\n        this._renderResults();\n        break;\n      case 'item':\n        this._renderItem();\n        break;\n      case 'layers':\n        this._renderLayers();\n        break;\n    }\n  }\n\n  /**\n   * Updates navigation tabs.\n   */\n  private _updateNavTabs(): void {\n    const nav = this._panel?.querySelector('.pc-control-nav');\n    if (!nav) return;\n\n    const layersBtn = nav.querySelector('[data-view=\"layers\"]');\n    if (layersBtn) {\n      layersBtn.textContent = `Layers (${this._state.activeLayers.length})`;\n    }\n\n    nav.querySelectorAll('.pc-nav-btn').forEach((btn) => {\n      const view = (btn as HTMLElement).dataset.view;\n      btn.classList.toggle('active', view === this._state.activeView ||\n        (view === 'collections' && ['collections', 'search', 'results', 'item'].includes(this._state.activeView)));\n    });\n  }\n\n  /**\n   * Renders collections view.\n   */\n  private _renderCollections(): void {\n    if (!this._contentEl) return;\n\n    if (this._state.collectionsLoading) {\n      this._contentEl.innerHTML = `\n        <div class=\"pc-loading\">\n          <div class=\"pc-spinner\"></div>\n          <span>Loading collections...</span>\n        </div>\n      `;\n      return;\n    }\n\n    if (this._state.error) {\n      this._contentEl.innerHTML = `\n        <div class=\"pc-error\">\n          <span>${this._state.error}</span>\n          <button type=\"button\" class=\"pc-btn pc-btn-small pc-retry\">Retry</button>\n        </div>\n      `;\n      this._contentEl.querySelector('.pc-retry')?.addEventListener('click', () => this._loadCollections());\n      return;\n    }\n\n    this._contentEl.innerHTML = `\n      <div class=\"pc-collection-browser\">\n        <div class=\"pc-search-box\">\n          <input type=\"text\" class=\"pc-search-input\" placeholder=\"Search ${this._state.collections.length} collections...\">\n        </div>\n        <div class=\"pc-collection-list\"></div>\n      </div>\n    `;\n\n    const input = this._contentEl.querySelector('.pc-search-input') as HTMLInputElement;\n    const listEl = this._contentEl.querySelector('.pc-collection-list') as HTMLElement;\n\n    const renderList = (filter: string = '') => {\n      const filtered = this._state.collections.filter((c) => {\n        const searchText = filter.toLowerCase();\n        return (\n          c.id.toLowerCase().includes(searchText) ||\n          c.title?.toLowerCase().includes(searchText) ||\n          c.description?.toLowerCase().includes(searchText) ||\n          c.keywords?.some((k) => k.toLowerCase().includes(searchText))\n        );\n      });\n\n      listEl.innerHTML = filtered\n        .map(\n          (c) => `\n          <div class=\"pc-collection-item\" data-id=\"${c.id}\">\n            <div class=\"pc-collection-title\">${c.title || c.id}</div>\n            <div class=\"pc-collection-description\">${truncate(c.description || '', 100)}</div>\n            ${\n              c.keywords?.length\n                ? `<div class=\"pc-collection-keywords\">${c.keywords\n                    .slice(0, 3)\n                    .map((k) => `<span class=\"pc-tag\">${k}</span>`)\n                    .join('')}</div>`\n                : ''\n            }\n          </div>\n        `\n        )\n        .join('');\n\n      listEl.querySelectorAll('.pc-collection-item').forEach((el) => {\n        el.addEventListener('click', () => {\n          const id = el.getAttribute('data-id');\n          const collection = this._state.collections.find((c) => c.id === id);\n          if (collection) this.selectCollection(collection);\n        });\n      });\n    };\n\n    renderList();\n    input.addEventListener('input', () => renderList(input.value));\n  }\n\n  /**\n   * Renders search view.\n   */\n  private _renderSearch(): void {\n    if (!this._contentEl || !this._state.selectedCollection) return;\n\n    const collection = this._state.selectedCollection;\n    const presets = getPresetsForCollection(collection.id);\n\n    // Check if collection supports cloud cover filtering\n    const supportsCloudCover = this._collectionSupportsCloudCover(collection);\n\n    this._contentEl.innerHTML = `\n      <div class=\"pc-search-panel\">\n        <button type=\"button\" class=\"pc-btn-back\">&larr; Back to collections</button>\n\n        <div class=\"pc-selected-collection\">\n          <span class=\"pc-label\">Collection</span>\n          <span class=\"pc-collection-name\">${collection.title || collection.id}</span>\n          <button type=\"button\" class=\"pc-btn pc-btn-small pc-open-collection-page\">Open Webpage</button>\n        </div>\n\n        <div class=\"pc-form-group\">\n          <label class=\"pc-label\">Bounding Box</label>\n          <div class=\"pc-bbox-display\">\n            <div class=\"pc-bbox-actions\">\n              ${\n                this._options.enableBboxSelector\n                  ? `<button type=\"button\" class=\"pc-btn pc-btn-small pc-draw-bbox${\n                      this._state.bboxSelectorActive ? ' pc-btn-active' : ''\n                    }\">${this._state.bboxSelectorActive ? 'Cancel Draw' : 'Draw Bbox'}</button>`\n                  : ''\n              }\n              <button type=\"button\" class=\"pc-btn pc-btn-small pc-use-view\">Use Map View</button>\n              <button type=\"button\" class=\"pc-btn pc-btn-small pc-clear-bbox\" ${\n                this._state.drawnBbox ? '' : 'disabled'\n              }>Clear</button>\n            </div>\n            <div class=\"pc-bbox-coordinates\">\n              <span class=\"pc-bbox-text\">${\n                this._state.bboxSelectorActive\n                  ? 'Drag on the map to draw a bounding box'\n                  : this._state.drawnBbox\n                    ? formatBbox(this._state.drawnBbox)\n                    : 'Use current map view'\n              }</span>\n            </div>\n          </div>\n        </div>\n\n        <div class=\"pc-form-group\">\n          <label class=\"pc-label\">Date Range</label>\n          <div class=\"pc-date-inputs\">\n            <input type=\"date\" class=\"pc-input pc-date-start\">\n            <span class=\"pc-date-separator\">to</span>\n            <input type=\"date\" class=\"pc-input pc-date-end\">\n          </div>\n        </div>\n\n        ${supportsCloudCover ? `\n        <div class=\"pc-form-group\">\n          <label class=\"pc-label\">Max Cloud Cover (%)</label>\n          <div class=\"pc-cloud-cover-input\">\n            <input type=\"range\" class=\"pc-cloud-slider\" min=\"0\" max=\"100\" value=\"100\">\n            <span class=\"pc-cloud-value\">100%</span>\n          </div>\n        </div>\n        ` : ''}\n\n        <div class=\"pc-form-group\">\n          <label class=\"pc-label\">Results Limit</label>\n          <select class=\"pc-input pc-limit-select\">\n            <option value=\"10\">10</option>\n            <option value=\"25\">25</option>\n            <option value=\"50\" selected>50</option>\n            <option value=\"100\">100</option>\n          </select>\n        </div>\n\n        <div class=\"pc-form-group\">\n          <label class=\"pc-label\">Sort By</label>\n          <select class=\"pc-input pc-sort-select\">\n            <option value=\"datetime-desc\">Date (Newest First)</option>\n            <option value=\"datetime-asc\">Date (Oldest First)</option>\n            ${supportsCloudCover ? `\n            <option value=\"cloud-asc\">Cloud Cover (Lowest First)</option>\n            <option value=\"cloud-desc\">Cloud Cover (Highest First)</option>\n            ` : ''}\n          </select>\n        </div>\n\n        ${\n          presets.length\n            ? `\n          <div class=\"pc-form-group\">\n            <label class=\"pc-label\">Visualization Preset</label>\n            <select class=\"pc-input pc-preset-select\">\n              ${presets.map((p) => `<option value=\"${p.name}\">${p.label}</option>`).join('')}\n            </select>\n          </div>\n        `\n            : ''\n        }\n\n        <button type=\"button\" class=\"pc-btn pc-btn-primary pc-search-btn${\n          this._state.searchLoading ? ' pc-search-btn-loading' : ''\n        }\" ${this._state.searchLoading ? 'disabled aria-busy=\"true\"' : ''}>\n          ${this._state.searchLoading ? '<span class=\"pc-search-spinner\"></span>Searching...' : 'Search Items'}\n        </button>\n      </div>\n    `;\n\n    // Event handlers\n    this._contentEl.querySelector('.pc-btn-back')?.addEventListener('click', () => {\n      this.selectCollection(null);\n    });\n\n    this._contentEl.querySelector('.pc-open-collection-page')?.addEventListener('click', () => {\n      window.open(this._getCollectionPageUrl(collection), '_blank');\n    });\n\n    this._contentEl.querySelector('.pc-use-view')?.addEventListener('click', () => {\n      if (this._map) {\n        this._stopBboxDraw(false);\n        const bounds = this._map.getBounds();\n        this._state.drawnBbox = [\n          bounds.getWest(),\n          bounds.getSouth(),\n          bounds.getEast(),\n          bounds.getNorth(),\n        ];\n        this._state.searchParams.bbox = this._state.drawnBbox;\n        this._renderContent();\n      }\n    });\n\n    this._contentEl.querySelector('.pc-clear-bbox')?.addEventListener('click', () => {\n      this._stopBboxDraw(false);\n      this._state.drawnBbox = null;\n      delete this._state.searchParams.bbox;\n      this._emit('statechange');\n      this._renderContent();\n    });\n\n    this._contentEl.querySelector('.pc-draw-bbox')?.addEventListener('click', () => {\n      if (this._state.bboxSelectorActive) {\n        this._stopBboxDraw();\n      } else {\n        this._startBboxDraw();\n      }\n    });\n\n    // Cloud cover slider\n    const cloudSlider = this._contentEl.querySelector('.pc-cloud-slider') as HTMLInputElement;\n    const cloudValue = this._contentEl.querySelector('.pc-cloud-value');\n    if (cloudSlider && cloudValue) {\n      cloudSlider.addEventListener('input', () => {\n        cloudValue.textContent = `${cloudSlider.value}%`;\n      });\n    }\n\n    this._contentEl.querySelector('.pc-search-btn')?.addEventListener('click', () => {\n      if (this._state.searchLoading) return;\n\n      const startDate = (this._contentEl?.querySelector('.pc-date-start') as HTMLInputElement)?.value;\n      const endDate = (this._contentEl?.querySelector('.pc-date-end') as HTMLInputElement)?.value;\n      const cloudCover = (this._contentEl?.querySelector('.pc-cloud-slider') as HTMLInputElement)?.value;\n      const limit = (this._contentEl?.querySelector('.pc-limit-select') as HTMLSelectElement)?.value;\n      const sortBy = (this._contentEl?.querySelector('.pc-sort-select') as HTMLSelectElement)?.value;\n\n      if (startDate || endDate) {\n        const start = startDate ? `${startDate}T00:00:00Z` : '..';\n        const end = endDate ? `${endDate}T23:59:59Z` : '..';\n        this._state.searchParams.datetime = `${start}/${end}`;\n      }\n\n      if (!this._state.searchParams.bbox && this._map) {\n        const bounds = this._map.getBounds();\n        this._state.searchParams.bbox = [\n          bounds.getWest(),\n          bounds.getSouth(),\n          bounds.getEast(),\n          bounds.getNorth(),\n        ];\n      }\n\n      // Apply cloud cover filter if set and less than 100%\n      if (cloudCover && parseInt(cloudCover) < 100) {\n        this._state.searchParams.query = {\n          'eo:cloud_cover': { lte: parseInt(cloudCover) },\n        };\n      }\n\n      // Apply limit\n      if (limit) {\n        this._state.searchParams.limit = parseInt(limit);\n      }\n\n      // Apply sort\n      if (sortBy) {\n        const [field, direction] = sortBy.split('-');\n        const sortField = field === 'cloud' ? 'properties.eo:cloud_cover' : 'properties.datetime';\n        this._state.searchParams.sortby = [{ field: sortField, direction: direction as 'asc' | 'desc' }];\n      }\n\n      this.search();\n    });\n  }\n\n  /**\n   * Checks if a collection supports cloud cover filtering.\n   */\n  private _collectionSupportsCloudCover(collection: STACCollection): boolean {\n    // Collections that typically have cloud cover metadata\n    const cloudCoverCollections = [\n      'sentinel-2-l2a',\n      'sentinel-2-l1c',\n      'landsat-c2-l1',\n      'landsat-c2-l2',\n      'landsat-8-c2-l2',\n      'landsat-9-c2-l2',\n      'modis-09A1-061',\n      'modis-09Q1-061',\n    ];\n\n    // Check if collection ID matches or if summaries include eo:cloud_cover\n    if (cloudCoverCollections.some(id => collection.id.includes(id))) {\n      return true;\n    }\n\n    // Check summaries\n    if (collection.summaries?.['eo:cloud_cover']) {\n      return true;\n    }\n\n    return false;\n  }\n\n  /**\n   * Gets the public Planetary Computer webpage URL for a collection.\n   */\n  private _getCollectionPageUrl(collection: STACCollection): string {\n    return `https://planetarycomputer.microsoft.com/dataset/${encodeURIComponent(collection.id)}`;\n  }\n\n  /**\n   * Starts interactive map bounding box drawing.\n   */\n  private _startBboxDraw(): void {\n    if (!this._map || !this._mapContainer || !this._options.enableBboxSelector) return;\n\n    this._stopBboxDraw(false);\n    this._state.bboxSelectorActive = true;\n    this._bboxStartPoint = null;\n    this._bboxDragPanWasEnabled = this._map.dragPan.isEnabled();\n    this._bboxBoxZoomWasEnabled = this._map.boxZoom.isEnabled();\n    this._map.dragPan.disable();\n    this._map.boxZoom.disable();\n\n    this._mapContainer.classList.add('pc-bbox-drawing');\n\n    this._bboxOverlay = document.createElement('div');\n    this._bboxOverlay.className = 'pc-bbox-overlay';\n    this._bboxOverlay.innerHTML = '<div class=\"pc-bbox-instructions\">Drag on the map to draw a bounding box</div>';\n\n    this._bboxBox = document.createElement('div');\n    this._bboxBox.className = 'pc-bbox-box';\n    this._bboxOverlay.appendChild(this._bboxBox);\n    this._mapContainer.appendChild(this._bboxOverlay);\n\n    this._bboxPointerDownHandler = (event: PointerEvent) => {\n      if (event.button !== 0 || !this._mapContainer) return;\n\n      event.preventDefault();\n      event.stopPropagation();\n      this._ignoreNextDocumentClick = true;\n      this._bboxStartPoint = this._getPointerPoint(event);\n      this._updateBboxBox(this._bboxStartPoint, this._bboxStartPoint);\n    };\n\n    this._bboxPointerMoveHandler = (event: PointerEvent) => {\n      if (!this._bboxStartPoint) return;\n\n      event.preventDefault();\n      this._updateBboxBox(this._bboxStartPoint, this._getPointerPoint(event));\n    };\n\n    this._bboxPointerUpHandler = (event: PointerEvent) => {\n      if (!this._bboxStartPoint || !this._map) return;\n\n      event.preventDefault();\n      this._ignoreNextDocumentClick = true;\n\n      const endPoint = this._getPointerPoint(event);\n      const left = Math.min(this._bboxStartPoint.x, endPoint.x);\n      const right = Math.max(this._bboxStartPoint.x, endPoint.x);\n      const top = Math.min(this._bboxStartPoint.y, endPoint.y);\n      const bottom = Math.max(this._bboxStartPoint.y, endPoint.y);\n\n      if (right - left < 4 || bottom - top < 4) {\n        this._bboxStartPoint = null;\n        if (this._bboxBox) {\n          this._bboxBox.style.display = 'none';\n        }\n        return;\n      }\n\n      const southwest = this._map.unproject([left, bottom]);\n      const northeast = this._map.unproject([right, top]);\n      const bbox: [number, number, number, number] = [\n        Math.min(southwest.lng, northeast.lng),\n        Math.min(southwest.lat, northeast.lat),\n        Math.max(southwest.lng, northeast.lng),\n        Math.max(southwest.lat, northeast.lat),\n      ];\n\n      this._state.drawnBbox = bbox;\n      this._state.searchParams.bbox = bbox;\n      this._stopBboxDraw(false);\n      this._emit('bbox:complete', bbox);\n      this._emit('statechange');\n      this._renderContent();\n    };\n\n    this._bboxKeyDownHandler = (event: KeyboardEvent) => {\n      if (event.key === 'Escape') {\n        this._stopBboxDraw();\n      }\n    };\n\n    this._mapContainer.addEventListener('pointerdown', this._bboxPointerDownHandler);\n    window.addEventListener('pointermove', this._bboxPointerMoveHandler);\n    window.addEventListener('pointerup', this._bboxPointerUpHandler);\n    document.addEventListener('keydown', this._bboxKeyDownHandler);\n\n    this._emit('bbox:start');\n    this._emit('statechange');\n    this._renderContent();\n  }\n\n  /**\n   * Stops interactive bounding box drawing and restores map input.\n   */\n  private _stopBboxDraw(render = true): void {\n    if (this._bboxPointerDownHandler && this._mapContainer) {\n      this._mapContainer.removeEventListener('pointerdown', this._bboxPointerDownHandler);\n    }\n    if (this._bboxPointerMoveHandler) {\n      window.removeEventListener('pointermove', this._bboxPointerMoveHandler);\n    }\n    if (this._bboxPointerUpHandler) {\n      window.removeEventListener('pointerup', this._bboxPointerUpHandler);\n    }\n    if (this._bboxKeyDownHandler) {\n      document.removeEventListener('keydown', this._bboxKeyDownHandler);\n    }\n\n    this._bboxPointerDownHandler = null;\n    this._bboxPointerMoveHandler = null;\n    this._bboxPointerUpHandler = null;\n    this._bboxKeyDownHandler = null;\n    this._bboxStartPoint = null;\n\n    this._bboxOverlay?.parentNode?.removeChild(this._bboxOverlay);\n    this._bboxOverlay = undefined;\n    this._bboxBox = undefined;\n\n    this._mapContainer?.classList.remove('pc-bbox-drawing');\n\n    if (this._map) {\n      if (this._bboxDragPanWasEnabled && !this._map.dragPan.isEnabled()) {\n        this._map.dragPan.enable();\n      }\n      if (this._bboxBoxZoomWasEnabled && !this._map.boxZoom.isEnabled()) {\n        this._map.boxZoom.enable();\n      }\n    }\n\n    if (!this._state.bboxSelectorActive) return;\n\n    this._state.bboxSelectorActive = false;\n    this._emit('statechange');\n    if (render) {\n      this._renderContent();\n    }\n  }\n\n  /**\n   * Gets a pointer location relative to the map container.\n   */\n  private _getPointerPoint(event: PointerEvent): ScreenPoint {\n    const rect = this._mapContainer?.getBoundingClientRect();\n    if (!rect) return { x: 0, y: 0 };\n\n    return {\n      x: event.clientX - rect.left,\n      y: event.clientY - rect.top,\n    };\n  }\n\n  /**\n   * Updates the visible bounding box rectangle.\n   */\n  private _updateBboxBox(startPoint: ScreenPoint, endPoint: ScreenPoint): void {\n    if (!this._bboxBox) return;\n\n    const left = Math.min(startPoint.x, endPoint.x);\n    const top = Math.min(startPoint.y, endPoint.y);\n    const width = Math.abs(startPoint.x - endPoint.x);\n    const height = Math.abs(startPoint.y - endPoint.y);\n\n    this._bboxBox.style.display = 'block';\n    this._bboxBox.style.left = `${left}px`;\n    this._bboxBox.style.top = `${top}px`;\n    this._bboxBox.style.width = `${width}px`;\n    this._bboxBox.style.height = `${height}px`;\n  }\n\n  /**\n   * Shows search result footprints on the map.\n   */\n  private _showSearchFootprints(items: STACItem[]): void {\n    if (!this._map) return;\n\n    if (!this._map.isStyleLoaded()) {\n      this._map.once('load', () => this._showSearchFootprints(items));\n      return;\n    }\n\n    const data: FeatureCollection<Geometry | Polygon, FootprintFeature['properties']> = {\n      type: 'FeatureCollection',\n      features: items\n        .map((item) => this._itemToFootprintFeature(item))\n        .filter((feature): feature is FootprintFeature => Boolean(feature)),\n    };\n\n    const source = this._map.getSource(FOOTPRINT_SOURCE_ID) as GeoJSONSource | undefined;\n    if (source) {\n      source.setData(data);\n    } else {\n      this._map.addSource(FOOTPRINT_SOURCE_ID, {\n        type: 'geojson',\n        data,\n      });\n    }\n\n    this._ensureFootprintLayers();\n    this._bindFootprintInteractions();\n    this._updateSelectedFootprint();\n  }\n\n  /**\n   * Adds footprint layers if they do not already exist.\n   */\n  private _ensureFootprintLayers(): void {\n    if (!this._map) return;\n\n    if (!this._map.getLayer(FOOTPRINT_FILL_LAYER_ID)) {\n      this._map.addLayer({\n        id: FOOTPRINT_FILL_LAYER_ID,\n        type: 'fill',\n        source: FOOTPRINT_SOURCE_ID,\n        paint: {\n          'fill-color': '#0078d4',\n          'fill-opacity': 0.1,\n        },\n      });\n    }\n\n    if (!this._map.getLayer(FOOTPRINT_OUTLINE_LAYER_ID)) {\n      this._map.addLayer({\n        id: FOOTPRINT_OUTLINE_LAYER_ID,\n        type: 'line',\n        source: FOOTPRINT_SOURCE_ID,\n        paint: {\n          'line-color': '#0078d4',\n          'line-width': 1.5,\n          'line-opacity': 0.75,\n        },\n      });\n    }\n\n    if (!this._map.getLayer(FOOTPRINT_SELECTED_FILL_LAYER_ID)) {\n      this._map.addLayer({\n        id: FOOTPRINT_SELECTED_FILL_LAYER_ID,\n        type: 'fill',\n        source: FOOTPRINT_SOURCE_ID,\n        filter: ['==', ['get', 'itemId'], ''],\n        paint: {\n          'fill-color': '#ffb900',\n          'fill-opacity': 0.24,\n        },\n      });\n    }\n\n    if (!this._map.getLayer(FOOTPRINT_SELECTED_OUTLINE_LAYER_ID)) {\n      this._map.addLayer({\n        id: FOOTPRINT_SELECTED_OUTLINE_LAYER_ID,\n        type: 'line',\n        source: FOOTPRINT_SOURCE_ID,\n        filter: ['==', ['get', 'itemId'], ''],\n        paint: {\n          'line-color': '#ff8c00',\n          'line-width': 3,\n          'line-opacity': 0.95,\n        },\n      });\n    }\n  }\n\n  /**\n   * Binds map interactions for selecting footprint features.\n   */\n  private _bindFootprintInteractions(): void {\n    if (!this._map || this._footprintClickHandler) return;\n\n    this._footprintClickHandler = (event: MapLayerMouseEvent) => {\n      if (this._state.bboxSelectorActive || this._inspectorLayerId) return;\n\n      const itemId = event.features?.[0]?.properties?.itemId;\n      if (typeof itemId !== 'string') return;\n\n      this._ignoreNextDocumentClick = true;\n      this._selectSearchResult(itemId, { fromMap: true });\n    };\n\n    this._footprintMouseEnterHandler = () => {\n      if (this._mapContainer && !this._state.bboxSelectorActive && !this._inspectorLayerId) {\n        this._mapContainer.style.cursor = 'pointer';\n      }\n    };\n\n    this._footprintMouseLeaveHandler = () => {\n      if (this._mapContainer && !this._state.bboxSelectorActive && !this._inspectorLayerId) {\n        this._mapContainer.style.cursor = '';\n      }\n    };\n\n    this._map.on('click', FOOTPRINT_FILL_LAYER_ID, this._footprintClickHandler);\n    this._map.on('mouseenter', FOOTPRINT_FILL_LAYER_ID, this._footprintMouseEnterHandler);\n    this._map.on('mouseleave', FOOTPRINT_FILL_LAYER_ID, this._footprintMouseLeaveHandler);\n  }\n\n  /**\n   * Selects a search result and highlights its footprint.\n   */\n  private _selectSearchResult(itemId: string | null, options: { fromMap?: boolean } = {}): void {\n    this._state.selectedSearchResultId = itemId;\n    this._state.selectedItem = itemId\n      ? this._state.searchResults.find((item) => item.id === itemId) || null\n      : null;\n    this._updateSelectedFootprint();\n    if (options.fromMap && this._state.activeView !== 'results') {\n      this._state.activeView = 'results';\n    }\n\n    this._emit('item:select');\n    this._emit('statechange');\n    this._renderContent();\n\n    if (options.fromMap) {\n      this._scrollSelectedResultIntoView();\n    }\n  }\n\n  /**\n   * Clears only the current search result selection.\n   */\n  private _clearSearchSelection(render = true): void {\n    this._state.selectedSearchResultId = null;\n    this._state.selectedItem = null;\n    this._updateSelectedFootprint();\n    this._emit('statechange');\n\n    if (render) {\n      this._renderContent();\n    }\n  }\n\n  /**\n   * Removes all search footprint overlays from the map.\n   */\n  private _clearSearchFootprints(render = true): void {\n    if (this._map) {\n      if (this._footprintClickHandler) {\n        this._map.off('click', FOOTPRINT_FILL_LAYER_ID, this._footprintClickHandler);\n      }\n      if (this._footprintMouseEnterHandler) {\n        this._map.off('mouseenter', FOOTPRINT_FILL_LAYER_ID, this._footprintMouseEnterHandler);\n      }\n      if (this._footprintMouseLeaveHandler) {\n        this._map.off('mouseleave', FOOTPRINT_FILL_LAYER_ID, this._footprintMouseLeaveHandler);\n      }\n\n      [\n        FOOTPRINT_SELECTED_OUTLINE_LAYER_ID,\n        FOOTPRINT_SELECTED_FILL_LAYER_ID,\n        FOOTPRINT_OUTLINE_LAYER_ID,\n        FOOTPRINT_FILL_LAYER_ID,\n      ].forEach((layerId) => {\n        if (this._map?.getLayer(layerId)) {\n          this._map.removeLayer(layerId);\n        }\n      });\n\n      if (this._map.getSource(FOOTPRINT_SOURCE_ID)) {\n        this._map.removeSource(FOOTPRINT_SOURCE_ID);\n      }\n    }\n\n    this._footprintClickHandler = null;\n    this._footprintMouseEnterHandler = null;\n    this._footprintMouseLeaveHandler = null;\n    this._mapContainer?.style.removeProperty('cursor');\n    this._state.selectedSearchResultId = null;\n    this._state.selectedItem = null;\n\n    if (render) {\n      this._emit('statechange');\n      this._renderContent();\n    }\n  }\n\n  /**\n   * Updates the highlighted footprint filter.\n   */\n  private _updateSelectedFootprint(): void {\n    if (!this._map) return;\n\n    const itemId = this._state.selectedSearchResultId || '';\n    const filter: ['==', ['get', string], string] = ['==', ['get', 'itemId'], itemId];\n\n    if (this._map.getLayer(FOOTPRINT_SELECTED_FILL_LAYER_ID)) {\n      this._map.setFilter(FOOTPRINT_SELECTED_FILL_LAYER_ID, filter);\n    }\n    if (this._map.getLayer(FOOTPRINT_SELECTED_OUTLINE_LAYER_ID)) {\n      this._map.setFilter(FOOTPRINT_SELECTED_OUTLINE_LAYER_ID, filter);\n    }\n  }\n\n  /**\n   * Converts a STAC item to a footprint feature.\n   */\n  private _itemToFootprintFeature(item: STACItem): FootprintFeature | null {\n    const geometry = item.geometry || this._bboxToPolygon(item.bbox);\n    if (!geometry) return null;\n\n    return {\n      type: 'Feature',\n      id: item.id,\n      geometry,\n      properties: {\n        itemId: item.id,\n        title: item.id,\n      },\n    };\n  }\n\n  /**\n   * Converts a bbox to a polygon geometry.\n   */\n  private _bboxToPolygon(bbox?: number[]): Polygon | null {\n    if (!bbox || bbox.length < 4) return null;\n\n    const [west, south, east, north] = bbox;\n    if (![west, south, east, north].every((value) => Number.isFinite(value))) {\n      return null;\n    }\n\n    return {\n      type: 'Polygon',\n      coordinates: [\n        [\n          [west, south],\n          [east, south],\n          [east, north],\n          [west, north],\n          [west, south],\n        ],\n      ],\n    };\n  }\n\n  /**\n   * Scrolls the selected result row into view.\n   */\n  private _scrollSelectedResultIntoView(): void {\n    if (!this._state.selectedSearchResultId) return;\n\n    const selectedEl = Array.from(this._contentEl?.querySelectorAll('.pc-result-item') || []).find(\n      (el) => el.getAttribute('data-id') === this._state.selectedSearchResultId\n    );\n    selectedEl?.scrollIntoView({ block: 'nearest' });\n  }\n\n  /**\n   * Renders results view.\n   */\n  private _renderResults(): void {\n    if (!this._contentEl) return;\n\n    if (this._state.searchLoading) {\n      this._contentEl.innerHTML = `\n        <div class=\"pc-loading\">\n          <div class=\"pc-spinner\"></div>\n          <span>Searching...</span>\n        </div>\n      `;\n      return;\n    }\n\n    const results = this._state.searchResults;\n    const selectedId = this._state.selectedSearchResultId;\n\n    this._contentEl.innerHTML = `\n      <div class=\"pc-results\">\n        <div class=\"pc-results-header\">\n          <button type=\"button\" class=\"pc-btn-back\">&larr; Back</button>\n          <span class=\"pc-results-count\">${results.length} items found</span>\n        </div>\n        ${\n          results.length\n            ? `\n        <div class=\"pc-results-toolbar\">\n          <button type=\"button\" class=\"pc-btn pc-btn-small pc-clear-result-selection\" ${selectedId ? '' : 'disabled'}>\n            Clear Selection\n          </button>\n          <button type=\"button\" class=\"pc-btn pc-btn-small pc-clear-footprints\">\n            Clear Footprints\n          </button>\n        </div>\n        `\n            : ''\n        }\n        <div class=\"pc-results-list\">\n          ${\n            results.length === 0\n              ? '<div class=\"pc-results-empty\">No items found. Try adjusting your search.</div>'\n              : results\n                  .map(\n                    (item) => `\n                <div class=\"pc-result-item${\n                  selectedId === item.id ? ' pc-result-selected' : ''\n                }\" data-id=\"${item.id}\">\n                  ${\n                    item.assets.thumbnail?.href\n                      ? `<div class=\"pc-result-thumbnail\"><img src=\"${item.assets.thumbnail.href}\" alt=\"\" loading=\"lazy\"></div>`\n                      : ''\n                  }\n                  <div class=\"pc-result-info\">\n                    <div class=\"pc-result-title\">${item.id}</div>\n                    <div class=\"pc-result-date\">${formatDate(getItemDate(item.properties))}</div>\n                    ${\n                      item.properties['eo:cloud_cover'] !== undefined\n                        ? `<div class=\"pc-result-cloud\">Cloud: ${item.properties['eo:cloud_cover'].toFixed(0)}%</div>`\n                        : ''\n                    }\n                  </div>\n                  <div class=\"pc-result-actions\">\n                    <button type=\"button\" class=\"pc-btn pc-btn-small pc-view-item\" title=\"View details\">View</button>\n                    <button type=\"button\" class=\"pc-btn pc-btn-small pc-add-layer\" title=\"Add to map\">+</button>\n                  </div>\n                </div>\n              `\n                  )\n                  .join('')\n          }\n        </div>\n      </div>\n    `;\n\n    this._contentEl.querySelector('.pc-btn-back')?.addEventListener('click', () => {\n      this.setView('search');\n    });\n\n    this._contentEl.querySelector('.pc-clear-result-selection')?.addEventListener('click', () => {\n      this._clearSearchSelection();\n    });\n\n    this._contentEl.querySelector('.pc-clear-footprints')?.addEventListener('click', () => {\n      this._clearSearchFootprints();\n    });\n\n    this._contentEl.querySelectorAll('.pc-result-item').forEach((el) => {\n      const id = el.getAttribute('data-id');\n      const item = results.find((i) => i.id === id);\n      if (!item) return;\n\n      el.querySelector('.pc-add-layer')?.addEventListener('click', (e) => {\n        e.stopPropagation();\n        const layer = this.addItemLayer(item);\n        if (layer) {\n          this.zoomToLayer(layer.id);\n        }\n      });\n\n      el.querySelector('.pc-view-item')?.addEventListener('click', (e) => {\n        e.stopPropagation();\n        this.selectItem(item);\n      });\n\n      el.addEventListener('click', () => {\n        this.selectItem(item);\n      });\n    });\n  }\n\n  /**\n   * Renders item detail view.\n   */\n  private _renderItem(): void {\n    if (!this._contentEl || !this._state.selectedItem) return;\n\n    const item = this._state.selectedItem;\n    const assets = Object.entries(item.assets);\n    const presets = item.collection ? getPresetsForCollection(item.collection) : [];\n\n    // Filter assets that can be visualized (COG, GeoTIFF, image types)\n    const visualizableAssets = assets.filter(([, asset]) => {\n      const type = asset.type || '';\n      return type.includes('tiff') || type.includes('geotiff') || type.includes('cog') ||\n             type.includes('image') || !type; // Include if no type specified\n    });\n\n    // Common colormaps available in TiTiler\n    const colormaps = [\n      { name: '', label: 'None (Default)' },\n      { name: 'viridis', label: 'Viridis' },\n      { name: 'plasma', label: 'Plasma' },\n      { name: 'inferno', label: 'Inferno' },\n      { name: 'magma', label: 'Magma' },\n      { name: 'cividis', label: 'Cividis' },\n      { name: 'terrain', label: 'Terrain' },\n      { name: 'rdylgn', label: 'Red-Yellow-Green' },\n      { name: 'rdylbu', label: 'Red-Yellow-Blue' },\n      { name: 'spectral', label: 'Spectral' },\n      { name: 'coolwarm', label: 'Cool-Warm' },\n      { name: 'blues', label: 'Blues' },\n      { name: 'greens', label: 'Greens' },\n      { name: 'reds', label: 'Reds' },\n      { name: 'greys', label: 'Greys' },\n      { name: 'ylgnbu', label: 'Yellow-Green-Blue' },\n      { name: 'rainbow', label: 'Rainbow' },\n    ];\n\n    this._contentEl.innerHTML = `\n      <div class=\"pc-item-details\">\n        <div class=\"pc-details-header\">\n          <button type=\"button\" class=\"pc-btn-back\">&larr; Back</button>\n          <h3 class=\"pc-details-title\">${item.id}</h3>\n        </div>\n\n        <div class=\"pc-details-meta\">\n          <div class=\"pc-meta-item\">\n            <span class=\"pc-label\">Date</span>\n            <span class=\"pc-value\">${formatDate(getItemDate(item.properties))}</span>\n          </div>\n          ${\n            item.properties['eo:cloud_cover'] !== undefined\n              ? `\n            <div class=\"pc-meta-item\">\n              <span class=\"pc-label\">Cloud Cover</span>\n              <span class=\"pc-value\">${(item.properties['eo:cloud_cover'] as number).toFixed(1)}%</span>\n            </div>\n          `\n              : ''\n          }\n        </div>\n\n        <div class=\"pc-details-section\">\n          <h4 class=\"pc-section-title\">Visualization Options</h4>\n\n          ${\n            presets.length\n              ? `\n            <div class=\"pc-form-group\">\n              <label class=\"pc-label\">Preset</label>\n              <select class=\"pc-input pc-preset-select\">\n                <option value=\"\">Custom</option>\n                ${presets.map((p) => `<option value=\"${p.name}\">${p.label}</option>`).join('')}\n              </select>\n            </div>\n          `\n              : ''\n          }\n\n          <div class=\"pc-custom-viz\">\n            <div class=\"pc-form-group\">\n              <label class=\"pc-label\">Asset</label>\n              <select class=\"pc-input pc-asset-select\">\n                ${visualizableAssets.map(([key, asset]) =>\n                  `<option value=\"${key}\">${asset.title || key}</option>`\n                ).join('')}\n              </select>\n            </div>\n\n            <div class=\"pc-form-group\">\n              <label class=\"pc-label\">Rescale (Min, Max)</label>\n              <div class=\"pc-rescale-inputs\">\n                <input type=\"number\" class=\"pc-input pc-rescale-min\" placeholder=\"Min (e.g., 0)\" step=\"any\">\n                <span class=\"pc-rescale-separator\">to</span>\n                <input type=\"number\" class=\"pc-input pc-rescale-max\" placeholder=\"Max (e.g., 255)\" step=\"any\">\n              </div>\n            </div>\n\n            <div class=\"pc-form-group\">\n              <label class=\"pc-label\">Colormap</label>\n              <select class=\"pc-input pc-colormap-select\">\n                ${colormaps.map((c) => `<option value=\"${c.name}\">${c.label}</option>`).join('')}\n              </select>\n            </div>\n\n            <div class=\"pc-form-group\">\n              <label class=\"pc-label\">Band Expression (optional)</label>\n              <input type=\"text\" class=\"pc-input pc-expression-input\" placeholder=\"e.g., (B08-B04)/(B08+B04)\">\n              <small class=\"pc-hint\">Leave empty to use selected asset. Use band math for indices like NDVI.</small>\n            </div>\n\n            <details class=\"pc-advanced-render\">\n              <summary>Advanced Rendering</summary>\n\n              <div class=\"pc-form-group\">\n                <label class=\"pc-label\">Tile Output</label>\n                <div class=\"pc-advanced-grid\">\n                  <select class=\"pc-input pc-tile-format\">\n                    <option value=\"\">Default</option>\n                    <option value=\"png\">PNG</option>\n                    <option value=\"jpg\">JPG</option>\n                    <option value=\"webp\">WebP</option>\n                    <option value=\"pngraw\">PNG Raw</option>\n                  </select>\n                  <select class=\"pc-input pc-tile-scale\">\n                    <option value=\"\">1x</option>\n                    <option value=\"2\">2x</option>\n                    <option value=\"3\">3x</option>\n                    <option value=\"4\">4x</option>\n                  </select>\n                </div>\n              </div>\n\n              <div class=\"pc-form-group\">\n                <label class=\"pc-label\">Zoom Range</label>\n                <div class=\"pc-rescale-inputs\">\n                  <input type=\"number\" class=\"pc-input pc-minzoom\" placeholder=\"Min zoom\" min=\"0\" max=\"30\">\n                  <span class=\"pc-rescale-separator\">to</span>\n                  <input type=\"number\" class=\"pc-input pc-maxzoom\" placeholder=\"Max zoom\" min=\"0\" max=\"30\">\n                </div>\n              </div>\n\n              <div class=\"pc-form-group\">\n                <label class=\"pc-label\">Color Formula</label>\n                <input type=\"text\" class=\"pc-input pc-color-formula\" placeholder=\"e.g., gamma rgb 1.8\">\n              </div>\n\n              <div class=\"pc-advanced-grid\">\n                <div class=\"pc-form-group\">\n                  <label class=\"pc-label\">Nodata</label>\n                  <input type=\"number\" class=\"pc-input pc-nodata\" placeholder=\"Auto\" step=\"any\">\n                </div>\n                <div class=\"pc-form-group\">\n                  <label class=\"pc-label\">Buffer</label>\n                  <input type=\"number\" class=\"pc-input pc-buffer\" placeholder=\"0\" min=\"0\" step=\"1\">\n                </div>\n              </div>\n\n              <div class=\"pc-checkbox-group\">\n                <label><input type=\"checkbox\" class=\"pc-unscale\"> Unscale</label>\n                <label><input type=\"checkbox\" class=\"pc-asset-as-band\"> Asset as band</label>\n                <label><input type=\"checkbox\" class=\"pc-return-mask\"> Return mask</label>\n              </div>\n            </details>\n          </div>\n        </div>\n\n        <div class=\"pc-details-section\">\n          <h4 class=\"pc-section-title\">Data API Tools</h4>\n          <div class=\"pc-tool-actions\">\n            <button type=\"button\" class=\"pc-btn pc-btn-small pc-load-stats\">Statistics</button>\n            <button type=\"button\" class=\"pc-btn pc-btn-small pc-auto-stretch\">Auto Stretch</button>\n            <button type=\"button\" class=\"pc-btn pc-btn-small pc-show-legend\">Legend</button>\n            <button type=\"button\" class=\"pc-btn pc-btn-small pc-load-tilejson\">TileJSON</button>\n            <button type=\"button\" class=\"pc-btn pc-btn-small pc-export-preview\">Preview</button>\n            <button type=\"button\" class=\"pc-btn pc-btn-small pc-export-bbox\" ${\n              this._state.drawnBbox ? '' : 'disabled'\n            }>BBox Image</button>\n          </div>\n          <div class=\"pc-tool-output pc-stats-output\"></div>\n        </div>\n\n        <div class=\"pc-details-section\">\n          <h4 class=\"pc-section-title\">Assets (${assets.length})</h4>\n          <div class=\"pc-assets-list\">\n            ${assets\n              .map(\n                ([key, asset]) => `\n              <div class=\"pc-asset-item\" data-key=\"${key}\">\n                <div class=\"pc-asset-info\">\n                  <div class=\"pc-asset-name\">${asset.title || key}</div>\n                  <div class=\"pc-asset-type\">${asset.type || 'Unknown'}</div>\n                </div>\n                <button type=\"button\" class=\"pc-btn pc-btn-small pc-download-asset\">Download</button>\n              </div>\n            `\n              )\n              .join('')}\n          </div>\n        </div>\n\n        <div class=\"pc-details-actions\">\n          <button type=\"button\" class=\"pc-btn pc-btn-primary pc-add-to-map\">Add to Map</button>\n        </div>\n      </div>\n    `;\n\n    // Toggle custom visualization options based on preset selection\n    const presetSelect = this._contentEl.querySelector('.pc-preset-select') as HTMLSelectElement;\n    const customViz = this._contentEl.querySelector('.pc-custom-viz') as HTMLElement;\n    if (presetSelect && customViz) {\n      presetSelect.addEventListener('change', () => {\n        customViz.style.display = presetSelect.value ? 'none' : 'block';\n      });\n    }\n\n    this._contentEl.querySelector('.pc-btn-back')?.addEventListener('click', () => {\n      this._state.activeView = 'results';\n      this._emit('statechange');\n      this._renderContent();\n    });\n\n    const getCurrentRenderParams = (): TileParams => {\n      const presetName = (this._contentEl?.querySelector('.pc-preset-select') as HTMLSelectElement)?.value;\n      const advancedParams = this._getAdvancedRenderParams();\n      if (presetName) {\n        return { ...(presets.find((p) => p.name === presetName)?.params || {}), ...advancedParams };\n      }\n\n      return { ...this._getCustomRenderParams(), ...advancedParams };\n    };\n\n    this._contentEl.querySelector('.pc-load-stats')?.addEventListener('click', async () => {\n      await this._loadItemStatistics(item, getCurrentRenderParams());\n    });\n\n    this._contentEl.querySelector('.pc-auto-stretch')?.addEventListener('click', async () => {\n      await this._autoStretchItem(item, getCurrentRenderParams());\n    });\n\n    this._contentEl.querySelector('.pc-show-legend')?.addEventListener('click', () => {\n      this._showRenderLegend(getCurrentRenderParams());\n    });\n\n    this._contentEl.querySelector('.pc-load-tilejson')?.addEventListener('click', async () => {\n      await this._loadItemTileJSON(item, getCurrentRenderParams());\n    });\n\n    this._contentEl.querySelector('.pc-export-preview')?.addEventListener('click', () => {\n      this._openItemPreview(item, getCurrentRenderParams());\n    });\n\n    this._contentEl.querySelector('.pc-export-bbox')?.addEventListener('click', () => {\n      this._openItemBboxImage(item, getCurrentRenderParams());\n    });\n\n    this._contentEl.querySelector('.pc-add-to-map')?.addEventListener('click', () => {\n      const presetName = (this._contentEl?.querySelector('.pc-preset-select') as HTMLSelectElement)?.value;\n      let layer;\n\n      if (presetName) {\n        // Use preset\n        const preset = presets.find((p) => p.name === presetName);\n        layer = this.addItemLayer(item, preset ? { presetName, renderParams: getCurrentRenderParams() } : undefined);\n      } else {\n        layer = this.addItemLayer(item, { renderParams: getCurrentRenderParams() });\n      }\n\n      // Zoom to the added layer\n      if (layer) {\n        this.zoomToLayer(layer.id);\n      }\n    });\n\n    this._contentEl.querySelectorAll('.pc-download-asset').forEach((btn) => {\n      btn.addEventListener('click', async (e) => {\n        e.stopPropagation();\n        const assetKey = (btn.closest('.pc-asset-item') as HTMLElement)?.dataset.key;\n        if (assetKey) {\n          try {\n            const url = await this.getDownloadUrl(item, assetKey);\n            window.open(url, '_blank');\n          } catch (error) {\n            console.error('Download error:', error);\n          }\n        }\n      });\n    });\n  }\n\n  /**\n   * Gets custom render parameters from the item detail form.\n   */\n  private _getCustomRenderParams(): TileParams {\n    const assetSelect = this._contentEl?.querySelector('.pc-asset-select') as HTMLSelectElement;\n    const rescaleMin = (this._contentEl?.querySelector('.pc-rescale-min') as HTMLInputElement)?.value;\n    const rescaleMax = (this._contentEl?.querySelector('.pc-rescale-max') as HTMLInputElement)?.value;\n    const colormap = (this._contentEl?.querySelector('.pc-colormap-select') as HTMLSelectElement)?.value;\n    const expression = (this._contentEl?.querySelector('.pc-expression-input') as HTMLInputElement)?.value;\n\n    const renderParams: TileParams = {};\n\n    if (assetSelect?.value) {\n      renderParams.assets = [assetSelect.value];\n    }\n\n    if (rescaleMin && rescaleMax) {\n      renderParams.rescale = `${rescaleMin},${rescaleMax}`;\n    }\n\n    if (colormap) {\n      renderParams.colormap_name = colormap;\n    }\n\n    if (expression) {\n      renderParams.expression = expression;\n      delete renderParams.assets;\n    }\n\n    return renderParams;\n  }\n\n  /**\n   * Gets advanced render parameters from the item detail form.\n   */\n  private _getAdvancedRenderParams(): TileParams {\n    const tileFormat = (this._contentEl?.querySelector('.pc-tile-format') as HTMLSelectElement)?.value;\n    const tileScale = (this._contentEl?.querySelector('.pc-tile-scale') as HTMLSelectElement)?.value;\n    const minzoom = (this._contentEl?.querySelector('.pc-minzoom') as HTMLInputElement)?.value;\n    const maxzoom = (this._contentEl?.querySelector('.pc-maxzoom') as HTMLInputElement)?.value;\n    const colorFormula = (this._contentEl?.querySelector('.pc-color-formula') as HTMLInputElement)?.value;\n    const nodata = (this._contentEl?.querySelector('.pc-nodata') as HTMLInputElement)?.value;\n    const buffer = (this._contentEl?.querySelector('.pc-buffer') as HTMLInputElement)?.value;\n    const unscale = (this._contentEl?.querySelector('.pc-unscale') as HTMLInputElement)?.checked;\n    const assetAsBand = (this._contentEl?.querySelector('.pc-asset-as-band') as HTMLInputElement)?.checked;\n    const returnMask = (this._contentEl?.querySelector('.pc-return-mask') as HTMLInputElement)?.checked;\n\n    const params: TileParams = {};\n\n    if (tileFormat) {\n      params.tile_format = tileFormat as TileParams['tile_format'];\n    }\n    if (tileScale) {\n      params.tile_scale = parseInt(tileScale) as TileParams['tile_scale'];\n    }\n    if (minzoom) {\n      params.minzoom = parseInt(minzoom);\n    }\n    if (maxzoom) {\n      params.maxzoom = parseInt(maxzoom);\n    }\n    if (colorFormula) {\n      params.color_formula = colorFormula;\n    }\n    if (nodata) {\n      params.nodata = parseFloat(nodata);\n    }\n    if (buffer) {\n      params.buffer = parseInt(buffer);\n    }\n    if (unscale) {\n      params.unscale = true;\n    }\n    if (assetAsBand) {\n      params.asset_as_band = true;\n    }\n    if (returnMask) {\n      params.return_mask = true;\n    }\n\n    return params;\n  }\n\n  /**\n   * Loads item statistics and renders them in the item detail panel.\n   */\n  private async _loadItemStatistics(item: STACItem, renderParams: TileParams): Promise<Record<string, unknown> | null> {\n    const collectionId = item.collection;\n    const output = this._contentEl?.querySelector('.pc-stats-output') as HTMLElement;\n    if (!collectionId || !output) return null;\n\n    output.innerHTML = '<div class=\"pc-tool-loading\">Loading statistics...</div>';\n\n    try {\n      const statistics = await this._tilerClient.getItemStatistics(collectionId, item.id, {\n        ...renderParams,\n        histogram_bins: 20,\n        max_size: 1024,\n      });\n      output.innerHTML = this._renderStatisticsOutput(statistics);\n      return statistics;\n    } catch (error) {\n      const errorMessage = error instanceof Error ? error.message : 'Failed to load statistics';\n      output.innerHTML = `<div class=\"pc-tool-error\">${this._escapeHtml(errorMessage)}</div>`;\n      return null;\n    }\n  }\n\n  /**\n   * Applies a min/max stretch from item statistics to the custom render form.\n   */\n  private async _autoStretchItem(item: STACItem, renderParams: TileParams): Promise<void> {\n    const statistics = await this._loadItemStatistics(item, renderParams);\n    if (!statistics) return;\n\n    const band = this._findFirstBandStatistics(statistics);\n    const output = this._contentEl?.querySelector('.pc-stats-output') as HTMLElement;\n    if (!band) {\n      if (output) {\n        output.innerHTML = '<div class=\"pc-tool-error\">No numeric band statistics were found.</div>';\n      }\n      return;\n    }\n\n    const presetSelect = this._contentEl?.querySelector('.pc-preset-select') as HTMLSelectElement;\n    const customViz = this._contentEl?.querySelector('.pc-custom-viz') as HTMLElement;\n    const minInput = this._contentEl?.querySelector('.pc-rescale-min') as HTMLInputElement;\n    const maxInput = this._contentEl?.querySelector('.pc-rescale-max') as HTMLInputElement;\n    const assetSelect = this._contentEl?.querySelector('.pc-asset-select') as HTMLSelectElement;\n    const expressionInput = this._contentEl?.querySelector('.pc-expression-input') as HTMLInputElement;\n\n    if (presetSelect) {\n      presetSelect.value = '';\n    }\n    if (customViz) {\n      customViz.style.display = 'flex';\n    }\n    if (renderParams.assets?.[0] && assetSelect) {\n      assetSelect.value = renderParams.assets[0];\n    }\n    if (renderParams.expression && expressionInput) {\n      expressionInput.value = renderParams.expression;\n    }\n    if (minInput) {\n      minInput.value = String(band.stats.min);\n    }\n    if (maxInput) {\n      maxInput.value = String(band.stats.max);\n    }\n\n    if (output) {\n      output.innerHTML = `\n        <div class=\"pc-tool-success\">Applied stretch ${this._formatNumber(band.stats.min)} to ${this._formatNumber(band.stats.max)} from ${this._escapeHtml(band.label)}.</div>\n        ${this._renderStatisticsOutput(statistics)}\n      `;\n    }\n  }\n\n  /**\n   * Opens a rendered item preview in a new browser tab.\n   */\n  private _openItemPreview(item: STACItem, renderParams: TileParams): void {\n    if (!item.collection) return;\n\n    const url = this._tilerClient.getItemPreviewUrl(item.collection, item.id, renderParams);\n    window.open(url, '_blank');\n  }\n\n  /**\n   * Opens a rendered bbox image in a new browser tab.\n   */\n  private _openItemBboxImage(item: STACItem, renderParams: TileParams): void {\n    if (!item.collection || !this._state.drawnBbox) return;\n\n    const url = this._tilerClient.getItemBboxImageUrl(\n      item.collection,\n      item.id,\n      this._state.drawnBbox,\n      { width: 768, height: 512 },\n      renderParams\n    );\n    window.open(url, '_blank');\n  }\n\n  /**\n   * Shows the legend for the current named colormap.\n   */\n  private _showRenderLegend(renderParams: TileParams): void {\n    const output = this._contentEl?.querySelector('.pc-stats-output') as HTMLElement;\n    if (!output) return;\n\n    if (!renderParams.colormap_name) {\n      output.innerHTML = '<div class=\"pc-tool-error\">Choose a named colormap to generate a legend.</div>';\n      return;\n    }\n\n    output.innerHTML = this._renderLegend(renderParams.colormap_name);\n  }\n\n  /**\n   * Loads and renders TileJSON metadata for an item.\n   */\n  private async _loadItemTileJSON(item: STACItem, renderParams: TileParams): Promise<void> {\n    const collectionId = item.collection;\n    const output = this._contentEl?.querySelector('.pc-stats-output') as HTMLElement;\n    if (!collectionId || !output) return;\n\n    output.innerHTML = '<div class=\"pc-tool-loading\">Loading TileJSON...</div>';\n\n    try {\n      const tilejson = await this._tilerClient.getItemTileJSON(collectionId, item.id, renderParams);\n      const bounds = Array.isArray(tilejson.bounds) ? tilejson.bounds.join(', ') : 'n/a';\n      const center = Array.isArray(tilejson.center) ? tilejson.center.join(', ') : 'n/a';\n      output.innerHTML = `\n        <div class=\"pc-tilejson-card\">\n          <div><span>Bounds</span><strong>${this._escapeHtml(bounds)}</strong></div>\n          <div><span>Center</span><strong>${this._escapeHtml(center)}</strong></div>\n          <div><span>Min Zoom</span><strong>${this._escapeHtml(String(tilejson.minzoom ?? 'n/a'))}</strong></div>\n          <div><span>Max Zoom</span><strong>${this._escapeHtml(String(tilejson.maxzoom ?? 'n/a'))}</strong></div>\n          <div><span>Tiles</span><strong>${this._escapeHtml(String(tilejson.tiles?.length || 0))}</strong></div>\n        </div>\n      `;\n    } catch (error) {\n      const errorMessage = error instanceof Error ? error.message : 'Failed to load TileJSON';\n      output.innerHTML = `<div class=\"pc-tool-error\">${this._escapeHtml(errorMessage)}</div>`;\n    }\n  }\n\n  /**\n   * Renders a legend ramp for a named colormap.\n   */\n  private _renderLegend(colormapName: string): string {\n    const gradient = this._getColormapGradient(colormapName);\n    return `\n      <div class=\"pc-legend-card\">\n        <div class=\"pc-legend-title\">${this._escapeHtml(colormapName)}</div>\n        <div class=\"pc-legend-ramp\" style=\"background:${gradient}\"></div>\n        <div class=\"pc-legend-labels\">\n          <span>Low</span>\n          <span>High</span>\n        </div>\n      </div>\n    `;\n  }\n\n  /**\n   * Gets a CSS gradient approximation for a named colormap.\n   */\n  private _getColormapGradient(colormapName: string): string {\n    const gradients: Record<string, string> = {\n      viridis: 'linear-gradient(to right, #440154, #414487, #2a788e, #22a884, #7ad151, #fde725)',\n      plasma: 'linear-gradient(to right, #0d0887, #6a00a8, #b12a90, #e16462, #fca636, #f0f921)',\n      inferno: 'linear-gradient(to right, #000004, #420a68, #932667, #dd513a, #fca50a, #fcffa4)',\n      magma: 'linear-gradient(to right, #000004, #3b0f70, #8c2981, #de4968, #fe9f6d, #fcfdbf)',\n      cividis: 'linear-gradient(to right, #00204c, #424086, #6c6f7c, #9b9e67, #d6d04d, #ffffe5)',\n      terrain: 'linear-gradient(to right, #333399, #00a6ca, #4ac16d, #f5d76e, #b07d45, #ffffff)',\n      rdylgn: 'linear-gradient(to right, #a50026, #f46d43, #fee08b, #ffffbf, #d9ef8b, #66bd63, #006837)',\n      rdylbu: 'linear-gradient(to right, #a50026, #f46d43, #fee090, #ffffbf, #e0f3f8, #74add1, #313695)',\n      spectral: 'linear-gradient(to right, #9e0142, #d53e4f, #f46d43, #fee08b, #ffffbf, #e6f598, #66c2a5, #3288bd, #5e4fa2)',\n      coolwarm: 'linear-gradient(to right, #3b4cc0, #7093f3, #dddcdc, #f7a889, #b40426)',\n      blues: 'linear-gradient(to right, #f7fbff, #deebf7, #9ecae1, #4292c6, #084594)',\n      greens: 'linear-gradient(to right, #f7fcf5, #c7e9c0, #74c476, #238b45, #00441b)',\n      reds: 'linear-gradient(to right, #fff5f0, #fcbba1, #fb6a4a, #cb181d, #67000d)',\n      greys: 'linear-gradient(to right, #ffffff, #d9d9d9, #969696, #525252, #000000)',\n      ylgnbu: 'linear-gradient(to right, #ffffd9, #c7e9b4, #41b6c4, #2c7fb8, #081d58)',\n      rainbow: 'linear-gradient(to right, #6e40aa, #4776d0, #1f9e89, #6cc24a, #f5d547, #f98e2b, #d23b3b)',\n    };\n\n    return gradients[colormapName] || 'linear-gradient(to right, #000000, #ffffff)';\n  }\n\n  /**\n   * Finds the first numeric band statistics object in a Data API response.\n   */\n  private _findFirstBandStatistics(data: unknown, label: string = 'band'): { label: string; stats: BandStatistics } | null {\n    if (!data || typeof data !== 'object') return null;\n\n    const record = data as Record<string, unknown>;\n    if (\n      typeof record.min === 'number' &&\n      typeof record.max === 'number' &&\n      typeof record.mean === 'number'\n    ) {\n      return { label, stats: record as BandStatistics };\n    }\n\n    for (const [key, value] of Object.entries(record)) {\n      const found = this._findFirstBandStatistics(value, key);\n      if (found) return found;\n    }\n\n    return null;\n  }\n\n  /**\n   * Renders a compact statistics panel.\n   */\n  private _renderStatisticsOutput(statistics: Record<string, unknown>): string {\n    const band = this._findFirstBandStatistics(statistics);\n    if (!band) {\n      return '<div class=\"pc-tool-error\">No numeric band statistics were found.</div>';\n    }\n\n    const stats = band.stats;\n    return `\n      <div class=\"pc-stats-card\">\n        <div class=\"pc-stats-title\">${this._escapeHtml(band.label)}</div>\n        <div class=\"pc-stats-grid\">\n          <div><span>Min</span><strong>${this._formatNumber(stats.min)}</strong></div>\n          <div><span>Max</span><strong>${this._formatNumber(stats.max)}</strong></div>\n          <div><span>Mean</span><strong>${this._formatNumber(stats.mean)}</strong></div>\n          <div><span>Std</span><strong>${this._formatNumber(stats.std)}</strong></div>\n          <div><span>Valid</span><strong>${this._formatNumber(stats.valid_percent)}%</strong></div>\n          <div><span>Pixels</span><strong>${this._formatNumber(stats.valid_pixels)}</strong></div>\n        </div>\n        ${this._renderHistogram(stats)}\n      </div>\n    `;\n  }\n\n  /**\n   * Renders a tiny histogram from band statistics.\n   */\n  private _renderHistogram(stats: BandStatistics): string {\n    const counts = stats.histogram?.[0];\n    if (!Array.isArray(counts) || counts.length === 0) return '';\n\n    const maxCount = Math.max(...counts.map((count) => Number(count) || 0));\n    if (maxCount <= 0) return '';\n\n    return `\n      <div class=\"pc-histogram\" aria-label=\"Histogram\">\n        ${counts\n          .map((count) => {\n            const height = Math.max(2, Math.round(((Number(count) || 0) / maxCount) * 36));\n            return `<span style=\"height:${height}px\"></span>`;\n          })\n          .join('')}\n      </div>\n    `;\n  }\n\n  /**\n   * Formats numeric output for compact display.\n   */\n  private _formatNumber(value: unknown): string {\n    if (typeof value !== 'number' || !isFinite(value)) return 'n/a';\n    if (Math.abs(value) >= 1000) return value.toLocaleString(undefined, { maximumFractionDigits: 0 });\n    if (Math.abs(value) >= 10) return value.toLocaleString(undefined, { maximumFractionDigits: 2 });\n    return value.toLocaleString(undefined, { maximumFractionDigits: 4 });\n  }\n\n  /**\n   * Escapes text for HTML rendering.\n   */\n  private _escapeHtml(value: string): string {\n    return value\n      .replace(/&/g, '&amp;')\n      .replace(/</g, '&lt;')\n      .replace(/>/g, '&gt;')\n      .replace(/\"/g, '&quot;')\n      .replace(/'/g, '&#039;');\n  }\n\n  /**\n   * Renders layers view.\n   */\n  private _renderLayers(): void {\n    if (!this._contentEl) return;\n\n    const layers = this._state.activeLayers;\n\n    if (layers.length === 0) {\n      this._contentEl.innerHTML = `\n        <div class=\"pc-layers-empty\">\n          <p>No layers added yet.</p>\n          <p>Search for data and add items to the map.</p>\n        </div>\n      `;\n      return;\n    }\n\n    this._contentEl.innerHTML = `\n      <div class=\"pc-layers-list\">\n        ${this._renderInspectorOutput()}\n        ${layers\n          .map(\n            (layer) => `\n          <div class=\"pc-layer-item\" data-id=\"${layer.id}\">\n            <div class=\"pc-layer-header\">\n              <input type=\"checkbox\" class=\"pc-layer-visibility\" ${layer.visible ? 'checked' : ''}>\n              <span class=\"pc-layer-name\" title=\"${layer.item?.id || layer.collection?.title || layer.id}\">\n                ${layer.item?.id || layer.collection?.title || layer.id}\n              </span>\n              <button type=\"button\" class=\"pc-btn-icon pc-toggle-layer-controls${\n                layer.showControls ? ' pc-layer-controls-active' : ''\n              }\" title=\"${layer.showControls ? 'Hide opacity and colormap' : 'Show opacity and colormap'}\">\n                <svg viewBox=\"0 0 24 24\" width=\"16\" height=\"16\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\">\n                  <path d=\"M4 21v-7\"/>\n                  <path d=\"M4 10V3\"/>\n                  <path d=\"M12 21v-9\"/>\n                  <path d=\"M12 8V3\"/>\n                  <path d=\"M20 21v-5\"/>\n                  <path d=\"M20 12V3\"/>\n                  <path d=\"M2 14h4\"/>\n                  <path d=\"M10 8h4\"/>\n                  <path d=\"M18 16h4\"/>\n                </svg>\n              </button>\n              ${\n                layer.item\n                  ? `<button type=\"button\" class=\"pc-btn-icon pc-inspect-layer${\n                      this._inspectorLayerId === layer.id ? ' pc-inspect-active' : ''\n                    }\" title=\"${this._inspectorLayerId === layer.id ? 'Stop inspecting' : 'Inspect pixel values'}\">\n                <svg viewBox=\"0 0 24 24\" width=\"16\" height=\"16\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\">\n                  <path d=\"M12 2v4\"/>\n                  <path d=\"M12 18v4\"/>\n                  <path d=\"M2 12h4\"/>\n                  <path d=\"M18 12h4\"/>\n                  <circle cx=\"12\" cy=\"12\" r=\"3\"/>\n                </svg>\n              </button>`\n                  : ''\n              }\n              <button type=\"button\" class=\"pc-btn-icon pc-zoom-to\" title=\"Zoom to layer\">\n                <svg viewBox=\"0 0 24 24\" width=\"16\" height=\"16\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\">\n                  <circle cx=\"11\" cy=\"11\" r=\"8\"/>\n                  <path d=\"M21 21l-4.35-4.35\"/>\n                </svg>\n              </button>\n              <button type=\"button\" class=\"pc-btn-icon pc-remove-layer\" title=\"Remove\">&times;</button>\n            </div>\n            <div class=\"pc-layer-controls${layer.showControls ? '' : ' pc-layer-controls-hidden'}\">\n              <label class=\"pc-opacity-label\">\n                Opacity: <span class=\"pc-opacity-value\">${Math.round(layer.opacity * 100)}%</span>\n              </label>\n              <input type=\"range\" class=\"pc-opacity-slider\" min=\"0\" max=\"100\" value=\"${Math.round(layer.opacity * 100)}\">\n              ${layer.renderParams.colormap_name ? this._renderLegend(layer.renderParams.colormap_name) : ''}\n            </div>\n          </div>\n        `\n          )\n          .join('')}\n      </div>\n    `;\n\n    this._contentEl.querySelectorAll('.pc-layer-item').forEach((el) => {\n      const layerId = el.getAttribute('data-id');\n      if (!layerId) return;\n\n      const visibility = el.querySelector('.pc-layer-visibility') as HTMLInputElement;\n      const slider = el.querySelector('.pc-opacity-slider') as HTMLInputElement;\n      const opacityValue = el.querySelector('.pc-opacity-value') as HTMLElement;\n\n      visibility?.addEventListener('change', () => {\n        this.updateLayer(layerId, { visible: visibility.checked });\n      });\n\n      el.querySelector('.pc-toggle-layer-controls')?.addEventListener('click', () => {\n        const layer = this._state.activeLayers.find((activeLayer) => activeLayer.id === layerId);\n        this.updateLayer(layerId, { showControls: !layer?.showControls });\n        this._renderContent();\n      });\n\n      slider?.addEventListener('input', () => {\n        const opacity = parseInt(slider.value) / 100;\n        opacityValue.textContent = `${slider.value}%`;\n        this.updateLayer(layerId, { opacity });\n      });\n\n      el.querySelector('.pc-zoom-to')?.addEventListener('click', () => {\n        this.zoomToLayer(layerId);\n      });\n\n      el.querySelector('.pc-remove-layer')?.addEventListener('click', () => {\n        this.removeLayer(layerId);\n      });\n\n      el.querySelector('.pc-inspect-layer')?.addEventListener('click', () => {\n        if (this._inspectorLayerId === layerId) {\n          this._stopInspector();\n        } else {\n          this._startInspector(layerId);\n        }\n      });\n    });\n  }\n\n  /**\n   * Starts map click inspection for an item layer.\n   */\n  private _startInspector(layerId: string): void {\n    if (!this._map || !this._layerManager) return;\n\n    const layer = this._layerManager.getLayer(layerId);\n    if (!layer?.item?.collection) return;\n\n    this._stopInspector(false);\n    this._inspectorLayerId = layerId;\n    this._inspectorResult = null;\n    this._mapContainer?.classList.add('pc-inspector-active');\n\n    this._inspectClickHandler = (event: MapMouseEvent) => {\n      this._queryInspectorPoint(layerId, event.lngLat.lng, event.lngLat.lat);\n    };\n\n    this._map.on('click', this._inspectClickHandler);\n    this._renderContent();\n  }\n\n  /**\n   * Stops map click inspection.\n   */\n  private _stopInspector(render = true): void {\n    if (this._inspectClickHandler && this._map) {\n      this._map.off('click', this._inspectClickHandler);\n    }\n\n    this._inspectClickHandler = null;\n    this._inspectorLayerId = null;\n    this._inspectorResult = null;\n    this._mapContainer?.classList.remove('pc-inspector-active');\n\n    if (render) {\n      this._renderContent();\n    }\n  }\n\n  /**\n   * Queries Data API point values for the active inspector layer.\n   */\n  private async _queryInspectorPoint(layerId: string, lon: number, lat: number): Promise<void> {\n    const layer = this._layerManager?.getLayer(layerId);\n    if (!layer?.item?.collection) return;\n\n    if (!this._itemBboxContainsPoint(layer.item, lon, lat)) {\n      this._inspectorResult = {\n        layerId,\n        lon,\n        lat,\n        loading: false,\n        error: 'Clicked outside this item footprint. Click inside the visible footprint to inspect pixel values.',\n      };\n      this._renderContent();\n      return;\n    }\n\n    this._inspectorResult = {\n      layerId,\n      lon,\n      lat,\n      loading: true,\n    };\n    this._renderContent();\n\n    try {\n      const data = await this._tilerClient.getItemPoint(\n        layer.item.collection,\n        layer.item.id,\n        lon,\n        lat,\n        layer.renderParams\n      );\n\n      if (this._inspectorLayerId !== layerId) return;\n\n      this._inspectorResult = {\n        layerId,\n        lon,\n        lat,\n        loading: false,\n        data,\n      };\n    } catch (error) {\n      if (this._inspectorLayerId !== layerId) return;\n\n      this._inspectorResult = {\n        layerId,\n        lon,\n        lat,\n        loading: false,\n        error: this._getInspectorErrorMessage(error),\n      };\n    }\n\n    this._renderContent();\n  }\n\n  /**\n   * Checks whether a coordinate is inside a STAC item's bbox.\n   */\n  private _itemBboxContainsPoint(item: STACItem, lon: number, lat: number): boolean {\n    if (!item.bbox || item.bbox.length < 4) return true;\n\n    const [west, south, east, north] = item.bbox;\n    if (![west, south, east, north].every((value) => Number.isFinite(value))) return true;\n\n    return lon >= west && lon <= east && lat >= south && lat <= north;\n  }\n\n  /**\n   * Converts point query failures into user-facing inspector messages.\n   */\n  private _getInspectorErrorMessage(error: unknown): string {\n    const message = error instanceof Error ? error.message.trim() : '';\n\n    if (!message || message === 'Failed to get point values:' || message === 'Failed to get point values') {\n      return 'No pixel value was returned for this location. Try a point inside the layer footprint and away from nodata areas.';\n    }\n\n    if (/not found|outside|bounds|intersect|empty|no data|nodata/i.test(message)) {\n      return 'No pixel value is available at this location. The click may be outside valid data or over a nodata pixel.';\n    }\n\n    return message;\n  }\n\n  /**\n   * Renders pixel inspector status and results.\n   */\n  private _renderInspectorOutput(): string {\n    if (!this._inspectorLayerId) return '';\n\n    const layer = this._state.activeLayers.find((activeLayer) => activeLayer.id === this._inspectorLayerId);\n    const layerName = layer?.item?.id || layer?.id || this._inspectorLayerId;\n    const result = this._inspectorResult;\n\n    if (!result) {\n      return `\n        <div class=\"pc-inspector-panel\">\n          <div class=\"pc-inspector-title\">Inspecting ${this._escapeHtml(layerName)}</div>\n          <div class=\"pc-inspector-hint\">Click the map to query pixel values.</div>\n        </div>\n      `;\n    }\n\n    if (result.loading) {\n      return `\n        <div class=\"pc-inspector-panel\">\n          <div class=\"pc-inspector-title\">Inspecting ${this._escapeHtml(layerName)}</div>\n          <div class=\"pc-tool-loading\">Querying ${this._formatNumber(result.lon)}, ${this._formatNumber(result.lat)}...</div>\n        </div>\n      `;\n    }\n\n    if (result.error) {\n      return `\n        <div class=\"pc-inspector-panel\">\n          <div class=\"pc-inspector-title\">Inspecting ${this._escapeHtml(layerName)}</div>\n          <div class=\"pc-tool-error\">${this._escapeHtml(result.error)}</div>\n        </div>\n      `;\n    }\n\n    return `\n      <div class=\"pc-inspector-panel\">\n        <div class=\"pc-inspector-title\">Inspecting ${this._escapeHtml(layerName)}</div>\n        <div class=\"pc-inspector-coords\">${this._formatNumber(result.lon)}, ${this._formatNumber(result.lat)}</div>\n        ${this._renderPointValues(result.data)}\n      </div>\n    `;\n  }\n\n  /**\n   * Renders point values from a Data API point response.\n   */\n  private _renderPointValues(data?: PointValueResponse): string {\n    if (!data) return '';\n\n    if (Array.isArray(data.values)) {\n      return `\n        <div class=\"pc-point-values\">\n          ${data.values\n            .map((value, index) => {\n              const label = data.band_names?.[index] || `Band ${index + 1}`;\n              return `\n                <div>\n                  <span>${this._escapeHtml(label)}</span>\n                  <strong>${this._escapeHtml(this._formatPointValue(value))}</strong>\n                </div>\n              `;\n            })\n            .join('')}\n        </div>\n      `;\n    }\n\n    return `<pre class=\"pc-point-json\">${this._escapeHtml(JSON.stringify(data, null, 2))}</pre>`;\n  }\n\n  /**\n   * Formats a point value.\n   */\n  private _formatPointValue(value: unknown): string {\n    if (typeof value === 'number') return this._formatNumber(value);\n    if (value === null || value === undefined) return 'n/a';\n    if (Array.isArray(value)) return value.map((entry) => this._formatPointValue(entry)).join(', ');\n    return String(value);\n  }\n\n  /**\n   * Loads collections from STAC API.\n   */\n  private async _loadCollections(): Promise<STACCollection[]> {\n    this._state.collectionsLoading = true;\n    this._state.error = null;\n    this._emit('statechange');\n    this._renderContent();\n\n    try {\n      const collections = await this._stacClient.getCollections();\n\n      // Filter by default collections if specified\n      if (this._options.defaultCollections.length > 0) {\n        this._state.collections = collections.filter((c) =>\n          this._options.defaultCollections.includes(c.id)\n        );\n      } else {\n        this._state.collections = collections;\n      }\n\n      // Sort by title\n      this._state.collections.sort((a, b) =>\n        (a.title || a.id).localeCompare(b.title || b.id)\n      );\n\n      this._emit('collections:load');\n      return this._state.collections;\n    } catch (error) {\n      const errorMessage = error instanceof Error ? error.message : 'Failed to load collections';\n      this._state.error = errorMessage;\n      this._emit('error');\n      throw error;\n    } finally {\n      this._state.collectionsLoading = false;\n      this._emit('statechange');\n      this._renderContent();\n    }\n  }\n\n  /**\n   * Updates panel visibility.\n   */\n  private _updatePanelVisibility(): void {\n    if (this._panel) {\n      if (this._state.collapsed) {\n        this._panel.classList.remove('expanded');\n      } else {\n        this._panel.classList.add('expanded');\n        this._updatePanelPosition();\n      }\n    }\n  }\n\n  /**\n   * Sets up event listeners.\n   */\n  private _setupEventListeners(): void {\n    this._clickOutsideHandler = (e: MouseEvent) => {\n      if (this._ignoreNextDocumentClick) {\n        this._ignoreNextDocumentClick = false;\n        return;\n      }\n      if (this._state.bboxSelectorActive || this._inspectorLayerId) return;\n\n      const target = e.target as Node;\n      if (\n        this._container &&\n        this._panel &&\n        !this._container.contains(target) &&\n        !this._panel.contains(target)\n      ) {\n        this.collapse();\n      }\n    };\n    document.addEventListener('click', this._clickOutsideHandler);\n\n    this._resizeHandler = () => {\n      if (!this._state.collapsed) {\n        this._updatePanelPosition();\n      }\n    };\n    window.addEventListener('resize', this._resizeHandler);\n\n    this._mapResizeHandler = () => {\n      if (!this._state.collapsed) {\n        this._updatePanelPosition();\n      }\n    };\n    this._map?.on('resize', this._mapResizeHandler);\n  }\n\n  /**\n   * Gets control position.\n   */\n  private _getControlPosition(): 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right' {\n    const parent = this._container?.parentElement;\n    if (!parent) return 'top-right';\n\n    if (parent.classList.contains('maplibregl-ctrl-top-left')) return 'top-left';\n    if (parent.classList.contains('maplibregl-ctrl-top-right')) return 'top-right';\n    if (parent.classList.contains('maplibregl-ctrl-bottom-left')) return 'bottom-left';\n    if (parent.classList.contains('maplibregl-ctrl-bottom-right')) return 'bottom-right';\n\n    return 'top-right';\n  }\n\n  /**\n   * Updates panel position.\n   */\n  private _updatePanelPosition(): void {\n    if (!this._container || !this._panel || !this._mapContainer) return;\n\n    const button = this._container.querySelector('.pc-control-toggle');\n    if (!button) return;\n\n    const buttonRect = button.getBoundingClientRect();\n    const mapRect = this._mapContainer.getBoundingClientRect();\n    const position = this._getControlPosition();\n\n    const buttonTop = buttonRect.top - mapRect.top;\n    const buttonBottom = mapRect.bottom - buttonRect.bottom;\n    const buttonLeft = buttonRect.left - mapRect.left;\n    const buttonRight = mapRect.right - buttonRect.right;\n\n    const panelGap = 5;\n\n    this._panel.style.top = '';\n    this._panel.style.bottom = '';\n    this._panel.style.left = '';\n    this._panel.style.right = '';\n\n    switch (position) {\n      case 'top-left':\n        this._panel.style.top = `${buttonTop + buttonRect.height + panelGap}px`;\n        this._panel.style.left = `${buttonLeft}px`;\n        break;\n      case 'top-right':\n        this._panel.style.top = `${buttonTop + buttonRect.height + panelGap}px`;\n        this._panel.style.right = `${buttonRight}px`;\n        break;\n      case 'bottom-left':\n        this._panel.style.bottom = `${buttonBottom + buttonRect.height + panelGap}px`;\n        this._panel.style.left = `${buttonLeft}px`;\n        break;\n      case 'bottom-right':\n        this._panel.style.bottom = `${buttonBottom + buttonRect.height + panelGap}px`;\n        this._panel.style.right = `${buttonRight}px`;\n        break;\n    }\n  }\n\n  getPanelElement(): HTMLElement | null {\n    return this._panel ?? null;\n  }\n}\n"],"names":["_a","_b","_d","_c","_f","_e"],"mappings":"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"}