@legendapp/list 3.0.0 → 3.0.2
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/CHANGELOG.md +10 -0
- package/package.json +1 -1
- package/react-native.js +1201 -1183
- package/react-native.mjs +1201 -1183
- package/react-native.web.js +1338 -1321
- package/react-native.web.mjs +1338 -1321
- package/react.js +1338 -1321
- package/react.mjs +1338 -1321
- package/section-list.d.ts +19 -2
- package/section-list.js +47 -26
- package/section-list.mjs +47 -26
package/react-native.mjs
CHANGED
|
@@ -1981,18 +1981,29 @@ function shouldFinishInitialZeroTargetScroll(ctx) {
|
|
|
1981
1981
|
const { state } = ctx;
|
|
1982
1982
|
return !!((_a3 = state.scrollingTo) == null ? void 0 : _a3.isInitialScroll) && state.props.data.length > 0 && getContentSize(ctx) <= state.scrollLength && state.scrollPending <= INITIAL_SCROLL_ZERO_TARGET_EPSILON;
|
|
1983
1983
|
}
|
|
1984
|
-
function
|
|
1984
|
+
function isEndAlignedLastItemTarget(ctx, scrollingTo) {
|
|
1985
|
+
return scrollingTo.index === ctx.state.props.data.length - 1 && scrollingTo.viewPosition === 1;
|
|
1986
|
+
}
|
|
1987
|
+
function getCurrentTargetOffset(ctx, scrollingTo) {
|
|
1985
1988
|
var _a3;
|
|
1989
|
+
const index = scrollingTo.index;
|
|
1990
|
+
const shouldRecomputeEndTarget = isEndAlignedLastItemTarget(ctx, scrollingTo);
|
|
1991
|
+
const requestedTargetOffset = shouldRecomputeEndTarget && index !== void 0 ? calculateOffsetWithOffsetPosition(ctx, calculateOffsetForIndex(ctx, index), scrollingTo) : (_a3 = scrollingTo.targetOffset) != null ? _a3 : clampScrollOffset(ctx, scrollingTo.offset - (scrollingTo.viewOffset || 0), scrollingTo);
|
|
1992
|
+
return clampScrollOffset(ctx, requestedTargetOffset, scrollingTo);
|
|
1993
|
+
}
|
|
1994
|
+
function getResolvedScrollCompletionState(ctx, scrollingTo) {
|
|
1986
1995
|
const { state } = ctx;
|
|
1987
1996
|
const scroll = state.scrollPending;
|
|
1988
1997
|
const adjust = state.scrollAdjustHandler.getAdjust();
|
|
1989
|
-
const clampedTargetOffset = (
|
|
1998
|
+
const clampedTargetOffset = getCurrentTargetOffset(ctx, scrollingTo);
|
|
1990
1999
|
const maxOffset = clampScrollOffset(ctx, scroll, scrollingTo);
|
|
1991
2000
|
const diff1 = Math.abs(scroll - clampedTargetOffset);
|
|
1992
|
-
const
|
|
2001
|
+
const adjustedTargetOffset = clampedTargetOffset + adjust;
|
|
2002
|
+
const diff2 = Math.abs(scroll - adjustedTargetOffset);
|
|
2003
|
+
const canUseAdjustedCompletion = !scrollingTo.animated || Platform.OS === "ios";
|
|
1993
2004
|
return {
|
|
1994
2005
|
clampedTargetOffset,
|
|
1995
|
-
isAtResolvedTarget: Math.abs(scroll - maxOffset) < 1 && (diff1 < 1 ||
|
|
2006
|
+
isAtResolvedTarget: Math.abs(scroll - maxOffset) < 1 && (diff1 < 1 || canUseAdjustedCompletion && diff2 < 1)
|
|
1996
2007
|
};
|
|
1997
2008
|
}
|
|
1998
2009
|
function checkFinishedScrollFrame(ctx) {
|
|
@@ -2049,6 +2060,7 @@ function checkFinishedScrollFallback(ctx) {
|
|
|
2049
2060
|
const shouldRetrySilentInitialNativeScroll = Platform.OS === "android" && canFinishAfterSilentNativeDispatch && !initialScrollCompletion.didRetrySilentInitialScroll(state);
|
|
2050
2061
|
const shouldFinishAfterObservedScroll = state.hasScrolled && (!isStillScrollingTo.isInitialScroll || completionState.isAtResolvedTarget);
|
|
2051
2062
|
const shouldRetryUnalignedInitialScroll = isStillScrollingTo.isInitialScroll && !completionState.isAtResolvedTarget && numChecks <= maxChecks;
|
|
2063
|
+
const shouldRetryUnalignedEndScroll = Platform.OS === "ios" && !isStillScrollingTo.isInitialScroll && isEndAlignedLastItemTarget(ctx, isStillScrollingTo) && !completionState.isAtResolvedTarget && numChecks <= maxChecks;
|
|
2052
2064
|
if (shouldRetrySilentInitialNativeScroll) {
|
|
2053
2065
|
const targetOffset = (_b = (_a3 = getInitialScrollWatchdogTargetOffset(state)) != null ? _a3 : isStillScrollingTo.targetOffset) != null ? _b : 0;
|
|
2054
2066
|
const jiggleOffset = targetOffset >= SILENT_INITIAL_SCROLL_TARGET_EPSILON ? targetOffset - SILENT_INITIAL_SCROLL_TARGET_EPSILON : targetOffset + SILENT_INITIAL_SCROLL_TARGET_EPSILON;
|
|
@@ -2058,6 +2070,9 @@ function checkFinishedScrollFallback(ctx) {
|
|
|
2058
2070
|
scrollToFallbackOffset(ctx, targetOffset);
|
|
2059
2071
|
});
|
|
2060
2072
|
scheduleFallbackCheck(SILENT_INITIAL_SCROLL_RETRY_DELAY_MS);
|
|
2073
|
+
} else if (shouldRetryUnalignedEndScroll) {
|
|
2074
|
+
scrollToFallbackOffset(ctx, completionState.clampedTargetOffset);
|
|
2075
|
+
scheduleFallbackCheck(100);
|
|
2061
2076
|
} else if (shouldFinishZeroTarget || shouldFinishAfterObservedScroll || canFinishInitialScrollWithoutNativeProgress || canFinishAfterSilentNativeDispatch || numChecks > maxChecks) {
|
|
2062
2077
|
finishScrollTo(ctx);
|
|
2063
2078
|
} else if ((isNativeInitialPending || shouldRetryUnalignedInitialScroll) && numChecks <= maxChecks) {
|
|
@@ -2100,773 +2115,1199 @@ function doScrollTo(ctx, params) {
|
|
|
2100
2115
|
}
|
|
2101
2116
|
}
|
|
2102
2117
|
|
|
2103
|
-
// src/core/
|
|
2104
|
-
function
|
|
2105
|
-
|
|
2106
|
-
|
|
2118
|
+
// src/core/doMaintainScrollAtEnd.ts
|
|
2119
|
+
function doMaintainScrollAtEnd(ctx) {
|
|
2120
|
+
const state = ctx.state;
|
|
2121
|
+
const {
|
|
2122
|
+
didContainersLayout,
|
|
2123
|
+
pendingNativeMVCPAdjust,
|
|
2124
|
+
refScroller,
|
|
2125
|
+
props: { maintainScrollAtEnd }
|
|
2126
|
+
} = state;
|
|
2127
|
+
const isWithinMaintainScrollAtEndThreshold = peek$(ctx, "isWithinMaintainScrollAtEndThreshold");
|
|
2128
|
+
const shouldMaintainScrollAtEnd = !!(isWithinMaintainScrollAtEndThreshold && maintainScrollAtEnd && didContainersLayout);
|
|
2129
|
+
if (pendingNativeMVCPAdjust) {
|
|
2130
|
+
state.pendingMaintainScrollAtEnd = shouldMaintainScrollAtEnd;
|
|
2131
|
+
return false;
|
|
2107
2132
|
}
|
|
2108
|
-
|
|
2109
|
-
|
|
2110
|
-
const
|
|
2111
|
-
|
|
2133
|
+
state.pendingMaintainScrollAtEnd = false;
|
|
2134
|
+
if (shouldMaintainScrollAtEnd) {
|
|
2135
|
+
const contentSize = getContentSize(ctx);
|
|
2136
|
+
if (contentSize < state.scrollLength) {
|
|
2137
|
+
state.scroll = 0;
|
|
2138
|
+
}
|
|
2139
|
+
if (!state.maintainingScrollAtEnd) {
|
|
2140
|
+
state.maintainingScrollAtEnd = true;
|
|
2141
|
+
requestAnimationFrame(() => {
|
|
2142
|
+
if (peek$(ctx, "isWithinMaintainScrollAtEndThreshold")) {
|
|
2143
|
+
const scroller = refScroller.current;
|
|
2144
|
+
if (state.props.horizontal && isHorizontalRTL(state)) {
|
|
2145
|
+
const currentContentSize = getContentSize(ctx);
|
|
2146
|
+
const logicalEndOffset = getLogicalHorizontalMaxOffset(state, currentContentSize);
|
|
2147
|
+
const nativeOffset = toNativeHorizontalOffset(state, logicalEndOffset, currentContentSize);
|
|
2148
|
+
scroller == null ? void 0 : scroller.scrollTo({
|
|
2149
|
+
animated: maintainScrollAtEnd.animated,
|
|
2150
|
+
x: nativeOffset,
|
|
2151
|
+
y: 0
|
|
2152
|
+
});
|
|
2153
|
+
} else {
|
|
2154
|
+
scroller == null ? void 0 : scroller.scrollToEnd({
|
|
2155
|
+
animated: maintainScrollAtEnd.animated
|
|
2156
|
+
});
|
|
2157
|
+
}
|
|
2158
|
+
setTimeout(
|
|
2159
|
+
() => {
|
|
2160
|
+
state.maintainingScrollAtEnd = false;
|
|
2161
|
+
},
|
|
2162
|
+
maintainScrollAtEnd.animated ? 500 : 0
|
|
2163
|
+
);
|
|
2164
|
+
} else {
|
|
2165
|
+
state.maintainingScrollAtEnd = false;
|
|
2166
|
+
}
|
|
2167
|
+
});
|
|
2168
|
+
}
|
|
2169
|
+
return true;
|
|
2112
2170
|
}
|
|
2113
|
-
return
|
|
2171
|
+
return false;
|
|
2114
2172
|
}
|
|
2115
|
-
|
|
2116
|
-
|
|
2117
|
-
|
|
2118
|
-
const
|
|
2119
|
-
|
|
2120
|
-
|
|
2121
|
-
|
|
2122
|
-
|
|
2123
|
-
|
|
2124
|
-
|
|
2125
|
-
|
|
2126
|
-
|
|
2127
|
-
|
|
2128
|
-
|
|
2129
|
-
|
|
2130
|
-
|
|
2173
|
+
|
|
2174
|
+
// src/utils/requestAdjust.ts
|
|
2175
|
+
function requestAdjust(ctx, positionDiff, dataChanged) {
|
|
2176
|
+
const state = ctx.state;
|
|
2177
|
+
if (Math.abs(positionDiff) > 0.1) {
|
|
2178
|
+
const needsScrollWorkaround = Platform.OS === "android" && !IsNewArchitecture && dataChanged && state.scroll <= positionDiff;
|
|
2179
|
+
const doit = () => {
|
|
2180
|
+
if (needsScrollWorkaround) {
|
|
2181
|
+
doScrollTo(ctx, { horizontal: state.props.horizontal, offset: state.scroll });
|
|
2182
|
+
} else {
|
|
2183
|
+
state.scrollAdjustHandler.requestAdjust(positionDiff);
|
|
2184
|
+
if (state.adjustingFromInitialMount) {
|
|
2185
|
+
state.adjustingFromInitialMount--;
|
|
2186
|
+
}
|
|
2187
|
+
}
|
|
2188
|
+
};
|
|
2189
|
+
state.scroll += positionDiff;
|
|
2190
|
+
state.scrollForNextCalculateItemsInView = void 0;
|
|
2191
|
+
const readyToRender = peek$(ctx, "readyToRender");
|
|
2192
|
+
if (readyToRender) {
|
|
2193
|
+
doit();
|
|
2194
|
+
if (Platform.OS !== "web") {
|
|
2195
|
+
const threshold = state.scroll - positionDiff / 2;
|
|
2196
|
+
if (!state.ignoreScrollFromMVCP) {
|
|
2197
|
+
state.ignoreScrollFromMVCP = {};
|
|
2198
|
+
}
|
|
2199
|
+
if (positionDiff > 0) {
|
|
2200
|
+
state.ignoreScrollFromMVCP.lt = threshold;
|
|
2201
|
+
} else {
|
|
2202
|
+
state.ignoreScrollFromMVCP.gt = threshold;
|
|
2203
|
+
}
|
|
2204
|
+
if (state.ignoreScrollFromMVCPTimeout) {
|
|
2205
|
+
clearTimeout(state.ignoreScrollFromMVCPTimeout);
|
|
2206
|
+
}
|
|
2207
|
+
const delay = needsScrollWorkaround ? 250 : 100;
|
|
2208
|
+
state.ignoreScrollFromMVCPTimeout = setTimeout(() => {
|
|
2209
|
+
var _a3;
|
|
2210
|
+
state.ignoreScrollFromMVCP = void 0;
|
|
2211
|
+
const shouldForceUpdate = state.ignoreScrollFromMVCPIgnored && state.scrollProcessingEnabled !== false;
|
|
2212
|
+
if (shouldForceUpdate) {
|
|
2213
|
+
state.ignoreScrollFromMVCPIgnored = false;
|
|
2214
|
+
state.scrollPending = state.scroll;
|
|
2215
|
+
(_a3 = state.reprocessCurrentScroll) == null ? void 0 : _a3.call(state);
|
|
2216
|
+
}
|
|
2217
|
+
}, delay);
|
|
2218
|
+
}
|
|
2219
|
+
} else {
|
|
2220
|
+
state.adjustingFromInitialMount = (state.adjustingFromInitialMount || 0) + 1;
|
|
2221
|
+
requestAnimationFrame(doit);
|
|
2222
|
+
}
|
|
2131
2223
|
}
|
|
2132
2224
|
}
|
|
2133
|
-
|
|
2134
|
-
|
|
2135
|
-
|
|
2136
|
-
|
|
2137
|
-
|
|
2138
|
-
|
|
2139
|
-
|
|
2140
|
-
|
|
2141
|
-
|
|
2142
|
-
|
|
2143
|
-
} = scrollTarget;
|
|
2144
|
-
const {
|
|
2145
|
-
props: { horizontal }
|
|
2146
|
-
} = state;
|
|
2147
|
-
if (state.animFrameCheckFinishedScroll) {
|
|
2148
|
-
cancelAnimationFrame(ctx.state.animFrameCheckFinishedScroll);
|
|
2225
|
+
|
|
2226
|
+
// src/core/mvcp.ts
|
|
2227
|
+
var MVCP_POSITION_EPSILON = 0.1;
|
|
2228
|
+
var MVCP_ANCHOR_LOCK_TTL_MS = 300;
|
|
2229
|
+
var MVCP_ANCHOR_LOCK_QUIET_PASSES_TO_RELEASE = 2;
|
|
2230
|
+
var NATIVE_END_CLAMP_EPSILON = 1;
|
|
2231
|
+
function resolveAnchorLock(state, enableMVCPAnchorLock, mvcpData, now) {
|
|
2232
|
+
if (!enableMVCPAnchorLock) {
|
|
2233
|
+
state.mvcpAnchorLock = void 0;
|
|
2234
|
+
return void 0;
|
|
2149
2235
|
}
|
|
2150
|
-
|
|
2151
|
-
|
|
2236
|
+
const lock = state.mvcpAnchorLock;
|
|
2237
|
+
if (!lock) {
|
|
2238
|
+
return void 0;
|
|
2152
2239
|
}
|
|
2153
|
-
const
|
|
2154
|
-
const
|
|
2155
|
-
|
|
2156
|
-
|
|
2157
|
-
|
|
2158
|
-
|
|
2159
|
-
|
|
2160
|
-
|
|
2240
|
+
const isExpired = now > lock.expiresAt;
|
|
2241
|
+
const isMissing = state.indexByKey.get(lock.id) === void 0;
|
|
2242
|
+
if (isExpired || isMissing || !mvcpData) {
|
|
2243
|
+
state.mvcpAnchorLock = void 0;
|
|
2244
|
+
return void 0;
|
|
2245
|
+
}
|
|
2246
|
+
return lock;
|
|
2247
|
+
}
|
|
2248
|
+
function updateAnchorLock(state, params) {
|
|
2249
|
+
if (Platform.OS === "web") {
|
|
2250
|
+
const { anchorId, anchorPosition, dataChanged, now, positionDiff } = params;
|
|
2251
|
+
const enableMVCPAnchorLock = !!dataChanged || !!state.mvcpAnchorLock;
|
|
2252
|
+
const mvcpData = state.props.maintainVisibleContentPosition.data;
|
|
2253
|
+
if (!enableMVCPAnchorLock || !mvcpData || state.scrollingTo || !anchorId || anchorPosition === void 0) {
|
|
2254
|
+
return;
|
|
2161
2255
|
}
|
|
2162
|
-
const
|
|
2163
|
-
|
|
2164
|
-
|
|
2165
|
-
|
|
2166
|
-
|
|
2167
|
-
|
|
2256
|
+
const existingLock = state.mvcpAnchorLock;
|
|
2257
|
+
const quietPasses = !dataChanged && Math.abs(positionDiff) <= MVCP_POSITION_EPSILON && (existingLock == null ? void 0 : existingLock.id) === anchorId ? existingLock.quietPasses + 1 : 0;
|
|
2258
|
+
if (!dataChanged && quietPasses >= MVCP_ANCHOR_LOCK_QUIET_PASSES_TO_RELEASE) {
|
|
2259
|
+
state.mvcpAnchorLock = void 0;
|
|
2260
|
+
return;
|
|
2261
|
+
}
|
|
2262
|
+
state.mvcpAnchorLock = {
|
|
2263
|
+
expiresAt: now + MVCP_ANCHOR_LOCK_TTL_MS,
|
|
2264
|
+
id: anchorId,
|
|
2265
|
+
position: anchorPosition,
|
|
2266
|
+
quietPasses
|
|
2168
2267
|
};
|
|
2169
2268
|
}
|
|
2170
|
-
|
|
2171
|
-
|
|
2172
|
-
if (
|
|
2173
|
-
|
|
2174
|
-
} else {
|
|
2175
|
-
state.scroll = offset;
|
|
2269
|
+
}
|
|
2270
|
+
function shouldQueueNativeMVCPAdjust(dataChanged, state, positionDiff, prevTotalSize, prevScroll, scrollTarget) {
|
|
2271
|
+
if (!dataChanged || Platform.OS === "web" || !state.props.maintainVisibleContentPosition.data || scrollTarget !== void 0 || positionDiff >= -MVCP_POSITION_EPSILON) {
|
|
2272
|
+
return false;
|
|
2176
2273
|
}
|
|
2274
|
+
const distanceFromEnd = prevTotalSize - prevScroll - state.scrollLength;
|
|
2275
|
+
return distanceFromEnd < Math.abs(positionDiff) - MVCP_POSITION_EPSILON;
|
|
2177
2276
|
}
|
|
2178
|
-
|
|
2179
|
-
|
|
2180
|
-
|
|
2181
|
-
if (dataLength <= 0) {
|
|
2182
|
-
return -1;
|
|
2277
|
+
function getPredictedNativeClamp(state, unresolvedAmount, totalSize) {
|
|
2278
|
+
if (Math.abs(unresolvedAmount) <= MVCP_POSITION_EPSILON) {
|
|
2279
|
+
return 0;
|
|
2183
2280
|
}
|
|
2184
|
-
|
|
2185
|
-
|
|
2281
|
+
const maxScroll = Math.max(0, totalSize - state.scrollLength);
|
|
2282
|
+
const clampDelta = maxScroll - state.scroll;
|
|
2283
|
+
if (unresolvedAmount < 0) {
|
|
2284
|
+
return Math.max(unresolvedAmount, Math.min(0, clampDelta));
|
|
2186
2285
|
}
|
|
2187
|
-
if (
|
|
2188
|
-
return 0;
|
|
2286
|
+
if (unresolvedAmount > 0) {
|
|
2287
|
+
return Math.min(unresolvedAmount, Math.max(0, clampDelta));
|
|
2189
2288
|
}
|
|
2190
|
-
return
|
|
2289
|
+
return 0;
|
|
2191
2290
|
}
|
|
2192
|
-
function
|
|
2193
|
-
|
|
2194
|
-
|
|
2195
|
-
|
|
2196
|
-
forceScroll,
|
|
2197
|
-
isInitialScroll,
|
|
2198
|
-
viewPosition
|
|
2199
|
-
}) {
|
|
2291
|
+
function getProgressTowardAmount(targetDelta, nativeDelta) {
|
|
2292
|
+
return targetDelta < 0 ? -nativeDelta : nativeDelta;
|
|
2293
|
+
}
|
|
2294
|
+
function settlePendingNativeMVCPAdjust(ctx, remainingAfterManual, nativeDelta) {
|
|
2200
2295
|
const state = ctx.state;
|
|
2201
|
-
|
|
2202
|
-
|
|
2203
|
-
|
|
2204
|
-
|
|
2205
|
-
const isLast = index === data.length - 1;
|
|
2206
|
-
if (isLast && viewPosition === void 0) {
|
|
2207
|
-
viewPosition = 1;
|
|
2296
|
+
state.pendingNativeMVCPAdjust = void 0;
|
|
2297
|
+
const remaining = remainingAfterManual - nativeDelta;
|
|
2298
|
+
if (Math.abs(remaining) > MVCP_POSITION_EPSILON) {
|
|
2299
|
+
requestAdjust(ctx, remaining, true);
|
|
2208
2300
|
}
|
|
2209
|
-
state.scrollForNextCalculateItemsInView = void 0;
|
|
2210
|
-
scrollTo(ctx, {
|
|
2211
|
-
animated,
|
|
2212
|
-
forceScroll,
|
|
2213
|
-
index,
|
|
2214
|
-
isInitialScroll,
|
|
2215
|
-
itemSize,
|
|
2216
|
-
offset: firstIndexOffset,
|
|
2217
|
-
viewOffset,
|
|
2218
|
-
viewPosition: viewPosition != null ? viewPosition : 0
|
|
2219
|
-
});
|
|
2220
|
-
}
|
|
2221
|
-
|
|
2222
|
-
// src/core/initialScroll.ts
|
|
2223
|
-
function dispatchInitialScroll(ctx, params) {
|
|
2224
|
-
const { forceScroll, resolvedOffset, target, waitForCompletionFrame } = params;
|
|
2225
|
-
const requestedIndex = target.index;
|
|
2226
|
-
const index = requestedIndex !== void 0 ? clampScrollIndex(requestedIndex, ctx.state.props.data.length) : void 0;
|
|
2227
|
-
const itemSize = getItemSizeAtIndex(ctx, index);
|
|
2228
|
-
scrollTo(ctx, {
|
|
2229
|
-
animated: false,
|
|
2230
|
-
forceScroll,
|
|
2231
|
-
index: index !== void 0 && index >= 0 ? index : void 0,
|
|
2232
|
-
isInitialScroll: true,
|
|
2233
|
-
itemSize,
|
|
2234
|
-
offset: resolvedOffset,
|
|
2235
|
-
precomputedWithViewOffset: true,
|
|
2236
|
-
viewOffset: target.viewOffset,
|
|
2237
|
-
viewPosition: target.viewPosition,
|
|
2238
|
-
waitForInitialScrollCompletionFrame: waitForCompletionFrame
|
|
2239
|
-
});
|
|
2240
|
-
}
|
|
2241
|
-
function setInitialScrollTarget(state, target, options) {
|
|
2242
|
-
var _a3;
|
|
2243
|
-
state.clearPreservedInitialScrollOnNextFinish = void 0;
|
|
2244
|
-
if (state.timeoutPreservedInitialScrollClear !== void 0) {
|
|
2245
|
-
clearTimeout(state.timeoutPreservedInitialScrollClear);
|
|
2246
|
-
state.timeoutPreservedInitialScrollClear = void 0;
|
|
2247
|
-
}
|
|
2248
|
-
state.initialScroll = target;
|
|
2249
|
-
if ((options == null ? void 0 : options.resetDidFinish) && state.didFinishInitialScroll) {
|
|
2250
|
-
state.didFinishInitialScroll = false;
|
|
2251
|
-
}
|
|
2252
|
-
setInitialScrollSession(state, {
|
|
2253
|
-
kind: ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) === "offset" ? "offset" : "bootstrap"
|
|
2254
|
-
});
|
|
2255
2301
|
}
|
|
2256
|
-
function
|
|
2257
|
-
var _a3, _b;
|
|
2302
|
+
function maybeApplyPredictedNativeMVCPAdjust(ctx) {
|
|
2258
2303
|
const state = ctx.state;
|
|
2259
|
-
|
|
2260
|
-
|
|
2304
|
+
const pending = state.pendingNativeMVCPAdjust;
|
|
2305
|
+
if (!pending || Math.abs(pending.manualApplied) > MVCP_POSITION_EPSILON) {
|
|
2306
|
+
return;
|
|
2261
2307
|
}
|
|
2262
|
-
const
|
|
2263
|
-
const
|
|
2264
|
-
|
|
2265
|
-
|
|
2266
|
-
function getAdvanceableInitialScrollState(state, options) {
|
|
2267
|
-
const { didFinishInitialScroll, queuedInitialLayout, scrollingTo } = state;
|
|
2268
|
-
const initialScroll = state.initialScroll;
|
|
2269
|
-
const isInitialScrollInProgress = !!(scrollingTo == null ? void 0 : scrollingTo.isInitialScroll);
|
|
2270
|
-
const shouldWaitForInitialLayout = !!(options == null ? void 0 : options.requiresMeasuredLayout) && !queuedInitialLayout && !isInitialScrollInProgress;
|
|
2271
|
-
if (!initialScroll || shouldWaitForInitialLayout || didFinishInitialScroll || scrollingTo && !isInitialScrollInProgress) {
|
|
2272
|
-
return void 0;
|
|
2308
|
+
const totalSize = getContentSize(ctx);
|
|
2309
|
+
const predictedNativeClamp = getPredictedNativeClamp(state, pending.amount, totalSize);
|
|
2310
|
+
if (Math.abs(predictedNativeClamp) <= MVCP_POSITION_EPSILON) {
|
|
2311
|
+
return;
|
|
2273
2312
|
}
|
|
2274
|
-
|
|
2275
|
-
|
|
2276
|
-
|
|
2277
|
-
|
|
2278
|
-
|
|
2279
|
-
|
|
2313
|
+
const manualDesired = pending.amount - predictedNativeClamp;
|
|
2314
|
+
if (Math.abs(manualDesired) <= MVCP_POSITION_EPSILON) {
|
|
2315
|
+
return;
|
|
2316
|
+
}
|
|
2317
|
+
pending.manualApplied = manualDesired;
|
|
2318
|
+
requestAdjust(ctx, manualDesired, true);
|
|
2319
|
+
pending.furthestProgressTowardAmount = 0;
|
|
2280
2320
|
}
|
|
2281
|
-
function
|
|
2282
|
-
var _a3, _b, _c;
|
|
2321
|
+
function resolvePendingNativeMVCPAdjust(ctx, newScroll) {
|
|
2283
2322
|
const state = ctx.state;
|
|
2284
|
-
const
|
|
2285
|
-
|
|
2286
|
-
});
|
|
2287
|
-
if (!advanceableState) {
|
|
2323
|
+
const pending = state.pendingNativeMVCPAdjust;
|
|
2324
|
+
if (!pending) {
|
|
2288
2325
|
return false;
|
|
2289
2326
|
}
|
|
2290
|
-
const
|
|
2291
|
-
const
|
|
2292
|
-
const
|
|
2293
|
-
const
|
|
2294
|
-
|
|
2295
|
-
|
|
2296
|
-
|
|
2297
|
-
if (!(options == null ? void 0 : options.forceScroll) && !didOffsetChange && isInitialScrollInProgress && !didActiveInitialTargetChange) {
|
|
2298
|
-
return false;
|
|
2327
|
+
const remainingAfterManual = pending.amount - pending.manualApplied;
|
|
2328
|
+
const nativeDelta = newScroll - (pending.startScroll + pending.manualApplied);
|
|
2329
|
+
const isWrongDirection = remainingAfterManual < 0 && nativeDelta > MVCP_POSITION_EPSILON || remainingAfterManual > 0 && nativeDelta < -MVCP_POSITION_EPSILON;
|
|
2330
|
+
const progressTowardAmount = getProgressTowardAmount(remainingAfterManual, nativeDelta);
|
|
2331
|
+
if (Math.abs(remainingAfterManual) <= MVCP_POSITION_EPSILON) {
|
|
2332
|
+
state.pendingNativeMVCPAdjust = void 0;
|
|
2333
|
+
return true;
|
|
2299
2334
|
}
|
|
2300
|
-
if (
|
|
2335
|
+
if (isWrongDirection) {
|
|
2336
|
+
state.pendingNativeMVCPAdjust = void 0;
|
|
2301
2337
|
return false;
|
|
2302
2338
|
}
|
|
2303
|
-
if (
|
|
2304
|
-
|
|
2339
|
+
if (progressTowardAmount + MVCP_POSITION_EPSILON >= Math.abs(remainingAfterManual)) {
|
|
2340
|
+
settlePendingNativeMVCPAdjust(ctx, remainingAfterManual, nativeDelta);
|
|
2341
|
+
return true;
|
|
2305
2342
|
}
|
|
2306
|
-
const
|
|
2307
|
-
|
|
2308
|
-
|
|
2309
|
-
|
|
2310
|
-
|
|
2311
|
-
|
|
2312
|
-
return true;
|
|
2313
|
-
}
|
|
2314
|
-
function advanceOffsetInitialScroll(ctx, options) {
|
|
2315
|
-
var _a3, _b;
|
|
2316
|
-
const state = ctx.state;
|
|
2317
|
-
const advanceableState = getAdvanceableInitialScrollState(state);
|
|
2318
|
-
if (!advanceableState) {
|
|
2319
|
-
return false;
|
|
2343
|
+
const expectedNativeClampScroll = Math.max(0, getContentSize(ctx) - state.scrollLength);
|
|
2344
|
+
const distanceToClamp = Math.abs(newScroll - expectedNativeClampScroll);
|
|
2345
|
+
const isAtExpectedNativeClamp = distanceToClamp <= NATIVE_END_CLAMP_EPSILON;
|
|
2346
|
+
if (isAtExpectedNativeClamp) {
|
|
2347
|
+
settlePendingNativeMVCPAdjust(ctx, remainingAfterManual, nativeDelta);
|
|
2348
|
+
return true;
|
|
2320
2349
|
}
|
|
2321
|
-
|
|
2322
|
-
|
|
2323
|
-
|
|
2324
|
-
|
|
2350
|
+
if (state.pendingMaintainScrollAtEnd && peek$(ctx, "isWithinMaintainScrollAtEndThreshold") && progressTowardAmount > MVCP_POSITION_EPSILON) {
|
|
2351
|
+
settlePendingNativeMVCPAdjust(ctx, remainingAfterManual, nativeDelta);
|
|
2352
|
+
return true;
|
|
2353
|
+
}
|
|
2354
|
+
if (progressTowardAmount > pending.furthestProgressTowardAmount + MVCP_POSITION_EPSILON) {
|
|
2355
|
+
pending.furthestProgressTowardAmount = progressTowardAmount;
|
|
2325
2356
|
return false;
|
|
2326
2357
|
}
|
|
2327
|
-
|
|
2328
|
-
|
|
2329
|
-
|
|
2330
|
-
forceScroll,
|
|
2331
|
-
resolvedOffset,
|
|
2332
|
-
target: initialScroll
|
|
2333
|
-
});
|
|
2334
|
-
return true;
|
|
2335
|
-
}
|
|
2336
|
-
function advanceCurrentInitialScrollSession(ctx, options) {
|
|
2337
|
-
var _a3;
|
|
2338
|
-
return ((_a3 = ctx.state.initialScrollSession) == null ? void 0 : _a3.kind) === "offset" ? advanceOffsetInitialScroll(ctx, {
|
|
2339
|
-
forceScroll: options == null ? void 0 : options.forceScroll
|
|
2340
|
-
}) : advanceMeasuredInitialScroll(ctx, {
|
|
2341
|
-
forceScroll: options == null ? void 0 : options.forceScroll
|
|
2342
|
-
});
|
|
2343
|
-
}
|
|
2344
|
-
|
|
2345
|
-
// src/utils/checkAllSizesKnown.ts
|
|
2346
|
-
function isNullOrUndefined2(value) {
|
|
2347
|
-
return value === null || value === void 0;
|
|
2348
|
-
}
|
|
2349
|
-
function getMountedIndicesInRange(state, start, end) {
|
|
2350
|
-
if (!isNullOrUndefined2(end) && !isNullOrUndefined2(start) && start >= 0 && end >= 0) {
|
|
2351
|
-
return Array.from(state.containerItemKeys.keys()).map((key) => state.indexByKey.get(key)).filter((index) => index !== void 0 && index >= start && index <= end).sort((a, b) => a - b);
|
|
2358
|
+
if (pending.furthestProgressTowardAmount > MVCP_POSITION_EPSILON && progressTowardAmount < pending.furthestProgressTowardAmount - MVCP_POSITION_EPSILON) {
|
|
2359
|
+
state.pendingNativeMVCPAdjust = void 0;
|
|
2360
|
+
return false;
|
|
2352
2361
|
}
|
|
2353
|
-
return
|
|
2354
|
-
}
|
|
2355
|
-
function getMountedBufferedIndices(state) {
|
|
2356
|
-
return getMountedIndicesInRange(state, state.startBuffered, state.endBuffered);
|
|
2357
|
-
}
|
|
2358
|
-
function getMountedNoBufferIndices(state) {
|
|
2359
|
-
return getMountedIndicesInRange(state, state.startNoBuffer, state.endNoBuffer);
|
|
2360
|
-
}
|
|
2361
|
-
function checkAllSizesKnown(state, indices) {
|
|
2362
|
-
return indices.length > 0 && indices.every((index) => {
|
|
2363
|
-
const key = getId(state, index);
|
|
2364
|
-
return key !== void 0 && state.sizesKnown.has(key);
|
|
2365
|
-
});
|
|
2362
|
+
return false;
|
|
2366
2363
|
}
|
|
2367
|
-
|
|
2368
|
-
// src/utils/requestAdjust.ts
|
|
2369
|
-
function requestAdjust(ctx, positionDiff, dataChanged) {
|
|
2364
|
+
function prepareMVCP(ctx, dataChanged) {
|
|
2370
2365
|
const state = ctx.state;
|
|
2371
|
-
|
|
2372
|
-
|
|
2373
|
-
|
|
2374
|
-
|
|
2375
|
-
|
|
2376
|
-
|
|
2377
|
-
|
|
2378
|
-
|
|
2379
|
-
|
|
2380
|
-
|
|
2381
|
-
|
|
2382
|
-
|
|
2383
|
-
|
|
2366
|
+
const { idsInView, positions, props } = state;
|
|
2367
|
+
const {
|
|
2368
|
+
maintainVisibleContentPosition: { data: mvcpData, size: mvcpScroll, shouldRestorePosition }
|
|
2369
|
+
} = props;
|
|
2370
|
+
const isWeb = Platform.OS === "web";
|
|
2371
|
+
const now = Date.now();
|
|
2372
|
+
const enableMVCPAnchorLock = isWeb && (!!dataChanged || !!state.mvcpAnchorLock);
|
|
2373
|
+
const scrollingTo = state.scrollingTo;
|
|
2374
|
+
const anchorLock = isWeb ? resolveAnchorLock(state, enableMVCPAnchorLock, mvcpData, now) : void 0;
|
|
2375
|
+
let prevPosition;
|
|
2376
|
+
let targetId;
|
|
2377
|
+
const idsInViewWithPositions = [];
|
|
2378
|
+
const scrollTarget = scrollingTo == null ? void 0 : scrollingTo.index;
|
|
2379
|
+
const scrollingToViewPosition = scrollingTo == null ? void 0 : scrollingTo.viewPosition;
|
|
2380
|
+
const isEndAnchoredScrollTarget = scrollTarget !== void 0 && state.props.data.length > 0 && scrollTarget >= state.props.data.length - 1 && (scrollingToViewPosition != null ? scrollingToViewPosition : 0) > 0;
|
|
2381
|
+
const shouldMVCP = dataChanged ? mvcpData : mvcpScroll;
|
|
2382
|
+
const indexByKey = state.indexByKey;
|
|
2383
|
+
const prevScroll = state.scroll;
|
|
2384
|
+
const prevTotalSize = getContentSize(ctx);
|
|
2385
|
+
if (shouldMVCP) {
|
|
2386
|
+
if (!isWeb && state.pendingNativeMVCPAdjust && scrollTarget === void 0) {
|
|
2387
|
+
maybeApplyPredictedNativeMVCPAdjust(ctx);
|
|
2388
|
+
return void 0;
|
|
2389
|
+
}
|
|
2390
|
+
if (anchorLock && scrollTarget === void 0) {
|
|
2391
|
+
targetId = anchorLock.id;
|
|
2392
|
+
prevPosition = anchorLock.position;
|
|
2393
|
+
} else if (scrollTarget !== void 0) {
|
|
2394
|
+
if (!IsNewArchitecture && (scrollingTo == null ? void 0 : scrollingTo.isInitialScroll)) {
|
|
2395
|
+
return void 0;
|
|
2384
2396
|
}
|
|
2385
|
-
|
|
2386
|
-
state.
|
|
2387
|
-
|
|
2388
|
-
|
|
2389
|
-
if (
|
|
2390
|
-
|
|
2391
|
-
|
|
2392
|
-
const
|
|
2393
|
-
if (
|
|
2394
|
-
|
|
2397
|
+
targetId = getId(state, scrollTarget);
|
|
2398
|
+
} else if (idsInView.length > 0 && state.didContainersLayout && !dataChanged) {
|
|
2399
|
+
targetId = idsInView.find((id) => indexByKey.get(id) !== void 0);
|
|
2400
|
+
}
|
|
2401
|
+
if (dataChanged && idsInView.length > 0 && state.didContainersLayout) {
|
|
2402
|
+
for (let i = 0; i < idsInView.length; i++) {
|
|
2403
|
+
const id = idsInView[i];
|
|
2404
|
+
const index = indexByKey.get(id);
|
|
2405
|
+
if (index !== void 0) {
|
|
2406
|
+
const position = positions[index];
|
|
2407
|
+
if (position !== void 0) {
|
|
2408
|
+
idsInViewWithPositions.push({ id, position });
|
|
2409
|
+
}
|
|
2395
2410
|
}
|
|
2396
|
-
|
|
2397
|
-
|
|
2398
|
-
|
|
2399
|
-
|
|
2411
|
+
}
|
|
2412
|
+
}
|
|
2413
|
+
if (targetId !== void 0 && prevPosition === void 0) {
|
|
2414
|
+
const targetIndex = indexByKey.get(targetId);
|
|
2415
|
+
if (targetIndex !== void 0) {
|
|
2416
|
+
prevPosition = positions[targetIndex];
|
|
2417
|
+
}
|
|
2418
|
+
}
|
|
2419
|
+
return () => {
|
|
2420
|
+
let positionDiff = 0;
|
|
2421
|
+
let anchorIdForLock = anchorLock == null ? void 0 : anchorLock.id;
|
|
2422
|
+
let anchorPositionForLock;
|
|
2423
|
+
let skipTargetAnchor = false;
|
|
2424
|
+
const data = state.props.data;
|
|
2425
|
+
const shouldValidateLockedAnchor = isWeb && dataChanged && mvcpData && scrollTarget === void 0 && targetId !== void 0 && (anchorLock == null ? void 0 : anchorLock.id) === targetId && shouldRestorePosition !== void 0;
|
|
2426
|
+
if (shouldValidateLockedAnchor && targetId !== void 0) {
|
|
2427
|
+
const index = indexByKey.get(targetId);
|
|
2428
|
+
if (index !== void 0) {
|
|
2429
|
+
const item = data[index];
|
|
2430
|
+
skipTargetAnchor = item === void 0 || !shouldRestorePosition(item, index, data);
|
|
2431
|
+
if (skipTargetAnchor && (anchorLock == null ? void 0 : anchorLock.id) === targetId) {
|
|
2432
|
+
state.mvcpAnchorLock = void 0;
|
|
2433
|
+
}
|
|
2400
2434
|
}
|
|
2401
|
-
|
|
2402
|
-
|
|
2435
|
+
}
|
|
2436
|
+
const shouldUseFallbackVisibleAnchor = dataChanged && mvcpData && scrollTarget === void 0 && (() => {
|
|
2437
|
+
if (targetId === void 0 || skipTargetAnchor) {
|
|
2438
|
+
return true;
|
|
2403
2439
|
}
|
|
2404
|
-
const
|
|
2405
|
-
|
|
2406
|
-
|
|
2407
|
-
|
|
2408
|
-
|
|
2409
|
-
|
|
2410
|
-
|
|
2411
|
-
|
|
2412
|
-
|
|
2440
|
+
const targetIndex = indexByKey.get(targetId);
|
|
2441
|
+
return targetIndex === void 0 || positions[targetIndex] === void 0;
|
|
2442
|
+
})();
|
|
2443
|
+
if (shouldUseFallbackVisibleAnchor) {
|
|
2444
|
+
for (let i = 0; i < idsInViewWithPositions.length; i++) {
|
|
2445
|
+
const { id, position } = idsInViewWithPositions[i];
|
|
2446
|
+
const index = indexByKey.get(id);
|
|
2447
|
+
if (index !== void 0 && shouldRestorePosition) {
|
|
2448
|
+
const item = data[index];
|
|
2449
|
+
if (item === void 0 || !shouldRestorePosition(item, index, data)) {
|
|
2450
|
+
continue;
|
|
2451
|
+
}
|
|
2413
2452
|
}
|
|
2414
|
-
|
|
2453
|
+
const newPosition = index !== void 0 ? positions[index] : void 0;
|
|
2454
|
+
if (newPosition !== void 0) {
|
|
2455
|
+
positionDiff = newPosition - position;
|
|
2456
|
+
anchorIdForLock = id;
|
|
2457
|
+
anchorPositionForLock = newPosition;
|
|
2458
|
+
break;
|
|
2459
|
+
}
|
|
2460
|
+
}
|
|
2415
2461
|
}
|
|
2416
|
-
|
|
2417
|
-
|
|
2418
|
-
|
|
2419
|
-
|
|
2462
|
+
if (!skipTargetAnchor && targetId !== void 0 && prevPosition !== void 0) {
|
|
2463
|
+
const targetIndex = indexByKey.get(targetId);
|
|
2464
|
+
const newPosition = targetIndex !== void 0 ? positions[targetIndex] : void 0;
|
|
2465
|
+
if (newPosition !== void 0) {
|
|
2466
|
+
const totalSize = getContentSize(ctx);
|
|
2467
|
+
let diff = newPosition - prevPosition;
|
|
2468
|
+
if (diff !== 0 && isEndAnchoredScrollTarget && state.scroll + state.scrollLength > totalSize) {
|
|
2469
|
+
if (diff > 0) {
|
|
2470
|
+
diff = Math.max(0, totalSize - state.scroll - state.scrollLength);
|
|
2471
|
+
} else {
|
|
2472
|
+
diff = 0;
|
|
2473
|
+
}
|
|
2474
|
+
}
|
|
2475
|
+
positionDiff = diff;
|
|
2476
|
+
anchorIdForLock = targetId;
|
|
2477
|
+
anchorPositionForLock = newPosition;
|
|
2478
|
+
}
|
|
2479
|
+
}
|
|
2480
|
+
if (scrollingToViewPosition && scrollingToViewPosition > 0) {
|
|
2481
|
+
const newSize = getItemSize(ctx, targetId, scrollTarget, state.props.data[scrollTarget]);
|
|
2482
|
+
const prevSize = scrollingTo == null ? void 0 : scrollingTo.itemSize;
|
|
2483
|
+
if (newSize !== void 0 && prevSize !== void 0 && newSize !== prevSize) {
|
|
2484
|
+
const diff = newSize - prevSize;
|
|
2485
|
+
if (diff !== 0) {
|
|
2486
|
+
positionDiff += diff * scrollingToViewPosition;
|
|
2487
|
+
scrollingTo.itemSize = newSize;
|
|
2488
|
+
}
|
|
2489
|
+
}
|
|
2490
|
+
}
|
|
2491
|
+
updateAnchorLock(state, {
|
|
2492
|
+
anchorId: anchorIdForLock,
|
|
2493
|
+
anchorPosition: anchorPositionForLock,
|
|
2494
|
+
dataChanged,
|
|
2495
|
+
now,
|
|
2496
|
+
positionDiff
|
|
2497
|
+
});
|
|
2498
|
+
if (shouldQueueNativeMVCPAdjust(dataChanged, state, positionDiff, prevTotalSize, prevScroll, scrollTarget)) {
|
|
2499
|
+
state.pendingNativeMVCPAdjust = {
|
|
2500
|
+
amount: positionDiff,
|
|
2501
|
+
furthestProgressTowardAmount: 0,
|
|
2502
|
+
manualApplied: 0,
|
|
2503
|
+
startScroll: prevScroll
|
|
2504
|
+
};
|
|
2505
|
+
maybeApplyPredictedNativeMVCPAdjust(ctx);
|
|
2506
|
+
return;
|
|
2507
|
+
}
|
|
2508
|
+
if (Math.abs(positionDiff) > MVCP_POSITION_EPSILON) {
|
|
2509
|
+
const shouldSkipAdjustForMaintainedEnd = state.maintainingScrollAtEnd && peek$(ctx, "isWithinMaintainScrollAtEndThreshold");
|
|
2510
|
+
if (!shouldSkipAdjustForMaintainedEnd) {
|
|
2511
|
+
requestAdjust(ctx, positionDiff, dataChanged && mvcpData);
|
|
2512
|
+
}
|
|
2513
|
+
}
|
|
2514
|
+
};
|
|
2420
2515
|
}
|
|
2421
2516
|
}
|
|
2422
2517
|
|
|
2423
|
-
// src/
|
|
2424
|
-
var
|
|
2425
|
-
|
|
2426
|
-
|
|
2427
|
-
|
|
2428
|
-
|
|
2429
|
-
|
|
2430
|
-
return ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) === "bootstrap" ? state.initialScrollSession.bootstrap : void 0;
|
|
2431
|
-
}
|
|
2432
|
-
function isOffsetInitialScrollSession(state) {
|
|
2518
|
+
// src/platform/flushSync.native.ts
|
|
2519
|
+
var flushSync = (fn) => {
|
|
2520
|
+
fn();
|
|
2521
|
+
};
|
|
2522
|
+
|
|
2523
|
+
// src/core/updateScroll.ts
|
|
2524
|
+
function updateScroll(ctx, newScroll, forceUpdate, options) {
|
|
2433
2525
|
var _a3;
|
|
2434
|
-
|
|
2435
|
-
}
|
|
2436
|
-
|
|
2437
|
-
if (
|
|
2438
|
-
|
|
2526
|
+
const state = ctx.state;
|
|
2527
|
+
const { ignoreScrollFromMVCP, lastScrollAdjustForHistory, scrollAdjustHandler, scrollHistory, scrollingTo } = state;
|
|
2528
|
+
const prevScroll = state.scroll;
|
|
2529
|
+
if ((options == null ? void 0 : options.markHasScrolled) !== false) {
|
|
2530
|
+
state.hasScrolled = true;
|
|
2439
2531
|
}
|
|
2440
|
-
|
|
2441
|
-
|
|
2442
|
-
|
|
2443
|
-
|
|
2532
|
+
state.lastBatchingAction = Date.now();
|
|
2533
|
+
const currentTime = Date.now();
|
|
2534
|
+
const adjust = scrollAdjustHandler.getAdjust();
|
|
2535
|
+
const adjustChanged = lastScrollAdjustForHistory !== void 0 && Math.abs(adjust - lastScrollAdjustForHistory) > 0.1;
|
|
2536
|
+
if (adjustChanged) {
|
|
2537
|
+
scrollHistory.length = 0;
|
|
2444
2538
|
}
|
|
2445
|
-
|
|
2446
|
-
|
|
2447
|
-
|
|
2448
|
-
|
|
2449
|
-
const endOffset = offset + scrollLength;
|
|
2450
|
-
const visibleIndices = [];
|
|
2451
|
-
let index = requestedStartIndex !== void 0 ? Math.max(0, Math.min(dataLength - 1, requestedStartIndex)) : 0;
|
|
2452
|
-
while (index > 0) {
|
|
2453
|
-
const previousIndex = index - 1;
|
|
2454
|
-
const previousPosition = positions[previousIndex];
|
|
2455
|
-
if (previousPosition === void 0) {
|
|
2456
|
-
index = previousIndex;
|
|
2457
|
-
continue;
|
|
2458
|
-
}
|
|
2459
|
-
const previousSize = getSize(previousIndex);
|
|
2460
|
-
if (previousSize === void 0) {
|
|
2461
|
-
index = previousIndex;
|
|
2462
|
-
continue;
|
|
2463
|
-
}
|
|
2464
|
-
if (previousPosition + previousSize <= offset) {
|
|
2465
|
-
break;
|
|
2539
|
+
state.lastScrollAdjustForHistory = adjust;
|
|
2540
|
+
if (scrollingTo === void 0 && !(scrollHistory.length === 0 && newScroll === state.scroll)) {
|
|
2541
|
+
if (!adjustChanged) {
|
|
2542
|
+
scrollHistory.push({ scroll: newScroll, time: currentTime });
|
|
2466
2543
|
}
|
|
2467
|
-
index = previousIndex;
|
|
2468
2544
|
}
|
|
2469
|
-
|
|
2470
|
-
|
|
2471
|
-
|
|
2472
|
-
|
|
2545
|
+
if (scrollHistory.length > 5) {
|
|
2546
|
+
scrollHistory.shift();
|
|
2547
|
+
}
|
|
2548
|
+
if (ignoreScrollFromMVCP && !scrollingTo) {
|
|
2549
|
+
const { lt, gt } = ignoreScrollFromMVCP;
|
|
2550
|
+
if (lt && newScroll < lt || gt && newScroll > gt) {
|
|
2551
|
+
state.ignoreScrollFromMVCPIgnored = true;
|
|
2552
|
+
return;
|
|
2473
2553
|
}
|
|
2474
|
-
|
|
2475
|
-
|
|
2476
|
-
|
|
2554
|
+
}
|
|
2555
|
+
state.scrollPrev = prevScroll;
|
|
2556
|
+
state.scrollPrevTime = state.scrollTime;
|
|
2557
|
+
state.scroll = newScroll;
|
|
2558
|
+
state.scrollTime = currentTime;
|
|
2559
|
+
const scrollDelta = Math.abs(newScroll - prevScroll);
|
|
2560
|
+
const didResolvePendingNativeMVCPAdjust = resolvePendingNativeMVCPAdjust(ctx, newScroll);
|
|
2561
|
+
const scrollLength = state.scrollLength;
|
|
2562
|
+
const lastCalculated = state.scrollLastCalculate;
|
|
2563
|
+
const useAggressiveItemRecalculation = isInMVCPActiveMode(state);
|
|
2564
|
+
const shouldUpdate = useAggressiveItemRecalculation || didResolvePendingNativeMVCPAdjust || forceUpdate || lastCalculated === void 0 || Math.abs(state.scroll - lastCalculated) > 2;
|
|
2565
|
+
if (shouldUpdate) {
|
|
2566
|
+
state.scrollLastCalculate = state.scroll;
|
|
2567
|
+
state.ignoreScrollFromMVCPIgnored = false;
|
|
2568
|
+
state.lastScrollDelta = scrollDelta;
|
|
2569
|
+
const runCalculateItems = () => {
|
|
2570
|
+
var _a4;
|
|
2571
|
+
(_a4 = state.triggerCalculateItemsInView) == null ? void 0 : _a4.call(state, { doMVCP: scrollingTo !== void 0 });
|
|
2572
|
+
checkThresholds(ctx);
|
|
2573
|
+
};
|
|
2574
|
+
if (scrollLength > 0 && scrollingTo === void 0 && scrollDelta > scrollLength && !state.pendingNativeMVCPAdjust) {
|
|
2575
|
+
state.mvcpAnchorLock = void 0;
|
|
2576
|
+
state.pendingNativeMVCPAdjust = void 0;
|
|
2577
|
+
state.userScrollAnchorResetKeys = /* @__PURE__ */ new Set();
|
|
2578
|
+
if (state.queuedMVCPRecalculate !== void 0) {
|
|
2579
|
+
cancelAnimationFrame(state.queuedMVCPRecalculate);
|
|
2580
|
+
state.queuedMVCPRecalculate = void 0;
|
|
2581
|
+
}
|
|
2582
|
+
flushSync(runCalculateItems);
|
|
2583
|
+
} else {
|
|
2584
|
+
runCalculateItems();
|
|
2477
2585
|
}
|
|
2478
|
-
|
|
2479
|
-
|
|
2480
|
-
|
|
2481
|
-
|
|
2586
|
+
const shouldMaintainScrollAtEndAfterPendingSettle = !!state.pendingMaintainScrollAtEnd || !!((_a3 = state.props.maintainScrollAtEnd) == null ? void 0 : _a3.onDataChange);
|
|
2587
|
+
if (didResolvePendingNativeMVCPAdjust && shouldMaintainScrollAtEndAfterPendingSettle) {
|
|
2588
|
+
state.pendingMaintainScrollAtEnd = false;
|
|
2589
|
+
doMaintainScrollAtEnd(ctx);
|
|
2482
2590
|
}
|
|
2591
|
+
state.dataChangeNeedsScrollUpdate = false;
|
|
2592
|
+
state.lastScrollDelta = 0;
|
|
2483
2593
|
}
|
|
2484
|
-
return visibleIndices;
|
|
2485
|
-
}
|
|
2486
|
-
function shouldAbortBootstrapReveal(options) {
|
|
2487
|
-
const {
|
|
2488
|
-
mountFrameCount,
|
|
2489
|
-
maxFrames = DEFAULT_BOOTSTRAP_REVEAL_MAX_FRAMES,
|
|
2490
|
-
maxPasses = DEFAULT_BOOTSTRAP_REVEAL_MAX_PASSES,
|
|
2491
|
-
passCount
|
|
2492
|
-
} = options;
|
|
2493
|
-
return mountFrameCount >= maxFrames || passCount >= maxPasses;
|
|
2494
2594
|
}
|
|
2495
|
-
|
|
2496
|
-
|
|
2497
|
-
|
|
2595
|
+
|
|
2596
|
+
// src/core/scrollTo.ts
|
|
2597
|
+
function getAverageSizeSnapshot(state) {
|
|
2598
|
+
if (Object.keys(state.averageSizes).length === 0) {
|
|
2599
|
+
return void 0;
|
|
2498
2600
|
}
|
|
2499
|
-
|
|
2500
|
-
|
|
2601
|
+
const snapshot = {};
|
|
2602
|
+
for (const itemType in state.averageSizes) {
|
|
2603
|
+
const averages = state.averageSizes[itemType];
|
|
2604
|
+
snapshot[itemType] = averages.avg;
|
|
2501
2605
|
}
|
|
2502
|
-
|
|
2503
|
-
return true;
|
|
2606
|
+
return snapshot;
|
|
2504
2607
|
}
|
|
2505
|
-
function
|
|
2608
|
+
function syncInitialScrollNativeWatchdog(state, options) {
|
|
2506
2609
|
var _a3;
|
|
2507
|
-
const
|
|
2508
|
-
const
|
|
2509
|
-
|
|
2510
|
-
|
|
2610
|
+
const { isInitialScroll, requestedOffset, targetOffset } = options;
|
|
2611
|
+
const existingWatchdog = initialScrollWatchdog.get(state);
|
|
2612
|
+
const shouldWatchInitialNativeScroll = !state.didFinishInitialScroll && (isInitialScroll || !!existingWatchdog) && initialScrollWatchdog.hasNonZeroTargetOffset(targetOffset);
|
|
2613
|
+
const shouldClearInitialNativeScrollWatchdog = !state.didFinishInitialScroll && !!existingWatchdog && initialScrollWatchdog.isAtZeroTargetOffset(requestedOffset);
|
|
2614
|
+
if (shouldWatchInitialNativeScroll) {
|
|
2615
|
+
state.hasScrolled = false;
|
|
2616
|
+
initialScrollWatchdog.set(state, {
|
|
2617
|
+
startScroll: (_a3 = existingWatchdog == null ? void 0 : existingWatchdog.startScroll) != null ? _a3 : state.scroll,
|
|
2618
|
+
targetOffset
|
|
2619
|
+
});
|
|
2620
|
+
return;
|
|
2511
2621
|
}
|
|
2512
|
-
if (
|
|
2513
|
-
|
|
2622
|
+
if (shouldClearInitialNativeScrollWatchdog) {
|
|
2623
|
+
initialScrollWatchdog.clear(state);
|
|
2514
2624
|
}
|
|
2515
|
-
setInitialScrollSession(state, {
|
|
2516
|
-
bootstrap: null,
|
|
2517
|
-
kind: (_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind
|
|
2518
|
-
});
|
|
2519
|
-
}
|
|
2520
|
-
function startBootstrapInitialScrollSession(state, options) {
|
|
2521
|
-
var _a3, _b, _c;
|
|
2522
|
-
const previousBootstrapInitialScroll = getBootstrapInitialScrollSession(state);
|
|
2523
|
-
setInitialScrollSession(state, {
|
|
2524
|
-
bootstrap: {
|
|
2525
|
-
frameHandle: previousBootstrapInitialScroll == null ? void 0 : previousBootstrapInitialScroll.frameHandle,
|
|
2526
|
-
// Re-arming during the initial mount should spend from the same watchdog budget.
|
|
2527
|
-
mountFrameCount: (_a3 = previousBootstrapInitialScroll == null ? void 0 : previousBootstrapInitialScroll.mountFrameCount) != null ? _a3 : 0,
|
|
2528
|
-
passCount: 0,
|
|
2529
|
-
previousResolvedOffset: void 0,
|
|
2530
|
-
scroll: options.scroll,
|
|
2531
|
-
seedContentOffset: (_c = (_b = options.seedContentOffset) != null ? _b : previousBootstrapInitialScroll == null ? void 0 : previousBootstrapInitialScroll.seedContentOffset) != null ? _c : options.scroll,
|
|
2532
|
-
targetIndexSeed: options.targetIndexSeed,
|
|
2533
|
-
visibleIndices: void 0
|
|
2534
|
-
},
|
|
2535
|
-
kind: "bootstrap"
|
|
2536
|
-
});
|
|
2537
2625
|
}
|
|
2538
|
-
function
|
|
2539
|
-
var _a3
|
|
2540
|
-
const
|
|
2541
|
-
|
|
2542
|
-
|
|
2543
|
-
|
|
2544
|
-
|
|
2545
|
-
|
|
2546
|
-
|
|
2547
|
-
|
|
2626
|
+
function scrollTo(ctx, params) {
|
|
2627
|
+
var _a3;
|
|
2628
|
+
const state = ctx.state;
|
|
2629
|
+
const { noScrollingTo, forceScroll, ...scrollTarget } = params;
|
|
2630
|
+
const {
|
|
2631
|
+
animated,
|
|
2632
|
+
isInitialScroll,
|
|
2633
|
+
offset: scrollTargetOffset,
|
|
2634
|
+
precomputedWithViewOffset,
|
|
2635
|
+
waitForInitialScrollCompletionFrame
|
|
2636
|
+
} = scrollTarget;
|
|
2637
|
+
const {
|
|
2638
|
+
props: { horizontal }
|
|
2639
|
+
} = state;
|
|
2640
|
+
if (state.animFrameCheckFinishedScroll) {
|
|
2641
|
+
cancelAnimationFrame(ctx.state.animFrameCheckFinishedScroll);
|
|
2642
|
+
}
|
|
2643
|
+
if (state.timeoutCheckFinishedScrollFallback) {
|
|
2644
|
+
clearTimeout(ctx.state.timeoutCheckFinishedScrollFallback);
|
|
2645
|
+
}
|
|
2646
|
+
const requestedOffset = precomputedWithViewOffset ? scrollTargetOffset : calculateOffsetWithOffsetPosition(ctx, scrollTargetOffset, scrollTarget);
|
|
2647
|
+
const shouldPreserveRawInitialOffsetRequest = !!isInitialScroll && ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) === "offset";
|
|
2648
|
+
const targetOffset = clampScrollOffset(ctx, requestedOffset, scrollTarget);
|
|
2649
|
+
const offset = shouldPreserveRawInitialOffsetRequest ? requestedOffset : targetOffset;
|
|
2650
|
+
state.scrollHistory.length = 0;
|
|
2651
|
+
if (!noScrollingTo) {
|
|
2652
|
+
if (isInitialScroll) {
|
|
2653
|
+
initialScrollCompletion.resetFlags(state);
|
|
2548
2654
|
}
|
|
2655
|
+
const averageSizeSnapshot = getAverageSizeSnapshot(state);
|
|
2656
|
+
state.scrollingTo = {
|
|
2657
|
+
...scrollTarget,
|
|
2658
|
+
...averageSizeSnapshot ? { averageSizeSnapshot } : {},
|
|
2659
|
+
targetOffset,
|
|
2660
|
+
waitForInitialScrollCompletionFrame
|
|
2661
|
+
};
|
|
2662
|
+
}
|
|
2663
|
+
state.scrollPending = targetOffset;
|
|
2664
|
+
syncInitialScrollNativeWatchdog(state, { isInitialScroll, requestedOffset: offset, targetOffset });
|
|
2665
|
+
if (!animated && !isInitialScroll && !noScrollingTo && Math.abs(state.scroll - targetOffset) > 1) {
|
|
2666
|
+
updateScroll(ctx, targetOffset, false, { markHasScrolled: false });
|
|
2667
|
+
}
|
|
2668
|
+
if (forceScroll || !isInitialScroll || Platform.OS === "android") {
|
|
2669
|
+
doScrollTo(ctx, { animated, horizontal, isInitialScroll, offset });
|
|
2549
2670
|
} else {
|
|
2550
|
-
|
|
2551
|
-
bootstrapInitialScroll.previousResolvedOffset = void 0;
|
|
2552
|
-
bootstrapInitialScroll.scroll = (_a3 = options == null ? void 0 : options.scroll) != null ? _a3 : bootstrapInitialScroll.scroll;
|
|
2553
|
-
bootstrapInitialScroll.seedContentOffset = (_b = options == null ? void 0 : options.seedContentOffset) != null ? _b : bootstrapInitialScroll.seedContentOffset;
|
|
2554
|
-
bootstrapInitialScroll.targetIndexSeed = (_c = options == null ? void 0 : options.targetIndexSeed) != null ? _c : bootstrapInitialScroll.targetIndexSeed;
|
|
2555
|
-
bootstrapInitialScroll.visibleIndices = void 0;
|
|
2556
|
-
setInitialScrollSession(state, {
|
|
2557
|
-
bootstrap: bootstrapInitialScroll,
|
|
2558
|
-
kind: "bootstrap"
|
|
2559
|
-
});
|
|
2671
|
+
state.scroll = offset;
|
|
2560
2672
|
}
|
|
2561
2673
|
}
|
|
2562
|
-
|
|
2563
|
-
|
|
2564
|
-
|
|
2565
|
-
|
|
2566
|
-
|
|
2567
|
-
|
|
2568
|
-
|
|
2674
|
+
|
|
2675
|
+
// src/core/scrollToIndex.ts
|
|
2676
|
+
function clampScrollIndex(index, dataLength) {
|
|
2677
|
+
if (dataLength <= 0) {
|
|
2678
|
+
return -1;
|
|
2679
|
+
}
|
|
2680
|
+
if (index >= dataLength) {
|
|
2681
|
+
return dataLength - 1;
|
|
2682
|
+
}
|
|
2683
|
+
if (index < 0) {
|
|
2684
|
+
return 0;
|
|
2685
|
+
}
|
|
2686
|
+
return index;
|
|
2569
2687
|
}
|
|
2570
|
-
function
|
|
2688
|
+
function scrollToIndex(ctx, {
|
|
2689
|
+
index,
|
|
2690
|
+
viewOffset = 0,
|
|
2691
|
+
animated = true,
|
|
2692
|
+
forceScroll,
|
|
2693
|
+
isInitialScroll,
|
|
2694
|
+
viewPosition
|
|
2695
|
+
}) {
|
|
2571
2696
|
const state = ctx.state;
|
|
2572
|
-
const
|
|
2573
|
-
|
|
2574
|
-
|
|
2697
|
+
const { data } = state.props;
|
|
2698
|
+
index = clampScrollIndex(index, data.length);
|
|
2699
|
+
const itemSize = getItemSizeAtIndex(ctx, index);
|
|
2700
|
+
const firstIndexOffset = calculateOffsetForIndex(ctx, index);
|
|
2701
|
+
const isLast = index === data.length - 1;
|
|
2702
|
+
if (isLast && viewPosition === void 0) {
|
|
2703
|
+
viewPosition = 1;
|
|
2575
2704
|
}
|
|
2576
|
-
|
|
2577
|
-
|
|
2578
|
-
|
|
2579
|
-
|
|
2580
|
-
|
|
2581
|
-
|
|
2582
|
-
|
|
2583
|
-
|
|
2584
|
-
|
|
2585
|
-
|
|
2586
|
-
|
|
2587
|
-
return;
|
|
2588
|
-
}
|
|
2589
|
-
ensureBootstrapInitialScrollFrameTicker(ctx);
|
|
2590
|
-
};
|
|
2591
|
-
bootstrapInitialScroll.frameHandle = requestAnimationFrame(tick);
|
|
2592
|
-
}
|
|
2593
|
-
function rearmBootstrapInitialScroll(ctx, options) {
|
|
2594
|
-
resetBootstrapInitialScrollSession(ctx.state, options);
|
|
2595
|
-
ensureBootstrapInitialScrollFrameTicker(ctx);
|
|
2596
|
-
queueBootstrapInitialScrollReevaluation(ctx.state);
|
|
2597
|
-
}
|
|
2598
|
-
function createInitialScrollAtEndTarget(options) {
|
|
2599
|
-
const { dataLength, footerSize, preserveForFooterLayout, stylePaddingBottom } = options;
|
|
2600
|
-
return {
|
|
2601
|
-
contentOffset: void 0,
|
|
2602
|
-
index: Math.max(0, dataLength - 1),
|
|
2603
|
-
preserveForBottomPadding: true,
|
|
2604
|
-
preserveForFooterLayout,
|
|
2605
|
-
viewOffset: -stylePaddingBottom - footerSize,
|
|
2606
|
-
viewPosition: 1
|
|
2607
|
-
};
|
|
2705
|
+
state.scrollForNextCalculateItemsInView = void 0;
|
|
2706
|
+
scrollTo(ctx, {
|
|
2707
|
+
animated,
|
|
2708
|
+
forceScroll,
|
|
2709
|
+
index,
|
|
2710
|
+
isInitialScroll,
|
|
2711
|
+
itemSize,
|
|
2712
|
+
offset: firstIndexOffset,
|
|
2713
|
+
viewOffset,
|
|
2714
|
+
viewPosition: viewPosition != null ? viewPosition : 0
|
|
2715
|
+
});
|
|
2608
2716
|
}
|
|
2609
|
-
|
|
2610
|
-
|
|
2717
|
+
|
|
2718
|
+
// src/core/initialScroll.ts
|
|
2719
|
+
function dispatchInitialScroll(ctx, params) {
|
|
2720
|
+
const { forceScroll, resolvedOffset, target, waitForCompletionFrame } = params;
|
|
2721
|
+
const requestedIndex = target.index;
|
|
2722
|
+
const index = requestedIndex !== void 0 ? clampScrollIndex(requestedIndex, ctx.state.props.data.length) : void 0;
|
|
2723
|
+
const itemSize = getItemSizeAtIndex(ctx, index);
|
|
2724
|
+
scrollTo(ctx, {
|
|
2725
|
+
animated: false,
|
|
2726
|
+
forceScroll,
|
|
2727
|
+
index: index !== void 0 && index >= 0 ? index : void 0,
|
|
2728
|
+
isInitialScroll: true,
|
|
2729
|
+
itemSize,
|
|
2730
|
+
offset: resolvedOffset,
|
|
2731
|
+
precomputedWithViewOffset: true,
|
|
2732
|
+
viewOffset: target.viewOffset,
|
|
2733
|
+
viewPosition: target.viewPosition,
|
|
2734
|
+
waitForInitialScrollCompletionFrame: waitForCompletionFrame
|
|
2735
|
+
});
|
|
2611
2736
|
}
|
|
2612
|
-
function
|
|
2613
|
-
|
|
2737
|
+
function setInitialScrollTarget(state, target, options) {
|
|
2738
|
+
var _a3;
|
|
2739
|
+
state.clearPreservedInitialScrollOnNextFinish = void 0;
|
|
2740
|
+
if (state.timeoutPreservedInitialScrollClear !== void 0) {
|
|
2741
|
+
clearTimeout(state.timeoutPreservedInitialScrollClear);
|
|
2742
|
+
state.timeoutPreservedInitialScrollClear = void 0;
|
|
2743
|
+
}
|
|
2744
|
+
state.initialScroll = target;
|
|
2745
|
+
if ((options == null ? void 0 : options.resetDidFinish) && state.didFinishInitialScroll) {
|
|
2746
|
+
state.didFinishInitialScroll = false;
|
|
2747
|
+
}
|
|
2748
|
+
setInitialScrollSession(state, {
|
|
2749
|
+
kind: ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) === "offset" ? "offset" : "bootstrap"
|
|
2750
|
+
});
|
|
2614
2751
|
}
|
|
2615
|
-
function
|
|
2616
|
-
|
|
2752
|
+
function resolveInitialScrollOffset(ctx, initialScroll) {
|
|
2753
|
+
var _a3, _b;
|
|
2754
|
+
const state = ctx.state;
|
|
2755
|
+
if (((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) === "offset") {
|
|
2756
|
+
return (_b = initialScroll.contentOffset) != null ? _b : 0;
|
|
2757
|
+
}
|
|
2758
|
+
const baseOffset = initialScroll.index !== void 0 ? calculateOffsetForIndex(ctx, initialScroll.index) : 0;
|
|
2759
|
+
const resolvedOffset = calculateOffsetWithOffsetPosition(ctx, baseOffset, initialScroll);
|
|
2760
|
+
return clampScrollOffset(ctx, resolvedOffset, initialScroll);
|
|
2617
2761
|
}
|
|
2618
|
-
function
|
|
2619
|
-
const {
|
|
2620
|
-
const
|
|
2762
|
+
function getAdvanceableInitialScrollState(state, options) {
|
|
2763
|
+
const { didFinishInitialScroll, queuedInitialLayout, scrollingTo } = state;
|
|
2764
|
+
const initialScroll = state.initialScroll;
|
|
2765
|
+
const isInitialScrollInProgress = !!(scrollingTo == null ? void 0 : scrollingTo.isInitialScroll);
|
|
2766
|
+
const shouldWaitForInitialLayout = !!(options == null ? void 0 : options.requiresMeasuredLayout) && !queuedInitialLayout && !isInitialScrollInProgress;
|
|
2767
|
+
if (!initialScroll || shouldWaitForInitialLayout || didFinishInitialScroll || scrollingTo && !isInitialScrollInProgress) {
|
|
2768
|
+
return void 0;
|
|
2769
|
+
}
|
|
2621
2770
|
return {
|
|
2622
|
-
|
|
2623
|
-
|
|
2624
|
-
|
|
2625
|
-
|
|
2626
|
-
preserveForFooterLayout,
|
|
2627
|
-
viewOffset: -stylePaddingBottom - (preserveForFooterLayout ? footerSize : 0),
|
|
2628
|
-
viewPosition: 1
|
|
2771
|
+
initialScroll,
|
|
2772
|
+
isInitialScrollInProgress,
|
|
2773
|
+
queuedInitialLayout,
|
|
2774
|
+
scrollingTo
|
|
2629
2775
|
};
|
|
2630
2776
|
}
|
|
2631
|
-
function
|
|
2632
|
-
|
|
2633
|
-
}
|
|
2634
|
-
function clearPendingInitialScrollFooterLayout(ctx, options) {
|
|
2635
|
-
const { dataLength, stylePaddingBottom, target } = options;
|
|
2777
|
+
function advanceMeasuredInitialScroll(ctx, options) {
|
|
2778
|
+
var _a3, _b, _c;
|
|
2636
2779
|
const state = ctx.state;
|
|
2637
|
-
|
|
2638
|
-
|
|
2780
|
+
const advanceableState = getAdvanceableInitialScrollState(state, {
|
|
2781
|
+
requiresMeasuredLayout: true
|
|
2782
|
+
});
|
|
2783
|
+
if (!advanceableState) {
|
|
2784
|
+
return false;
|
|
2639
2785
|
}
|
|
2640
|
-
const
|
|
2641
|
-
|
|
2642
|
-
|
|
2643
|
-
|
|
2644
|
-
|
|
2786
|
+
const { initialScroll, isInitialScrollInProgress, queuedInitialLayout } = advanceableState;
|
|
2787
|
+
const scrollingTo = isInitialScrollInProgress ? advanceableState.scrollingTo : void 0;
|
|
2788
|
+
const resolvedOffset = resolveInitialScrollOffset(ctx, initialScroll);
|
|
2789
|
+
const activeInitialTargetOffset = scrollingTo ? (_a3 = scrollingTo.targetOffset) != null ? _a3 : scrollingTo.offset : void 0;
|
|
2790
|
+
const didOffsetChange = initialScroll.contentOffset === void 0 || Math.abs(initialScroll.contentOffset - resolvedOffset) > 1;
|
|
2791
|
+
const didActiveInitialTargetChange = activeInitialTargetOffset !== void 0 && Math.abs(activeInitialTargetOffset - resolvedOffset) > 1;
|
|
2792
|
+
const isAlreadyAtDesiredInitialTarget = activeInitialTargetOffset !== void 0 && Math.abs(state.scroll - resolvedOffset) <= 1 && Math.abs(state.scrollPending - resolvedOffset) <= 1;
|
|
2793
|
+
if (!(options == null ? void 0 : options.forceScroll) && !didOffsetChange && isInitialScrollInProgress && !didActiveInitialTargetChange) {
|
|
2794
|
+
return false;
|
|
2795
|
+
}
|
|
2796
|
+
if ((options == null ? void 0 : options.forceScroll) && isAlreadyAtDesiredInitialTarget) {
|
|
2797
|
+
return false;
|
|
2798
|
+
}
|
|
2799
|
+
if (didOffsetChange && ((_b = state.initialScrollSession) == null ? void 0 : _b.kind) !== "offset") {
|
|
2800
|
+
setInitialScrollTarget(state, { ...initialScroll, contentOffset: resolvedOffset });
|
|
2801
|
+
}
|
|
2802
|
+
const forceScroll = (_c = options == null ? void 0 : options.forceScroll) != null ? _c : !!queuedInitialLayout || isInitialScrollInProgress && didOffsetChange;
|
|
2803
|
+
dispatchInitialScroll(ctx, {
|
|
2804
|
+
forceScroll,
|
|
2805
|
+
resolvedOffset,
|
|
2806
|
+
target: initialScroll
|
|
2645
2807
|
});
|
|
2646
|
-
|
|
2647
|
-
}
|
|
2648
|
-
function clearFinishedViewportRetargetableInitialScroll(state) {
|
|
2649
|
-
clearPreservedInitialScrollTarget(state);
|
|
2808
|
+
return true;
|
|
2650
2809
|
}
|
|
2651
|
-
function
|
|
2810
|
+
function advanceOffsetInitialScroll(ctx, options) {
|
|
2811
|
+
var _a3, _b;
|
|
2652
2812
|
const state = ctx.state;
|
|
2653
|
-
|
|
2813
|
+
const advanceableState = getAdvanceableInitialScrollState(state);
|
|
2814
|
+
if (!advanceableState) {
|
|
2654
2815
|
return false;
|
|
2655
2816
|
}
|
|
2656
|
-
const
|
|
2657
|
-
|
|
2658
|
-
|
|
2659
|
-
|
|
2660
|
-
|
|
2661
|
-
|
|
2662
|
-
|
|
2817
|
+
const { initialScroll, queuedInitialLayout } = advanceableState;
|
|
2818
|
+
const resolvedOffset = (_a3 = initialScroll.contentOffset) != null ? _a3 : 0;
|
|
2819
|
+
const isAlreadyAtDesiredInitialTarget = Math.abs(state.scroll - resolvedOffset) <= 1 && Math.abs(state.scrollPending - resolvedOffset) <= 1;
|
|
2820
|
+
if ((options == null ? void 0 : options.forceScroll) && isAlreadyAtDesiredInitialTarget) {
|
|
2821
|
+
return false;
|
|
2822
|
+
}
|
|
2823
|
+
const hasMeasuredScrollLayout = !!state.lastLayout && state.scrollLength > 0;
|
|
2824
|
+
const forceScroll = (_b = options == null ? void 0 : options.forceScroll) != null ? _b : hasMeasuredScrollLayout || !!queuedInitialLayout;
|
|
2825
|
+
dispatchInitialScroll(ctx, {
|
|
2826
|
+
forceScroll,
|
|
2827
|
+
resolvedOffset,
|
|
2828
|
+
target: initialScroll
|
|
2829
|
+
});
|
|
2830
|
+
return true;
|
|
2663
2831
|
}
|
|
2664
|
-
function
|
|
2832
|
+
function advanceCurrentInitialScrollSession(ctx, options) {
|
|
2665
2833
|
var _a3;
|
|
2666
|
-
|
|
2667
|
-
|
|
2668
|
-
|
|
2669
|
-
|
|
2834
|
+
return ((_a3 = ctx.state.initialScrollSession) == null ? void 0 : _a3.kind) === "offset" ? advanceOffsetInitialScroll(ctx, {
|
|
2835
|
+
forceScroll: options == null ? void 0 : options.forceScroll
|
|
2836
|
+
}) : advanceMeasuredInitialScroll(ctx, {
|
|
2837
|
+
forceScroll: options == null ? void 0 : options.forceScroll
|
|
2838
|
+
});
|
|
2839
|
+
}
|
|
2840
|
+
|
|
2841
|
+
// src/utils/checkAllSizesKnown.ts
|
|
2842
|
+
function isNullOrUndefined2(value) {
|
|
2843
|
+
return value === null || value === void 0;
|
|
2844
|
+
}
|
|
2845
|
+
function getMountedIndicesInRange(state, start, end) {
|
|
2846
|
+
if (!isNullOrUndefined2(end) && !isNullOrUndefined2(start) && start >= 0 && end >= 0) {
|
|
2847
|
+
return Array.from(state.containerItemKeys.keys()).map((key) => state.indexByKey.get(key)).filter((index) => index !== void 0 && index >= start && index <= end).sort((a, b) => a - b);
|
|
2670
2848
|
}
|
|
2671
|
-
|
|
2672
|
-
return resolveInitialScrollOffset(ctx, initialScroll) - currentOffset;
|
|
2849
|
+
return [];
|
|
2673
2850
|
}
|
|
2674
|
-
function
|
|
2675
|
-
|
|
2851
|
+
function getMountedBufferedIndices(state) {
|
|
2852
|
+
return getMountedIndicesInRange(state, state.startBuffered, state.endBuffered);
|
|
2853
|
+
}
|
|
2854
|
+
function getMountedNoBufferIndices(state) {
|
|
2855
|
+
return getMountedIndicesInRange(state, state.startNoBuffer, state.endNoBuffer);
|
|
2856
|
+
}
|
|
2857
|
+
function checkAllSizesKnown(state, indices) {
|
|
2858
|
+
return indices.length > 0 && indices.every((index) => {
|
|
2859
|
+
const key = getId(state, index);
|
|
2860
|
+
return key !== void 0 && state.sizesKnown.has(key);
|
|
2861
|
+
});
|
|
2862
|
+
}
|
|
2863
|
+
|
|
2864
|
+
// src/core/bootstrapInitialScroll.ts
|
|
2865
|
+
var DEFAULT_BOOTSTRAP_REVEAL_EPSILON = 1;
|
|
2866
|
+
var DEFAULT_BOOTSTRAP_REVEAL_MAX_FRAMES = 8;
|
|
2867
|
+
var DEFAULT_BOOTSTRAP_REVEAL_MAX_PASSES = 24;
|
|
2868
|
+
var BOOTSTRAP_REVEAL_ABORT_WARNING = "LegendList bootstrap initial scroll aborted after exceeding convergence bounds.";
|
|
2869
|
+
function getBootstrapInitialScrollSession(state) {
|
|
2870
|
+
var _a3;
|
|
2871
|
+
return ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) === "bootstrap" ? state.initialScrollSession.bootstrap : void 0;
|
|
2872
|
+
}
|
|
2873
|
+
function isOffsetInitialScrollSession(state) {
|
|
2874
|
+
var _a3;
|
|
2875
|
+
return ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) === "offset";
|
|
2876
|
+
}
|
|
2877
|
+
function doVisibleIndicesMatch(previous, next) {
|
|
2878
|
+
if (!previous || previous.length !== next.length) {
|
|
2676
2879
|
return false;
|
|
2677
2880
|
}
|
|
2678
|
-
|
|
2679
|
-
|
|
2881
|
+
for (let i = 0; i < previous.length; i++) {
|
|
2882
|
+
if (previous[i] !== next[i]) {
|
|
2883
|
+
return false;
|
|
2884
|
+
}
|
|
2885
|
+
}
|
|
2680
2886
|
return true;
|
|
2681
2887
|
}
|
|
2682
|
-
function
|
|
2683
|
-
const
|
|
2684
|
-
|
|
2685
|
-
|
|
2686
|
-
|
|
2687
|
-
|
|
2688
|
-
|
|
2689
|
-
|
|
2888
|
+
function getBootstrapRevealVisibleIndices(options) {
|
|
2889
|
+
const { dataLength, getSize, offset, positions, scrollLength, startIndex: requestedStartIndex } = options;
|
|
2890
|
+
const endOffset = offset + scrollLength;
|
|
2891
|
+
const visibleIndices = [];
|
|
2892
|
+
let index = requestedStartIndex !== void 0 ? Math.max(0, Math.min(dataLength - 1, requestedStartIndex)) : 0;
|
|
2893
|
+
while (index > 0) {
|
|
2894
|
+
const previousIndex = index - 1;
|
|
2895
|
+
const previousPosition = positions[previousIndex];
|
|
2896
|
+
if (previousPosition === void 0) {
|
|
2897
|
+
index = previousIndex;
|
|
2898
|
+
continue;
|
|
2690
2899
|
}
|
|
2691
|
-
const
|
|
2692
|
-
if (
|
|
2693
|
-
|
|
2694
|
-
|
|
2900
|
+
const previousSize = getSize(previousIndex);
|
|
2901
|
+
if (previousSize === void 0) {
|
|
2902
|
+
index = previousIndex;
|
|
2903
|
+
continue;
|
|
2695
2904
|
}
|
|
2696
|
-
|
|
2697
|
-
|
|
2698
|
-
activeCorrection.lastRequestTime = Date.now();
|
|
2699
|
-
requestAdjust(ctx, offsetDiff);
|
|
2905
|
+
if (previousPosition + previousSize <= offset) {
|
|
2906
|
+
break;
|
|
2700
2907
|
}
|
|
2701
|
-
|
|
2702
|
-
});
|
|
2703
|
-
}
|
|
2704
|
-
function clearFinishedBootstrapInitialScrollTargetIfMovedAway(ctx) {
|
|
2705
|
-
var _a3, _b;
|
|
2706
|
-
const state = ctx.state;
|
|
2707
|
-
const initialScroll = state.initialScroll;
|
|
2708
|
-
if (!state.didFinishInitialScroll || ((_a3 = state.scrollingTo) == null ? void 0 : _a3.isInitialScroll) || (initialScroll == null ? void 0 : initialScroll.viewPosition) !== 1 || state.preservedEndAnchorCorrection) {
|
|
2709
|
-
return;
|
|
2908
|
+
index = previousIndex;
|
|
2710
2909
|
}
|
|
2711
|
-
|
|
2712
|
-
const
|
|
2713
|
-
if (
|
|
2714
|
-
|
|
2715
|
-
|
|
2716
|
-
|
|
2717
|
-
|
|
2718
|
-
|
|
2719
|
-
|
|
2720
|
-
|
|
2721
|
-
|
|
2722
|
-
|
|
2910
|
+
for (; index < dataLength; index++) {
|
|
2911
|
+
const position = positions[index];
|
|
2912
|
+
if (position === void 0) {
|
|
2913
|
+
continue;
|
|
2914
|
+
}
|
|
2915
|
+
const size = getSize(index);
|
|
2916
|
+
if (size === void 0) {
|
|
2917
|
+
continue;
|
|
2918
|
+
}
|
|
2919
|
+
if (position < endOffset && position + size > offset) {
|
|
2920
|
+
visibleIndices.push(index);
|
|
2921
|
+
} else if (visibleIndices.length > 0 && position >= endOffset) {
|
|
2922
|
+
break;
|
|
2723
2923
|
}
|
|
2724
2924
|
}
|
|
2925
|
+
return visibleIndices;
|
|
2725
2926
|
}
|
|
2726
|
-
function
|
|
2727
|
-
|
|
2728
|
-
|
|
2729
|
-
|
|
2730
|
-
|
|
2731
|
-
|
|
2732
|
-
|
|
2733
|
-
|
|
2734
|
-
clearBootstrapInitialScrollSession(state);
|
|
2735
|
-
finishInitialScroll(ctx, {
|
|
2736
|
-
resolvedOffset: offset
|
|
2737
|
-
});
|
|
2738
|
-
} else if (shouldFinishWithPreservedTarget) {
|
|
2739
|
-
clearBootstrapInitialScrollSession(state);
|
|
2740
|
-
finishInitialScroll(ctx, {
|
|
2741
|
-
preserveTarget: true,
|
|
2742
|
-
resolvedOffset: offset
|
|
2743
|
-
});
|
|
2744
|
-
} else {
|
|
2745
|
-
startBootstrapInitialScrollSession(state, {
|
|
2746
|
-
scroll: offset,
|
|
2747
|
-
seedContentOffset: Platform.OS === "web" ? 0 : offset,
|
|
2748
|
-
targetIndexSeed: target.index
|
|
2749
|
-
});
|
|
2750
|
-
ensureBootstrapInitialScrollFrameTicker(ctx);
|
|
2751
|
-
}
|
|
2927
|
+
function shouldAbortBootstrapReveal(options) {
|
|
2928
|
+
const {
|
|
2929
|
+
mountFrameCount,
|
|
2930
|
+
maxFrames = DEFAULT_BOOTSTRAP_REVEAL_MAX_FRAMES,
|
|
2931
|
+
maxPasses = DEFAULT_BOOTSTRAP_REVEAL_MAX_PASSES,
|
|
2932
|
+
passCount
|
|
2933
|
+
} = options;
|
|
2934
|
+
return mountFrameCount >= maxFrames || passCount >= maxPasses;
|
|
2752
2935
|
}
|
|
2753
|
-
function
|
|
2754
|
-
|
|
2755
|
-
|
|
2756
|
-
const initialScroll = state.initialScroll;
|
|
2757
|
-
if (isOffsetInitialScrollSession(state) || !initialScroll) {
|
|
2758
|
-
return;
|
|
2936
|
+
function abortBootstrapRevealIfNeeded(ctx, options) {
|
|
2937
|
+
if (!shouldAbortBootstrapReveal(options)) {
|
|
2938
|
+
return false;
|
|
2759
2939
|
}
|
|
2760
|
-
|
|
2761
|
-
|
|
2762
|
-
const shouldClearFinishedResizePreservation = !initialScrollAtEnd && didDataChange && dataLength > 0 && state.didFinishInitialScroll && !bootstrapInitialScroll && !shouldResetDidFinish;
|
|
2763
|
-
if (shouldClearFinishedResizePreservation) {
|
|
2764
|
-
clearPreservedInitialScrollTarget(state);
|
|
2765
|
-
return;
|
|
2940
|
+
if (IS_DEV) {
|
|
2941
|
+
console.warn(BOOTSTRAP_REVEAL_ABORT_WARNING);
|
|
2766
2942
|
}
|
|
2767
|
-
|
|
2768
|
-
|
|
2769
|
-
|
|
2943
|
+
abortBootstrapInitialScroll(ctx);
|
|
2944
|
+
return true;
|
|
2945
|
+
}
|
|
2946
|
+
function clearBootstrapInitialScrollSession(state) {
|
|
2947
|
+
var _a3;
|
|
2948
|
+
const bootstrapInitialScroll = getBootstrapInitialScrollSession(state);
|
|
2949
|
+
const frameHandle = bootstrapInitialScroll == null ? void 0 : bootstrapInitialScroll.frameHandle;
|
|
2950
|
+
if (frameHandle !== void 0 && typeof cancelAnimationFrame === "function") {
|
|
2951
|
+
cancelAnimationFrame(frameHandle);
|
|
2770
2952
|
}
|
|
2771
|
-
if (
|
|
2772
|
-
|
|
2773
|
-
|
|
2774
|
-
|
|
2775
|
-
|
|
2776
|
-
|
|
2777
|
-
|
|
2778
|
-
|
|
2779
|
-
|
|
2780
|
-
|
|
2781
|
-
|
|
2782
|
-
|
|
2783
|
-
|
|
2784
|
-
|
|
2785
|
-
|
|
2786
|
-
|
|
2787
|
-
|
|
2788
|
-
|
|
2953
|
+
if (bootstrapInitialScroll) {
|
|
2954
|
+
bootstrapInitialScroll.frameHandle = void 0;
|
|
2955
|
+
}
|
|
2956
|
+
setInitialScrollSession(state, {
|
|
2957
|
+
bootstrap: null,
|
|
2958
|
+
kind: (_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind
|
|
2959
|
+
});
|
|
2960
|
+
}
|
|
2961
|
+
function startBootstrapInitialScrollSession(state, options) {
|
|
2962
|
+
var _a3, _b, _c;
|
|
2963
|
+
const previousBootstrapInitialScroll = getBootstrapInitialScrollSession(state);
|
|
2964
|
+
setInitialScrollSession(state, {
|
|
2965
|
+
bootstrap: {
|
|
2966
|
+
frameHandle: previousBootstrapInitialScroll == null ? void 0 : previousBootstrapInitialScroll.frameHandle,
|
|
2967
|
+
// Re-arming during the initial mount should spend from the same watchdog budget.
|
|
2968
|
+
mountFrameCount: (_a3 = previousBootstrapInitialScroll == null ? void 0 : previousBootstrapInitialScroll.mountFrameCount) != null ? _a3 : 0,
|
|
2969
|
+
passCount: 0,
|
|
2970
|
+
previousResolvedOffset: void 0,
|
|
2971
|
+
scroll: options.scroll,
|
|
2972
|
+
seedContentOffset: (_c = (_b = options.seedContentOffset) != null ? _b : previousBootstrapInitialScroll == null ? void 0 : previousBootstrapInitialScroll.seedContentOffset) != null ? _c : options.scroll,
|
|
2973
|
+
targetIndexSeed: options.targetIndexSeed,
|
|
2974
|
+
visibleIndices: void 0
|
|
2975
|
+
},
|
|
2976
|
+
kind: "bootstrap"
|
|
2977
|
+
});
|
|
2978
|
+
}
|
|
2979
|
+
function resetBootstrapInitialScrollSession(state, options) {
|
|
2980
|
+
var _a3, _b, _c;
|
|
2981
|
+
const bootstrapInitialScroll = getBootstrapInitialScrollSession(state);
|
|
2982
|
+
if (!bootstrapInitialScroll) {
|
|
2983
|
+
if ((options == null ? void 0 : options.scroll) !== void 0) {
|
|
2984
|
+
startBootstrapInitialScrollSession(state, {
|
|
2985
|
+
scroll: options.scroll,
|
|
2986
|
+
seedContentOffset: options.seedContentOffset,
|
|
2987
|
+
targetIndexSeed: options.targetIndexSeed
|
|
2789
2988
|
});
|
|
2989
|
+
}
|
|
2990
|
+
} else {
|
|
2991
|
+
bootstrapInitialScroll.passCount = 0;
|
|
2992
|
+
bootstrapInitialScroll.previousResolvedOffset = void 0;
|
|
2993
|
+
bootstrapInitialScroll.scroll = (_a3 = options == null ? void 0 : options.scroll) != null ? _a3 : bootstrapInitialScroll.scroll;
|
|
2994
|
+
bootstrapInitialScroll.seedContentOffset = (_b = options == null ? void 0 : options.seedContentOffset) != null ? _b : bootstrapInitialScroll.seedContentOffset;
|
|
2995
|
+
bootstrapInitialScroll.targetIndexSeed = (_c = options == null ? void 0 : options.targetIndexSeed) != null ? _c : bootstrapInitialScroll.targetIndexSeed;
|
|
2996
|
+
bootstrapInitialScroll.visibleIndices = void 0;
|
|
2997
|
+
setInitialScrollSession(state, {
|
|
2998
|
+
bootstrap: bootstrapInitialScroll,
|
|
2999
|
+
kind: "bootstrap"
|
|
3000
|
+
});
|
|
3001
|
+
}
|
|
3002
|
+
}
|
|
3003
|
+
function queueBootstrapInitialScrollReevaluation(state) {
|
|
3004
|
+
requestAnimationFrame(() => {
|
|
3005
|
+
var _a3;
|
|
3006
|
+
if (getBootstrapInitialScrollSession(state)) {
|
|
3007
|
+
(_a3 = state.triggerCalculateItemsInView) == null ? void 0 : _a3.call(state, { forceFullItemPositions: true });
|
|
3008
|
+
}
|
|
3009
|
+
});
|
|
3010
|
+
}
|
|
3011
|
+
function ensureBootstrapInitialScrollFrameTicker(ctx) {
|
|
3012
|
+
const state = ctx.state;
|
|
3013
|
+
const bootstrapInitialScroll = getBootstrapInitialScrollSession(state);
|
|
3014
|
+
if (!bootstrapInitialScroll || bootstrapInitialScroll.frameHandle !== void 0) {
|
|
3015
|
+
return;
|
|
3016
|
+
}
|
|
3017
|
+
const tick = () => {
|
|
3018
|
+
const activeBootstrapInitialScroll = getBootstrapInitialScrollSession(state);
|
|
3019
|
+
if (!activeBootstrapInitialScroll) {
|
|
2790
3020
|
return;
|
|
2791
3021
|
}
|
|
2792
|
-
|
|
2793
|
-
|
|
2794
|
-
|
|
2795
|
-
|
|
2796
|
-
|
|
2797
|
-
|
|
2798
|
-
seedContentOffset: shouldResetDidFinish && !bootstrapInitialScroll ? getObservedBootstrapInitialScrollOffset(state) : void 0,
|
|
2799
|
-
targetIndexSeed: updatedInitialScroll.index
|
|
2800
|
-
});
|
|
3022
|
+
activeBootstrapInitialScroll.frameHandle = void 0;
|
|
3023
|
+
activeBootstrapInitialScroll.mountFrameCount += 1;
|
|
3024
|
+
if (abortBootstrapRevealIfNeeded(ctx, {
|
|
3025
|
+
mountFrameCount: activeBootstrapInitialScroll.mountFrameCount,
|
|
3026
|
+
passCount: activeBootstrapInitialScroll.passCount
|
|
3027
|
+
})) {
|
|
2801
3028
|
return;
|
|
2802
3029
|
}
|
|
2803
|
-
|
|
2804
|
-
|
|
3030
|
+
ensureBootstrapInitialScrollFrameTicker(ctx);
|
|
3031
|
+
};
|
|
3032
|
+
bootstrapInitialScroll.frameHandle = requestAnimationFrame(tick);
|
|
3033
|
+
}
|
|
3034
|
+
function rearmBootstrapInitialScroll(ctx, options) {
|
|
3035
|
+
resetBootstrapInitialScrollSession(ctx.state, options);
|
|
3036
|
+
ensureBootstrapInitialScrollFrameTicker(ctx);
|
|
3037
|
+
queueBootstrapInitialScrollReevaluation(ctx.state);
|
|
3038
|
+
}
|
|
3039
|
+
function createInitialScrollAtEndTarget(options) {
|
|
3040
|
+
const { dataLength, footerSize, preserveForFooterLayout, stylePaddingBottom } = options;
|
|
3041
|
+
return {
|
|
3042
|
+
contentOffset: void 0,
|
|
3043
|
+
index: Math.max(0, dataLength - 1),
|
|
3044
|
+
preserveForBottomPadding: true,
|
|
3045
|
+
preserveForFooterLayout,
|
|
3046
|
+
viewOffset: -stylePaddingBottom - footerSize,
|
|
3047
|
+
viewPosition: 1
|
|
3048
|
+
};
|
|
3049
|
+
}
|
|
3050
|
+
function shouldPreserveInitialScrollForBottomPadding(target) {
|
|
3051
|
+
return !!(target == null ? void 0 : target.preserveForBottomPadding);
|
|
3052
|
+
}
|
|
3053
|
+
function shouldPreserveInitialScrollForFooterLayout(target) {
|
|
3054
|
+
return !!(target == null ? void 0 : target.preserveForFooterLayout);
|
|
3055
|
+
}
|
|
3056
|
+
function isRetargetableBottomAlignedInitialScrollTarget(target) {
|
|
3057
|
+
return !!(target && target.viewPosition === 1 && (shouldPreserveInitialScrollForBottomPadding(target) || shouldPreserveInitialScrollForFooterLayout(target)));
|
|
3058
|
+
}
|
|
3059
|
+
function createRetargetedBottomAlignedInitialScroll(options) {
|
|
3060
|
+
const { dataLength, footerSize, initialScrollAtEnd, stylePaddingBottom, target } = options;
|
|
3061
|
+
const preserveForFooterLayout = shouldPreserveInitialScrollForFooterLayout(target);
|
|
3062
|
+
return {
|
|
3063
|
+
...target,
|
|
3064
|
+
contentOffset: void 0,
|
|
3065
|
+
index: initialScrollAtEnd ? Math.max(0, dataLength - 1) : target.index,
|
|
3066
|
+
preserveForBottomPadding: true,
|
|
3067
|
+
preserveForFooterLayout,
|
|
3068
|
+
viewOffset: -stylePaddingBottom - (preserveForFooterLayout ? footerSize : 0),
|
|
3069
|
+
viewPosition: 1
|
|
3070
|
+
};
|
|
3071
|
+
}
|
|
3072
|
+
function areEquivalentBootstrapInitialScrollTargets(current, next) {
|
|
3073
|
+
return current.index === next.index && current.preserveForBottomPadding === next.preserveForBottomPadding && current.preserveForFooterLayout === next.preserveForFooterLayout && current.viewOffset === next.viewOffset && current.viewPosition === next.viewPosition;
|
|
3074
|
+
}
|
|
3075
|
+
function clearPendingInitialScrollFooterLayout(ctx, options) {
|
|
3076
|
+
const { dataLength, stylePaddingBottom, target } = options;
|
|
3077
|
+
const state = ctx.state;
|
|
3078
|
+
if (!shouldPreserveInitialScrollForFooterLayout(target)) {
|
|
2805
3079
|
return;
|
|
2806
3080
|
}
|
|
2807
|
-
|
|
2808
|
-
|
|
2809
|
-
|
|
2810
|
-
|
|
2811
|
-
|
|
2812
|
-
|
|
2813
|
-
|
|
2814
|
-
targetIndexSeed: initialScroll.index
|
|
2815
|
-
});
|
|
2816
|
-
}
|
|
3081
|
+
const clearedFooterTarget = createInitialScrollAtEndTarget({
|
|
3082
|
+
dataLength,
|
|
3083
|
+
footerSize: 0,
|
|
3084
|
+
preserveForFooterLayout: void 0,
|
|
3085
|
+
stylePaddingBottom
|
|
3086
|
+
});
|
|
3087
|
+
setInitialScrollTarget(state, clearedFooterTarget);
|
|
2817
3088
|
}
|
|
2818
|
-
function
|
|
2819
|
-
|
|
3089
|
+
function clearFinishedViewportRetargetableInitialScroll(state) {
|
|
3090
|
+
clearPreservedInitialScrollTarget(state);
|
|
3091
|
+
}
|
|
3092
|
+
function didFinishedInitialScrollMoveAwayFromTarget(ctx, target, epsilon = DEFAULT_BOOTSTRAP_REVEAL_EPSILON) {
|
|
2820
3093
|
const state = ctx.state;
|
|
2821
|
-
if (!
|
|
2822
|
-
return;
|
|
3094
|
+
if (!state.didFinishInitialScroll) {
|
|
3095
|
+
return false;
|
|
2823
3096
|
}
|
|
3097
|
+
const currentOffset = getObservedBootstrapInitialScrollOffset(state);
|
|
3098
|
+
return Math.abs(currentOffset - resolveInitialScrollOffset(ctx, target)) > epsilon;
|
|
3099
|
+
}
|
|
3100
|
+
function getObservedBootstrapInitialScrollOffset(state) {
|
|
3101
|
+
var _a3, _b, _c, _d;
|
|
3102
|
+
const observedOffset = (_b = (_a3 = state.refScroller.current) == null ? void 0 : _a3.getCurrentScrollOffset) == null ? void 0 : _b.call(_a3);
|
|
3103
|
+
return typeof observedOffset === "number" && Number.isFinite(observedOffset) ? observedOffset : (_d = (_c = state.scrollPending) != null ? _c : state.scroll) != null ? _d : 0;
|
|
3104
|
+
}
|
|
3105
|
+
function getPreservedEndAnchorOffsetDiff(ctx) {
|
|
3106
|
+
var _a3;
|
|
3107
|
+
const state = ctx.state;
|
|
2824
3108
|
const initialScroll = state.initialScroll;
|
|
2825
|
-
if (
|
|
2826
|
-
return;
|
|
2827
|
-
}
|
|
2828
|
-
const shouldProcessFooterLayout = !!getBootstrapInitialScrollSession(state) || shouldPreserveInitialScrollForFooterLayout(initialScroll);
|
|
2829
|
-
if (!shouldProcessFooterLayout) {
|
|
3109
|
+
if (!state.didFinishInitialScroll || ((_a3 = state.scrollingTo) == null ? void 0 : _a3.isInitialScroll) || !initialScroll || initialScroll.viewPosition !== 1 || state.props.data.length === 0 || isOffsetInitialScrollSession(state)) {
|
|
2830
3110
|
return;
|
|
2831
3111
|
}
|
|
2832
|
-
|
|
2833
|
-
|
|
2834
|
-
|
|
2835
|
-
|
|
2836
|
-
|
|
2837
|
-
|
|
2838
|
-
} else {
|
|
2839
|
-
const updatedInitialScroll = createInitialScrollAtEndTarget({
|
|
2840
|
-
dataLength,
|
|
2841
|
-
footerSize,
|
|
2842
|
-
preserveForFooterLayout: shouldPreserveInitialScrollForFooterLayout(initialScroll),
|
|
2843
|
-
stylePaddingBottom
|
|
2844
|
-
});
|
|
2845
|
-
const didTargetChange = initialScroll.index !== updatedInitialScroll.index || initialScroll.viewPosition !== updatedInitialScroll.viewPosition || initialScroll.viewOffset !== updatedInitialScroll.viewOffset;
|
|
2846
|
-
if (!didTargetChange) {
|
|
2847
|
-
clearPendingInitialScrollFooterLayout(ctx, {
|
|
2848
|
-
dataLength,
|
|
2849
|
-
stylePaddingBottom,
|
|
2850
|
-
target: initialScroll
|
|
2851
|
-
});
|
|
2852
|
-
} else {
|
|
2853
|
-
const didFinishInitialScroll = !!state.didFinishInitialScroll;
|
|
2854
|
-
setInitialScrollTarget(state, updatedInitialScroll, {
|
|
2855
|
-
resetDidFinish: didFinishInitialScroll
|
|
2856
|
-
});
|
|
2857
|
-
rearmBootstrapInitialScroll(ctx, {
|
|
2858
|
-
scroll: resolveInitialScrollOffset(ctx, updatedInitialScroll),
|
|
2859
|
-
targetIndexSeed: updatedInitialScroll.index
|
|
2860
|
-
});
|
|
2861
|
-
}
|
|
3112
|
+
const currentOffset = typeof state.lastNativeScroll === "number" && Number.isFinite(state.lastNativeScroll) ? state.lastNativeScroll : getObservedBootstrapInitialScrollOffset(state);
|
|
3113
|
+
return resolveInitialScrollOffset(ctx, initialScroll) - currentOffset;
|
|
3114
|
+
}
|
|
3115
|
+
function schedulePreservedEndAnchorCorrection(ctx) {
|
|
3116
|
+
if (getPreservedEndAnchorOffsetDiff(ctx) === void 0) {
|
|
3117
|
+
return false;
|
|
2862
3118
|
}
|
|
3119
|
+
const correction = {};
|
|
3120
|
+
schedulePreservedEndAnchorCorrectionFrame(ctx, correction);
|
|
3121
|
+
return true;
|
|
2863
3122
|
}
|
|
2864
|
-
function
|
|
2865
|
-
var _a3, _b, _c;
|
|
3123
|
+
function schedulePreservedEndAnchorCorrectionFrame(ctx, correction) {
|
|
2866
3124
|
const state = ctx.state;
|
|
2867
|
-
|
|
2868
|
-
|
|
2869
|
-
|
|
3125
|
+
state.preservedEndAnchorCorrection = correction;
|
|
3126
|
+
requestAnimationFrame(() => {
|
|
3127
|
+
var _a3;
|
|
3128
|
+
const activeCorrection = state.preservedEndAnchorCorrection;
|
|
3129
|
+
if (activeCorrection !== correction) {
|
|
3130
|
+
return;
|
|
3131
|
+
}
|
|
3132
|
+
const offsetDiff = getPreservedEndAnchorOffsetDiff(ctx);
|
|
3133
|
+
if (offsetDiff === void 0 || Math.abs(offsetDiff) <= DEFAULT_BOOTSTRAP_REVEAL_EPSILON) {
|
|
3134
|
+
state.preservedEndAnchorCorrection = void 0;
|
|
3135
|
+
return;
|
|
3136
|
+
}
|
|
3137
|
+
const hasObservedNativeScrollAfterRequest = !activeCorrection.lastRequestTime || ((_a3 = state.lastNativeScrollTime) != null ? _a3 : 0) > activeCorrection.lastRequestTime;
|
|
3138
|
+
if (hasObservedNativeScrollAfterRequest) {
|
|
3139
|
+
activeCorrection.lastRequestTime = Date.now();
|
|
3140
|
+
requestAdjust(ctx, offsetDiff);
|
|
3141
|
+
}
|
|
3142
|
+
schedulePreservedEndAnchorCorrectionFrame(ctx, correction);
|
|
3143
|
+
});
|
|
3144
|
+
}
|
|
3145
|
+
function clearFinishedBootstrapInitialScrollTargetIfMovedAway(ctx) {
|
|
3146
|
+
var _a3, _b;
|
|
3147
|
+
const state = ctx.state;
|
|
3148
|
+
const initialScroll = state.initialScroll;
|
|
3149
|
+
if (!state.didFinishInitialScroll || ((_a3 = state.scrollingTo) == null ? void 0 : _a3.isInitialScroll) || (initialScroll == null ? void 0 : initialScroll.viewPosition) !== 1 || state.preservedEndAnchorCorrection) {
|
|
3150
|
+
return;
|
|
3151
|
+
}
|
|
3152
|
+
if (didFinishedInitialScrollMoveAwayFromTarget(ctx, initialScroll)) {
|
|
3153
|
+
const shouldKeepEndTargetAlive = isRetargetableBottomAlignedInitialScrollTarget(initialScroll) && peek$(ctx, "isAtEnd");
|
|
3154
|
+
if (!shouldKeepEndTargetAlive) {
|
|
3155
|
+
if (shouldPreserveInitialScrollForFooterLayout(initialScroll)) {
|
|
3156
|
+
clearPendingInitialScrollFooterLayout(ctx, {
|
|
3157
|
+
dataLength: state.props.data.length,
|
|
3158
|
+
stylePaddingBottom: (_b = state.props.stylePaddingBottom) != null ? _b : 0,
|
|
3159
|
+
target: initialScroll
|
|
3160
|
+
});
|
|
3161
|
+
} else {
|
|
3162
|
+
clearFinishedViewportRetargetableInitialScroll(state);
|
|
3163
|
+
}
|
|
3164
|
+
}
|
|
3165
|
+
}
|
|
3166
|
+
}
|
|
3167
|
+
function startBootstrapInitialScrollOnMount(ctx, options) {
|
|
3168
|
+
var _a3, _b, _c;
|
|
3169
|
+
const { initialScrollAtEnd, target } = options;
|
|
3170
|
+
const state = ctx.state;
|
|
3171
|
+
const offset = resolveInitialScrollOffset(ctx, target);
|
|
3172
|
+
const shouldFinishAtOrigin = offset === 0 && !initialScrollAtEnd && (isOffsetInitialScrollSession(state) ? Math.abs((_a3 = target.contentOffset) != null ? _a3 : 0) <= 1 : target.index === 0 && ((_b = target.viewPosition) != null ? _b : 0) === 0 && Math.abs((_c = target.viewOffset) != null ? _c : 0) <= 1);
|
|
3173
|
+
const shouldFinishWithPreservedTarget = state.props.data.length === 0 && target.index !== void 0;
|
|
3174
|
+
if (shouldFinishAtOrigin) {
|
|
3175
|
+
clearBootstrapInitialScrollSession(state);
|
|
3176
|
+
finishInitialScroll(ctx, {
|
|
3177
|
+
resolvedOffset: offset
|
|
3178
|
+
});
|
|
3179
|
+
} else if (shouldFinishWithPreservedTarget) {
|
|
3180
|
+
clearBootstrapInitialScrollSession(state);
|
|
3181
|
+
finishInitialScroll(ctx, {
|
|
3182
|
+
preserveTarget: true,
|
|
3183
|
+
resolvedOffset: offset
|
|
3184
|
+
});
|
|
3185
|
+
} else {
|
|
3186
|
+
startBootstrapInitialScrollSession(state, {
|
|
3187
|
+
scroll: offset,
|
|
3188
|
+
seedContentOffset: Platform.OS === "web" ? 0 : offset,
|
|
3189
|
+
targetIndexSeed: target.index
|
|
3190
|
+
});
|
|
3191
|
+
ensureBootstrapInitialScrollFrameTicker(ctx);
|
|
3192
|
+
}
|
|
3193
|
+
}
|
|
3194
|
+
function handleBootstrapInitialScrollDataChange(ctx, options) {
|
|
3195
|
+
const { dataLength, didDataChange, initialScrollAtEnd, previousDataLength, stylePaddingBottom } = options;
|
|
3196
|
+
const state = ctx.state;
|
|
3197
|
+
const initialScroll = state.initialScroll;
|
|
3198
|
+
if (isOffsetInitialScrollSession(state) || !initialScroll) {
|
|
3199
|
+
return;
|
|
3200
|
+
}
|
|
3201
|
+
const shouldResetDidFinish = !!(state.didFinishInitialScroll && previousDataLength === 0 && dataLength > 0 && initialScroll.index !== void 0);
|
|
3202
|
+
const bootstrapInitialScroll = getBootstrapInitialScrollSession(state);
|
|
3203
|
+
const shouldClearFinishedResizePreservation = !initialScrollAtEnd && didDataChange && dataLength > 0 && state.didFinishInitialScroll && !bootstrapInitialScroll && !shouldResetDidFinish;
|
|
3204
|
+
if (shouldClearFinishedResizePreservation) {
|
|
3205
|
+
clearPreservedInitialScrollTarget(state);
|
|
3206
|
+
return;
|
|
3207
|
+
}
|
|
3208
|
+
const shouldRetargetBottomAligned = dataLength > 0 && (initialScrollAtEnd || isRetargetableBottomAlignedInitialScrollTarget(initialScroll));
|
|
3209
|
+
if (!didDataChange && !shouldResetDidFinish && !shouldRetargetBottomAligned) {
|
|
3210
|
+
return;
|
|
3211
|
+
}
|
|
3212
|
+
if (shouldRetargetBottomAligned) {
|
|
3213
|
+
const updatedInitialScroll = initialScrollAtEnd ? createInitialScrollAtEndTarget({
|
|
3214
|
+
dataLength,
|
|
3215
|
+
footerSize: peek$(ctx, "footerSize") || 0,
|
|
3216
|
+
preserveForFooterLayout: shouldPreserveInitialScrollForFooterLayout(initialScroll),
|
|
3217
|
+
stylePaddingBottom
|
|
3218
|
+
}) : createRetargetedBottomAlignedInitialScroll({
|
|
3219
|
+
dataLength,
|
|
3220
|
+
footerSize: peek$(ctx, "footerSize") || 0,
|
|
3221
|
+
initialScrollAtEnd,
|
|
3222
|
+
stylePaddingBottom,
|
|
3223
|
+
target: initialScroll
|
|
3224
|
+
});
|
|
3225
|
+
if (!shouldResetDidFinish && didFinishedInitialScrollMoveAwayFromTarget(ctx, initialScroll)) {
|
|
3226
|
+
clearPendingInitialScrollFooterLayout(ctx, {
|
|
3227
|
+
dataLength,
|
|
3228
|
+
stylePaddingBottom,
|
|
3229
|
+
target: initialScroll
|
|
3230
|
+
});
|
|
3231
|
+
return;
|
|
3232
|
+
}
|
|
3233
|
+
if (!areEquivalentBootstrapInitialScrollTargets(initialScroll, updatedInitialScroll) || !!bootstrapInitialScroll || shouldResetDidFinish || didDataChange) {
|
|
3234
|
+
setInitialScrollTarget(state, updatedInitialScroll, {
|
|
3235
|
+
resetDidFinish: shouldResetDidFinish
|
|
3236
|
+
});
|
|
3237
|
+
rearmBootstrapInitialScroll(ctx, {
|
|
3238
|
+
scroll: resolveInitialScrollOffset(ctx, updatedInitialScroll),
|
|
3239
|
+
seedContentOffset: shouldResetDidFinish && !bootstrapInitialScroll ? getObservedBootstrapInitialScrollOffset(state) : void 0,
|
|
3240
|
+
targetIndexSeed: updatedInitialScroll.index
|
|
3241
|
+
});
|
|
3242
|
+
return;
|
|
3243
|
+
}
|
|
3244
|
+
}
|
|
3245
|
+
if (!didDataChange) {
|
|
3246
|
+
return;
|
|
3247
|
+
}
|
|
3248
|
+
if (bootstrapInitialScroll || shouldResetDidFinish) {
|
|
3249
|
+
setInitialScrollTarget(state, initialScroll, {
|
|
3250
|
+
resetDidFinish: shouldResetDidFinish
|
|
3251
|
+
});
|
|
3252
|
+
rearmBootstrapInitialScroll(ctx, {
|
|
3253
|
+
scroll: resolveInitialScrollOffset(ctx, initialScroll),
|
|
3254
|
+
seedContentOffset: shouldResetDidFinish && !bootstrapInitialScroll ? getObservedBootstrapInitialScrollOffset(state) : void 0,
|
|
3255
|
+
targetIndexSeed: initialScroll.index
|
|
3256
|
+
});
|
|
3257
|
+
}
|
|
3258
|
+
}
|
|
3259
|
+
function handleBootstrapInitialScrollFooterLayout(ctx, options) {
|
|
3260
|
+
const { dataLength, footerSize, initialScrollAtEnd, stylePaddingBottom } = options;
|
|
3261
|
+
const state = ctx.state;
|
|
3262
|
+
if (!initialScrollAtEnd) {
|
|
3263
|
+
return;
|
|
3264
|
+
}
|
|
3265
|
+
const initialScroll = state.initialScroll;
|
|
3266
|
+
if (isOffsetInitialScrollSession(state) || dataLength === 0 || !initialScroll) {
|
|
3267
|
+
return;
|
|
3268
|
+
}
|
|
3269
|
+
const shouldProcessFooterLayout = !!getBootstrapInitialScrollSession(state) || shouldPreserveInitialScrollForFooterLayout(initialScroll);
|
|
3270
|
+
if (!shouldProcessFooterLayout) {
|
|
3271
|
+
return;
|
|
3272
|
+
}
|
|
3273
|
+
if (didFinishedInitialScrollMoveAwayFromTarget(ctx, initialScroll)) {
|
|
3274
|
+
clearPendingInitialScrollFooterLayout(ctx, {
|
|
3275
|
+
dataLength,
|
|
3276
|
+
stylePaddingBottom,
|
|
3277
|
+
target: initialScroll
|
|
3278
|
+
});
|
|
3279
|
+
} else {
|
|
3280
|
+
const updatedInitialScroll = createInitialScrollAtEndTarget({
|
|
3281
|
+
dataLength,
|
|
3282
|
+
footerSize,
|
|
3283
|
+
preserveForFooterLayout: shouldPreserveInitialScrollForFooterLayout(initialScroll),
|
|
3284
|
+
stylePaddingBottom
|
|
3285
|
+
});
|
|
3286
|
+
const didTargetChange = initialScroll.index !== updatedInitialScroll.index || initialScroll.viewPosition !== updatedInitialScroll.viewPosition || initialScroll.viewOffset !== updatedInitialScroll.viewOffset;
|
|
3287
|
+
if (!didTargetChange) {
|
|
3288
|
+
clearPendingInitialScrollFooterLayout(ctx, {
|
|
3289
|
+
dataLength,
|
|
3290
|
+
stylePaddingBottom,
|
|
3291
|
+
target: initialScroll
|
|
3292
|
+
});
|
|
3293
|
+
} else {
|
|
3294
|
+
const didFinishInitialScroll = !!state.didFinishInitialScroll;
|
|
3295
|
+
setInitialScrollTarget(state, updatedInitialScroll, {
|
|
3296
|
+
resetDidFinish: didFinishInitialScroll
|
|
3297
|
+
});
|
|
3298
|
+
rearmBootstrapInitialScroll(ctx, {
|
|
3299
|
+
scroll: resolveInitialScrollOffset(ctx, updatedInitialScroll),
|
|
3300
|
+
targetIndexSeed: updatedInitialScroll.index
|
|
3301
|
+
});
|
|
3302
|
+
}
|
|
3303
|
+
}
|
|
3304
|
+
}
|
|
3305
|
+
function handleBootstrapInitialScrollLayoutChange(ctx) {
|
|
3306
|
+
var _a3, _b, _c;
|
|
3307
|
+
const state = ctx.state;
|
|
3308
|
+
const initialScroll = state.initialScroll;
|
|
3309
|
+
const bootstrapInitialScroll = getBootstrapInitialScrollSession(state);
|
|
3310
|
+
if (initialScroll && state.props.data.length > 0 && !isOffsetInitialScrollSession(state) && (bootstrapInitialScroll || initialScroll.viewPosition === 1)) {
|
|
2870
3311
|
const resolvedOffset = resolveInitialScrollOffset(ctx, initialScroll);
|
|
2871
3312
|
const scrollingTo = ((_a3 = state.scrollingTo) == null ? void 0 : _a3.isInitialScroll) ? state.scrollingTo : void 0;
|
|
2872
3313
|
if (!bootstrapInitialScroll && (scrollingTo || state.didFinishInitialScroll)) {
|
|
@@ -2987,403 +3428,111 @@ function abortBootstrapInitialScroll(ctx) {
|
|
|
2987
3428
|
const initialScroll = state.initialScroll;
|
|
2988
3429
|
if (bootstrapInitialScroll && initialScroll && !isOffsetInitialScrollSession(state) && state.refScroller.current) {
|
|
2989
3430
|
clearBootstrapInitialScrollSession(state);
|
|
2990
|
-
dispatchInitialScroll(ctx, {
|
|
2991
|
-
forceScroll: true,
|
|
2992
|
-
resolvedOffset: bootstrapInitialScroll.scroll,
|
|
2993
|
-
target: initialScroll,
|
|
2994
|
-
waitForCompletionFrame: Platform.OS === "web"
|
|
2995
|
-
});
|
|
2996
|
-
} else {
|
|
2997
|
-
finishBootstrapInitialScrollWithoutScroll(
|
|
2998
|
-
ctx,
|
|
2999
|
-
(_d = (_c = (_b = (_a3 = getBootstrapInitialScrollSession(state)) == null ? void 0 : _a3.scroll) != null ? _b : state.scrollPending) != null ? _c : state.scroll) != null ? _d : 0
|
|
3000
|
-
);
|
|
3001
|
-
}
|
|
3002
|
-
}
|
|
3003
|
-
|
|
3004
|
-
// src/core/initialScrollLifecycle.ts
|
|
3005
|
-
function retargetActiveInitialScrollAtEnd(ctx) {
|
|
3006
|
-
var _a3;
|
|
3007
|
-
const state = ctx.state;
|
|
3008
|
-
const initialScroll = state.initialScroll;
|
|
3009
|
-
if (state.didFinishInitialScroll) {
|
|
3010
|
-
return schedulePreservedEndAnchorCorrection(ctx);
|
|
3011
|
-
}
|
|
3012
|
-
if (!initialScroll || ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) === "offset" || initialScroll.viewPosition !== 1 || state.props.data.length === 0) {
|
|
3013
|
-
return false;
|
|
3014
|
-
}
|
|
3015
|
-
return advanceCurrentInitialScrollSession(ctx, { forceScroll: true });
|
|
3016
|
-
}
|
|
3017
|
-
function handleInitialScrollLayoutReady(ctx) {
|
|
3018
|
-
var _a3;
|
|
3019
|
-
if (!ctx.state.initialScroll) {
|
|
3020
|
-
return;
|
|
3021
|
-
}
|
|
3022
|
-
const runScroll = () => advanceCurrentInitialScrollSession(ctx, { forceScroll: true });
|
|
3023
|
-
runScroll();
|
|
3024
|
-
if (((_a3 = ctx.state.initialScrollSession) == null ? void 0 : _a3.kind) !== "offset") {
|
|
3025
|
-
requestAnimationFrame(runScroll);
|
|
3026
|
-
}
|
|
3027
|
-
checkFinishedScroll(ctx, { onlyIfAligned: true });
|
|
3028
|
-
}
|
|
3029
|
-
function initializeInitialScrollOnMount(ctx, options) {
|
|
3030
|
-
var _a3, _b;
|
|
3031
|
-
const {
|
|
3032
|
-
alwaysDispatchInitialScroll,
|
|
3033
|
-
dataLength,
|
|
3034
|
-
hasFooterComponent,
|
|
3035
|
-
initialContentOffset,
|
|
3036
|
-
initialScrollAtEnd,
|
|
3037
|
-
useBootstrapInitialScroll
|
|
3038
|
-
} = options;
|
|
3039
|
-
const state = ctx.state;
|
|
3040
|
-
const initialScroll = state.initialScroll;
|
|
3041
|
-
const resolvedInitialContentOffset = initialContentOffset != null ? initialContentOffset : 0;
|
|
3042
|
-
const preserveForFooterLayout = useBootstrapInitialScroll && initialScrollAtEnd && hasFooterComponent;
|
|
3043
|
-
if (initialScroll && (initialScroll.contentOffset === void 0 || !!initialScroll.preserveForFooterLayout !== preserveForFooterLayout && ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) !== "offset")) {
|
|
3044
|
-
setInitialScrollTarget(state, {
|
|
3045
|
-
...initialScroll,
|
|
3046
|
-
contentOffset: resolvedInitialContentOffset,
|
|
3047
|
-
preserveForFooterLayout
|
|
3048
|
-
});
|
|
3049
|
-
}
|
|
3050
|
-
if (useBootstrapInitialScroll && initialScroll && ((_b = state.initialScrollSession) == null ? void 0 : _b.kind) !== "offset") {
|
|
3051
|
-
startBootstrapInitialScrollOnMount(ctx, {
|
|
3052
|
-
initialScrollAtEnd,
|
|
3053
|
-
target: state.initialScroll
|
|
3054
|
-
});
|
|
3055
|
-
return;
|
|
3056
|
-
}
|
|
3057
|
-
const hasPendingDataDependentInitialScroll = !!initialScroll && dataLength === 0 && !(resolvedInitialContentOffset === 0 && !initialScrollAtEnd);
|
|
3058
|
-
if (!alwaysDispatchInitialScroll && !resolvedInitialContentOffset && !hasPendingDataDependentInitialScroll) {
|
|
3059
|
-
if (initialScroll && !initialScrollAtEnd) {
|
|
3060
|
-
finishInitialScroll(ctx, {
|
|
3061
|
-
resolvedOffset: resolvedInitialContentOffset
|
|
3062
|
-
});
|
|
3063
|
-
} else {
|
|
3064
|
-
setInitialRenderState(ctx, { didInitialScroll: true });
|
|
3065
|
-
}
|
|
3066
|
-
}
|
|
3067
|
-
}
|
|
3068
|
-
function handleInitialScrollDataChange(ctx, options) {
|
|
3069
|
-
var _a3, _b, _c;
|
|
3070
|
-
const { dataLength, didDataChange, initialScrollAtEnd, stylePaddingBottom, useBootstrapInitialScroll } = options;
|
|
3071
|
-
const state = ctx.state;
|
|
3072
|
-
const previousDataLength = (_b = (_a3 = state.initialScrollSession) == null ? void 0 : _a3.previousDataLength) != null ? _b : 0;
|
|
3073
|
-
if (state.initialScrollSession) {
|
|
3074
|
-
state.initialScrollSession.previousDataLength = dataLength;
|
|
3075
|
-
}
|
|
3076
|
-
setInitialScrollSession(state);
|
|
3077
|
-
if (useBootstrapInitialScroll) {
|
|
3078
|
-
handleBootstrapInitialScrollDataChange(ctx, {
|
|
3079
|
-
dataLength,
|
|
3080
|
-
didDataChange,
|
|
3081
|
-
initialScrollAtEnd,
|
|
3082
|
-
previousDataLength,
|
|
3083
|
-
stylePaddingBottom
|
|
3084
|
-
});
|
|
3085
|
-
return;
|
|
3086
|
-
}
|
|
3087
|
-
const shouldReplayFinishedOffsetInitialScroll = previousDataLength === 0 && dataLength > 0 && !!state.initialScroll && ((_c = ctx.state.initialScrollSession) == null ? void 0 : _c.kind) === "offset" && !!state.didFinishInitialScroll;
|
|
3088
|
-
if (previousDataLength !== 0 || dataLength === 0 || !state.initialScroll || !state.queuedInitialLayout || state.didFinishInitialScroll && !shouldReplayFinishedOffsetInitialScroll) {
|
|
3089
|
-
return;
|
|
3090
|
-
}
|
|
3091
|
-
if (shouldReplayFinishedOffsetInitialScroll) {
|
|
3092
|
-
state.didFinishInitialScroll = false;
|
|
3093
|
-
}
|
|
3094
|
-
advanceCurrentInitialScrollSession(ctx);
|
|
3095
|
-
}
|
|
3096
|
-
|
|
3097
|
-
// src/core/mvcp.ts
|
|
3098
|
-
var MVCP_POSITION_EPSILON = 0.1;
|
|
3099
|
-
var MVCP_ANCHOR_LOCK_TTL_MS = 300;
|
|
3100
|
-
var MVCP_ANCHOR_LOCK_QUIET_PASSES_TO_RELEASE = 2;
|
|
3101
|
-
var NATIVE_END_CLAMP_EPSILON = 1;
|
|
3102
|
-
function resolveAnchorLock(state, enableMVCPAnchorLock, mvcpData, now) {
|
|
3103
|
-
if (!enableMVCPAnchorLock) {
|
|
3104
|
-
state.mvcpAnchorLock = void 0;
|
|
3105
|
-
return void 0;
|
|
3106
|
-
}
|
|
3107
|
-
const lock = state.mvcpAnchorLock;
|
|
3108
|
-
if (!lock) {
|
|
3109
|
-
return void 0;
|
|
3110
|
-
}
|
|
3111
|
-
const isExpired = now > lock.expiresAt;
|
|
3112
|
-
const isMissing = state.indexByKey.get(lock.id) === void 0;
|
|
3113
|
-
if (isExpired || isMissing || !mvcpData) {
|
|
3114
|
-
state.mvcpAnchorLock = void 0;
|
|
3115
|
-
return void 0;
|
|
3116
|
-
}
|
|
3117
|
-
return lock;
|
|
3118
|
-
}
|
|
3119
|
-
function updateAnchorLock(state, params) {
|
|
3120
|
-
if (Platform.OS === "web") {
|
|
3121
|
-
const { anchorId, anchorPosition, dataChanged, now, positionDiff } = params;
|
|
3122
|
-
const enableMVCPAnchorLock = !!dataChanged || !!state.mvcpAnchorLock;
|
|
3123
|
-
const mvcpData = state.props.maintainVisibleContentPosition.data;
|
|
3124
|
-
if (!enableMVCPAnchorLock || !mvcpData || state.scrollingTo || !anchorId || anchorPosition === void 0) {
|
|
3125
|
-
return;
|
|
3126
|
-
}
|
|
3127
|
-
const existingLock = state.mvcpAnchorLock;
|
|
3128
|
-
const quietPasses = !dataChanged && Math.abs(positionDiff) <= MVCP_POSITION_EPSILON && (existingLock == null ? void 0 : existingLock.id) === anchorId ? existingLock.quietPasses + 1 : 0;
|
|
3129
|
-
if (!dataChanged && quietPasses >= MVCP_ANCHOR_LOCK_QUIET_PASSES_TO_RELEASE) {
|
|
3130
|
-
state.mvcpAnchorLock = void 0;
|
|
3131
|
-
return;
|
|
3132
|
-
}
|
|
3133
|
-
state.mvcpAnchorLock = {
|
|
3134
|
-
expiresAt: now + MVCP_ANCHOR_LOCK_TTL_MS,
|
|
3135
|
-
id: anchorId,
|
|
3136
|
-
position: anchorPosition,
|
|
3137
|
-
quietPasses
|
|
3138
|
-
};
|
|
3139
|
-
}
|
|
3140
|
-
}
|
|
3141
|
-
function shouldQueueNativeMVCPAdjust(dataChanged, state, positionDiff, prevTotalSize, prevScroll, scrollTarget) {
|
|
3142
|
-
if (!dataChanged || Platform.OS === "web" || !state.props.maintainVisibleContentPosition.data || scrollTarget !== void 0 || positionDiff >= -MVCP_POSITION_EPSILON) {
|
|
3143
|
-
return false;
|
|
3144
|
-
}
|
|
3145
|
-
const distanceFromEnd = prevTotalSize - prevScroll - state.scrollLength;
|
|
3146
|
-
return distanceFromEnd < Math.abs(positionDiff) - MVCP_POSITION_EPSILON;
|
|
3147
|
-
}
|
|
3148
|
-
function getPredictedNativeClamp(state, unresolvedAmount, totalSize) {
|
|
3149
|
-
if (Math.abs(unresolvedAmount) <= MVCP_POSITION_EPSILON) {
|
|
3150
|
-
return 0;
|
|
3151
|
-
}
|
|
3152
|
-
const maxScroll = Math.max(0, totalSize - state.scrollLength);
|
|
3153
|
-
const clampDelta = maxScroll - state.scroll;
|
|
3154
|
-
if (unresolvedAmount < 0) {
|
|
3155
|
-
return Math.max(unresolvedAmount, Math.min(0, clampDelta));
|
|
3156
|
-
}
|
|
3157
|
-
if (unresolvedAmount > 0) {
|
|
3158
|
-
return Math.min(unresolvedAmount, Math.max(0, clampDelta));
|
|
3159
|
-
}
|
|
3160
|
-
return 0;
|
|
3161
|
-
}
|
|
3162
|
-
function getProgressTowardAmount(targetDelta, nativeDelta) {
|
|
3163
|
-
return targetDelta < 0 ? -nativeDelta : nativeDelta;
|
|
3164
|
-
}
|
|
3165
|
-
function settlePendingNativeMVCPAdjust(ctx, remainingAfterManual, nativeDelta) {
|
|
3166
|
-
const state = ctx.state;
|
|
3167
|
-
state.pendingNativeMVCPAdjust = void 0;
|
|
3168
|
-
const remaining = remainingAfterManual - nativeDelta;
|
|
3169
|
-
if (Math.abs(remaining) > MVCP_POSITION_EPSILON) {
|
|
3170
|
-
requestAdjust(ctx, remaining, true);
|
|
3171
|
-
}
|
|
3172
|
-
}
|
|
3173
|
-
function maybeApplyPredictedNativeMVCPAdjust(ctx) {
|
|
3174
|
-
const state = ctx.state;
|
|
3175
|
-
const pending = state.pendingNativeMVCPAdjust;
|
|
3176
|
-
if (!pending || Math.abs(pending.manualApplied) > MVCP_POSITION_EPSILON) {
|
|
3177
|
-
return;
|
|
3178
|
-
}
|
|
3179
|
-
const totalSize = getContentSize(ctx);
|
|
3180
|
-
const predictedNativeClamp = getPredictedNativeClamp(state, pending.amount, totalSize);
|
|
3181
|
-
if (Math.abs(predictedNativeClamp) <= MVCP_POSITION_EPSILON) {
|
|
3182
|
-
return;
|
|
3183
|
-
}
|
|
3184
|
-
const manualDesired = pending.amount - predictedNativeClamp;
|
|
3185
|
-
if (Math.abs(manualDesired) <= MVCP_POSITION_EPSILON) {
|
|
3186
|
-
return;
|
|
3187
|
-
}
|
|
3188
|
-
pending.manualApplied = manualDesired;
|
|
3189
|
-
requestAdjust(ctx, manualDesired, true);
|
|
3190
|
-
pending.furthestProgressTowardAmount = 0;
|
|
3191
|
-
}
|
|
3192
|
-
function resolvePendingNativeMVCPAdjust(ctx, newScroll) {
|
|
3193
|
-
const state = ctx.state;
|
|
3194
|
-
const pending = state.pendingNativeMVCPAdjust;
|
|
3195
|
-
if (!pending) {
|
|
3196
|
-
return false;
|
|
3197
|
-
}
|
|
3198
|
-
const remainingAfterManual = pending.amount - pending.manualApplied;
|
|
3199
|
-
const nativeDelta = newScroll - (pending.startScroll + pending.manualApplied);
|
|
3200
|
-
const isWrongDirection = remainingAfterManual < 0 && nativeDelta > MVCP_POSITION_EPSILON || remainingAfterManual > 0 && nativeDelta < -MVCP_POSITION_EPSILON;
|
|
3201
|
-
const progressTowardAmount = getProgressTowardAmount(remainingAfterManual, nativeDelta);
|
|
3202
|
-
if (Math.abs(remainingAfterManual) <= MVCP_POSITION_EPSILON) {
|
|
3203
|
-
state.pendingNativeMVCPAdjust = void 0;
|
|
3204
|
-
return true;
|
|
3205
|
-
}
|
|
3206
|
-
if (isWrongDirection) {
|
|
3207
|
-
state.pendingNativeMVCPAdjust = void 0;
|
|
3208
|
-
return false;
|
|
3209
|
-
}
|
|
3210
|
-
if (progressTowardAmount + MVCP_POSITION_EPSILON >= Math.abs(remainingAfterManual)) {
|
|
3211
|
-
settlePendingNativeMVCPAdjust(ctx, remainingAfterManual, nativeDelta);
|
|
3212
|
-
return true;
|
|
3213
|
-
}
|
|
3214
|
-
const expectedNativeClampScroll = Math.max(0, getContentSize(ctx) - state.scrollLength);
|
|
3215
|
-
const distanceToClamp = Math.abs(newScroll - expectedNativeClampScroll);
|
|
3216
|
-
const isAtExpectedNativeClamp = distanceToClamp <= NATIVE_END_CLAMP_EPSILON;
|
|
3217
|
-
if (isAtExpectedNativeClamp) {
|
|
3218
|
-
settlePendingNativeMVCPAdjust(ctx, remainingAfterManual, nativeDelta);
|
|
3219
|
-
return true;
|
|
3220
|
-
}
|
|
3221
|
-
if (state.pendingMaintainScrollAtEnd && peek$(ctx, "isWithinMaintainScrollAtEndThreshold") && progressTowardAmount > MVCP_POSITION_EPSILON) {
|
|
3222
|
-
settlePendingNativeMVCPAdjust(ctx, remainingAfterManual, nativeDelta);
|
|
3223
|
-
return true;
|
|
3224
|
-
}
|
|
3225
|
-
if (progressTowardAmount > pending.furthestProgressTowardAmount + MVCP_POSITION_EPSILON) {
|
|
3226
|
-
pending.furthestProgressTowardAmount = progressTowardAmount;
|
|
3227
|
-
return false;
|
|
3228
|
-
}
|
|
3229
|
-
if (pending.furthestProgressTowardAmount > MVCP_POSITION_EPSILON && progressTowardAmount < pending.furthestProgressTowardAmount - MVCP_POSITION_EPSILON) {
|
|
3230
|
-
state.pendingNativeMVCPAdjust = void 0;
|
|
3231
|
-
return false;
|
|
3232
|
-
}
|
|
3233
|
-
return false;
|
|
3234
|
-
}
|
|
3235
|
-
function prepareMVCP(ctx, dataChanged) {
|
|
3236
|
-
const state = ctx.state;
|
|
3237
|
-
const { idsInView, positions, props } = state;
|
|
3238
|
-
const {
|
|
3239
|
-
maintainVisibleContentPosition: { data: mvcpData, size: mvcpScroll, shouldRestorePosition }
|
|
3240
|
-
} = props;
|
|
3241
|
-
const isWeb = Platform.OS === "web";
|
|
3242
|
-
const now = Date.now();
|
|
3243
|
-
const enableMVCPAnchorLock = isWeb && (!!dataChanged || !!state.mvcpAnchorLock);
|
|
3244
|
-
const scrollingTo = state.scrollingTo;
|
|
3245
|
-
const anchorLock = isWeb ? resolveAnchorLock(state, enableMVCPAnchorLock, mvcpData, now) : void 0;
|
|
3246
|
-
let prevPosition;
|
|
3247
|
-
let targetId;
|
|
3248
|
-
const idsInViewWithPositions = [];
|
|
3249
|
-
const scrollTarget = scrollingTo == null ? void 0 : scrollingTo.index;
|
|
3250
|
-
const scrollingToViewPosition = scrollingTo == null ? void 0 : scrollingTo.viewPosition;
|
|
3251
|
-
const isEndAnchoredScrollTarget = scrollTarget !== void 0 && state.props.data.length > 0 && scrollTarget >= state.props.data.length - 1 && (scrollingToViewPosition != null ? scrollingToViewPosition : 0) > 0;
|
|
3252
|
-
const shouldMVCP = dataChanged ? mvcpData : mvcpScroll;
|
|
3253
|
-
const indexByKey = state.indexByKey;
|
|
3254
|
-
const prevScroll = state.scroll;
|
|
3255
|
-
const prevTotalSize = getContentSize(ctx);
|
|
3256
|
-
if (shouldMVCP) {
|
|
3257
|
-
if (!isWeb && state.pendingNativeMVCPAdjust && scrollTarget === void 0) {
|
|
3258
|
-
maybeApplyPredictedNativeMVCPAdjust(ctx);
|
|
3259
|
-
return void 0;
|
|
3260
|
-
}
|
|
3261
|
-
if (anchorLock && scrollTarget === void 0) {
|
|
3262
|
-
targetId = anchorLock.id;
|
|
3263
|
-
prevPosition = anchorLock.position;
|
|
3264
|
-
} else if (scrollTarget !== void 0) {
|
|
3265
|
-
if (!IsNewArchitecture && (scrollingTo == null ? void 0 : scrollingTo.isInitialScroll)) {
|
|
3266
|
-
return void 0;
|
|
3267
|
-
}
|
|
3268
|
-
targetId = getId(state, scrollTarget);
|
|
3269
|
-
} else if (idsInView.length > 0 && state.didContainersLayout && !dataChanged) {
|
|
3270
|
-
targetId = idsInView.find((id) => indexByKey.get(id) !== void 0);
|
|
3271
|
-
}
|
|
3272
|
-
if (dataChanged && idsInView.length > 0 && state.didContainersLayout) {
|
|
3273
|
-
for (let i = 0; i < idsInView.length; i++) {
|
|
3274
|
-
const id = idsInView[i];
|
|
3275
|
-
const index = indexByKey.get(id);
|
|
3276
|
-
if (index !== void 0) {
|
|
3277
|
-
const position = positions[index];
|
|
3278
|
-
if (position !== void 0) {
|
|
3279
|
-
idsInViewWithPositions.push({ id, position });
|
|
3280
|
-
}
|
|
3281
|
-
}
|
|
3282
|
-
}
|
|
3283
|
-
}
|
|
3284
|
-
if (targetId !== void 0 && prevPosition === void 0) {
|
|
3285
|
-
const targetIndex = indexByKey.get(targetId);
|
|
3286
|
-
if (targetIndex !== void 0) {
|
|
3287
|
-
prevPosition = positions[targetIndex];
|
|
3288
|
-
}
|
|
3289
|
-
}
|
|
3290
|
-
return () => {
|
|
3291
|
-
let positionDiff = 0;
|
|
3292
|
-
let anchorIdForLock = anchorLock == null ? void 0 : anchorLock.id;
|
|
3293
|
-
let anchorPositionForLock;
|
|
3294
|
-
let skipTargetAnchor = false;
|
|
3295
|
-
const data = state.props.data;
|
|
3296
|
-
const shouldValidateLockedAnchor = isWeb && dataChanged && mvcpData && scrollTarget === void 0 && targetId !== void 0 && (anchorLock == null ? void 0 : anchorLock.id) === targetId && shouldRestorePosition !== void 0;
|
|
3297
|
-
if (shouldValidateLockedAnchor && targetId !== void 0) {
|
|
3298
|
-
const index = indexByKey.get(targetId);
|
|
3299
|
-
if (index !== void 0) {
|
|
3300
|
-
const item = data[index];
|
|
3301
|
-
skipTargetAnchor = item === void 0 || !shouldRestorePosition(item, index, data);
|
|
3302
|
-
if (skipTargetAnchor && (anchorLock == null ? void 0 : anchorLock.id) === targetId) {
|
|
3303
|
-
state.mvcpAnchorLock = void 0;
|
|
3304
|
-
}
|
|
3305
|
-
}
|
|
3306
|
-
}
|
|
3307
|
-
const shouldUseFallbackVisibleAnchor = dataChanged && mvcpData && scrollTarget === void 0 && (() => {
|
|
3308
|
-
if (targetId === void 0 || skipTargetAnchor) {
|
|
3309
|
-
return true;
|
|
3310
|
-
}
|
|
3311
|
-
const targetIndex = indexByKey.get(targetId);
|
|
3312
|
-
return targetIndex === void 0 || positions[targetIndex] === void 0;
|
|
3313
|
-
})();
|
|
3314
|
-
if (shouldUseFallbackVisibleAnchor) {
|
|
3315
|
-
for (let i = 0; i < idsInViewWithPositions.length; i++) {
|
|
3316
|
-
const { id, position } = idsInViewWithPositions[i];
|
|
3317
|
-
const index = indexByKey.get(id);
|
|
3318
|
-
if (index !== void 0 && shouldRestorePosition) {
|
|
3319
|
-
const item = data[index];
|
|
3320
|
-
if (item === void 0 || !shouldRestorePosition(item, index, data)) {
|
|
3321
|
-
continue;
|
|
3322
|
-
}
|
|
3323
|
-
}
|
|
3324
|
-
const newPosition = index !== void 0 ? positions[index] : void 0;
|
|
3325
|
-
if (newPosition !== void 0) {
|
|
3326
|
-
positionDiff = newPosition - position;
|
|
3327
|
-
anchorIdForLock = id;
|
|
3328
|
-
anchorPositionForLock = newPosition;
|
|
3329
|
-
break;
|
|
3330
|
-
}
|
|
3331
|
-
}
|
|
3332
|
-
}
|
|
3333
|
-
if (!skipTargetAnchor && targetId !== void 0 && prevPosition !== void 0) {
|
|
3334
|
-
const targetIndex = indexByKey.get(targetId);
|
|
3335
|
-
const newPosition = targetIndex !== void 0 ? positions[targetIndex] : void 0;
|
|
3336
|
-
if (newPosition !== void 0) {
|
|
3337
|
-
const totalSize = getContentSize(ctx);
|
|
3338
|
-
let diff = newPosition - prevPosition;
|
|
3339
|
-
if (diff !== 0 && isEndAnchoredScrollTarget && state.scroll + state.scrollLength > totalSize) {
|
|
3340
|
-
if (diff > 0) {
|
|
3341
|
-
diff = Math.max(0, totalSize - state.scroll - state.scrollLength);
|
|
3342
|
-
} else {
|
|
3343
|
-
diff = 0;
|
|
3344
|
-
}
|
|
3345
|
-
}
|
|
3346
|
-
positionDiff = diff;
|
|
3347
|
-
anchorIdForLock = targetId;
|
|
3348
|
-
anchorPositionForLock = newPosition;
|
|
3349
|
-
}
|
|
3350
|
-
}
|
|
3351
|
-
if (scrollingToViewPosition && scrollingToViewPosition > 0) {
|
|
3352
|
-
const newSize = getItemSize(ctx, targetId, scrollTarget, state.props.data[scrollTarget]);
|
|
3353
|
-
const prevSize = scrollingTo == null ? void 0 : scrollingTo.itemSize;
|
|
3354
|
-
if (newSize !== void 0 && prevSize !== void 0 && newSize !== prevSize) {
|
|
3355
|
-
const diff = newSize - prevSize;
|
|
3356
|
-
if (diff !== 0) {
|
|
3357
|
-
positionDiff += diff * scrollingToViewPosition;
|
|
3358
|
-
scrollingTo.itemSize = newSize;
|
|
3359
|
-
}
|
|
3360
|
-
}
|
|
3361
|
-
}
|
|
3362
|
-
updateAnchorLock(state, {
|
|
3363
|
-
anchorId: anchorIdForLock,
|
|
3364
|
-
anchorPosition: anchorPositionForLock,
|
|
3365
|
-
dataChanged,
|
|
3366
|
-
now,
|
|
3367
|
-
positionDiff
|
|
3431
|
+
dispatchInitialScroll(ctx, {
|
|
3432
|
+
forceScroll: true,
|
|
3433
|
+
resolvedOffset: bootstrapInitialScroll.scroll,
|
|
3434
|
+
target: initialScroll,
|
|
3435
|
+
waitForCompletionFrame: Platform.OS === "web"
|
|
3436
|
+
});
|
|
3437
|
+
} else {
|
|
3438
|
+
finishBootstrapInitialScrollWithoutScroll(
|
|
3439
|
+
ctx,
|
|
3440
|
+
(_d = (_c = (_b = (_a3 = getBootstrapInitialScrollSession(state)) == null ? void 0 : _a3.scroll) != null ? _b : state.scrollPending) != null ? _c : state.scroll) != null ? _d : 0
|
|
3441
|
+
);
|
|
3442
|
+
}
|
|
3443
|
+
}
|
|
3444
|
+
|
|
3445
|
+
// src/core/initialScrollLifecycle.ts
|
|
3446
|
+
function retargetActiveInitialScrollAtEnd(ctx) {
|
|
3447
|
+
var _a3;
|
|
3448
|
+
const state = ctx.state;
|
|
3449
|
+
const initialScroll = state.initialScroll;
|
|
3450
|
+
if (state.didFinishInitialScroll) {
|
|
3451
|
+
return schedulePreservedEndAnchorCorrection(ctx);
|
|
3452
|
+
}
|
|
3453
|
+
if (!initialScroll || ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) === "offset" || initialScroll.viewPosition !== 1 || state.props.data.length === 0) {
|
|
3454
|
+
return false;
|
|
3455
|
+
}
|
|
3456
|
+
return advanceCurrentInitialScrollSession(ctx, { forceScroll: true });
|
|
3457
|
+
}
|
|
3458
|
+
function handleInitialScrollLayoutReady(ctx) {
|
|
3459
|
+
var _a3;
|
|
3460
|
+
if (!ctx.state.initialScroll) {
|
|
3461
|
+
return;
|
|
3462
|
+
}
|
|
3463
|
+
const runScroll = () => advanceCurrentInitialScrollSession(ctx, { forceScroll: true });
|
|
3464
|
+
runScroll();
|
|
3465
|
+
if (((_a3 = ctx.state.initialScrollSession) == null ? void 0 : _a3.kind) !== "offset") {
|
|
3466
|
+
requestAnimationFrame(runScroll);
|
|
3467
|
+
}
|
|
3468
|
+
checkFinishedScroll(ctx, { onlyIfAligned: true });
|
|
3469
|
+
}
|
|
3470
|
+
function initializeInitialScrollOnMount(ctx, options) {
|
|
3471
|
+
var _a3, _b;
|
|
3472
|
+
const {
|
|
3473
|
+
alwaysDispatchInitialScroll,
|
|
3474
|
+
dataLength,
|
|
3475
|
+
hasFooterComponent,
|
|
3476
|
+
initialContentOffset,
|
|
3477
|
+
initialScrollAtEnd,
|
|
3478
|
+
useBootstrapInitialScroll
|
|
3479
|
+
} = options;
|
|
3480
|
+
const state = ctx.state;
|
|
3481
|
+
const initialScroll = state.initialScroll;
|
|
3482
|
+
const resolvedInitialContentOffset = initialContentOffset != null ? initialContentOffset : 0;
|
|
3483
|
+
const preserveForFooterLayout = useBootstrapInitialScroll && initialScrollAtEnd && hasFooterComponent;
|
|
3484
|
+
if (initialScroll && (initialScroll.contentOffset === void 0 || !!initialScroll.preserveForFooterLayout !== preserveForFooterLayout && ((_a3 = state.initialScrollSession) == null ? void 0 : _a3.kind) !== "offset")) {
|
|
3485
|
+
setInitialScrollTarget(state, {
|
|
3486
|
+
...initialScroll,
|
|
3487
|
+
contentOffset: resolvedInitialContentOffset,
|
|
3488
|
+
preserveForFooterLayout
|
|
3489
|
+
});
|
|
3490
|
+
}
|
|
3491
|
+
if (useBootstrapInitialScroll && initialScroll && ((_b = state.initialScrollSession) == null ? void 0 : _b.kind) !== "offset") {
|
|
3492
|
+
startBootstrapInitialScrollOnMount(ctx, {
|
|
3493
|
+
initialScrollAtEnd,
|
|
3494
|
+
target: state.initialScroll
|
|
3495
|
+
});
|
|
3496
|
+
return;
|
|
3497
|
+
}
|
|
3498
|
+
const hasPendingDataDependentInitialScroll = !!initialScroll && dataLength === 0 && !(resolvedInitialContentOffset === 0 && !initialScrollAtEnd);
|
|
3499
|
+
if (!alwaysDispatchInitialScroll && !resolvedInitialContentOffset && !hasPendingDataDependentInitialScroll) {
|
|
3500
|
+
if (initialScroll && !initialScrollAtEnd) {
|
|
3501
|
+
finishInitialScroll(ctx, {
|
|
3502
|
+
resolvedOffset: resolvedInitialContentOffset
|
|
3368
3503
|
});
|
|
3369
|
-
|
|
3370
|
-
|
|
3371
|
-
|
|
3372
|
-
|
|
3373
|
-
|
|
3374
|
-
|
|
3375
|
-
|
|
3376
|
-
|
|
3377
|
-
|
|
3378
|
-
|
|
3379
|
-
|
|
3380
|
-
|
|
3381
|
-
|
|
3382
|
-
|
|
3383
|
-
|
|
3384
|
-
|
|
3385
|
-
|
|
3504
|
+
} else {
|
|
3505
|
+
setInitialRenderState(ctx, { didInitialScroll: true });
|
|
3506
|
+
}
|
|
3507
|
+
}
|
|
3508
|
+
}
|
|
3509
|
+
function handleInitialScrollDataChange(ctx, options) {
|
|
3510
|
+
var _a3, _b, _c;
|
|
3511
|
+
const { dataLength, didDataChange, initialScrollAtEnd, stylePaddingBottom, useBootstrapInitialScroll } = options;
|
|
3512
|
+
const state = ctx.state;
|
|
3513
|
+
const previousDataLength = (_b = (_a3 = state.initialScrollSession) == null ? void 0 : _a3.previousDataLength) != null ? _b : 0;
|
|
3514
|
+
if (state.initialScrollSession) {
|
|
3515
|
+
state.initialScrollSession.previousDataLength = dataLength;
|
|
3516
|
+
}
|
|
3517
|
+
setInitialScrollSession(state);
|
|
3518
|
+
if (useBootstrapInitialScroll) {
|
|
3519
|
+
handleBootstrapInitialScrollDataChange(ctx, {
|
|
3520
|
+
dataLength,
|
|
3521
|
+
didDataChange,
|
|
3522
|
+
initialScrollAtEnd,
|
|
3523
|
+
previousDataLength,
|
|
3524
|
+
stylePaddingBottom
|
|
3525
|
+
});
|
|
3526
|
+
return;
|
|
3386
3527
|
}
|
|
3528
|
+
const shouldReplayFinishedOffsetInitialScroll = previousDataLength === 0 && dataLength > 0 && !!state.initialScroll && ((_c = ctx.state.initialScrollSession) == null ? void 0 : _c.kind) === "offset" && !!state.didFinishInitialScroll;
|
|
3529
|
+
if (previousDataLength !== 0 || dataLength === 0 || !state.initialScroll || !state.queuedInitialLayout || state.didFinishInitialScroll && !shouldReplayFinishedOffsetInitialScroll) {
|
|
3530
|
+
return;
|
|
3531
|
+
}
|
|
3532
|
+
if (shouldReplayFinishedOffsetInitialScroll) {
|
|
3533
|
+
state.didFinishInitialScroll = false;
|
|
3534
|
+
}
|
|
3535
|
+
advanceCurrentInitialScrollSession(ctx);
|
|
3387
3536
|
}
|
|
3388
3537
|
|
|
3389
3538
|
// src/core/resetLayoutCachesForDataChange.ts
|
|
@@ -4338,7 +4487,7 @@ function calculateItemsInView(ctx, params = {}) {
|
|
|
4338
4487
|
scrollBottomBuffered = scrollBottom + scrollBufferBottom;
|
|
4339
4488
|
};
|
|
4340
4489
|
updateScrollRange();
|
|
4341
|
-
if (!suppressInitialScrollSideEffects && !dataChanged && !forceFullItemPositions && scrollForNextCalculateItemsInView) {
|
|
4490
|
+
if (enableScrollForNextCalculateItemsInView && !suppressInitialScrollSideEffects && !dataChanged && !forceFullItemPositions && scrollForNextCalculateItemsInView) {
|
|
4342
4491
|
const { top, bottom } = scrollForNextCalculateItemsInView;
|
|
4343
4492
|
if (top === null && bottom === null) {
|
|
4344
4493
|
state.scrollForNextCalculateItemsInView = void 0;
|
|
@@ -4669,62 +4818,6 @@ function calculateItemsInView(ctx, params = {}) {
|
|
|
4669
4818
|
});
|
|
4670
4819
|
}
|
|
4671
4820
|
|
|
4672
|
-
// src/core/doMaintainScrollAtEnd.ts
|
|
4673
|
-
function doMaintainScrollAtEnd(ctx) {
|
|
4674
|
-
const state = ctx.state;
|
|
4675
|
-
const {
|
|
4676
|
-
didContainersLayout,
|
|
4677
|
-
pendingNativeMVCPAdjust,
|
|
4678
|
-
refScroller,
|
|
4679
|
-
props: { maintainScrollAtEnd }
|
|
4680
|
-
} = state;
|
|
4681
|
-
const isWithinMaintainScrollAtEndThreshold = peek$(ctx, "isWithinMaintainScrollAtEndThreshold");
|
|
4682
|
-
const shouldMaintainScrollAtEnd = !!(isWithinMaintainScrollAtEndThreshold && maintainScrollAtEnd && didContainersLayout);
|
|
4683
|
-
if (pendingNativeMVCPAdjust) {
|
|
4684
|
-
state.pendingMaintainScrollAtEnd = shouldMaintainScrollAtEnd;
|
|
4685
|
-
return false;
|
|
4686
|
-
}
|
|
4687
|
-
state.pendingMaintainScrollAtEnd = false;
|
|
4688
|
-
if (shouldMaintainScrollAtEnd) {
|
|
4689
|
-
const contentSize = getContentSize(ctx);
|
|
4690
|
-
if (contentSize < state.scrollLength) {
|
|
4691
|
-
state.scroll = 0;
|
|
4692
|
-
}
|
|
4693
|
-
if (!state.maintainingScrollAtEnd) {
|
|
4694
|
-
state.maintainingScrollAtEnd = true;
|
|
4695
|
-
requestAnimationFrame(() => {
|
|
4696
|
-
if (peek$(ctx, "isWithinMaintainScrollAtEndThreshold")) {
|
|
4697
|
-
const scroller = refScroller.current;
|
|
4698
|
-
if (state.props.horizontal && isHorizontalRTL(state)) {
|
|
4699
|
-
const currentContentSize = getContentSize(ctx);
|
|
4700
|
-
const logicalEndOffset = getLogicalHorizontalMaxOffset(state, currentContentSize);
|
|
4701
|
-
const nativeOffset = toNativeHorizontalOffset(state, logicalEndOffset, currentContentSize);
|
|
4702
|
-
scroller == null ? void 0 : scroller.scrollTo({
|
|
4703
|
-
animated: maintainScrollAtEnd.animated,
|
|
4704
|
-
x: nativeOffset,
|
|
4705
|
-
y: 0
|
|
4706
|
-
});
|
|
4707
|
-
} else {
|
|
4708
|
-
scroller == null ? void 0 : scroller.scrollToEnd({
|
|
4709
|
-
animated: maintainScrollAtEnd.animated
|
|
4710
|
-
});
|
|
4711
|
-
}
|
|
4712
|
-
setTimeout(
|
|
4713
|
-
() => {
|
|
4714
|
-
state.maintainingScrollAtEnd = false;
|
|
4715
|
-
},
|
|
4716
|
-
maintainScrollAtEnd.animated ? 500 : 0
|
|
4717
|
-
);
|
|
4718
|
-
} else {
|
|
4719
|
-
state.maintainingScrollAtEnd = false;
|
|
4720
|
-
}
|
|
4721
|
-
});
|
|
4722
|
-
}
|
|
4723
|
-
return true;
|
|
4724
|
-
}
|
|
4725
|
-
return false;
|
|
4726
|
-
}
|
|
4727
|
-
|
|
4728
4821
|
// src/core/checkResetContainers.ts
|
|
4729
4822
|
function checkResetContainers(ctx, dataProp, { didColumnsChange = false } = {}) {
|
|
4730
4823
|
const state = ctx.state;
|
|
@@ -4905,84 +4998,6 @@ function handleLayout(ctx, layoutParam, setCanRender) {
|
|
|
4905
4998
|
setCanRender(true);
|
|
4906
4999
|
}
|
|
4907
5000
|
|
|
4908
|
-
// src/platform/flushSync.native.ts
|
|
4909
|
-
var flushSync = (fn) => {
|
|
4910
|
-
fn();
|
|
4911
|
-
};
|
|
4912
|
-
|
|
4913
|
-
// src/core/updateScroll.ts
|
|
4914
|
-
function updateScroll(ctx, newScroll, forceUpdate, options) {
|
|
4915
|
-
var _a3;
|
|
4916
|
-
const state = ctx.state;
|
|
4917
|
-
const { ignoreScrollFromMVCP, lastScrollAdjustForHistory, scrollAdjustHandler, scrollHistory, scrollingTo } = state;
|
|
4918
|
-
const prevScroll = state.scroll;
|
|
4919
|
-
if ((options == null ? void 0 : options.markHasScrolled) !== false) {
|
|
4920
|
-
state.hasScrolled = true;
|
|
4921
|
-
}
|
|
4922
|
-
state.lastBatchingAction = Date.now();
|
|
4923
|
-
const currentTime = Date.now();
|
|
4924
|
-
const adjust = scrollAdjustHandler.getAdjust();
|
|
4925
|
-
const adjustChanged = lastScrollAdjustForHistory !== void 0 && Math.abs(adjust - lastScrollAdjustForHistory) > 0.1;
|
|
4926
|
-
if (adjustChanged) {
|
|
4927
|
-
scrollHistory.length = 0;
|
|
4928
|
-
}
|
|
4929
|
-
state.lastScrollAdjustForHistory = adjust;
|
|
4930
|
-
if (scrollingTo === void 0 && !(scrollHistory.length === 0 && newScroll === state.scroll)) {
|
|
4931
|
-
if (!adjustChanged) {
|
|
4932
|
-
scrollHistory.push({ scroll: newScroll, time: currentTime });
|
|
4933
|
-
}
|
|
4934
|
-
}
|
|
4935
|
-
if (scrollHistory.length > 5) {
|
|
4936
|
-
scrollHistory.shift();
|
|
4937
|
-
}
|
|
4938
|
-
if (ignoreScrollFromMVCP && !scrollingTo) {
|
|
4939
|
-
const { lt, gt } = ignoreScrollFromMVCP;
|
|
4940
|
-
if (lt && newScroll < lt || gt && newScroll > gt) {
|
|
4941
|
-
state.ignoreScrollFromMVCPIgnored = true;
|
|
4942
|
-
return;
|
|
4943
|
-
}
|
|
4944
|
-
}
|
|
4945
|
-
state.scrollPrev = prevScroll;
|
|
4946
|
-
state.scrollPrevTime = state.scrollTime;
|
|
4947
|
-
state.scroll = newScroll;
|
|
4948
|
-
state.scrollTime = currentTime;
|
|
4949
|
-
const scrollDelta = Math.abs(newScroll - prevScroll);
|
|
4950
|
-
const didResolvePendingNativeMVCPAdjust = resolvePendingNativeMVCPAdjust(ctx, newScroll);
|
|
4951
|
-
const scrollLength = state.scrollLength;
|
|
4952
|
-
const lastCalculated = state.scrollLastCalculate;
|
|
4953
|
-
const useAggressiveItemRecalculation = isInMVCPActiveMode(state);
|
|
4954
|
-
const shouldUpdate = useAggressiveItemRecalculation || didResolvePendingNativeMVCPAdjust || forceUpdate || lastCalculated === void 0 || Math.abs(state.scroll - lastCalculated) > 2;
|
|
4955
|
-
if (shouldUpdate) {
|
|
4956
|
-
state.scrollLastCalculate = state.scroll;
|
|
4957
|
-
state.ignoreScrollFromMVCPIgnored = false;
|
|
4958
|
-
state.lastScrollDelta = scrollDelta;
|
|
4959
|
-
const runCalculateItems = () => {
|
|
4960
|
-
var _a4;
|
|
4961
|
-
(_a4 = state.triggerCalculateItemsInView) == null ? void 0 : _a4.call(state, { doMVCP: scrollingTo !== void 0 });
|
|
4962
|
-
checkThresholds(ctx);
|
|
4963
|
-
};
|
|
4964
|
-
if (scrollLength > 0 && scrollingTo === void 0 && scrollDelta > scrollLength && !state.pendingNativeMVCPAdjust) {
|
|
4965
|
-
state.mvcpAnchorLock = void 0;
|
|
4966
|
-
state.pendingNativeMVCPAdjust = void 0;
|
|
4967
|
-
state.userScrollAnchorResetKeys = /* @__PURE__ */ new Set();
|
|
4968
|
-
if (state.queuedMVCPRecalculate !== void 0) {
|
|
4969
|
-
cancelAnimationFrame(state.queuedMVCPRecalculate);
|
|
4970
|
-
state.queuedMVCPRecalculate = void 0;
|
|
4971
|
-
}
|
|
4972
|
-
flushSync(runCalculateItems);
|
|
4973
|
-
} else {
|
|
4974
|
-
runCalculateItems();
|
|
4975
|
-
}
|
|
4976
|
-
const shouldMaintainScrollAtEndAfterPendingSettle = !!state.pendingMaintainScrollAtEnd || !!((_a3 = state.props.maintainScrollAtEnd) == null ? void 0 : _a3.onDataChange);
|
|
4977
|
-
if (didResolvePendingNativeMVCPAdjust && shouldMaintainScrollAtEndAfterPendingSettle) {
|
|
4978
|
-
state.pendingMaintainScrollAtEnd = false;
|
|
4979
|
-
doMaintainScrollAtEnd(ctx);
|
|
4980
|
-
}
|
|
4981
|
-
state.dataChangeNeedsScrollUpdate = false;
|
|
4982
|
-
state.lastScrollDelta = 0;
|
|
4983
|
-
}
|
|
4984
|
-
}
|
|
4985
|
-
|
|
4986
5001
|
// src/core/onScroll.ts
|
|
4987
5002
|
function trackInitialScrollNativeProgress(state, newScroll) {
|
|
4988
5003
|
const initialNativeScrollWatchdog = initialScrollWatchdog.get(state);
|
|
@@ -6328,6 +6343,9 @@ var LegendListInner = typedForwardRef(function LegendListInner2(props, forwarded
|
|
|
6328
6343
|
});
|
|
6329
6344
|
state.viewabilityConfigCallbackPairs = viewability;
|
|
6330
6345
|
state.enableScrollForNextCalculateItemsInView = !viewability;
|
|
6346
|
+
if (viewability) {
|
|
6347
|
+
state.scrollForNextCalculateItemsInView = void 0;
|
|
6348
|
+
}
|
|
6331
6349
|
}, [viewabilityConfig, viewabilityConfigCallbackPairs, onViewableItemsChanged]);
|
|
6332
6350
|
useInit(() => {
|
|
6333
6351
|
if (!IsNewArchitecture) {
|