在 SwiftUI 视图中设置计算属性无法编译

Posted

技术标签:

【中文标题】在 SwiftUI 视图中设置计算属性无法编译【英文标题】:setting computed property in a SwiftUI view doesn't compile 【发布时间】:2020-06-12 13:39:45 【问题描述】:

尝试在 SwiftUI 视图中设置计算属性 s 会导致编译器错误“无法分配给属性:'self' 是不可变的”。 我该如何调用 setter?

struct Test: View
  @State var _s = "test"
  @State var _s2 = true
  private var s : String
   get  _s 
    set (new)
     _s = "no test"
      _s2 = false
      // do something else
    
  

  var body: some View
   Text("\(s)")
    .onTapGesture 
      self.s = "anyting"  // compiler error
    
  

【问题讨论】:

您实际上是在尝试复制 @State 行为...为什么?视图是结构,值,它不能从内部修改自己,这就是为什么有@State - 它是为了你尝试做的事情。就用它吧。 @Asperi 我想在设置s的时候改变一些其他的状态,我会扩展例子 【参考方案1】:

啊哈……我明白了。只需使用非变异集

  private var s : String
   get  _s 
    nonmutating set (new)
     _s = "no test"
      _s2 = false
      // do something else
    
  

【讨论】:

【参考方案2】:

也就是说,为什么您的视图中已经有了 @State 属性包装器。

struct Test: View
  @State var s = "test"
    var body: some View 
    Text("\(s)")
    .onTapGesture 
      self.s = "anyting"  // compiler error
    
  

您可以直接从代码中更改 s,因为 s 用 @State 包装。

这与上面的功能等效

struct Test: View
    let s = State<String>(initialValue: "alfa")
    var body: some View 
        VStack 
            Text("\(s.wrappedValue)")
                .onTapGesture 
                    self.s.wrappedValue = "beta"
            
        
    

或者如果需要绑定

struct Test: View
    let s = State<String>(initialValue: "alfa")
    var body: some View 
        VStack 
            TextField("label", text: s.projectedValue)
        
    

【讨论】:

我想在设置s的时候改变一些其他的状态,我会扩展例子

以上是关于在 SwiftUI 视图中设置计算属性无法编译的主要内容,如果未能解决你的问题,请参考以下文章

SwiftUI 基于计算属性显示警报

SwiftUI 中的计算(NSObject)属性不会更新视图

SwiftUI:具有计算属性的 ObservableObject

SwiftUI 计算属性显示“在视图更新期间修改状态,这将导致未定义的行为。”错误

SwiftUI:如何在函数计算 @State 值时同时更新视图?

SwiftUI:如何计算文本视图的宽度?