UNPKG

4.52 kBJavaScriptView Raw
1import _toConsumableArray from "@babel/runtime/helpers/esm/toConsumableArray";
2import _slicedToArray from "@babel/runtime/helpers/esm/slicedToArray";
3import _objectWithoutProperties from "@babel/runtime/helpers/esm/objectWithoutProperties";
4var _excluded = ["getContainer", "motion", "prefixCls", "maxCount", "className", "style", "onAllRemoved"];
5import * as React from 'react';
6import Notifications from './Notifications';
7var defaultGetContainer = function defaultGetContainer() {
8 return document.body;
9};
10var uniqueKey = 0;
11function mergeConfig() {
12 var clone = {};
13 for (var _len = arguments.length, objList = new Array(_len), _key = 0; _key < _len; _key++) {
14 objList[_key] = arguments[_key];
15 }
16 objList.forEach(function (obj) {
17 if (obj) {
18 Object.keys(obj).forEach(function (key) {
19 var val = obj[key];
20 if (val !== undefined) {
21 clone[key] = val;
22 }
23 });
24 }
25 });
26 return clone;
27}
28export default function useNotification() {
29 var rootConfig = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
30 var _rootConfig$getContai = rootConfig.getContainer,
31 getContainer = _rootConfig$getContai === void 0 ? defaultGetContainer : _rootConfig$getContai,
32 motion = rootConfig.motion,
33 prefixCls = rootConfig.prefixCls,
34 maxCount = rootConfig.maxCount,
35 className = rootConfig.className,
36 style = rootConfig.style,
37 onAllRemoved = rootConfig.onAllRemoved,
38 shareConfig = _objectWithoutProperties(rootConfig, _excluded);
39 var _React$useState = React.useState(),
40 _React$useState2 = _slicedToArray(_React$useState, 2),
41 container = _React$useState2[0],
42 setContainer = _React$useState2[1];
43 var notificationsRef = React.useRef();
44 var contextHolder = /*#__PURE__*/React.createElement(Notifications, {
45 container: container,
46 ref: notificationsRef,
47 prefixCls: prefixCls,
48 motion: motion,
49 maxCount: maxCount,
50 className: className,
51 style: style,
52 onAllRemoved: onAllRemoved
53 });
54 var _React$useState3 = React.useState([]),
55 _React$useState4 = _slicedToArray(_React$useState3, 2),
56 taskQueue = _React$useState4[0],
57 setTaskQueue = _React$useState4[1];
58 // ========================= Refs =========================
59 var api = React.useMemo(function () {
60 return {
61 open: function open(config) {
62 var mergedConfig = mergeConfig(shareConfig, config);
63 if (mergedConfig.key === null || mergedConfig.key === undefined) {
64 mergedConfig.key = "rc-notification-".concat(uniqueKey);
65 uniqueKey += 1;
66 }
67 setTaskQueue(function (queue) {
68 return [].concat(_toConsumableArray(queue), [{
69 type: 'open',
70 config: mergedConfig
71 }]);
72 });
73 },
74 close: function close(key) {
75 setTaskQueue(function (queue) {
76 return [].concat(_toConsumableArray(queue), [{
77 type: 'close',
78 key: key
79 }]);
80 });
81 },
82 destroy: function destroy() {
83 setTaskQueue(function (queue) {
84 return [].concat(_toConsumableArray(queue), [{
85 type: 'destroy'
86 }]);
87 });
88 }
89 };
90 }, []);
91 // ======================= Container ======================
92 // React 18 should all in effect that we will check container in each render
93 // Which means getContainer should be stable.
94 React.useEffect(function () {
95 setContainer(getContainer());
96 });
97 // ======================== Effect ========================
98 React.useEffect(function () {
99 // Flush task when node ready
100 if (notificationsRef.current && taskQueue.length) {
101 taskQueue.forEach(function (task) {
102 switch (task.type) {
103 case 'open':
104 notificationsRef.current.open(task.config);
105 break;
106 case 'close':
107 notificationsRef.current.close(task.key);
108 break;
109 case 'destroy':
110 notificationsRef.current.destroy();
111 break;
112 }
113 });
114 // React 17 will mix order of effect & setState in async
115 // - open: setState[0]
116 // - effect[0]
117 // - open: setState[1]
118 // - effect setState([]) * here will clean up [0, 1] in React 17
119 setTaskQueue(function (oriQueue) {
120 return oriQueue.filter(function (task) {
121 return !taskQueue.includes(task);
122 });
123 });
124 }
125 }, [taskQueue]);
126 // ======================== Return ========================
127 return [api, contextHolder];
128}
\No newline at end of file