3

我使用带有选择器的表单,一切正常(我可以从选择器中选择一个元素),但我无法取消选择它。是否存在从选择器中取消选择项目的方法?谢谢!

在此处输入图像描述

Picker(selection: $model.countries, label: Text("country")) {
                        ForEach(model.countries, id: \.self) { country in
                            Text(country!.name)
                                .tag(country)
                        }
                    }
4

4 回答 4

4

要取消选择,我们需要选择器值的可选存储,所以这里是一个可能的方法的演示。

使用 Xcode 12.1 / iOS 14.1 测试

演示

struct ContentView: View {
    @State private var value: Int?
    var body: some View {
        NavigationView {
            Form {
                let selected = Binding(
                    get: { self.value },
                    set: { self.value = $0 == self.value ? nil : $0 }
                )
                Picker("Select", selection: selected) {
                    ForEach(0...9, id: \.self) {
                        Text("\($0)").tag(Optional($0))
                    }
                }
            }
        }
    }
}
于 2021-01-27T18:00:44.427 回答
2

通过阅读Jim Dovey的这篇博客,我几乎了解了所有关于 SwiftUI 绑定(使用核心数据)的知识。剩下的就是一些研究和数小时犯错的结合。

因此,当我将 JimExtensions在 SwiftUI上创建的技术Binding与 Asperi 的答案相结合时,我们最终会得到这样的结果......

public extension Binding where Value: Equatable {
    init(_ source: Binding<Value>, deselectTo value: Value) {
        self.init(get: { source.wrappedValue },
                  set: { source.wrappedValue = $0 == source.wrappedValue ? value : $0 }
        )
    }
}

然后可以像这样在整个代码中使用它......

Picker("country", selection: Binding($selection, deselectTo: nil)) { ... }

或者

Picker("country", selection: Binding($selection, deselectTo: someOtherValue)) { ... }
于 2021-07-18T10:46:37.337 回答
0

首先,我们可以修复选择。它应该与标签的类型相匹配。标签是给定的Country,所以要选择什么都不能选择,我们应该使用Country?类型selection

它应该看起来像这样:

struct ContentView: View {
    
    @ObservedObject private var model = Model()
    @State private var selection: Country?
    
    var body: some View {
        NavigationView {
            Form {
                Picker(selection: $selection, label: Text("country")) {
                    ForEach(model.countries, id: \.self) { country in
                        Text(country!.name)
                            .tag(country)
                    }
                }
                
                Button("Clear") {
                    selection = nil
                }
            }
        }
    }
}

然后,您只需将 设置selectionnil,这是在按钮中完成的。您可以通过任何您想要的操作selection来设置。nil

于 2021-01-27T18:01:57.273 回答
0

如果您的部署目标设置为 iOS 14 或更高版本——Apple 为 View 提供了一个内置的 onChange 扩展,您可以在其中使用标签取消选择您的行,可以像这样使用它(谢谢)

Picker(selection: $favoriteColor, label: Text("Color")) {
    // ..
}
.onChange(of: favoriteColor) { print("Color tag: \($0)") }
于 2021-01-27T18:04:43.547 回答