UNPKG

@base-ui/react

Version:

Base UI is a library of headless ('unstyled') React components and low-level hooks. You gain complete control over your app's CSS and accessibility features.

97 lines (92 loc) 4.06 kB
"use strict"; var _interopRequireWildcard = require("@babel/runtime/helpers/interopRequireWildcard").default; Object.defineProperty(exports, "__esModule", { value: true }); exports.TooltipStore = void 0; exports.createNullTooltipStore = createNullTooltipStore; var React = _interopRequireWildcard(require("react")); var _store = require("@base-ui/utils/store"); var _empty = require("@base-ui/utils/empty"); var _createBaseUIEventDetails = require("../../internals/createBaseUIEventDetails"); var _reasons = require("../../internals/reasons"); var _NullStore = require("../../utils/NullStore"); var _popups = require("../../utils/popups"); const selectors = { ..._popups.popupStoreSelectors, disabled: state => state.disabled, instantType: state => state.instantType, isInstantPhase: state => state.isInstantPhase, trackCursorAxis: state => state.trackCursorAxis, disableHoverablePopup: state => state.disableHoverablePopup, lastOpenChangeReason: state => state.openChangeReason, closeOnClick: state => state.closeOnClick, closeDelay: state => state.closeDelay, adaptiveOrigin: state => state.adaptiveOrigin }; /** * The store view that detached handle-backed triggers read from. Both the real `TooltipStore` and * the inert fallback store satisfy it, so a trigger can read from whichever store the handle * currently exposes. Narrowed to the members a trigger actually uses — the trigger-data members plus * `setOpen`/`cancelPendingOpen` (called directly by the trigger) and `useSyncedValue` — so the * exposed surface can't bypass the open-change pipeline; on the detached fallback store every one of * these mutations is a no-op. */ class TooltipStore extends _store.ReactStore { constructor(initialState, floatingId, nested) { const triggerElements = new _popups.PopupTriggerMap(); super(createInitialState(initialState, triggerElements, floatingId, nested), createInitialContext(triggerElements), selectors); } setOpen = (nextOpen, eventDetails) => { (0, _popups.applyPopupOpenChange)(this, nextOpen, eventDetails, { extraState: { openChangeReason: eventDetails.reason } }); }; // Used by trigger clicks to clear a delayed hover open without reporting a public open-state change. cancelPendingOpen(event) { this.state.floatingRootContext.dispatchOpenChange(false, (0, _createBaseUIEventDetails.createChangeEventDetails)(_reasons.REASONS.triggerPress, event)); } } /** * Creates the inert fallback store used by detached handle-backed triggers while no `Tooltip.Root` * is attached. It preserves a tooltip-specific trigger registry in context so detached triggers can * register before migrating to the live root store. `setOpen`/`cancelPendingOpen` are no-ops * (matching the inert reads/writes of `NullStore`), so a trigger can call them from hover/click * handlers while detached without any effect. */ exports.TooltipStore = TooltipStore; function createNullTooltipStore() { const triggerElements = new _popups.PopupTriggerMap(); const store = new _NullStore.NullStore(Object.freeze(createInitialState(undefined, triggerElements)), Object.freeze(createInitialContext(triggerElements)), selectors); return Object.assign(store, { setOpen: _empty.NOOP, cancelPendingOpen: _empty.NOOP }); } function createInitialState(initialState, triggerElements, floatingId, nested = false) { const state = { ...(0, _popups.createInitialPopupStoreState)(), disabled: false, instantType: undefined, isInstantPhase: false, trackCursorAxis: 'none', disableHoverablePopup: false, openChangeReason: null, closeOnClick: true, closeDelay: 0, adaptiveOrigin: undefined, ...initialState }; state.floatingRootContext = (0, _popups.createPopupFloatingRootContext)(triggerElements, floatingId, nested); return state; } function createInitialContext(triggerElements) { return { popupRef: /*#__PURE__*/React.createRef(), onOpenChange: undefined, onOpenChangeComplete: undefined, triggerElements }; }