SwiftUI开发求助:将CoreML模型计算的理想就寝时间固定显示在顶部
解决方案
要将计算出的理想就寝时间固定显示在界面顶部,只需对现有代码做以下几点修改:
- 添加状态变量存储计算结果
- 在界面顶部增加结果展示区域
- 调整计算逻辑,将结果赋值给状态变量而非弹窗展示
修改后的完整代码:
import CoreML import SwiftUI struct ContentView: View { @State private var wakeUp = defaultWakeUpTime @State private var sleepAmount = 8.0 @State private var coffeeAmount = 1 @State private var alertTitle = "" @State private var alertMessage = "" @State private var showingAlert = false // 新增:存储理想就寝时间的状态变量 @State private var idealBedtime: Date? static var defaultWakeUpTime: Date { var components = DateComponents() components.hour = 7 components.minute = 0 return Calendar.current.date(from: components) ?? Date.now } var body: some View { NavigationView { VStack(spacing: 0) { // 新增:顶部固定展示理想就寝时间的区域 if let bedtime = idealBedtime { HStack { Text("你的理想就寝时间") .font(.subheadline) .foregroundColor(.secondary) Spacer() Text(bedtime.formatted(date: .omitted, time: .shortened)) .font(.title) .fontWeight(.bold) } .padding() .background(Color(.systemGray6)) } Form { Section() { Text("你打算几点起床?") .font(.headline) DatePicker("请选择时间", selection: $wakeUp, displayedComponents: .hourAndMinute) .labelsHidden() } Section() { Text("期望睡眠时间") .font(.headline) Stepper("\(sleepAmount.formatted()) 小时", value: $sleepAmount, in: 4...12, step: 0.25) } Section() { Text("每日咖啡摄入量") Picker("杯数", selection: $coffeeAmount) { ForEach(1..<21) { Text("\($0) 杯") } } .pickerStyle(.wheel) } } } .navigationTitle("优质睡眠助手") .toolbar { Button("计算", action: calculateBedTime) } .alert(alertTitle, isPresented: $showingAlert) { Button("确定") { } } message: { Text(alertMessage) } } } func calculateBedTime() { do { let config = MLModelConfiguration() let model = try SleepCalculator(configuration: config) let components = Calendar.current.dateComponents([.hour, .minute], from: wakeUp) let hour = (components.hour ?? 0) * 60 * 60 let minute = (components.minute ?? 0) * 60 let prediction = try model.prediction(wake: Double(hour + minute), estimatedSleep: sleepAmount, coffee: Double(coffeeAmount)) let sleepTime = wakeUp - prediction.actualSleep // 将结果赋值给状态变量,而非弹窗 idealBedtime = sleepTime } catch { alertTitle = "错误" alertMessage = "抱歉,计算就寝时间时出现问题。" showingAlert = true } } } struct ContentView_Previews: PreviewProvider { static var previews: some View { ContentView() } }
关键修改说明:
- 新增状态变量:
@State private var idealBedtime: Date?用于存储计算后的就寝时间,初始值为nil表示未计算。 - 顶部展示区域:通过
if let bedtime = idealBedtime判断是否已计算,若有结果则在Form上方显示一个带背景的信息栏,用加粗字体突出显示时间。 - 调整计算逻辑:在
calculateBedTime函数中,成功计算后将结果赋值给idealBedtime,不再触发弹窗;错误情况仍保留弹窗提示。
内容的提问来源于stack exchange,提问作者Hamza
相关产品推荐
相关产品推荐

