半相關問題:SwiftUI ActionSheet 在計時器運行時不會關閉
我目前在我正在進行的專案中遇到警報問題。當有計時器在后臺運行時,顯示的警報不會解除。大多數情況下,它需要點擊幾下關閉按鈕才能消失。我在示例專案中以盡可能少的開銷重新創建了這個問題。
我的主要專案在嘗試在不同視圖上顯示警報時出現此問題,但我無法在示例專案中重現該問題。通過在計時器運行的同一視圖上切換警報,可以可靠地復制該問題。我還通過從文本欄位中洗掉系結來阻止文本欄位視圖更新來進行測驗。第一次單擊時警報仍然無法解除。我不確定是否有辦法解決這個問題,我正在尋找任何可能的建議。
Xcode 13.0/iOS 15.0 和 iOS 14.0 中也出現
Timerview.swift
struct TimerView: View {
@ObservedObject var stopwatch = Stopwatch()
@State var isAlertPresented:Bool = false
var body: some View {
VStack{
Text(String(format: "%.1f", stopwatch.secondsElapsed))
.font(.system(size: 70.0))
.minimumScaleFactor(0.1)
.lineLimit(1)
Button(action:{
stopwatch.actionStartStop()
}){
Text("Toggle Timer")
}
Button(action:{
isAlertPresented.toggle()
}){
Text("Toggle Alert")
}
}
.alert(isPresented: $isAlertPresented){
Alert(title:Text("Error"),message:Text("I am presented"))
}
}
}
秒表.swift
class Stopwatch: ObservableObject{
@Published var secondsElapsed: TimeInterval = 0.0
@Published var mode: stopWatchMode = .stopped
func actionStartStop(){
if mode == .stopped{
start()
}else{
stop()
}
}
var timer = Timer()
func start() {
secondsElapsed = 0.0
mode = .running
timer = Timer.scheduledTimer(withTimeInterval: 0.1, repeats: true) { timer in
self.secondsElapsed = 0.1
}
}
func stop() {
timer.invalidate()
mode = .stopped
}
enum stopWatchMode {
case running
case stopped
}
}
編輯:將按鈕移動到自定義視圖解決了最初的問題,但是當按鈕需要與 Observable 物件互動時是否有解決方案?
Button(action:{
do{
try stopwatch.actionDoThis()
}catch{
isAlertPresented = true
}
}){
Text("Toggle Alert")
}.alert(isPresented: $isAlertPresented){
Alert(title:Text("Error"),message:Text("I am presented"))
uj5u.com熱心網友回復:
每次計時器運行時 UI 都會重新創建,因為“secondsElapsed”是一個可觀察物件。SwiftUI 將自動監視“secondsElapsed”中的變化,并重新呼叫視圖的 body 屬性。為了避免這種情況,我們需要將按鈕和警報分開到另一個視圖,如下所示。
struct TimerView: View {
@ObservedObject var stopwatch = Stopwatch()
@State var isAlertPresented:Bool = false
var body: some View {
VStack{
Text(String(format: "%.1f", stopwatch.secondsElapsed))
.font(.system(size: 70.0))
.minimumScaleFactor(0.1)
.lineLimit(1)
Button(action:{
stopwatch.actionStartStop()
}){
Text("Toggle Timer")
}
CustomAlertView(isAlertPresented: $isAlertPresented)
}
}
}
struct CustomAlertView: View {
@Binding var isAlertPresented: Bool
var body: some View {
Button(action:{
isAlertPresented.toggle()
}){
Text("Toggle Alert")
}.alert(isPresented: $isAlertPresented){
Alert(title:Text("Error"),message:Text("I am presented"))
}
}
}
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/334837.html
