SwiftUI距离传感器报错:Found no UIEvent for backing event of type:14 求助
问题
测试距离传感器(Proximity Sensor)时,每次触发传感器,错误日志都会反复出现以下信息:
2023-10-03 02:37:36.095925+0900 PushUp[40969:7329614] [EventDispatcher] Found no UIEvent for backing event of type: 14; contextId: 0x0
对应的SwiftUI实现代码如下:
import SwiftUI struct ProximitySensor: View { @State private var theNumber = 30 let TTS = TextToSpeech() let device = UIDevice.current init() { device.isProximityMonitoringEnabled = true } var body: some View { VStack { Text("\(theNumber)") .id("theNumber" + "\(theNumber)") .font(.system(size: 100)) .fontWeight(.heavy) .italic() }.onReceive(NotificationCenter.default.publisher( for: UIDevice.proximityStateDidChangeNotification), perform: { _ in if UIDevice.current.proximityState { theNumber += 1 let toHan = getOrdinaryNumber(theNumber) TTS.speak(text: toHan) } } ) } }
错误修复与优化方案
错误修复
这条日志属于系统级警告,并非代码逻辑错误,但可通过调整操作时机消除:
- 问题本质:距离传感器状态变化通知触发时,SwiftUI视图更新与系统事件调度存在短暂时序差,导致系统找不到对应UIEvent。
- 修复代码:在处理通知时延迟执行业务逻辑,给系统留出事件调度时间:
.onReceive(NotificationCenter.default.publisher(for: UIDevice.proximityStateDidChangeNotification)) { _ in DispatchQueue.main.asyncAfter(deadline: .now() + 0.05) { if UIDevice.current.proximityState { theNumber += 1 let toHan = getOrdinaryNumber(theNumber) TTS.speak(text: toHan) } } }
更优实现方式
1. 封装传感器管理逻辑
将传感器的启用、状态监听封装到独立的ObservableObject中,分离视图与业务逻辑:
class ProximityManager: ObservableObject { @Published var proximityState = false private let device = UIDevice.current init() { device.isProximityMonitoringEnabled = true NotificationCenter.default.addObserver( self, selector: #selector(updateProximityState), name: UIDevice.proximityStateDidChangeNotification, object: nil ) } @objc private func updateProximityState() { proximityState = device.proximityState } deinit { NotificationCenter.default.removeObserver(self) } }
2. 简化视图层实现
使用@StateObject订阅传感器状态,代码更简洁易维护:
struct ProximitySensor: View { @State private var theNumber = 30 @StateObject private var proximityManager = ProximityManager() let TTS = TextToSpeech() var body: some View { VStack { Text("\(theNumber)") .font(.system(size: 100, weight: .heavy)) .italic() } .onChange(of: proximityManager.proximityState) { newState in if newState { DispatchQueue.main.asyncAfter(deadline: .now() + 0.05) { theNumber += 1 let toHan = getOrdinaryNumber(theNumber) TTS.speak(text: toHan) } } } } }
3. 其他细节优化
- 移除不必要的
.id("theNumber" + "\(theNumber)"):SwiftUI会自动根据@State变量变化更新视图,手动设置id易引发不必要的视图重建。 - 合并字体设置:将
.font(.system(size: 100))与.fontWeight(.heavy)合并为.font(.system(size: 100, weight: .heavy)),简化代码。
内容的提问来源于stack exchange,提问作者goodman
相关产品推荐
相关产品推荐

