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

SwiftUI中如何将ContentView的Timer传递给SecondView?

解决SwiftUI中ContentView定时器传递到SecondView的问题

核心问题分析

你当前的困惑在于不清楚定时器的具体类型,且错误尝试用@Binding传递定时器——@Binding用于双向绑定状态值,而定时器本质是事件发布者(Publisher),直接传递实例即可。

修正后的完整代码

ContentView

struct ContentView: View {
    // 显式声明定时器类型,代码更清晰
    @State private var timer: Timer.TimerPublisher.Autoconnect = Timer.publish(every: 1, tolerance: 0.5, on: .main, in: .common).autoconnect()
    @State private var timeRemaining = 10
    
    var body: some View {
        NavigationView {
            VStack {
                Text("\(timeRemaining)")
                    .onReceive(timer) { _ in
                        if timeRemaining > 0 {
                            timeRemaining -= 1
                        }
                    }
                
                NavigationLink {
                    // 直接传递timer实例
                    SecondView(timer: timer)
                } label: {
                    Text("切换页面")
                }
            }
        }
    }
}

SecondView

struct SecondView: View {
    // 声明与ContentView一致的定时器类型,用let接收(无需绑定)
    let timer: Timer.TimerPublisher.Autoconnect
    @State private var timeRemaining = 5
    
    var body: some View {
        Text("\(timeRemaining)")
            .onReceive(timer) { _ in
                if timeRemaining > 0 {
                    timeRemaining -= 1
                }
            }
    }
}

struct SecondView_Previews: PreviewProvider {
    static var previews: some View {
        // 预览时创建测试用的定时器实例
        SecondView(timer: Timer.publish(every: 1, on: .main, in: .common).autoconnect())
    }
}

关键说明

  1. 定时器类型:Timer.publish(...)返回Timer.TimerPublisher,调用autoconnect()后变为Timer.TimerPublisher.Autoconnect,这就是需要传递的具体类型。
  2. 无需@Binding:我们传递的是事件发布者本身,不是需要双向修改的状态值,因此用let直接接收即可。
  3. 预览处理:预览时需手动创建定时器实例,保证预览正常运行。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.22 21:39:17