從 iOS17 開始,對於 KVO(Key-Value Observing)機制 ,Xcode 提供了一個新的框架,稱為Observation。之前,我們用的是Combine框架。
先來看下面這個計數器例子,這段程式碼會在畫面出現時啟動計數器,雖然每秒更新一次計數器內容,但畫面上永遠顯示都是0,因為計數器內容的改變並不會通知Text元件要更新。
class Counter {
var n = 0
init() {
Timer.scheduledTimer(withTimeInterval: 1, repeats: true) { _ in
self.n += 1
}
}
}
struct ContentView: View {
var counter = Counter()
var body: some View {
Text(counter.n, format: .number)
}
}
如果要讓Text立即呈現計數器內容,在使用Combine框架時,程式要這樣寫。
class Counter: ObservableObject {
@Published var n = 0
init() {
Timer.scheduledTimer(withTimeInterval: 1, repeats: true) { _ in
self.n += 1
}
}
}
struct ContentView: View {
@ObservedObject var counter = Counter()
var body: some View {
Text(counter.n, format: .number)
}
}
由於Swift 5.9中加入了Macro語法,很多事情變的簡單許多,因此當使用新的Observation框架時,程式碼變成下面這樣。在@Observable加持下,class中的每一個屬性都是@Published。
@Observable
class Counter {
var n = 0
init() {
Timer.scheduledTimer(withTimeInterval: 1, repeats: true) { _ in
self.n += 1
}
}
}
struct ContentView: View {
let counter = Counter()
var body: some View {
Text(counter.n, format: .number)
}
}