UNPKG

8.37 kBJavaScriptView Raw
1'use strict';
2
3exports.__esModule = true;
4
5var _extends2 = require('babel-runtime/helpers/extends');
6
7var _extends3 = _interopRequireDefault(_extends2);
8
9var _objectWithoutProperties2 = require('babel-runtime/helpers/objectWithoutProperties');
10
11var _objectWithoutProperties3 = _interopRequireDefault(_objectWithoutProperties2);
12
13var _classCallCheck2 = require('babel-runtime/helpers/classCallCheck');
14
15var _classCallCheck3 = _interopRequireDefault(_classCallCheck2);
16
17var _possibleConstructorReturn2 = require('babel-runtime/helpers/possibleConstructorReturn');
18
19var _possibleConstructorReturn3 = _interopRequireDefault(_possibleConstructorReturn2);
20
21var _inherits2 = require('babel-runtime/helpers/inherits');
22
23var _inherits3 = _interopRequireDefault(_inherits2);
24
25var _collapseStyles;
26
27var _classnames = require('classnames');
28
29var _classnames2 = _interopRequireDefault(_classnames);
30
31var _style = require('dom-helpers/style');
32
33var _style2 = _interopRequireDefault(_style);
34
35var _react = require('react');
36
37var _react2 = _interopRequireDefault(_react);
38
39var _propTypes = require('prop-types');
40
41var _propTypes2 = _interopRequireDefault(_propTypes);
42
43var _Transition = require('react-transition-group/Transition');
44
45var _Transition2 = _interopRequireDefault(_Transition);
46
47var _capitalize = require('./utils/capitalize');
48
49var _capitalize2 = _interopRequireDefault(_capitalize);
50
51var _createChainedFunction = require('./utils/createChainedFunction');
52
53var _createChainedFunction2 = _interopRequireDefault(_createChainedFunction);
54
55function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
56
57var MARGINS = {
58 height: ['marginTop', 'marginBottom'],
59 width: ['marginLeft', 'marginRight']
60};
61
62// reading a dimension prop will cause the browser to recalculate,
63// which will let our animations work
64function triggerBrowserReflow(node) {
65 node.offsetHeight; // eslint-disable-line no-unused-expressions
66}
67
68function getDimensionValue(dimension, elem) {
69 var value = elem['offset' + (0, _capitalize2.default)(dimension)];
70 var margins = MARGINS[dimension];
71
72 return value + parseInt((0, _style2.default)(elem, margins[0]), 10) + parseInt((0, _style2.default)(elem, margins[1]), 10);
73}
74
75var collapseStyles = (_collapseStyles = {}, _collapseStyles[_Transition.EXITED] = 'collapse', _collapseStyles[_Transition.EXITING] = 'collapsing', _collapseStyles[_Transition.ENTERING] = 'collapsing', _collapseStyles[_Transition.ENTERED] = 'collapse in', _collapseStyles);
76
77var propTypes = {
78 /**
79 * Show the component; triggers the expand or collapse animation
80 */
81 in: _propTypes2.default.bool,
82
83 /**
84 * Wait until the first "enter" transition to mount the component (add it to the DOM)
85 */
86 mountOnEnter: _propTypes2.default.bool,
87
88 /**
89 * Unmount the component (remove it from the DOM) when it is collapsed
90 */
91 unmountOnExit: _propTypes2.default.bool,
92
93 /**
94 * Run the expand animation when the component mounts, if it is initially
95 * shown
96 */
97 appear: _propTypes2.default.bool,
98
99 /**
100 * Duration of the collapse animation in milliseconds, to ensure that
101 * finishing callbacks are fired even if the original browser transition end
102 * events are canceled
103 */
104 timeout: _propTypes2.default.number,
105
106 /**
107 * Callback fired before the component expands
108 */
109 onEnter: _propTypes2.default.func,
110 /**
111 * Callback fired after the component starts to expand
112 */
113 onEntering: _propTypes2.default.func,
114 /**
115 * Callback fired after the component has expanded
116 */
117 onEntered: _propTypes2.default.func,
118 /**
119 * Callback fired before the component collapses
120 */
121 onExit: _propTypes2.default.func,
122 /**
123 * Callback fired after the component starts to collapse
124 */
125 onExiting: _propTypes2.default.func,
126 /**
127 * Callback fired after the component has collapsed
128 */
129 onExited: _propTypes2.default.func,
130
131 /**
132 * The dimension used when collapsing, or a function that returns the
133 * dimension
134 *
135 * _Note: Bootstrap only partially supports 'width'!
136 * You will need to supply your own CSS animation for the `.width` CSS class._
137 */
138 dimension: _propTypes2.default.oneOfType([_propTypes2.default.oneOf(['height', 'width']), _propTypes2.default.func]),
139
140 /**
141 * Function that returns the height or width of the animating DOM node
142 *
143 * Allows for providing some custom logic for how much the Collapse component
144 * should animate in its specified dimension. Called with the current
145 * dimension prop value and the DOM node.
146 */
147 getDimensionValue: _propTypes2.default.func,
148
149 /**
150 * ARIA role of collapsible element
151 */
152 role: _propTypes2.default.string
153};
154
155var defaultProps = {
156 in: false,
157 timeout: 300,
158 mountOnEnter: false,
159 unmountOnExit: false,
160 appear: false,
161
162 dimension: 'height',
163 getDimensionValue: getDimensionValue
164};
165
166var Collapse = function (_React$Component) {
167 (0, _inherits3.default)(Collapse, _React$Component);
168
169 function Collapse() {
170 var _temp, _this, _ret;
171
172 (0, _classCallCheck3.default)(this, Collapse);
173
174 for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) {
175 args[_key] = arguments[_key];
176 }
177
178 return _ret = (_temp = (_this = (0, _possibleConstructorReturn3.default)(this, _React$Component.call.apply(_React$Component, [this].concat(args))), _this), _this.handleEnter = function (elem) {
179 elem.style[_this.getDimension()] = '0';
180 }, _this.handleEntering = function (elem) {
181 var dimension = _this.getDimension();
182 elem.style[dimension] = _this._getScrollDimensionValue(elem, dimension);
183 }, _this.handleEntered = function (elem) {
184 elem.style[_this.getDimension()] = null;
185 }, _this.handleExit = function (elem) {
186 var dimension = _this.getDimension();
187 elem.style[dimension] = _this.props.getDimensionValue(dimension, elem) + 'px';
188 triggerBrowserReflow(elem);
189 }, _this.handleExiting = function (elem) {
190 elem.style[_this.getDimension()] = '0';
191 }, _temp), (0, _possibleConstructorReturn3.default)(_this, _ret);
192 }
193
194 Collapse.prototype.getDimension = function getDimension() {
195 return typeof this.props.dimension === 'function' ? this.props.dimension() : this.props.dimension;
196 };
197
198 // for testing
199
200
201 Collapse.prototype._getScrollDimensionValue = function _getScrollDimensionValue(elem, dimension) {
202 return elem['scroll' + (0, _capitalize2.default)(dimension)] + 'px';
203 };
204
205 /* -- Expanding -- */
206
207
208 /* -- Collapsing -- */
209
210
211 Collapse.prototype.render = function render() {
212 var _this2 = this;
213
214 var _props = this.props,
215 onEnter = _props.onEnter,
216 onEntering = _props.onEntering,
217 onEntered = _props.onEntered,
218 onExit = _props.onExit,
219 onExiting = _props.onExiting,
220 className = _props.className,
221 children = _props.children,
222 props = (0, _objectWithoutProperties3.default)(_props, ['onEnter', 'onEntering', 'onEntered', 'onExit', 'onExiting', 'className', 'children']);
223
224
225 delete props.dimension;
226 delete props.getDimensionValue;
227
228 var handleEnter = (0, _createChainedFunction2.default)(this.handleEnter, onEnter);
229 var handleEntering = (0, _createChainedFunction2.default)(this.handleEntering, onEntering);
230 var handleEntered = (0, _createChainedFunction2.default)(this.handleEntered, onEntered);
231 var handleExit = (0, _createChainedFunction2.default)(this.handleExit, onExit);
232 var handleExiting = (0, _createChainedFunction2.default)(this.handleExiting, onExiting);
233
234 return _react2.default.createElement(
235 _Transition2.default,
236 (0, _extends3.default)({}, props, {
237 'aria-expanded': props.role ? props.in : null,
238 onEnter: handleEnter,
239 onEntering: handleEntering,
240 onEntered: handleEntered,
241 onExit: handleExit,
242 onExiting: handleExiting
243 }),
244 function (state, innerProps) {
245 return _react2.default.cloneElement(children, (0, _extends3.default)({}, innerProps, {
246 className: (0, _classnames2.default)(className, children.props.className, collapseStyles[state], _this2.getDimension() === 'width' && 'width')
247 }));
248 }
249 );
250 };
251
252 return Collapse;
253}(_react2.default.Component);
254
255Collapse.propTypes = propTypes;
256Collapse.defaultProps = defaultProps;
257
258exports.default = Collapse;
259module.exports = exports['default'];
\No newline at end of file