Skip to content

Commit b25eb4d

Browse files
committed
vl: mutex
1 parent 3a2a188 commit b25eb4d

1 file changed

Lines changed: 14 additions & 6 deletions

File tree

src/pages/scripts/virtualList.mjs

Lines changed: 14 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,14 @@ export function createVirtualList({
6565
resizeObserver: null, // ResizeObserver 用于容器大小变化
6666
}
6767

68+
/**
69+
* 获取加载锁,确保只有一个请求在进行中。
70+
*/
71+
async function getMutex() {
72+
while (state.isLoading) await new Promise((resolve) => setTimeout(resolve, 100))
73+
return state.isLoading = true
74+
}
75+
6876
/**
6977
* 更新动态缓冲区大小和平均项高度。
7078
*/
@@ -168,7 +176,7 @@ export function createVirtualList({
168176
*/
169177
async function prependItems() {
170178
if (state.startIndex <= 0) return
171-
state.isLoading = true
179+
await getMutex()
172180
try {
173181
const itemsToFetch = Math.min(state.bufferSize, state.startIndex)
174182
const newStartIndex = state.startIndex - itemsToFetch
@@ -214,7 +222,7 @@ export function createVirtualList({
214222
async function appendItems() {
215223
const currentCount = state.startIndex + state.queue.length
216224
if (currentCount >= state.totalCount) return
217-
state.isLoading = true
225+
await getMutex()
218226
try {
219227
const itemsToFetch = Math.min(state.bufferSize, state.totalCount - currentCount)
220228
const { items: newItems } = await fetchData(currentCount, itemsToFetch)
@@ -284,7 +292,7 @@ export function createVirtualList({
284292
* 强制刷新整个列表。
285293
*/
286294
async function refresh() {
287-
state.isLoading = true
295+
await getMutex()
288296
try {
289297
const { total } = await fetchData(0, 0)
290298
state.totalCount = total || 0
@@ -333,7 +341,7 @@ export function createVirtualList({
333341
* @param {boolean} [scrollTo=true] - 是否滚动到新项目。
334342
*/
335343
async function appendItem(item, scrollTo = true) {
336-
state.isLoading = true
344+
await getMutex()
337345
try {
338346
state.totalCount++
339347
const itemIndex = state.startIndex + state.queue.length
@@ -365,7 +373,7 @@ export function createVirtualList({
365373
state.totalCount = Math.max(0, state.totalCount - 1)
366374
return
367375
}
368-
state.isLoading = true
376+
await getMutex()
369377
try {
370378
state.queue.splice(queueIndex, 1)
371379
state.totalCount--
@@ -401,7 +409,7 @@ export function createVirtualList({
401409
console.warn(`[virtualList] replaceItem called for index ${index} which is not in view.`)
402410
return
403411
}
404-
state.isLoading = true
412+
await getMutex()
405413
try {
406414
const oldElement = state.renderedElements.get(index)
407415
if (!oldElement) return

0 commit comments

Comments
 (0)