我在SwiftUI Picker
中有一个Form
,并且每当选择器发生更改时,我都试图处理该值。我希望能够使用didSet
在代表当前所选值的变量上执行此操作。
import SwiftUI
struct ContentView: View {
enum TransmissionType: Int {
case automatic
case manual
}
@State private var selectedTransmissionType: Int = TransmissionType.automatic.rawValue {
didSet {
print("selection changed to \(selectedTransmissionType)")
}
}
private let transmissionTypes: [String] = ["Automatic","Manual"]
var body: some View {
NavigationView {
Form {
Section {
Picker(selection: $selectedTransmissionType,label: Text("Transmission Type")) {
ForEach(0 ..< transmissionTypes.count) {
Text(self.transmissionTypes[$0])
}
}
}
}
}
}
}
Picker
UI(通常)按预期工作:我可以看到已选择默认值,点击选择器,打开一个新视图,我可以选择其他值,然后返回到并向我显示新值已被选择。但是,didSet
永远不会被调用。
我看到了this question,但对我来说,向变量View
添加更多内容,而不是仅仅在变量更改时处理新值,即使有可能,这似乎很奇怪。使用onReceive
会更好,尽管会导致更复杂的视图?我的主要问题是:我的代码有什么问题,可防止调用didSet
?
我使用this example到了这一点。
除了我的常规问题外,我还有其他一些有关此示例的信息:
A)看起来很奇怪,我有一个enum
和一个Array
来代表相同的两个值。有人还能建议一种更好的方法来构造它以避免这种冗余吗?我考虑过一个TransmissionType
对象,但与enum
相比似乎有点过分了……也许不是吗?
B)当点击选择器时,带有选择器选项的屏幕会滑过,然后两个选项会略微跳起来。这让人感到震撼,跳动,并带来糟糕的用户体验。我在这里做错了什么导致UX错误吗?还是可能是SwiftUI错误?每次更改选择器时都会出现此错误:
[TableView] Warning once only: UITableView was told to layout its visible cells and other contents without being in the view hierarchy (the table view or one of its superviews has not been added to a window). This may cause bugs by forcing views inside the table view to load and perform layout without accurate information (e.g. table view bounds,trait collection,layout margins,safe area insets,etc),and will also cause unnecessary performance overhead due to extra layout passes. Make a symbolic breakpoint at UITableViewAlertForLayoutOutsideViewHierarchy to catch this in the debugger and see what caused this to occur,so you can avoid this action altogether if possible,or defer it until the table view has been added to a window.