自定义倒计时DatePicker SwiftUI中的错误



我实现了这个自定义的倒计时DatePicker,我在堆栈溢出中发现了这个链接,但它有一个错误,如果我从不同的地方更改选择器,那么第一次启动计时器时1分钟,它仍然会将计时器设置为1分钟,但如果我在第一次启动后更改它,它会正常工作。

import SwiftUI
struct DurationPicker: UIViewRepresentable {
@Binding var duration: Double
func makeUIView(context: Context) -> UIDatePicker {
let datePicker = UIDatePicker()
datePicker.datePickerMode = .countDownTimer
datePicker.addTarget(context.coordinator, action: #selector(Coordinator.updateDuration), for: .valueChanged)
return datePicker
}
func updateUIView(_ datePicker: UIDatePicker, context: Context) {
datePicker.countDownDuration = duration

}
func makeCoordinator() -> Coordinator {
Coordinator(self)
}
class Coordinator: NSObject {
let parent: DurationPicker
init(_ parent: DurationPicker) {
self.parent = parent
}
@objc func updateDuration(datePicker: UIDatePicker) {
parent.duration = datePicker.countDownDuration
}
}
}
struct ContentView: View {

@State var duration = 60.0
@State var timeRemaining = 60.0
@State private var isActive = false
var timer = Timer.publish(every: 1, on: .main, in: .common).autoconnect()


var body: some View {
VStack {
Text("(timeRemaining)")
.bold()
.font(.largeTitle)
DurationPicker(duration: $duration)
HStack {
Button("Cancel") {
isActive = false
}
.padding()
Button("Start") {
self.timeRemaining = duration
isActive = true
}
.padding()
}
}
.onReceive(timer) { time in
guard self.isActive else { return }

if self.timeRemaining > 0 {
self.timeRemaining -= 1
}
}
.onReceive(NotificationCenter.default.publisher(for: UIApplication.willResignActiveNotification)) { _ in
self.isActive = false
}
.onReceive(NotificationCenter.default.publisher(for: UIApplication.willEnterForegroundNotification)) { _ in
self.isActive = true
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}

我不太确定该把medtateTime设置为什么,我想如果它真的改变了,@State会自动改变它,所以我不太清楚发生了什么。

这个bug似乎在SwiftUI中,下面是我的解决方法

import SwiftUI
struct CountDownPicker: View {

var hours = Array(0...23)
var min = Array(0...59)

@Binding var selectedHours: Int
@Binding var selectedMins: Int

var body: some View {
GeometryReader { geometry in
HStack {
Picker(selection: $selectedHours, label: Text("hrs")) {
ForEach(0..<self.hours.count) {
Text("(self.hours[$0]) hrs")
.bold()
}
}
.frame(maxWidth: geometry.size.width / 2)
.clipped()
.pickerStyle(.wheel)

Picker(selection: self.$selectedMins, label: Text("mins")) {
ForEach(0..<self.min.count) {
Text("(self.min[$0]) mins")
.bold()
}
}
.frame(maxWidth: geometry.size.width / 2)
.clipped()
.pickerStyle(.wheel)
}
}
.offset(y: -100)
.padding()
.frame(width: .infinity, height: 140, alignment: .center)

}
}

我愿意接受任何建议

最新更新