{"version":3,"sources":["../../src/use-element-by-point/index.ts"],"sourcesContent":["import { useIntervalFn } from '../use-interval-fn'\nimport { useLatest } from '../use-latest'\nimport { useSafeState } from '../use-safe-state'\nimport { useSupported } from '../use-supported'\nimport { noNullish } from '../utils/basic'\n\nimport type { UseIntervalFnInterval } from '../use-interval-fn'\nimport type { Pausable } from '../use-pausable'\nimport type { Position } from '../utils/basic'\n\nexport interface UseElementByPointReturns<E extends Element | Element[]> extends Pausable {\n  /**\n   * Whether the browser supports the API\n   */\n  isSupported: boolean\n  /**\n   * The element at the specified position\n   */\n  element: E | null\n}\n\nexport interface UseElementByPointOptions<M extends boolean = false> extends Position {\n  /**\n   * Whether to return multiple elements\n   *\n   * @defaultValue false\n   */\n  multiple?: M\n  /**\n   * Whether to execute immediately\n   *\n   * @defaultValue true\n   */\n  immediate?: boolean\n  /**\n   * The interval to execute\n   *\n   * @defaultValue 'requestAnimationFrame'\n   */\n  interval?: UseIntervalFnInterval\n}\n\n/**\n * A React Hook that returns the element at a given point.\n */\nexport function useElementByPoint<\n  M extends boolean = false,\n  E extends Element | Element[] = M extends true ? Element[] : Element,\n>(options: UseElementByPointOptions<M>): UseElementByPointReturns<E> {\n  const { x, y, multiple = false, interval = 'requestAnimationFrame', immediate = true } = options\n  const [element, setElement] = useSafeState<E | null>(null)\n  const latest = useLatest({ x, y, multiple })\n\n  // https://developer.mozilla.org/en-US/docs/Web/API/Document/elementFromPoint#browser_compatibility\n  const isSupported = useSupported(() => (multiple ? 'elementsFromPoint' : 'elementFromPoint') in document, [multiple])\n\n  const controls = useIntervalFn(\n    () => {\n      if (!isSupported) return\n      const { x, y, multiple } = latest.current\n      const result = document?.[multiple ? 'elementsFromPoint' : 'elementFromPoint'](x, y)\n      const element = Array.isArray(result) ? result.filter(noNullish) : result\n      setElement((element ?? (multiple ? [] : null)) as E | null)\n    },\n    interval,\n    { immediate },\n  )\n\n  return {\n    isSupported,\n    element,\n    ...controls,\n  }\n}\n"],"names":["useElementByPoint","options","x","y","multiple","interval","immediate","useSafeState","element","setElement","latest","useLatest","isSupported","useSupported","document","controls","useIntervalFn","current","result","Array","isArray","filter","noNullish"],"mappings":";;;;+BA6CgBA;;;eAAAA;;;6BA7Cc;yBACJ;4BACG;4BACA;qBACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAyCnB,SAASA,kBAGdC,OAAoC;IACpC,IAAQC,IAAiFD,QAAjFC,GAAGC,IAA8EF,QAA9EE,uBAA8EF,QAA3EG,UAAAA,0CAAW,+CAAgEH,QAAzDI,UAAAA,0CAAW,kEAA8CJ,QAArBK,WAAAA,4CAAY;IAChF,IAA8BC,iCAAAA,IAAAA,0BAAY,EAAW,WAA9CC,UAAuBD,kBAAdE,aAAcF;IAC9B,IAAMG,SAASC,IAAAA,oBAAS,EAAC;QAAET,GAAAA;QAAGC,GAAAA;QAAGC,UAAAA;IAAS;IAE1C,mGAAmG;IACnG,IAAMQ,cAAcC,IAAAA,0BAAY,EAAC;eAAM,AAACT,CAAAA,WAAW,sBAAsB,kBAAiB,KAAMU;OAAU;QAACV;KAAS;IAEpH,IAAMW,WAAWC,IAAAA,4BAAa,EAC5B;YAGiBF;QAFf,IAAI,CAACF,aAAa;QAClB,IAA2BF,kBAAAA,OAAOO,OAAO,EAAjCf,IAAmBQ,gBAAnBR,GAAGC,IAAgBO,gBAAhBP,GAAGC,WAAaM,gBAAbN;QACd,IAAMc,UAASJ,YAAAA,sBAAAA,gCAAAA,SAAU,CAACV,WAAW,sBAAsB,mBAAmB,CAACF,GAAGC;QAClF,IAAMK,UAAUW,MAAMC,OAAO,CAACF,UAAUA,OAAOG,MAAM,CAACC,gBAAS,IAAIJ;QACnET,WAAYD,oBAAAA,qBAAAA,UAAYJ,WAAW,EAAE,GAAG;IAC1C,GACAC,UACA;QAAEC,WAAAA;IAAU;IAGd,OAAO;QACLM,aAAAA;QACAJ,SAAAA;OACGO;AAEP"}