├── .babelrc
├── .gitignore
├── .travis.yml
├── LICENSE
├── Procfile
├── README.md
├── dist
└── react-delayed.js
├── example
├── css
│ ├── default.scss
│ └── modal.scss
├── images
│ └── nyan.gif
├── index.html
├── js
│ ├── default.js
│ └── modal.js
└── server
│ └── default.js
├── package-lock.json
├── package.json
├── src
└── react-delayed.js
├── tests
├── helpers
│ └── browser-env.js
└── react-delayed.test.js
├── webpack.config.example.js
└── webpack.config.release.js
/.babelrc:
--------------------------------------------------------------------------------
1 | {
2 | "presets": ["es2015", "stage-0", "react"]
3 | }
4 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # os
2 | .DS_Store
3 |
4 | # ide
5 | .idea
6 |
7 | # npm
8 | node_modules
9 | npm-debug.log
10 | yarn.lock
11 |
12 | # example
13 | example/js/build.js
14 | example/css/default.css
15 |
16 | # coverage
17 | coverage
18 | .nyc_output
19 |
--------------------------------------------------------------------------------
/.travis.yml:
--------------------------------------------------------------------------------
1 | language: node_js
2 | node_js: stable
3 |
4 | after_success:
5 | - ./node_modules/.bin/nyc report --reporter=text-lcov | ./node_modules/.bin/coveralls
6 |
7 | script:
8 | - npm install
9 | - npm test
10 | - npm run build
11 |
12 | deploy:
13 | provider: heroku
14 | api_key:
15 | secure: RtWvyS5xmLYIEjG7fmYbrnvx2zScs8ryDMkHyar52CwlSloPfH+TlF9thuIWgNbUQTXF5xWi/moKY2Dm4i2ojXXI15pgOviuQGVUm4ZoAaKClZIrA9kjW/q+srU8hGKlwVAywtV0TMIZN4F8JZZ5fiQLjamJnDHrbxZ2/dNs1kkV7D6hJhmLh6RMe+gCSlfnttZwV1/Ed0PJbIV5n0PDYBFCwqqCfLLWG9M4A2MN9l9gtsHenbZBF7NTw95frSHv8TjIZrMejsi4NEC8vQ0WyvbIzW/JIkteitkhB4H2BRw70pByWF0gI04W4sNxBIAQbMTUARViZDQt2qHsiv6zCy0zztlf6oNbbgciZea8OFopZCvnodGvkFo5klIG3yAsJifMY75/b7SJYIieLWba8BW5aK+UyEjec8BMN5m4KjQFyjVA0i94hjiEvHguKcsPEzZStjGWpX9Sg+oo3327Sdf4XOzjm/1aCOVX/wG37mePIcRoDrils2H+1kFRxHbqheoGUfj+EzhSEVNunKML7x+eLJVY8tp+2lIO9xrRDNkRW4UeRxYnYDhVFcX4w00D6nQI6u3P1YfP+pdG88p6YpVqu5Z3O1lRM/8CtwzshvZKtB8odUNCWIMUAcP4DMbVNdYF02PzD1ZBlFhTVb8pzdYpnXtp2segTvXssobnaZQ=
16 | app: react-delayed
17 | on:
18 | repo: Wildhoney/ReactDelayed
19 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2017 Adam Timberlake
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/Procfile:
--------------------------------------------------------------------------------
1 | web: npm run start
2 |
3 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # React Delayed
2 |
3 | > Small component for delaying the mounting and unmounting of a child component for CSS animation purposes.
4 |
5 | 
6 |
7 | 
8 |
9 | 
10 |
11 | 
12 |
13 | * **npm**: `npm i react-delayed --save`
14 | * **Heroku**: [http://react-delayed.herokuapp.com/](http://react-delayed.herokuapp.com/)
15 |
16 | ---
17 |
18 | ## Getting Started
19 |
20 | Use the optional `mountAfter` and `unmountAfter` props for delaying the mounting and unmounting of nested components.
21 |
22 | ```javascript
23 |
24 |
25 |
26 | ```
27 |
28 | When `mounted` is `false` a dummy node will be rendered, which defaults to `span` and can be changed with the `nodeName` prop.
29 |
30 | You're also able to pass a *thunk* as the `children` for truly deferred components.
31 |
32 | ```javascript
33 |
34 | {() =>
}
35 |
36 | ```
37 |
--------------------------------------------------------------------------------
/dist/react-delayed.js:
--------------------------------------------------------------------------------
1 | module.exports =
2 | /******/ (function(modules) { // webpackBootstrap
3 | /******/ // The module cache
4 | /******/ var installedModules = {};
5 | /******/
6 | /******/ // The require function
7 | /******/ function __webpack_require__(moduleId) {
8 | /******/
9 | /******/ // Check if module is in cache
10 | /******/ if(installedModules[moduleId])
11 | /******/ return installedModules[moduleId].exports;
12 | /******/
13 | /******/ // Create a new module (and put it into the cache)
14 | /******/ var module = installedModules[moduleId] = {
15 | /******/ i: moduleId,
16 | /******/ l: false,
17 | /******/ exports: {}
18 | /******/ };
19 | /******/
20 | /******/ // Execute the module function
21 | /******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
22 | /******/
23 | /******/ // Flag the module as loaded
24 | /******/ module.l = true;
25 | /******/
26 | /******/ // Return the exports of the module
27 | /******/ return module.exports;
28 | /******/ }
29 | /******/
30 | /******/
31 | /******/ // expose the modules object (__webpack_modules__)
32 | /******/ __webpack_require__.m = modules;
33 | /******/
34 | /******/ // expose the module cache
35 | /******/ __webpack_require__.c = installedModules;
36 | /******/
37 | /******/ // identity function for calling harmony imports with the correct context
38 | /******/ __webpack_require__.i = function(value) { return value; };
39 | /******/
40 | /******/ // define getter function for harmony exports
41 | /******/ __webpack_require__.d = function(exports, name, getter) {
42 | /******/ if(!__webpack_require__.o(exports, name)) {
43 | /******/ Object.defineProperty(exports, name, {
44 | /******/ configurable: false,
45 | /******/ enumerable: true,
46 | /******/ get: getter
47 | /******/ });
48 | /******/ }
49 | /******/ };
50 | /******/
51 | /******/ // getDefaultExport function for compatibility with non-harmony modules
52 | /******/ __webpack_require__.n = function(module) {
53 | /******/ var getter = module && module.__esModule ?
54 | /******/ function getDefault() { return module['default']; } :
55 | /******/ function getModuleExports() { return module; };
56 | /******/ __webpack_require__.d(getter, 'a', getter);
57 | /******/ return getter;
58 | /******/ };
59 | /******/
60 | /******/ // Object.prototype.hasOwnProperty.call
61 | /******/ __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
62 | /******/
63 | /******/ // __webpack_public_path__
64 | /******/ __webpack_require__.p = "";
65 | /******/
66 | /******/ // Load entry module and return exports
67 | /******/ return __webpack_require__(__webpack_require__.s = 10);
68 | /******/ })
69 | /************************************************************************/
70 | /******/ ([
71 | /* 0 */
72 | /***/ (function(module, exports, __webpack_require__) {
73 |
74 | "use strict";
75 |
76 |
77 | // shim for using process in browser
78 | var process = module.exports = {};
79 |
80 | // cached from whatever global is present so that test runners that stub it
81 | // don't break things. But we need to wrap it in a try catch in case it is
82 | // wrapped in strict mode code which doesn't define any globals. It's inside a
83 | // function because try/catches deoptimize in certain engines.
84 |
85 | var cachedSetTimeout;
86 | var cachedClearTimeout;
87 |
88 | function defaultSetTimout() {
89 | throw new Error('setTimeout has not been defined');
90 | }
91 | function defaultClearTimeout() {
92 | throw new Error('clearTimeout has not been defined');
93 | }
94 | (function () {
95 | try {
96 | if (typeof setTimeout === 'function') {
97 | cachedSetTimeout = setTimeout;
98 | } else {
99 | cachedSetTimeout = defaultSetTimout;
100 | }
101 | } catch (e) {
102 | cachedSetTimeout = defaultSetTimout;
103 | }
104 | try {
105 | if (typeof clearTimeout === 'function') {
106 | cachedClearTimeout = clearTimeout;
107 | } else {
108 | cachedClearTimeout = defaultClearTimeout;
109 | }
110 | } catch (e) {
111 | cachedClearTimeout = defaultClearTimeout;
112 | }
113 | })();
114 | function runTimeout(fun) {
115 | if (cachedSetTimeout === setTimeout) {
116 | //normal enviroments in sane situations
117 | return setTimeout(fun, 0);
118 | }
119 | // if setTimeout wasn't available but was latter defined
120 | if ((cachedSetTimeout === defaultSetTimout || !cachedSetTimeout) && setTimeout) {
121 | cachedSetTimeout = setTimeout;
122 | return setTimeout(fun, 0);
123 | }
124 | try {
125 | // when when somebody has screwed with setTimeout but no I.E. maddness
126 | return cachedSetTimeout(fun, 0);
127 | } catch (e) {
128 | try {
129 | // When we are in I.E. but the script has been evaled so I.E. doesn't trust the global object when called normally
130 | return cachedSetTimeout.call(null, fun, 0);
131 | } catch (e) {
132 | // same as above but when it's a version of I.E. that must have the global object for 'this', hopfully our context correct otherwise it will throw a global error
133 | return cachedSetTimeout.call(this, fun, 0);
134 | }
135 | }
136 | }
137 | function runClearTimeout(marker) {
138 | if (cachedClearTimeout === clearTimeout) {
139 | //normal enviroments in sane situations
140 | return clearTimeout(marker);
141 | }
142 | // if clearTimeout wasn't available but was latter defined
143 | if ((cachedClearTimeout === defaultClearTimeout || !cachedClearTimeout) && clearTimeout) {
144 | cachedClearTimeout = clearTimeout;
145 | return clearTimeout(marker);
146 | }
147 | try {
148 | // when when somebody has screwed with setTimeout but no I.E. maddness
149 | return cachedClearTimeout(marker);
150 | } catch (e) {
151 | try {
152 | // When we are in I.E. but the script has been evaled so I.E. doesn't trust the global object when called normally
153 | return cachedClearTimeout.call(null, marker);
154 | } catch (e) {
155 | // same as above but when it's a version of I.E. that must have the global object for 'this', hopfully our context correct otherwise it will throw a global error.
156 | // Some versions of I.E. have different rules for clearTimeout vs setTimeout
157 | return cachedClearTimeout.call(this, marker);
158 | }
159 | }
160 | }
161 | var queue = [];
162 | var draining = false;
163 | var currentQueue;
164 | var queueIndex = -1;
165 |
166 | function cleanUpNextTick() {
167 | if (!draining || !currentQueue) {
168 | return;
169 | }
170 | draining = false;
171 | if (currentQueue.length) {
172 | queue = currentQueue.concat(queue);
173 | } else {
174 | queueIndex = -1;
175 | }
176 | if (queue.length) {
177 | drainQueue();
178 | }
179 | }
180 |
181 | function drainQueue() {
182 | if (draining) {
183 | return;
184 | }
185 | var timeout = runTimeout(cleanUpNextTick);
186 | draining = true;
187 |
188 | var len = queue.length;
189 | while (len) {
190 | currentQueue = queue;
191 | queue = [];
192 | while (++queueIndex < len) {
193 | if (currentQueue) {
194 | currentQueue[queueIndex].run();
195 | }
196 | }
197 | queueIndex = -1;
198 | len = queue.length;
199 | }
200 | currentQueue = null;
201 | draining = false;
202 | runClearTimeout(timeout);
203 | }
204 |
205 | process.nextTick = function (fun) {
206 | var args = new Array(arguments.length - 1);
207 | if (arguments.length > 1) {
208 | for (var i = 1; i < arguments.length; i++) {
209 | args[i - 1] = arguments[i];
210 | }
211 | }
212 | queue.push(new Item(fun, args));
213 | if (queue.length === 1 && !draining) {
214 | runTimeout(drainQueue);
215 | }
216 | };
217 |
218 | // v8 likes predictible objects
219 | function Item(fun, array) {
220 | this.fun = fun;
221 | this.array = array;
222 | }
223 | Item.prototype.run = function () {
224 | this.fun.apply(null, this.array);
225 | };
226 | process.title = 'browser';
227 | process.browser = true;
228 | process.env = {};
229 | process.argv = [];
230 | process.version = ''; // empty string to avoid regexp issues
231 | process.versions = {};
232 |
233 | function noop() {}
234 |
235 | process.on = noop;
236 | process.addListener = noop;
237 | process.once = noop;
238 | process.off = noop;
239 | process.removeListener = noop;
240 | process.removeAllListeners = noop;
241 | process.emit = noop;
242 | process.prependListener = noop;
243 | process.prependOnceListener = noop;
244 |
245 | process.listeners = function (name) {
246 | return [];
247 | };
248 |
249 | process.binding = function (name) {
250 | throw new Error('process.binding is not supported');
251 | };
252 |
253 | process.cwd = function () {
254 | return '/';
255 | };
256 | process.chdir = function (dir) {
257 | throw new Error('process.chdir is not supported');
258 | };
259 | process.umask = function () {
260 | return 0;
261 | };
262 |
263 | /***/ }),
264 | /* 1 */
265 | /***/ (function(module, exports, __webpack_require__) {
266 |
267 | "use strict";
268 |
269 |
270 | /**
271 | * Copyright (c) 2013-present, Facebook, Inc.
272 | *
273 | * This source code is licensed under the MIT license found in the
274 | * LICENSE file in the root directory of this source tree.
275 | *
276 | *
277 | */
278 |
279 | function makeEmptyFunction(arg) {
280 | return function () {
281 | return arg;
282 | };
283 | }
284 |
285 | /**
286 | * This function accepts and discards inputs; it has no side effects. This is
287 | * primarily useful idiomatically for overridable function endpoints which
288 | * always need to be callable, since JS lacks a null-call idiom ala Cocoa.
289 | */
290 | var emptyFunction = function emptyFunction() {};
291 |
292 | emptyFunction.thatReturns = makeEmptyFunction;
293 | emptyFunction.thatReturnsFalse = makeEmptyFunction(false);
294 | emptyFunction.thatReturnsTrue = makeEmptyFunction(true);
295 | emptyFunction.thatReturnsNull = makeEmptyFunction(null);
296 | emptyFunction.thatReturnsThis = function () {
297 | return this;
298 | };
299 | emptyFunction.thatReturnsArgument = function (arg) {
300 | return arg;
301 | };
302 |
303 | module.exports = emptyFunction;
304 |
305 | /***/ }),
306 | /* 2 */
307 | /***/ (function(module, exports, __webpack_require__) {
308 |
309 | "use strict";
310 | /* WEBPACK VAR INJECTION */(function(process) {/**
311 | * Copyright (c) 2013-present, Facebook, Inc.
312 | *
313 | * This source code is licensed under the MIT license found in the
314 | * LICENSE file in the root directory of this source tree.
315 | *
316 | */
317 |
318 |
319 |
320 | /**
321 | * Use invariant() to assert state which your program assumes to be true.
322 | *
323 | * Provide sprintf-style format (only %s is supported) and arguments
324 | * to provide information about what broke and what you were
325 | * expecting.
326 | *
327 | * The invariant message will be stripped in production, but the invariant
328 | * will remain to ensure logic does not differ in production.
329 | */
330 |
331 | var validateFormat = function validateFormat(format) {};
332 |
333 | if (process.env.NODE_ENV !== 'production') {
334 | validateFormat = function validateFormat(format) {
335 | if (format === undefined) {
336 | throw new Error('invariant requires an error message argument');
337 | }
338 | };
339 | }
340 |
341 | function invariant(condition, format, a, b, c, d, e, f) {
342 | validateFormat(format);
343 |
344 | if (!condition) {
345 | var error;
346 | if (format === undefined) {
347 | error = new Error('Minified exception occurred; use the non-minified dev environment ' + 'for the full error message and additional helpful warnings.');
348 | } else {
349 | var args = [a, b, c, d, e, f];
350 | var argIndex = 0;
351 | error = new Error(format.replace(/%s/g, function () {
352 | return args[argIndex++];
353 | }));
354 | error.name = 'Invariant Violation';
355 | }
356 |
357 | error.framesToPop = 1; // we don't care about invariant's own frame
358 | throw error;
359 | }
360 | }
361 |
362 | module.exports = invariant;
363 | /* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))
364 |
365 | /***/ }),
366 | /* 3 */
367 | /***/ (function(module, exports, __webpack_require__) {
368 |
369 | "use strict";
370 | /**
371 | * Copyright 2013-present, Facebook, Inc.
372 | * All rights reserved.
373 | *
374 | * This source code is licensed under the BSD-style license found in the
375 | * LICENSE file in the root directory of this source tree. An additional grant
376 | * of patent rights can be found in the PATENTS file in the same directory.
377 | */
378 |
379 |
380 |
381 | var ReactPropTypesSecret = 'SECRET_DO_NOT_PASS_THIS_OR_YOU_WILL_BE_FIRED';
382 |
383 | module.exports = ReactPropTypesSecret;
384 |
385 | /***/ }),
386 | /* 4 */
387 | /***/ (function(module, exports, __webpack_require__) {
388 |
389 | "use strict";
390 | /* WEBPACK VAR INJECTION */(function(process) {/**
391 | * Copyright (c) 2014-present, Facebook, Inc.
392 | *
393 | * This source code is licensed under the MIT license found in the
394 | * LICENSE file in the root directory of this source tree.
395 | *
396 | */
397 |
398 |
399 |
400 | var emptyFunction = __webpack_require__(1);
401 |
402 | /**
403 | * Similar to invariant but only logs a warning if the condition is not met.
404 | * This can be used to log issues in development environments in critical
405 | * paths. Removing the logging code for production environments will keep the
406 | * same logic and follow the same code paths.
407 | */
408 |
409 | var warning = emptyFunction;
410 |
411 | if (process.env.NODE_ENV !== 'production') {
412 | var printWarning = function printWarning(format) {
413 | for (var _len = arguments.length, args = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
414 | args[_key - 1] = arguments[_key];
415 | }
416 |
417 | var argIndex = 0;
418 | var message = 'Warning: ' + format.replace(/%s/g, function () {
419 | return args[argIndex++];
420 | });
421 | if (typeof console !== 'undefined') {
422 | console.error(message);
423 | }
424 | try {
425 | // --- Welcome to debugging React ---
426 | // This error was thrown as a convenience so that you can use this stack
427 | // to find the callsite that caused this warning to fire.
428 | throw new Error(message);
429 | } catch (x) {}
430 | };
431 |
432 | warning = function warning(condition, format) {
433 | if (format === undefined) {
434 | throw new Error('`warning(condition, format, ...args)` requires a warning ' + 'message argument');
435 | }
436 |
437 | if (format.indexOf('Failed Composite propType: ') === 0) {
438 | return; // Ignore CompositeComponent proptype check.
439 | }
440 |
441 | if (!condition) {
442 | for (var _len2 = arguments.length, args = Array(_len2 > 2 ? _len2 - 2 : 0), _key2 = 2; _key2 < _len2; _key2++) {
443 | args[_key2 - 2] = arguments[_key2];
444 | }
445 |
446 | printWarning.apply(undefined, [format].concat(args));
447 | }
448 | };
449 | }
450 |
451 | module.exports = warning;
452 | /* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))
453 |
454 | /***/ }),
455 | /* 5 */
456 | /***/ (function(module, exports, __webpack_require__) {
457 |
458 | "use strict";
459 | /* WEBPACK VAR INJECTION */(function(process) {
460 |
461 | var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };
462 |
463 | /**
464 | * Copyright 2013-present, Facebook, Inc.
465 | * All rights reserved.
466 | *
467 | * This source code is licensed under the BSD-style license found in the
468 | * LICENSE file in the root directory of this source tree. An additional grant
469 | * of patent rights can be found in the PATENTS file in the same directory.
470 | */
471 |
472 | if (process.env.NODE_ENV !== 'production') {
473 | var REACT_ELEMENT_TYPE = typeof Symbol === 'function' && Symbol.for && Symbol.for('react.element') || 0xeac7;
474 |
475 | var isValidElement = function isValidElement(object) {
476 | return (typeof object === 'undefined' ? 'undefined' : _typeof(object)) === 'object' && object !== null && object.$$typeof === REACT_ELEMENT_TYPE;
477 | };
478 |
479 | // By explicitly using `prop-types` you are opting into new development behavior.
480 | // http://fb.me/prop-types-in-prod
481 | var throwOnDirectAccess = true;
482 | module.exports = __webpack_require__(9)(isValidElement, throwOnDirectAccess);
483 | } else {
484 | // By explicitly using `prop-types` you are opting into new production behavior.
485 | // http://fb.me/prop-types-in-prod
486 | module.exports = __webpack_require__(8)();
487 | }
488 | /* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))
489 |
490 | /***/ }),
491 | /* 6 */
492 | /***/ (function(module, exports) {
493 |
494 | module.exports = require("react");
495 |
496 | /***/ }),
497 | /* 7 */
498 | /***/ (function(module, exports, __webpack_require__) {
499 |
500 | "use strict";
501 | /* WEBPACK VAR INJECTION */(function(process) {/**
502 | * Copyright 2013-present, Facebook, Inc.
503 | * All rights reserved.
504 | *
505 | * This source code is licensed under the BSD-style license found in the
506 | * LICENSE file in the root directory of this source tree. An additional grant
507 | * of patent rights can be found in the PATENTS file in the same directory.
508 | */
509 |
510 |
511 |
512 | var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };
513 |
514 | if (process.env.NODE_ENV !== 'production') {
515 | var invariant = __webpack_require__(2);
516 | var warning = __webpack_require__(4);
517 | var ReactPropTypesSecret = __webpack_require__(3);
518 | var loggedTypeFailures = {};
519 | }
520 |
521 | /**
522 | * Assert that the values match with the type specs.
523 | * Error messages are memorized and will only be shown once.
524 | *
525 | * @param {object} typeSpecs Map of name to a ReactPropType
526 | * @param {object} values Runtime values that need to be type-checked
527 | * @param {string} location e.g. "prop", "context", "child context"
528 | * @param {string} componentName Name of the component for error messages.
529 | * @param {?Function} getStack Returns the component stack.
530 | * @private
531 | */
532 | function checkPropTypes(typeSpecs, values, location, componentName, getStack) {
533 | if (process.env.NODE_ENV !== 'production') {
534 | for (var typeSpecName in typeSpecs) {
535 | if (typeSpecs.hasOwnProperty(typeSpecName)) {
536 | var error;
537 | // Prop type validation may throw. In case they do, we don't want to
538 | // fail the render phase where it didn't fail before. So we log it.
539 | // After these have been cleaned up, we'll let them throw.
540 | try {
541 | // This is intentionally an invariant that gets caught. It's the same
542 | // behavior as without this statement except with a better message.
543 | invariant(typeof typeSpecs[typeSpecName] === 'function', '%s: %s type `%s` is invalid; it must be a function, usually from ' + 'React.PropTypes.', componentName || 'React class', location, typeSpecName);
544 | error = typeSpecs[typeSpecName](values, typeSpecName, componentName, location, null, ReactPropTypesSecret);
545 | } catch (ex) {
546 | error = ex;
547 | }
548 | warning(!error || error instanceof Error, '%s: type specification of %s `%s` is invalid; the type checker ' + 'function must return `null` or an `Error` but returned a %s. ' + 'You may have forgotten to pass an argument to the type checker ' + 'creator (arrayOf, instanceOf, objectOf, oneOf, oneOfType, and ' + 'shape all require an argument).', componentName || 'React class', location, typeSpecName, typeof error === 'undefined' ? 'undefined' : _typeof(error));
549 | if (error instanceof Error && !(error.message in loggedTypeFailures)) {
550 | // Only monitor this failure once because there tends to be a lot of the
551 | // same error.
552 | loggedTypeFailures[error.message] = true;
553 |
554 | var stack = getStack ? getStack() : '';
555 |
556 | warning(false, 'Failed %s type: %s%s', location, error.message, stack != null ? stack : '');
557 | }
558 | }
559 | }
560 | }
561 | }
562 |
563 | module.exports = checkPropTypes;
564 | /* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))
565 |
566 | /***/ }),
567 | /* 8 */
568 | /***/ (function(module, exports, __webpack_require__) {
569 |
570 | "use strict";
571 | /**
572 | * Copyright 2013-present, Facebook, Inc.
573 | * All rights reserved.
574 | *
575 | * This source code is licensed under the BSD-style license found in the
576 | * LICENSE file in the root directory of this source tree. An additional grant
577 | * of patent rights can be found in the PATENTS file in the same directory.
578 | */
579 |
580 |
581 |
582 | var emptyFunction = __webpack_require__(1);
583 | var invariant = __webpack_require__(2);
584 | var ReactPropTypesSecret = __webpack_require__(3);
585 |
586 | module.exports = function () {
587 | function shim(props, propName, componentName, location, propFullName, secret) {
588 | if (secret === ReactPropTypesSecret) {
589 | // It is still safe when called from React.
590 | return;
591 | }
592 | invariant(false, 'Calling PropTypes validators directly is not supported by the `prop-types` package. ' + 'Use PropTypes.checkPropTypes() to call them. ' + 'Read more at http://fb.me/use-check-prop-types');
593 | };
594 | shim.isRequired = shim;
595 | function getShim() {
596 | return shim;
597 | };
598 | // Important!
599 | // Keep this list in sync with production version in `./factoryWithTypeCheckers.js`.
600 | var ReactPropTypes = {
601 | array: shim,
602 | bool: shim,
603 | func: shim,
604 | number: shim,
605 | object: shim,
606 | string: shim,
607 | symbol: shim,
608 |
609 | any: shim,
610 | arrayOf: getShim,
611 | element: shim,
612 | instanceOf: getShim,
613 | node: shim,
614 | objectOf: getShim,
615 | oneOf: getShim,
616 | oneOfType: getShim,
617 | shape: getShim
618 | };
619 |
620 | ReactPropTypes.checkPropTypes = emptyFunction;
621 | ReactPropTypes.PropTypes = ReactPropTypes;
622 |
623 | return ReactPropTypes;
624 | };
625 |
626 | /***/ }),
627 | /* 9 */
628 | /***/ (function(module, exports, __webpack_require__) {
629 |
630 | "use strict";
631 | /* WEBPACK VAR INJECTION */(function(process) {/**
632 | * Copyright 2013-present, Facebook, Inc.
633 | * All rights reserved.
634 | *
635 | * This source code is licensed under the BSD-style license found in the
636 | * LICENSE file in the root directory of this source tree. An additional grant
637 | * of patent rights can be found in the PATENTS file in the same directory.
638 | */
639 |
640 |
641 |
642 | var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };
643 |
644 | var emptyFunction = __webpack_require__(1);
645 | var invariant = __webpack_require__(2);
646 | var warning = __webpack_require__(4);
647 |
648 | var ReactPropTypesSecret = __webpack_require__(3);
649 | var checkPropTypes = __webpack_require__(7);
650 |
651 | module.exports = function (isValidElement, throwOnDirectAccess) {
652 | /* global Symbol */
653 | var ITERATOR_SYMBOL = typeof Symbol === 'function' && Symbol.iterator;
654 | var FAUX_ITERATOR_SYMBOL = '@@iterator'; // Before Symbol spec.
655 |
656 | /**
657 | * Returns the iterator method function contained on the iterable object.
658 | *
659 | * Be sure to invoke the function with the iterable as context:
660 | *
661 | * var iteratorFn = getIteratorFn(myIterable);
662 | * if (iteratorFn) {
663 | * var iterator = iteratorFn.call(myIterable);
664 | * ...
665 | * }
666 | *
667 | * @param {?object} maybeIterable
668 | * @return {?function}
669 | */
670 | function getIteratorFn(maybeIterable) {
671 | var iteratorFn = maybeIterable && (ITERATOR_SYMBOL && maybeIterable[ITERATOR_SYMBOL] || maybeIterable[FAUX_ITERATOR_SYMBOL]);
672 | if (typeof iteratorFn === 'function') {
673 | return iteratorFn;
674 | }
675 | }
676 |
677 | /**
678 | * Collection of methods that allow declaration and validation of props that are
679 | * supplied to React components. Example usage:
680 | *
681 | * var Props = require('ReactPropTypes');
682 | * var MyArticle = React.createClass({
683 | * propTypes: {
684 | * // An optional string prop named "description".
685 | * description: Props.string,
686 | *
687 | * // A required enum prop named "category".
688 | * category: Props.oneOf(['News','Photos']).isRequired,
689 | *
690 | * // A prop named "dialog" that requires an instance of Dialog.
691 | * dialog: Props.instanceOf(Dialog).isRequired
692 | * },
693 | * render: function() { ... }
694 | * });
695 | *
696 | * A more formal specification of how these methods are used:
697 | *
698 | * type := array|bool|func|object|number|string|oneOf([...])|instanceOf(...)
699 | * decl := ReactPropTypes.{type}(.isRequired)?
700 | *
701 | * Each and every declaration produces a function with the same signature. This
702 | * allows the creation of custom validation functions. For example:
703 | *
704 | * var MyLink = React.createClass({
705 | * propTypes: {
706 | * // An optional string or URI prop named "href".
707 | * href: function(props, propName, componentName) {
708 | * var propValue = props[propName];
709 | * if (propValue != null && typeof propValue !== 'string' &&
710 | * !(propValue instanceof URI)) {
711 | * return new Error(
712 | * 'Expected a string or an URI for ' + propName + ' in ' +
713 | * componentName
714 | * );
715 | * }
716 | * }
717 | * },
718 | * render: function() {...}
719 | * });
720 | *
721 | * @internal
722 | */
723 |
724 | var ANONYMOUS = '<>';
725 |
726 | // Important!
727 | // Keep this list in sync with production version in `./factoryWithThrowingShims.js`.
728 | var ReactPropTypes = {
729 | array: createPrimitiveTypeChecker('array'),
730 | bool: createPrimitiveTypeChecker('boolean'),
731 | func: createPrimitiveTypeChecker('function'),
732 | number: createPrimitiveTypeChecker('number'),
733 | object: createPrimitiveTypeChecker('object'),
734 | string: createPrimitiveTypeChecker('string'),
735 | symbol: createPrimitiveTypeChecker('symbol'),
736 |
737 | any: createAnyTypeChecker(),
738 | arrayOf: createArrayOfTypeChecker,
739 | element: createElementTypeChecker(),
740 | instanceOf: createInstanceTypeChecker,
741 | node: createNodeChecker(),
742 | objectOf: createObjectOfTypeChecker,
743 | oneOf: createEnumTypeChecker,
744 | oneOfType: createUnionTypeChecker,
745 | shape: createShapeTypeChecker
746 | };
747 |
748 | /**
749 | * inlined Object.is polyfill to avoid requiring consumers ship their own
750 | * https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
751 | */
752 | /*eslint-disable no-self-compare*/
753 | function is(x, y) {
754 | // SameValue algorithm
755 | if (x === y) {
756 | // Steps 1-5, 7-10
757 | // Steps 6.b-6.e: +0 != -0
758 | return x !== 0 || 1 / x === 1 / y;
759 | } else {
760 | // Step 6.a: NaN == NaN
761 | return x !== x && y !== y;
762 | }
763 | }
764 | /*eslint-enable no-self-compare*/
765 |
766 | /**
767 | * We use an Error-like object for backward compatibility as people may call
768 | * PropTypes directly and inspect their output. However, we don't use real
769 | * Errors anymore. We don't inspect their stack anyway, and creating them
770 | * is prohibitively expensive if they are created too often, such as what
771 | * happens in oneOfType() for any type before the one that matched.
772 | */
773 | function PropTypeError(message) {
774 | this.message = message;
775 | this.stack = '';
776 | }
777 | // Make `instanceof Error` still work for returned errors.
778 | PropTypeError.prototype = Error.prototype;
779 |
780 | function createChainableTypeChecker(validate) {
781 | if (process.env.NODE_ENV !== 'production') {
782 | var manualPropTypeCallCache = {};
783 | var manualPropTypeWarningCount = 0;
784 | }
785 | function checkType(isRequired, props, propName, componentName, location, propFullName, secret) {
786 | componentName = componentName || ANONYMOUS;
787 | propFullName = propFullName || propName;
788 |
789 | if (secret !== ReactPropTypesSecret) {
790 | if (throwOnDirectAccess) {
791 | // New behavior only for users of `prop-types` package
792 | invariant(false, 'Calling PropTypes validators directly is not supported by the `prop-types` package. ' + 'Use `PropTypes.checkPropTypes()` to call them. ' + 'Read more at http://fb.me/use-check-prop-types');
793 | } else if (process.env.NODE_ENV !== 'production' && typeof console !== 'undefined') {
794 | // Old behavior for people using React.PropTypes
795 | var cacheKey = componentName + ':' + propName;
796 | if (!manualPropTypeCallCache[cacheKey] &&
797 | // Avoid spamming the console because they are often not actionable except for lib authors
798 | manualPropTypeWarningCount < 3) {
799 | warning(false, 'You are manually calling a React.PropTypes validation ' + 'function for the `%s` prop on `%s`. This is deprecated ' + 'and will throw in the standalone `prop-types` package. ' + 'You may be seeing this warning due to a third-party PropTypes ' + 'library. See https://fb.me/react-warning-dont-call-proptypes ' + 'for details.', propFullName, componentName);
800 | manualPropTypeCallCache[cacheKey] = true;
801 | manualPropTypeWarningCount++;
802 | }
803 | }
804 | }
805 | if (props[propName] == null) {
806 | if (isRequired) {
807 | if (props[propName] === null) {
808 | return new PropTypeError('The ' + location + ' `' + propFullName + '` is marked as required ' + ('in `' + componentName + '`, but its value is `null`.'));
809 | }
810 | return new PropTypeError('The ' + location + ' `' + propFullName + '` is marked as required in ' + ('`' + componentName + '`, but its value is `undefined`.'));
811 | }
812 | return null;
813 | } else {
814 | return validate(props, propName, componentName, location, propFullName);
815 | }
816 | }
817 |
818 | var chainedCheckType = checkType.bind(null, false);
819 | chainedCheckType.isRequired = checkType.bind(null, true);
820 |
821 | return chainedCheckType;
822 | }
823 |
824 | function createPrimitiveTypeChecker(expectedType) {
825 | function validate(props, propName, componentName, location, propFullName, secret) {
826 | var propValue = props[propName];
827 | var propType = getPropType(propValue);
828 | if (propType !== expectedType) {
829 | // `propValue` being instance of, say, date/regexp, pass the 'object'
830 | // check, but we can offer a more precise error message here rather than
831 | // 'of type `object`'.
832 | var preciseType = getPreciseType(propValue);
833 |
834 | return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + preciseType + '` supplied to `' + componentName + '`, expected ') + ('`' + expectedType + '`.'));
835 | }
836 | return null;
837 | }
838 | return createChainableTypeChecker(validate);
839 | }
840 |
841 | function createAnyTypeChecker() {
842 | return createChainableTypeChecker(emptyFunction.thatReturnsNull);
843 | }
844 |
845 | function createArrayOfTypeChecker(typeChecker) {
846 | function validate(props, propName, componentName, location, propFullName) {
847 | if (typeof typeChecker !== 'function') {
848 | return new PropTypeError('Property `' + propFullName + '` of component `' + componentName + '` has invalid PropType notation inside arrayOf.');
849 | }
850 | var propValue = props[propName];
851 | if (!Array.isArray(propValue)) {
852 | var propType = getPropType(propValue);
853 | return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + propType + '` supplied to `' + componentName + '`, expected an array.'));
854 | }
855 | for (var i = 0; i < propValue.length; i++) {
856 | var error = typeChecker(propValue, i, componentName, location, propFullName + '[' + i + ']', ReactPropTypesSecret);
857 | if (error instanceof Error) {
858 | return error;
859 | }
860 | }
861 | return null;
862 | }
863 | return createChainableTypeChecker(validate);
864 | }
865 |
866 | function createElementTypeChecker() {
867 | function validate(props, propName, componentName, location, propFullName) {
868 | var propValue = props[propName];
869 | if (!isValidElement(propValue)) {
870 | var propType = getPropType(propValue);
871 | return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + propType + '` supplied to `' + componentName + '`, expected a single ReactElement.'));
872 | }
873 | return null;
874 | }
875 | return createChainableTypeChecker(validate);
876 | }
877 |
878 | function createInstanceTypeChecker(expectedClass) {
879 | function validate(props, propName, componentName, location, propFullName) {
880 | if (!(props[propName] instanceof expectedClass)) {
881 | var expectedClassName = expectedClass.name || ANONYMOUS;
882 | var actualClassName = getClassName(props[propName]);
883 | return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + actualClassName + '` supplied to `' + componentName + '`, expected ') + ('instance of `' + expectedClassName + '`.'));
884 | }
885 | return null;
886 | }
887 | return createChainableTypeChecker(validate);
888 | }
889 |
890 | function createEnumTypeChecker(expectedValues) {
891 | if (!Array.isArray(expectedValues)) {
892 | process.env.NODE_ENV !== 'production' ? warning(false, 'Invalid argument supplied to oneOf, expected an instance of array.') : void 0;
893 | return emptyFunction.thatReturnsNull;
894 | }
895 |
896 | function validate(props, propName, componentName, location, propFullName) {
897 | var propValue = props[propName];
898 | for (var i = 0; i < expectedValues.length; i++) {
899 | if (is(propValue, expectedValues[i])) {
900 | return null;
901 | }
902 | }
903 |
904 | var valuesString = JSON.stringify(expectedValues);
905 | return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of value `' + propValue + '` ' + ('supplied to `' + componentName + '`, expected one of ' + valuesString + '.'));
906 | }
907 | return createChainableTypeChecker(validate);
908 | }
909 |
910 | function createObjectOfTypeChecker(typeChecker) {
911 | function validate(props, propName, componentName, location, propFullName) {
912 | if (typeof typeChecker !== 'function') {
913 | return new PropTypeError('Property `' + propFullName + '` of component `' + componentName + '` has invalid PropType notation inside objectOf.');
914 | }
915 | var propValue = props[propName];
916 | var propType = getPropType(propValue);
917 | if (propType !== 'object') {
918 | return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + propType + '` supplied to `' + componentName + '`, expected an object.'));
919 | }
920 | for (var key in propValue) {
921 | if (propValue.hasOwnProperty(key)) {
922 | var error = typeChecker(propValue, key, componentName, location, propFullName + '.' + key, ReactPropTypesSecret);
923 | if (error instanceof Error) {
924 | return error;
925 | }
926 | }
927 | }
928 | return null;
929 | }
930 | return createChainableTypeChecker(validate);
931 | }
932 |
933 | function createUnionTypeChecker(arrayOfTypeCheckers) {
934 | if (!Array.isArray(arrayOfTypeCheckers)) {
935 | process.env.NODE_ENV !== 'production' ? warning(false, 'Invalid argument supplied to oneOfType, expected an instance of array.') : void 0;
936 | return emptyFunction.thatReturnsNull;
937 | }
938 |
939 | for (var i = 0; i < arrayOfTypeCheckers.length; i++) {
940 | var checker = arrayOfTypeCheckers[i];
941 | if (typeof checker !== 'function') {
942 | warning(false, 'Invalid argument supplid to oneOfType. Expected an array of check functions, but ' + 'received %s at index %s.', getPostfixForTypeWarning(checker), i);
943 | return emptyFunction.thatReturnsNull;
944 | }
945 | }
946 |
947 | function validate(props, propName, componentName, location, propFullName) {
948 | for (var i = 0; i < arrayOfTypeCheckers.length; i++) {
949 | var checker = arrayOfTypeCheckers[i];
950 | if (checker(props, propName, componentName, location, propFullName, ReactPropTypesSecret) == null) {
951 | return null;
952 | }
953 | }
954 |
955 | return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` supplied to ' + ('`' + componentName + '`.'));
956 | }
957 | return createChainableTypeChecker(validate);
958 | }
959 |
960 | function createNodeChecker() {
961 | function validate(props, propName, componentName, location, propFullName) {
962 | if (!isNode(props[propName])) {
963 | return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` supplied to ' + ('`' + componentName + '`, expected a ReactNode.'));
964 | }
965 | return null;
966 | }
967 | return createChainableTypeChecker(validate);
968 | }
969 |
970 | function createShapeTypeChecker(shapeTypes) {
971 | function validate(props, propName, componentName, location, propFullName) {
972 | var propValue = props[propName];
973 | var propType = getPropType(propValue);
974 | if (propType !== 'object') {
975 | return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type `' + propType + '` ' + ('supplied to `' + componentName + '`, expected `object`.'));
976 | }
977 | for (var key in shapeTypes) {
978 | var checker = shapeTypes[key];
979 | if (!checker) {
980 | continue;
981 | }
982 | var error = checker(propValue, key, componentName, location, propFullName + '.' + key, ReactPropTypesSecret);
983 | if (error) {
984 | return error;
985 | }
986 | }
987 | return null;
988 | }
989 | return createChainableTypeChecker(validate);
990 | }
991 |
992 | function isNode(propValue) {
993 | switch (typeof propValue === 'undefined' ? 'undefined' : _typeof(propValue)) {
994 | case 'number':
995 | case 'string':
996 | case 'undefined':
997 | return true;
998 | case 'boolean':
999 | return !propValue;
1000 | case 'object':
1001 | if (Array.isArray(propValue)) {
1002 | return propValue.every(isNode);
1003 | }
1004 | if (propValue === null || isValidElement(propValue)) {
1005 | return true;
1006 | }
1007 |
1008 | var iteratorFn = getIteratorFn(propValue);
1009 | if (iteratorFn) {
1010 | var iterator = iteratorFn.call(propValue);
1011 | var step;
1012 | if (iteratorFn !== propValue.entries) {
1013 | while (!(step = iterator.next()).done) {
1014 | if (!isNode(step.value)) {
1015 | return false;
1016 | }
1017 | }
1018 | } else {
1019 | // Iterator will provide entry [k,v] tuples rather than values.
1020 | while (!(step = iterator.next()).done) {
1021 | var entry = step.value;
1022 | if (entry) {
1023 | if (!isNode(entry[1])) {
1024 | return false;
1025 | }
1026 | }
1027 | }
1028 | }
1029 | } else {
1030 | return false;
1031 | }
1032 |
1033 | return true;
1034 | default:
1035 | return false;
1036 | }
1037 | }
1038 |
1039 | function isSymbol(propType, propValue) {
1040 | // Native Symbol.
1041 | if (propType === 'symbol') {
1042 | return true;
1043 | }
1044 |
1045 | // 19.4.3.5 Symbol.prototype[@@toStringTag] === 'Symbol'
1046 | if (propValue['@@toStringTag'] === 'Symbol') {
1047 | return true;
1048 | }
1049 |
1050 | // Fallback for non-spec compliant Symbols which are polyfilled.
1051 | if (typeof Symbol === 'function' && propValue instanceof Symbol) {
1052 | return true;
1053 | }
1054 |
1055 | return false;
1056 | }
1057 |
1058 | // Equivalent of `typeof` but with special handling for array and regexp.
1059 | function getPropType(propValue) {
1060 | var propType = typeof propValue === 'undefined' ? 'undefined' : _typeof(propValue);
1061 | if (Array.isArray(propValue)) {
1062 | return 'array';
1063 | }
1064 | if (propValue instanceof RegExp) {
1065 | // Old webkits (at least until Android 4.0) return 'function' rather than
1066 | // 'object' for typeof a RegExp. We'll normalize this here so that /bla/
1067 | // passes PropTypes.object.
1068 | return 'object';
1069 | }
1070 | if (isSymbol(propType, propValue)) {
1071 | return 'symbol';
1072 | }
1073 | return propType;
1074 | }
1075 |
1076 | // This handles more types than `getPropType`. Only used for error messages.
1077 | // See `createPrimitiveTypeChecker`.
1078 | function getPreciseType(propValue) {
1079 | if (typeof propValue === 'undefined' || propValue === null) {
1080 | return '' + propValue;
1081 | }
1082 | var propType = getPropType(propValue);
1083 | if (propType === 'object') {
1084 | if (propValue instanceof Date) {
1085 | return 'date';
1086 | } else if (propValue instanceof RegExp) {
1087 | return 'regexp';
1088 | }
1089 | }
1090 | return propType;
1091 | }
1092 |
1093 | // Returns a string that is postfixed to a warning about an invalid type.
1094 | // For example, "undefined" or "of type array"
1095 | function getPostfixForTypeWarning(value) {
1096 | var type = getPreciseType(value);
1097 | switch (type) {
1098 | case 'array':
1099 | case 'object':
1100 | return 'an ' + type;
1101 | case 'boolean':
1102 | case 'date':
1103 | case 'regexp':
1104 | return 'a ' + type;
1105 | default:
1106 | return type;
1107 | }
1108 | }
1109 |
1110 | // Returns class name of the object, if any.
1111 | function getClassName(propValue) {
1112 | if (!propValue.constructor || !propValue.constructor.name) {
1113 | return ANONYMOUS;
1114 | }
1115 | return propValue.constructor.name;
1116 | }
1117 |
1118 | ReactPropTypes.checkPropTypes = checkPropTypes;
1119 | ReactPropTypes.PropTypes = ReactPropTypes;
1120 |
1121 | return ReactPropTypes;
1122 | };
1123 | /* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))
1124 |
1125 | /***/ }),
1126 | /* 10 */
1127 | /***/ (function(module, exports, __webpack_require__) {
1128 |
1129 | "use strict";
1130 |
1131 |
1132 | Object.defineProperty(exports, "__esModule", {
1133 | value: true
1134 | });
1135 |
1136 | var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
1137 |
1138 | var _react = __webpack_require__(6);
1139 |
1140 | var _react2 = _interopRequireDefault(_react);
1141 |
1142 | var _propTypes = __webpack_require__(5);
1143 |
1144 | var _propTypes2 = _interopRequireDefault(_propTypes);
1145 |
1146 | function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
1147 |
1148 | function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
1149 |
1150 | function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
1151 |
1152 | function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
1153 |
1154 | /**
1155 | * @constant types
1156 | * @type {{mount: string, unmounted: string}}
1157 | */
1158 | var types = {
1159 | MOUNT: 'mount',
1160 | UNMOUNT: 'unmount'
1161 | };
1162 |
1163 | /**
1164 | * @class ReactDelayed
1165 | * @extends {Component}
1166 | */
1167 |
1168 | var ReactDelayed = function (_Component) {
1169 | _inherits(ReactDelayed, _Component);
1170 |
1171 | function ReactDelayed() {
1172 | var _ref;
1173 |
1174 | var _temp, _this, _ret;
1175 |
1176 | _classCallCheck(this, ReactDelayed);
1177 |
1178 | for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) {
1179 | args[_key] = arguments[_key];
1180 | }
1181 |
1182 | return _ret = (_temp = (_this = _possibleConstructorReturn(this, (_ref = ReactDelayed.__proto__ || Object.getPrototypeOf(ReactDelayed)).call.apply(_ref, [this].concat(args))), _this), _this.state = { mounted: typeof window === 'undefined' ? _this.props.mounted : false, deferred: null }, _temp), _possibleConstructorReturn(_this, _ret);
1183 | }
1184 |
1185 | /**
1186 | * @constant state
1187 | * @type {{mounted: boolean}}
1188 | */
1189 |
1190 |
1191 | /**
1192 | * @constant propTypes
1193 | * @type {{mountAfter: function, unmountAfter: function}}
1194 | */
1195 |
1196 |
1197 | /**
1198 | * @constant defaultProps
1199 | * @type {{mountAfter: number, unmountAfter: number}}
1200 | */
1201 |
1202 |
1203 | _createClass(ReactDelayed, [{
1204 | key: 'componentDidMount',
1205 |
1206 |
1207 | /**
1208 | * @method componentDidMount
1209 | * @return {void}
1210 | */
1211 | value: function componentDidMount() {
1212 | this.isComponentMounted = true;
1213 | this.props.mounted === true && this.handleVisibility(types.MOUNT);
1214 | }
1215 |
1216 | /**
1217 | * @method componentWillUnmount
1218 | * @return {void}
1219 | */
1220 |
1221 | }, {
1222 | key: 'componentWillUnmount',
1223 | value: function componentWillUnmount() {
1224 | this.isComponentMounted = false;
1225 | }
1226 |
1227 | /**
1228 | * @method componentWillReceiveProps
1229 | * @param {Object} nextProps
1230 | * @return {void}
1231 | */
1232 |
1233 | }, {
1234 | key: 'componentWillReceiveProps',
1235 | value: function componentWillReceiveProps(nextProps) {
1236 | this.props.mounted === false && nextProps.mounted === true && this.handleVisibility(types.MOUNT);
1237 | this.props.mounted === true && nextProps.mounted === false && this.handleVisibility(types.UNMOUNT);
1238 | }
1239 |
1240 | /**
1241 | * @method handleVisibility
1242 | * @param {String} type
1243 | * @return {void}
1244 | */
1245 |
1246 | }, {
1247 | key: 'handleVisibility',
1248 | value: function handleVisibility(type) {
1249 | var _this2 = this;
1250 |
1251 | var mounted = type === types.MOUNT;
1252 | var timeout = this.props[type + 'After'];
1253 | var invoker = timeout === 0 ? function (fn) {
1254 | return fn();
1255 | } : setTimeout;
1256 |
1257 | clearTimeout(this.state.deferred);
1258 | var deferred = invoker(function () {
1259 | return _this2.isComponentMounted && _this2.setState({ mounted: mounted });
1260 | }, timeout);
1261 | this.setState({ deferred: deferred });
1262 | }
1263 |
1264 | /**
1265 | * @method render
1266 | * @return {XML}
1267 | */
1268 |
1269 | }, {
1270 | key: 'render',
1271 | value: function render() {
1272 | var isFunction = typeof this.props.children === 'function';
1273 | return this.state.mounted ? isFunction ? this.props.children() : this.props.children : _react2.default.createElement(this.props.nodeName, null);
1274 | }
1275 | }]);
1276 |
1277 | return ReactDelayed;
1278 | }(_react.Component);
1279 |
1280 | ReactDelayed.propTypes = {
1281 | mounted: _propTypes2.default.bool.isRequired,
1282 | mountAfter: _propTypes2.default.number.isRequired,
1283 | unmountAfter: _propTypes2.default.number.isRequired,
1284 | children: _propTypes2.default.oneOfType([_propTypes2.default.node, _propTypes2.default.func]).isRequired,
1285 | nodeName: _propTypes2.default.string.isRequired
1286 | };
1287 | ReactDelayed.defaultProps = {
1288 | mounted: false,
1289 | mountAfter: 0,
1290 | unmountAfter: 0,
1291 | children: _react2.default.createElement('span', null),
1292 | nodeName: 'span'
1293 | };
1294 | exports.default = ReactDelayed;
1295 |
1296 | /***/ })
1297 | /******/ ]);
--------------------------------------------------------------------------------
/example/css/default.scss:
--------------------------------------------------------------------------------
1 | * {
2 | margin: 0;
3 | padding: 0;
4 | box-sizing: border-box;
5 | font-family: Lato, Arial, Tahoma, Helvetica, sans-serif;
6 | }
7 |
8 | main {
9 | @import './modal';
10 |
11 | > h1 {
12 | display: flex;
13 | align-items: center;
14 | width: 100vw;
15 | text-transform: uppercase;
16 | font-size: 9px;
17 | padding: 5px 20px;
18 | font-weight: normal;
19 | height: 50px;
20 | border-bottom: 1px solid rgba(0, 0, 0, .05);
21 | }
22 |
23 | > section.buttons {
24 | display: flex;
25 | align-items: center;
26 | justify-content: center;
27 | width: 100vw;
28 | height: calc(100vh - 50px);
29 |
30 | @media (max-width: 480px) {
31 | flex-direction: column;
32 | justify-content: flex-start;
33 | padding-top: 10px;
34 | }
35 |
36 | > button {
37 | border: 0;
38 | outline: none;
39 | color: white;
40 | padding: 30px 45px;
41 | margin: 0 10px;
42 | font-size: 12px;
43 | text-transform: uppercase;
44 | cursor: pointer;
45 | transition: background-color .25s;
46 |
47 | @media (max-width: 480px) {
48 | margin: 10px 0;
49 | width: 90vw;
50 | }
51 |
52 | &:first-of-type {
53 | background-color: rebeccapurple;
54 | border-bottom: 1px solid darken(rebeccapurple, 5);
55 |
56 | &:hover {
57 | background-color: darken(rebeccapurple, 5);
58 | }
59 | }
60 |
61 | &:nth-of-type(2) {
62 | background-color: darkolivegreen;
63 | border-bottom: 1px solid darken(darkolivegreen, 5);
64 |
65 | &:hover {
66 | background-color: darken(darkolivegreen, 5);
67 | }
68 | }
69 | }
70 | }
71 | }
72 |
--------------------------------------------------------------------------------
/example/css/modal.scss:
--------------------------------------------------------------------------------
1 | span.modal-container {
2 |
3 | > a {
4 | position: relative;
5 | z-index: 101;
6 | }
7 |
8 | > section.modal {
9 | position: fixed;
10 | top: 0;
11 | left: 0;
12 | width: 100%;
13 | height: 100%;
14 | display: inline-flex;
15 | justify-content: center;
16 | align-items: center;
17 | z-index: 1001;
18 | background-color: rgba(0, 0, 0, .05);
19 | transition: opacity .35s, visibility .35s;
20 | visibility: visible;
21 |
22 | &.closed {
23 | opacity: 0;
24 | pointer-events: none;
25 | visibility: hidden;
26 | }
27 |
28 | &.open > section.dialog {
29 | transform: scale(1);
30 | }
31 |
32 | > section.dialog {
33 | background-color: white;
34 | box-shadow: 0 0 50px rgba(0, 0, 0, .35);
35 | min-width: 200px;
36 | text-align: left;
37 | transition: all .4s cubic-bezier(0.175, 0.885, 0.32, 1.275);
38 | transform: scale(0.65);
39 | overflow: hidden;
40 |
41 | > header {
42 | $height: 40px;
43 | position: relative;
44 | height: $height;
45 | line-height: $height;
46 |
47 | > h5 {
48 | width: calc(70% - #{$height});
49 | white-space: nowrap;
50 | text-overflow: ellipsis;
51 | overflow: hidden;
52 | padding-left: 15px;
53 | color: black;
54 | text-transform: uppercase;
55 | font-size: 12px;
56 | }
57 |
58 | > a.close {
59 | cursor: pointer;
60 | height: $height;
61 | line-height: $height;
62 | width: $height;
63 | position: absolute;
64 | text-align: center;
65 | top: 0;
66 | right: 0;
67 | text-decoration: none;
68 | font-size: 20px;
69 | border-left: 1px solid rgba(0, 0, 0, .1);
70 | transition: background-color .15s;
71 | user-select: none;
72 | color: black;
73 |
74 | &:hover {
75 | background-color: white;
76 | }
77 | }
78 | }
79 |
80 | > div.content {
81 | display: flex;
82 | }
83 | }
84 | }
85 | }
86 |
--------------------------------------------------------------------------------
/example/images/nyan.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Wildhoney/ReactDelayed/73272c53cbef1c4b7ccc75f0fb224d941e006c31/example/images/nyan.gif
--------------------------------------------------------------------------------
/example/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 | React Delayed
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
--------------------------------------------------------------------------------
/example/js/default.js:
--------------------------------------------------------------------------------
1 | import React, { Component } from 'react';
2 | import { render } from 'react-dom';
3 | import Symbol from 'es6-symbol';
4 | import Modal from './modal';
5 | import Delayed from '../../src/react-delayed';
6 |
7 | /**
8 | * @constant modalTypes
9 | * @type {{without: *, with: *}}
10 | */
11 | const modalTypes = {
12 | without: Symbol('without'),
13 | with: Symbol('with')
14 | };
15 |
16 | /**
17 | * @class Example
18 | * @extends {Component}
19 | */
20 | class Example extends Component {
21 |
22 | /**
23 | * @constant state
24 | * @type {{modal: null}}
25 | */
26 | state = { modal: null };
27 |
28 | /**
29 | * @method render
30 | * @return {XML}
31 | */
32 | render() {
33 |
34 | const isWithoutOpen = this.state.modal === modalTypes.without;
35 | const isWithOpen = this.state.modal === modalTypes.with;
36 |
37 | return (
38 |
39 |
40 | <Delayed />
41 |
42 |
43 |
44 |
45 |
46 |
47 | this.setState({ modal: null })}
51 | >
52 | {isWithoutOpen &&
}
53 |
54 |
55 | this.setState({ modal: null })}
59 | >
60 |
61 |
62 |
63 |
64 |
65 |
66 | );
67 |
68 | }
69 |
70 | }
71 |
72 | document.addEventListener('DOMContentLoaded', () => {
73 | const mountNode = document.querySelector('section.app');
74 | render(, mountNode);
75 | });
76 |
--------------------------------------------------------------------------------
/example/js/modal.js:
--------------------------------------------------------------------------------
1 | import React, { PureComponent } from 'react';
2 | import PropTypes from 'prop-types';
3 |
4 | export default class Modal extends PureComponent {
5 |
6 | /**
7 | * @constant propTypes
8 | * @type {Object}
9 | */
10 | static propTypes = {
11 | className: PropTypes.string,
12 | title: PropTypes.string.isRequired,
13 | children: PropTypes.node.isRequired,
14 | isOpen: PropTypes.bool.isRequired,
15 | onOpen: PropTypes.func.isRequired,
16 | onClose: PropTypes.func.isRequired,
17 | stopPropagation: PropTypes.func.isRequired
18 | };
19 |
20 | /**
21 | * @constant defaultProps
22 | * @type {Object}
23 | */
24 | static defaultProps = {
25 | isOpen: false,
26 | className: '',
27 | onOpen: () => {},
28 | onClose: () => {},
29 | stopPropagation: event => event.stopPropagation()
30 | };
31 |
32 | /**
33 | * @method componentWillReceiveProps
34 | * @param {Object} nextProps
35 | * @return {void}
36 | */
37 | componentWillReceiveProps(nextProps) {
38 | !this.props.isOpen && nextProps.isOpen && this.props.onOpen();
39 | }
40 |
41 | /**
42 | * @method render
43 | * @return {XML}
44 | */
45 | render() {
46 |
47 | const { children, isOpen, className, onClose, stopPropagation } = this.props;
48 | const modalClassName = `modal ${isOpen ? 'open' : 'closed'} ${className}`.trim();
49 |
50 | return (
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 | {this.props.title}
59 | ×
60 |
61 |
62 |
63 | {children}
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 | );
72 |
73 | }
74 |
75 | }
76 |
--------------------------------------------------------------------------------
/example/server/default.js:
--------------------------------------------------------------------------------
1 | import http from 'http';
2 | import express from 'express';
3 |
4 | const app = express();
5 | const server = http.createServer(app);
6 | const port = process.env.PORT || 5000;
7 |
8 | app.use(express.static(`${__dirname}/..`));
9 | server.listen(port);
10 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "react-delayed",
3 | "version": "0.2.3",
4 | "description": "Small component for delaying the mounting and unmounting of a child component for CSS animation purposes.",
5 | "main": "dist/react-delayed.js",
6 | "scripts": {
7 | "build": "webpack --config webpack.config.release.js",
8 | "sass": "node-sass ./example/css/default.scss -o ./example/css",
9 | "start": "npm run sass && webpack --config webpack.config.example.js && babel-node example/server/default.js",
10 | "watch": "webpack --config webpack.config.example.js --watch",
11 | "test": "npm run spec && npm run lint",
12 | "spec": "nyc ava && npm run report",
13 | "lint": "xo src/*.js",
14 | "report": "nyc report --reporter=html"
15 | },
16 | "repository": {
17 | "type": "git",
18 | "url": "git+https://github.com/Wildhoney/ReactDelayed.git"
19 | },
20 | "keywords": [
21 | "delayed",
22 | "deferred",
23 | "delay",
24 | "delay",
25 | "render",
26 | "mount",
27 | "unmount",
28 | "css",
29 | "animation",
30 | "transition"
31 | ],
32 | "author": "Adam Timberlake ",
33 | "license": "MIT",
34 | "bugs": {
35 | "url": "https://github.com/Wildhoney/ReactDelayed/issues"
36 | },
37 | "homepage": "https://github.com/Wildhoney/ReactDelayed#readme",
38 | "peerDependencies": {
39 | "react": ">=15.4.2",
40 | "react-dom": ">=15.4.2"
41 | },
42 | "devDependencies": {
43 | "async-delay": "~1.0.3",
44 | "ava": "~0.18.2",
45 | "babel-cli": "~6.24.0",
46 | "babel-eslint": "~7.2.1",
47 | "babel-loader": "~6.4.1",
48 | "babel-polyfill": "~6.23.0",
49 | "babel-preset-es2015": "~6.24.0",
50 | "babel-preset-react": "~6.23.0",
51 | "babel-preset-stage-0": "~6.22.0",
52 | "coveralls": "~2.13.0",
53 | "enzyme": "~2.8.0",
54 | "es6-symbol": "~3.1.1",
55 | "eslint-config-xo-react": "~0.11.1",
56 | "eslint-plugin-react": "~6.10.3",
57 | "express": "~4.15.2",
58 | "jsdom": "~9.12.0",
59 | "node-sass": "~4.5.1",
60 | "nyc": "~10.2.0",
61 | "prop-types": "~15.5.8",
62 | "react": ">=15.4.2",
63 | "react-dom": ">=15.4.2",
64 | "react-addons-test-utils": ">=15.4.2",
65 | "sinon": "~2.1.0",
66 | "webpack": "~2.3.2",
67 | "xo": "~0.18.1"
68 | },
69 | "ava": {
70 | "files": [
71 | "tests/*.test.js"
72 | ],
73 | "babel": "inherit",
74 | "require": [
75 | "babel-register",
76 | "babel-polyfill",
77 | "./tests/helpers/browser-env.js"
78 | ]
79 | },
80 | "xo": {
81 | "space": 4,
82 | "esnext": true,
83 | "parser": "babel-eslint",
84 | "globals": [
85 | "window",
86 | "document"
87 | ],
88 | "extends": "xo-react",
89 | "rules": {
90 | "padded-blocks": "off",
91 | "object-curly-spacing": [
92 | 2,
93 | "always"
94 | ],
95 | "react/jsx-tag-spacing": [
96 | 2,
97 | "never"
98 | ],
99 | "no-unused-expressions": "off",
100 | "react/no-unused-prop-types": "off",
101 | "react/jsx-space-before-closing": [
102 | 2,
103 | "always"
104 | ],
105 | "react/jsx-filename-extension": [
106 | 1,
107 | {
108 | "extensions": [
109 | ".js"
110 | ]
111 | }
112 | ]
113 | }
114 | }
115 | }
116 |
--------------------------------------------------------------------------------
/src/react-delayed.js:
--------------------------------------------------------------------------------
1 | import React, { Component } from 'react';
2 | import PropTypes from 'prop-types';
3 |
4 | /**
5 | * @constant types
6 | * @type {{mount: string, unmounted: string}}
7 | */
8 | const types = {
9 | MOUNT: 'mount',
10 | UNMOUNT: 'unmount'
11 | };
12 |
13 | /**
14 | * @class ReactDelayed
15 | * @extends {Component}
16 | */
17 | export default class ReactDelayed extends Component {
18 |
19 | /**
20 | * @constant state
21 | * @type {{mounted: boolean}}
22 | */
23 | state = { mounted: typeof window === 'undefined' ? this.props.mounted : false, deferred: null };
24 |
25 | /**
26 | * @constant propTypes
27 | * @type {{mountAfter: function, unmountAfter: function}}
28 | */
29 | static propTypes = {
30 | mounted: PropTypes.bool.isRequired,
31 | mountAfter: PropTypes.number.isRequired,
32 | unmountAfter: PropTypes.number.isRequired,
33 | children: PropTypes.oneOfType([PropTypes.node, PropTypes.func]).isRequired,
34 | nodeName: PropTypes.string.isRequired
35 | };
36 |
37 | /**
38 | * @constant defaultProps
39 | * @type {{mountAfter: number, unmountAfter: number}}
40 | */
41 | static defaultProps = {
42 | mounted: false,
43 | mountAfter: 0,
44 | unmountAfter: 0,
45 | children: ,
46 | nodeName: 'span'
47 | };
48 |
49 | /**
50 | * @method componentDidMount
51 | * @return {void}
52 | */
53 | componentDidMount() {
54 | this.isComponentMounted = true;
55 | this.props.mounted === true && this.handleVisibility(types.MOUNT);
56 | }
57 |
58 | /**
59 | * @method componentWillUnmount
60 | * @return {void}
61 | */
62 | componentWillUnmount() {
63 | this.isComponentMounted = false;
64 | }
65 |
66 | /**
67 | * @method componentWillReceiveProps
68 | * @param {Object} nextProps
69 | * @return {void}
70 | */
71 | componentWillReceiveProps(nextProps) {
72 | this.props.mounted === false && nextProps.mounted === true && this.handleVisibility(types.MOUNT);
73 | this.props.mounted === true && nextProps.mounted === false && this.handleVisibility(types.UNMOUNT);
74 | }
75 |
76 | /**
77 | * @method handleVisibility
78 | * @param {String} type
79 | * @return {void}
80 | */
81 | handleVisibility(type) {
82 |
83 | const mounted = type === types.MOUNT;
84 | const timeout = this.props[`${type}After`];
85 | const invoker = timeout === 0 ? fn => fn() : setTimeout;
86 |
87 | clearTimeout(this.state.deferred);
88 | const deferred = invoker(() => this.isComponentMounted && this.setState({ mounted }), timeout);
89 | this.setState({ deferred });
90 |
91 | }
92 |
93 | /**
94 | * @method render
95 | * @return {XML}
96 | */
97 | render() {
98 | const isFunction = typeof this.props.children === 'function';
99 | return this.state.mounted ? (isFunction ? this.props.children() : this.props.children) : ;
100 | }
101 |
102 | }
103 |
--------------------------------------------------------------------------------
/tests/helpers/browser-env.js:
--------------------------------------------------------------------------------
1 | import { jsdom } from 'jsdom';
2 |
3 | global.document = jsdom('');
4 | global.window = document.defaultView;
5 | global.navigator = window.navigator;
6 |
--------------------------------------------------------------------------------
/tests/react-delayed.test.js:
--------------------------------------------------------------------------------
1 | import test from 'ava';
2 | import { mount } from 'enzyme';
3 | import React, { Component } from 'react';
4 | import delay from 'async-delay';
5 | import { spy } from 'sinon';
6 | import Delayed from '../src/react-delayed';
7 |
8 | test.beforeEach(t => {
9 |
10 | class Nested extends Component {
11 |
12 | /**
13 | * @method componentDidMount
14 | * @return {void}
15 | */
16 | componentDidMount() {}
17 |
18 | /**
19 | * @method componentWillUnmount
20 | * @return {void}
21 | */
22 | componentWillUnmount() {}
23 |
24 | /**
25 | * @method render
26 | * @return {XML}
27 | */
28 | render() {
29 | return <Delayed />
30 | }
31 |
32 | }
33 |
34 | /**
35 | * @constant lifecycle
36 | * @type {{componentDidMount: *}}
37 | */
38 | t.context.lifecycle = {
39 | componentDidMount: spy(Nested.prototype, 'componentDidMount'),
40 | componentWillUnmount: spy(Nested.prototype, 'componentWillUnmount')
41 | };
42 |
43 | /**
44 | * @method createComponent
45 | * @param {Object} props
46 | * @return {XML}
47 | */
48 | t.context.createComponent = props => ;
49 |
50 | });
51 |
52 | test('It should be able to delay mounting;', async t => {
53 |
54 | mount(t.context.createComponent({ mounted: true, mountAfter: 100 }));
55 | t.is(t.context.lifecycle.componentDidMount.callCount, 0);
56 | await delay(200);
57 | t.is(t.context.lifecycle.componentDidMount.callCount, 1);
58 | t.context.lifecycle.componentDidMount.reset();
59 |
60 | const wrapper = mount(t.context.createComponent({ mounted: false, mountAfter: 100 }));
61 | t.is(t.context.lifecycle.componentDidMount.callCount, 0);
62 | wrapper.setProps({ mounted: true });
63 | t.is(t.context.lifecycle.componentDidMount.callCount, 0);
64 | await delay(200);
65 | t.is(t.context.lifecycle.componentDidMount.callCount, 1);
66 |
67 | });
68 |
69 | test('It should be able to delay unmounting;', async t => {
70 |
71 | const wrapper = mount(t.context.createComponent({ mounted: true, unmountAfter: 100 }));
72 |
73 | t.is(t.context.lifecycle.componentWillUnmount.callCount, 0);
74 | wrapper.setProps({ mounted: false });
75 | t.is(t.context.lifecycle.componentWillUnmount.callCount, 0);
76 | await delay(200);
77 | t.is(t.context.lifecycle.componentWillUnmount.callCount, 1);
78 |
79 | });
80 |
--------------------------------------------------------------------------------
/webpack.config.example.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | entry: ['babel-polyfill', './example/js/default.js'],
3 | output: {
4 | path: __dirname + '/example/js',
5 | filename: 'build.js',
6 | libraryTarget: 'var'
7 | },
8 | module: {
9 | loaders: [
10 | {
11 | test: /\.js$/,
12 | loader: 'babel-loader'
13 | }
14 | ]
15 | }
16 | };
17 |
--------------------------------------------------------------------------------
/webpack.config.release.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | entry: './src/react-delayed.js',
3 | output: {
4 | path: __dirname + '/dist',
5 | filename: 'react-delayed.js',
6 | libraryTarget: 'commonjs2'
7 | },
8 | externals: {
9 | 'react': {
10 | commonjs2: 'react',
11 | },
12 | 'react-dom':{
13 | commonjs2: 'react-dom',
14 | }
15 | },
16 | module: {
17 | loaders: [
18 | {
19 | test: /\.js$/,
20 | loader: 'babel-loader'
21 | }
22 | ]
23 | }
24 | };
25 |
--------------------------------------------------------------------------------