在《源碼3》requestUpdateLane函數根據eventLane獲取不同情況對應優先級。
一、優先級
1.Lane的tag
一共有32種lane。
var TotalLanes = 31;
var NoLanes =
/* */
0;
var NoLane =
/* */
0;
var SyncLane =
/* */
1;
var InputContinuousHydrationLane =
/* */
2;
var InputContinuousLane =
/* */
4;
var DefaultHydrationLane =
/* */
8;
var DefaultLane =
/* */
16;
var TransitionHydrationLane =
/* */
32;
var TransitionLanes =
/* */
4194240;
var TransitionLane1 =
/* */
64;
var TransitionLane2 =
/* */
128;
var TransitionLane3 =
/* */
256;
var TransitionLane4 =
/* */
512;
var TransitionLane5 =
/* */
1024;
var TransitionLane6 =
/* */
2048;
var TransitionLane7 =
/* */
4096;
var TransitionLane8 =
/* */
8192;
var TransitionLane9 =
/* */
16384;
var TransitionLane10 =
/* */
32768;
var TransitionLane11 =
/* */
65536;
var TransitionLane12 =
/* */
131072;
var TransitionLane13 =
/* */
262144;
var TransitionLane14 =
/* */
524288;
var TransitionLane15 =
/* */
1048576;
var TransitionLane16 =
/* */
2097152;
var RetryLanes =
/* */
130023424;
var RetryLane1 =
/* */
4194304;
var RetryLane2 =
/* */
8388608;
var RetryLane3 =
/* */
16777216;
var RetryLane4 =
/* */
33554432;
var RetryLane5 =
/* */
67108864;
var SomeRetryLane = RetryLane1;
var SelectiveHydrationLane =
/* */
134217728;
var NonIdleLanes =
/* */
268435455;
var IdleHydrationLane =
/* */
268435456;
var IdleLane =
/* */
536870912;
var OffscreenLane =
/* */
1073741824; // This function is used for the experimental timeline (react-devtools-timeline)
// It should be kept in sync with the Lanes values above.
2.React中事件對應的優先級(獲取事件對應的優先級getEventPriority函數)
一共有4種優先級。
在getEventPriority中獲取事件對應的react優先級,有:
- DiscreteEventPriority(離散事件優先級)
ContinuousEventPriority(連續事件優先級)
DefaultEventPriority(默認優先級)
IdleEventPriority(空間時間優先級)
function getEventPriority(domEventName) {switch (domEventName) {// Used by SimpleEventPlugin:case 'cancel':case 'click':case 'close':case 'contextmenu':case 'copy':case 'cut':case 'auxclick':case 'dblclick':case 'dragend':case 'dragstart':case 'drop':case 'focusin':case 'focusout':case 'input':case 'invalid':case 'keydown':case 'keypress':case 'keyup':case 'mousedown':case 'mouseup':case 'paste':case 'pause':case 'play':case 'pointercancel':case 'pointerdown':case 'pointerup':case 'ratechange':case 'reset':case 'resize':case 'seeked':case 'submit':case 'touchcancel':case 'touchend':case 'touchstart':case 'volumechange': // Used by polyfills:// eslint-disable-next-line no-fallthroughcase 'change':case 'selectionchange':case 'textInput':case 'compositionstart':case 'compositionend':case 'compositionupdate': // Only enableCreateEventHandleAPI:// eslint-disable-next-line no-fallthroughcase 'beforeblur':case 'afterblur': // Not used by React but could be by user code:// eslint-disable-next-line no-fallthroughcase 'beforeinput':case 'blur':case 'fullscreenchange':case 'focus':case 'hashchange':case 'popstate':case 'select':case 'selectstart':return DiscreteEventPriority;case 'drag':case 'dragenter':case 'dragexit':case 'dragleave':case 'dragover':case 'mousemove':case 'mouseout':case 'mouseover':case 'pointermove':case 'pointerout':case 'pointerover':case 'scroll':case 'toggle':case 'touchmove':case 'wheel': // Not used by React but could be by user code:// eslint-disable-next-line no-fallthroughcase 'mouseenter':case 'mouseleave':case 'pointerenter':case 'pointerleave':return ContinuousEventPriority;case 'message':{// We might be in the Scheduler callback.// Eventually this mechanism will be replaced by a check// of the current priority on the native scheduler.//見shceduler優先級轉換為React優先級}default:return DefaultEventPriority;}
}
3.schedule中的優先級
一共有5種優先級。
var ImmediatePriority = Scheduler.unstable_ImmediatePriority;
var UserBlockingPriority = Scheduler.unstable_UserBlockingPriority;
var NormalPriority = Scheduler.unstable_NormalPriority;
var LowPriority = Scheduler.unstable_LowPriority;
var IdlePriority = Scheduler.unstable_IdlePriority;const unstable_ImmediatePriority = 1;
const unstable_UserBlockingPriority = 2;
const unstable_NormalPriority = 3;
const unstable_IdlePriority = 5;
const unstable_LowPriority = 4;
二、優先級轉換的函數
1. lanes優先級轉換為React優先級
lane和React全局對應關系:
var DiscreteEventPriority = SyncLane;
var ContinuousEventPriority = InputContinuousLane;
var DefaultEventPriority = DefaultLane;
var IdleEventPriority = IdleLane;
var currentUpdatePriority = NoLane;
lane與React優先級轉換:?
function lanesToEventPriority(lanes) {var lane = getHighestPriorityLane(lanes);if (!isHigherEventPriority(DiscreteEventPriority, lane)) {return DiscreteEventPriority;}if (!isHigherEventPriority(ContinuousEventPriority, lane)) {return ContinuousEventPriority;}if (includesNonIdleWork(lane)) {return DefaultEventPriority;}return IdleEventPriority;
}
2. React優先級轉換為scheduler優先級
var schedulerPriorityLevel;switch (lanesToEventPriority(nextLanes)) {case DiscreteEventPriority:schedulerPriorityLevel = ImmediatePriority;break;case ContinuousEventPriority:schedulerPriorityLevel = UserBlockingPriority;break;case DefaultEventPriority:schedulerPriorityLevel = NormalPriority;break;case IdleEventPriority:schedulerPriorityLevel = IdlePriority;break;default:schedulerPriorityLevel = NormalPriority;break;
}
3.scheduler優先級轉換為React優先級
// We might be in the Scheduler callback.
// Eventually this mechanism will be replaced by a check
// of the current priority on the native scheduler.
var schedulerPriority = getCurrentPriorityLevel();switch (schedulerPriority) {case ImmediatePriority:return DiscreteEventPriority;case UserBlockingPriority:return ContinuousEventPriority;case NormalPriority:case LowPriority:// TODO: Handle LowSchedulerPriority, somehow. Maybe the same lane as hydration.return DefaultEventPriority;case IdlePriority:return IdleEventPriority;default:return DefaultEventPriority;
}
三、requestUpdateLane函數
暫不考慮transition情況,優先級有四種返回情況:
非并發模式,產生同步優先級
render階段產生的 update,返回 render 階段進行中的優先級
使用手動設置的優先級
如果沒有手動設置的優先級,則獲取當前事件的優先級。
function requestUpdateLane(fiber) {var mode = fiber.mode;if ((mode & ConcurrentMode) === NoMode) {//非并發模式,產生同步優先級return SyncLane;} else if ((executionContext & RenderContext) !== NoContext &&workInProgressRootRenderLanes !== NoLanes) {// render階段產生的 update,返回 render 階段進行中的優先級return pickArbitraryLane(workInProgressRootRenderLanes);}//transition情況暫不做討論//使用手動設置的優先級var updateLane = getCurrentUpdatePriority();if (updateLane !== NoLane) {return updateLane;}//如果沒有手動設置的優先級,則獲取當前事件的優先級var eventLane = getCurrentEventPriority();return eventLane;
}function getCurrentEventPriority() {var currentEvent = window.event;if (currentEvent === undefined) {return DefaultEventPriority;}//詳見本文(一、優先級)第二節getEventPriority函數,返回React優先級return getEventPriority(currentEvent.type);
}//currentUpdatePriority是存儲優先級的全局變量
function getCurrentUpdatePriority() {return currentUpdatePriority;
}
?