Skip to content

Commit 7b60c07

Browse files
committed
fix: make page size/total pages reactive
1 parent 8556bd8 commit 7b60c07

3 files changed

Lines changed: 34 additions & 7 deletions

File tree

app/components/PackageList.vue

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,7 @@ const { handleScroll, scrollToPage } = useVirtualInfiniteScroll({
9898
itemCount,
9999
hasMore,
100100
isLoading,
101-
pageSize: numericPageSize.value,
101+
pageSize: numericPageSize,
102102
threshold: 5,
103103
onLoadMore: () => emit('loadMore'),
104104
onPageChange: page => emit('pageChange', page),
@@ -212,7 +212,19 @@ defineExpose({
212212

213213
<!-- Card View with Pagination -->
214214
<template v-else>
215-
<ol class="list-none m-0 p-0">
215+
<!-- Loading state when fetching page data -->
216+
<div
217+
v-if="isLoading && displayedResults.length === 0"
218+
class="py-12 flex items-center justify-center"
219+
>
220+
<div class="flex items-center gap-3 text-fg-muted font-mono text-sm">
221+
<span
222+
class="w-5 h-5 border-2 border-fg-subtle border-t-fg rounded-full motion-safe:animate-spin"
223+
/>
224+
{{ $t('common.loading') }}
225+
</div>
226+
</div>
227+
<ol v-else class="list-none m-0 p-0">
216228
<li v-for="(item, index) in displayedResults" :key="item.package.name" class="pb-4">
217229
<PackageCard
218230
:result="item"

app/composables/useVirtualInfiniteScroll.ts

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import type { Ref } from 'vue'
1+
import type { MaybeRefOrGetter, Ref } from 'vue'
22

33
export interface WindowVirtualizerHandle {
44
readonly scrollOffset: number
@@ -20,8 +20,8 @@ export interface UseVirtualInfiniteScrollOptions {
2020
hasMore: Ref<boolean>
2121
/** Whether currently loading */
2222
isLoading: Ref<boolean>
23-
/** Page size for calculating current page */
24-
pageSize: number
23+
/** Page size for calculating current page (reactive) */
24+
pageSize: MaybeRefOrGetter<number>
2525
/** Threshold in items before end to trigger load */
2626
threshold?: number
2727
/** Callback to load more items */
@@ -60,7 +60,8 @@ export function useVirtualInfiniteScroll(options: UseVirtualInfiniteScrollOption
6060

6161
// Calculate current visible page based on first visible item
6262
const startIndex = list.findItemIndex(list.scrollOffset)
63-
const newPage = Math.floor(startIndex / pageSize) + 1
63+
const currentPageSize = toValue(pageSize)
64+
const newPage = Math.floor(startIndex / currentPageSize) + 1
6465

6566
if (newPage !== currentPage.value && onPageChange) {
6667
currentPage.value = newPage
@@ -92,7 +93,7 @@ export function useVirtualInfiniteScroll(options: UseVirtualInfiniteScrollOption
9293
const list = listRef.value
9394
if (!list || page < 1) return
9495

95-
const targetIndex = (page - 1) * pageSize
96+
const targetIndex = (page - 1) * toValue(pageSize)
9697
list.scrollToIndex(targetIndex, { align: 'start' })
9798
currentPage.value = page
9899
}

app/pages/@[org].vue

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,11 +60,25 @@ const {
6060
// Pagination state
6161
const currentPage = ref(1)
6262
63+
// Calculate total pages
64+
const totalPages = computed(() => {
65+
if (pageSize.value === 'all') return 1
66+
const numericSize = typeof pageSize.value === 'number' ? pageSize.value : 25
67+
return Math.ceil(sortedPackages.value.length / numericSize)
68+
})
69+
6370
// Reset to page 1 when filters change
6471
watch([filters, sortOption], () => {
6572
currentPage.value = 1
6673
})
6774
75+
// Clamp current page when total pages decreases (e.g., after filtering)
76+
watch(totalPages, newTotal => {
77+
if (currentPage.value > newTotal && newTotal > 0) {
78+
currentPage.value = newTotal
79+
}
80+
})
81+
6882
// Debounced URL update for filter/sort
6983
const updateUrl = debounce((updates: { filter?: string; sort?: string }) => {
7084
router.replace({

0 commit comments

Comments
 (0)