"use strict";

Object.defineProperty(exports, "__esModule", {
  value: true
});
exports.Item = Item;
exports.ItemText = ItemText;
exports.Root = Root;
var _react = require("react");
var _reactNative = require("react-native");
var _reactNativeReanimated = _interopRequireWildcard(require("react-native-reanimated"));
var _useTheme = require("../theme/use-theme.js");
var _useInteractionState = require("../hooks/useInteractionState.js");
var _index = require("../styles/index.js");
var _jsxRuntime = require("react/jsx-runtime");
function _interopRequireWildcard(e, t) { if ("function" == typeof WeakMap) var r = new WeakMap(), n = new WeakMap(); return (_interopRequireWildcard = function (e, t) { if (!t && e && e.__esModule) return e; var o, i, f = { __proto__: null, default: e }; if (null === e || "object" != typeof e && "function" != typeof e) return f; if (o = t ? n : r) { if (o.has(e)) return o.get(e); o.set(e, f); } for (const t in e) "default" !== t && {}.hasOwnProperty.call(e, t) && ((i = (o = Object.defineProperty) && Object.getOwnPropertyDescriptor(e, t)) && (i.get || i.set) ? o(f, t, i) : f[t] = e[t]); return f; })(e, t); }
const InternalContext = /*#__PURE__*/(0, _react.createContext)(null);

/**
 * Segmented control component.
 *
 * @example
 * ```tsx
 * <SegmentedControl.Root value={value} onChange={setValue}>
 *   <SegmentedControl.Item value="one">
 *     <SegmentedControl.ItemText value="one">
 *       One
 *     </SegmentedControl.ItemText>
 *   </SegmentedControl.Item>
 *   <SegmentedControl.Item value="two">
 *     <SegmentedControl.ItemText value="two">
 *       Two
 *     </SegmentedControl.ItemText>
 *   </SegmentedControl.Item>
 * </SegmentedControl.Root>
 * ```
 */
