aoye 0.0.22 → 0.0.24
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/dist/aoye.cjs.js +729 -1090
- package/dist/aoye.cjs.js.map +1 -1
- package/dist/aoye.esm.js +720 -1086
- package/dist/aoye.esm.js.map +1 -1
- package/dist/index.d.ts +111 -212
- package/dist/index.umd.js +729 -1090
- package/dist/index.umd.js.map +1 -1
- package/package.json +2 -2
package/dist/aoye.cjs.js
CHANGED
|
@@ -2,996 +2,654 @@
|
|
|
2
2
|
|
|
3
3
|
var bobeShared = require('bobe-shared');
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
const
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
State2[State2["ScopeAbort"] = 128] = "ScopeAbort";
|
|
21
|
-
State2[State2["ScopeReady"] = 64] = "ScopeReady";
|
|
22
|
-
State2[State2["IsScope"] = 32] = "IsScope";
|
|
23
|
-
State2[State2["PullingDirty"] = 16] = "PullingDirty";
|
|
24
|
-
State2[State2["PullingUnknown"] = 8] = "PullingUnknown";
|
|
25
|
-
State2[State2["Unknown"] = 4] = "Unknown";
|
|
26
|
-
State2[State2["Dirty"] = 2] = "Dirty";
|
|
27
|
-
State2[State2["Pulling"] = 1] = "Pulling";
|
|
28
|
-
return State2;
|
|
29
|
-
})(State || {});
|
|
30
|
-
const DirtyState = 4 /* Unknown */ | 2 /* Dirty */;
|
|
31
|
-
const ScopeExecuted = 64 /* ScopeReady */ | 128 /* ScopeAbort */;
|
|
32
|
-
const ScopeAbort = 128 /* ScopeAbort */;
|
|
5
|
+
let _execId = 0;
|
|
6
|
+
let currentExecId = 0;
|
|
7
|
+
const execIdInc = () => ++_execId;
|
|
8
|
+
const execId = () => currentExecId;
|
|
9
|
+
const setExecId = v => currentExecId = v;
|
|
10
|
+
let pulling = null;
|
|
11
|
+
const setPulling = v => pulling = v;
|
|
12
|
+
const getPulling = () => pulling;
|
|
13
|
+
function runWithPulling(fn, scope) {
|
|
14
|
+
const oldPulling = pulling;
|
|
15
|
+
pulling = scope;
|
|
16
|
+
const ret = fn();
|
|
17
|
+
pulling = oldPulling;
|
|
18
|
+
return ret;
|
|
19
|
+
}
|
|
33
20
|
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
const
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
this.arr = [];
|
|
50
|
-
this.goUp = (arr, current, len) => {
|
|
51
|
-
let i = len - 1;
|
|
52
|
-
while (i > 0) {
|
|
53
|
-
const item = arr[i];
|
|
54
|
-
const pI = getParent(i, len);
|
|
55
|
-
const parent = arr[pI];
|
|
56
|
-
if (this.aIsUrgent(item, parent)) {
|
|
57
|
-
exchange(arr, i, pI);
|
|
58
|
-
i = pI;
|
|
59
|
-
} else {
|
|
60
|
-
break;
|
|
21
|
+
function mark(signal) {
|
|
22
|
+
let line = signal.emitHead;
|
|
23
|
+
while (line) {
|
|
24
|
+
const _line = line,
|
|
25
|
+
down = _line.down;
|
|
26
|
+
_line.up;
|
|
27
|
+
const scope = down.scope,
|
|
28
|
+
emitHead = down.emitHead,
|
|
29
|
+
state = down.state;
|
|
30
|
+
if (scope && scope.state & 128) ; else {
|
|
31
|
+
const notLocked = (state & 1) === 0;
|
|
32
|
+
down.state |= notLocked ? 2 : 16;
|
|
33
|
+
if (state & 32) {
|
|
34
|
+
if (notLocked && state & 512) {
|
|
35
|
+
addEffect(down);
|
|
61
36
|
}
|
|
37
|
+
} else if (emitHead) {
|
|
38
|
+
markUnknownDeep(emitHead);
|
|
62
39
|
}
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
40
|
+
}
|
|
41
|
+
line = line.nextEmitLine;
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
function markUnknownDeep(initialLine) {
|
|
45
|
+
const noPulling = !getPulling();
|
|
46
|
+
const stack = [initialLine];
|
|
47
|
+
let len = 1;
|
|
48
|
+
while (len > 0) {
|
|
49
|
+
let line = stack[--len];
|
|
50
|
+
stack[len] = null;
|
|
51
|
+
while (line) {
|
|
52
|
+
const _line2 = line,
|
|
53
|
+
down = _line2.down;
|
|
54
|
+
_line2.up;
|
|
55
|
+
const state = down.state,
|
|
56
|
+
scope = down.scope;
|
|
57
|
+
if (scope && scope.state & 128 || noPulling && state & 6) ; else {
|
|
58
|
+
const notLocked = (state & 1) === 0;
|
|
59
|
+
down.state |= notLocked ? 4 : 8;
|
|
60
|
+
if (state & 32) {
|
|
61
|
+
if (notLocked && state & 512) {
|
|
62
|
+
addEffect(down);
|
|
63
|
+
}
|
|
64
|
+
} else if (down.emitHead) {
|
|
65
|
+
stack[len++] = down.emitHead;
|
|
79
66
|
}
|
|
80
|
-
exchange(arr, i, point);
|
|
81
|
-
i = point;
|
|
82
67
|
}
|
|
83
|
-
|
|
84
|
-
}
|
|
85
|
-
// 添加一个元素
|
|
86
|
-
_add(current) {
|
|
87
|
-
this.arr.push(current);
|
|
88
|
-
const len = this.size();
|
|
89
|
-
if (len === 1) {
|
|
90
|
-
return;
|
|
68
|
+
line = line.nextEmitLine;
|
|
91
69
|
}
|
|
92
|
-
this.goUp(this.arr, current, len);
|
|
93
70
|
}
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
71
|
+
}
|
|
72
|
+
function pullDeep(root) {
|
|
73
|
+
let node = root,
|
|
74
|
+
top = null,
|
|
75
|
+
i = -1;
|
|
76
|
+
const lineStack = [];
|
|
77
|
+
do {
|
|
78
|
+
const _node = node,
|
|
79
|
+
state = _node.state,
|
|
80
|
+
scope = _node.scope;
|
|
81
|
+
let noSkipSelf = !(state & 193 || (state & 6) === 0 || scope && scope.state & 128);
|
|
82
|
+
const firstLine = node.recHead;
|
|
83
|
+
if (noSkipSelf) {
|
|
84
|
+
node.state |= 1;
|
|
85
|
+
if ((state & 2) === 0 && firstLine) {
|
|
86
|
+
node = firstLine.up;
|
|
87
|
+
lineStack[++i] = top;
|
|
88
|
+
top = firstLine;
|
|
89
|
+
continue;
|
|
90
|
+
}
|
|
103
91
|
}
|
|
104
|
-
const last = arr.pop();
|
|
105
|
-
const first = arr[0];
|
|
106
|
-
arr[0] = last;
|
|
107
|
-
this.goDown(this.arr, 0);
|
|
108
|
-
return first;
|
|
109
|
-
}
|
|
110
|
-
// 取得头元素
|
|
111
|
-
peek() {
|
|
112
|
-
return this.arr[0];
|
|
113
|
-
}
|
|
114
|
-
// 取得元素数量
|
|
115
|
-
size() {
|
|
116
|
-
return this.arr.length;
|
|
117
|
-
}
|
|
118
|
-
logTree() {
|
|
119
|
-
const arr = this.arr;
|
|
120
|
-
let i = 0;
|
|
121
|
-
let j = 1;
|
|
122
|
-
let level = 0;
|
|
123
|
-
const matrix = [];
|
|
124
92
|
do {
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
93
|
+
const _node2 = node,
|
|
94
|
+
state = _node2.state;
|
|
95
|
+
let noGoSibling = false;
|
|
96
|
+
if (noSkipSelf) {
|
|
97
|
+
if (state & 2) {
|
|
98
|
+
const prevValue = node.value;
|
|
99
|
+
const prevPulling = getPulling();
|
|
100
|
+
setPulling(node);
|
|
101
|
+
const value = node.get(false, false);
|
|
102
|
+
setPulling(prevPulling);
|
|
103
|
+
if (noGoSibling = value !== prevValue) {
|
|
104
|
+
let line = node.emitHead;
|
|
105
|
+
while (line) {
|
|
106
|
+
const _line3 = line,
|
|
107
|
+
down = _line3.down;
|
|
108
|
+
down.state &= -5;
|
|
109
|
+
down.state |= 2;
|
|
110
|
+
line = line.nextEmitLine;
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
} else {
|
|
114
|
+
transferDirtyState(node, state);
|
|
115
|
+
}
|
|
116
|
+
node.state &= -2;
|
|
117
|
+
}
|
|
118
|
+
if (node === root) {
|
|
119
|
+
return node.value;
|
|
120
|
+
}
|
|
121
|
+
if (!noGoSibling && top.nextRecLine) {
|
|
122
|
+
top = top.nextRecLine;
|
|
123
|
+
node = top.up;
|
|
124
|
+
break;
|
|
125
|
+
}
|
|
126
|
+
noSkipSelf = true;
|
|
127
|
+
node = top.down;
|
|
128
|
+
top = lineStack[i];
|
|
129
|
+
lineStack[i--] = null;
|
|
130
|
+
} while (true);
|
|
131
|
+
} while (true);
|
|
140
132
|
}
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
class TaskQueue {
|
|
147
|
-
constructor(callbackAble, aIsUrgent) {
|
|
148
|
-
this.callbackAble = callbackAble;
|
|
149
|
-
this.aIsUrgent = aIsUrgent;
|
|
150
|
-
this.isScheduling = false;
|
|
151
|
-
}
|
|
152
|
-
static create({
|
|
153
|
-
callbackAble,
|
|
154
|
-
aIsUrgent
|
|
155
|
-
}) {
|
|
156
|
-
const queue = new TaskQueue(callbackAble, aIsUrgent);
|
|
157
|
-
queue.taskQueue = new PriorityQueue(aIsUrgent);
|
|
158
|
-
return queue;
|
|
159
|
-
}
|
|
160
|
-
pushTask(task) {
|
|
161
|
-
const taskQueue = this.taskQueue,
|
|
162
|
-
isScheduling = this.isScheduling;
|
|
163
|
-
taskQueue._add(task);
|
|
164
|
-
if (!isScheduling) {
|
|
165
|
-
this.callbackAble(this.scheduleTask.bind(this));
|
|
166
|
-
this.isScheduling = true;
|
|
167
|
-
}
|
|
133
|
+
function transferDirtyState(node, state) {
|
|
134
|
+
if (state & 8) {
|
|
135
|
+
node.state = state & -9 | 4;
|
|
136
|
+
} else {
|
|
137
|
+
node.state &= -5;
|
|
168
138
|
}
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
let info = fn() || {};
|
|
174
|
-
info = {
|
|
175
|
-
...DefaultTaskControlReturn,
|
|
176
|
-
...info
|
|
177
|
-
};
|
|
178
|
-
if (info.finished) {
|
|
179
|
-
taskQueue.poll();
|
|
180
|
-
if (taskQueue.size() === 0) {
|
|
181
|
-
return this.isScheduling = false;
|
|
182
|
-
}
|
|
183
|
-
}
|
|
184
|
-
if (info.startNewCallbackAble) {
|
|
185
|
-
this.callbackAble(this.scheduleTask.bind(this));
|
|
186
|
-
} else {
|
|
187
|
-
this.scheduleTask();
|
|
188
|
-
}
|
|
139
|
+
if (state & 16) {
|
|
140
|
+
node.state = state & -17 | 2;
|
|
141
|
+
} else {
|
|
142
|
+
node.state &= -3;
|
|
189
143
|
}
|
|
190
144
|
}
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
return Keys2;
|
|
197
|
-
})(Keys || {});
|
|
198
|
-
const IsStore = /* @__PURE__ */Symbol("__AOYE_IS_STORE"),
|
|
199
|
-
StoreIgnoreKeys = /* @__PURE__ */Symbol("__AOYE_IGNORE_KEYS");
|
|
200
|
-
|
|
201
|
-
let channel = globalThis.MessageChannel ? new MessageChannel() : null;
|
|
202
|
-
if (globalThis.MessageChannel) {
|
|
203
|
-
channel = new MessageChannel();
|
|
145
|
+
const effectQueue = [];
|
|
146
|
+
let consumeI = -1,
|
|
147
|
+
produceI = -1;
|
|
148
|
+
function addEffect(effect) {
|
|
149
|
+
effectQueue[++produceI] = effect;
|
|
204
150
|
}
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
setTimeout(fn);
|
|
151
|
+
function flushEffect() {
|
|
152
|
+
if (consumeI !== -1) {
|
|
153
|
+
return;
|
|
209
154
|
}
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
if (
|
|
213
|
-
|
|
214
|
-
channel.port2.removeEventListener("message", onMessage);
|
|
155
|
+
while (++consumeI <= produceI) {
|
|
156
|
+
const effect = effectQueue[consumeI];
|
|
157
|
+
if (effect.state | 6) {
|
|
158
|
+
effect.get();
|
|
215
159
|
}
|
|
160
|
+
effectQueue[consumeI] = null;
|
|
216
161
|
}
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
}
|
|
220
|
-
|
|
221
|
-
const
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
return toRaw(a[Keys.Raw]);
|
|
162
|
+
consumeI = -1;
|
|
163
|
+
produceI = -1;
|
|
164
|
+
}
|
|
165
|
+
let _batchDeep = 0;
|
|
166
|
+
const batchStart = () => _batchDeep++;
|
|
167
|
+
const batchEnd = () => {
|
|
168
|
+
_batchDeep--;
|
|
169
|
+
if (_batchDeep === 0) {
|
|
170
|
+
flushEffect();
|
|
227
171
|
}
|
|
228
|
-
return a;
|
|
229
172
|
};
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
static {
|
|
246
|
-
this.Micro = "__Micro_";
|
|
247
|
-
}
|
|
248
|
-
static {
|
|
249
|
-
this.Macro = "__Macro_";
|
|
173
|
+
const batchDeep = () => _batchDeep;
|
|
174
|
+
function unlink(line, deep) {
|
|
175
|
+
const nextEmitLine = line.nextEmitLine,
|
|
176
|
+
prevEmitLine = line.prevEmitLine,
|
|
177
|
+
nextRecLine = line.nextRecLine,
|
|
178
|
+
prevRecLine = line.prevRecLine,
|
|
179
|
+
up = line.up,
|
|
180
|
+
down = line.down,
|
|
181
|
+
prevOutLink = line.prevOutLink,
|
|
182
|
+
nextOutLink = line.nextOutLink;
|
|
183
|
+
const scope = down.scope;
|
|
184
|
+
if (prevEmitLine) {
|
|
185
|
+
prevEmitLine.nextEmitLine = nextEmitLine;
|
|
186
|
+
} else {
|
|
187
|
+
up.emitHead = nextEmitLine;
|
|
250
188
|
}
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
this.lastEffectItem = null;
|
|
256
|
-
this.onOneSetEffectsAdded?.(subQueue, this.effectQueue);
|
|
189
|
+
if (nextEmitLine) {
|
|
190
|
+
nextEmitLine.prevEmitLine = prevEmitLine;
|
|
191
|
+
} else {
|
|
192
|
+
up.emitTail = prevEmitLine;
|
|
257
193
|
}
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
194
|
+
if (prevRecLine) {
|
|
195
|
+
prevRecLine.nextRecLine = nextRecLine;
|
|
196
|
+
} else {
|
|
197
|
+
down.recHead = nextRecLine;
|
|
262
198
|
}
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
199
|
+
if (nextRecLine) {
|
|
200
|
+
nextRecLine.prevRecLine = prevRecLine;
|
|
201
|
+
} else {
|
|
202
|
+
down.recTail = prevRecLine;
|
|
203
|
+
}
|
|
204
|
+
if (prevOutLink) {
|
|
205
|
+
prevOutLink.nextOutLink = nextOutLink;
|
|
206
|
+
}
|
|
207
|
+
if (nextOutLink) {
|
|
208
|
+
nextOutLink.prevOutLink = prevOutLink;
|
|
209
|
+
}
|
|
210
|
+
if (scope && scope.outLink === line) {
|
|
211
|
+
scope.outLink = nextOutLink;
|
|
212
|
+
}
|
|
213
|
+
if (up.state & 32) {
|
|
214
|
+
up.dispose();
|
|
215
|
+
} else if (deep && !prevEmitLine && !nextEmitLine) {
|
|
216
|
+
let _ref = up,
|
|
217
|
+
line = _ref.recHead;
|
|
218
|
+
while (line) {
|
|
219
|
+
const next = line.nextRecLine;
|
|
220
|
+
unlink(line, true);
|
|
221
|
+
line = next;
|
|
222
|
+
}
|
|
270
223
|
}
|
|
271
224
|
}
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
225
|
+
function dispose() {
|
|
226
|
+
let toDel = this.recHead,
|
|
227
|
+
emitHead = this.emitHead;
|
|
228
|
+
while (toDel) {
|
|
229
|
+
const _toDel = toDel,
|
|
230
|
+
up = _toDel.up,
|
|
231
|
+
nextRecLine = _toDel.nextRecLine;
|
|
232
|
+
if ((up.state & 32) === 0) {
|
|
233
|
+
unlink(toDel, true);
|
|
234
|
+
toDel = nextRecLine;
|
|
235
|
+
continue;
|
|
236
|
+
}
|
|
237
|
+
let node = up,
|
|
238
|
+
top = null,
|
|
239
|
+
i = -1;
|
|
240
|
+
const lineStack = [];
|
|
241
|
+
outer: do {
|
|
242
|
+
let noSkipSelf = node.state & 32 && (node.state & 128) === 0;
|
|
243
|
+
const firstLine = node.recHead;
|
|
244
|
+
if (noSkipSelf && firstLine) {
|
|
245
|
+
node = firstLine.up;
|
|
246
|
+
lineStack[++i] = top;
|
|
247
|
+
top = firstLine;
|
|
248
|
+
continue;
|
|
249
|
+
}
|
|
250
|
+
do {
|
|
251
|
+
if (noSkipSelf) {
|
|
252
|
+
releaseScope(node);
|
|
253
|
+
}
|
|
254
|
+
if (node === up) {
|
|
255
|
+
break outer;
|
|
256
|
+
}
|
|
257
|
+
if (top.nextRecLine) {
|
|
258
|
+
top = top.nextRecLine;
|
|
259
|
+
node = top.up;
|
|
260
|
+
break;
|
|
261
|
+
}
|
|
262
|
+
noSkipSelf = true;
|
|
263
|
+
node = top.down;
|
|
264
|
+
top = lineStack[i];
|
|
265
|
+
lineStack[i--] = null;
|
|
266
|
+
} while (true);
|
|
267
|
+
} while (true);
|
|
268
|
+
toDel = nextRecLine;
|
|
293
269
|
}
|
|
270
|
+
releaseScope(this);
|
|
271
|
+
if (emitHead) unlink(emitHead, false);
|
|
294
272
|
}
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
this.taskQueue = TaskQueue.create({
|
|
299
|
-
callbackAble: macro,
|
|
300
|
-
aIsUrgent: (a, b) => a.time < b.time
|
|
301
|
-
});
|
|
302
|
-
}
|
|
303
|
-
onOneSetEffectsAdded(subQueue, queue) {
|
|
304
|
-
const task = () => {
|
|
305
|
-
subQueue.forEach((effect, item) => {
|
|
306
|
-
queue.delete(item);
|
|
307
|
-
effect.runIfDirty();
|
|
308
|
-
});
|
|
309
|
-
};
|
|
310
|
-
task.time = Date.now();
|
|
311
|
-
this.taskQueue.pushTask(task);
|
|
312
|
-
}
|
|
273
|
+
function clean(onClean) {
|
|
274
|
+
const current = getPulling();
|
|
275
|
+
current.clean = onClean;
|
|
313
276
|
}
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
});
|
|
321
|
-
}
|
|
322
|
-
onOneSetEffectsAdded(subQueue, queue) {
|
|
323
|
-
const task = () => {
|
|
324
|
-
subQueue.forEach((effect, item) => {
|
|
325
|
-
queue.delete(item);
|
|
326
|
-
effect.runIfDirty();
|
|
327
|
-
});
|
|
328
|
-
};
|
|
329
|
-
task.time = Date.now();
|
|
330
|
-
this.taskQueue.pushTask(task);
|
|
277
|
+
function releaseScope(scope) {
|
|
278
|
+
let outLink = scope.outLink;
|
|
279
|
+
while (outLink) {
|
|
280
|
+
const next = outLink.nextOutLink;
|
|
281
|
+
unlink(outLink, true);
|
|
282
|
+
outLink = next;
|
|
331
283
|
}
|
|
284
|
+
scope.state |= 128;
|
|
285
|
+
scope.clean?.();
|
|
286
|
+
scope.clean = null;
|
|
332
287
|
}
|
|
333
|
-
const _scheduler = {
|
|
334
|
-
[Scheduler.Sync]: new SyncScheduler(),
|
|
335
|
-
[Scheduler.Micro]: new MicroScheduler(),
|
|
336
|
-
[Scheduler.Macro]: new MacroScheduler(),
|
|
337
|
-
[Scheduler.Layout]: new LayoutScheduler()
|
|
338
|
-
};
|
|
339
|
-
globalThis["sche"] = _scheduler[Scheduler.Sync];
|
|
340
|
-
const registerScheduler = (key, Ctor) => _scheduler[key] = new Ctor();
|
|
341
288
|
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
const _DefaultDFSOpt$opt = {
|
|
352
|
-
...DefaultDFSOpt,
|
|
353
|
-
...opt
|
|
354
|
-
},
|
|
355
|
-
isUp = _DefaultDFSOpt$opt.isUp,
|
|
356
|
-
begin = _DefaultDFSOpt$opt.begin,
|
|
357
|
-
complete = _DefaultDFSOpt$opt.complete,
|
|
358
|
-
lineStack = _DefaultDFSOpt$opt.breakStack,
|
|
359
|
-
breakLine = _DefaultDFSOpt$opt.breakLine;
|
|
360
|
-
let node = opt.breakNode || root;
|
|
361
|
-
let line = breakLine;
|
|
362
|
-
const listKey = isUp ? "recStart" : "emitStart";
|
|
363
|
-
const nodeKey = isUp ? "upstream" : "downstream";
|
|
364
|
-
const nextLineKey = isUp ? "nextRecLine" : "nextEmitLine";
|
|
365
|
-
const reverseNodeKey = isUp ? "downstream" : "upstream";
|
|
366
|
-
while (true) {
|
|
367
|
-
let notGoDeep = begin?.({
|
|
368
|
-
node,
|
|
369
|
-
lineFromUp: line,
|
|
370
|
-
walkedLine: lineStack
|
|
371
|
-
});
|
|
372
|
-
lineStack.push(line);
|
|
373
|
-
line = node[listKey];
|
|
374
|
-
if (line && !notGoDeep) {
|
|
375
|
-
const firstChild = line[nodeKey];
|
|
376
|
-
node = firstChild;
|
|
377
|
-
continue;
|
|
378
|
-
}
|
|
379
|
-
while (true) {
|
|
380
|
-
const noGoSibling = complete?.({
|
|
381
|
-
node,
|
|
382
|
-
lineToDeep: line,
|
|
383
|
-
walkedLine: lineStack,
|
|
384
|
-
notGoDeep
|
|
385
|
-
});
|
|
386
|
-
line = lineStack.pop();
|
|
387
|
-
if (node === root) {
|
|
388
|
-
return;
|
|
389
|
-
}
|
|
390
|
-
notGoDeep = false;
|
|
391
|
-
const nextLine = line[nextLineKey];
|
|
392
|
-
if (!noGoSibling && nextLine) {
|
|
393
|
-
line = nextLine;
|
|
394
|
-
node = nextLine[nodeKey];
|
|
395
|
-
break;
|
|
396
|
-
}
|
|
397
|
-
node = line[reverseNodeKey];
|
|
398
|
-
}
|
|
289
|
+
function link(up = null, down = null) {
|
|
290
|
+
const prevEmitLine = up.emitTail,
|
|
291
|
+
scopeUp = up.scope;
|
|
292
|
+
let recHead = down.recHead,
|
|
293
|
+
recTail = down.recTail,
|
|
294
|
+
scopeDown = down.scope;
|
|
295
|
+
if (scopeDown && scopeDown !== scopeUp && (up.state & 32) === 0) {
|
|
296
|
+
outLink(up, down);
|
|
297
|
+
return;
|
|
399
298
|
}
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
/** 上游顶点 */
|
|
405
|
-
this.upstream = null;
|
|
406
|
-
/** 上游节点 发出的上一条线 */
|
|
407
|
-
this.prevEmitLine = null;
|
|
408
|
-
/** 上游节点 发出的下一条线 */
|
|
409
|
-
this.nextEmitLine = null;
|
|
410
|
-
/** 下游顶点 */
|
|
411
|
-
this.downstream = null;
|
|
412
|
-
/** 下游节点 接收的上一条线 */
|
|
413
|
-
this.prevRecLine = null;
|
|
414
|
-
/** 下游节点 接收的下一条线 */
|
|
415
|
-
this.nextRecLine = null;
|
|
416
|
-
/** 表示 scope 当前存在的 外部 link */
|
|
417
|
-
this.prevOutLink = null;
|
|
418
|
-
this.nextOutLink = null;
|
|
419
|
-
}
|
|
420
|
-
static link(v1, v2) {
|
|
421
|
-
let emitEnd = v1.emitEnd,
|
|
422
|
-
recEnd = v2.recEnd,
|
|
423
|
-
recStart = v2.recStart,
|
|
424
|
-
noRecEnd = !recEnd,
|
|
425
|
-
head = {
|
|
426
|
-
nextRecLine: recStart
|
|
427
|
-
},
|
|
428
|
-
line;
|
|
429
|
-
recEnd = recEnd || head;
|
|
430
|
-
const _ref = recEnd || {},
|
|
431
|
-
nextRecLine = _ref.nextRecLine;
|
|
432
|
-
if (!nextRecLine) {
|
|
433
|
-
line = new Line();
|
|
434
|
-
Line.emit_line(v1, line);
|
|
435
|
-
Line.rec_line(v2, line);
|
|
436
|
-
emitEnd && Line.line_line_emit(emitEnd, line);
|
|
437
|
-
!noRecEnd && Line.line_line_rec(recEnd, line);
|
|
438
|
-
} else if (nextRecLine.upstream === v1) {
|
|
439
|
-
v2.recEnd = nextRecLine;
|
|
440
|
-
} else {
|
|
441
|
-
line = new Line();
|
|
442
|
-
Line.emit_line(v1, line);
|
|
443
|
-
Line.rec_line(v2, line);
|
|
444
|
-
emitEnd && Line.line_line_emit(emitEnd, line);
|
|
445
|
-
Line.insert_line_rec(recEnd, nextRecLine, line);
|
|
446
|
-
}
|
|
447
|
-
for (const key in head) {
|
|
448
|
-
head[key] = null;
|
|
449
|
-
}
|
|
450
|
-
if (line && v2.scope && v1.scope !== v2.scope && (v1.state & State.IsScope) === 0) {
|
|
451
|
-
const first = v2.scope.outLink;
|
|
452
|
-
if (!first) {
|
|
453
|
-
v2.scope.outLink = line;
|
|
454
|
-
} else {
|
|
455
|
-
first.prevOutLink = line;
|
|
456
|
-
line.nextOutLink = first;
|
|
457
|
-
v2.scope.outLink = line;
|
|
458
|
-
}
|
|
459
|
-
}
|
|
299
|
+
const nextRec = recTail ? recTail.nextRecLine : recHead;
|
|
300
|
+
const eid = execId();
|
|
301
|
+
if (prevEmitLine && prevEmitLine.down === down && prevEmitLine.execId === eid) {
|
|
302
|
+
return;
|
|
460
303
|
}
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
line.nextEmitLine = null;
|
|
472
|
-
line.prevRecLine = null;
|
|
473
|
-
line.nextRecLine = null;
|
|
474
|
-
line.upstream = null;
|
|
475
|
-
line.downstream = null;
|
|
476
|
-
line.prevOutLink = null;
|
|
477
|
-
line.nextOutLink = null;
|
|
478
|
-
const downNode = downstream;
|
|
479
|
-
if (prevOutLink) {
|
|
480
|
-
prevOutLink.nextOutLink = nextOutLink;
|
|
481
|
-
}
|
|
482
|
-
if (nextOutLink) {
|
|
483
|
-
nextOutLink.prevOutLink = prevOutLink;
|
|
484
|
-
}
|
|
485
|
-
if (downNode.scope && downNode.scope.outLink === line) {
|
|
486
|
-
downNode.scope.outLink = nextOutLink;
|
|
487
|
-
}
|
|
304
|
+
if (!nextRec) {
|
|
305
|
+
const line = {
|
|
306
|
+
execId: eid,
|
|
307
|
+
up,
|
|
308
|
+
down,
|
|
309
|
+
prevEmitLine,
|
|
310
|
+
nextEmitLine: null,
|
|
311
|
+
prevRecLine: recTail,
|
|
312
|
+
nextRecLine: null
|
|
313
|
+
};
|
|
488
314
|
if (prevEmitLine) {
|
|
489
|
-
prevEmitLine.nextEmitLine =
|
|
315
|
+
prevEmitLine.nextEmitLine = line;
|
|
490
316
|
} else {
|
|
491
|
-
|
|
317
|
+
up.emitHead = line;
|
|
492
318
|
}
|
|
493
|
-
|
|
494
|
-
|
|
319
|
+
up.emitTail = line;
|
|
320
|
+
if (recTail) {
|
|
321
|
+
recTail.nextRecLine = line;
|
|
495
322
|
} else {
|
|
496
|
-
|
|
497
|
-
}
|
|
498
|
-
if (prevRecLine) {
|
|
499
|
-
prevRecLine.nextRecLine = nextRecLine;
|
|
500
|
-
} else {
|
|
501
|
-
downstream.recStart = nextRecLine;
|
|
502
|
-
}
|
|
503
|
-
if (nextRecLine) {
|
|
504
|
-
nextRecLine.prevRecLine = prevRecLine;
|
|
505
|
-
} else {
|
|
506
|
-
downstream.recEnd = prevRecLine;
|
|
507
|
-
}
|
|
508
|
-
}
|
|
509
|
-
static unlinkRec(line) {
|
|
510
|
-
let toDel = line;
|
|
511
|
-
while (toDel) {
|
|
512
|
-
const memoNext = toDel.nextRecLine;
|
|
513
|
-
Line.unlink(toDel);
|
|
514
|
-
toDel = memoNext;
|
|
323
|
+
down.recHead = line;
|
|
515
324
|
}
|
|
325
|
+
down.recTail = line;
|
|
326
|
+
return;
|
|
516
327
|
}
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
|
|
521
|
-
Line.unlink(toDel);
|
|
522
|
-
toDel = memoNext;
|
|
523
|
-
}
|
|
328
|
+
if (nextRec.up === up) {
|
|
329
|
+
nextRec.execId = eid;
|
|
330
|
+
down.recTail = nextRec;
|
|
331
|
+
return;
|
|
524
332
|
}
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
|
|
333
|
+
const line = {
|
|
334
|
+
execId: eid,
|
|
335
|
+
up,
|
|
336
|
+
down,
|
|
337
|
+
prevEmitLine,
|
|
338
|
+
nextEmitLine: null,
|
|
339
|
+
prevRecLine: recTail,
|
|
340
|
+
nextRecLine: nextRec
|
|
341
|
+
};
|
|
342
|
+
if (prevEmitLine) {
|
|
343
|
+
prevEmitLine.nextEmitLine = line;
|
|
344
|
+
} else {
|
|
345
|
+
up.emitHead = line;
|
|
532
346
|
}
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
downstream.recEnd = line;
|
|
539
|
-
line.downstream = downstream;
|
|
540
|
-
}
|
|
541
|
-
/** 同一节点发出的 两个条线 相连 */
|
|
542
|
-
static line_line_emit(l1, l2) {
|
|
543
|
-
if (!l1 || !l2) return;
|
|
544
|
-
l1.nextEmitLine = l2;
|
|
545
|
-
l2.prevEmitLine = l1;
|
|
546
|
-
}
|
|
547
|
-
/** 同一节点接收的 两个条线 相连 */
|
|
548
|
-
static line_line_rec(l1, l2) {
|
|
549
|
-
if (!l1 || !l2) return;
|
|
550
|
-
l1.nextRecLine = l2;
|
|
551
|
-
l2.prevRecLine = l1;
|
|
552
|
-
}
|
|
553
|
-
static insert_line_emit(l1, l2, ins) {
|
|
554
|
-
l1.nextEmitLine = ins;
|
|
555
|
-
ins.prevEmitLine = l1;
|
|
556
|
-
l2.prevEmitLine = ins;
|
|
557
|
-
ins.nextEmitLine = l2;
|
|
558
|
-
}
|
|
559
|
-
static insert_line_rec(l1, l2, ins) {
|
|
560
|
-
l1.nextRecLine = ins;
|
|
561
|
-
ins.prevRecLine = l1;
|
|
562
|
-
l2.prevRecLine = ins;
|
|
563
|
-
ins.nextRecLine = l2;
|
|
347
|
+
up.emitTail = line;
|
|
348
|
+
if (recHead) {
|
|
349
|
+
recTail.nextRecLine = line;
|
|
350
|
+
} else {
|
|
351
|
+
down.recHead = line;
|
|
564
352
|
}
|
|
353
|
+
down.recTail = line;
|
|
354
|
+
if (recTail) recTail.nextRecLine = line;
|
|
355
|
+
nextRec.prevRecLine = line;
|
|
565
356
|
}
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
let
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
357
|
+
function outLink(up = null, down = null) {
|
|
358
|
+
const prevEmitLine = up.emitTail;
|
|
359
|
+
let recHead = down.recHead,
|
|
360
|
+
recTail = down.recTail,
|
|
361
|
+
scopeDown = down.scope;
|
|
362
|
+
const nextRec = recTail ? recTail.nextRecLine : recHead;
|
|
363
|
+
if (!nextRec) {
|
|
364
|
+
const line = {
|
|
365
|
+
execId: execId(),
|
|
366
|
+
up,
|
|
367
|
+
down,
|
|
368
|
+
prevEmitLine,
|
|
369
|
+
nextEmitLine: null,
|
|
370
|
+
prevRecLine: recTail,
|
|
371
|
+
nextRecLine: null,
|
|
372
|
+
nextOutLink: null,
|
|
373
|
+
prevOutLink: null
|
|
374
|
+
};
|
|
375
|
+
if (prevEmitLine) {
|
|
376
|
+
prevEmitLine.nextEmitLine = line;
|
|
574
377
|
} else {
|
|
575
|
-
|
|
378
|
+
up.emitHead = line;
|
|
576
379
|
}
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
if (upstream.emitStart === upstream.emitEnd) {
|
|
583
|
-
unlinkSingleRefedNode(upstream);
|
|
584
|
-
} else {
|
|
585
|
-
Line.unlink(line);
|
|
586
|
-
}
|
|
587
|
-
}
|
|
588
|
-
function unlinkSingleRefedNode(delRoot) {
|
|
589
|
-
let toUnlink;
|
|
590
|
-
dfs(delRoot, {
|
|
591
|
-
isUp: true,
|
|
592
|
-
begin: ({
|
|
593
|
-
node
|
|
594
|
-
}) => {
|
|
595
|
-
doUnlink(toUnlink);
|
|
596
|
-
toUnlink = null;
|
|
597
|
-
if (node.emitStart !== node.emitEnd) {
|
|
598
|
-
return true;
|
|
599
|
-
}
|
|
600
|
-
},
|
|
601
|
-
complete: ({
|
|
602
|
-
node,
|
|
603
|
-
notGoDeep
|
|
604
|
-
}) => {
|
|
605
|
-
doUnlink(toUnlink);
|
|
606
|
-
toUnlink = null;
|
|
607
|
-
const isSingleRefed = !notGoDeep;
|
|
608
|
-
if (isSingleRefed) {
|
|
609
|
-
toUnlink = node.emitStart;
|
|
610
|
-
}
|
|
380
|
+
up.emitTail = line;
|
|
381
|
+
if (recTail) {
|
|
382
|
+
recTail.nextRecLine = line;
|
|
383
|
+
} else {
|
|
384
|
+
down.recHead = line;
|
|
611
385
|
}
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
}
|
|
615
|
-
function doUnlink(line) {
|
|
616
|
-
if (!line) {
|
|
386
|
+
down.recTail = line;
|
|
387
|
+
makeOutLink(scopeDown, line);
|
|
617
388
|
return;
|
|
618
389
|
}
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
let toDel = this.recStart;
|
|
623
|
-
while (toDel) {
|
|
624
|
-
const memoNext = toDel.nextRecLine;
|
|
625
|
-
const upstream = toDel.upstream;
|
|
626
|
-
if (upstream.state & State.IsScope) {
|
|
627
|
-
dfs(upstream, {
|
|
628
|
-
isUp: true,
|
|
629
|
-
begin: ({
|
|
630
|
-
node
|
|
631
|
-
}) => {
|
|
632
|
-
if ((node.state & State.IsScope) === 0 || node.state & ScopeAbort) return true;
|
|
633
|
-
},
|
|
634
|
-
complete: ({
|
|
635
|
-
node: scope,
|
|
636
|
-
notGoDeep
|
|
637
|
-
}) => {
|
|
638
|
-
const shouldAbort = !notGoDeep;
|
|
639
|
-
if (shouldAbort) {
|
|
640
|
-
releaseScope(scope);
|
|
641
|
-
}
|
|
642
|
-
}
|
|
643
|
-
});
|
|
644
|
-
} else {
|
|
645
|
-
unlinkSingleLine(toDel);
|
|
646
|
-
}
|
|
647
|
-
toDel = memoNext;
|
|
390
|
+
if (nextRec.up === up) {
|
|
391
|
+
down.recTail = nextRec;
|
|
392
|
+
return;
|
|
648
393
|
}
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
394
|
+
const line = {
|
|
395
|
+
execId: execId(),
|
|
396
|
+
up,
|
|
397
|
+
down,
|
|
398
|
+
prevEmitLine,
|
|
399
|
+
nextEmitLine: null,
|
|
400
|
+
prevRecLine: recTail,
|
|
401
|
+
nextRecLine: nextRec,
|
|
402
|
+
nextOutLink: null,
|
|
403
|
+
prevOutLink: null
|
|
404
|
+
};
|
|
405
|
+
if (prevEmitLine) {
|
|
406
|
+
prevEmitLine.nextEmitLine = line;
|
|
407
|
+
} else {
|
|
408
|
+
up.emitHead = line;
|
|
658
409
|
}
|
|
659
|
-
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
}
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
const res = fn();
|
|
670
|
-
G.PullingSignal = prevPulling;
|
|
671
|
-
return res;
|
|
672
|
-
}
|
|
673
|
-
function getPulling() {
|
|
674
|
-
return G.PullingSignal;
|
|
410
|
+
up.emitTail = line;
|
|
411
|
+
if (recHead) {
|
|
412
|
+
recTail.nextRecLine = line;
|
|
413
|
+
} else {
|
|
414
|
+
down.recHead = line;
|
|
415
|
+
}
|
|
416
|
+
down.recTail = line;
|
|
417
|
+
if (recTail) recTail.nextRecLine = line;
|
|
418
|
+
nextRec.prevRecLine = line;
|
|
419
|
+
makeOutLink(scopeDown, line);
|
|
675
420
|
}
|
|
676
|
-
function
|
|
677
|
-
|
|
421
|
+
function makeOutLink(scopeDown, line) {
|
|
422
|
+
const first = scopeDown.outLink;
|
|
423
|
+
if (first) {
|
|
424
|
+
first.prevOutLink = line;
|
|
425
|
+
line.nextOutLink = first;
|
|
426
|
+
}
|
|
427
|
+
scopeDown.outLink = line;
|
|
678
428
|
}
|
|
679
429
|
|
|
680
|
-
|
|
681
|
-
|
|
682
|
-
|
|
683
|
-
|
|
684
|
-
|
|
685
|
-
|
|
686
|
-
|
|
687
|
-
|
|
688
|
-
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
692
|
-
|
|
693
|
-
|
|
694
|
-
|
|
695
|
-
|
|
696
|
-
|
|
697
|
-
|
|
698
|
-
if (isEffect) {
|
|
699
|
-
node.state |= inPullingArea ? State.PullingUnknown : State.Unknown;
|
|
700
|
-
} else if (!isLeaf) {
|
|
701
|
-
node.state |= State.Dirty;
|
|
430
|
+
class Computed {
|
|
431
|
+
emitHead = null;
|
|
432
|
+
emitTail = null;
|
|
433
|
+
recHead = null;
|
|
434
|
+
recTail = null;
|
|
435
|
+
state = 0;
|
|
436
|
+
scope = getPulling();
|
|
437
|
+
value = null;
|
|
438
|
+
constructor(callback) {
|
|
439
|
+
this.callback = callback;
|
|
440
|
+
}
|
|
441
|
+
get(shouldLink = true, notForceUpdate = true) {
|
|
442
|
+
const scope = this.scope;
|
|
443
|
+
if (scope && scope.state & 128) return this.value;
|
|
444
|
+
const down = getPulling();
|
|
445
|
+
if (this.recHead && notForceUpdate) {
|
|
446
|
+
if (this.state & 6) {
|
|
447
|
+
this.value = pullDeep(this);
|
|
702
448
|
}
|
|
703
|
-
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
710
|
-
|
|
449
|
+
} else {
|
|
450
|
+
this.state |= 1;
|
|
451
|
+
const nextId = execIdInc();
|
|
452
|
+
const prevId = execId();
|
|
453
|
+
setExecId(nextId);
|
|
454
|
+
setPulling(this);
|
|
455
|
+
this.recTail = null;
|
|
456
|
+
this.value = this.callback(this);
|
|
457
|
+
this.state &= -2;
|
|
458
|
+
setPulling(down);
|
|
459
|
+
setExecId(prevId);
|
|
460
|
+
transferDirtyState(this, this.state);
|
|
461
|
+
let line = this.recTail?.nextRecLine;
|
|
462
|
+
while (line) {
|
|
463
|
+
const nextLine = line.nextRecLine;
|
|
464
|
+
unlink(line, true);
|
|
465
|
+
line = nextLine;
|
|
711
466
|
}
|
|
712
467
|
}
|
|
713
|
-
if (
|
|
714
|
-
|
|
715
|
-
parent = node;
|
|
716
|
-
node = emitStart.downstream;
|
|
717
|
-
noGoDeep = false;
|
|
718
|
-
continue;
|
|
468
|
+
if (shouldLink && down && (down.state & 256) === 0) {
|
|
469
|
+
link(this, down);
|
|
719
470
|
}
|
|
720
|
-
|
|
721
|
-
if (i === -1) {
|
|
722
|
-
break outer;
|
|
723
|
-
}
|
|
724
|
-
const backLine = stack[i];
|
|
725
|
-
const nextLine = backLine.nextEmitLine;
|
|
726
|
-
if (nextLine) {
|
|
727
|
-
node = nextLine.downstream;
|
|
728
|
-
stack[i] = nextLine;
|
|
729
|
-
break;
|
|
730
|
-
}
|
|
731
|
-
node = parent;
|
|
732
|
-
if (--i !== -1) {
|
|
733
|
-
parent = stack[i].upstream;
|
|
734
|
-
}
|
|
735
|
-
}
|
|
736
|
-
} while (true);
|
|
737
|
-
};
|
|
738
|
-
const pullingPostprocess = node => {
|
|
739
|
-
let s = node.state;
|
|
740
|
-
s &= ~State.Pulling;
|
|
741
|
-
if (s & State.PullingUnknown) {
|
|
742
|
-
s = s & ~State.PullingUnknown | State.Unknown;
|
|
471
|
+
return this.value;
|
|
743
472
|
}
|
|
744
|
-
|
|
745
|
-
|
|
473
|
+
}
|
|
474
|
+
|
|
746
475
|
class Signal {
|
|
747
|
-
|
|
748
|
-
|
|
749
|
-
|
|
750
|
-
|
|
751
|
-
|
|
752
|
-
this.
|
|
753
|
-
|
|
754
|
-
|
|
755
|
-
|
|
756
|
-
|
|
757
|
-
|
|
758
|
-
|
|
759
|
-
this.scheduler = null;
|
|
760
|
-
this.value = null;
|
|
761
|
-
this.outLink = null;
|
|
762
|
-
this.pull = null;
|
|
763
|
-
/** 记录当前 effect 中 clean */
|
|
764
|
-
this.clean = null;
|
|
765
|
-
}
|
|
766
|
-
static {
|
|
767
|
-
this.Pulling = null;
|
|
768
|
-
}
|
|
769
|
-
static create(nextValue, {
|
|
770
|
-
customPull,
|
|
771
|
-
isScope,
|
|
772
|
-
scope,
|
|
773
|
-
immediate,
|
|
774
|
-
...rest
|
|
775
|
-
}) {
|
|
776
|
-
const s = new Signal(nextValue, customPull);
|
|
777
|
-
s.pull = s.customPull || s.DEFAULT_PULL;
|
|
778
|
-
Object.assign(s, rest);
|
|
779
|
-
if (isScope) {
|
|
780
|
-
s.state |= State.IsScope;
|
|
781
|
-
}
|
|
782
|
-
if (scope !== void 0) {
|
|
783
|
-
s.scope = scope;
|
|
784
|
-
}
|
|
785
|
-
return s;
|
|
786
|
-
}
|
|
787
|
-
DEFAULT_PULL() {
|
|
788
|
-
return this.nextValue;
|
|
789
|
-
}
|
|
790
|
-
/**
|
|
791
|
-
* 递归拉取负责建立以来链
|
|
792
|
-
*/
|
|
793
|
-
pullRecurse(shouldLink = true) {
|
|
794
|
-
G.PullingRecurseDeep++;
|
|
795
|
-
const downstream = G.PullingSignal;
|
|
796
|
-
this.linkWhenPull(downstream, shouldLink);
|
|
797
|
-
try {
|
|
798
|
-
if (this.version === G.version) {
|
|
799
|
-
return this.value;
|
|
800
|
-
}
|
|
801
|
-
if (this.pull !== this.DEFAULT_PULL) this.recEnd = null;
|
|
802
|
-
this.state |= State.Pulling;
|
|
803
|
-
G.PullingSignal = this;
|
|
804
|
-
this.clean?.();
|
|
805
|
-
this.clean = null;
|
|
806
|
-
let v = this.pull();
|
|
807
|
-
if (this.state & State.IsScope && typeof v === "function") {
|
|
808
|
-
const fn = v;
|
|
809
|
-
this.clean = () => runWithPulling(fn, null);
|
|
810
|
-
v = this.value;
|
|
476
|
+
scope = getPulling();
|
|
477
|
+
emitHead = null;
|
|
478
|
+
emitTail = null;
|
|
479
|
+
state = 0;
|
|
480
|
+
constructor(value) {
|
|
481
|
+
this.value = value;
|
|
482
|
+
}
|
|
483
|
+
get(shouldLink = true) {
|
|
484
|
+
if (shouldLink) {
|
|
485
|
+
const down = getPulling();
|
|
486
|
+
if (down && (down.state & 256) === 0) {
|
|
487
|
+
link(this, down);
|
|
811
488
|
}
|
|
812
|
-
this.value = v;
|
|
813
|
-
this.version = G.version;
|
|
814
|
-
return this.value;
|
|
815
|
-
} catch (error) {
|
|
816
|
-
console.error("\u8BA1\u7B97\u5C5E\u6027\u62A5\u9519\u8FD9\u6B21\u4E0D\u89E6\u53D1\uFF0C\u540E\u7EED\u72B6\u6001\u53EF\u80FD\u51FA\u9519", error);
|
|
817
|
-
return this.value;
|
|
818
|
-
} finally {
|
|
819
|
-
this.pull = this.customPull || this.DEFAULT_PULL;
|
|
820
|
-
pullingPostprocess(this);
|
|
821
|
-
const toDel = this.recEnd?.nextRecLine;
|
|
822
|
-
unlinkRecWithScope(toDel);
|
|
823
|
-
G.PullingSignal = downstream;
|
|
824
|
-
G.PullingRecurseDeep--;
|
|
825
489
|
}
|
|
826
|
-
}
|
|
827
|
-
linkWhenPull(downstream, shouldLink) {
|
|
828
|
-
const isScope = this.state & State.IsScope;
|
|
829
|
-
if (
|
|
830
|
-
// 2. 有下游
|
|
831
|
-
downstream && shouldLink && (
|
|
832
|
-
// 3. 下游是 watcher 不是 watch,或 是watcher 但 当前是 scope
|
|
833
|
-
(downstream.state & State.LinkScopeOnly) === 0 || isScope) && (
|
|
834
|
-
/**4. scope 只能被一个下游节点管理,就是初始化它的那个下游节点
|
|
835
|
-
* 发生在 outEffect(() => scope(() => innerEffect(), null))
|
|
836
|
-
* 虽然通过 scope 让 innerEffect 被管理,
|
|
837
|
-
* 如果 innerEffect 在 outEffect 中被再次触发,就导致其被 outEffect 管理,
|
|
838
|
-
* 若 outEffect 后续重新触发, 则导致 innerEffect 被销毁
|
|
839
|
-
*/
|
|
840
|
-
!isScope || !this.emitStart)) {
|
|
841
|
-
Line.link(this, downstream);
|
|
842
|
-
}
|
|
843
|
-
}
|
|
844
|
-
pullDeep() {
|
|
845
|
-
const signal = this;
|
|
846
|
-
if (signal.state & DirtyState) {
|
|
847
|
-
let node = signal,
|
|
848
|
-
i = -1,
|
|
849
|
-
parent;
|
|
850
|
-
const stack = [];
|
|
851
|
-
outer: do {
|
|
852
|
-
let noGoDeep = false;
|
|
853
|
-
if (node.state & (State.Pulling | State.Dirty) || (node.state & DirtyState) === 0 || node.isDisabled()) {
|
|
854
|
-
noGoDeep = true;
|
|
855
|
-
} else {
|
|
856
|
-
node.state |= State.Pulling;
|
|
857
|
-
}
|
|
858
|
-
const recStart = node.recStart;
|
|
859
|
-
if (recStart && !noGoDeep) {
|
|
860
|
-
stack[++i] = recStart;
|
|
861
|
-
parent = node;
|
|
862
|
-
node = recStart.upstream;
|
|
863
|
-
continue;
|
|
864
|
-
}
|
|
865
|
-
while (true) {
|
|
866
|
-
const isDirty = node.state & State.Dirty;
|
|
867
|
-
let currentClean = noGoDeep && !isDirty;
|
|
868
|
-
if (noGoDeep && node.state & State.Pulling) {
|
|
869
|
-
currentClean = true;
|
|
870
|
-
}
|
|
871
|
-
let noGoSibling = false;
|
|
872
|
-
const downstream2 = parent;
|
|
873
|
-
const isEmitter = node.pull === node.DEFAULT_PULL;
|
|
874
|
-
if (currentClean) ; else if (isDirty) {
|
|
875
|
-
if (isEmitter && node.value !== node.nextValue) {
|
|
876
|
-
node.markDownStreamsDirty();
|
|
877
|
-
node.state &= ~State.Dirty;
|
|
878
|
-
} else {
|
|
879
|
-
const prevPulling = G.PullingSignal;
|
|
880
|
-
G.PullingSignal = downstream2;
|
|
881
|
-
const prevValue = node.value;
|
|
882
|
-
node.pullRecurse(false);
|
|
883
|
-
if (prevValue !== node.value) {
|
|
884
|
-
node.markDownStreamsDirty();
|
|
885
|
-
}
|
|
886
|
-
node.state &= ~State.Dirty;
|
|
887
|
-
G.PullingSignal = prevPulling;
|
|
888
|
-
noGoSibling = true;
|
|
889
|
-
}
|
|
890
|
-
} else if (node.state & State.Unknown) {
|
|
891
|
-
node.state &= ~State.Unknown;
|
|
892
|
-
}
|
|
893
|
-
if (!isEmitter) {
|
|
894
|
-
node.version = G.version;
|
|
895
|
-
}
|
|
896
|
-
pullingPostprocess(node);
|
|
897
|
-
noGoDeep = false;
|
|
898
|
-
if (i === -1) {
|
|
899
|
-
break outer;
|
|
900
|
-
}
|
|
901
|
-
const backLine = stack[i];
|
|
902
|
-
const nextLine = backLine.nextRecLine;
|
|
903
|
-
if (!noGoSibling && nextLine) {
|
|
904
|
-
node = nextLine.upstream;
|
|
905
|
-
stack[i] = nextLine;
|
|
906
|
-
break;
|
|
907
|
-
} else {
|
|
908
|
-
node = parent;
|
|
909
|
-
if (--i !== -1) {
|
|
910
|
-
parent = stack[i].downstream;
|
|
911
|
-
}
|
|
912
|
-
}
|
|
913
|
-
}
|
|
914
|
-
} while (true);
|
|
915
|
-
}
|
|
916
|
-
const downstream = G.PullingSignal;
|
|
917
|
-
this.linkWhenPull(downstream, true);
|
|
918
490
|
return this.value;
|
|
919
491
|
}
|
|
920
|
-
|
|
921
|
-
if (this.
|
|
922
|
-
|
|
923
|
-
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
}
|
|
929
|
-
// pause() {
|
|
930
|
-
// this.state |= State.SelfPaused;
|
|
931
|
-
// }
|
|
932
|
-
// resume() {
|
|
933
|
-
// this.state &= ~State.SelfPaused;
|
|
934
|
-
// }
|
|
935
|
-
markDownStreamsDirty() {
|
|
936
|
-
let point = this.emitStart;
|
|
937
|
-
while (point != null) {
|
|
938
|
-
const downstream = point.downstream;
|
|
939
|
-
downstream.state |= State.Dirty;
|
|
940
|
-
downstream.state &= ~State.Unknown;
|
|
941
|
-
point = point.nextEmitLine;
|
|
492
|
+
set(v) {
|
|
493
|
+
if (this.value === v) return;
|
|
494
|
+
this.value = v;
|
|
495
|
+
if (this.emitHead) {
|
|
496
|
+
mark(this);
|
|
497
|
+
if (batchDeep() === 0) {
|
|
498
|
+
flushEffect();
|
|
499
|
+
}
|
|
942
500
|
}
|
|
943
501
|
}
|
|
944
|
-
|
|
945
|
-
|
|
946
|
-
|
|
947
|
-
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
502
|
+
}
|
|
503
|
+
|
|
504
|
+
const EffectState = 512 | 32;
|
|
505
|
+
class Effect {
|
|
506
|
+
emitHead = null;
|
|
507
|
+
emitTail = null;
|
|
508
|
+
recHead = null;
|
|
509
|
+
recTail = null;
|
|
510
|
+
state = EffectState;
|
|
511
|
+
scope = getPulling();
|
|
512
|
+
outLink = null;
|
|
513
|
+
clean = null;
|
|
514
|
+
constructor(callback) {
|
|
515
|
+
this.callback = callback;
|
|
516
|
+
this.get();
|
|
517
|
+
}
|
|
518
|
+
get(shouldLink = true, notForceUpdate = true) {
|
|
519
|
+
if (this.state & 128) return;
|
|
520
|
+
const down = getPulling();
|
|
521
|
+
if (this.recHead && notForceUpdate) {
|
|
522
|
+
pullDeep(this);
|
|
523
|
+
} else {
|
|
524
|
+
this.state |= 1;
|
|
525
|
+
setPulling(null);
|
|
526
|
+
this.clean?.();
|
|
527
|
+
this.clean = null;
|
|
528
|
+
const nextId = execIdInc();
|
|
529
|
+
const prevId = execId();
|
|
530
|
+
setExecId(nextId);
|
|
531
|
+
setPulling(this);
|
|
532
|
+
this.recTail = null;
|
|
533
|
+
const res = this.callback(this);
|
|
534
|
+
typeof res === 'function' && (this.clean = res);
|
|
535
|
+
this.state &= -2;
|
|
536
|
+
setPulling(down);
|
|
537
|
+
setExecId(prevId);
|
|
538
|
+
transferDirtyState(this, this.state);
|
|
539
|
+
let line = this.recTail?.nextRecLine;
|
|
540
|
+
while (line) {
|
|
541
|
+
const nextLine = line.nextRecLine;
|
|
542
|
+
unlink(line, true);
|
|
543
|
+
line = nextLine;
|
|
955
544
|
}
|
|
956
545
|
}
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
for (const key in _scheduler) {
|
|
960
|
-
const instance = _scheduler[key];
|
|
961
|
-
instance.endSet();
|
|
546
|
+
if (!this.emitHead && shouldLink && down) {
|
|
547
|
+
link(this, down);
|
|
962
548
|
}
|
|
963
549
|
}
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
|
|
974
|
-
|
|
550
|
+
}
|
|
551
|
+
Effect.prototype.dispose = dispose;
|
|
552
|
+
|
|
553
|
+
const ScopeAndLinkScopeOnly = 32 | 256;
|
|
554
|
+
class Scope {
|
|
555
|
+
emitHead = null;
|
|
556
|
+
emitTail = null;
|
|
557
|
+
recHead = null;
|
|
558
|
+
recTail = null;
|
|
559
|
+
state = ScopeAndLinkScopeOnly;
|
|
560
|
+
scope = getPulling();
|
|
561
|
+
outLink = null;
|
|
562
|
+
constructor(callback) {
|
|
563
|
+
this.callback = callback;
|
|
564
|
+
}
|
|
565
|
+
get(shouldLink = true) {
|
|
566
|
+
const scope = this.scope;
|
|
567
|
+
this.state |= 1;
|
|
568
|
+
setPulling(this);
|
|
569
|
+
this.recTail = null;
|
|
570
|
+
const res = this.callback();
|
|
571
|
+
typeof res === 'function' && (this.clean = res);
|
|
572
|
+
this.state &= -2;
|
|
573
|
+
setPulling(scope);
|
|
574
|
+
if (!this.emitHead && shouldLink && scope) {
|
|
575
|
+
link(this, scope);
|
|
576
|
+
}
|
|
975
577
|
}
|
|
976
578
|
}
|
|
977
|
-
|
|
978
|
-
|
|
979
|
-
|
|
579
|
+
Scope.prototype.dispose = dispose;
|
|
580
|
+
|
|
581
|
+
const rawToProxy = new WeakMap();
|
|
582
|
+
let State = function (State) {
|
|
583
|
+
State[State["Clean"] = 0] = "Clean";
|
|
584
|
+
State[State["LinkScopeOnly"] = 256] = "LinkScopeOnly";
|
|
585
|
+
State[State["ScopeAbort"] = 128] = "ScopeAbort";
|
|
586
|
+
State[State["ScopeReady"] = 64] = "ScopeReady";
|
|
587
|
+
State[State["IsScope"] = 32] = "IsScope";
|
|
588
|
+
State[State["PullingDirty"] = 16] = "PullingDirty";
|
|
589
|
+
State[State["PullingUnknown"] = 8] = "PullingUnknown";
|
|
590
|
+
State[State["Unknown"] = 4] = "Unknown";
|
|
591
|
+
State[State["Dirty"] = 2] = "Dirty";
|
|
592
|
+
State[State["Pulling"] = 1] = "Pulling";
|
|
593
|
+
return State;
|
|
594
|
+
}({});
|
|
595
|
+
State.Unknown | State.Dirty;
|
|
596
|
+
State.ScopeReady | State.ScopeAbort;
|
|
597
|
+
State.ScopeAbort;
|
|
598
|
+
|
|
599
|
+
let Keys = function (Keys) {
|
|
600
|
+
Keys["Iterator"] = "__AOYE_ITERATOR";
|
|
601
|
+
Keys["Raw"] = "__AOYE_RAW";
|
|
602
|
+
Keys["Meta"] = "__AOYE_META";
|
|
603
|
+
return Keys;
|
|
604
|
+
}({});
|
|
605
|
+
const IsStore = Symbol('__AOYE_IS_STORE'),
|
|
606
|
+
StoreIgnoreKeys = Symbol('__AOYE_IGNORE_KEYS');
|
|
607
|
+
|
|
608
|
+
const ide = globalThis.requestIdleCallback || (globalThis.requestAnimationFrame ? fn => globalThis.requestAnimationFrame(() => {
|
|
609
|
+
setTimeout(() => {
|
|
610
|
+
fn();
|
|
611
|
+
});
|
|
612
|
+
}) : globalThis.setTimeout);
|
|
613
|
+
const now = () => {
|
|
614
|
+
const timer = globalThis.performance || globalThis.Date;
|
|
615
|
+
return timer.now();
|
|
616
|
+
};
|
|
617
|
+
let channel = globalThis.MessageChannel ? new MessageChannel() : null;
|
|
618
|
+
if (globalThis.MessageChannel) {
|
|
619
|
+
channel = new MessageChannel();
|
|
980
620
|
}
|
|
981
|
-
|
|
982
|
-
|
|
983
|
-
|
|
984
|
-
|
|
985
|
-
instance.endSet();
|
|
621
|
+
let msgId = 0;
|
|
622
|
+
const macro = fn => {
|
|
623
|
+
if (!channel) {
|
|
624
|
+
setTimeout(fn);
|
|
986
625
|
}
|
|
987
|
-
|
|
626
|
+
const memoId = msgId;
|
|
627
|
+
function onMessage(e) {
|
|
628
|
+
if (memoId === e.data) {
|
|
629
|
+
fn();
|
|
630
|
+
channel.port2.removeEventListener('message', onMessage);
|
|
631
|
+
}
|
|
632
|
+
}
|
|
633
|
+
channel.port2.addEventListener('message', onMessage);
|
|
634
|
+
channel.port1.postMessage(msgId++);
|
|
635
|
+
};
|
|
636
|
+
const p = Promise.resolve();
|
|
637
|
+
const micro = cb => {
|
|
638
|
+
p.then(cb);
|
|
639
|
+
};
|
|
640
|
+
const toRaw = a => {
|
|
641
|
+
if (typeof a === 'object' && a !== null && a[Keys.Raw]) {
|
|
642
|
+
return toRaw(a[Keys.Raw]);
|
|
643
|
+
}
|
|
644
|
+
return a;
|
|
645
|
+
};
|
|
988
646
|
|
|
989
647
|
const deepSignal = (target, scope, deep = true) => {
|
|
990
|
-
const isObj = typeof target ===
|
|
648
|
+
const isObj = typeof target === 'object' && target !== null;
|
|
991
649
|
if (!isObj || target[Keys.Raw]) return target;
|
|
992
650
|
const p = rawToProxy.get(target);
|
|
993
651
|
if (p) return p;
|
|
994
|
-
const cells =
|
|
652
|
+
const cells = new Map();
|
|
995
653
|
const targetIsArray = Array.isArray(target);
|
|
996
654
|
const targetIsStore = Boolean(target.constructor?.[IsStore]);
|
|
997
655
|
const meta = {
|
|
@@ -1012,12 +670,12 @@ const deepSignal = (target, scope, deep = true) => {
|
|
|
1012
670
|
return Reflect.get(obj, prop, receiver);
|
|
1013
671
|
}
|
|
1014
672
|
const desc = Reflect.getOwnPropertyDescriptor(obj, prop);
|
|
1015
|
-
const isGetter = desc && typeof desc.get ===
|
|
673
|
+
const isGetter = desc && typeof desc.get === 'function';
|
|
1016
674
|
if (isGetter) {
|
|
1017
675
|
return handleGetterAsComputed(obj, prop, receiver, cells, scope);
|
|
1018
676
|
}
|
|
1019
677
|
const value = Reflect.get(obj, prop, receiver);
|
|
1020
|
-
const valueIsFn = typeof value ===
|
|
678
|
+
const valueIsFn = typeof value === 'function';
|
|
1021
679
|
if (valueIsFn) {
|
|
1022
680
|
if (targetIsArray) {
|
|
1023
681
|
return arrayMethodReWrites[prop] || value;
|
|
@@ -1027,26 +685,22 @@ const deepSignal = (target, scope, deep = true) => {
|
|
|
1027
685
|
}
|
|
1028
686
|
let s = cells.get(prop);
|
|
1029
687
|
if (s) {
|
|
1030
|
-
return s.
|
|
688
|
+
return s.get();
|
|
1031
689
|
}
|
|
1032
690
|
const wrappedValue = deep ? deepSignal(value, scope) : value;
|
|
1033
|
-
s = Signal
|
|
1034
|
-
scheduler: Scheduler.Sync,
|
|
1035
|
-
isScope: false,
|
|
1036
|
-
scope
|
|
1037
|
-
});
|
|
691
|
+
s = new Signal(wrappedValue);
|
|
1038
692
|
cells.set(prop, s);
|
|
1039
|
-
return s.
|
|
693
|
+
return s.get();
|
|
1040
694
|
},
|
|
1041
695
|
set(obj, prop, value, receiver) {
|
|
1042
|
-
if (targetIsStore && isIgnoreKey(obj.constructor[StoreIgnoreKeys], prop) || typeof value ===
|
|
696
|
+
if (targetIsStore && isIgnoreKey(obj.constructor[StoreIgnoreKeys], prop) || typeof value === 'function') {
|
|
1043
697
|
return Reflect.set(obj, prop, value, receiver);
|
|
1044
698
|
}
|
|
1045
699
|
batchStart();
|
|
1046
700
|
const success = Reflect.set(obj, prop, value, receiver);
|
|
1047
701
|
const cell = cells.get(prop);
|
|
1048
702
|
if (cell) {
|
|
1049
|
-
cell.
|
|
703
|
+
cell.set(deep ? deepSignal(value, scope) : value);
|
|
1050
704
|
}
|
|
1051
705
|
if (targetIsArray) {
|
|
1052
706
|
handleArraySet(obj, prop, value, receiver);
|
|
@@ -1056,13 +710,12 @@ const deepSignal = (target, scope, deep = true) => {
|
|
|
1056
710
|
batchEnd();
|
|
1057
711
|
return success;
|
|
1058
712
|
},
|
|
1059
|
-
// 【核心修改】拦截 delete 操作
|
|
1060
713
|
deleteProperty(obj, prop) {
|
|
1061
|
-
if (targetIsStore && isIgnoreKey(obj.constructor[StoreIgnoreKeys], prop) || typeof obj[prop] ===
|
|
714
|
+
if (targetIsStore && isIgnoreKey(obj.constructor[StoreIgnoreKeys], prop) || typeof obj[prop] === 'function') {
|
|
1062
715
|
return Reflect.deleteProperty(obj, prop);
|
|
1063
716
|
}
|
|
1064
717
|
cells.delete(prop);
|
|
1065
|
-
triggerIter(obj, prop,
|
|
718
|
+
triggerIter(obj, prop, undefined, proxy);
|
|
1066
719
|
return Reflect.deleteProperty(obj, prop);
|
|
1067
720
|
},
|
|
1068
721
|
ownKeys(obj) {
|
|
@@ -1079,8 +732,8 @@ const deepSignal = (target, scope, deep = true) => {
|
|
|
1079
732
|
};
|
|
1080
733
|
const shareSignal = (from, fromPath, to, toPath) => {
|
|
1081
734
|
try {
|
|
1082
|
-
const toPaths = toPath.split(
|
|
1083
|
-
const formPaths = Array.isArray(fromPath) ? fromPath : fromPath.split(
|
|
735
|
+
const toPaths = toPath.split('.');
|
|
736
|
+
const formPaths = Array.isArray(fromPath) ? fromPath : fromPath.split('.');
|
|
1084
737
|
runWithPulling(() => {
|
|
1085
738
|
const _getTargetAndKey = getTargetAndKey(from, formPaths),
|
|
1086
739
|
fromTarget = _getTargetAndKey.target,
|
|
@@ -1094,13 +747,13 @@ const shareSignal = (from, fromPath, to, toPath) => {
|
|
|
1094
747
|
toTarget[Keys.Raw][toKey] = val;
|
|
1095
748
|
}, null);
|
|
1096
749
|
} catch (error) {
|
|
1097
|
-
console.error(
|
|
750
|
+
console.error('映射了不存在的Key!');
|
|
1098
751
|
throw error;
|
|
1099
752
|
}
|
|
1100
753
|
};
|
|
1101
754
|
function getTargetAndKey(obj, paths) {
|
|
1102
755
|
let target = obj;
|
|
1103
|
-
let key =
|
|
756
|
+
let key = '';
|
|
1104
757
|
const len = paths.length;
|
|
1105
758
|
for (let i = 0; i < len; i++) {
|
|
1106
759
|
key = paths[i];
|
|
@@ -1114,27 +767,23 @@ function getTargetAndKey(obj, paths) {
|
|
|
1114
767
|
};
|
|
1115
768
|
}
|
|
1116
769
|
function isIgnoreKey(ignores, key) {
|
|
1117
|
-
if (typeof key !==
|
|
770
|
+
if (typeof key !== 'string') {
|
|
1118
771
|
return ignores.includes(key);
|
|
1119
772
|
}
|
|
1120
|
-
return ignores.some(it => typeof it ===
|
|
773
|
+
return ignores.some(it => typeof it === 'string' && key.startsWith(it));
|
|
1121
774
|
}
|
|
1122
775
|
function handleGetterAsComputed(obj, prop, receiver, cells, scope) {
|
|
1123
776
|
let s = cells.get(prop);
|
|
1124
777
|
if (s) {
|
|
1125
|
-
return s.
|
|
778
|
+
return s.get();
|
|
1126
779
|
}
|
|
1127
|
-
s =
|
|
1128
|
-
|
|
1129
|
-
scheduler: Scheduler.Sync,
|
|
1130
|
-
isScope: false,
|
|
1131
|
-
scope
|
|
1132
|
-
});
|
|
780
|
+
s = new Computed(() => Reflect.get(obj, prop, receiver));
|
|
781
|
+
s.scope = scope;
|
|
1133
782
|
cells.set(prop, s);
|
|
1134
|
-
return s.
|
|
783
|
+
return s.get();
|
|
1135
784
|
}
|
|
1136
785
|
function handleArraySet(arr, prop, value, receiver) {
|
|
1137
|
-
if (prop ===
|
|
786
|
+
if (prop === 'length') ; else if (bobeShared.isNatureNumStr(prop)) {
|
|
1138
787
|
receiver[Keys.Iterator] = (arr[Keys.Iterator] || 0) + 1;
|
|
1139
788
|
} else {
|
|
1140
789
|
triggerIter(arr, prop, value, receiver);
|
|
@@ -1142,11 +791,11 @@ function handleArraySet(arr, prop, value, receiver) {
|
|
|
1142
791
|
}
|
|
1143
792
|
function triggerIter(obj, prop, value, receiver) {
|
|
1144
793
|
if (!Reflect.has(obj, prop)) {
|
|
1145
|
-
receiver[Keys.Iterator] = receiver[Keys.Raw][Keys.Iterator] + 1;
|
|
794
|
+
receiver[Keys.Iterator] = (receiver[Keys.Raw][Keys.Iterator] || 0) + 1;
|
|
1146
795
|
}
|
|
1147
796
|
}
|
|
1148
797
|
const arrayMethodReWrites = {};
|
|
1149
|
-
[
|
|
798
|
+
['pop', 'push', 'shift', 'splice', 'unshift', 'copyWithin', 'reverse', 'fill'].forEach(key => {
|
|
1150
799
|
arrayMethodReWrites[key] = function (...args) {
|
|
1151
800
|
batchStart();
|
|
1152
801
|
const fn = Array.prototype[key];
|
|
@@ -1156,13 +805,13 @@ const arrayMethodReWrites = {};
|
|
|
1156
805
|
return res;
|
|
1157
806
|
};
|
|
1158
807
|
});
|
|
1159
|
-
[
|
|
808
|
+
['includes', 'indexOf', 'lastIndexOf'].forEach(key => {
|
|
1160
809
|
arrayMethodReWrites[key] = function (...args) {
|
|
1161
810
|
const fn = Array.prototype[key];
|
|
1162
811
|
const that = toRaw(this);
|
|
1163
812
|
let result = fn.call(that, ...args);
|
|
1164
813
|
const value = args[0];
|
|
1165
|
-
if ((result === false || result === -1) && typeof value ===
|
|
814
|
+
if ((result === false || result === -1) && typeof value === 'object' && value !== null) {
|
|
1166
815
|
if (value[Keys.Raw]) {
|
|
1167
816
|
args[0] = value[Keys.Raw];
|
|
1168
817
|
result = fn.call(that, ...args);
|
|
@@ -1177,8 +826,8 @@ const arrayMethodReWrites = {};
|
|
|
1177
826
|
return result;
|
|
1178
827
|
};
|
|
1179
828
|
});
|
|
1180
|
-
[Symbol.iterator,
|
|
1181
|
-
const isEntries = key ===
|
|
829
|
+
[Symbol.iterator, 'values', 'entries'].forEach(key => {
|
|
830
|
+
const isEntries = key === 'entries';
|
|
1182
831
|
arrayMethodReWrites[key] = function (...args) {
|
|
1183
832
|
const fn = Array.prototype[key];
|
|
1184
833
|
const rawArray = toRaw(this);
|
|
@@ -1236,7 +885,7 @@ arrayMethodReWrites.slice = function (start, end) {
|
|
|
1236
885
|
} else {
|
|
1237
886
|
k = Math.min(k, len);
|
|
1238
887
|
}
|
|
1239
|
-
let final = end ===
|
|
888
|
+
let final = end === undefined ? len : end;
|
|
1240
889
|
if (final < 0) {
|
|
1241
890
|
final = Math.max(len + final, 0);
|
|
1242
891
|
} else {
|
|
@@ -1364,42 +1013,42 @@ arrayMethodReWrites.concat = function (...items) {
|
|
|
1364
1013
|
};
|
|
1365
1014
|
const GetMethodConf = {
|
|
1366
1015
|
wrapReturn: false,
|
|
1367
|
-
wrapArgs:
|
|
1016
|
+
wrapArgs: 0b01
|
|
1368
1017
|
};
|
|
1369
1018
|
[{
|
|
1370
|
-
key:
|
|
1019
|
+
key: 'every',
|
|
1371
1020
|
...GetMethodConf
|
|
1372
1021
|
}, {
|
|
1373
|
-
key:
|
|
1022
|
+
key: 'find',
|
|
1374
1023
|
wrapReturn: true,
|
|
1375
1024
|
...GetMethodConf
|
|
1376
1025
|
}, {
|
|
1377
|
-
key:
|
|
1026
|
+
key: 'findLast',
|
|
1378
1027
|
...GetMethodConf,
|
|
1379
1028
|
wrapReturn: true
|
|
1380
1029
|
}, {
|
|
1381
|
-
key:
|
|
1030
|
+
key: 'findIndex',
|
|
1382
1031
|
...GetMethodConf
|
|
1383
1032
|
}, {
|
|
1384
|
-
key:
|
|
1033
|
+
key: 'findLastIndex',
|
|
1385
1034
|
...GetMethodConf
|
|
1386
1035
|
}, {
|
|
1387
|
-
key:
|
|
1036
|
+
key: 'forEach',
|
|
1388
1037
|
...GetMethodConf
|
|
1389
1038
|
}, {
|
|
1390
|
-
key:
|
|
1039
|
+
key: 'map',
|
|
1391
1040
|
...GetMethodConf
|
|
1392
1041
|
}, {
|
|
1393
|
-
key:
|
|
1042
|
+
key: 'some',
|
|
1394
1043
|
...GetMethodConf
|
|
1395
1044
|
}, {
|
|
1396
|
-
key:
|
|
1045
|
+
key: 'reduce',
|
|
1397
1046
|
...GetMethodConf,
|
|
1398
|
-
wrapArgs:
|
|
1047
|
+
wrapArgs: 0b10
|
|
1399
1048
|
}, {
|
|
1400
|
-
key:
|
|
1049
|
+
key: 'reduceRight',
|
|
1401
1050
|
...GetMethodConf,
|
|
1402
|
-
wrapArgs:
|
|
1051
|
+
wrapArgs: 0b10
|
|
1403
1052
|
}].forEach(({
|
|
1404
1053
|
key,
|
|
1405
1054
|
wrapReturn,
|
|
@@ -1421,17 +1070,17 @@ const GetMethodConf = {
|
|
|
1421
1070
|
};
|
|
1422
1071
|
});
|
|
1423
1072
|
arrayMethodReWrites.toSorted = function (...args) {
|
|
1424
|
-
const fn = Array.prototype[
|
|
1073
|
+
const fn = Array.prototype['toSorted'];
|
|
1425
1074
|
const meta = this[Keys.Meta];
|
|
1426
1075
|
const isDeep = meta.deep,
|
|
1427
1076
|
scope = meta.scope;
|
|
1428
1077
|
const that = toRaw(this);
|
|
1429
|
-
warpCallbackArgs(isDeep, args, scope,
|
|
1078
|
+
warpCallbackArgs(isDeep, args, scope, 0b11);
|
|
1430
1079
|
let result = fn.call(that, ...args);
|
|
1431
1080
|
this[Keys.Iterator];
|
|
1432
1081
|
return isDeep ? result.map(it => deepSignal(it, scope)) : result;
|
|
1433
1082
|
};
|
|
1434
|
-
[
|
|
1083
|
+
['join', 'toString', 'toLocaleString'].forEach(key => {
|
|
1435
1084
|
arrayMethodReWrites[key] = function (...args) {
|
|
1436
1085
|
const fn = Array.prototype[key];
|
|
1437
1086
|
const that = toRaw(this);
|
|
@@ -1440,38 +1089,30 @@ arrayMethodReWrites.toSorted = function (...args) {
|
|
|
1440
1089
|
return result;
|
|
1441
1090
|
};
|
|
1442
1091
|
});
|
|
1443
|
-
function warpCallbackArgs(isDeep, args, scope, wrapArgs =
|
|
1092
|
+
function warpCallbackArgs(isDeep, args, scope, wrapArgs = 0b01) {
|
|
1444
1093
|
const callback = args[0];
|
|
1445
1094
|
const wrapCb = function (...cbArgs) {
|
|
1446
1095
|
if (isDeep) {
|
|
1447
|
-
if (wrapArgs &
|
|
1448
|
-
if (wrapArgs &
|
|
1096
|
+
if (wrapArgs & 0b01) cbArgs[0] = deepSignal(cbArgs[0], scope);
|
|
1097
|
+
if (wrapArgs & 0b10) cbArgs[1] = deepSignal(cbArgs[1], scope);
|
|
1449
1098
|
}
|
|
1450
1099
|
return callback.call(this, ...cbArgs);
|
|
1451
1100
|
};
|
|
1452
1101
|
args[0] = wrapCb;
|
|
1453
1102
|
}
|
|
1454
1103
|
|
|
1455
|
-
|
|
1456
|
-
|
|
1457
|
-
|
|
1104
|
+
class Store {
|
|
1105
|
+
static [IsStore] = true;
|
|
1106
|
+
static [StoreIgnoreKeys] = ['ui', 'raw'];
|
|
1107
|
+
static Current = null;
|
|
1458
1108
|
constructor() {
|
|
1459
|
-
|
|
1460
|
-
|
|
1461
|
-
_Store.Current = proxy;
|
|
1109
|
+
const proxy = deepSignal(this, getPulling(), true);
|
|
1110
|
+
Store.Current = proxy;
|
|
1462
1111
|
return proxy;
|
|
1463
1112
|
}
|
|
1464
|
-
|
|
1465
|
-
this[_b] = true;
|
|
1466
|
-
}
|
|
1467
|
-
static {
|
|
1468
|
-
this[_a] = ["ui", "raw"];
|
|
1469
|
-
}
|
|
1470
|
-
static {
|
|
1471
|
-
this.Current = null;
|
|
1472
|
-
}
|
|
1113
|
+
parent = () => null;
|
|
1473
1114
|
static new(keyMap = {}, staticMap = {}) {
|
|
1474
|
-
const parentStore =
|
|
1115
|
+
const parentStore = Store.Current;
|
|
1475
1116
|
const child = new this();
|
|
1476
1117
|
if (parentStore) {
|
|
1477
1118
|
for (const childKey in keyMap) {
|
|
@@ -1484,7 +1125,7 @@ const _Store = class _Store {
|
|
|
1484
1125
|
child[key] = value;
|
|
1485
1126
|
}
|
|
1486
1127
|
child.parent = () => parentStore;
|
|
1487
|
-
|
|
1128
|
+
Store.Current = parentStore;
|
|
1488
1129
|
return child;
|
|
1489
1130
|
}
|
|
1490
1131
|
map(keyMap = {}) {
|
|
@@ -1497,56 +1138,44 @@ const _Store = class _Store {
|
|
|
1497
1138
|
}
|
|
1498
1139
|
this.parent = null;
|
|
1499
1140
|
}
|
|
1500
|
-
}
|
|
1501
|
-
let Store = _Store;
|
|
1141
|
+
}
|
|
1502
1142
|
|
|
1503
|
-
|
|
1504
|
-
|
|
1505
|
-
|
|
1506
|
-
|
|
1507
|
-
|
|
1508
|
-
|
|
1509
|
-
|
|
1510
|
-
|
|
1511
|
-
|
|
1512
|
-
|
|
1513
|
-
(
|
|
1514
|
-
|
|
1515
|
-
|
|
1516
|
-
opt = {
|
|
1517
|
-
...DefaultCustomSignalOpt,
|
|
1518
|
-
...opt
|
|
1519
|
-
};
|
|
1520
|
-
let intiValue, customPull;
|
|
1521
|
-
if (typeof init === "function") {
|
|
1522
|
-
intiValue = null;
|
|
1523
|
-
customPull = init;
|
|
1524
|
-
} else if (opt.mode !== "ref" && typeof init === "object" && init !== null) {
|
|
1525
|
-
return deepSignal(init, G.PullingSignal, opt.deep);
|
|
1143
|
+
function $(data) {
|
|
1144
|
+
if (typeof data === 'object' && data !== null) {
|
|
1145
|
+
return deepSignal(data, getPulling());
|
|
1146
|
+
}
|
|
1147
|
+
if (typeof data === 'function') {
|
|
1148
|
+
const s = new Computed(data),
|
|
1149
|
+
get = s.get.bind(s);
|
|
1150
|
+
return {
|
|
1151
|
+
ins: s,
|
|
1152
|
+
get v() {
|
|
1153
|
+
return get();
|
|
1154
|
+
}
|
|
1155
|
+
};
|
|
1526
1156
|
} else {
|
|
1527
|
-
|
|
1157
|
+
const s = new Signal(data),
|
|
1158
|
+
set = s.set.bind(s),
|
|
1159
|
+
get = s.get.bind(s);
|
|
1160
|
+
return {
|
|
1161
|
+
ins: s,
|
|
1162
|
+
get v() {
|
|
1163
|
+
return get();
|
|
1164
|
+
},
|
|
1165
|
+
set v(v) {
|
|
1166
|
+
set(v);
|
|
1167
|
+
}
|
|
1168
|
+
};
|
|
1528
1169
|
}
|
|
1529
|
-
|
|
1530
|
-
|
|
1531
|
-
isScope: false,
|
|
1532
|
-
customPull
|
|
1533
|
-
});
|
|
1534
|
-
return s;
|
|
1535
|
-
};
|
|
1536
|
-
const effect = (customPull, depOrOpt, opt) => {
|
|
1170
|
+
}
|
|
1171
|
+
function effectUt(callback, depOrOpt, opt) {
|
|
1537
1172
|
const hasDep = Array.isArray(depOrOpt);
|
|
1538
1173
|
opt = hasDep ? opt || {} : depOrOpt || {};
|
|
1539
1174
|
if (!hasDep) {
|
|
1540
|
-
const
|
|
1541
|
-
|
|
1542
|
-
|
|
1543
|
-
|
|
1544
|
-
...opt
|
|
1545
|
-
});
|
|
1546
|
-
s2.v;
|
|
1547
|
-
const bound2 = dispose.bind(s2);
|
|
1548
|
-
bound2.ins = s2;
|
|
1549
|
-
return bound2;
|
|
1175
|
+
const ef = new Effect(callback);
|
|
1176
|
+
const run = ef.dispose.bind(ef);
|
|
1177
|
+
run.ins = ef;
|
|
1178
|
+
return run;
|
|
1550
1179
|
}
|
|
1551
1180
|
let mounted = false;
|
|
1552
1181
|
const deps = depOrOpt;
|
|
@@ -1557,84 +1186,94 @@ const effect = (customPull, depOrOpt, opt) => {
|
|
|
1557
1186
|
old: null,
|
|
1558
1187
|
val: null
|
|
1559
1188
|
}));
|
|
1560
|
-
const
|
|
1561
|
-
|
|
1562
|
-
|
|
1563
|
-
|
|
1564
|
-
|
|
1565
|
-
|
|
1566
|
-
|
|
1567
|
-
|
|
1568
|
-
|
|
1569
|
-
|
|
1570
|
-
|
|
1571
|
-
|
|
1572
|
-
mounted = true;
|
|
1573
|
-
},
|
|
1574
|
-
scheduler: Scheduler.Sync,
|
|
1575
|
-
isScope: true,
|
|
1576
|
-
...opt
|
|
1577
|
-
});
|
|
1578
|
-
s.v;
|
|
1579
|
-
const bound = dispose.bind(s);
|
|
1580
|
-
bound.ins = s;
|
|
1581
|
-
return bound;
|
|
1582
|
-
};
|
|
1583
|
-
const scope = (...args) => {
|
|
1584
|
-
const hasScope = args.length > 1;
|
|
1585
|
-
const s = Signal.create(null, {
|
|
1586
|
-
customPull: args[0],
|
|
1587
|
-
scheduler: Scheduler.Sync,
|
|
1588
|
-
isScope: true,
|
|
1589
|
-
scope: hasScope ? args[1] : G.PullingSignal
|
|
1189
|
+
const ef = new Effect(() => {
|
|
1190
|
+
for (let i = 0; i < deps.length; i++) {
|
|
1191
|
+
const value = deps[i].v;
|
|
1192
|
+
vs[i].old = vs[i].val;
|
|
1193
|
+
vs[i].val = value;
|
|
1194
|
+
}
|
|
1195
|
+
if (mounted || immediate) {
|
|
1196
|
+
ef.state |= 256;
|
|
1197
|
+
callback(...vs);
|
|
1198
|
+
ef.state &= -257;
|
|
1199
|
+
}
|
|
1200
|
+
mounted = true;
|
|
1590
1201
|
});
|
|
1591
|
-
|
|
1592
|
-
|
|
1593
|
-
|
|
1594
|
-
|
|
1595
|
-
|
|
1596
|
-
|
|
1202
|
+
const run = ef.dispose.bind(ef);
|
|
1203
|
+
run.ins = ef;
|
|
1204
|
+
return run;
|
|
1205
|
+
}
|
|
1206
|
+
function effect(callback, depOrOpt, opt) {
|
|
1207
|
+
const hasDep = Array.isArray(depOrOpt);
|
|
1208
|
+
opt = hasDep ? opt || {} : depOrOpt || {};
|
|
1209
|
+
if (!hasDep) {
|
|
1210
|
+
const ef = new Effect(callback);
|
|
1211
|
+
const run = ef.dispose.bind(ef);
|
|
1212
|
+
run.ins = ef;
|
|
1213
|
+
return run;
|
|
1597
1214
|
}
|
|
1598
|
-
|
|
1599
|
-
const
|
|
1600
|
-
|
|
1601
|
-
|
|
1602
|
-
|
|
1603
|
-
|
|
1604
|
-
|
|
1605
|
-
|
|
1606
|
-
|
|
1607
|
-
|
|
1608
|
-
|
|
1609
|
-
|
|
1610
|
-
|
|
1611
|
-
|
|
1612
|
-
|
|
1613
|
-
|
|
1614
|
-
|
|
1615
|
-
|
|
1616
|
-
|
|
1215
|
+
let mounted = false;
|
|
1216
|
+
const deps = depOrOpt;
|
|
1217
|
+
const immediate = deps.length === 0 ? true : opt.immediate ?? true;
|
|
1218
|
+
const vs = Array.from({
|
|
1219
|
+
length: deps.length
|
|
1220
|
+
}, () => ({
|
|
1221
|
+
old: null,
|
|
1222
|
+
val: null
|
|
1223
|
+
}));
|
|
1224
|
+
const ef = new Effect(eff => {
|
|
1225
|
+
for (let i = 0; i < deps.length; i++) {
|
|
1226
|
+
const value = deps[i].get();
|
|
1227
|
+
vs[i].old = vs[i].val;
|
|
1228
|
+
vs[i].val = value;
|
|
1229
|
+
}
|
|
1230
|
+
if (mounted || immediate) {
|
|
1231
|
+
eff.state |= 256;
|
|
1232
|
+
callback(...vs);
|
|
1233
|
+
eff.state &= -257;
|
|
1234
|
+
}
|
|
1235
|
+
mounted = true;
|
|
1236
|
+
});
|
|
1237
|
+
const run = ef.dispose.bind(ef);
|
|
1238
|
+
run.ins = ef;
|
|
1239
|
+
return run;
|
|
1240
|
+
}
|
|
1241
|
+
function scope(...args) {
|
|
1242
|
+
const ins = new Scope(args[0]);
|
|
1243
|
+
if (args.length === 2) {
|
|
1244
|
+
ins.scope = args[1];
|
|
1245
|
+
}
|
|
1246
|
+
ins.get();
|
|
1247
|
+
const run = ins.dispose.bind(ins);
|
|
1248
|
+
run.ins = ins;
|
|
1249
|
+
return run;
|
|
1250
|
+
}
|
|
1617
1251
|
|
|
1618
1252
|
exports.$ = $;
|
|
1253
|
+
exports.Computed = Computed;
|
|
1254
|
+
exports.Effect = Effect;
|
|
1619
1255
|
exports.IsStore = IsStore;
|
|
1620
1256
|
exports.Keys = Keys;
|
|
1621
|
-
exports.
|
|
1257
|
+
exports.Scope = Scope;
|
|
1622
1258
|
exports.Signal = Signal;
|
|
1623
1259
|
exports.Store = Store;
|
|
1624
1260
|
exports.StoreIgnoreKeys = StoreIgnoreKeys;
|
|
1625
|
-
exports.TaskQueue = TaskQueue;
|
|
1626
1261
|
exports.batchEnd = batchEnd;
|
|
1627
1262
|
exports.batchStart = batchStart;
|
|
1628
1263
|
exports.clean = clean;
|
|
1629
|
-
exports.customEffect = customEffect;
|
|
1630
1264
|
exports.deepSignal = deepSignal;
|
|
1631
1265
|
exports.effect = effect;
|
|
1266
|
+
exports.effectUt = effectUt;
|
|
1267
|
+
exports.execId = execId;
|
|
1268
|
+
exports.execIdInc = execIdInc;
|
|
1632
1269
|
exports.getPulling = getPulling;
|
|
1633
|
-
exports.
|
|
1634
|
-
exports.
|
|
1635
|
-
exports.
|
|
1270
|
+
exports.ide = ide;
|
|
1271
|
+
exports.macro = macro;
|
|
1272
|
+
exports.micro = micro;
|
|
1273
|
+
exports.now = now;
|
|
1636
1274
|
exports.runWithPulling = runWithPulling;
|
|
1637
1275
|
exports.scope = scope;
|
|
1276
|
+
exports.setExecId = setExecId;
|
|
1638
1277
|
exports.setPulling = setPulling;
|
|
1639
1278
|
exports.shareSignal = shareSignal;
|
|
1640
1279
|
exports.toRaw = toRaw;
|