11

每次textField更改 a 的值时,我都会尝试执行一个操作。

@Published var value: String = ""

var body: some View {            
     $value.sink { (val) in
        print(val)
     }
     return TextField($value)       
}

但我得到以下错误。

无法将“已发布”类型的值转换为预期的参数类型“绑定”

4

4 回答 4

22

这应该是一种非脆弱的方式:

class MyData: ObservableObject {
    var value: String = "" {
        willSet(newValue) {
            print(newValue)
        }
    }
}

struct ContentView: View {
    @ObservedObject var data = MyData()
    var body: some View {
        TextField("Input:", text: $data.value)
    }
}
于 2019-09-26T12:55:57.940 回答
8

在您的代码中,$value是发布者,同时TextField需要绑定。虽然您可以从@Publishedto@State甚至更改@Binding,但在值更改时无法观察到事件。

似乎没有办法观察绑定。

另一种方法是使用ObservableObject包装您的值类型,然后观察发布者 ( $value)。

class MyValue: ObservableObject {
  @Published var value: String = ""
  init() {
    $value.sink { ... }
  }
}

然后在您看来,您拥有了 binding $viewModel.value

struct ContentView: View {
    @ObservedObject var viewModel = MyValue()
    var body: some View {
        TextField($viewModel.value)
    }
}
于 2020-03-28T11:49:36.037 回答
4

我不为此使用 combine 。这对我有用:

 TextField("write your answer here...",
            text: Binding(
                     get: {
                        return self.query
                       },
                     set: { (newValue) in
                        self.fetch(query: newValue) // any action you need
                                return self.query = newValue
                      }
            )
  )

不得不说这不是我的主意,我是在这篇博客中看到的:SwiftUI 绑定:一个非常简单的技巧

于 2020-01-05T12:37:18.407 回答
2

如果你想观察,value那么它应该是一个State

@State var value: String = ""
于 2019-06-24T11:30:23.080 回答