Как определить, что изменило значение @Published в SwiftUI? - PullRequest
0 голосов
/ 15 марта 2020

У меня есть ObservableObject со значением @Published, как я могу определить, было ли значение изменено с помощью вида TextField или оно было установлено напрямую (например, при нажатии Button)?

struct ContentView: View {

    @ObservedObject var model = Model()

    var body: some View {
        VStack {
            Button("set value") {
                self.model.value = "user set value"
            }
            TextField("value", text: $model.value)
        }
    }
}

class Model: ObservableObject {

     @Published var value = ""

     var anyCancellable: AnyCancellable?

      init() {
          anyCancellable = $value.sink { val in
              // if changed by Button then ...
              // if changed by TextField then ...
          }
      }
}

Мой реальный сценарий звучит так: когда пользователь изменяет значение, запрос должен быть отправлен на сервер с новым значением, но сервер также может ответить новым значением (в этом случае новым запросом). на сервер не должен отправляться), поэтому я должен различать guish между случаем, когда пользователь изменяет значение (через TextField), и случаем, когда сервер изменяет значение.

Ответы [ 2 ]

0 голосов
/ 16 марта 2020

Вы можете передать закрытие onEditingChanged инициализатору TextField. Вы должны использовать замыкание для запуска запроса к серверу.

struct ContentView: View {    
    @ObservedObject var model = Model()

    var body: some View {
        VStack {
            Button("set value") {
                self.model.value = "user set value"
            }
            TextField(
                "value",
                text: $model.value,
                onEditingChanged: { _ in self.model.sendServerRequest() )
        }
    }
}
0 голосов
/ 15 марта 2020

Вы можете сделать это с помощью @Binding легко. Я не думаю, что вам нужно использовать @Published Если вы все еще хотите использовать его, вы можете попробовать этот код

struct ContentView: View {

    @ObservedObject var model = Model()

    var body: some View {
        VStack {
            Button("set value") {
                DispatchQueue.main.async{
                     self.model.value = "user set value"
                }
            }
            TextField("value", text: $model.value)
        }
    }
}
...