function Root({
  label,
  type = 'radio',
  size = 'large',
  value,
  onChange,
  children,
  style,
  accessibilityHint
}) {
  const theme = (0, _useTheme.useTheme)();
  const [selectedPosition, setSelectedPosition] = (0, _react.useState)(null);
  const contextValue = (0, _react.useMemo)(() => {
    return {
      type,
      size,
      selectedValue: value,
      selectedPosition,
      onSelectValue: (val, position) => {
        onChange(val);
        if (position) setSelectedPosition(position);
      },
      updatePosition: position => {
        setSelectedPosition(currPos => {
          if (currPos && currPos.width === position.width && currPos.x === position.x) {
            return currPos;
          }
          return position;
        });
      }
    };
  }, [value, selectedPosition, setSelectedPosition, onChange, type, size]);

  // Height of the wrapping pill matches the active item height (item
  // `minHeight` + 4px outer `p_xs` padding on both sides). Locking the
  // outer View to this exact height keeps the control as a tight inline
  // pill on every platform — without it, a parent column flex context
  // (the default on a `<View>`) would let the Root stretch vertically
  // and the items inside would inherit that stretched height, blowing
  // the control up into a giant block on native.
  const itemMinHeight = size === 'large' ? 40 : 32;
  const pillHeight = itemMinHeight + 8;
  return /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
    accessibilityLabel: label,
    accessibilityHint: accessibilityHint ?? '',
    style: [_index.atoms.w_full, _index.atoms.relative, _index.atoms.flex_row, _index.atoms.align_center, {
      backgroundColor: theme.colors.contrast50
    }, {
      borderRadius: 14,
      height: pillHeight
    }, _index.atoms.p_xs, style],
    role: type === 'tabs' ? 'tablist' : 'radiogroup',
    children: [selectedPosition !== null && /*#__PURE__*/(0, _jsxRuntime.jsx)(Slider, {
      x: selectedPosition.x,
      width: selectedPosition.width
    }), /*#__PURE__*/(0, _jsxRuntime.jsx)(InternalContext.Provider, {
      value: contextValue,
      children: children
    })]
  });
}
const InternalItemContext = /*#__PURE__*/(0, _react.createContext)(null);
function Item({
  value,
  style,
  children,
  onPress: onPressProp,
  accessibilityLabel,
  accessibilityHint,
  testID,
  disabled
}) {
  const [position, setPosition] = (0, _react.useState)(null);
  // Drive press-opacity via state, not Pressable's function-form `style`:
  // NativeWind v4's css-interop swallows the function form, which would drop
  // the segment's base layout styles (flex_1, padding, minHeight, radius).
  const {
    state: pressed,
    onIn: onPressIn,
    onOut: onPressOut
  } = (0, _useInteractionState.useInteractionState)();
  const ctx = (0, _react.useContext)(InternalContext);
  if (!ctx) {
    throw new Error('SegmentedControl.Item must be used within a SegmentedControl.Root');
  }
  const active = ctx.selectedValue === value;
  const needsUpdate = active && position && (ctx.selectedPosition?.x !== position.x || ctx.selectedPosition?.width !== position.width);

  // Use a ref to avoid re-running the layout effect when updatePosition changes
  const updatePositionRef = (0, _react.useRef)(ctx.updatePosition);
  updatePositionRef.current = ctx.updatePosition;
  const positionRef = (0, _react.useRef)(position);
  positionRef.current = position;
  (0, _react.useLayoutEffect)(() => {
    if (needsUpdate && positionRef.current) {
      updatePositionRef.current(positionRef.current);
    }
  }, [needsUpdate]);
  const onPress = (0, _react.useCallback)(() => {
    ctx.onSelectValue(value, position);
    onPressProp?.();
  }, [ctx, value, position, onPressProp]);

  // We render the segment as a flat `Pressable` (not Bloom's `Button`)
  // for two reasons:
  //   1. Layout: we need the touch target to participate directly in the
  //      Root's row flex layout so `flex: 1` distributes the items
  //      evenly on every platform. Bloom Button wraps its Pressable in
  //      an Animated.View that doesn't forward layout-affecting styles,
  //      which would collapse the segment to its natural text width.
  //   2. Semantics: the Root carries `role="tablist"`/`"radiogroup"` and
  //      each item carries `role="tab"`/`"radio"`. Bloom Button always
  //      adds `accessibilityRole="button"` — that overrides the correct
  //      a11y role for tablist children.
  const itemRole = ctx.type === 'tabs' ? 'tab' : 'radio';
  const itemMinHeight = ctx.size === 'large' ? 40 : 32;
  return /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
    style: [_index.atoms.flex_1, _index.atoms.flex_row, _index.atoms.align_stretch],
    onLayout: evt => {
      const measuredPosition = {
        x: evt.nativeEvent.layout.x,
        width: evt.nativeEvent.layout.width
      };
      if (!ctx.selectedPosition && active) {
        ctx.onSelectValue(value, measuredPosition);
      }
      setPosition(measuredPosition);
    },
    children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Pressable, {
      onPress: onPress,
      onPressIn: disabled ? undefined : onPressIn,
      onPressOut: disabled ? undefined : onPressOut,
      accessibilityLabel: accessibilityLabel,
      accessibilityHint: accessibilityHint,
      accessibilityState: {
        selected: active,
        disabled: !!disabled
      },
      role: itemRole,
      disabled: disabled,
      testID: testID,
      style: [_index.atoms.flex_1, _index.atoms.flex_row, _index.atoms.align_center, _index.atoms.justify_center, _index.atoms.bg_transparent, _index.atoms.px_sm, _index.atoms.py_xs, {
        minHeight: itemMinHeight,
        borderRadius: 10
      }, pressed && !disabled && {
        opacity: 0.7
      }, style],
      children: /*#__PURE__*/(0, _jsxRuntime.jsx)(InternalItemContext.Provider, {
        value: {
          active
        },
        children: children
      })
    })
  });
}
function ItemText({
  style,
  children,
  ...props
}) {
  const theme = (0, _useTheme.useTheme)();
  const ctx = (0, _react.useContext)(InternalItemContext);
  if (!ctx) {
    throw new Error('SegmentedControl.ItemText must be used within a SegmentedControl.Item');
  }
  return /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
    ...props,
    style: [_index.atoms.text_center, _index.atoms.text_md, _index.atoms.font_medium, _index.atoms.px_xs, ctx.active ? {
      color: theme.colors.text
    } : {
      color: theme.colors.textTertiary
    }, style],
    children: children
  });
}
function Slider({
  x,
  width
}) {
  const theme = (0, _useTheme.useTheme)();
  const nativeLayout = _reactNative.Platform.OS !== 'web' ? _reactNativeReanimated.LinearTransition.easing(_reactNativeReanimated.Easing.out(_reactNativeReanimated.Easing.exp)) : undefined;
  return /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNativeReanimated.default.View, {
    layout: nativeLayout,
    style: [_index.atoms.absolute, {
      backgroundColor: theme.colors.background
    }, {
      top: 4,
      bottom: 4,
      left: 0,
      width,
      borderRadius: 10
    }, (0, _index.platform)({
      web: {
        boxShadow: '0px 2px 4px 0px #0000000D'
      },
      ios: {
        shadowColor: '#000',
        shadowOffset: {
          width: 0,
          height: 2
        },
        shadowOpacity: 0x0d / 0xff,
        shadowRadius: 4
      },
      android: {
        elevation: 0.25
      }
    }), (0, _index.platform)({
      native: {
        left: x
      },
      web: {
        transform: [{
          translateX: x
        }]
      }
    })]
  });
}
//# sourceMappingURL=index.js.map