"use strict";

Object.defineProperty(exports, "__esModule", {
  value: true
});
exports.FloatingBubble = void 0;
var _react = _interopRequireWildcard(require("react"));
var _web = require("@react-spring/web");
var _react2 = require("@use-gesture/react");
var _withDefaultProps = require("../../utils/with-default-props");
var _nativeProps = require("../../utils/native-props");
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 classPrefix = `adm-floating-bubble`;
const defaultProps = {
  axis: 'y',
  defaultOffset: {
    x: 0,
    y: 0
  }
};
const FloatingBubble = p => {
  const props = (0, _withDefaultProps.mergeProps)(defaultProps, p);
  const boundaryRef = (0, _react.useRef)(null);
  const buttonRef = (0, _react.useRef)(null);
  const [innerValue, setInnerValue] = (0, _react.useState)(props.offset === undefined ? props.defaultOffset : props.offset);
  (0, _react.useEffect)(() => {
    if (props.offset === undefined) return;
    api.start({
      x: props.offset.x,
      y: props.offset.y
    });
  }, [props.offset]);
  /**
   * memoize the `to` function
   * inside a component that renders frequently
   * to prevent an unintended restart
   */
  const [{
    x,
    y,
    opacity
  }, api] = (0, _web.useSpring)(() => ({
    x: innerValue.x,
    y: innerValue.y,
    opacity: 1
  }));
  const bind = (0, _react2.useDrag)(state => {
    var _a;
    let nextX = state.offset[0];
    let nextY = state.offset[1];
    if (state.last && props.magnetic) {
      const boundary = boundaryRef.current;
      const button = buttonRef.current;
      if (!boundary || !button) return;
      const boundaryRect = boundary.getBoundingClientRect();
      const buttonRect = button.getBoundingClientRect();
      if (props.magnetic === 'x') {
        const compensation = x.goal - x.get();
        const leftDistance = buttonRect.left + compensation - boundaryRect.left;
        const rightDistance = boundaryRect.right - (buttonRect.right + compensation);
        if (rightDistance <= leftDistance) {
          nextX += rightDistance;
        } else {
          nextX -= leftDistance;
        }
      } else if (props.magnetic === 'y') {
        const compensation = y.goal - y.get();
        const topDistance = buttonRect.top + compensation - boundaryRect.top;
        const bottomDistance = boundaryRect.bottom - (buttonRect.bottom + compensation);
        if (bottomDistance <= topDistance) {
          nextY += bottomDistance;
        } else {
          nextY -= topDistance;
        }
      }
    }
    const nextOffest = {
      x: nextX,
      y: nextY
    };
    if (props.offset === undefined) {
      // Uncontrolled mode
      api.start(nextOffest);
    } else {
      setInnerValue(nextOffest);
    }
    (_a = props.onOffsetChange) === null || _a === void 0 ? void 0 : _a.call(props, nextOffest);
    // active status
    api.start({
      opacity: state.active ? 0.8 : 1
    });
  }, {
    axis: props.axis === 'xy' ? undefined : props.axis,
    pointer: {
      touch: true
    },
    // the component won't trigger drag logic if the user just clicked on the component.
    filterTaps: true,
    // set constraints to the user gesture
    bounds: boundaryRef,
    from: () => [x.get(), y.get()]
  });
  return (0, _nativeProps.withNativeProps)(props, _react.default.createElement("div", {
    className: classPrefix
  }, _react.default.createElement("div", {
    className: `${classPrefix}-boundary-outer`
  }, _react.default.createElement("div", {
    className: `${classPrefix}-boundary`,
    ref: boundaryRef
  })), _react.default.createElement(_web.animated.div, Object.assign({}, bind(), {
    style: {
      opacity,
      transform: (0, _web.to)([x, y], (x, y) => `translate(${x}px, ${y}px)`)
    },
    onClick: props.onClick,
    className: `${classPrefix}-button`,
    ref: buttonRef
  }), props.children)));
};
exports.FloatingBubble = FloatingBubble;