@legendapp/list 0.3.2 → 0.3.3
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/README.md +2 -2
- package/index.d.mts +1 -5
- package/index.d.ts +1 -5
- package/index.js +343 -421
- package/index.mjs +345 -423
- package/package.json +1 -1
package/index.js
CHANGED
|
@@ -24,10 +24,10 @@ function _interopNamespace(e) {
|
|
|
24
24
|
var React6__namespace = /*#__PURE__*/_interopNamespace(React6);
|
|
25
25
|
|
|
26
26
|
// src/LegendList.tsx
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
27
|
+
var LeanView = React6__namespace.forwardRef((props, ref) => {
|
|
28
|
+
return React6__namespace.createElement("RCTView", { ...props, ref });
|
|
29
|
+
});
|
|
30
|
+
LeanView.displayName = "RCTView";
|
|
31
31
|
var ContextListener = React6__namespace.createContext(null);
|
|
32
32
|
function StateProvider({ children }) {
|
|
33
33
|
const [value] = React6__namespace.useState(() => ({
|
|
@@ -57,309 +57,6 @@ function set$(ctx, signalName, value) {
|
|
|
57
57
|
(_a = listeners.get(signalName)) == null ? void 0 : _a();
|
|
58
58
|
}
|
|
59
59
|
}
|
|
60
|
-
function applyDefaultProps(props) {
|
|
61
|
-
return {
|
|
62
|
-
...props,
|
|
63
|
-
recycleItems: props.recycleItems || false,
|
|
64
|
-
onEndReachedThreshold: props.onEndReachedThreshold || 0.5,
|
|
65
|
-
maintainScrollAtEndThreshold: props.maintainScrollAtEndThreshold || 0.1,
|
|
66
|
-
maintainScrollAtEnd: props.maintainScrollAtEnd || false,
|
|
67
|
-
alignItemsAtEnd: props.alignItemsAtEnd || false
|
|
68
|
-
};
|
|
69
|
-
}
|
|
70
|
-
function allocateContainers(state) {
|
|
71
|
-
var _a, _b;
|
|
72
|
-
const { scrollLength, props, ctx, scrollBuffer } = state;
|
|
73
|
-
const averageItemSize = (_b = props.estimatedItemSize) != null ? _b : (_a = props.getEstimatedItemSize) == null ? void 0 : _a.call(props, 0, props.data[0]);
|
|
74
|
-
const numContainers = props.initialNumContainers || Math.ceil((scrollLength + scrollBuffer * 2) / averageItemSize) + 4;
|
|
75
|
-
for (let i = 0; i < numContainers; i++) {
|
|
76
|
-
set$(ctx, `containerIndex${i}`, -1);
|
|
77
|
-
set$(ctx, `containerPosition${i}`, POSITION_OUT_OF_VIEW);
|
|
78
|
-
}
|
|
79
|
-
set$(ctx, `numContainers`, numContainers);
|
|
80
|
-
}
|
|
81
|
-
function getId(state, index) {
|
|
82
|
-
const { data, keyExtractor } = state.props;
|
|
83
|
-
if (!data) {
|
|
84
|
-
return "";
|
|
85
|
-
}
|
|
86
|
-
const ret = index < data.length ? keyExtractor ? keyExtractor(data[index], index) : index : null;
|
|
87
|
-
return ret + "";
|
|
88
|
-
}
|
|
89
|
-
function calculateInitialOffset(props) {
|
|
90
|
-
const { data, initialScrollIndex, estimatedItemSize, getEstimatedItemSize } = props;
|
|
91
|
-
if (initialScrollIndex) {
|
|
92
|
-
if (getEstimatedItemSize) {
|
|
93
|
-
let offset = 0;
|
|
94
|
-
for (let i = 0; i < initialScrollIndex; i++) {
|
|
95
|
-
offset += getEstimatedItemSize(i, data[i]);
|
|
96
|
-
}
|
|
97
|
-
return offset;
|
|
98
|
-
} else if (estimatedItemSize) {
|
|
99
|
-
return initialScrollIndex * estimatedItemSize;
|
|
100
|
-
}
|
|
101
|
-
}
|
|
102
|
-
return void 0;
|
|
103
|
-
}
|
|
104
|
-
function addTotalLength(state, add) {
|
|
105
|
-
const { ctx, props } = state;
|
|
106
|
-
const totalLength = (peek$(ctx, `totalLength`) || 0) + add;
|
|
107
|
-
set$(ctx, `totalLength`, totalLength);
|
|
108
|
-
const screenLength = state.scrollLength;
|
|
109
|
-
if (props.alignItemsAtEnd) {
|
|
110
|
-
const listPaddingTop = peek$(ctx, `stylePaddingTop`);
|
|
111
|
-
set$(ctx, `paddingTop`, Math.max(0, screenLength - totalLength - listPaddingTop));
|
|
112
|
-
}
|
|
113
|
-
}
|
|
114
|
-
function getRenderedItem(state, index) {
|
|
115
|
-
const { data, renderItem } = state.props;
|
|
116
|
-
if (!data) {
|
|
117
|
-
return null;
|
|
118
|
-
}
|
|
119
|
-
const renderedItem = renderItem == null ? void 0 : renderItem({
|
|
120
|
-
item: data[index],
|
|
121
|
-
index
|
|
122
|
-
});
|
|
123
|
-
return renderedItem;
|
|
124
|
-
}
|
|
125
|
-
var getItemSize = (state, index, data) => {
|
|
126
|
-
const { getEstimatedItemSize, estimatedItemSize } = state.props;
|
|
127
|
-
return getEstimatedItemSize ? getEstimatedItemSize(index, data) : estimatedItemSize;
|
|
128
|
-
};
|
|
129
|
-
function calculateItemsInView(state) {
|
|
130
|
-
reactNative.unstable_batchedUpdates(() => {
|
|
131
|
-
var _a, _b, _c;
|
|
132
|
-
const {
|
|
133
|
-
props: { data, onViewableRangeChanged },
|
|
134
|
-
scrollLength,
|
|
135
|
-
scroll: scrollState,
|
|
136
|
-
startNoBuffer: startNoBufferState,
|
|
137
|
-
startBuffered: startBufferedState,
|
|
138
|
-
endNoBuffer: endNoBufferState,
|
|
139
|
-
endBuffered: endBufferedState,
|
|
140
|
-
lengths,
|
|
141
|
-
positions,
|
|
142
|
-
scrollBuffer,
|
|
143
|
-
ctx
|
|
144
|
-
} = state;
|
|
145
|
-
if (!data) {
|
|
146
|
-
return;
|
|
147
|
-
}
|
|
148
|
-
const topPad = (peek$(ctx, `stylePaddingTop`) || 0) + (peek$(ctx, `headerSize`) || 0);
|
|
149
|
-
const scroll = scrollState - topPad;
|
|
150
|
-
scroll > state.scrollPrevious ? 1 : -1;
|
|
151
|
-
const scrollBufferTop = scrollBuffer;
|
|
152
|
-
const scrollBufferBottom = scrollBuffer;
|
|
153
|
-
let startNoBuffer = null;
|
|
154
|
-
let startBuffered = null;
|
|
155
|
-
let endNoBuffer = null;
|
|
156
|
-
let endBuffered = null;
|
|
157
|
-
let loopStart = startBufferedState || 0;
|
|
158
|
-
if (startBufferedState) {
|
|
159
|
-
for (let i = startBufferedState; i >= 0; i--) {
|
|
160
|
-
const id = getId(state, i);
|
|
161
|
-
const top2 = positions.get(id);
|
|
162
|
-
if (top2 !== void 0) {
|
|
163
|
-
const length = (_a = lengths.get(id)) != null ? _a : getItemSize(state, i, data[i]);
|
|
164
|
-
const bottom = top2 + length;
|
|
165
|
-
if (bottom > scroll - scrollBufferTop) {
|
|
166
|
-
loopStart = i;
|
|
167
|
-
} else {
|
|
168
|
-
break;
|
|
169
|
-
}
|
|
170
|
-
}
|
|
171
|
-
}
|
|
172
|
-
}
|
|
173
|
-
let top = loopStart > 0 ? positions.get(getId(state, loopStart)) : 0;
|
|
174
|
-
for (let i = loopStart; i < data.length; i++) {
|
|
175
|
-
const id = getId(state, i);
|
|
176
|
-
const length = (_b = lengths.get(id)) != null ? _b : getItemSize(state, i, data[i]);
|
|
177
|
-
if (positions.get(id) !== top) {
|
|
178
|
-
positions.set(id, top);
|
|
179
|
-
}
|
|
180
|
-
if (startNoBuffer === null && top + length > scroll) {
|
|
181
|
-
startNoBuffer = i;
|
|
182
|
-
}
|
|
183
|
-
if (startBuffered === null && top + length > scroll - scrollBufferTop) {
|
|
184
|
-
startBuffered = i;
|
|
185
|
-
}
|
|
186
|
-
if (startNoBuffer !== null) {
|
|
187
|
-
if (top <= scroll + scrollLength) {
|
|
188
|
-
endNoBuffer = i;
|
|
189
|
-
}
|
|
190
|
-
if (top <= scroll + scrollLength + scrollBufferBottom) {
|
|
191
|
-
endBuffered = i;
|
|
192
|
-
} else {
|
|
193
|
-
break;
|
|
194
|
-
}
|
|
195
|
-
}
|
|
196
|
-
top += length;
|
|
197
|
-
}
|
|
198
|
-
Object.assign(state, {
|
|
199
|
-
startBuffered,
|
|
200
|
-
startNoBuffer,
|
|
201
|
-
endBuffered,
|
|
202
|
-
endNoBuffer
|
|
203
|
-
});
|
|
204
|
-
if (startBuffered !== null && endBuffered !== null) {
|
|
205
|
-
const prevNumContainers = ctx.values.get("numContainers");
|
|
206
|
-
let numContainers = prevNumContainers;
|
|
207
|
-
for (let i = startBuffered; i <= endBuffered; i++) {
|
|
208
|
-
let isContained = false;
|
|
209
|
-
for (let j = 0; j < numContainers; j++) {
|
|
210
|
-
const index = peek$(ctx, `containerIndex${j}`);
|
|
211
|
-
if (index === i) {
|
|
212
|
-
isContained = true;
|
|
213
|
-
break;
|
|
214
|
-
}
|
|
215
|
-
}
|
|
216
|
-
if (!isContained) {
|
|
217
|
-
const id = getId(state, i);
|
|
218
|
-
const top2 = positions.get(id) || 0;
|
|
219
|
-
let furthestIndex = -1;
|
|
220
|
-
let furthestDistance = 0;
|
|
221
|
-
for (let u = 0; u < numContainers; u++) {
|
|
222
|
-
const index = peek$(ctx, `containerIndex${u}`);
|
|
223
|
-
if (index < 0) {
|
|
224
|
-
furthestIndex = u;
|
|
225
|
-
break;
|
|
226
|
-
}
|
|
227
|
-
const pos = peek$(ctx, `containerPosition${u}`);
|
|
228
|
-
if (index < startBuffered || index > endBuffered) {
|
|
229
|
-
const distance = Math.abs(pos - top2);
|
|
230
|
-
if (index < 0 || distance > furthestDistance) {
|
|
231
|
-
furthestDistance = distance;
|
|
232
|
-
furthestIndex = u;
|
|
233
|
-
}
|
|
234
|
-
}
|
|
235
|
-
}
|
|
236
|
-
if (furthestIndex >= 0) {
|
|
237
|
-
set$(ctx, `containerIndex${furthestIndex}`, i);
|
|
238
|
-
} else {
|
|
239
|
-
if (__DEV__) {
|
|
240
|
-
console.warn(
|
|
241
|
-
"[legend-list] No container to recycle, consider increasing initialContainers or estimatedItemLength",
|
|
242
|
-
i
|
|
243
|
-
);
|
|
244
|
-
}
|
|
245
|
-
const containerId = numContainers;
|
|
246
|
-
numContainers++;
|
|
247
|
-
set$(ctx, `containerIndex${containerId}`, i);
|
|
248
|
-
set$(ctx, `containerPosition${containerId}`, POSITION_OUT_OF_VIEW);
|
|
249
|
-
}
|
|
250
|
-
}
|
|
251
|
-
}
|
|
252
|
-
if (numContainers !== prevNumContainers) {
|
|
253
|
-
set$(ctx, `numContainers`, numContainers);
|
|
254
|
-
}
|
|
255
|
-
for (let i = 0; i < numContainers; i++) {
|
|
256
|
-
const itemIndex = peek$(ctx, `containerIndex${i}`);
|
|
257
|
-
const item = data[itemIndex];
|
|
258
|
-
if (item) {
|
|
259
|
-
const id = getId(state, itemIndex);
|
|
260
|
-
if (itemIndex < startBuffered || itemIndex > endBuffered) ; else {
|
|
261
|
-
const pos = (_c = positions.get(id)) != null ? _c : -1;
|
|
262
|
-
const prevPos = peek$(ctx, `containerPosition${i}`);
|
|
263
|
-
if (pos >= 0 && pos !== prevPos) {
|
|
264
|
-
set$(ctx, `containerPosition${i}`, pos);
|
|
265
|
-
}
|
|
266
|
-
}
|
|
267
|
-
}
|
|
268
|
-
}
|
|
269
|
-
if (onViewableRangeChanged) {
|
|
270
|
-
if (startNoBuffer !== startNoBufferState || startBuffered !== startBufferedState || endNoBuffer !== endNoBufferState || endBuffered !== endBufferedState) {
|
|
271
|
-
onViewableRangeChanged({
|
|
272
|
-
start: startNoBuffer,
|
|
273
|
-
startBuffered,
|
|
274
|
-
end: endNoBuffer,
|
|
275
|
-
endBuffered,
|
|
276
|
-
items: data.slice(startNoBuffer, endNoBuffer + 1)
|
|
277
|
-
});
|
|
278
|
-
}
|
|
279
|
-
}
|
|
280
|
-
}
|
|
281
|
-
});
|
|
282
|
-
}
|
|
283
|
-
function updateItemSize(state, refScroller, index, length) {
|
|
284
|
-
const {
|
|
285
|
-
props: { data, maintainScrollAtEnd },
|
|
286
|
-
ctx,
|
|
287
|
-
lengths,
|
|
288
|
-
idsInFirstRender,
|
|
289
|
-
isAtBottom
|
|
290
|
-
} = state;
|
|
291
|
-
if (!data) {
|
|
292
|
-
return;
|
|
293
|
-
}
|
|
294
|
-
const id = getId(state, index);
|
|
295
|
-
const wasInFirstRender = idsInFirstRender.has(id);
|
|
296
|
-
const prevLength = lengths.get(id) || (wasInFirstRender ? getItemSize(state, index, data[index]) : 0);
|
|
297
|
-
if (!prevLength || prevLength !== length) {
|
|
298
|
-
lengths.set(id, length);
|
|
299
|
-
addTotalLength(state, length - prevLength);
|
|
300
|
-
if (isAtBottom && maintainScrollAtEnd) {
|
|
301
|
-
requestAnimationFrame(() => {
|
|
302
|
-
var _a;
|
|
303
|
-
(_a = refScroller.current) == null ? void 0 : _a.scrollToEnd({
|
|
304
|
-
animated: true
|
|
305
|
-
});
|
|
306
|
-
});
|
|
307
|
-
}
|
|
308
|
-
if (!state.animFrameScroll && !state.animFrameLayout) {
|
|
309
|
-
state.animFrameLayout = requestAnimationFrame(() => {
|
|
310
|
-
state.animFrameLayout = null;
|
|
311
|
-
if (!state.animFrameScroll) {
|
|
312
|
-
calculateItemsInView(state);
|
|
313
|
-
}
|
|
314
|
-
});
|
|
315
|
-
}
|
|
316
|
-
}
|
|
317
|
-
}
|
|
318
|
-
function checkAtBottom(state) {
|
|
319
|
-
const {
|
|
320
|
-
ctx,
|
|
321
|
-
scrollLength,
|
|
322
|
-
scroll,
|
|
323
|
-
props: { maintainScrollAtEndThreshold, onEndReached, onEndReachedThreshold }
|
|
324
|
-
} = state;
|
|
325
|
-
const totalLength = peek$(ctx, "totalLength");
|
|
326
|
-
const distanceFromEnd = totalLength - scroll - scrollLength;
|
|
327
|
-
state.isAtBottom = distanceFromEnd < scrollLength * maintainScrollAtEndThreshold;
|
|
328
|
-
if (onEndReached && !state.isEndReached) {
|
|
329
|
-
if (distanceFromEnd < onEndReachedThreshold * scrollLength) {
|
|
330
|
-
state.isEndReached = true;
|
|
331
|
-
onEndReached({ distanceFromEnd });
|
|
332
|
-
}
|
|
333
|
-
}
|
|
334
|
-
}
|
|
335
|
-
function handleScrollDebounced(state) {
|
|
336
|
-
calculateItemsInView(state);
|
|
337
|
-
checkAtBottom(state);
|
|
338
|
-
state.animFrameScroll = null;
|
|
339
|
-
}
|
|
340
|
-
function handleScroll(state, onScrollDebounced, event) {
|
|
341
|
-
var _a, _b, _c;
|
|
342
|
-
if (((_b = (_a = event.nativeEvent) == null ? void 0 : _a.contentSize) == null ? void 0 : _b.height) === 0 && ((_c = event.nativeEvent.contentSize) == null ? void 0 : _c.width) === 0) {
|
|
343
|
-
return;
|
|
344
|
-
}
|
|
345
|
-
const { horizontal, onScroll } = state.props;
|
|
346
|
-
state.hasScrolled = true;
|
|
347
|
-
const newScroll = event.nativeEvent.contentOffset[horizontal ? "x" : "y"];
|
|
348
|
-
state.scrollPrevious = state.scroll;
|
|
349
|
-
state.scroll = newScroll;
|
|
350
|
-
if (state && !state.animFrameScroll) {
|
|
351
|
-
state.animFrameScroll = requestAnimationFrame(onScrollDebounced);
|
|
352
|
-
}
|
|
353
|
-
onScroll == null ? void 0 : onScroll(event);
|
|
354
|
-
}
|
|
355
|
-
function onLayout(state, event) {
|
|
356
|
-
const scrollLength = event.nativeEvent.layout[state.props.horizontal ? "width" : "height"];
|
|
357
|
-
state.scrollLength = scrollLength;
|
|
358
|
-
}
|
|
359
|
-
var LeanView = React6__namespace.forwardRef((props, ref) => {
|
|
360
|
-
return React6__namespace.createElement("RCTView", { ...props, ref });
|
|
361
|
-
});
|
|
362
|
-
LeanView.displayName = "RCTView";
|
|
363
60
|
|
|
364
61
|
// src/$View.tsx
|
|
365
62
|
function $View({ $key, $style, ...rest }) {
|
|
@@ -367,27 +64,28 @@ function $View({ $key, $style, ...rest }) {
|
|
|
367
64
|
const style = $style();
|
|
368
65
|
return /* @__PURE__ */ React6__namespace.createElement(LeanView, { style, ...rest });
|
|
369
66
|
}
|
|
370
|
-
function InnerContainer({ id, getRenderedItem
|
|
67
|
+
function InnerContainer({ id, getRenderedItem, recycleItems, ItemSeparatorComponent }) {
|
|
371
68
|
const itemIndex = use$(`containerIndex${id}`);
|
|
372
69
|
const numItems = ItemSeparatorComponent ? use$("numItems") : 0;
|
|
373
70
|
if (itemIndex < 0) {
|
|
374
71
|
return null;
|
|
375
72
|
}
|
|
376
|
-
const renderedItem =
|
|
73
|
+
const renderedItem = getRenderedItem(itemIndex);
|
|
377
74
|
return /* @__PURE__ */ React6__namespace.createElement(React6__namespace.Fragment, { key: recycleItems ? void 0 : itemIndex }, renderedItem, ItemSeparatorComponent && itemIndex < numItems - 1 && ItemSeparatorComponent);
|
|
378
75
|
}
|
|
379
76
|
var Container = ({
|
|
380
77
|
id,
|
|
381
78
|
recycleItems,
|
|
382
79
|
horizontal,
|
|
383
|
-
getRenderedItem
|
|
384
|
-
onLayout
|
|
80
|
+
getRenderedItem,
|
|
81
|
+
onLayout,
|
|
385
82
|
ItemSeparatorComponent
|
|
386
83
|
}) => {
|
|
387
84
|
const ctx = useStateContext();
|
|
388
85
|
const createStyle = () => {
|
|
389
86
|
const position = peek$(ctx, `containerPosition${id}`);
|
|
390
87
|
return horizontal ? {
|
|
88
|
+
flexDirection: "row",
|
|
391
89
|
position: "absolute",
|
|
392
90
|
top: 0,
|
|
393
91
|
bottom: 0,
|
|
@@ -410,7 +108,7 @@ var Container = ({
|
|
|
410
108
|
const index = peek$(ctx, `containerIndex${id}`);
|
|
411
109
|
if (index >= 0) {
|
|
412
110
|
const length = Math.round(event.nativeEvent.layout[horizontal ? "width" : "height"]);
|
|
413
|
-
|
|
111
|
+
onLayout(index, length);
|
|
414
112
|
}
|
|
415
113
|
}
|
|
416
114
|
},
|
|
@@ -418,7 +116,7 @@ var Container = ({
|
|
|
418
116
|
InnerContainer,
|
|
419
117
|
{
|
|
420
118
|
id,
|
|
421
|
-
getRenderedItem
|
|
119
|
+
getRenderedItem,
|
|
422
120
|
recycleItems,
|
|
423
121
|
ItemSeparatorComponent
|
|
424
122
|
}
|
|
@@ -431,8 +129,8 @@ var Containers = React6__namespace.memo(function Containers2({
|
|
|
431
129
|
horizontal,
|
|
432
130
|
recycleItems,
|
|
433
131
|
ItemSeparatorComponent,
|
|
434
|
-
updateItemSize
|
|
435
|
-
getRenderedItem
|
|
132
|
+
updateItemSize,
|
|
133
|
+
getRenderedItem
|
|
436
134
|
}) {
|
|
437
135
|
const ctx = useStateContext();
|
|
438
136
|
const numContainers = use$("numContainers");
|
|
@@ -446,8 +144,8 @@ var Containers = React6__namespace.memo(function Containers2({
|
|
|
446
144
|
key: i,
|
|
447
145
|
recycleItems,
|
|
448
146
|
horizontal,
|
|
449
|
-
getRenderedItem
|
|
450
|
-
onLayout:
|
|
147
|
+
getRenderedItem,
|
|
148
|
+
onLayout: updateItemSize,
|
|
451
149
|
ItemSeparatorComponent
|
|
452
150
|
}
|
|
453
151
|
)
|
|
@@ -485,15 +183,14 @@ var ListComponent = React6__namespace.memo(function ListComponent2({
|
|
|
485
183
|
recycleItems,
|
|
486
184
|
ItemSeparatorComponent,
|
|
487
185
|
alignItemsAtEnd,
|
|
488
|
-
handleScroll
|
|
489
|
-
onLayout
|
|
186
|
+
handleScroll,
|
|
187
|
+
onLayout,
|
|
490
188
|
ListHeaderComponent,
|
|
491
189
|
ListHeaderComponentStyle,
|
|
492
190
|
ListFooterComponent,
|
|
493
191
|
ListFooterComponentStyle,
|
|
494
|
-
getRenderedItem
|
|
495
|
-
updateItemSize
|
|
496
|
-
addTotalLength: addTotalLength2,
|
|
192
|
+
getRenderedItem,
|
|
193
|
+
updateItemSize,
|
|
497
194
|
refScroller,
|
|
498
195
|
...rest
|
|
499
196
|
}) {
|
|
@@ -509,64 +206,37 @@ var ListComponent = React6__namespace.memo(function ListComponent2({
|
|
|
509
206
|
height: "100%"
|
|
510
207
|
} : {}
|
|
511
208
|
],
|
|
512
|
-
onScroll:
|
|
513
|
-
onLayout
|
|
209
|
+
onScroll: handleScroll,
|
|
210
|
+
onLayout,
|
|
514
211
|
horizontal,
|
|
515
212
|
contentOffset: initialContentOffset ? horizontal ? { x: initialContentOffset, y: 0 } : { x: 0, y: initialContentOffset } : void 0,
|
|
516
213
|
ref: refScroller
|
|
517
214
|
},
|
|
518
215
|
alignItemsAtEnd && /* @__PURE__ */ React6__namespace.createElement($View, { $key: "paddingTop", $style: () => ({ height: peek$(ctx, "paddingTop") }) }),
|
|
519
|
-
ListHeaderComponent && /* @__PURE__ */ React6__namespace.createElement(
|
|
520
|
-
reactNative.View,
|
|
521
|
-
{
|
|
522
|
-
style: ListHeaderComponentStyle,
|
|
523
|
-
onLayout: (event) => {
|
|
524
|
-
const size = event.nativeEvent.layout[horizontal ? "width" : "height"];
|
|
525
|
-
const prevSize = peek$(ctx, "headerSize") || 0;
|
|
526
|
-
if (size !== prevSize) {
|
|
527
|
-
set$(ctx, "headerSize", size);
|
|
528
|
-
addTotalLength2(size - prevSize);
|
|
529
|
-
}
|
|
530
|
-
}
|
|
531
|
-
},
|
|
532
|
-
getComponent(ListHeaderComponent)
|
|
533
|
-
),
|
|
216
|
+
ListHeaderComponent && /* @__PURE__ */ React6__namespace.createElement(reactNative.View, { style: ListHeaderComponentStyle }, getComponent(ListHeaderComponent)),
|
|
534
217
|
/* @__PURE__ */ React6__namespace.createElement(
|
|
535
218
|
Containers,
|
|
536
219
|
{
|
|
537
220
|
horizontal,
|
|
538
221
|
recycleItems,
|
|
539
|
-
getRenderedItem
|
|
222
|
+
getRenderedItem,
|
|
540
223
|
ItemSeparatorComponent: ItemSeparatorComponent && getComponent(ItemSeparatorComponent),
|
|
541
|
-
updateItemSize
|
|
224
|
+
updateItemSize
|
|
542
225
|
}
|
|
543
226
|
),
|
|
544
|
-
ListFooterComponent && /* @__PURE__ */ React6__namespace.createElement(
|
|
545
|
-
reactNative.View,
|
|
546
|
-
{
|
|
547
|
-
style: ListFooterComponentStyle,
|
|
548
|
-
onLayout: (event) => {
|
|
549
|
-
const size = event.nativeEvent.layout[horizontal ? "width" : "height"];
|
|
550
|
-
const prevSize = peek$(ctx, "footerSize") || 0;
|
|
551
|
-
if (size !== prevSize) {
|
|
552
|
-
set$(ctx, "footerSize", size);
|
|
553
|
-
addTotalLength2(size - prevSize);
|
|
554
|
-
}
|
|
555
|
-
}
|
|
556
|
-
},
|
|
557
|
-
getComponent(ListFooterComponent)
|
|
558
|
-
)
|
|
227
|
+
ListFooterComponent && /* @__PURE__ */ React6__namespace.createElement(reactNative.View, { style: ListFooterComponentStyle }, getComponent(ListFooterComponent))
|
|
559
228
|
);
|
|
560
229
|
});
|
|
561
230
|
|
|
562
231
|
// src/LegendList.tsx
|
|
232
|
+
var DEFAULT_SCROLL_BUFFER = 0;
|
|
233
|
+
var POSITION_OUT_OF_VIEW = -1e4;
|
|
563
234
|
var LegendList = React6.forwardRef(function LegendList2(props, forwardedRef) {
|
|
564
235
|
return /* @__PURE__ */ React6__namespace.createElement(StateProvider, null, /* @__PURE__ */ React6__namespace.createElement(LegendListInner, { ...props, ref: forwardedRef }));
|
|
565
236
|
});
|
|
566
237
|
var LegendListInner = React6.forwardRef(
|
|
567
|
-
function LegendListInner2(
|
|
238
|
+
function LegendListInner2(props, forwardedRef) {
|
|
568
239
|
var _a, _b;
|
|
569
|
-
const props = applyDefaultProps(props_);
|
|
570
240
|
const {
|
|
571
241
|
data,
|
|
572
242
|
initialScrollIndex,
|
|
@@ -574,14 +244,61 @@ var LegendListInner = React6.forwardRef(
|
|
|
574
244
|
horizontal,
|
|
575
245
|
style: styleProp,
|
|
576
246
|
contentContainerStyle: contentContainerStyleProp,
|
|
247
|
+
initialNumContainers,
|
|
577
248
|
drawDistance,
|
|
249
|
+
recycleItems = true,
|
|
250
|
+
onEndReachedThreshold = 0.5,
|
|
251
|
+
maintainScrollAtEnd = false,
|
|
252
|
+
maintainScrollAtEndThreshold = 0.1,
|
|
253
|
+
alignItemsAtEnd = false,
|
|
254
|
+
onScroll: onScrollProp,
|
|
255
|
+
keyExtractor,
|
|
256
|
+
renderItem,
|
|
257
|
+
estimatedItemSize,
|
|
258
|
+
getEstimatedItemSize,
|
|
259
|
+
onEndReached,
|
|
260
|
+
onViewableRangeChanged,
|
|
578
261
|
...rest
|
|
579
262
|
} = props;
|
|
580
263
|
const ctx = useStateContext();
|
|
581
|
-
const
|
|
264
|
+
const internalRef = React6.useRef(null);
|
|
265
|
+
const refScroller = forwardedRef || internalRef;
|
|
582
266
|
const scrollBuffer = drawDistance != null ? drawDistance : DEFAULT_SCROLL_BUFFER;
|
|
267
|
+
const styleFlattened = reactNative.StyleSheet.flatten(styleProp);
|
|
268
|
+
const style = React6.useMemo(() => styleFlattened, [JSON.stringify(styleProp)]);
|
|
269
|
+
const contentContainerStyleFlattened = reactNative.StyleSheet.flatten(contentContainerStyleProp);
|
|
270
|
+
const contentContainerStyle = React6.useMemo(
|
|
271
|
+
() => contentContainerStyleFlattened,
|
|
272
|
+
[JSON.stringify(contentContainerStyleProp)]
|
|
273
|
+
);
|
|
583
274
|
const refState = React6.useRef();
|
|
584
|
-
const
|
|
275
|
+
const getId = (index) => {
|
|
276
|
+
var _a2;
|
|
277
|
+
const data2 = (_a2 = refState.current) == null ? void 0 : _a2.data;
|
|
278
|
+
if (!data2) {
|
|
279
|
+
return "";
|
|
280
|
+
}
|
|
281
|
+
const ret = index < data2.length ? keyExtractor ? keyExtractor(data2[index], index) : index : null;
|
|
282
|
+
return ret + "";
|
|
283
|
+
};
|
|
284
|
+
const getItemLength = (index, data2) => {
|
|
285
|
+
return getEstimatedItemSize ? getEstimatedItemSize(index, data2) : estimatedItemSize;
|
|
286
|
+
};
|
|
287
|
+
const calculateInitialOffset = () => {
|
|
288
|
+
if (initialScrollIndex) {
|
|
289
|
+
if (getEstimatedItemSize) {
|
|
290
|
+
let offset = 0;
|
|
291
|
+
for (let i = 0; i < initialScrollIndex; i++) {
|
|
292
|
+
offset += getEstimatedItemSize(i, data[i]);
|
|
293
|
+
}
|
|
294
|
+
return offset;
|
|
295
|
+
} else if (estimatedItemSize) {
|
|
296
|
+
return initialScrollIndex * estimatedItemSize;
|
|
297
|
+
}
|
|
298
|
+
}
|
|
299
|
+
return void 0;
|
|
300
|
+
};
|
|
301
|
+
const initialContentOffset = initialScrollOffset != null ? initialScrollOffset : React6.useMemo(calculateInitialOffset, [initialScrollIndex, estimatedItemSize]);
|
|
585
302
|
if (!refState.current) {
|
|
586
303
|
refState.current = {
|
|
587
304
|
lengths: /* @__PURE__ */ new Map(),
|
|
@@ -592,6 +309,7 @@ var LegendListInner = React6.forwardRef(
|
|
|
592
309
|
isStartReached: false,
|
|
593
310
|
isEndReached: false,
|
|
594
311
|
isAtBottom: false,
|
|
312
|
+
data,
|
|
595
313
|
idsInFirstRender: void 0,
|
|
596
314
|
hasScrolled: false,
|
|
597
315
|
scrollLength: reactNative.Dimensions.get("window")[horizontal ? "width" : "height"],
|
|
@@ -599,91 +317,295 @@ var LegendListInner = React6.forwardRef(
|
|
|
599
317
|
startNoBuffer: 0,
|
|
600
318
|
endBuffered: 0,
|
|
601
319
|
endNoBuffer: 0,
|
|
602
|
-
scroll: initialContentOffset || 0
|
|
603
|
-
scrollPrevious: initialContentOffset || 0,
|
|
604
|
-
previousViewableItems: /* @__PURE__ */ new Set(),
|
|
605
|
-
props,
|
|
606
|
-
ctx,
|
|
607
|
-
scrollBuffer
|
|
320
|
+
scroll: initialContentOffset || 0
|
|
608
321
|
};
|
|
609
|
-
refState.current.idsInFirstRender = new Set(
|
|
610
|
-
data.map((_, i) => getId(refState.current, i))
|
|
611
|
-
);
|
|
322
|
+
refState.current.idsInFirstRender = new Set(data.map((_, i) => getId(i)));
|
|
612
323
|
}
|
|
613
|
-
refState.current.
|
|
614
|
-
refState.current.ctx = ctx;
|
|
615
|
-
const styleFlattened = reactNative.StyleSheet.flatten(styleProp);
|
|
616
|
-
const style = React6.useMemo(() => styleFlattened, [JSON.stringify(styleProp)]);
|
|
617
|
-
const contentContainerStyleFlattened = reactNative.StyleSheet.flatten(contentContainerStyleProp);
|
|
618
|
-
const contentContainerStyle = React6.useMemo(
|
|
619
|
-
() => contentContainerStyleFlattened,
|
|
620
|
-
[JSON.stringify(contentContainerStyleProp)]
|
|
621
|
-
);
|
|
622
|
-
const fns = React6.useMemo(
|
|
623
|
-
() => ({
|
|
624
|
-
getRenderedItem: getRenderedItem.bind(void 0, refState.current),
|
|
625
|
-
getId: getId.bind(void 0, refState.current),
|
|
626
|
-
getItemSize: getItemSize.bind(void 0, refState.current),
|
|
627
|
-
calculateItemsInView: calculateItemsInView.bind(void 0, refState.current),
|
|
628
|
-
updateItemSize: updateItemSize.bind(void 0, refState.current, refScroller),
|
|
629
|
-
checkAtBottom: checkAtBottom.bind(void 0, refState.current),
|
|
630
|
-
handleScrollDebounced: handleScrollDebounced.bind(void 0, refState.current),
|
|
631
|
-
onLayout: onLayout.bind(void 0, refState.current),
|
|
632
|
-
addTotalLength: addTotalLength.bind(void 0, refState.current),
|
|
633
|
-
handleScroll: handleScroll.bind(
|
|
634
|
-
void 0,
|
|
635
|
-
refState.current,
|
|
636
|
-
handleScrollDebounced.bind(void 0, refState.current)
|
|
637
|
-
)
|
|
638
|
-
}),
|
|
639
|
-
[]
|
|
640
|
-
);
|
|
641
|
-
const {
|
|
642
|
-
calculateItemsInView: calculateItemsInView2,
|
|
643
|
-
getId: getId2,
|
|
644
|
-
getItemSize: getItemSize2,
|
|
645
|
-
checkAtBottom: checkAtBottom2,
|
|
646
|
-
updateItemSize: updateItemSize2,
|
|
647
|
-
getRenderedItem: getRenderedItem2,
|
|
648
|
-
onLayout: onLayout2,
|
|
649
|
-
handleScroll: handleScroll2,
|
|
650
|
-
addTotalLength: addTotalLength2
|
|
651
|
-
} = fns;
|
|
324
|
+
refState.current.data = data;
|
|
652
325
|
set$(ctx, `numItems`, data.length);
|
|
653
326
|
set$(ctx, `stylePaddingTop`, (_b = (_a = styleFlattened == null ? void 0 : styleFlattened.paddingTop) != null ? _a : contentContainerStyleFlattened == null ? void 0 : contentContainerStyleFlattened.paddingTop) != null ? _b : 0);
|
|
327
|
+
const addTotalSize = (add) => {
|
|
328
|
+
const length = (peek$(ctx, `totalLength`) || 0) + add;
|
|
329
|
+
set$(ctx, `totalLength`, length);
|
|
330
|
+
const screenLength = refState.current.scrollLength;
|
|
331
|
+
if (alignItemsAtEnd) {
|
|
332
|
+
const listPaddingTop = peek$(ctx, `stylePaddingTop`);
|
|
333
|
+
set$(ctx, `paddingTop`, Math.max(0, screenLength - length - listPaddingTop));
|
|
334
|
+
}
|
|
335
|
+
};
|
|
336
|
+
const allocateContainers = React6.useCallback(() => {
|
|
337
|
+
const scrollLength = refState.current.scrollLength;
|
|
338
|
+
const averageItemSize = estimatedItemSize != null ? estimatedItemSize : getEstimatedItemSize == null ? void 0 : getEstimatedItemSize(0, data[0]);
|
|
339
|
+
const numContainers = initialNumContainers || Math.ceil((scrollLength + scrollBuffer * 2) / averageItemSize) + 4;
|
|
340
|
+
for (let i = 0; i < numContainers; i++) {
|
|
341
|
+
set$(ctx, `containerIndex${i}`, -1);
|
|
342
|
+
set$(ctx, `containerPosition${i}`, POSITION_OUT_OF_VIEW);
|
|
343
|
+
}
|
|
344
|
+
set$(ctx, `numContainers`, numContainers);
|
|
345
|
+
}, []);
|
|
346
|
+
const getRenderedItem = React6.useCallback(
|
|
347
|
+
(index) => {
|
|
348
|
+
var _a2;
|
|
349
|
+
const data2 = (_a2 = refState.current) == null ? void 0 : _a2.data;
|
|
350
|
+
if (!data2) {
|
|
351
|
+
return null;
|
|
352
|
+
}
|
|
353
|
+
const renderedItem = renderItem == null ? void 0 : renderItem({
|
|
354
|
+
item: data2[index],
|
|
355
|
+
index
|
|
356
|
+
});
|
|
357
|
+
return renderedItem;
|
|
358
|
+
},
|
|
359
|
+
[renderItem]
|
|
360
|
+
);
|
|
361
|
+
const calculateItemsInView = React6.useCallback(() => {
|
|
362
|
+
reactNative.unstable_batchedUpdates(() => {
|
|
363
|
+
var _a2, _b2, _c;
|
|
364
|
+
const {
|
|
365
|
+
data: data2,
|
|
366
|
+
scrollLength,
|
|
367
|
+
scroll: scrollState,
|
|
368
|
+
startNoBuffer: startNoBufferState,
|
|
369
|
+
startBuffered: startBufferedState,
|
|
370
|
+
endNoBuffer: endNoBufferState,
|
|
371
|
+
endBuffered: endBufferedState
|
|
372
|
+
} = refState.current;
|
|
373
|
+
if (!data2) {
|
|
374
|
+
return;
|
|
375
|
+
}
|
|
376
|
+
const topPad = (peek$(ctx, `stylePaddingTop`) || 0) + (peek$(ctx, `headerSize`) || 0);
|
|
377
|
+
const scroll = scrollState - topPad;
|
|
378
|
+
const { lengths, positions } = refState.current;
|
|
379
|
+
let startNoBuffer = null;
|
|
380
|
+
let startBuffered = null;
|
|
381
|
+
let endNoBuffer = null;
|
|
382
|
+
let endBuffered = null;
|
|
383
|
+
let loopStart = startBufferedState || 0;
|
|
384
|
+
if (startBufferedState) {
|
|
385
|
+
for (let i = startBufferedState; i >= 0; i--) {
|
|
386
|
+
const id = getId(i);
|
|
387
|
+
const top2 = positions.get(id);
|
|
388
|
+
if (top2 !== void 0) {
|
|
389
|
+
const length = (_a2 = lengths.get(id)) != null ? _a2 : getItemLength(i, data2[i]);
|
|
390
|
+
const bottom = top2 + length;
|
|
391
|
+
if (bottom > scroll - scrollBuffer) {
|
|
392
|
+
loopStart = i;
|
|
393
|
+
} else {
|
|
394
|
+
break;
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
}
|
|
398
|
+
}
|
|
399
|
+
let top = loopStart > 0 ? positions.get(getId(loopStart)) : 0;
|
|
400
|
+
for (let i = loopStart; i < data2.length; i++) {
|
|
401
|
+
const id = getId(i);
|
|
402
|
+
const length = (_b2 = lengths.get(id)) != null ? _b2 : getItemLength(i, data2[i]);
|
|
403
|
+
if (positions.get(id) !== top) {
|
|
404
|
+
positions.set(id, top);
|
|
405
|
+
}
|
|
406
|
+
if (startNoBuffer === null && top + length > scroll) {
|
|
407
|
+
startNoBuffer = i;
|
|
408
|
+
}
|
|
409
|
+
if (startBuffered === null && top + length > scroll - scrollBuffer) {
|
|
410
|
+
startBuffered = i;
|
|
411
|
+
}
|
|
412
|
+
if (startNoBuffer !== null) {
|
|
413
|
+
if (top <= scroll + scrollLength) {
|
|
414
|
+
endNoBuffer = i;
|
|
415
|
+
}
|
|
416
|
+
if (top <= scroll + scrollLength + scrollBuffer) {
|
|
417
|
+
endBuffered = i;
|
|
418
|
+
} else {
|
|
419
|
+
break;
|
|
420
|
+
}
|
|
421
|
+
}
|
|
422
|
+
top += length;
|
|
423
|
+
}
|
|
424
|
+
Object.assign(refState.current, {
|
|
425
|
+
startBuffered,
|
|
426
|
+
startNoBuffer,
|
|
427
|
+
endBuffered,
|
|
428
|
+
endNoBuffer
|
|
429
|
+
});
|
|
430
|
+
if (startBuffered !== null && endBuffered !== null) {
|
|
431
|
+
const prevNumContainers = ctx.values.get("numContainers");
|
|
432
|
+
let numContainers = prevNumContainers;
|
|
433
|
+
for (let i = startBuffered; i <= endBuffered; i++) {
|
|
434
|
+
let isContained = false;
|
|
435
|
+
for (let j = 0; j < numContainers; j++) {
|
|
436
|
+
const index = peek$(ctx, `containerIndex${j}`);
|
|
437
|
+
if (index === i) {
|
|
438
|
+
isContained = true;
|
|
439
|
+
break;
|
|
440
|
+
}
|
|
441
|
+
}
|
|
442
|
+
if (!isContained) {
|
|
443
|
+
let didRecycle = false;
|
|
444
|
+
for (let u = 0; u < numContainers; u++) {
|
|
445
|
+
const index = peek$(ctx, `containerIndex${u}`);
|
|
446
|
+
if (index < startBuffered || index > endBuffered) {
|
|
447
|
+
set$(ctx, `containerIndex${u}`, i);
|
|
448
|
+
didRecycle = true;
|
|
449
|
+
break;
|
|
450
|
+
}
|
|
451
|
+
}
|
|
452
|
+
if (!didRecycle) {
|
|
453
|
+
if (__DEV__) {
|
|
454
|
+
console.warn(
|
|
455
|
+
"[legend-list] No container to recycle, consider increasing initialContainers or estimatedItemSize",
|
|
456
|
+
i
|
|
457
|
+
);
|
|
458
|
+
}
|
|
459
|
+
const id = numContainers;
|
|
460
|
+
numContainers++;
|
|
461
|
+
set$(ctx, `containerIndex${id}`, i);
|
|
462
|
+
set$(ctx, `containerPosition${id}`, POSITION_OUT_OF_VIEW);
|
|
463
|
+
}
|
|
464
|
+
}
|
|
465
|
+
}
|
|
466
|
+
if (numContainers !== prevNumContainers) {
|
|
467
|
+
set$(ctx, `numContainers`, numContainers);
|
|
468
|
+
}
|
|
469
|
+
for (let i = 0; i < numContainers; i++) {
|
|
470
|
+
const itemIndex = peek$(ctx, `containerIndex${i}`);
|
|
471
|
+
const item = data2[itemIndex];
|
|
472
|
+
if (item) {
|
|
473
|
+
const id = getId(itemIndex);
|
|
474
|
+
if (itemIndex < startBuffered || itemIndex > endBuffered) {
|
|
475
|
+
set$(ctx, `containerPosition${i}`, POSITION_OUT_OF_VIEW);
|
|
476
|
+
} else {
|
|
477
|
+
const pos = (_c = positions.get(id)) != null ? _c : -1;
|
|
478
|
+
const prevPos = peek$(ctx, `containerPosition${i}`);
|
|
479
|
+
if (pos >= 0 && pos !== prevPos) {
|
|
480
|
+
set$(ctx, `containerPosition${i}`, pos);
|
|
481
|
+
}
|
|
482
|
+
}
|
|
483
|
+
}
|
|
484
|
+
}
|
|
485
|
+
if (onViewableRangeChanged) {
|
|
486
|
+
if (startNoBuffer !== startNoBufferState || startBuffered !== startBufferedState || endNoBuffer !== endNoBufferState || endBuffered !== endBufferedState) {
|
|
487
|
+
onViewableRangeChanged({
|
|
488
|
+
start: startNoBuffer,
|
|
489
|
+
startBuffered,
|
|
490
|
+
end: endNoBuffer,
|
|
491
|
+
endBuffered,
|
|
492
|
+
items: data2.slice(startNoBuffer, endNoBuffer + 1)
|
|
493
|
+
});
|
|
494
|
+
}
|
|
495
|
+
}
|
|
496
|
+
}
|
|
497
|
+
});
|
|
498
|
+
}, [data]);
|
|
654
499
|
React6.useMemo(() => {
|
|
655
500
|
var _a2, _b2;
|
|
656
|
-
allocateContainers(
|
|
657
|
-
|
|
501
|
+
allocateContainers();
|
|
502
|
+
calculateItemsInView();
|
|
658
503
|
const lengths = (_a2 = refState.current) == null ? void 0 : _a2.lengths;
|
|
659
|
-
let totalLength =
|
|
504
|
+
let totalLength = 0;
|
|
660
505
|
for (let i = 0; i < data.length; i++) {
|
|
661
|
-
const id =
|
|
662
|
-
totalLength += (_b2 = lengths.get(id)) != null ? _b2 :
|
|
506
|
+
const id = getId(i);
|
|
507
|
+
totalLength += (_b2 = lengths.get(id)) != null ? _b2 : getItemLength(i, data[i]);
|
|
663
508
|
}
|
|
664
|
-
|
|
509
|
+
addTotalSize(totalLength);
|
|
665
510
|
}, []);
|
|
511
|
+
const checkAtBottom = () => {
|
|
512
|
+
var _a2;
|
|
513
|
+
const { scrollLength, scroll } = refState.current;
|
|
514
|
+
const totalLength = peek$(ctx, "totalLength");
|
|
515
|
+
const distanceFromEnd = totalLength - scroll - scrollLength;
|
|
516
|
+
if (refState.current) {
|
|
517
|
+
refState.current.isAtBottom = distanceFromEnd < scrollLength * maintainScrollAtEndThreshold;
|
|
518
|
+
}
|
|
519
|
+
if (onEndReached && !((_a2 = refState.current) == null ? void 0 : _a2.isEndReached)) {
|
|
520
|
+
if (distanceFromEnd < onEndReachedThreshold * scrollLength) {
|
|
521
|
+
if (refState.current) {
|
|
522
|
+
refState.current.isEndReached = true;
|
|
523
|
+
}
|
|
524
|
+
onEndReached({ distanceFromEnd });
|
|
525
|
+
}
|
|
526
|
+
}
|
|
527
|
+
};
|
|
666
528
|
React6.useMemo(() => {
|
|
667
529
|
if (refState.current) {
|
|
668
530
|
refState.current.isEndReached = false;
|
|
669
531
|
}
|
|
670
|
-
|
|
671
|
-
|
|
532
|
+
calculateItemsInView();
|
|
533
|
+
checkAtBottom();
|
|
672
534
|
}, [data]);
|
|
535
|
+
const updateItemSize = React6.useCallback((index, length) => {
|
|
536
|
+
var _a2, _b2, _c, _d;
|
|
537
|
+
const data2 = (_a2 = refState.current) == null ? void 0 : _a2.data;
|
|
538
|
+
if (!data2) {
|
|
539
|
+
return;
|
|
540
|
+
}
|
|
541
|
+
const lengths = (_b2 = refState.current) == null ? void 0 : _b2.lengths;
|
|
542
|
+
const id = getId(index);
|
|
543
|
+
const wasInFirstRender = (_c = refState.current) == null ? void 0 : _c.idsInFirstRender.has(id);
|
|
544
|
+
const prevLength = lengths.get(id) || (wasInFirstRender ? getItemLength(index, data2[index]) : 0);
|
|
545
|
+
if (!prevLength || prevLength !== length) {
|
|
546
|
+
lengths.set(id, length);
|
|
547
|
+
addTotalSize(length - prevLength);
|
|
548
|
+
if (((_d = refState.current) == null ? void 0 : _d.isAtBottom) && maintainScrollAtEnd) {
|
|
549
|
+
requestAnimationFrame(() => {
|
|
550
|
+
var _a3;
|
|
551
|
+
(_a3 = refScroller.current) == null ? void 0 : _a3.scrollToEnd({
|
|
552
|
+
animated: true
|
|
553
|
+
});
|
|
554
|
+
});
|
|
555
|
+
}
|
|
556
|
+
const state = refState.current;
|
|
557
|
+
if (!state.animFrameScroll && !state.animFrameLayout) {
|
|
558
|
+
state.animFrameLayout = requestAnimationFrame(() => {
|
|
559
|
+
state.animFrameLayout = null;
|
|
560
|
+
calculateItemsInView();
|
|
561
|
+
});
|
|
562
|
+
}
|
|
563
|
+
}
|
|
564
|
+
}, []);
|
|
565
|
+
const handleScrollDebounced = React6.useCallback(() => {
|
|
566
|
+
calculateItemsInView();
|
|
567
|
+
checkAtBottom();
|
|
568
|
+
if (refState.current) {
|
|
569
|
+
refState.current.animFrameScroll = null;
|
|
570
|
+
}
|
|
571
|
+
}, []);
|
|
572
|
+
const onLayout = React6.useCallback((event) => {
|
|
573
|
+
const scrollLength = event.nativeEvent.layout[horizontal ? "width" : "height"];
|
|
574
|
+
refState.current.scrollLength = scrollLength;
|
|
575
|
+
}, []);
|
|
576
|
+
const handleScroll = React6.useCallback(
|
|
577
|
+
(event, fromSelf) => {
|
|
578
|
+
var _a2, _b2, _c;
|
|
579
|
+
if (((_b2 = (_a2 = event.nativeEvent) == null ? void 0 : _a2.contentSize) == null ? void 0 : _b2.height) === 0 && ((_c = event.nativeEvent.contentSize) == null ? void 0 : _c.width) === 0) {
|
|
580
|
+
return;
|
|
581
|
+
}
|
|
582
|
+
refState.current.hasScrolled = true;
|
|
583
|
+
const newScroll = event.nativeEvent.contentOffset[horizontal ? "x" : "y"];
|
|
584
|
+
refState.current.scroll = newScroll;
|
|
585
|
+
if (refState.current && !refState.current.animFrameScroll) {
|
|
586
|
+
refState.current.animFrameScroll = requestAnimationFrame(handleScrollDebounced);
|
|
587
|
+
}
|
|
588
|
+
if (!fromSelf) {
|
|
589
|
+
onScrollProp == null ? void 0 : onScrollProp(event);
|
|
590
|
+
}
|
|
591
|
+
},
|
|
592
|
+
[]
|
|
593
|
+
);
|
|
673
594
|
return /* @__PURE__ */ React6__namespace.createElement(
|
|
674
595
|
ListComponent,
|
|
675
596
|
{
|
|
676
597
|
...rest,
|
|
677
|
-
addTotalLength: addTotalLength2,
|
|
678
598
|
contentContainerStyle,
|
|
679
599
|
style,
|
|
680
600
|
horizontal,
|
|
681
601
|
refScroller,
|
|
682
602
|
initialContentOffset,
|
|
683
|
-
getRenderedItem
|
|
684
|
-
updateItemSize
|
|
685
|
-
handleScroll
|
|
686
|
-
onLayout
|
|
603
|
+
getRenderedItem,
|
|
604
|
+
updateItemSize,
|
|
605
|
+
handleScroll,
|
|
606
|
+
onLayout,
|
|
607
|
+
recycleItems,
|
|
608
|
+
alignItemsAtEnd
|
|
687
609
|
}
|
|
688
610
|
);
|
|
689
611
|
}
|