import { useCallback, useState, useRef, useEffect } from 'react';
import { u as useOpenCloseTransitionStates, t as tabbable } from './usePopoverTransitionStates-CDXCdyKa.js';

const useDialogTransitionStates = (ref, openProp, options = {}) => {
  const { onOpenAnimationStart, onCloseAnimationComplete } = options;
  const getDurationMs = useCallback(() => {
    if (!ref.current || !window) return 0;
    const duration = window.getComputedStyle(ref.current).animationDuration;
    return parseFloat(duration) * 1e3;
  }, [ref]);
  const handleOpenAnimationStart = useCallback(() => {
    if (!ref.current) return;
    ref.current.showModal();
    onOpenAnimationStart?.();
  }, [ref, onOpenAnimationStart]);
  const handleCloseAnimationComplete = useCallback(() => {
    if (!ref.current) return;
    ref.current.close();
    onCloseAnimationComplete?.();
  }, [ref, onCloseAnimationComplete]);
  return useOpenCloseTransitionStates(openProp, {
    ...options,
    onOpenAnimationStart: handleOpenAnimationStart,
    onCloseAnimationComplete: handleCloseAnimationComplete,
    durationMs: getDurationMs
  });
};

const useKeyboardFocusables = (element, options = {
  observeChange: true,
  attributes: true,
  characterData: true,
  childList: true,
  subtree: true
}) => {
  const [focusables, setFocusables] = useState(null);
  const observerRef = useRef();
  useEffect(() => {
    const target = element instanceof HTMLElement ? element : element?.current;
    if (!target) return;
    if (!options.observeChange && !focusables) {
      setFocusables(tabbable(target));
      return;
    }
    const mutationCallback = () => {
      const targetArr = tabbable(target);
      if (targetArr.length === 0) return;
      setFocusables(targetArr);
    };
    const observer = new MutationObserver(mutationCallback);
    observerRef.current = observer;
    observer.observe(target, {
      childList: true,
      // Observe changes to child elements
      subtree: true,
      // Observe changes to descendants of the target
      attributes: true,
      // Observe changes to attributes
      characterData: true
      // Observe changes to text content
    });
    return () => {
      observer.disconnect();
    };
  }, [element, options, focusables]);
  return { focusables };
};

