Skip to content

Commit

Permalink
Merge pull request #8728 from acdlite/fibernocallbacklist
Browse files Browse the repository at this point in the history
[Fiber] Remove callbackList field from Fiber
  • Loading branch information
acdlite authored Jan 10, 2017
2 parents 378ef5e + 288a4c4 commit 00be2e4
Show file tree
Hide file tree
Showing 4 changed files with 40 additions and 48 deletions.
6 changes: 2 additions & 4 deletions src/renderers/shared/fiber/ReactFiber.js
Original file line number Diff line number Diff line change
Expand Up @@ -111,8 +111,7 @@ export type Fiber = {

// A queue of state updates and callbacks.
updateQueue: UpdateQueue | null,
// A list of callbacks that should be called during the next commit.
callbackList: UpdateQueue | null,

// The state used to create the output
memoizedState: any,

Expand Down Expand Up @@ -203,7 +202,6 @@ var createFiber = function(tag : TypeOfWork, key : null | string) : Fiber {
pendingProps: null,
memoizedProps: null,
updateQueue: null,
callbackList: null,
memoizedState: null,

effectTag: NoEffect,
Expand Down Expand Up @@ -279,7 +277,7 @@ exports.cloneFiber = function(fiber : Fiber, priorityLevel : PriorityLevel) : Fi
// pendingProps is here for symmetry but is unnecessary in practice for now.
// TODO: Pass in the new pendingProps as an argument maybe?
alt.pendingProps = fiber.pendingProps;
cloneUpdateQueue(alt, fiber);
cloneUpdateQueue(fiber, alt);
alt.pendingWorkPriority = priorityLevel;

alt.memoizedProps = fiber.memoizedProps;
Expand Down
12 changes: 6 additions & 6 deletions src/renderers/shared/fiber/ReactFiberCommitWork.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ var { commitCallbacks } = require('ReactFiberUpdateQueue');
var {
Placement,
Update,
Callback,
ContentReset,
} = require('ReactTypeOfSideEffect');

Expand Down Expand Up @@ -410,17 +411,16 @@ module.exports = function<T, P, I, TI, C, CX, CI>(
}
}
}
const callbackList = finishedWork.callbackList;
if (callbackList) {
commitCallbacks(finishedWork, callbackList, instance);
if ((finishedWork.effectTag & Callback) && finishedWork.updateQueue) {
commitCallbacks(finishedWork, finishedWork.updateQueue, instance);
}
return;
}
case HostRoot: {
const callbackList = finishedWork.callbackList;
if (callbackList) {
const updateQueue = finishedWork.updateQueue;
if (updateQueue) {
const instance = finishedWork.child && finishedWork.child.stateNode;
commitCallbacks(finishedWork, callbackList, instance);
commitCallbacks(finishedWork, updateQueue, instance);
}
return;
}
Expand Down
1 change: 0 additions & 1 deletion src/renderers/shared/fiber/ReactFiberRoot.js
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,6 @@ exports.createFiberRoot = function(containerInfo : any) : FiberRoot {
containerInfo: containerInfo,
isScheduled: false,
nextScheduledRoot: null,
callbackList: null,
context: null,
pendingContext: null,
};
Expand Down
69 changes: 32 additions & 37 deletions src/renderers/shared/fiber/ReactFiberUpdateQueue.js
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@ export type UpdateQueue = {
first: Update | null,
last: Update | null,
hasForceUpdate: boolean,
callbackList: null | Array<Callback>,

// Dev only
isProcessing?: boolean,
Expand Down Expand Up @@ -95,13 +96,15 @@ function ensureUpdateQueue(fiber : Fiber) : UpdateQueue {
first: null,
last: null,
hasForceUpdate: false,
callbackList: null,
isProcessing: false,
};
} else {
queue = {
first: null,
last: null,
hasForceUpdate: false,
callbackList: null,
};
}

Expand All @@ -110,19 +113,25 @@ function ensureUpdateQueue(fiber : Fiber) : UpdateQueue {
}

// Clones an update queue from a source fiber onto its alternate.
function cloneUpdateQueue(alt : Fiber, fiber : Fiber) : UpdateQueue | null {
const sourceQueue = fiber.updateQueue;
if (!sourceQueue) {
function cloneUpdateQueue(current : Fiber, workInProgress : Fiber) : UpdateQueue | null {
const currentQueue = current.updateQueue;
if (!currentQueue) {
// The source fiber does not have an update queue.
alt.updateQueue = null;
workInProgress.updateQueue = null;
return null;
}
// If the alternate already has a queue, reuse the previous object.
const altQueue = alt.updateQueue || {};
altQueue.first = sourceQueue.first;
altQueue.last = sourceQueue.last;
altQueue.hasForceUpdate = sourceQueue.hasForceUpdate;
alt.updateQueue = altQueue;
const altQueue = workInProgress.updateQueue || {};
altQueue.first = currentQueue.first;
altQueue.last = currentQueue.last;

// These fields are invalid by the time we clone from current. Reset them.
altQueue.hasForceUpdate = false;
altQueue.callbackList = null;
altQueue.isProcessing = false;

workInProgress.updateQueue = altQueue;

return altQueue;
}
exports.cloneUpdateQueue = cloneUpdateQueue;
Expand Down Expand Up @@ -438,29 +447,20 @@ function beginUpdateQueue(
// Second condition ignores top-level unmount callbacks if they are not the
// last update in the queue, since a subsequent update will cause a remount.
if (update.callback && !(update.isTopLevelUnmount && update.next)) {
const callbackUpdate = cloneUpdate(update);
if (callbackList && callbackList.last) {
callbackList.last.next = callbackUpdate;
callbackList.last = callbackUpdate;
} else {
callbackList = {
first: callbackUpdate,
last: callbackUpdate,
hasForceUpdate: false,
};
}
callbackList = callbackList || [];
callbackList.push(update.callback);
workInProgress.effectTag |= CallbackEffect;
}
update = update.next;
}

if (!queue.first && !queue.hasForceUpdate) {
// Queue is now empty
queue.callbackList = callbackList;

if (!queue.first && !callbackList && !queue.hasForceUpdate) {
// The queue is empty and there are no callbacks. We can reset it.
workInProgress.updateQueue = null;
}

workInProgress.callbackList = callbackList;

if (__DEV__) {
queue.isProcessing = false;
}
Expand All @@ -469,19 +469,14 @@ function beginUpdateQueue(
}
exports.beginUpdateQueue = beginUpdateQueue;

function commitCallbacks(finishedWork : Fiber, callbackList : UpdateQueue, context : mixed) {
const stopAfter = callbackList.last;
let update = callbackList.first;
while (update) {
const callback = update.callback;
if (typeof callback === 'function') {
callback.call(context);
}
if (update === stopAfter) {
break;
}
update = update.next;
function commitCallbacks(finishedWork : Fiber, queue : UpdateQueue, context : mixed) {
const callbackList = queue.callbackList;
if (!callbackList) {
return;
}
for (let i = 0; i < callbackList.length; i++) {
const callback = callbackList[i];
callback.call(context);
}
finishedWork.callbackList = null;
}
exports.commitCallbacks = commitCallbacks;

0 comments on commit 00be2e4

Please sign in to comment.