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

SwiftUI Date Picker选中日期后滚动自动回退问题求助

iOS 16.2 SwiftUI DatePicker 滚动自动回退问题修复

问题现象

在iOS 16.2中使用SwiftUI图形化样式的DatePicker时,选中某一日期后尝试滚动切换其他日期,控件会自动回退到当前选中的日期,无法正常选择其他日期。

问题代码

struct DatePickerExample: View {

  @State var expiry = Date.now

  let dateRange: ClosedRange<Date> = {
    let calendar = Calendar.current
    let yesterday = Calendar.current.date(byAdding: .day, value: -1, to: Date()) ?? Date()
    let startComponents = Calendar.current.dateComponents(
      [.year, .month, .day, .hour, .minute, .second], from: yesterday)
    let tenYearsFromNow = Calendar.current.date(byAdding: .year, value: 10, to: Date()) ?? Date()
    let endComponents = Calendar.current.dateComponents(
      [.year, .month, .day, .hour, .minute, .second], from: tenYearsFromNow)
    return calendar.date(from: startComponents)!...calendar.date(from: endComponents)!
  }()

  var body: some View {
    VStack {
      DatePicker(
        "Start Date",
        selection: $expiry,
        in: dateRange,
        displayedComponents: [.date]
      )
      .datePickerStyle(.graphical)
    }
  }
}

问题原因

当DatePicker设置displayedComponents: [.date]时,选中的日期会被自动处理为当天0点整(时分秒均为0)。但你定义的dateRange中,起始和结束日期都包含了具体的时分秒信息(比如当前时间的时分秒),这就导致选中的日期不在设定范围内,控件会强制回退到合法范围内的当前值。

解决方案

将dateRange的起始和结束日期统一处理为当天起始时间(时分秒置0),确保选中的日期落在范围内。

修改后的代码

struct DatePickerExample: View {
  @State var expiry = Date.now

  let dateRange: ClosedRange<Date> = {
    let calendar = Calendar.current
    // 将日期统一转为当天起始时间(时分秒为0)
    let startDate = calendar.startOfDay(for: calendar.date(byAdding: .day, value: -1, to: Date()) ?? Date())
    let endDate = calendar.startOfDay(for: calendar.date(byAdding: .year, value: 10, to: Date()) ?? Date())
    return startDate...endDate
  }()

  var body: some View {
    VStack {
      DatePicker(
        "Start Date",
        selection: $expiry,
        in: dateRange,
        displayedComponents: [.date]
      )
      .datePickerStyle(.graphical)
    }
  }
}

关键修改点

使用Calendar的startOfDay(for:)方法,将所有参与范围计算的日期都转为当天的0点整,这样DatePicker选中的日期(同样会被处理为0点)就会完全落在dateRange范围内,不会触发自动回退的逻辑。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.25 19:02:48