想要知道目前行動裝置的電池電量與電池狀態(例如:充電或未充電),可以透過 UIDevice 的 batteryLevel 與 batteryState 取得。但是要在值有變化時會主動通知我們,就需要透過 NotificationCenter 來完成。
在 SwiftUI 中要做到這一點,可以呼叫 NotificationCenter 的 publisher 函數,這樣就不再需要使用 #selector 再加上一個 @objc 修飾的函數來設定 callback function,讓整個語法上簡潔許多。下面的程式碼可以在電池電量或是充電狀態改變時通知 App 要更新內容了。
struct ContentView: View {
@State private var level: Float = 0
@State private var state = ""
private let levelPublish = NotificationCenter.default.publisher(
for: UIDevice.batteryLevelDidChangeNotification
)
private let statePublish = NotificationCenter.default.publisher(
for: UIDevice.batteryStateDidChangeNotification
)
var body: some View {
HStack {
Text(state)
Text("\(Int(level * 100)) %")
}
.onReceive(levelPublish) { output in
// 電池電量
level = UIDevice.current.batteryLevel
}
.onReceive(statePublish) { output in
// 充電狀態
state = batteryState()
}
.onAppear {
UIDevice.current.isBatteryMonitoringEnabled = true
level = UIDevice.current.batteryLevel
state = batteryState()
}
.padding()
}
private func batteryState() -> String {
switch UIDevice.current.batteryState {
case .charging:
return "充電中"
case .full:
return "滿電"
case .unplugged:
return "使用電池"
case .unknown:
return "未知"
@unknown default:
fatalError()
}
}
}