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

SwiftUI 中如何在父视图中重新初始化 StateObject 实例?

解决方案

你可以从两种实现思路里选最适配你业务场景的:

方案1:每次弹出训练页时生成全新的WorkoutManager实例(推荐,完全无历史残留)

不需要修改WorkoutView的逻辑,只要调整ContentView的实例初始化时机,保证每次打开Sheet都是全新的干净实例:

struct ContentView: View {
    // 仅声明,不提前初始化实例
    @StateObject var workoutManager: WorkoutManager?
    @State var showingWorkoutView = false
    
    var body: some View {
        Button {
            // 每次点击开始训练时生成全新实例
            workoutManager = WorkoutManager()
            showingWorkoutView.toggle()
        } label: {
            Text("Start Workout")
        }
        .sheet(isPresented: $showingWorkoutView) {
            // Sheet关闭后销毁旧实例
            workoutManager = nil
        } content: {
            if let workoutManager = workoutManager {
                WorkoutView(showingWorkoutView: $showingWorkoutView)
                    .environmentObject(workoutManager)
            }
        }
    }
}

方案2:给WorkoutManager加重置方法,手动清理状态

如果你不需要完全销毁实例,仅需要清理训练相关的历史状态,可以给WorkoutManager新增重置方法:

  1. 先扩展WorkoutManager,新增重置逻辑:
class WorkoutManager: ObservableObject {
    var workout: HKWorkout?
    // 其他训练相关状态属性
    
    func resetState() {
        workout = nil
        // 所有需要清空的历史状态都在此处恢复为初始值
    }
}
  1. 在结束训练时调用重置方法即可:
struct WorkoutView: View {
    @EnvironmentObject var workoutManager:  WorkoutManager
    @Binding var showingWorkoutView: Bool
    
    var body: some View {
        Text("Workout Started")
            .padding()
        Button {
            workoutManager.resetState()
            showingWorkoutView.toggle()
        } label: {
            Text("End Workout")
        }
    }
}

注意:如果你的WorkoutManager属性变化需要驱动视图刷新,记得给对应属性加上@Published包装器。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.27 08:36:05