You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

SwiftUI List更新后内部ProgressView消失问题咨询

SwiftUI List底部ProgressView新增内容后消失的原因与解决方法

问题原因

你遇到的问题核心在于SwiftUI的视图身份识别机制和.onAppear的触发逻辑冲突:

  • 当滚动到ProgressView时,.onAppear触发加载新数据,数据添加后List会重新渲染所有子视图
  • 由于ProgressView没有绑定稳定的身份标识(id),List在更新时无法正确复用这个视图实例,而是会尝试重建它
  • 加上.onAppear已经触发过,新重建的ProgressView会出现状态异常,表现为进度指示器消失,但单元格和标签还保留

解决方法

要解决这个问题,需要做两件事:

  1. 给ProgressView添加稳定的身份标识,让List能正确识别并复用它
  2. 添加加载状态控制,避免重复触发加载逻辑(防止多次调用接口)

修正后的代码

struct ContentView: View {
    
    @State var items: [String] = ["Item 1", "Item 2", "Item 3", "Item 4", "Item 5", "Item 6"]
    @State private var isLoading = false // 新增加载状态控制
        
    var body: some View {
        List {
            ForEach(items, id: \.self) { item in
                Text(item)
                    .frame(height: 100)
            }
            
            ProgressView {
                Text("Loading")
            }
            .frame(maxWidth: .greatestFiniteMagnitude, alignment: .center)
            .id("loading-footer") // 给ProgressView添加固定id
            .onAppear(perform: endOfListReached)
            .disabled(isLoading) // 加载中禁用触发
        }
    }
    
    func endOfListReached() {
        guard !isLoading else { return } // 避免重复加载
        isLoading = true
        
        DispatchQueue.main.asyncAfter(deadline: .now() + 2) {
            items.append("Item \(items.count + 1)")
            isLoading = false // 加载完成恢复状态
        }
    }
}

补充说明

  • 添加.id("loading-footer")后,List在更新时会识别到这是同一个视图,不会重建导致进度指示器消失
  • 加载状态isLoading能防止用户快速滚动时多次触发加载逻辑,避免重复请求服务器

内容的提问来源于stack exchange,提问作者Thofreym

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.01 10:45:33