{"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;;;;;;;;;;CAUC;;;;;;;;;;;;;;;;;;AA0FM,SAAS,0CAAmB,KAAiC,EAAE,KAAwB;IAC5F,IAAI,YACF,QAAQ,iBACR,aAAa,UACb,MAAM,yBACN,wBAAwB,4BACxB,sBAAsB,OACvB,GAAG;IAEJ,IAAI,eAAe,CAAA,GAAA,+BAAI;IACvB,IAAI,UAAU,CAAA,GAAA,mBAAK,EAA6C;IAChE,IAAI,4BAA4B,CAAA,GAAA,mBAAK,EAAE;IACvC,IAAI,yBAAyB,CAAA,GAAA,mBAAK,EAAiB;IAEnD,2HAA2H;IAC3H,uCAAuC;IACvC,IAAI,uBAAuB,CAAA,GAAA,gDAAqB,QAAQ,aAAc,CAAA,CAAA,GAAA,+BAAI,OAAO,CAAA,GAAA,mCAAQ,GAAE;IAC3F,IAAI,CAAC,uBAAuB,yBAAyB,GAAG,CAAA,GAAA,qBAAO,EAAE,CAAC,wBAAwB,CAAC;IAC3F,6IAA6I;IAC7I,iEAAiE;IACjE,IAAI,CAAC,eAAe,iBAAiB,GAAG,CAAA,GAAA,qBAAO,EAAE;IAEjD,CAAA,GAAA,sBAAQ,EAAE;QACR,OAAO,IAAM,aAAa,QAAQ,OAAO;IAC3C,GAAG,EAAE;IAEL,IAAI,8BAA8B,CAAA,GAAA,wCAAa,EAAE,CAAC;QAChD,yEAAyE;QACzE,uFAAuF;QACvF,IAAI,CAAC,EAAE,SAAS,IAAI,yBAAyB,SAAS,OAAO,IAAI,CAAA,GAAA,0CAAe,EAAE,CAAA,GAAA,0CAAe,EAAE,SAAS,OAAO,OAAO,SAAS,OAAO,IAAI,CAAA,GAAA,wCAAa,QAAQ,SACjK,SAAS,OAAO,CAAC,KAAK;QAGxB,IAAI,SAAS,CAAA,GAAA,wCAAa,EAAE;QAC5B,IAAI,EAAE,SAAS,IAAI,CAAC,UAAU,uBAAuB,OAAO,KAAK,OAAO,EAAE,EACxE;QAGF,aAAa,QAAQ,OAAO;QAC5B,IAAI,WAAW,cAAc,OAAO;YAClC,IAAI,0BAA0B,OAAO,EAAE;gBACrC,uBAAuB,OAAO,GAAG,OAAO,EAAE;gBAC1C,QAAQ,OAAO,GAAG,WAAW;oBAC3B,MAAM,gBAAgB,CAAC,OAAO,EAAE;gBAClC,GAAG;YACL,OAAO;gBACL,uBAAuB,OAAO,GAAG,OAAO,EAAE;gBAC1C,MAAM,gBAAgB,CAAC,OAAO,EAAE;YAClC;eACK,IAAI,uBAAuB,OAAO,IAAI,CAAC,SAAS,cAAc,CAAC,uBAAuB,OAAO,GAAG;YACrG,0HAA0H;YAC1H,sEAAsE;YACtE,0HAA0H;YAC1H,gFAAgF;YAChF,uBAAuB,OAAO,GAAG;YACjC,MAAM,gBAAgB,CAAC;QACzB;QAEA,0BAA0B,OAAO,GAAG;IACtC;IAEA,IAAI,CAAC,gBAAgB,kBAAkB,GAAG,CAAA,GAAA,qBAAO,EAAsB;IACvE,IAAI,cAAc,CAAA,GAAA,wBAAU,EAAE,CAAC;QAC7B,kBAAkB;QAClB,IAAI,QAAQ,MAAM;YAChB,sGAAsG;YACtG,wHAAwH;YACxH,sGAAsG;YACtG,IAAI,KAAK,YAAY,CAAC,eAAe,MACnC,yBAAyB;YAE3B,iBAAiB;QACnB,OACE,iBAAiB;IAErB,GAAG,EAAE;IACL,CAAA,GAAA,yCAAc,EAAE;QACd,IAAI,kBAAkB,MACpB,gIAAgI;QAChI,kGAAkG;QAClG,eAAe,gBAAgB,CAAC,WAAW;QAE7C,OAAO;YACL,gBAAgB,oBAAoB,WAAW;QACjD;IACF,GAAG;QAAC;KAAe;IAEnB,6HAA6H;IAC7H,IAAI,sBAAsB,CAAA,GAAA,sCAAW,EAAE,CAAA,GAAA,oBAAM,EAAE,IAAM,CAAA,GAAA,mCAAQ,EAAE,eAAe,cAAc;QAAC;QAAe;KAAY;IAExH,IAAI,iBAAiB,CAAA,GAAA,wBAAU,EAAE;QAC/B,0BAA0B,OAAO,GAAG;QACpC,cAAc,OAAO,EAAE,cACrB,IAAI,YAAY,CAAA,GAAA,qCAAU,GAAG;YAC3B,YAAY;YACZ,SAAS;YACT,QAAQ;gBACN,eAAe;YACjB;QACF;IAEJ,GAAG;QAAC;KAAc;IAElB,IAAI,oBAAoB,CAAA,GAAA,wBAAU,EAAE,CAAC;QACnC,CAAA,GAAA,0CAAe,EAAE,CAAA,GAAA,0CAAe;QAChC,uBAAuB,OAAO,GAAG;QACjC,MAAM,gBAAgB,CAAC;QACvB,IAAI,kBAAkB,IAAI,YAAY,CAAA,GAAA,2CAAgB,GAAG;YACvD,YAAY;YACZ,SAAS;YACT,QAAQ;+BACN;YACF;QACF;QACA,aAAa,QAAQ,OAAO;QAC5B,0BAA0B,OAAO,GAAG;QACpC,cAAc,OAAO,EAAE,cAAc;IACvC,GAAG;QAAC;QAAe;KAAM;IAEzB,IAAI,gBAAgB,CAAA,GAAA,mBAAK,EAAE;IAC3B,CAAA,GAAA,kCAAO,EAAE,UAAU,SAAS,CAAA;QAC1B,IAAI,aAAC,SAAS,EAAC,GAAG;QAClB,cAAc,OAAO,GAAG;IAC1B;IAEA,IAAI,WAAW,CAAC;QACd,0IAA0I;QAC1I,mEAAmE;QACnE,IAAI,cAAc,OAAO,KAAK,gBAAgB,CAAC,uBAC7C;aACK,IAAI,cAAc,OAAO,IAAK,CAAA,cAAc,OAAO,CAAC,QAAQ,CAAC,aAAa,cAAc,OAAO,CAAC,QAAQ,CAAC,aAAa,cAAc,OAAO,CAAC,QAAQ,CAAC,UAAS,GAAI;YACvK,kBAAkB;YAElB,sGAAsG;YACtG,2EAA2E;YAC3E,IAAI,CAAA,GAAA,oDAAyB,EAAE,cAAc,SAAS,OAAO,EAC3D,CAAA,GAAA,8CAAmB,EAAE,SAAS,OAAO,EAAG;QAE5C;QAEA,MAAM,aAAa,CAAC;IACtB;IAEA,IAAI,gBAAgB,CAAA,GAAA,mBAAK,EAAkB;IAC3C,4CAA4C;IAC5C,IAAI,YAAY,CAAC;QACf,cAAc,OAAO,GAAG,CAAA,GAAA,wCAAa,EAAE;QACvC,IAAI,EAAE,WAAW,CAAC,WAAW,EAC3B;QAGF,IAAI,gBAAgB,uBAAuB,OAAO;QAClD,IAAI,kBAAkB,QAAQ,CAAA,GAAA,0CAAe,EAAE,SAAS,OAAO,EAAE,cAAc,CAAC,kBAAkB,MAAM;YACtG,yGAAyG;YACzG,mIAAmI;YACnI,iHAAiH;YACjH,uBAAuB,OAAO,GAAG;YACjC,gBAAgB;QAClB;QAEA,OAAQ,EAAE,GAAG;YACX,KAAK;gBACH,IAAI,CAAA,GAAA,0CAAe,EAAE,IACnB;gBAEF;YACF,KAAK;gBACH,iHAAiH;gBACjH,iHAAiH;gBACjH,2BAA2B;gBAC3B,IAAI,EAAE,kBAAkB,IACtB;gBAEF;YACF,KAAK;gBACH,oDAAoD;gBACpD;YACF,KAAK;gBACH,4JAA4J;gBAC5J,4FAA4F;gBAC5F,IAAI,yBAAyB,GAC3B,EAAE,mBAAmB;gBAEvB;YACF,KAAK;YACL,KAAK;YACL,KAAK;YACL,KAAK;YACL,KAAK;YACL,KAAK;YACL,KAAK;YACL,KAAK;gBAAa;oBAChB,IAAI,AAAC,CAAA,EAAE,GAAG,KAAK,UAAU,EAAE,GAAG,KAAK,KAAI,KAAM,iBAAiB,QAAQ,EAAE,QAAQ,EAC9E;oBAGF,uFAAuF;oBACvF,8FAA8F;oBAC9F,iGAAiG;oBACjG,4FAA4F;oBAC5F,IAAI,AAAC,CAAA,EAAE,GAAG,KAAK,gBAAgB,EAAE,GAAG,KAAK,WAAU,KAAM,MAAM,UAAU,CAAC,MAAM,GAAG,GAAG;wBACpF,IAAI,iBAAiB,MAAM;4BACzB,IAAI,CAAC,EAAE,oBAAoB,IACzB,EAAE,eAAe;4BAEnB;wBACF;wBAEA;oBACF;oBAEA,8DAA8D;oBAC9D,EAAE,cAAc;oBAChB,iDAAiD;oBACjD,IAAI,kBAAkB,IAAI,YAAY,CAAA,GAAA,qCAAU,GAAG;wBACjD,YAAY;wBACZ,SAAS;oBACX;oBAEA,cAAc,OAAO,EAAE,cAAc;oBACrC;gBACF;QACF;QAEA,8IAA8I;QAC9I,+IAA+I;QAC/I,qJAAqJ;QACrJ,cAAc;QACd,IAAI,CAAC,EAAE,oBAAoB,IACzB,EAAE,eAAe;QAGnB,IAAI,6BAA6B;QACjC,IAAI,cAAc,OAAO,KAAK;YAC5B,IAAI,iBAAiB,MACnB,6BAA6B,cAAc,OAAO,EAAE,cAClD,IAAI,cAAc,EAAE,WAAW,CAAC,IAAI,EAAE,EAAE,WAAW,MAChD;iBACA;gBACL,IAAI,OAAO,SAAS,cAAc,CAAC;gBACnC,IAAI,MACF,6BAA6B,MAAM,cACjC,IAAI,cAAc,EAAE,WAAW,CAAC,IAAI,EAAE,EAAE,WAAW,MAChD;YAET;;QAGF,IAAI,4BACF,OAAQ,EAAE,GAAG;YACX,KAAK;YACL,KAAK;gBACH,0HAA0H;gBAC1H,+DAA+D;gBAC/D;gBACA;YAEF,KAAK;gBACH,2DAA2D;gBAC3D,IAAI,iBAAiB,MAAM;oBACzB,IAAI,OAAO,SAAS,cAAc,CAAC;oBACnC,MAAM,cAAc,IAAI,aAAa,SAAS,EAAE,WAAW;gBAC7D;gBACA;QACJ;aAEA,6HAA6H;QAC7H,EAAE,cAAc;IAEpB;IAEA,IAAI,iBAAiB,CAAA,GAAA,wCAAa,EAAE,CAAC;QACnC,+EAA+E;QAC/E,mGAAmG;QACnG,mFAAmF;QACnF,IAAI,CAAA,GAAA,wCAAa,EAAE,OAAO,cAAc,OAAO,EAAE;YAC/C,EAAE,wBAAwB;YAC1B,IAAI,gBAAgB,uBAAuB,OAAO;YAClD,IAAI,iBAAiB,MACnB,cAAc,OAAO,EAAE,cACrB,IAAI,cAAc,EAAE,IAAI,EAAE;iBAEvB;gBACL,IAAI,OAAO,SAAS,cAAc,CAAC;gBACnC,MAAM,cACJ,IAAI,cAAc,EAAE,IAAI,EAAE;YAE9B;QACF;IACF;IAEA,CAAA,GAAA,sBAAQ,EAAE;QACR,SAAS,gBAAgB,CAAC,SAAS,gBAAgB;QACnD,OAAO;YACL,SAAS,mBAAmB,CAAC,SAAS,gBAAgB;QACxD;IACF,GAAG,EAAE;IAEL,IAAI,kBAAkB,CAAA,GAAA,qDAA0B,EAAE,CAAA,GAAA,mDAAW,GAAG;IAChE,IAAI,kBAAkB,CAAA,GAAA,mCAAQ,EAAE;QAC9B,IAAI;QACJ,cAAc,gBAAgB,MAAM,CAAC;IACvC;IAEA,IAAI,WAAW,CAAA,GAAA,wBAAU,EAAE,CAAC,eAAuB;QACjD,IAAI,QACF,OAAO,OAAO,eAAe,MAAM,UAAU,EAAE;QAGjD,OAAO;IACT,GAAG;QAAC,MAAM,UAAU;QAAE;KAAO;IAE7B,iHAAiH;IACjH,qGAAqG;IACrG,IAAI,SAAS,CAAC;QACZ,IAAI,CAAC,EAAE,SAAS,EACd;QAGF,IAAI,kBAAkB,uBAAuB,OAAO,GAAG,SAAS,cAAc,CAAC,uBAAuB,OAAO,IAAI;QACjH,IAAI,iBACF,CAAA,GAAA,6CAAkB,EAAE,iBAAiB,EAAE,aAAa;IAExD;IAEA,IAAI,UAAU,CAAC;QACb,IAAI,CAAC,EAAE,SAAS,EACd;QAGF,IAAI,iBAAiB,uBAAuB,OAAO,GAAG,SAAS,cAAc,CAAC,uBAAuB,OAAO,IAAI;QAChH,IAAI,gBAAgB;YAClB,IAAI,SAAS,CAAA,GAAA,wCAAa,EAAE;YAC5B,eAAe;gBACb,kKAAkK;gBAClK,CAAA,GAAA,6CAAkB,EAAE,QAAQ,cAAc,OAAO;gBACjD,CAAA,GAAA,8CAAmB,EAAE,cAAc,OAAO,EAAG;YAC/C;QACF;IACF;IAEA,2FAA2F;IAC3F,oFAAoF;IACpF,+EAA+E;IAC/E,wFAAwF;IACxF,IAAI,gBAAgB,CAAC;QACnB,IAAI,EAAE,MAAM,KAAK,KAAK,EAAE,WAAW,KAAK,WAAW,uBAAuB,OAAO,IAAI,QAAQ,SAAS,OAAO,IAAI,MAC/G;QAGF,IAAI,CAAA,GAAA,wCAAa,EAAE,OAAO,SAAS,OAAO,EACxC;IAEJ;IAEA,uGAAuG;IACvG,uDAAuD;IACvD,IAAI,aAAa;QACf,OAAO,MAAM,UAAU;kBACvB;IACF;IAEA,IAAI,oBAAoB;mBACtB;QACA,yBAAyB,MAAM,aAAa,IAAI;gBAChD;iBACA;uBACA;IACF;IAEA,IAAI,eACF,aAAa;QACX,GAAG,UAAU;QACb,GAAI,yBAAyB,iBAAiB;QAC9C,cAAc;QACd,iBAAiB;QACjB,mFAAmF;QACnF,qBAAqB;QACrB,qGAAqG;QACrG,aAAa;QACb,gEAAgE;QAChE,YAAY;QACZ,cAAc;IAChB;IAGF,OAAO;oBACL;QACA,iBAAiB,CAAA,GAAA,oCAAS,EAAE,iBAAiB;mCAC3C;YACA,mBAAmB;QACrB;QACA,eAAe;QACf,QAAQ,UAAU,OAAO,WAAW;IACtC;AACF","sources":["packages/react-aria/src/autocomplete/useAutocomplete.ts"],"sourcesContent":["/*\n * Copyright 2024 Adobe. All rights reserved.\n * This file is licensed to you under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License. You may obtain a copy\n * of the License at http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software distributed under\n * the License is distributed on an \"AS IS\" BASIS, WITHOUT WARRANTIES OR REPRESENTATIONS\n * OF ANY KIND, either express or implied. See the License for the specific language\n * governing permissions and limitations under the License.\n */\n\nimport {AriaLabelingProps, BaseEvent, DOMProps, FocusableElement, FocusEvents, KeyboardEvents, Node, RefObject, ValueBase} from '@react-types/shared';\nimport {AriaTextFieldProps} from '../textfield/useTextField';\nimport {AutocompleteProps, AutocompleteState} from 'react-stately/private/autocomplete/useAutocompleteState';\nimport {CLEAR_FOCUS_EVENT, FOCUS_EVENT} from '../utils/constants';\nimport {\n  dispatchVirtualBlur,\n  dispatchVirtualFocus,\n  getVirtuallyFocusedElement,\n  moveVirtualFocus\n} from '../focus/virtualFocus';\nimport {getActiveElement, getEventTarget} from '../utils/shadowdom/DOMFunctions';\nimport {getInteractionModality, getPointerType} from '../interactions/useFocusVisible';\nimport {getOwnerDocument} from '../utils/domHelpers';\nimport intlMessages from '../../intl/autocomplete/*.json';\nimport {isAndroid, isIOS} from '../utils/platform';\nimport {isCtrlKeyPressed} from '../utils/keyboard';\nimport {mergeProps} from '../utils/mergeProps';\nimport {mergeRefs} from '../utils/mergeRefs';\nimport {FocusEvent as ReactFocusEvent, KeyboardEvent as ReactKeyboardEvent, PointerEvent as ReactPointerEvent, useCallback, useEffect, useMemo, useRef, useState} from 'react';\nimport {useEffectEvent} from '../utils/useEffectEvent';\nimport {useEvent} from '../utils/useEvent';\n\nimport {useId} from '../utils/useId';\n\nimport {useLabels} from '../utils/useLabels';\n// @ts-ignore\nimport {useLayoutEffect} from '../utils/useLayoutEffect';\nimport {useLocalizedStringFormatter} from '../i18n/useLocalizedStringFormatter';\nimport {useObjectRef} from '../utils/useObjectRef';\n\nexport interface CollectionOptions extends DOMProps, AriaLabelingProps {\n  /** Whether the collection items should use virtual focus instead of being focused directly. */\n  shouldUseVirtualFocus: boolean,\n  /** Whether typeahead is disabled. */\n  disallowTypeAhead: boolean\n}\n\nexport interface InputProps<T = FocusableElement> extends DOMProps,\n  FocusEvents<T>,\n  KeyboardEvents,\n  Pick<ValueBase<string>, 'onChange' | 'value'>,\n  Pick<AriaTextFieldProps, 'enterKeyHint' | 'aria-controls' | 'aria-autocomplete' | 'aria-activedescendant' | 'spellCheck' | 'autoCorrect' | 'autoComplete'> {}\n\nexport interface AriaAutocompleteProps<T> extends AutocompleteProps {\n  /**\n   * An optional filter function used to determine if a option should be included in the autocomplete list.\n   * Include this if the items you are providing to your wrapped collection aren't filtered by default.\n   */\n  filter?: (textValue: string, inputValue: string, node: Node<T>) => boolean,\n\n  /**\n   * Whether or not to focus the first item in the collection after a filter is performed. Note this is only applicable\n   * if virtual focus behavior is not turned off via `disableVirtualFocus`.\n   * @default false\n   */\n  disableAutoFocusFirst?: boolean,\n\n  /**\n   * Whether the autocomplete should disable virtual focus, instead making the wrapped collection directly tabbable.\n   * @default false\n   */\n  disableVirtualFocus?: boolean\n}\n\nexport interface AriaAutocompleteOptions<T> extends Omit<AriaAutocompleteProps<T>, 'children'> {\n  /** The ref for the wrapped collection element. */\n  inputRef: RefObject<HTMLInputElement | null>,\n  /** The ref for the wrapped collection element. */\n  collectionRef: RefObject<HTMLElement | null>\n}\n\nexport interface AutocompleteAria<T> {\n  /** Props for the autocomplete input element. These should be passed to the input's aria hooks (e.g. useTextField/useSearchField/etc) respectively. */\n  inputProps: InputProps,\n  /** Props for the collection, to be passed to collection's respective aria hook (e.g. useMenu). */\n  collectionProps: CollectionOptions,\n  /** Ref to attach to the wrapped collection. */\n  collectionRef: RefObject<HTMLElement | null>,\n  /** A filter function that returns if the provided collection node should be filtered out of the collection. */\n  filter?: (nodeTextValue: string, node: Node<T>) => boolean\n}\n\n/**\n * Provides the behavior and accessibility implementation for an autocomplete component.\n * An autocomplete combines a text input with a collection, allowing users to filter the collection's contents match a query.\n * @param props - Props for the autocomplete.\n * @param state - State for the autocomplete, as returned by `useAutocompleteState`.\n */\nexport function useAutocomplete<T>(props: AriaAutocompleteOptions<T>, state: AutocompleteState): AutocompleteAria<T> {\n  let {\n    inputRef,\n    collectionRef,\n    filter,\n    disableAutoFocusFirst = false,\n    disableVirtualFocus = false\n  } = props;\n\n  let collectionId = useId();\n  let timeout = useRef<ReturnType<typeof setTimeout> | undefined>(undefined);\n  let delayNextActiveDescendant = useRef(false);\n  let queuedActiveDescendant = useRef<string | null>(null);\n\n  // For mobile screen readers, we don't want virtual focus, instead opting to disable FocusScope's restoreFocus and manually\n  // moving focus back to the subtriggers\n  let isMobileScreenReader = getInteractionModality() === 'virtual' && (isIOS() || isAndroid());\n  let [shouldUseVirtualFocus, setShouldUseVirtualFocus] = useState(!isMobileScreenReader && !disableVirtualFocus);\n  // Tracks if a collection has been connected to the autocomplete. If false, we don't want to add various attributes to the autocomplete input\n  // since it isn't attached to a filterable collection (e.g. Tabs)\n  let [hasCollection, setHasCollection] = useState(false);\n\n  useEffect(() => {\n    return () => clearTimeout(timeout.current);\n  }, []);\n\n  let updateActiveDescendantEvent = useEffectEvent((e: Event) => {\n    // Ensure input is focused if the user clicks on the collection directly.\n    // don't trigger on touch so that mobile keyboard doesnt appear when tapping on options\n    if (!e.isTrusted && shouldUseVirtualFocus && inputRef.current && getActiveElement(getOwnerDocument(inputRef.current)) !== inputRef.current && getPointerType() !== 'touch') {\n      inputRef.current.focus();\n    }\n\n    let target = getEventTarget(e) as Element | null;\n    if (e.isTrusted || !target || queuedActiveDescendant.current === target.id) {\n      return;\n    }\n\n    clearTimeout(timeout.current);\n    if (target !== collectionRef.current) {\n      if (delayNextActiveDescendant.current) {\n        queuedActiveDescendant.current = target.id;\n        timeout.current = setTimeout(() => {\n          state.setFocusedNodeId(target.id);\n        }, 500);\n      } else {\n        queuedActiveDescendant.current = target.id;\n        state.setFocusedNodeId(target.id);\n      }\n    } else if (queuedActiveDescendant.current && !document.getElementById(queuedActiveDescendant.current)) {\n      // If we recieve a focus event refocusing the collection, either we have newly refocused the input and are waiting for the\n      // wrapped collection to refocus the previously focused node if any OR\n      // we are in a state where we've filtered to such a point that there aren't any matching items in the collection to focus.\n      // In this case we want to clear tracked item if any and clear active descendant\n      queuedActiveDescendant.current = null;\n      state.setFocusedNodeId(null);\n    }\n\n    delayNextActiveDescendant.current = false;\n  });\n\n  let [collectionNode, setCollectionNode] = useState<HTMLElement | null>(null);\n  let callbackRef = useCallback((node) => {\n    setCollectionNode(node);\n    if (node != null) {\n      // If useSelectableCollection isn't passed shouldUseVirtualFocus even when useAutocomplete provides it\n      // that means the collection doesn't support it (e.g. Table). If that is the case, we need to disable it here regardless\n      // of what the user's provided so that the input doesn't recieve the onKeyDown and autocomplete props.\n      if (node.getAttribute('tabindex') != null) {\n        setShouldUseVirtualFocus(false);\n      }\n      setHasCollection(true);\n    } else {\n      setHasCollection(false);\n    }\n  }, []);\n  useLayoutEffect(() => {\n    if (collectionNode != null) {\n      // When typing forward, we want to delay the setting of active descendant to not interrupt the native screen reader announcement\n      // of the letter you just typed. If we recieve another focus event then we clear the queued update\n      collectionNode.addEventListener('focusin', updateActiveDescendantEvent);\n    }\n    return () => {\n      collectionNode?.removeEventListener('focusin', updateActiveDescendantEvent);\n    };\n  }, [collectionNode]);\n\n  // Make sure to memo so that React doesn't keep registering a new event listeners on every rerender of the wrapped collection\n  let mergedCollectionRef = useObjectRef(useMemo(() => mergeRefs(collectionRef, callbackRef), [collectionRef, callbackRef]));\n\n  let focusFirstItem = useCallback(() => {\n    delayNextActiveDescendant.current = true;\n    collectionRef.current?.dispatchEvent(\n      new CustomEvent(FOCUS_EVENT, {\n        cancelable: true,\n        bubbles: true,\n        detail: {\n          focusStrategy: 'first'\n        }\n      })\n    );\n  }, [collectionRef]);\n\n  let clearVirtualFocus = useCallback((clearFocusKey?: boolean) => {\n    moveVirtualFocus(getActiveElement());\n    queuedActiveDescendant.current = null;\n    state.setFocusedNodeId(null);\n    let clearFocusEvent = new CustomEvent(CLEAR_FOCUS_EVENT, {\n      cancelable: true,\n      bubbles: true,\n      detail: {\n        clearFocusKey\n      }\n    });\n    clearTimeout(timeout.current);\n    delayNextActiveDescendant.current = false;\n    collectionRef.current?.dispatchEvent(clearFocusEvent);\n  }, [collectionRef, state]);\n\n  let lastInputType = useRef('');\n  useEvent(inputRef, 'input', e => {\n    let {inputType} = e as InputEvent;\n    lastInputType.current = inputType;\n  });\n\n  let onChange = (value: string) => {\n    // Tell wrapped collection to focus the first element in the list when typing forward and to clear focused key when modifying the text via\n    // copy paste/backspacing/undo/redo for screen reader announcements\n    if (lastInputType.current === 'insertText' && !disableAutoFocusFirst) {\n      focusFirstItem();\n    } else if (lastInputType.current && (lastInputType.current.includes('insert') || lastInputType.current.includes('delete') || lastInputType.current.includes('history'))) {\n      clearVirtualFocus(true);\n\n      // If onChange was triggered before the timeout actually updated the activedescendant, we need to fire\n      // our own dispatchVirtualFocus so focusVisible gets reapplied on the input\n      if (getVirtuallyFocusedElement(document) === inputRef.current) {\n        dispatchVirtualFocus(inputRef.current!, null);\n      }\n    }\n\n    state.setInputValue(value);\n  };\n\n  let keyDownTarget = useRef<Element | null>(null);\n  // For textfield specific keydown operations\n  let onKeyDown = (e: BaseEvent<ReactKeyboardEvent<any>>) => {\n    keyDownTarget.current = getEventTarget(e) as Element;\n    if (e.nativeEvent.isComposing) {\n      return;\n    }\n\n    let focusedNodeId = queuedActiveDescendant.current;\n    if (focusedNodeId !== null && getOwnerDocument(inputRef.current).getElementById(focusedNodeId) == null) {\n      // if the focused id doesn't exist in document, then we need to clear the tracked focused node, otherwise\n      // we will be attempting to fire key events on a non-existing node instead of trying to focus the newly swapped wrapped collection.\n      // This can happen if you are swapping out the Autocomplete wrapped collection component like in the docs search.\n      queuedActiveDescendant.current = null;\n      focusedNodeId = null;\n    }\n\n    switch (e.key) {\n      case 'a':\n        if (isCtrlKeyPressed(e)) {\n          return;\n        }\n        break;\n      case 'Escape':\n        // Early return for Escape here so it doesn't leak the Escape event from the simulated collection event below and\n        // close the dialog prematurely. Ideally that should be up to the discretion of the input element hence the check\n        // for isPropagationStopped\n        if (e.isDefaultPrevented()) {\n          return;\n        }\n        break;\n      case ' ':\n        // Space shouldn't trigger onAction so early return.\n        return;\n      case 'Tab':\n        // Don't propogate Tab down to the collection, otherwise we will try to focus the collection via useSelectableCollection's Tab handler (aka shift tab logic)\n        // We want FocusScope to handle Tab if one exists (aka sub dialog), so special casepropogate\n        if ('continuePropagation' in e) {\n          e.continuePropagation();\n        }\n        return;\n      case 'Home':\n      case 'End':\n      case 'PageDown':\n      case 'PageUp':\n      case 'ArrowUp':\n      case 'ArrowDown':\n      case 'ArrowRight':\n      case 'ArrowLeft': {\n        if ((e.key === 'Home' || e.key === 'End') && focusedNodeId == null && e.shiftKey) {\n          return;\n        }\n\n        // If there is text within the input field, we'll want continue propagating events down\n        // to the wrapped collection if there is a focused node so that a user can continue moving the\n        // virtual focus. However, if the user doesn't have a focus in the collection, just move the text\n        // cursor instead. They can move focus down into the collection via down/up arrow if need be\n        if ((e.key === 'ArrowRight' || e.key === 'ArrowLeft') && state.inputValue.length > 0) {\n          if (focusedNodeId == null) {\n            if (!e.isPropagationStopped()) {\n              e.stopPropagation();\n            }\n            return;\n          }\n\n          break;\n        }\n\n        // Prevent these keys from moving the text cursor in the input\n        e.preventDefault();\n        // Move virtual focus into the wrapped collection\n        let focusCollection = new CustomEvent(FOCUS_EVENT, {\n          cancelable: true,\n          bubbles: true\n        });\n\n        collectionRef.current?.dispatchEvent(focusCollection);\n        break;\n      }\n    }\n\n    // Emulate the keyboard events that happen in the input field in the wrapped collection. This is for triggering things like onAction via Enter\n    // or moving focus from one item to another. Stop propagation on the input event if it isn't already stopped so it doesn't leak out. For events\n    // like ESC, the dispatched event below will bubble out of the collection and be stopped if handled by useSelectableCollection, otherwise will bubble\n    // as expected\n    if (!e.isPropagationStopped()) {\n      e.stopPropagation();\n    }\n\n    let shouldPerformDefaultAction = true;\n    if (collectionRef.current !== null) {\n      if (focusedNodeId == null) {\n        shouldPerformDefaultAction = collectionRef.current?.dispatchEvent(\n          new KeyboardEvent(e.nativeEvent.type, e.nativeEvent)\n        ) || false;\n      } else {\n        let item = document.getElementById(focusedNodeId);\n        if (item) {\n          shouldPerformDefaultAction = item?.dispatchEvent(\n            new KeyboardEvent(e.nativeEvent.type, e.nativeEvent)\n          ) || false;\n        }\n      }\n    }\n\n    if (shouldPerformDefaultAction) {\n      switch (e.key) {\n        case 'ArrowLeft':\n        case 'ArrowRight': {\n          // Clear the activedescendant so NVDA announcements aren't interrupted but retain the focused key in the collection so the\n          // user's keyboard navigation restarts from where they left off\n          clearVirtualFocus();\n          break;\n        }\n        case 'Enter':\n          // Trigger click action on item when Enter key was pressed.\n          if (focusedNodeId != null) {\n            let item = document.getElementById(focusedNodeId);\n            item?.dispatchEvent(new PointerEvent('click', e.nativeEvent));\n          }\n          break;\n      }\n    } else {\n      // TODO: check if we can do this, want to stop textArea from using its default Enter behavior so items are properly triggered\n      e.preventDefault();\n    }\n  };\n\n  let onKeyUpCapture = useEffectEvent((e) => {\n    // Dispatch simulated key up events for things like triggering links in listbox\n    // Make sure to stop the propagation of the input keyup event so that the simulated keyup/down pair\n    // is detected by usePress instead of the original keyup originating from the input\n    if (getEventTarget(e) === keyDownTarget.current) {\n      e.stopImmediatePropagation();\n      let focusedNodeId = queuedActiveDescendant.current;\n      if (focusedNodeId == null) {\n        collectionRef.current?.dispatchEvent(\n          new KeyboardEvent(e.type, e)\n        );\n      } else {\n        let item = document.getElementById(focusedNodeId);\n        item?.dispatchEvent(\n          new KeyboardEvent(e.type, e)\n        );\n      }\n    }\n  });\n\n  useEffect(() => {\n    document.addEventListener('keyup', onKeyUpCapture, true);\n    return () => {\n      document.removeEventListener('keyup', onKeyUpCapture, true);\n    };\n  }, []);\n\n  let stringFormatter = useLocalizedStringFormatter(intlMessages, '@react-aria/autocomplete');\n  let collectionProps = useLabels({\n    id: collectionId,\n    'aria-label': stringFormatter.format('collectionLabel')\n  });\n\n  let filterFn = useCallback((nodeTextValue: string, node: Node<T>) => {\n    if (filter) {\n      return filter(nodeTextValue, state.inputValue, node);\n    }\n\n    return true;\n  }, [state.inputValue, filter]);\n\n  // Be sure to clear/restore the virtual + collection focus when blurring/refocusing the field so we only show the\n  // focus ring on the virtually focused collection when are actually interacting with the Autocomplete\n  let onBlur = (e: ReactFocusEvent) => {\n    if (!e.isTrusted) {\n      return;\n    }\n\n    let lastFocusedNode = queuedActiveDescendant.current ? document.getElementById(queuedActiveDescendant.current) : null;\n    if (lastFocusedNode) {\n      dispatchVirtualBlur(lastFocusedNode, e.relatedTarget);\n    }\n  };\n\n  let onFocus = (e: ReactFocusEvent) => {\n    if (!e.isTrusted) {\n      return;\n    }\n\n    let curFocusedNode = queuedActiveDescendant.current ? document.getElementById(queuedActiveDescendant.current) : null;\n    if (curFocusedNode) {\n      let target = getEventTarget(e);\n      queueMicrotask(() => {\n        // instead of focusing the last focused node, just focus the collection instead and have the collection handle what item to focus via useSelectableCollection/Item\n        dispatchVirtualBlur(target, collectionRef.current);\n        dispatchVirtualFocus(collectionRef.current!, target);\n      });\n    }\n  };\n\n  // Clicking back into the input can happen after focus moved elsewhere in the dialog, while\n  // virtual focus is still on an option. Clear virtual focus on pointer down so mouse\n  // interactions restore the input state before the click's focus handling runs.\n  // Touch is excluded because touch interactions should not move focus back to the input.\n  let onPointerDown = (e: ReactPointerEvent) => {\n    if (e.button !== 0 || e.pointerType === 'touch' || queuedActiveDescendant.current == null || inputRef.current == null) {\n      return;\n    }\n\n    if (getEventTarget(e) === inputRef.current) {\n      clearVirtualFocus();\n    }\n  };\n\n  // Only apply the autocomplete specific behaviors if the collection component wrapped by it is actually\n  // being filtered/allows filtering by the Autocomplete.\n  let inputProps = {\n    value: state.inputValue,\n    onChange\n  } as AriaTextFieldProps<FocusableElement>;\n\n  let virtualFocusProps = {\n    onKeyDown,\n    'aria-activedescendant': state.focusedNodeId ?? undefined,\n    onBlur,\n    onFocus,\n    onPointerDown\n  };\n\n  if (hasCollection) {\n    inputProps = {\n      ...inputProps,\n      ...(shouldUseVirtualFocus && virtualFocusProps),\n      enterKeyHint: 'go',\n      'aria-controls': collectionId,\n      // TODO: readd proper logic for completionMode = complete (aria-autocomplete: both)\n      'aria-autocomplete': 'list',\n      // This disable's iOS's autocorrect suggestions, since the autocomplete provides its own suggestions.\n      autoCorrect: 'off',\n      // This disable's the macOS Safari spell check auto corrections.\n      spellCheck: 'false',\n      autoComplete: 'off'\n    };\n  }\n\n  return {\n    inputProps,\n    collectionProps: mergeProps(collectionProps, {\n      shouldUseVirtualFocus,\n      disallowTypeAhead: shouldUseVirtualFocus\n    }),\n    collectionRef: mergedCollectionRef,\n    filter: filter != null ? filterFn : undefined\n  };\n}\n"],"names":[],"version":3,"file":"useAutocomplete.cjs.map"}