为何SwiftUI中toggle()函数与显式切换代码效果不一致?
SwiftUI中toggle()无法触发视图更新的问题
初始可运行代码
主文件
import SwiftUI struct Home: View { @State private var ToDoItems: [ToDoItem] = [ToDoItem(title: "Task", description: "Need to do", urgent: false)] @State private var isAddingToDo: Bool = false var body: some View { VStack { ScrollView { ForEach(ToDoItems.indices, id: \.self) { index in HStack { Button { if ToDoItems[index].done { ToDoItems[index].done = false } else { ToDoItems[index].done = true } } label: { if ToDoItems[index].done { Image(systemName: "square.fill") } else { Image(systemName: "square") } } Text(ToDoItems[index].title) .font(.title) } .padding() } } } } }
ToDoItem 声明
import SwiftUI struct ToDoItem: Identifiable { var title: String var createdAt: NSDate = NSDate() var id = UUID() var description: String var done = false var urgent: Bool init(title: String, description: String, done: Bool = false, urgent: Bool) { self.title = title self.description = description self.done = done self.urgent = urgent } }
ToDoItem结构体中的done属性是默认值为false的布尔类型。
问题场景
将按钮点击事件的代码替换为使用toggle()后,视图不再更新:
原代码:
Button { if ToDoItems[index].done { ToDoItems[index].done = false } else { ToDoItems[index].done = true } } label: { if ToDoItems[index].done { Image(systemName: "square.fill") } else { Image(systemName: "square") } }
替换后的代码:
Button { ToDoItems[index].done.toggle() } label: { if ToDoItems[index].done { Image(systemName: "square.fill") } else { Image(systemName: "square") } }
明明toggle()的逻辑和手动赋值完全一致,为什么视图不会更新?
解决方法
在ToDoItem结构体中为done属性显式添加Bool类型声明后,问题解决。
更新后的ToDoItem声明
import SwiftUI struct ToDoItem: Identifiable { var title: String var createdAt: NSDate = NSDate() var id = UUID() var description: String var done: Bool = false // 更新行 var urgent: Bool init(title: String, description: String, done: Bool = false, urgent: Bool) { self.title = title self.description = description self.done = done self.urgent = urgent } }
内容的提问来源于stack exchange,提问作者Simon
相关产品推荐
相关产品推荐

