关于此主题有几个有用的问题,但是我发现所有这些都使用了早期Beta中不推荐使用的语法(例如BindableObject),或者不需要传递绑定(例如传递给Toggle)。
我想创建绑定到数组中元素的Toggles列表。我尝试了很多方法,但是语法永远不会正确。下面的版本与an existing question的答案最接近。
struct Item: Identifiable {
var id: String { self.name }
var name: String
var enabled: Bool
}
final class ItemSet: ObservableObject {
@Published var items: [Item]
init() {
items = [
Item(name: "aaa", enabled: true),
Item(name: "bbb", enabled: false),
Item(name: "ccc", enabled: true)
]
}
}
var myItems = ItemSet()
struct ContentView: View {
@ObservedObject var items: ItemSet
var body: some View {
List {
ForEach(items.items) { item in
Toggle(item.name, isOn: $item.enabled)
}
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView(items: myItems)
}
}
我在Xcode 11.1中遇到的编译器错误是:
使用未解决的标识符'$ item'
在定义切换的行上。
我的印象是,每个Item
本身都需要是一个带有ObservableObject
参数的@Published var enabled: Bool
,但是我也无法正常工作,并且所有stackoverflow答案似乎是要避免使Item
本身ObservableObject
。
任何帮助将不胜感激。
答案 0 :(得分:1)
您正在将items
(这是当前值主题)的属性包装与Toggle
期望的绑定参数混淆。请参见下面的具有绑定的更正实现:
import SwiftUI
import Combine
struct Item: Identifiable {
var isEnabled: Binding<Bool>
var id: String { self.name }
var name: String
init(name: String, enabled enabledValue: Bool) {
self.name = name
let enabled = CurrentValueSubject<Bool, Never>(enabledValue)
isEnabled = Binding<Bool>(
get: { enabled.value },
set: { enabled.value = $0}
)
}
}
final class ItemSet: ObservableObject {
@Published var items: [Item]
init() {
items = [
Item(name: "aaa", enabled: true),
Item(name: "bbb", enabled: false),
Item(name: "ccc", enabled: true)
]
}
}
var myItems = ItemSet()
struct ContentView: View {
@ObservedObject var items: ItemSet
var body: some View {
List {
ForEach(items.items) { item in
Toggle(isOn: item.isEnabled, label: { Text (item.name) })
}
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView(items: myItems)
}
}