const getActiveHTMLElement = () => {
  return document.activeElement instanceof HTMLElement ? document.activeElement : null;
};
function useDrillDownContextState({
  defaultDrillDownIndex = 0
}) {
  const [drillDownIndex, setDrillDownIndex] = useState(void 0);
  const [registeredIndices, setRegisteredIndices] = useState([]);
  const drillDownPath = useRef([]);
  const [onClose, setOnClose] = useState([]);
  const navigationTriggerFocusRef = useRef(null);
  const hostTriggerFocusRef = useRef(null);
  const shouldRestoreHostFocusRef = useRef(false);
  const hasActiveDrillDownRef = useRef(false);
  const restoreFocus = useCallback(
    (focusRef) => {
      requestAnimationFrame(() => {
        focusRef.current?.focus();
        focusRef.current = null;
      });
    },
    []
  );
  const restoreNavigationFocus = useCallback(() => {
    restoreFocus(navigationTriggerFocusRef);
  }, [restoreFocus]);
  const restoreHostFocus = useCallback(() => {
    restoreFocus(hostTriggerFocusRef);
  }, [restoreFocus]);
  const back = useCallback(() => {
    const newIndex = drillDownPath.current.pop();
    if (newIndex == null && navigationTriggerFocusRef.current) {
      setDrillDownIndex(void 0);
      restoreNavigationFocus();
      return;
    }
    setDrillDownIndex(newIndex);
  }, [setDrillDownIndex, drillDownPath, restoreNavigationFocus]);
  const next = useCallback(() => {
    if (drillDownIndex == null) {
      navigationTriggerFocusRef.current = getActiveHTMLElement();
      drillDownPath.current = [];
      setDrillDownIndex(defaultDrillDownIndex);
      return;
    }
    if (registeredIndices && registeredIndices[drillDownIndex + 1] == null) {
      drillDownPath.current = [];
      setDrillDownIndex(void 0);
      restoreNavigationFocus();
      return;
    }
    drillDownPath.current.push(drillDownIndex);
    setDrillDownIndex(drillDownIndex + 1);
  }, [
    drillDownIndex,
    setDrillDownIndex,
    defaultDrillDownIndex,
    drillDownPath,
    registeredIndices,
    restoreNavigationFocus
  ]);
  const setIndexWithinBounds = useCallback(
    (index) => {
      if (index == null || index < 0 || registeredIndices && registeredIndices[index] == null) {
        setDrillDownIndex(void 0);
        restoreNavigationFocus();
        return;
      }
      if (drillDownIndex === void 0) {
        navigationTriggerFocusRef.current = getActiveHTMLElement();
        drillDownPath.current = [];
      } else {
        drillDownPath.current.push(drillDownIndex);
      }
      setDrillDownIndex(index);
    },
    [
      drillDownIndex,
      setDrillDownIndex,
      drillDownPath,
      registeredIndices,
      restoreNavigationFocus
    ]
  );
  const setHostTrigger = useCallback((element) => {
    if (element == null || hostTriggerFocusRef.current != null) return;
    hostTriggerFocusRef.current = element;
  }, []);
  const onHostCloseHandler = useCallback(() => {
    const shouldResetToDefault = drillDownIndex != null || hasActiveDrillDownRef.current;
    drillDownPath.current = [];
    navigationTriggerFocusRef.current = null;
    shouldRestoreHostFocusRef.current = true;
    hasActiveDrillDownRef.current = false;
    if (shouldResetToDefault) {
      setDrillDownIndex(defaultDrillDownIndex);
    }
  }, [defaultDrillDownIndex, drillDownIndex]);
  const onHostClosedHandler = useCallback(() => {
    if (!shouldRestoreHostFocusRef.current) return;
    shouldRestoreHostFocusRef.current = false;
    restoreHostFocus();
  }, [restoreHostFocus]);
  if (drillDownIndex != null) {
    hasActiveDrillDownRef.current = true;
  }
  const setOnCloseForIndex = useCallback(
    (fn, index) => {
      setOnClose((arr) => {
        const nextOnClose = [...arr];
        nextOnClose[index] = () => {
          fn();
          setDrillDownIndex(void 0);
          restoreNavigationFocus();
        };
        return nextOnClose;
      });
    },
    [restoreNavigationFocus]
  );
  return {
    index: drillDownIndex,
    setIndex: setIndexWithinBounds,
    back,
    next,
    registeredIndices,
    setRegisteredIndices,
    onClose,
    setOnClose: setOnCloseForIndex,
    hostIsInteractive: true,
    setHostTrigger,
    onHostClose: onHostCloseHandler,
    onHostClosed: onHostClosedHandler
  };
}

const useInitialFocus = (dialogRef, { computeFocus }) => {
  useEffect(() => {
    if (!dialogRef.current) {
      return () => {
      };
    }
    const observer = new MutationObserver((mutations) => {
      mutations.forEach((mutation) => {
        if (mutation.attributeName === "open" && mutation.target === dialogRef.current && mutation.target instanceof HTMLDialogElement && mutation.target.open === true) {
          const focusables = tabbable(dialogRef.current);
          const target = computeFocus?.(focusables) || focusables[0];
          target?.focus();
        }
      });
    });
    observer.observe(dialogRef.current, {
      attributes: true,
      attributeFilter: ["open"]
    });
    return () => {
      observer.disconnect();
    };
  }, [dialogRef, computeFocus]);
};

export { useDialogTransitionStates as a, useKeyboardFocusables as b, useInitialFocus as c, useDrillDownContextState as u };
//# sourceMappingURL=useInitialFocus-BUxEDMEG.js.map
