fix: replace virtual card grid with progressive loading

This commit is contained in:
jxxghp
2026-05-09 22:23:45 +08:00
parent 5909d2423c
commit 2f1a356e65
13 changed files with 289 additions and 326 deletions

View File

@@ -2,7 +2,7 @@
import api from '@/api'
import type { MediaInfo } from '@/api/types'
import MediaCard from '@/components/cards/MediaCard.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import NoDataFound from '@/components/NoDataFound.vue'
import { useI18n } from 'vue-i18n'
@@ -154,7 +154,7 @@ async function fetchData({ done }: { done: any }) {
<VInfiniteScroll mode="intersect" side="end" :items="dataList" class="overflow-visible pt-3 px-2" @load="fetchData">
<template #loading />
<template #empty />
<VirtualCardGrid
<ProgressiveCardGrid
v-if="dataList.length > 0"
:items="dataList"
:get-item-key="item => item.tmdb_id || item.douban_id || item.bangumi_id || item.media_id || item.title"
@@ -163,7 +163,7 @@ async function fetchData({ done }: { done: any }) {
<template #default="{ item }">
<MediaCard :media="item" />
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
<NoDataFound
v-if="dataList.length === 0 && isRefreshed"
error-code="404"

View File

@@ -2,7 +2,7 @@
import api from '@/api'
import type { Person } from '@/api/types'
import PersonCard from '@/components/cards/PersonCard.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import NoDataFound from '@/components/NoDataFound.vue'
import { useI18n } from 'vue-i18n'
@@ -123,11 +123,11 @@ async function fetchData({ done }: { done: any }) {
<VInfiniteScroll mode="intersect" side="end" :items="dataList" class="overflow-visible px-3" @load="fetchData">
<template #loading />
<template #empty />
<VirtualCardGrid v-if="dataList.length > 0" :items="dataList" :get-item-key="item => item.id" tabindex="0">
<ProgressiveCardGrid v-if="dataList.length > 0" :items="dataList" :get-item-key="item => item.id" tabindex="0">
<template #default="{ item }">
<PersonCard :person="item" />
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
<NoDataFound
v-if="dataList.length === 0 && isRefreshed"
error-code="404"

View File

@@ -13,7 +13,7 @@ import PluginMarketSettingDialog from '@/components/dialog/PluginMarketSettingDi
import { useDynamicButton } from '@/composables/useDynamicButton'
import { useI18n } from 'vue-i18n'
import PluginMixedSortCard from '@/components/cards/PluginMixedSortCard.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import { usePWA } from '@/composables/usePWA'
import { useDynamicHeaderTab } from '@/composables/useDynamicHeaderTab'
@@ -1566,12 +1566,11 @@ function onDragStartPlugin(evt: any) {
/>
</template>
</draggable>
<VirtualCardGrid
<ProgressiveCardGrid
v-else-if="shouldVirtualizeInstalledMainList"
:items="mixedSortList"
:get-item-key="item => `${item.type}:${item.id}`"
:min-item-width="256"
:estimated-item-height="260"
:scroll-to-index="installedScrollToIndex"
>
<template #default="{ item }">
@@ -1593,7 +1592,7 @@ function onDragStartPlugin(evt: any) {
@drop-to-folder="(event, folderName) => handleDropToFolder(event, folderName)"
/>
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
</template>
<template v-else>
@@ -1625,12 +1624,11 @@ function onDragStartPlugin(evt: any) {
/>
</template>
</draggable>
<VirtualCardGrid
<ProgressiveCardGrid
v-else-if="shouldVirtualizeInstalledFolderList"
:items="draggableFolderPlugins"
:get-item-key="item => item.id"
:min-item-width="256"
:estimated-item-height="260"
>
<template #default="{ item }">
<PluginMixedSortCard
@@ -1648,7 +1646,7 @@ function onDragStartPlugin(evt: any) {
@remove-from-folder="removeFromFolder"
/>
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
</template>
</div>
@@ -1679,7 +1677,7 @@ function onDragStartPlugin(evt: any) {
>
<template #loading />
<template #empty />
<VirtualCardGrid
<ProgressiveCardGrid
v-if="displayUninstalledList.length > 0"
:items="displayUninstalledList"
:get-item-key="item => `${item.id}_v${item.plugin_version}`"
@@ -1689,7 +1687,7 @@ function onDragStartPlugin(evt: any) {
<template #default="{ item }">
<PluginAppCard :plugin="item" :count="PluginStatistics[item.id || '0']" @install="pluginInstalled" />
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
</VInfiniteScroll>
<NoDataFound
v-if="displayUninstalledList.length === 0 && isAppMarketLoaded"

View File

@@ -4,7 +4,7 @@ import api from '@/api'
import type { DownloadingInfo } from '@/api/types'
import NoDataFound from '@/components/NoDataFound.vue'
import DownloadingCard from '@/components/cards/DownloadingCard.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import { useUserStore } from '@/stores'
import { useI18n } from 'vue-i18n'
import { useBackgroundOptimization } from '@/composables/useBackgroundOptimization'
@@ -68,7 +68,7 @@ const { loading: dataLoading } = useDataRefresh(
<template>
<LoadingBanner v-if="!isRefreshed" class="mt-12" />
<VPullToRefresh v-model="loading" @load="onRefresh" :pull-down-threshold="64">
<VirtualCardGrid
<ProgressiveCardGrid
v-if="filteredDataList.length > 0"
:items="filteredDataList"
:get-item-key="item => item.hash || item.name"
@@ -78,7 +78,7 @@ const { loading: dataLoading } = useDataRefresh(
<template #default="{ item }">
<DownloadingCard :info="item" :downloader-name="props.name" />
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
<NoDataFound
v-if="filteredDataList.length === 0 && isRefreshed"
error-code="404"

View File

@@ -7,7 +7,7 @@ import NoDataFound from '@/components/NoDataFound.vue'
import SiteAddEditDialog from '@/components/dialog/SiteAddEditDialog.vue'
import SiteStatisticsDialog from '@/components/dialog/SiteStatisticsDialog.vue'
import SiteImportDialog from '@/components/dialog/SiteImportDialog.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import { useDynamicButton } from '@/composables/useDynamicButton'
import { useI18n } from 'vue-i18n'
import { usePWA } from '@/composables/usePWA'
@@ -422,12 +422,11 @@ useDynamicButton({
/>
</template>
</draggable>
<VirtualCardGrid
<ProgressiveCardGrid
v-else-if="draggableSiteList.length > 0 && shouldVirtualizeList"
:items="draggableSiteList"
:get-item-key="item => item.id"
:min-item-width="256"
:estimated-item-height="240"
class="px-2"
>
<template #default="{ item }">
@@ -441,7 +440,7 @@ useDynamicButton({
@refresh-stats="handleRefreshStats"
/>
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
</div>
<NoDataFound
v-if="draggableSiteList.length === 0 && isRefreshed"

View File

@@ -5,7 +5,7 @@ import type { Subscribe } from '@/api/types'
import NoDataFound from '@/components/NoDataFound.vue'
import SubscribeCard from '@/components/cards/SubscribeCard.vue'
import SubscribeHistoryDialog from '@/components/dialog/SubscribeHistoryDialog.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import { useUserStore } from '@/stores'
import { useI18n } from 'vue-i18n'
import { useToast } from 'vue-toastification'
@@ -513,12 +513,11 @@ defineExpose({
/>
</template>
</draggable>
<VirtualCardGrid
<ProgressiveCardGrid
v-else-if="displayList.length > 0 && shouldVirtualizeList"
:items="displayList"
:get-item-key="item => item.id"
:min-item-width="240"
:estimated-item-height="300"
:scroll-to-index="scrollToIndex"
class="px-2"
>
@@ -534,7 +533,7 @@ defineExpose({
@select="toggleSelectSubscribe(item.id)"
/>
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
<NoDataFound
v-if="displayList.length === 0 && isRefreshed"
error-code="404"

View File

@@ -3,7 +3,7 @@ import api from '@/api'
import type { MediaInfo } from '@/api/types'
import MediaCard from '@/components/cards/MediaCard.vue'
import NoDataFound from '@/components/NoDataFound.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import { useI18n } from 'vue-i18n'
// 国际化
@@ -275,7 +275,7 @@ async function fetchData({ done }: { done: any }) {
>
<template #loading />
<template #empty />
<VirtualCardGrid
<ProgressiveCardGrid
v-if="dataList.length > 0"
:items="dataList"
:get-item-key="item => item.tmdb_id || item.douban_id || item.bangumi_id || item.media_id || item.title"
@@ -292,7 +292,7 @@ async function fetchData({ done }: { done: any }) {
</div>
</div>
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
<NoDataFound
v-if="dataList.length === 0 && isRefreshed"
error-code="404"

View File

@@ -3,7 +3,7 @@ import api from '@/api'
import type { SubscribeShare } from '@/api/types'
import NoDataFound from '@/components/NoDataFound.vue'
import SubscribeShareCard from '@/components/cards/SubscribeShareCard.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import { useI18n } from 'vue-i18n'
// 国际化
@@ -295,7 +295,7 @@ function removeData(id: number) {
>
<template #loading />
<template #empty />
<VirtualCardGrid
<ProgressiveCardGrid
v-if="dataList.length > 0"
:items="dataList"
:get-item-key="item => item.id || `${item.tmdbid || item.doubanid || item.name}-${item.share_user}`"
@@ -306,7 +306,7 @@ function removeData(id: number) {
<template #default="{ item }">
<SubscribeShareCard :media="item" @delete="removeData(item.id || 0)" />
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
<NoDataFound
v-if="dataList.length === 0 && isRefreshed"
error-code="404"

View File

@@ -4,7 +4,7 @@ import { Workflow } from '@/api/types'
import WorkflowAddEditDialog from '@/components/dialog/WorkflowAddEditDialog.vue'
import WorkflowTaskCard from '@/components/cards/WorkflowTaskCard.vue'
import NoDataFound from '@/components/NoDataFound.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import { useI18n } from 'vue-i18n'
// 国际化
@@ -67,7 +67,7 @@ defineExpose({
<template>
<div>
<LoadingBanner v-if="!isRefreshed" class="mt-12" />
<VirtualCardGrid
<ProgressiveCardGrid
v-if="workflowList.length > 0 && isRefreshed"
:items="workflowList"
:get-item-key="item => item.id"
@@ -78,7 +78,7 @@ defineExpose({
<template #default="{ item }">
<WorkflowTaskCard :workflow="item" :event-types="eventTypes" @refresh="fetchData" />
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
<NoDataFound
v-if="workflowList.length === 0 && isRefreshed"
error-code="404"

View File

@@ -3,7 +3,7 @@ import api from '@/api'
import type { WorkflowShare } from '@/api/types'
import NoDataFound from '@/components/NoDataFound.vue'
import WorkflowShareCard from '@/components/cards/WorkflowShareCard.vue'
import VirtualCardGrid from '@/components/misc/VirtualCardGrid.vue'
import ProgressiveCardGrid from '@/components/misc/ProgressiveCardGrid.vue'
import { useI18n } from 'vue-i18n'
// 国际化
@@ -157,7 +157,7 @@ onActivated(() => {
<VInfiniteScroll mode="intersect" side="end" :items="dataList" class="overflow-visible px-2" @load="fetchData" :key="currentKey">
<template #loading />
<template #empty />
<VirtualCardGrid
<ProgressiveCardGrid
v-if="dataList.length > 0"
:items="dataList"
:get-item-key="item => item.id"
@@ -173,7 +173,7 @@ onActivated(() => {
@update="emit('update')"
/>
</template>
</VirtualCardGrid>
</ProgressiveCardGrid>
<NoDataFound
v-if="dataList.length === 0 && isRefreshed"
error-code="404"