UNPKG

@commercetools-uikit/collapsible-motion

Version:

A component which allows building collapsible elements with an arbitrary height.

175 lines (165 loc) • 9.36 kB
'use strict'; Object.defineProperty(exports, '__esModule', { value: true }); var _Object$keys = require('@babel/runtime-corejs3/core-js-stable/object/keys'); var _Object$getOwnPropertySymbols = require('@babel/runtime-corejs3/core-js-stable/object/get-own-property-symbols'); var _filterInstanceProperty = require('@babel/runtime-corejs3/core-js-stable/instance/filter'); var _Object$getOwnPropertyDescriptor = require('@babel/runtime-corejs3/core-js-stable/object/get-own-property-descriptor'); var _forEachInstanceProperty = require('@babel/runtime-corejs3/core-js-stable/instance/for-each'); var _Object$getOwnPropertyDescriptors = require('@babel/runtime-corejs3/core-js-stable/object/get-own-property-descriptors'); var _Object$defineProperties = require('@babel/runtime-corejs3/core-js-stable/object/define-properties'); var _Object$defineProperty = require('@babel/runtime-corejs3/core-js-stable/object/define-property'); var _objectDestructuringEmpty = require('@babel/runtime-corejs3/helpers/objectDestructuringEmpty'); var _extends = require('@babel/runtime-corejs3/helpers/extends'); var _objectWithoutProperties = require('@babel/runtime-corejs3/helpers/objectWithoutProperties'); var _defineProperty = require('@babel/runtime-corejs3/helpers/defineProperty'); var _slicedToArray = require('@babel/runtime-corejs3/helpers/slicedToArray'); var react$1 = require('react'); var utils = require('@commercetools-uikit/utils'); var react = require('@emotion/react'); var isNil = require('lodash/isNil'); var hooks = require('@commercetools-uikit/hooks'); var jsxRuntime = require('@emotion/react/jsx-runtime'); function _interopDefault (e) { return e && e.__esModule ? e : { 'default': e }; } var _Object$keys__default = /*#__PURE__*/_interopDefault(_Object$keys); var _Object$getOwnPropertySymbols__default = /*#__PURE__*/_interopDefault(_Object$getOwnPropertySymbols); var _filterInstanceProperty__default = /*#__PURE__*/_interopDefault(_filterInstanceProperty); var _Object$getOwnPropertyDescriptor__default = /*#__PURE__*/_interopDefault(_Object$getOwnPropertyDescriptor); var _forEachInstanceProperty__default = /*#__PURE__*/_interopDefault(_forEachInstanceProperty); var _Object$getOwnPropertyDescriptors__default = /*#__PURE__*/_interopDefault(_Object$getOwnPropertyDescriptors); var _Object$defineProperties__default = /*#__PURE__*/_interopDefault(_Object$defineProperties); var _Object$defineProperty__default = /*#__PURE__*/_interopDefault(_Object$defineProperty); var isNil__default = /*#__PURE__*/_interopDefault(isNil); const _excluded = ["minHeight"]; function ownKeys(e, r) { var t = _Object$keys__default["default"](e); if (_Object$getOwnPropertySymbols__default["default"]) { var o = _Object$getOwnPropertySymbols__default["default"](e); r && (o = _filterInstanceProperty__default["default"](o).call(o, function (r) { return _Object$getOwnPropertyDescriptor__default["default"](e, r).enumerable; })), t.push.apply(t, o); } return t; } function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var _context, _context2; var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? _forEachInstanceProperty__default["default"](_context = ownKeys(Object(t), !0)).call(_context, function (r) { _defineProperty(e, r, t[r]); }) : _Object$getOwnPropertyDescriptors__default["default"] ? _Object$defineProperties__default["default"](e, _Object$getOwnPropertyDescriptors__default["default"](t)) : _forEachInstanceProperty__default["default"](_context2 = ownKeys(Object(t))).call(_context2, function (r) { _Object$defineProperty__default["default"](e, r, _Object$getOwnPropertyDescriptor__default["default"](t, r)); }); } return e; } const getMinHeight = minHeight => minHeight !== 0 ? `${minHeight}px` : minHeight; const getVisibility = height => height === 0 ? 'hidden' : 'visible'; const createOpeningAnimation = function (height) { let minHeight = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0; return react.keyframes` 0% { height: ${getMinHeight(minHeight)}; overflow: hidden; visibility: ${getVisibility(minHeight)}; } 99% { height: ${height}px; overflow: hidden; } 100% { height: auto; overflow: visible; } `; }; const createClosingAnimation = function (height) { let minHeight = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0; return react.keyframes` from { height: ${height}px; } to { height: ${getMinHeight(minHeight)}; overflow: hidden; visibility: ${getVisibility(minHeight)}; } `; }; const useToggleAnimation = function (isOpen, toggle) { let minHeight = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 0; const nodeRef = react$1.useRef(null); const animationRef = react$1.useRef(null); const prevIsOpen = hooks.usePrevious(isOpen); react$1.useEffect(() => { process.env.NODE_ENV !== "production" ? utils.warning(nodeRef.current, 'You need to call `registerContentNode` in order to use this component') : void 0; }, // to match the componentDidMount behaviour [nodeRef]); const handleToggle = react$1.useCallback(() => { process.env.NODE_ENV !== "production" ? utils.warning(nodeRef.current, 'You need to call `registerContentNode` in order to use this component') : void 0; // set panel height to the height of the content, // so we can animate between the height and 0 toggle && toggle(); }, [nodeRef, toggle]); const containerStyles = isOpen ? { height: 'auto' } : { height: getMinHeight(minHeight), overflow: 'hidden', visibility: getVisibility(minHeight) }; // if state has changed if (typeof prevIsOpen !== 'undefined' && prevIsOpen !== isOpen && nodeRef.current) { animationRef.current = isOpen ? createOpeningAnimation(nodeRef.current.clientHeight, minHeight) : createClosingAnimation(nodeRef.current.clientHeight, minHeight); } return [animationRef.current, containerStyles, handleToggle, nodeRef]; }; const ControlledCollapsibleMotion = props => { const _useToggleAnimation = useToggleAnimation(!props.isClosed, props.onToggle, props.minHeight), _useToggleAnimation2 = _slicedToArray(_useToggleAnimation, 4), animation = _useToggleAnimation2[0], containerStyles = _useToggleAnimation2[1], animationToggle = _useToggleAnimation2[2], registerContentNode = _useToggleAnimation2[3]; return jsxRuntime.jsx(react.ClassNames, { children: _ref => { let css = _ref.css; let animationStyle = {}; if (animation) { // By calling `css`, emotion injects the required CSS into the document head. // eslint-disable-next-line no-unused-expressions css` animation: ${animation} 200ms forwards; `; animationStyle = { animation: `${animation.name} 200ms forwards` }; } return props.children({ isOpen: !props.isClosed, containerStyles: _objectSpread(_objectSpread({}, containerStyles), animationStyle), toggle: animationToggle, registerContentNode: registerContentNode }); } }); }; ControlledCollapsibleMotion.displayName = 'ControlledCollapsibleMotion'; const UncontrolledCollapsibleMotion = _ref2 => { let _ref2$minHeight = _ref2.minHeight, minHeight = _ref2$minHeight === void 0 ? 0 : _ref2$minHeight, props = _objectWithoutProperties(_ref2, _excluded); const _useToggleState = hooks.useToggleState(!props.isDefaultClosed), _useToggleState2 = _slicedToArray(_useToggleState, 2), isOpen = _useToggleState2[0], toggle = _useToggleState2[1]; const _useToggleAnimation3 = useToggleAnimation(isOpen, toggle, minHeight), _useToggleAnimation4 = _slicedToArray(_useToggleAnimation3, 4), animation = _useToggleAnimation4[0], containerStyles = _useToggleAnimation4[1], animationToggle = _useToggleAnimation4[2], registerContentNode = _useToggleAnimation4[3]; return jsxRuntime.jsx(react.ClassNames, { children: _ref3 => { let css = _ref3.css; let animationStyle = {}; if (animation) { // By calling `css`, emotion injects the required CSS into the document head. // eslint-disable-next-line no-unused-expressions css` animation: ${animation} 200ms forwards; `; animationStyle = { animation: `${animation.name} 200ms forwards` }; } return props.children({ isOpen, containerStyles: _objectSpread(_objectSpread({}, containerStyles), animationStyle), toggle: animationToggle, registerContentNode: registerContentNode }); } }); }; UncontrolledCollapsibleMotion.displayName = 'UncontrolledCollapsibleMotion'; const CollapsibleMotion = _ref4 => { let props = _extends({}, (_objectDestructuringEmpty(_ref4), _ref4)); const isControlledComponent = !isNil__default["default"](props.isClosed); if (isControlledComponent) { return jsxRuntime.jsx(ControlledCollapsibleMotion, _objectSpread({}, props)); } return jsxRuntime.jsx(UncontrolledCollapsibleMotion, _objectSpread({}, props)); }; CollapsibleMotion.displayName = 'CollapsibleMotion'; var CollapsibleMotion$1 = CollapsibleMotion; // NOTE: This string will be replaced on build time with the package version. var version = "20.2.3"; exports["default"] = CollapsibleMotion$1; exports.version = version;