Ios 如何聆听可观察对象
好的,iOS 13上的SwiftUI和ObservableObject。我有一个实现ObservieObject的模型:Ios 如何聆听可观察对象,ios,swift,observable,swiftui,Ios,Swift,Observable,Swiftui,好的,iOS 13上的SwiftUI和ObservableObject。我有一个实现ObservieObject的模型: class Model: ObservableObject { @Published public var toggle: Bool = false init() { NSLog("Model init") objectWillChange.sink { void in NSLog("1 toggle
class Model: ObservableObject {
@Published public var toggle: Bool = false
init() {
NSLog("Model init")
objectWillChange.sink { void in
NSLog("1 toggle \(self.toggle)")
}
$toggle.sink { v in
NSLog("2 toggle \(self.toggle) -> \(v)")
}
}
}
和一个切换切换的按钮:
struct ContentView: View {
@ObservedObject var model: Model
var body: some View {
Button(action: {
self.model.toggle.toggle()
}, label: {Text(model.toggle ? "on" : "off")})
}
}
现在,这是可行的。你按下按钮,它会在“开”和“关”之间切换。(在进行切换之前,
@Published
,它没有执行此操作。)但是,日志记录无法按预期工作。我在启动时立即得到两个日志:“modelinit”和“2 toggle false->false”。点击按钮,虽然显然改变了切换的值
,但不会导致任何一个闭包执行
当视图改变您的模型时,我希望有一种方法可以通知更改,以防您需要更新计算值或同步到磁盘或其他东西。也许sink
是错误的方法
具有@已发布的字段的可观察对象如何在其字段更新时得到通知?函数返回值的最新文档:
//-返回:一个可取消的实例;结束对接收值的赋值时使用。取消分配结果将中断订阅流。
本质上,这意味着sink创建了一个订户,但不保留它。一旦初始化完成,订阅服务器就会被删除并从内存中删除。您需要通过创建如下强引用来保持它们:
class Model: ObservableObject {
@Published public var toggle: Bool = false
var changeSink: AnyCancellable?
var toggleSink: AnyCancellable?
init() {
NSLog("Model init")
changeSink = objectWillChange.sink { void in
NSLog("1 toggle \(self.toggle)")
}
toggleSink = $toggle.sink { v in
NSLog("2 toggle \(self.toggle) -> \(v)")
}
}
}
我没有使用过很多<代码>合并,但我经常看到的一个选择,就是把一个<代码> DIDSET 添加到你的属性中,如:
@Published public var toggle: Bool = false {
didSet {
print("1 toggle \(self.toggle)")
}
}
您的ObservieObject类模型已正确完成,但:
1。ObjectWillChange的类型应为ObservableObjectPublisher()
创建objectWillChange属性作为的实例
ObservieObjetPublisher。这来自于Combine框架,该框架
这就是为什么需要添加import Combine来编译代码。这个
可观察对象发布者的工作很简单:只要我们愿意
告诉全世界我们的目标已经改变,我们要求出版商去做
这是给我们的
2。您需要观察的属性(切换)的实现方式如下:
var toggle = "" {
willSet {
objectWillChange.send()
}
}
第二,我们将一个willSet属性观察器附加到切换
属性,以便我们可以随时运行代码
价值变化。在您的示例代码中,我们调用objectWillChange.send()
无论何时切换更改,这都会告诉objectWillChange
发布者发布我们的数据已更改的消息,以便
订阅的视图可以刷新
3。确保您的类模型符合ObserveObject,并且its实例标记为@ObserveObject
由于您的模型类符合ObserveObject,您可以
使用它就像使用任何其他@ObservedObject属性一样。所以,我们可以使用
观看切换时会像这样,如下所示:
class Model: ObservableObject {
@Published public var toggle: Bool = false
var changeSink: AnyCancellable?
var toggleSink: AnyCancellable?
init() {
NSLog("Model init")
changeSink = objectWillChange.sink { void in
NSLog("1 toggle \(self.toggle)")
}
toggleSink = $toggle.sink { v in
NSLog("2 toggle \(self.toggle) -> \(v)")
}
}
}
希望这有帮助,
参考:
啊,这就是我所缺少的!谢谢有时我可能会使用didSet
,但知道如何使用objectWillChange同时监视所有内容也很好objectDidChange
可能也很不错,但我认为至少在默认情况下,我们并没有这样做。