Files
2026-02-10 04:16:30 +08:00

71 lines
2.2 KiB
TypeScript
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { defineStore } from 'pinia'
import { ref, computed, readonly } from 'vue'
import { Config, UserInfo } from './bindings.ts'
import { CurrentNavName } from './AppContent.vue'
import { ProgressData } from './panes/DownloadPane/DownloadPane.vue'
export const useStore = defineStore('store', () => {
const config = ref<Config>()
const userInfo = ref<UserInfo>()
const currentNavName = ref<CurrentNavName>('search')
const downloadSpeed = ref<string>('')
const { progresses, updateProgresses } = useProgresses()
const uncompletedProgressesCount = computed<number>(() => {
return Array.from(progresses.value.values()).filter(({ state }) => state !== 'Completed').length
})
return {
config,
currentNavName,
userInfo,
progresses,
updateProgresses,
uncompletedProgressesCount,
downloadSpeed,
}
})
function useProgresses() {
// 内部的高频更新状态
const _progresses = new Map<string, ProgressData>()
// 对外暴露的响应式状态
const progresses = ref<Map<string, ProgressData>>(new Map())
// 用于确保在同一渲染帧内只安排一次UI更新
let isUpdateScheduled = false
// 将 `_progresses` 的内容更新到 `progresses` 中,并触发重新渲染
const updateProgressesOnFrame = () => {
const newProgressesMap = new Map<string, ProgressData>()
for (const [key, value] of _progresses.entries()) {
const progressData = progresses.value.get(key)
if (progressData !== undefined) {
Object.assign(progressData, value)
newProgressesMap.set(key, progressData)
} else {
newProgressesMap.set(key, { ...value })
}
}
progresses.value = newProgressesMap
isUpdateScheduled = false
}
const updateProgresses = (updateFn: (progresses: Map<string, ProgressData>) => void) => {
// 使用传入的更新函数来修改 `_progresses`
updateFn(_progresses)
if (!isUpdateScheduled) {
// 如果没有安排过UI更新则安排一次
isUpdateScheduled = true
// 使用 `requestAnimationFrame` 调度 UI 更新
requestAnimationFrame(updateProgressesOnFrame)
}
}
return { progresses: readonly(progresses), updateProgresses }
}