-
-
Notifications
You must be signed in to change notification settings - Fork 2k
Expand file tree
/
Copy pathcreate-context.js
More file actions
61 lines (50 loc) · 1.31 KB
/
create-context.js
File metadata and controls
61 lines (50 loc) · 1.31 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
import { enqueueRender } from './component';
import { NULL, COMPONENT_FORCE, CONTEXT_TYPE } from './constants';
export let i = 0;
export function createContext(defaultValue) {
function Context(props) {
if (!this.getChildContext) {
/** @type {Set<import('./internal').Component> | null} */
let subs = new Set();
let ctx = {};
ctx[Context._id] = this;
this.getChildContext = () => ctx;
this.componentWillUnmount = () => {
subs = NULL;
};
this.shouldComponentUpdate = function (_props) {
// @ts-expect-error even
if (this.props.value != _props.value) {
subs.forEach(c => {
c._bits |= COMPONENT_FORCE;
enqueueRender(c);
});
}
};
this.sub = c => {
subs.add(c);
let old = c.componentWillUnmount;
c.componentWillUnmount = () => {
if (subs) {
subs.delete(c);
}
if (old) old.call(c);
};
};
}
return props.children;
}
Context.$$typeof = CONTEXT_TYPE;
Context._id = '__cC' + i++;
Context._defaultValue = defaultValue;
/** @type {import('./internal').FunctionComponent} */
Context.Consumer = (props, contextValue) => {
return props.children(contextValue);
};
// we could also get rid of _contextRef entirely
Context.Provider =
Context._contextRef =
Context.Consumer.contextType =
Context;
return Context;
}