SwiftUI:didSet 不更新视图

SwiftUI: didSet doesn't update view

在下面的复制示例中,我有以下构成单个屏幕的代码。代码很多,但是很简单!

预期功能:屏幕填充纯色。在颜色下方,有一个选择器(在这个例子中是 DisclosureGroup,但我认为使用哪种类型的选择器并不重要。),这个选择器允许用户在 mode1mode2。屏幕开始填充黑色,一旦用户选择一种模式,黑色视图应使用 mode 变量上的 didSet 变为红色。

问题主要是mode变量的didSet。我知道 mode 正在更新,因为标签(注释为“显示当前模式”)正在更改。但是,视图本身的颜色并未更新,如 didSet

中所定义

我检查了 ,我有一个 @State,但问题仍然存在。

我没有出错,我是 运行 XCode 13.2

代码:

struct ContentView: View {
    @State var color: Color = .black               //COLOR BEING SHOWN

    @State var mode: SHModes = .mode1 {            //CURRENT MODE
        didSet {
            color = .red
        }
    }
    
    public enum SHModes {                         //MODE OPTIONS
        case mode1, mode2
    }
    
    var body: some View {
        VStack {
            color                         
            ModePicker(mode: $mode)
        }
    }
    
    
    struct ModePicker: View {
        
        @Binding var mode: SHModes               //BINDING TO CONTENTVIEW MODE

        @State var clicked = false            //the rest is irrelevant code , just changes the binding variable above
        
        var body: some View {
            DisclosureGroup(isExpanded: $clicked, content: {
                VStack {
                    if mode != .mode1 {
                        Text("Mode 1")
                            .onTapGesture {
                                mode = .mode1
                                clicked.toggle()
                            }
                    }
                    if mode != .mode2 {
                        Text("Mode 2")
                            .onTapGesture {
                                mode = .mode2
                                clicked.toggle()
                            }
                    }
                }
            }, label: {
                Text(mode == .mode1 ? "mode1" : "mode2")    //label for current mode, proves `mode` is being changed
            })
        }
    }
}

我怀疑这与我绑定 mode 值的方式有关,但为什么在调用 didSet 时视图上的颜色没有更新?

改用.onChange(of:...,喜欢

var body: some View {
    VStack {
        color                         
        ModePicker(mode: $mode)
          .onChange(of: mode) { _ in // or with arg if needed
             color = .red     // << here 
          }
    }
}