@tanstack/solid-virtual 3.0.0-beta.23 → 3.0.0-beta.26
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/build/lib/index.d.ts +4 -0
- package/build/lib/index.esm.js +72 -0
- package/build/lib/index.esm.js.map +1 -0
- package/build/{cjs/solid-virtual/src → lib}/index.js +14 -26
- package/build/lib/index.js.map +1 -0
- package/build/lib/index.mjs +72 -0
- package/build/lib/index.mjs.map +1 -0
- package/build/umd/index.development.js +53 -169
- package/build/umd/index.development.js.map +1 -1
- package/build/umd/index.production.js +12 -2
- package/build/umd/index.production.js.map +1 -1
- package/package.json +21 -10
- package/src/index.tsx +76 -51
- package/build/cjs/solid-virtual/src/index.js.map +0 -1
- package/build/cjs/virtual-core/build/esm/index.js +0 -681
- package/build/cjs/virtual-core/build/esm/index.js.map +0 -1
- package/build/esm/index.js +0 -732
- package/build/esm/index.js.map +0 -1
- package/build/stats.html +0 -2689
- package/build/stats.json +0 -104
- package/build/types/index.d.ts +0 -17
package/build/esm/index.js
DELETED
|
@@ -1,732 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* solid-virtual
|
|
3
|
-
*
|
|
4
|
-
* Copyright (c) TanStack
|
|
5
|
-
*
|
|
6
|
-
* This source code is licensed under the MIT license found in the
|
|
7
|
-
* LICENSE.md file in the root directory of this source tree.
|
|
8
|
-
*
|
|
9
|
-
* @license MIT
|
|
10
|
-
*/
|
|
11
|
-
import { mergeProps, createSignal, onMount, onCleanup, createComputed } from 'solid-js';
|
|
12
|
-
import { createStore, reconcile } from 'solid-js/store';
|
|
13
|
-
|
|
14
|
-
/**
|
|
15
|
-
* virtual-core
|
|
16
|
-
*
|
|
17
|
-
* Copyright (c) TanStack
|
|
18
|
-
*
|
|
19
|
-
* This source code is licensed under the MIT license found in the
|
|
20
|
-
* LICENSE.md file in the root directory of this source tree.
|
|
21
|
-
*
|
|
22
|
-
* @license MIT
|
|
23
|
-
*/
|
|
24
|
-
function memo(getDeps, fn, opts) {
|
|
25
|
-
let deps = [];
|
|
26
|
-
let result;
|
|
27
|
-
return () => {
|
|
28
|
-
let depTime;
|
|
29
|
-
if (opts.key && opts.debug != null && opts.debug()) depTime = Date.now();
|
|
30
|
-
const newDeps = getDeps();
|
|
31
|
-
const depsChanged = newDeps.length !== deps.length || newDeps.some((dep, index) => deps[index] !== dep);
|
|
32
|
-
|
|
33
|
-
if (!depsChanged) {
|
|
34
|
-
return result;
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
deps = newDeps;
|
|
38
|
-
let resultTime;
|
|
39
|
-
if (opts.key && opts.debug != null && opts.debug()) resultTime = Date.now();
|
|
40
|
-
result = fn(...newDeps);
|
|
41
|
-
opts == null ? void 0 : opts.onChange == null ? void 0 : opts.onChange(result);
|
|
42
|
-
|
|
43
|
-
if (opts.key && opts.debug != null && opts.debug()) {
|
|
44
|
-
const depEndTime = Math.round((Date.now() - depTime) * 100) / 100;
|
|
45
|
-
const resultEndTime = Math.round((Date.now() - resultTime) * 100) / 100;
|
|
46
|
-
const resultFpsPercentage = resultEndTime / 16;
|
|
47
|
-
|
|
48
|
-
const pad = (str, num) => {
|
|
49
|
-
str = String(str);
|
|
50
|
-
|
|
51
|
-
while (str.length < num) {
|
|
52
|
-
str = ' ' + str;
|
|
53
|
-
}
|
|
54
|
-
|
|
55
|
-
return str;
|
|
56
|
-
};
|
|
57
|
-
|
|
58
|
-
console.info("%c\u23F1 " + pad(resultEndTime, 5) + " /" + pad(depEndTime, 5) + " ms", "\n font-size: .6rem;\n font-weight: bold;\n color: hsl(" + Math.max(0, Math.min(120 - 120 * resultFpsPercentage, 120)) + "deg 100% 31%);", opts == null ? void 0 : opts.key);
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
return result;
|
|
62
|
-
};
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
//
|
|
66
|
-
const defaultKeyExtractor = index => index;
|
|
67
|
-
const defaultRangeExtractor = range => {
|
|
68
|
-
const start = Math.max(range.startIndex - range.overscan, 0);
|
|
69
|
-
const end = Math.min(range.endIndex + range.overscan, range.count - 1);
|
|
70
|
-
const arr = [];
|
|
71
|
-
|
|
72
|
-
for (let i = start; i <= end; i++) {
|
|
73
|
-
arr.push(i);
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
return arr;
|
|
77
|
-
};
|
|
78
|
-
|
|
79
|
-
const memoRectCallback = (instance, cb) => {
|
|
80
|
-
let prev = {
|
|
81
|
-
height: -1,
|
|
82
|
-
width: -1
|
|
83
|
-
};
|
|
84
|
-
return rect => {
|
|
85
|
-
if (instance.options.horizontal ? rect.width !== prev.width : rect.height !== prev.height) {
|
|
86
|
-
cb(rect);
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
prev = rect;
|
|
90
|
-
};
|
|
91
|
-
};
|
|
92
|
-
|
|
93
|
-
const observeElementRect = (instance, cb) => {
|
|
94
|
-
const observer = new ResizeObserver(entries => {
|
|
95
|
-
var _entries$, _entries$2;
|
|
96
|
-
|
|
97
|
-
cb({
|
|
98
|
-
width: (_entries$ = entries[0]) == null ? void 0 : _entries$.contentRect.width,
|
|
99
|
-
height: (_entries$2 = entries[0]) == null ? void 0 : _entries$2.contentRect.height
|
|
100
|
-
});
|
|
101
|
-
});
|
|
102
|
-
|
|
103
|
-
if (!instance.scrollElement) {
|
|
104
|
-
return;
|
|
105
|
-
}
|
|
106
|
-
|
|
107
|
-
cb(instance.scrollElement.getBoundingClientRect());
|
|
108
|
-
observer.observe(instance.scrollElement);
|
|
109
|
-
return () => {
|
|
110
|
-
observer.unobserve(instance.scrollElement);
|
|
111
|
-
};
|
|
112
|
-
};
|
|
113
|
-
const observeWindowRect = (instance, cb) => {
|
|
114
|
-
const memoizedCallback = memoRectCallback(instance, cb);
|
|
115
|
-
|
|
116
|
-
const onResize = () => memoizedCallback({
|
|
117
|
-
width: instance.scrollElement.innerWidth,
|
|
118
|
-
height: instance.scrollElement.innerHeight
|
|
119
|
-
});
|
|
120
|
-
|
|
121
|
-
if (!instance.scrollElement) {
|
|
122
|
-
return;
|
|
123
|
-
}
|
|
124
|
-
|
|
125
|
-
onResize();
|
|
126
|
-
instance.scrollElement.addEventListener('resize', onResize, {
|
|
127
|
-
capture: false,
|
|
128
|
-
passive: true
|
|
129
|
-
});
|
|
130
|
-
return () => {
|
|
131
|
-
instance.scrollElement.removeEventListener('resize', onResize);
|
|
132
|
-
};
|
|
133
|
-
};
|
|
134
|
-
const scrollProps = {
|
|
135
|
-
element: ['scrollLeft', 'scrollTop'],
|
|
136
|
-
window: ['scrollX', 'scrollY']
|
|
137
|
-
};
|
|
138
|
-
|
|
139
|
-
const createOffsetObserver = mode => {
|
|
140
|
-
return (instance, cb) => {
|
|
141
|
-
if (!instance.scrollElement) {
|
|
142
|
-
return;
|
|
143
|
-
}
|
|
144
|
-
|
|
145
|
-
const propX = scrollProps[mode][0];
|
|
146
|
-
const propY = scrollProps[mode][1];
|
|
147
|
-
let prevX = instance.scrollElement[propX];
|
|
148
|
-
let prevY = instance.scrollElement[propY];
|
|
149
|
-
|
|
150
|
-
const scroll = () => {
|
|
151
|
-
const offset = instance.scrollElement[instance.options.horizontal ? propX : propY];
|
|
152
|
-
cb(Math.max(0, offset - instance.options.scrollMargin));
|
|
153
|
-
};
|
|
154
|
-
|
|
155
|
-
scroll();
|
|
156
|
-
|
|
157
|
-
const onScroll = e => {
|
|
158
|
-
const target = e.currentTarget;
|
|
159
|
-
const scrollX = target[propX];
|
|
160
|
-
const scrollY = target[propY];
|
|
161
|
-
|
|
162
|
-
if (instance.options.horizontal ? prevX - scrollX : prevY - scrollY) {
|
|
163
|
-
scroll();
|
|
164
|
-
}
|
|
165
|
-
|
|
166
|
-
prevX = scrollX;
|
|
167
|
-
prevY = scrollY;
|
|
168
|
-
};
|
|
169
|
-
|
|
170
|
-
instance.scrollElement.addEventListener('scroll', onScroll, {
|
|
171
|
-
capture: false,
|
|
172
|
-
passive: true
|
|
173
|
-
});
|
|
174
|
-
return () => {
|
|
175
|
-
instance.scrollElement.removeEventListener('scroll', onScroll);
|
|
176
|
-
};
|
|
177
|
-
};
|
|
178
|
-
};
|
|
179
|
-
|
|
180
|
-
const observeElementOffset = createOffsetObserver('element');
|
|
181
|
-
const observeWindowOffset = createOffsetObserver('window');
|
|
182
|
-
const measureElement = (element, instance) => {
|
|
183
|
-
return Math.round(element.getBoundingClientRect()[instance.options.horizontal ? 'width' : 'height']);
|
|
184
|
-
};
|
|
185
|
-
const windowScroll = (offset, _ref, instance) => {
|
|
186
|
-
var _instance$scrollEleme;
|
|
187
|
-
|
|
188
|
-
let {
|
|
189
|
-
canSmooth,
|
|
190
|
-
sync
|
|
191
|
-
} = _ref;
|
|
192
|
-
const toOffset = sync ? offset : offset + instance.options.scrollMargin;
|
|
193
|
-
(_instance$scrollEleme = instance.scrollElement) == null ? void 0 : _instance$scrollEleme.scrollTo == null ? void 0 : _instance$scrollEleme.scrollTo({
|
|
194
|
-
[instance.options.horizontal ? 'left' : 'top']: toOffset,
|
|
195
|
-
behavior: canSmooth ? 'smooth' : undefined
|
|
196
|
-
});
|
|
197
|
-
};
|
|
198
|
-
const elementScroll = (offset, _ref2, instance) => {
|
|
199
|
-
var _instance$scrollEleme2;
|
|
200
|
-
|
|
201
|
-
let {
|
|
202
|
-
canSmooth,
|
|
203
|
-
sync
|
|
204
|
-
} = _ref2;
|
|
205
|
-
const toOffset = sync ? offset : offset + instance.options.scrollMargin;
|
|
206
|
-
(_instance$scrollEleme2 = instance.scrollElement) == null ? void 0 : _instance$scrollEleme2.scrollTo == null ? void 0 : _instance$scrollEleme2.scrollTo({
|
|
207
|
-
[instance.options.horizontal ? 'left' : 'top']: toOffset,
|
|
208
|
-
behavior: canSmooth ? 'smooth' : undefined
|
|
209
|
-
});
|
|
210
|
-
};
|
|
211
|
-
class Virtualizer {
|
|
212
|
-
constructor(_opts) {
|
|
213
|
-
var _this = this;
|
|
214
|
-
|
|
215
|
-
this.unsubs = [];
|
|
216
|
-
this.scrollElement = null;
|
|
217
|
-
this.isScrolling = false;
|
|
218
|
-
this.isScrollingTimeoutId = null;
|
|
219
|
-
this.measurementsCache = [];
|
|
220
|
-
this.itemMeasurementsCache = {};
|
|
221
|
-
this.pendingMeasuredCacheIndexes = [];
|
|
222
|
-
this.scrollDelta = 0;
|
|
223
|
-
this.measureElementCache = {};
|
|
224
|
-
|
|
225
|
-
this.getResizeObserver = (() => {
|
|
226
|
-
let _ro = null;
|
|
227
|
-
return () => {
|
|
228
|
-
if (_ro) {
|
|
229
|
-
return _ro;
|
|
230
|
-
} else if (typeof ResizeObserver !== 'undefined') {
|
|
231
|
-
return _ro = new ResizeObserver(entries => {
|
|
232
|
-
entries.forEach(entry => {
|
|
233
|
-
this._measureElement(entry.target, false);
|
|
234
|
-
});
|
|
235
|
-
});
|
|
236
|
-
} else {
|
|
237
|
-
return null;
|
|
238
|
-
}
|
|
239
|
-
};
|
|
240
|
-
})();
|
|
241
|
-
|
|
242
|
-
this.range = {
|
|
243
|
-
startIndex: 0,
|
|
244
|
-
endIndex: 0
|
|
245
|
-
};
|
|
246
|
-
|
|
247
|
-
this.setOptions = opts => {
|
|
248
|
-
Object.entries(opts).forEach(_ref3 => {
|
|
249
|
-
let [key, value] = _ref3;
|
|
250
|
-
if (typeof value === 'undefined') delete opts[key];
|
|
251
|
-
});
|
|
252
|
-
this.options = {
|
|
253
|
-
debug: false,
|
|
254
|
-
initialOffset: 0,
|
|
255
|
-
overscan: 1,
|
|
256
|
-
paddingStart: 0,
|
|
257
|
-
paddingEnd: 0,
|
|
258
|
-
scrollPaddingStart: 0,
|
|
259
|
-
scrollPaddingEnd: 0,
|
|
260
|
-
horizontal: false,
|
|
261
|
-
getItemKey: defaultKeyExtractor,
|
|
262
|
-
rangeExtractor: defaultRangeExtractor,
|
|
263
|
-
enableSmoothScroll: true,
|
|
264
|
-
onChange: () => {},
|
|
265
|
-
measureElement,
|
|
266
|
-
initialRect: {
|
|
267
|
-
width: 0,
|
|
268
|
-
height: 0
|
|
269
|
-
},
|
|
270
|
-
scrollMargin: 0,
|
|
271
|
-
scrollingDelay: 150,
|
|
272
|
-
indexAttribute: 'data-index',
|
|
273
|
-
...opts
|
|
274
|
-
};
|
|
275
|
-
};
|
|
276
|
-
|
|
277
|
-
this.notify = () => {
|
|
278
|
-
var _this$options$onChang, _this$options;
|
|
279
|
-
|
|
280
|
-
(_this$options$onChang = (_this$options = this.options).onChange) == null ? void 0 : _this$options$onChang.call(_this$options, this);
|
|
281
|
-
};
|
|
282
|
-
|
|
283
|
-
this.cleanup = () => {
|
|
284
|
-
this.unsubs.filter(Boolean).forEach(d => d());
|
|
285
|
-
this.unsubs = [];
|
|
286
|
-
this.scrollElement = null;
|
|
287
|
-
};
|
|
288
|
-
|
|
289
|
-
this._didMount = () => {
|
|
290
|
-
return () => {
|
|
291
|
-
var _this$getResizeObserv;
|
|
292
|
-
|
|
293
|
-
(_this$getResizeObserv = this.getResizeObserver()) == null ? void 0 : _this$getResizeObserv.disconnect();
|
|
294
|
-
this.measureElementCache = {};
|
|
295
|
-
this.cleanup();
|
|
296
|
-
};
|
|
297
|
-
};
|
|
298
|
-
|
|
299
|
-
this._willUpdate = () => {
|
|
300
|
-
const scrollElement = this.options.getScrollElement();
|
|
301
|
-
|
|
302
|
-
if (this.scrollElement !== scrollElement) {
|
|
303
|
-
this.cleanup();
|
|
304
|
-
this.scrollElement = scrollElement;
|
|
305
|
-
|
|
306
|
-
this._scrollToOffset(this.scrollOffset, {
|
|
307
|
-
canSmooth: false,
|
|
308
|
-
sync: true,
|
|
309
|
-
requested: false
|
|
310
|
-
});
|
|
311
|
-
|
|
312
|
-
this.unsubs.push(this.options.observeElementRect(this, rect => {
|
|
313
|
-
this.scrollRect = rect;
|
|
314
|
-
this.calculateRange();
|
|
315
|
-
}));
|
|
316
|
-
this.unsubs.push(this.options.observeElementOffset(this, offset => {
|
|
317
|
-
if (this.isScrollingTimeoutId !== null) {
|
|
318
|
-
clearTimeout(this.isScrollingTimeoutId);
|
|
319
|
-
this.isScrollingTimeoutId = null;
|
|
320
|
-
}
|
|
321
|
-
|
|
322
|
-
if (this.scrollOffset !== offset) {
|
|
323
|
-
this.scrollOffset = offset;
|
|
324
|
-
this.isScrolling = true;
|
|
325
|
-
this.scrollDelta = 0;
|
|
326
|
-
this.isScrollingTimeoutId = setTimeout(() => {
|
|
327
|
-
this.isScrollingTimeoutId = null;
|
|
328
|
-
this.isScrolling = false;
|
|
329
|
-
this.notify();
|
|
330
|
-
}, this.options.scrollingDelay);
|
|
331
|
-
} else {
|
|
332
|
-
this.isScrolling = false;
|
|
333
|
-
this.scrollDelta = 0;
|
|
334
|
-
}
|
|
335
|
-
|
|
336
|
-
this.calculateRange();
|
|
337
|
-
}));
|
|
338
|
-
} else if (!this.isScrolling) {
|
|
339
|
-
this.calculateRange();
|
|
340
|
-
}
|
|
341
|
-
};
|
|
342
|
-
|
|
343
|
-
this.getSize = () => {
|
|
344
|
-
return this.scrollRect[this.options.horizontal ? 'width' : 'height'];
|
|
345
|
-
};
|
|
346
|
-
|
|
347
|
-
this.getMeasurements = memo(() => [this.options.count, this.options.paddingStart, this.options.getItemKey, this.itemMeasurementsCache], (count, paddingStart, getItemKey, measurementsCache) => {
|
|
348
|
-
const min = this.pendingMeasuredCacheIndexes.length > 0 ? Math.min(...this.pendingMeasuredCacheIndexes) : 0;
|
|
349
|
-
this.pendingMeasuredCacheIndexes = [];
|
|
350
|
-
const measurements = this.measurementsCache.slice(0, min);
|
|
351
|
-
|
|
352
|
-
for (let i = min; i < count; i++) {
|
|
353
|
-
const key = getItemKey(i);
|
|
354
|
-
const measuredSize = measurementsCache[key];
|
|
355
|
-
const start = measurements[i - 1] ? measurements[i - 1].end : paddingStart;
|
|
356
|
-
const size = typeof measuredSize === 'number' ? measuredSize : this.options.estimateSize(i);
|
|
357
|
-
const end = start + size;
|
|
358
|
-
measurements[i] = {
|
|
359
|
-
index: i,
|
|
360
|
-
start,
|
|
361
|
-
size,
|
|
362
|
-
end,
|
|
363
|
-
key
|
|
364
|
-
};
|
|
365
|
-
}
|
|
366
|
-
|
|
367
|
-
this.measurementsCache = measurements;
|
|
368
|
-
return measurements;
|
|
369
|
-
}, {
|
|
370
|
-
key: process.env.NODE_ENV !== 'production' && 'getMeasurements',
|
|
371
|
-
debug: () => this.options.debug
|
|
372
|
-
});
|
|
373
|
-
this.calculateRange = memo(() => [this.getMeasurements(), this.getSize(), this.scrollOffset], (measurements, outerSize, scrollOffset) => {
|
|
374
|
-
const range = calculateRange({
|
|
375
|
-
measurements,
|
|
376
|
-
outerSize,
|
|
377
|
-
scrollOffset
|
|
378
|
-
});
|
|
379
|
-
|
|
380
|
-
if (range.startIndex !== this.range.startIndex || range.endIndex !== this.range.endIndex) {
|
|
381
|
-
this.range = range;
|
|
382
|
-
this.notify();
|
|
383
|
-
}
|
|
384
|
-
|
|
385
|
-
return this.range;
|
|
386
|
-
}, {
|
|
387
|
-
key: process.env.NODE_ENV !== 'production' && 'calculateRange',
|
|
388
|
-
debug: () => this.options.debug
|
|
389
|
-
});
|
|
390
|
-
this.getIndexes = memo(() => [this.options.rangeExtractor, this.range, this.options.overscan, this.options.count], (rangeExtractor, range, overscan, count) => {
|
|
391
|
-
return rangeExtractor({ ...range,
|
|
392
|
-
overscan,
|
|
393
|
-
count: count
|
|
394
|
-
});
|
|
395
|
-
}, {
|
|
396
|
-
key: process.env.NODE_ENV !== 'production' && 'getIndexes',
|
|
397
|
-
debug: () => this.options.debug
|
|
398
|
-
});
|
|
399
|
-
|
|
400
|
-
this.indexFromElement = node => {
|
|
401
|
-
const attributeName = this.options.indexAttribute;
|
|
402
|
-
const indexStr = node.getAttribute(attributeName);
|
|
403
|
-
|
|
404
|
-
if (!indexStr) {
|
|
405
|
-
console.warn("Missing attribute name '" + attributeName + "={index}' on measured element.");
|
|
406
|
-
return -1;
|
|
407
|
-
}
|
|
408
|
-
|
|
409
|
-
return parseInt(indexStr, 10);
|
|
410
|
-
};
|
|
411
|
-
|
|
412
|
-
this._measureElement = (node, _sync) => {
|
|
413
|
-
var _this$itemMeasurement;
|
|
414
|
-
|
|
415
|
-
const index = this.indexFromElement(node);
|
|
416
|
-
const item = this.measurementsCache[index];
|
|
417
|
-
|
|
418
|
-
if (!item) {
|
|
419
|
-
return;
|
|
420
|
-
}
|
|
421
|
-
|
|
422
|
-
const prevNode = this.measureElementCache[item.key];
|
|
423
|
-
const ro = this.getResizeObserver();
|
|
424
|
-
|
|
425
|
-
if (!node.isConnected) {
|
|
426
|
-
if (prevNode) {
|
|
427
|
-
ro == null ? void 0 : ro.unobserve(prevNode);
|
|
428
|
-
delete this.measureElementCache[item.key];
|
|
429
|
-
}
|
|
430
|
-
|
|
431
|
-
return;
|
|
432
|
-
}
|
|
433
|
-
|
|
434
|
-
if (!prevNode || prevNode !== node) {
|
|
435
|
-
if (prevNode) {
|
|
436
|
-
ro == null ? void 0 : ro.unobserve(prevNode);
|
|
437
|
-
}
|
|
438
|
-
|
|
439
|
-
this.measureElementCache[item.key] = node;
|
|
440
|
-
ro == null ? void 0 : ro.observe(node);
|
|
441
|
-
}
|
|
442
|
-
|
|
443
|
-
const measuredItemSize = this.options.measureElement(node, this);
|
|
444
|
-
const itemSize = (_this$itemMeasurement = this.itemMeasurementsCache[item.key]) != null ? _this$itemMeasurement : item.size;
|
|
445
|
-
const delta = measuredItemSize - itemSize;
|
|
446
|
-
|
|
447
|
-
if (delta !== 0) {
|
|
448
|
-
if (item.start < this.scrollOffset && this.isScrolling && this.destinationOffset === undefined) {
|
|
449
|
-
if (process.env.NODE_ENV !== 'production' && this.options.debug) {
|
|
450
|
-
console.info('correction', delta);
|
|
451
|
-
}
|
|
452
|
-
|
|
453
|
-
this.scrollDelta += delta;
|
|
454
|
-
|
|
455
|
-
this._scrollToOffset(this.scrollOffset + this.scrollDelta, {
|
|
456
|
-
canSmooth: false,
|
|
457
|
-
sync: false,
|
|
458
|
-
requested: false
|
|
459
|
-
});
|
|
460
|
-
}
|
|
461
|
-
|
|
462
|
-
this.pendingMeasuredCacheIndexes.push(index);
|
|
463
|
-
this.itemMeasurementsCache = { ...this.itemMeasurementsCache,
|
|
464
|
-
[item.key]: measuredItemSize
|
|
465
|
-
};
|
|
466
|
-
this.notify();
|
|
467
|
-
}
|
|
468
|
-
};
|
|
469
|
-
|
|
470
|
-
this.measureElement = node => {
|
|
471
|
-
if (!node) {
|
|
472
|
-
return;
|
|
473
|
-
}
|
|
474
|
-
|
|
475
|
-
this._measureElement(node, true);
|
|
476
|
-
};
|
|
477
|
-
|
|
478
|
-
this.getVirtualItems = memo(() => [this.getIndexes(), this.getMeasurements()], (indexes, measurements) => {
|
|
479
|
-
const virtualItems = [];
|
|
480
|
-
|
|
481
|
-
for (let k = 0, len = indexes.length; k < len; k++) {
|
|
482
|
-
const i = indexes[k];
|
|
483
|
-
const measurement = measurements[i];
|
|
484
|
-
virtualItems.push(measurement);
|
|
485
|
-
}
|
|
486
|
-
|
|
487
|
-
return virtualItems;
|
|
488
|
-
}, {
|
|
489
|
-
key: process.env.NODE_ENV !== 'production' && 'getIndexes',
|
|
490
|
-
debug: () => this.options.debug
|
|
491
|
-
});
|
|
492
|
-
|
|
493
|
-
this.scrollToOffset = function (toOffset, _temp) {
|
|
494
|
-
let {
|
|
495
|
-
align = 'start',
|
|
496
|
-
smoothScroll = _this.options.enableSmoothScroll
|
|
497
|
-
} = _temp === void 0 ? {} : _temp;
|
|
498
|
-
const offset = _this.scrollOffset;
|
|
499
|
-
|
|
500
|
-
const size = _this.getSize();
|
|
501
|
-
|
|
502
|
-
if (align === 'auto') {
|
|
503
|
-
if (toOffset <= offset) {
|
|
504
|
-
align = 'start';
|
|
505
|
-
} else if (toOffset >= offset + size) {
|
|
506
|
-
align = 'end';
|
|
507
|
-
} else {
|
|
508
|
-
align = 'start';
|
|
509
|
-
}
|
|
510
|
-
}
|
|
511
|
-
|
|
512
|
-
const options = {
|
|
513
|
-
canSmooth: smoothScroll,
|
|
514
|
-
sync: false,
|
|
515
|
-
requested: true
|
|
516
|
-
};
|
|
517
|
-
|
|
518
|
-
if (align === 'start') {
|
|
519
|
-
_this._scrollToOffset(toOffset, options);
|
|
520
|
-
} else if (align === 'end') {
|
|
521
|
-
_this._scrollToOffset(toOffset - size, options);
|
|
522
|
-
} else if (align === 'center') {
|
|
523
|
-
_this._scrollToOffset(toOffset - size / 2, options);
|
|
524
|
-
}
|
|
525
|
-
};
|
|
526
|
-
|
|
527
|
-
this.scrollToIndex = function (index, _temp2) {
|
|
528
|
-
let {
|
|
529
|
-
align = 'auto',
|
|
530
|
-
smoothScroll = _this.options.enableSmoothScroll,
|
|
531
|
-
...rest
|
|
532
|
-
} = _temp2 === void 0 ? {} : _temp2;
|
|
533
|
-
|
|
534
|
-
const measurements = _this.getMeasurements();
|
|
535
|
-
|
|
536
|
-
const offset = _this.scrollOffset;
|
|
537
|
-
|
|
538
|
-
const size = _this.getSize();
|
|
539
|
-
|
|
540
|
-
const {
|
|
541
|
-
count
|
|
542
|
-
} = _this.options;
|
|
543
|
-
const measurement = measurements[Math.max(0, Math.min(index, count - 1))];
|
|
544
|
-
|
|
545
|
-
if (!measurement) {
|
|
546
|
-
return;
|
|
547
|
-
}
|
|
548
|
-
|
|
549
|
-
if (align === 'auto') {
|
|
550
|
-
if (measurement.end >= offset + size - _this.options.scrollPaddingEnd) {
|
|
551
|
-
align = 'end';
|
|
552
|
-
} else if (measurement.start <= offset + _this.options.scrollPaddingStart) {
|
|
553
|
-
align = 'start';
|
|
554
|
-
} else {
|
|
555
|
-
return;
|
|
556
|
-
}
|
|
557
|
-
}
|
|
558
|
-
|
|
559
|
-
const toOffset = align === 'end' ? measurement.end + _this.options.scrollPaddingEnd : measurement.start - _this.options.scrollPaddingStart;
|
|
560
|
-
|
|
561
|
-
_this.scrollToOffset(toOffset, {
|
|
562
|
-
align,
|
|
563
|
-
smoothScroll,
|
|
564
|
-
...rest
|
|
565
|
-
});
|
|
566
|
-
};
|
|
567
|
-
|
|
568
|
-
this.getTotalSize = () => {
|
|
569
|
-
var _this$getMeasurements;
|
|
570
|
-
|
|
571
|
-
return (((_this$getMeasurements = this.getMeasurements()[this.options.count - 1]) == null ? void 0 : _this$getMeasurements.end) || this.options.paddingStart) + this.options.paddingEnd;
|
|
572
|
-
};
|
|
573
|
-
|
|
574
|
-
this._scrollToOffset = (offset, _ref4) => {
|
|
575
|
-
let {
|
|
576
|
-
requested,
|
|
577
|
-
canSmooth,
|
|
578
|
-
sync
|
|
579
|
-
} = _ref4;
|
|
580
|
-
clearTimeout(this.scrollCheckFrame);
|
|
581
|
-
|
|
582
|
-
if (requested) {
|
|
583
|
-
this.destinationOffset = offset;
|
|
584
|
-
}
|
|
585
|
-
|
|
586
|
-
this.options.scrollToFn(offset, {
|
|
587
|
-
canSmooth,
|
|
588
|
-
sync
|
|
589
|
-
}, this);
|
|
590
|
-
let scrollCheckFrame;
|
|
591
|
-
|
|
592
|
-
const check = () => {
|
|
593
|
-
let lastOffset = this.scrollOffset;
|
|
594
|
-
this.scrollCheckFrame = scrollCheckFrame = setTimeout(() => {
|
|
595
|
-
if (this.scrollCheckFrame !== scrollCheckFrame) {
|
|
596
|
-
return;
|
|
597
|
-
}
|
|
598
|
-
|
|
599
|
-
if (this.scrollOffset === lastOffset) {
|
|
600
|
-
this.destinationOffset = undefined;
|
|
601
|
-
return;
|
|
602
|
-
}
|
|
603
|
-
|
|
604
|
-
lastOffset = this.scrollOffset;
|
|
605
|
-
check();
|
|
606
|
-
}, 100);
|
|
607
|
-
};
|
|
608
|
-
|
|
609
|
-
check();
|
|
610
|
-
};
|
|
611
|
-
|
|
612
|
-
this.measure = () => {
|
|
613
|
-
this.itemMeasurementsCache = {};
|
|
614
|
-
this.notify();
|
|
615
|
-
};
|
|
616
|
-
|
|
617
|
-
this.setOptions(_opts);
|
|
618
|
-
this.scrollRect = this.options.initialRect;
|
|
619
|
-
this.scrollOffset = this.options.initialOffset;
|
|
620
|
-
this.calculateRange();
|
|
621
|
-
}
|
|
622
|
-
|
|
623
|
-
}
|
|
624
|
-
|
|
625
|
-
const findNearestBinarySearch = (low, high, getCurrentValue, value) => {
|
|
626
|
-
while (low <= high) {
|
|
627
|
-
const middle = (low + high) / 2 | 0;
|
|
628
|
-
const currentValue = getCurrentValue(middle);
|
|
629
|
-
|
|
630
|
-
if (currentValue < value) {
|
|
631
|
-
low = middle + 1;
|
|
632
|
-
} else if (currentValue > value) {
|
|
633
|
-
high = middle - 1;
|
|
634
|
-
} else {
|
|
635
|
-
return middle;
|
|
636
|
-
}
|
|
637
|
-
}
|
|
638
|
-
|
|
639
|
-
if (low > 0) {
|
|
640
|
-
return low - 1;
|
|
641
|
-
} else {
|
|
642
|
-
return 0;
|
|
643
|
-
}
|
|
644
|
-
};
|
|
645
|
-
|
|
646
|
-
function calculateRange(_ref5) {
|
|
647
|
-
let {
|
|
648
|
-
measurements,
|
|
649
|
-
outerSize,
|
|
650
|
-
scrollOffset
|
|
651
|
-
} = _ref5;
|
|
652
|
-
const count = measurements.length - 1;
|
|
653
|
-
|
|
654
|
-
const getOffset = index => measurements[index].start;
|
|
655
|
-
|
|
656
|
-
const startIndex = findNearestBinarySearch(0, count, getOffset, scrollOffset);
|
|
657
|
-
let endIndex = startIndex;
|
|
658
|
-
|
|
659
|
-
while (endIndex < count && measurements[endIndex].end < scrollOffset + outerSize) {
|
|
660
|
-
endIndex++;
|
|
661
|
-
}
|
|
662
|
-
|
|
663
|
-
return {
|
|
664
|
-
startIndex,
|
|
665
|
-
endIndex
|
|
666
|
-
};
|
|
667
|
-
}
|
|
668
|
-
|
|
669
|
-
function createVirtualizerBase(options) {
|
|
670
|
-
const resolvedOptions = mergeProps(options);
|
|
671
|
-
const instance = new Virtualizer(resolvedOptions);
|
|
672
|
-
const [virtualItems, setVirtualItems] = createStore(instance.getVirtualItems());
|
|
673
|
-
const [totalSize, setTotalSize] = createSignal(instance.getTotalSize());
|
|
674
|
-
const handler = {
|
|
675
|
-
get(target, prop) {
|
|
676
|
-
switch (prop) {
|
|
677
|
-
case 'getVirtualItems':
|
|
678
|
-
return () => virtualItems;
|
|
679
|
-
|
|
680
|
-
case 'getTotalSize':
|
|
681
|
-
return () => totalSize();
|
|
682
|
-
|
|
683
|
-
default:
|
|
684
|
-
return Reflect.get(target, prop);
|
|
685
|
-
}
|
|
686
|
-
}
|
|
687
|
-
|
|
688
|
-
};
|
|
689
|
-
const virtualizer = new Proxy(instance, handler);
|
|
690
|
-
virtualizer.setOptions(resolvedOptions);
|
|
691
|
-
onMount(() => {
|
|
692
|
-
const cleanup = virtualizer._didMount();
|
|
693
|
-
|
|
694
|
-
virtualizer._willUpdate();
|
|
695
|
-
|
|
696
|
-
onCleanup(cleanup);
|
|
697
|
-
});
|
|
698
|
-
createComputed(() => {
|
|
699
|
-
virtualizer.setOptions(mergeProps(resolvedOptions, options, {
|
|
700
|
-
onChange: instance => {
|
|
701
|
-
instance._willUpdate();
|
|
702
|
-
|
|
703
|
-
setVirtualItems(reconcile(instance.getVirtualItems(), {
|
|
704
|
-
key: 'index'
|
|
705
|
-
}));
|
|
706
|
-
setTotalSize(instance.getTotalSize());
|
|
707
|
-
options.onChange == null ? void 0 : options.onChange(instance);
|
|
708
|
-
}
|
|
709
|
-
}));
|
|
710
|
-
virtualizer.measure();
|
|
711
|
-
});
|
|
712
|
-
return virtualizer;
|
|
713
|
-
}
|
|
714
|
-
|
|
715
|
-
function createVirtualizer(options) {
|
|
716
|
-
return createVirtualizerBase(mergeProps({
|
|
717
|
-
observeElementRect: observeElementRect,
|
|
718
|
-
observeElementOffset: observeElementOffset,
|
|
719
|
-
scrollToFn: elementScroll
|
|
720
|
-
}, options));
|
|
721
|
-
}
|
|
722
|
-
function createWindowVirtualizer(options) {
|
|
723
|
-
return createVirtualizerBase(mergeProps({
|
|
724
|
-
getScrollElement: () => typeof window !== 'undefined' ? window : null,
|
|
725
|
-
observeElementRect: observeWindowRect,
|
|
726
|
-
observeElementOffset: observeWindowOffset,
|
|
727
|
-
scrollToFn: windowScroll
|
|
728
|
-
}, options));
|
|
729
|
-
}
|
|
730
|
-
|
|
731
|
-
export { Virtualizer, createVirtualizer, createWindowVirtualizer, defaultKeyExtractor, defaultRangeExtractor, elementScroll, measureElement, memo, observeElementOffset, observeElementRect, observeWindowOffset, observeWindowRect, windowScroll };
|
|
732
|
-
//# sourceMappingURL=index.js.map
|