diff --git a/VirtualList.svelte b/VirtualList.svelte index adbc2f2..55c8180 100644 --- a/VirtualList.svelte +++ b/VirtualList.svelte @@ -9,7 +9,6 @@ // read-only, but visible to consumers via bind:start export let start = 0; export let end = 0; - // local state let height_map = []; let rows; @@ -31,6 +30,12 @@ $: if (mounted) refresh(items, viewport_height, itemHeight); async function refresh(items, viewport_height, itemHeight) { + const isStartOverflow = items.length < start + + if (isStartOverflow) { + await scrollToIndex(items.length - 1, {behavior: 'auto'}) + } + const { scrollTop } = viewport; await tick(); // wait until the DOM is up to date @@ -102,29 +107,25 @@ while (i < items.length) height_map[i++] = average_height; bottom = remaining * average_height; - // prevent jumping if we scrolled up into unknown territory - if (start < old_start) { - await tick(); - - let expected_height = 0; - let actual_height = 0; - - for (let i = start; i < old_start; i +=1) { - if (rows[i - start]) { - expected_height += height_map[i]; - actual_height += itemHeight || rows[i - start].offsetHeight; - } - } - - const d = actual_height - expected_height; - viewport.scrollTo(0, scrollTop + d); - } - // TODO if we overestimated the space these // rows would occupy we may need to add some // more. maybe we can just call handle_scroll again? } + export async function scrollToIndex (index, opts) { + const {scrollTop} = viewport; + const itemsDelta = index - start; + const _itemHeight = itemHeight || average_height; + const distance = itemsDelta * _itemHeight; + opts = { + left: 0, + top: scrollTop + distance, + behavior: 'smooth', + ...opts + }; + viewport.scrollTo(opts); + } + // trigger initial refresh onMount(() => { rows = contents.getElementsByTagName('svelte-virtual-list-row'); diff --git a/logo_svelte-virtual-list-ce.png b/logo_svelte-virtual-list-ce.png new file mode 100644 index 0000000..0562c31 Binary files /dev/null and b/logo_svelte-virtual-list-ce.png differ diff --git a/logo_svelte-virtual-list-ce.svg b/logo_svelte-virtual-list-ce.svg new file mode 100644 index 0000000..b616f3e --- /dev/null +++ b/logo_svelte-virtual-list-ce.svg @@ -0,0 +1 @@ + \ No newline at end of file