141
includesBlockingLane,
142
includesExpiredLane,
143
getNextLanes,
144
+ getEntangledLanes,
145
getLanesToRetrySynchronouslyOnError,
146
markRootUpdated,
147
markRootSuspended as markRootSuspended_dontCallThisOneDirectly,
148
markRootPinged,
148
- markRootEntangled,
149
+ upgradePendingLanesToSync,
150
markRootFinished,
151
addFiberToLanesMap,
152
movePendingFibersToMemoized,
350
// HiddenContext module.
351
//
352
// Most things in the work loop should deal with workInProgressRootRenderLanes.
352
-// Most things in begin/complete phases should deal with renderLanes.
353
-export let renderLanes: Lanes = NoLanes;
353
+// Most things in begin/complete phases should deal with entangledRenderLanes.
354
+export let entangledRenderLanes: Lanes = NoLanes;
355
356
// Whether to root completed, errored, suspended, etc.
357
let workInProgressRootExitStatus: RootExitStatus = RootInProgress;
1336
1337
export function flushRoot(root: FiberRoot, lanes: Lanes) {
1338
if (lanes !== NoLanes) {
1338
- markRootEntangled(root, mergeLanes(lanes, SyncLane));
1339
+ upgradePendingLanesToSync(root, lanes);
1340
ensureRootIsScheduled(root);
1341
if ((executionContext & (RenderContext | CommitContext)) === NoContext) {
1342
resetRenderTimer();
1472
// hidden subtree. The stack logic is managed there because that's the only
1473
// place that ever modifies it. Which module it lives in doesn't matter for
1474
// performance because this function will get inlined regardless
1474
-export function setRenderLanes(subtreeRenderLanes: Lanes) {
1475
- renderLanes = subtreeRenderLanes;
1475
+export function setEntangledRenderLanes(newEntangledRenderLanes: Lanes) {
1476
+ entangledRenderLanes = newEntangledRenderLanes;
1477
}
1478
1478
-export function getRenderLanes(): Lanes {
1479
- return renderLanes;
1479
+export function getEntangledRenderLanes(): Lanes {
1480
+ return entangledRenderLanes;
1481
}
1482
1483
function resetWorkInProgressStack() {
1527
workInProgressRoot = root;
1528
const rootWorkInProgress = createWorkInProgress(root.current, null);
1529
workInProgress = rootWorkInProgress;
1529
- workInProgressRootRenderLanes = renderLanes = lanes;
1530
+ workInProgressRootRenderLanes = lanes;
1531
workInProgressSuspendedReason = NotSuspended;
1532
workInProgressThrownValue = null;
1533
workInProgressRootDidAttachPingListener = false;
1540
workInProgressRootConcurrentErrors = null;
1541
workInProgressRootRecoverableErrors = null;
1542
1543
+ // Get the lanes that are entangled with whatever we're about to render. We
1544
+ // track these separately so we can distinguish the priority of the render
1545
+ // task from the priority of the lanes it is entangled with. For example, a
1546
+ // transition may not be allowed to finish unless it includes the Sync lane,
1547
+ // which is currently suspended. We should be able to render the Transition
1548
+ // and Sync lane in the same batch, but at Transition priority, because the
1549
+ // Sync lane already suspended.
1550
+ entangledRenderLanes = getEntangledLanes(root, lanes);
1551
+
1552
finishQueueingConcurrentUpdates();
1553
1554
if (__DEV__) {
2259
let next;
2260
if (enableProfilerTimer && (unitOfWork.mode & ProfileMode) !== NoMode) {
2261
startProfilerTimer(unitOfWork);
2252
- next = beginWork(current, unitOfWork, renderLanes);
2262
+ next = beginWork(current, unitOfWork, entangledRenderLanes);
2263
stopProfilerTimerIfRunningAndRecordDelta(unitOfWork, true);
2264
} else {
2255
- next = beginWork(current, unitOfWork, renderLanes);
2265
+ next = beginWork(current, unitOfWork, entangledRenderLanes);
2266
}
2267
2268
resetCurrentDebugFiberInDEV();
2369
unwindInterruptedWork(current, unitOfWork, workInProgressRootRenderLanes);
2370
unitOfWork = workInProgress = resetWorkInProgress(
2371
unitOfWork,
2362
- renderLanes,
2372
+ entangledRenderLanes,
2373
);
2364
- next = beginWork(current, unitOfWork, renderLanes);
2374
+ next = beginWork(current, unitOfWork, entangledRenderLanes);
2375
break;
2376
}
2377
}
2481
setCurrentDebugFiberInDEV(completedWork);
2482
let next;
2483
if (!enableProfilerTimer || (completedWork.mode & ProfileMode) === NoMode) {
2474
- next = completeWork(current, completedWork, renderLanes);
2484
+ next = completeWork(current, completedWork, entangledRenderLanes);
2485
} else {
2486
startProfilerTimer(completedWork);
2477
- next = completeWork(current, completedWork, renderLanes);
2487
+ next = completeWork(current, completedWork, entangledRenderLanes);
2488
// Update render duration assuming we didn't error.
2489
stopProfilerTimerIfRunningAndRecordDelta(completedWork, false);
2490
}
2526
// This fiber did not complete because something threw. Pop values off
2527
// the stack without entering the complete phase. If this is a boundary,
2528
// capture values if possible.
2519
- const next = unwindWork(current, incompleteWork, renderLanes);
2529
+ const next = unwindWork(current, incompleteWork, entangledRenderLanes);
2530
2531
// Because this fiber did not complete, don't reset its lanes.
2532