@webkrafters/react-observable-context 2.1.12 → 3.0.0-rc.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +13 -32
- package/dist/index.d.ts +1 -17
- package/dist/index.js +166 -148
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
A context bearing an observable consumer [store](#store).\
|
|
4
4
|
Only re-renders subscribing components on context state change.\
|
|
5
|
-
Subscribing component decides which context state properties' change trigger its update.
|
|
5
|
+
Subscribing component decides which context state properties' change to trigger its update.
|
|
6
6
|
|
|
7
7
|
**Name:** React-Observable-Context
|
|
8
8
|
|
|
@@ -18,23 +18,23 @@ A context bearing an observable consumer [store](#store). State changes within t
|
|
|
18
18
|
|
|
19
19
|
**React::memo** *(and PureComponents)* remain the go-to solution for the repeated automatic re-renderings of entire component trees resulting from ***component*** state changes.
|
|
20
20
|
|
|
21
|
-
***Recommendation:*** For optimum performance, consider wrapping in **React::memo** most components using this
|
|
21
|
+
***Recommendation:*** For optimum performance, consider wrapping in **React::memo** most components using this module's ***useContext*** hook either directly or through another React hook. This will protect such components and their descendants from unrelated cascading render operations.
|
|
22
22
|
|
|
23
23
|
***Exempt*** from the recommendation are certain components such as those wrapped in the `React-Redux::connect()` Higher Order Component (HOC). Such HOC provides similar cascade-render protections to wrapped components and their descendants.
|
|
24
24
|
|
|
25
25
|
# API
|
|
26
26
|
|
|
27
|
-
The React-Observable-Context
|
|
27
|
+
The React-Observable-Context module contains **3** exports namely: the **createContext** function, the **useContext** hook and the **UsageError** class.
|
|
28
28
|
|
|
29
29
|
* **createContext** is a zero-parameter function returning a store-bearing context. Pass the context as a `context` parameter to the [useContext()](#usecontext) to obtain the context's [store](#store).
|
|
30
30
|
|
|
31
|
-
* <b id="usecontext">useContext</b> is analogous to React::useContext hook but returns the context store and takes a second parameter named ***watchedKeys***. The `watchedKeys` parameter is a list of state object property paths to watch. A change in any of the referenced properties automatically triggers a render of the component
|
|
32
|
-
|
|
33
|
-
* **Provider** can immediately be used as-is anywhere the React-Observable-Context is required. It accepts **3** props and the customary Provider `children` prop. Supply the context to its `context` prop; the initial state to the customary Provider `value` prop; and the optional `prehooks` prop <i>(discussed in the [prehooks](#prehooks) section below)</i>.
|
|
31
|
+
* <b id="usecontext">useContext</b> is analogous to React::useContext hook but returns the context store and takes a second parameter named ***watchedKeys***. The `watchedKeys` parameter is a list of state object property paths to watch. A change in any of the referenced properties automatically triggers a render of the component using this hook.
|
|
34
32
|
|
|
35
33
|
* **UsageError** class is the Error type reported for attempts to access this context's store outside of its Provider component tree.
|
|
36
34
|
|
|
37
|
-
|
|
35
|
+
## Provider
|
|
36
|
+
|
|
37
|
+
The Provider component is a property of the `context`. It can immediately be used as-is anywhere the React-Observable-Context is required. It accepts the customary `children` and `value` props, and an optional `prehooks` prop <i>(discussed in the [prehooks](#prehooks) subsection below)</i>.
|
|
38
38
|
|
|
39
39
|
## Store
|
|
40
40
|
|
|
@@ -69,35 +69,16 @@ The context's `store` exposes **4** methods for interacting with the context's i
|
|
|
69
69
|
### <u>*context.js*</u>
|
|
70
70
|
|
|
71
71
|
import React from 'react';
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
createContext,
|
|
75
|
-
Provider,
|
|
76
|
-
useContext
|
|
77
|
-
} from '@webkrafters/react-observable-context';
|
|
78
|
-
|
|
79
|
-
export const ObservableContext = createContext();
|
|
80
|
-
|
|
81
|
-
export const ObservableContextProvider = ({ children, prehooks, value }) => (
|
|
82
|
-
<Provider
|
|
83
|
-
context={ ObservableContext }
|
|
84
|
-
prehooks={ prehooks }
|
|
85
|
-
value={ value }
|
|
86
|
-
>
|
|
87
|
-
{ children }
|
|
88
|
-
</Provider>
|
|
89
|
-
);
|
|
90
|
-
ObservableContextProvider.displayName = 'ObservableContextProvider';
|
|
91
|
-
|
|
72
|
+
import { createContext, useContext } from '@webkrafters/react-observable-context';
|
|
73
|
+
const ObservableContext = createContext();
|
|
92
74
|
export const useObservableContext = watchedKeys => useContext( ObservableContext, watchedKeys );
|
|
93
|
-
|
|
94
75
|
export default ObservableContext;
|
|
95
76
|
|
|
96
77
|
### <u>*index.js*</u>
|
|
97
78
|
|
|
98
79
|
import React from 'react';
|
|
99
80
|
import ReactDOM from 'react-dom';
|
|
100
|
-
import App from './app';
|
|
81
|
+
import App from './app';s
|
|
101
82
|
ReactDOM.render(<App />, document.getElementById('root'));
|
|
102
83
|
|
|
103
84
|
### <u>*app.js*</u>
|
|
@@ -137,7 +118,7 @@ The context's `store` exposes **4** methods for interacting with the context's i
|
|
|
137
118
|
### <u>*product.js*</u>
|
|
138
119
|
|
|
139
120
|
import React, { useCallback, useEffect, useState } from 'react';
|
|
140
|
-
import
|
|
121
|
+
import ObservableContext from './context';
|
|
141
122
|
import Editor from './editor';
|
|
142
123
|
import PriceSticker from './price-sticker';
|
|
143
124
|
import ProductDescription from './product-description';
|
|
@@ -158,7 +139,7 @@ The context's `store` exposes **4** methods for interacting with the context's i
|
|
|
158
139
|
<div style={{ marginBottom: 10 }}>
|
|
159
140
|
<label>$ <input onKeyUp={ overridePricing } placeholder="override price here..." /></label>
|
|
160
141
|
</div>
|
|
161
|
-
<
|
|
142
|
+
<ObservableContext.Provider
|
|
162
143
|
prehooks={ updateHooks }
|
|
163
144
|
value={ state }
|
|
164
145
|
>
|
|
@@ -172,7 +153,7 @@ The context's `store` exposes **4** methods for interacting with the context's i
|
|
|
172
153
|
</div>
|
|
173
154
|
<ProductDescription />
|
|
174
155
|
<PriceSticker />
|
|
175
|
-
</
|
|
156
|
+
</ObservableContext.Provider>
|
|
176
157
|
</div>
|
|
177
158
|
);
|
|
178
159
|
};
|
package/dist/index.d.ts
CHANGED
|
@@ -2,23 +2,6 @@ export class UsageError extends Error {
|
|
|
2
2
|
}
|
|
3
3
|
export function createContext<T_1 extends State>(): import("react").Context<Store<T_1>>;
|
|
4
4
|
export function useContext<T_1 extends State>(context: import("react").Context<Store<T_1>>, watchedKeys?: (string | keyof T_1)[]): Store<T_1>;
|
|
5
|
-
/**
|
|
6
|
-
* Note: `context` prop is not updateable. Furtther updates to this prop are ignored.
|
|
7
|
-
*
|
|
8
|
-
* @type {FC<{
|
|
9
|
-
* children?: ReactNode,
|
|
10
|
-
* context: ObservableContext<T>,
|
|
11
|
-
* prehooks?: Prehooks<T>
|
|
12
|
-
* value: PartialState<T>
|
|
13
|
-
* }>}
|
|
14
|
-
* @template {State} T
|
|
15
|
-
*/
|
|
16
|
-
export const Provider: FC<{
|
|
17
|
-
children?: ReactNode;
|
|
18
|
-
context: ObservableContext<T>;
|
|
19
|
-
prehooks?: Prehooks<T>;
|
|
20
|
-
value: PartialState<T>;
|
|
21
|
-
}>;
|
|
22
5
|
export type ObservableContext<T_1 extends State> = Context<Store<T>>;
|
|
23
6
|
export type OptionalTask<F = void> = F extends void ? () => never : F;
|
|
24
7
|
export type Listener<T_1 extends State> = (newValue: PartialState<T>, oldValue: PartialState<T>) => void;
|
|
@@ -45,5 +28,6 @@ export type Store<T_1 extends State> = {
|
|
|
45
28
|
export type Unsubscribe = VoidFunction;
|
|
46
29
|
export type ReactNode = import("react").ReactNode;
|
|
47
30
|
export type FC<P = {}> = import("react").FC<P>;
|
|
31
|
+
export type Provider<T_1> = import("react").Provider<T>;
|
|
48
32
|
export type Context<T_1> = import("react").Context<T>;
|
|
49
33
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.js
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
Object.defineProperty(exports, "__esModule", {
|
|
4
4
|
value: true
|
|
5
5
|
});
|
|
6
|
-
exports.useContext = exports.createContext = exports.UsageError =
|
|
6
|
+
exports.useContext = exports.createContext = exports.UsageError = void 0;
|
|
7
7
|
var _react = _interopRequireWildcard(require("react"));
|
|
8
8
|
var _lodash = _interopRequireDefault(require("lodash.clonedeep"));
|
|
9
9
|
var _lodash2 = _interopRequireDefault(require("lodash.has"));
|
|
@@ -43,75 +43,27 @@ var UsageError = /*#__PURE__*/function (_Error) {
|
|
|
43
43
|
}
|
|
44
44
|
return _createClass(UsageError);
|
|
45
45
|
}( /*#__PURE__*/_wrapNativeSuper(Error));
|
|
46
|
-
/** @type {OptionalTask} */
|
|
47
|
-
exports.UsageError = UsageError;
|
|
48
|
-
var reportNonReactUsage = function reportNonReactUsage() {
|
|
49
|
-
throw new UsageError('Detected usage outside of this context\'s Provider component tree. Please apply the exported Provider component');
|
|
50
|
-
};
|
|
51
|
-
|
|
52
46
|
/**
|
|
53
47
|
* @param {T} state
|
|
54
48
|
* @return {PartialState<T>}
|
|
55
49
|
* @template {State} T
|
|
56
50
|
*/
|
|
51
|
+
exports.UsageError = UsageError;
|
|
57
52
|
var defaultSelector = function defaultSelector(state) {
|
|
58
53
|
return state;
|
|
59
54
|
};
|
|
60
55
|
|
|
61
|
-
/**
|
|
62
|
-
* @returns {ObservableContext<T>}
|
|
63
|
-
* @template {State} T
|
|
64
|
-
*/
|
|
65
|
-
var createContext = function createContext() {
|
|
66
|
-
return /*#__PURE__*/(0, _react.createContext)({
|
|
67
|
-
getState: reportNonReactUsage,
|
|
68
|
-
resetState: reportNonReactUsage,
|
|
69
|
-
setState: reportNonReactUsage,
|
|
70
|
-
subscribe: reportNonReactUsage
|
|
71
|
-
});
|
|
72
|
-
};
|
|
73
|
-
|
|
74
|
-
/**
|
|
75
|
-
* Actively monitors the store and triggers component re-render if any of the watched keys in the state objects changes
|
|
76
|
-
*
|
|
77
|
-
* @param {ObservableContext<T>} context
|
|
78
|
-
* @param {Array<string|keyof T>} [watchedKeys = []] A list of state object property paths to watch. A change in any of the referenced properties results in this component render.
|
|
79
|
-
* @returns {Store<T>}
|
|
80
|
-
* @template {State} T
|
|
81
|
-
*/
|
|
82
|
-
exports.createContext = createContext;
|
|
83
|
-
var useContext = function useContext(context) {
|
|
84
|
-
var watchedKeys = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : [];
|
|
85
|
-
/** @type {Store<T>} */
|
|
86
|
-
var store = (0, _react.useContext)(context);
|
|
87
|
-
var _useState = (0, _react.useState)(false),
|
|
88
|
-
_useState2 = _slicedToArray(_useState, 2),
|
|
89
|
-
tripRender = _useState2[1];
|
|
90
|
-
var watched = (0, _react.useMemo)(function () {
|
|
91
|
-
return Array.isArray(watchedKeys) ? Array.from(new Set(watchedKeys)) : [];
|
|
92
|
-
}, [watchedKeys]);
|
|
93
|
-
(0, _react.useEffect)(function () {
|
|
94
|
-
if (!watched.length) {
|
|
95
|
-
return;
|
|
96
|
-
}
|
|
97
|
-
return store.subscribe(function (newChanges) {
|
|
98
|
-
watched.some(function (w) {
|
|
99
|
-
return (0, _lodash2["default"])(newChanges, w);
|
|
100
|
-
}) && tripRender(function (s) {
|
|
101
|
-
return !s;
|
|
102
|
-
});
|
|
103
|
-
});
|
|
104
|
-
}, [watched]);
|
|
105
|
-
return store;
|
|
106
|
-
};
|
|
107
|
-
|
|
108
56
|
/**
|
|
109
57
|
* @readonly
|
|
110
58
|
* @type {Prehooks<T>}
|
|
111
59
|
* @template {State} T
|
|
112
60
|
*/
|
|
113
|
-
exports.useContext = useContext;
|
|
114
61
|
var defaultPrehooks = Object.freeze({});
|
|
62
|
+
|
|
63
|
+
/** @type {OptionalTask} */
|
|
64
|
+
var reportNonReactUsage = function reportNonReactUsage() {
|
|
65
|
+
throw new UsageError('Detected usage outside of this context\'s Provider component tree. Please apply the exported Provider component');
|
|
66
|
+
};
|
|
115
67
|
var _setState = function () {
|
|
116
68
|
var initDiff = function initDiff(propKey, changed, replaced) {
|
|
117
69
|
changed[propKey] = {};
|
|
@@ -180,101 +132,28 @@ var usePrehooksRef = function usePrehooksRef(prehooks) {
|
|
|
180
132
|
return prehooksRef;
|
|
181
133
|
};
|
|
182
134
|
|
|
183
|
-
/** @type {FC<{child: ReactNode}>} */
|
|
184
|
-
var ChildMemo = function () {
|
|
185
|
-
var useNodeMemo = function useNodeMemo(node) {
|
|
186
|
-
var nodeRef = (0, _react.useRef)(node);
|
|
187
|
-
if (!(0, _lodash4["default"])((0, _lodash6["default"])(nodeRef.current, '_owner'), (0, _lodash6["default"])(node, '_owner'))) {
|
|
188
|
-
nodeRef.current = node;
|
|
189
|
-
}
|
|
190
|
-
return nodeRef.current;
|
|
191
|
-
};
|
|
192
|
-
var ChildMemo = /*#__PURE__*/(0, _react.memo)(function (_ref) {
|
|
193
|
-
var child = _ref.child;
|
|
194
|
-
return child;
|
|
195
|
-
});
|
|
196
|
-
ChildMemo.displayName = 'ObservableContext.Provider.Internal.Guardian.ChildMemo';
|
|
197
|
-
var Guardian = function Guardian(_ref2) {
|
|
198
|
-
var child = _ref2.child;
|
|
199
|
-
return /*#__PURE__*/_react["default"].createElement(ChildMemo, {
|
|
200
|
-
child: useNodeMemo(child)
|
|
201
|
-
});
|
|
202
|
-
};
|
|
203
|
-
Guardian.displayName = 'ObservableContext.Provider.Internal.Guardian';
|
|
204
|
-
return Guardian;
|
|
205
|
-
}();
|
|
206
|
-
|
|
207
|
-
/** @type {(children: ReactNode) => ReactNode} */
|
|
208
|
-
var memoizeImmediateChildTree = function memoizeImmediateChildTree(children) {
|
|
209
|
-
return _react.Children.map(children, function (child) {
|
|
210
|
-
var _child$props;
|
|
211
|
-
if (_typeof(child.type) === 'object' && 'compare' in child.type) {
|
|
212
|
-
return child;
|
|
213
|
-
}
|
|
214
|
-
if ((_child$props = child.props) !== null && _child$props !== void 0 && _child$props.children) {
|
|
215
|
-
child = /*#__PURE__*/(0, _react.cloneElement)(child, (0, _lodash6["default"])(child.props, 'children'), memoizeImmediateChildTree(child.props.children));
|
|
216
|
-
}
|
|
217
|
-
return /*#__PURE__*/_react["default"].createElement(ChildMemo, {
|
|
218
|
-
child: child
|
|
219
|
-
});
|
|
220
|
-
});
|
|
221
|
-
};
|
|
222
|
-
|
|
223
|
-
/**
|
|
224
|
-
* @type {FC<{
|
|
225
|
-
* children?: ReactNode,
|
|
226
|
-
* context: ObservableContext<T>,
|
|
227
|
-
* value: Store<T>
|
|
228
|
-
* }>}
|
|
229
|
-
* @template {State} T
|
|
230
|
-
*/
|
|
231
|
-
var ProviderInternal = function ProviderInternal(_ref3) {
|
|
232
|
-
var children = _ref3.children,
|
|
233
|
-
StoreContext = _ref3.context,
|
|
234
|
-
value = _ref3.value;
|
|
235
|
-
return /*#__PURE__*/_react["default"].createElement(StoreContext.Provider, {
|
|
236
|
-
value: value
|
|
237
|
-
}, memoizeImmediateChildTree(children));
|
|
238
|
-
};
|
|
239
|
-
ProviderInternal.displayName = 'ObservableContext.Provider.Internal';
|
|
240
|
-
|
|
241
135
|
/**
|
|
242
|
-
*
|
|
243
|
-
*
|
|
244
|
-
* @
|
|
245
|
-
* children?: ReactNode,
|
|
246
|
-
* context: ObservableContext<T>,
|
|
247
|
-
* prehooks?: Prehooks<T>
|
|
248
|
-
* value: PartialState<T>
|
|
249
|
-
* }>}
|
|
136
|
+
* @param {Prehooks<T>} prehooks
|
|
137
|
+
* @param {T} value
|
|
138
|
+
* @returns {Store<T>}
|
|
250
139
|
* @template {State} T
|
|
251
140
|
*/
|
|
252
|
-
var
|
|
253
|
-
var _ref4$children = _ref4.children,
|
|
254
|
-
children = _ref4$children === void 0 ? null : _ref4$children,
|
|
255
|
-
context = _ref4.context,
|
|
256
|
-
_ref4$prehooks = _ref4.prehooks,
|
|
257
|
-
prehooks = _ref4$prehooks === void 0 ? defaultPrehooks : _ref4$prehooks,
|
|
258
|
-
value = _ref4.value;
|
|
141
|
+
var useStore = function useStore(prehooks, value) {
|
|
259
142
|
var prehooksRef = usePrehooksRef(prehooks);
|
|
260
143
|
var initialState = (0, _react.useRef)(value);
|
|
261
144
|
|
|
262
145
|
/** @type {[Set<Listener<T>>, Function]} */
|
|
263
|
-
var
|
|
146
|
+
var _useState = (0, _react.useState)(function () {
|
|
264
147
|
return new Set();
|
|
265
148
|
}),
|
|
266
|
-
|
|
267
|
-
listeners =
|
|
149
|
+
_useState2 = _slicedToArray(_useState, 1),
|
|
150
|
+
listeners = _useState2[0];
|
|
268
151
|
/** @type {[T, Function]} */
|
|
269
|
-
var
|
|
152
|
+
var _useState3 = (0, _react.useState)(function () {
|
|
270
153
|
return (0, _lodash["default"])(value);
|
|
271
154
|
}),
|
|
272
|
-
|
|
273
|
-
state =
|
|
274
|
-
/** @type {ObservableContext<T>} */
|
|
275
|
-
var _useState7 = (0, _react.useState)(context),
|
|
276
|
-
_useState8 = _slicedToArray(_useState7, 1),
|
|
277
|
-
StoreContext = _useState8[0];
|
|
155
|
+
_useState4 = _slicedToArray(_useState3, 1),
|
|
156
|
+
state = _useState4[0];
|
|
278
157
|
|
|
279
158
|
/** @type {Listener<T>} */
|
|
280
159
|
var onChange = function onChange(newValue, oldValue) {
|
|
@@ -317,7 +196,7 @@ var Provider = function Provider(_ref4) {
|
|
|
317
196
|
}, [value]);
|
|
318
197
|
|
|
319
198
|
/** @type {[Store<T>, Function]} */
|
|
320
|
-
var
|
|
199
|
+
var _useState5 = (0, _react.useState)(function () {
|
|
321
200
|
return {
|
|
322
201
|
getState: getState,
|
|
323
202
|
resetState: resetState,
|
|
@@ -325,15 +204,148 @@ var Provider = function Provider(_ref4) {
|
|
|
325
204
|
subscribe: subscribe
|
|
326
205
|
};
|
|
327
206
|
}),
|
|
328
|
-
|
|
329
|
-
store =
|
|
330
|
-
return
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
207
|
+
_useState6 = _slicedToArray(_useState5, 1),
|
|
208
|
+
store = _useState6[0];
|
|
209
|
+
return store;
|
|
210
|
+
};
|
|
211
|
+
|
|
212
|
+
/** @type {FC<{child: ReactNode}>} */
|
|
213
|
+
var ChildMemo = function () {
|
|
214
|
+
var useNodeMemo = function useNodeMemo(node) {
|
|
215
|
+
var nodeRef = (0, _react.useRef)(node);
|
|
216
|
+
if (!(0, _lodash4["default"])((0, _lodash6["default"])(nodeRef.current, '_owner'), (0, _lodash6["default"])(node, '_owner'))) {
|
|
217
|
+
nodeRef.current = node;
|
|
218
|
+
}
|
|
219
|
+
return nodeRef.current;
|
|
220
|
+
};
|
|
221
|
+
var ChildMemo = /*#__PURE__*/(0, _react.memo)(function (_ref) {
|
|
222
|
+
var child = _ref.child;
|
|
223
|
+
return child;
|
|
224
|
+
});
|
|
225
|
+
ChildMemo.displayName = 'ObservableContext.Provider.Internal.Guardian.ChildMemo';
|
|
226
|
+
var Guardian = function Guardian(_ref2) {
|
|
227
|
+
var child = _ref2.child;
|
|
228
|
+
return /*#__PURE__*/_react["default"].createElement(ChildMemo, {
|
|
229
|
+
child: useNodeMemo(child)
|
|
230
|
+
});
|
|
231
|
+
};
|
|
232
|
+
Guardian.displayName = 'ObservableContext.Provider.Internal.Guardian';
|
|
233
|
+
return Guardian;
|
|
234
|
+
}();
|
|
235
|
+
|
|
236
|
+
/** @type {(children: ReactNode) => ReactNode} */
|
|
237
|
+
var memoizeImmediateChildTree = function memoizeImmediateChildTree(children) {
|
|
238
|
+
return _react.Children.map(children, function (child) {
|
|
239
|
+
var _child$props;
|
|
240
|
+
if (_typeof(child.type) === 'object' && 'compare' in child.type) {
|
|
241
|
+
return child;
|
|
242
|
+
} // memo element
|
|
243
|
+
if ((_child$props = child.props) !== null && _child$props !== void 0 && _child$props.children) {
|
|
244
|
+
child = /*#__PURE__*/(0, _react.cloneElement)(child, (0, _lodash6["default"])(child.props, 'children'), memoizeImmediateChildTree(child.props.children));
|
|
245
|
+
}
|
|
246
|
+
return /*#__PURE__*/_react["default"].createElement(ChildMemo, {
|
|
247
|
+
child: child
|
|
248
|
+
});
|
|
249
|
+
});
|
|
250
|
+
};
|
|
251
|
+
|
|
252
|
+
/**
|
|
253
|
+
* @type {FC<{
|
|
254
|
+
* children?: ReactNode,
|
|
255
|
+
* provider: ObservableContext<T>["Provider"],
|
|
256
|
+
* value: Store<T>
|
|
257
|
+
* }>}
|
|
258
|
+
* @template {State} T
|
|
259
|
+
*/
|
|
260
|
+
var ProviderInternal = function ProviderInternal(_ref3) {
|
|
261
|
+
var children = _ref3.children,
|
|
262
|
+
Provider = _ref3.provider,
|
|
263
|
+
value = _ref3.value;
|
|
264
|
+
return /*#__PURE__*/_react["default"].createElement(Provider, {
|
|
265
|
+
value: value
|
|
266
|
+
}, memoizeImmediateChildTree(children));
|
|
267
|
+
};
|
|
268
|
+
ProviderInternal.displayName = 'ObservableContext.Provider.Internal';
|
|
269
|
+
|
|
270
|
+
/**
|
|
271
|
+
* @param {Provider<Store<T>>} Provider
|
|
272
|
+
*/
|
|
273
|
+
var makeObservable = function makeObservable(Provider) {
|
|
274
|
+
/**
|
|
275
|
+
* Note: `context` prop is not updateable. Furtther updates to this prop are ignored.
|
|
276
|
+
*
|
|
277
|
+
* @type {FC<{
|
|
278
|
+
* children?: ReactNode,
|
|
279
|
+
* context: ObservableContext<T>,
|
|
280
|
+
* prehooks?: Prehooks<T>
|
|
281
|
+
* value: PartialState<T>
|
|
282
|
+
* }>}
|
|
283
|
+
* @template {State} T
|
|
284
|
+
*/
|
|
285
|
+
var Observable = function Observable(_ref4) {
|
|
286
|
+
var _ref4$children = _ref4.children,
|
|
287
|
+
children = _ref4$children === void 0 ? null : _ref4$children,
|
|
288
|
+
_ref4$prehooks = _ref4.prehooks,
|
|
289
|
+
prehooks = _ref4$prehooks === void 0 ? defaultPrehooks : _ref4$prehooks,
|
|
290
|
+
value = _ref4.value;
|
|
291
|
+
return /*#__PURE__*/_react["default"].createElement(ProviderInternal, {
|
|
292
|
+
provider: Provider,
|
|
293
|
+
value: useStore(prehooks, value)
|
|
294
|
+
}, children);
|
|
295
|
+
};
|
|
296
|
+
Observable.displayName = 'ObservableContext.Provider';
|
|
297
|
+
return Observable;
|
|
298
|
+
};
|
|
299
|
+
|
|
300
|
+
/**
|
|
301
|
+
* @returns {ObservableContext<T>}
|
|
302
|
+
* @template {State} T
|
|
303
|
+
*/
|
|
304
|
+
var createContext = function createContext() {
|
|
305
|
+
var Context = /*#__PURE__*/(0, _react.createContext)({
|
|
306
|
+
getState: reportNonReactUsage,
|
|
307
|
+
resetState: reportNonReactUsage,
|
|
308
|
+
setState: reportNonReactUsage,
|
|
309
|
+
subscribe: reportNonReactUsage
|
|
310
|
+
});
|
|
311
|
+
var provider = Context.Provider;
|
|
312
|
+
Context.Provider = makeObservable(provider);
|
|
313
|
+
return Context;
|
|
314
|
+
};
|
|
315
|
+
|
|
316
|
+
/**
|
|
317
|
+
* Actively monitors the store and triggers component re-render if any of the watched keys in the state objects changes
|
|
318
|
+
*
|
|
319
|
+
* @param {ObservableContext<T>} context
|
|
320
|
+
* @param {Array<string|keyof T>} [watchedKeys = []] A list of state object property paths to watch. A change in any of the referenced properties results in this component render.
|
|
321
|
+
* @returns {Store<T>}
|
|
322
|
+
* @template {State} T
|
|
323
|
+
*/
|
|
324
|
+
exports.createContext = createContext;
|
|
325
|
+
var useContext = function useContext(context) {
|
|
326
|
+
var watchedKeys = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : [];
|
|
327
|
+
/** @type {Store<T>} */
|
|
328
|
+
var store = (0, _react.useContext)(context);
|
|
329
|
+
var _useState7 = (0, _react.useState)(false),
|
|
330
|
+
_useState8 = _slicedToArray(_useState7, 2),
|
|
331
|
+
tripRender = _useState8[1];
|
|
332
|
+
var watched = (0, _react.useMemo)(function () {
|
|
333
|
+
return Array.isArray(watchedKeys) ? Array.from(new Set(watchedKeys)) : [];
|
|
334
|
+
}, [watchedKeys]);
|
|
335
|
+
(0, _react.useEffect)(function () {
|
|
336
|
+
if (!watched.length) {
|
|
337
|
+
return;
|
|
338
|
+
}
|
|
339
|
+
return store.subscribe(function (newChanges) {
|
|
340
|
+
watched.some(function (w) {
|
|
341
|
+
return (0, _lodash2["default"])(newChanges, w);
|
|
342
|
+
}) && tripRender(function (s) {
|
|
343
|
+
return !s;
|
|
344
|
+
});
|
|
345
|
+
});
|
|
346
|
+
}, [watched]);
|
|
347
|
+
return store;
|
|
334
348
|
};
|
|
335
|
-
exports.Provider = Provider;
|
|
336
|
-
Provider.displayName = 'ObservableContext.Provider';
|
|
337
349
|
|
|
338
350
|
/**
|
|
339
351
|
* @typedef {Context<Store<T>>} ObservableContext
|
|
@@ -389,7 +401,13 @@ Provider.displayName = 'ObservableContext.Provider';
|
|
|
389
401
|
* @template [P={}]
|
|
390
402
|
*/
|
|
391
403
|
|
|
404
|
+
/**
|
|
405
|
+
* @typedef {import("react").Provider<T>} Provider
|
|
406
|
+
* @template T
|
|
407
|
+
*/
|
|
408
|
+
|
|
392
409
|
/**
|
|
393
410
|
* @typedef {import("react").Context<T>} Context
|
|
394
411
|
* @template T
|
|
395
|
-
*/
|
|
412
|
+
*/
|
|
413
|
+
exports.useContext = useContext;
|
package/package.json
CHANGED