SwiftUI中UITextViewRepresentable模拟器NaN警告问题求助
UITextViewRepresentable鼠标悬停模拟器弹出NaN警告的问题解决
问题描述
在SwiftUI应用中使用UITextViewRepresentable时,鼠标悬停文本区域时模拟器会弹出以下警告:
Error: this application, or a library it uses, has passed an invalid numeric value (NaN, or not-a-number) to CoreGraphics API and this value is being ignored. Please fix this problem.
If you want to see the backtrace, please set CG_NUMERICS_SHOW_BACKTRACE
该问题仅在模拟器中出现,真机上无法复现。开启CG_NUMERICS_SHOW_BACKTRACE后得到调用栈:
2023-06-04 10:21:38.983039+0100 TextViewRepresentable[12699:10411840] [Unknown process name] Error: this application, or a library it uses, has passed an invalid numeric value (NaN, or not-a-number) to CoreGraphics API and this value is being ignored. Please fix this problem. 2023-06-04 10:21:38.992493+0100 TextViewRepresentable[12699:10411840] [Unknown process name] Backtrace: <CGPathMoveToPoint+71> <+[UIBezierPath _continuousRoundedRectBezierPath:withRoundedCorners:cornerRadii:segments:smoothPillShapes:]+1636> <+[UIBezierPath _continuousRoundedRectBezierPath:withRoundedCorners:cornerRadius:segments:]+170> <+[UIBezierPath _roundedRectBezierPath:withRoundedCorners:cornerRadius:segments:legacyCorners:]+337> <-[UIScrollViewAccessibility accessibilityPath]+1575> <-[NSObject(AXPrivCategory) _accessibilityBaseHitTest:withEvent:]+2879> <-[NSObject(AXPrivCategory) _accessibilityHitTest:withEvent:]+92> <-[UIViewAccessibility _accessibilityHitTest:withEvent:]+154> <-[UIViewAccessibility __accessibilityHitTest:withEvent:]+1675> <-[UIViewAccessibility _accessibilityHitTest:withEvent:]+101> <__64-[NSObject(AXPrivCategory) _accessibilityBaseHitTest:withEvent:]_block_invoke.243+180> <-[NSObject(AXPrivCategory) _accessibilityBaseHitTest:withEvent:]+4038> <-[NSObject(AXPrivCategory) _accessibilityHitTest:withEvent:]+92> <-[UIViewAccessibility _accessibilityHitTest:withEvent:]+154> <-[UIViewAccessibility __accessibilityHitTest:withEvent:]+1675> <-[UIViewAccessibility _accessibilityHitTest:withEvent:]+101> <-[UIViewAccessibility __accessibilityHitTest:withEvent:]+1675> <-[UIViewAccessibility _accessibilityHitTest:withEvent:]+101> <-[UIViewAccessibility __accessibilityHitTest:withEvent:]+1675> <-[UIViewAccessibility _accessibilityHitTest:withEvent:]+101> <-[UIWindowAccessibility _accessibilityHitTest:withEvent:]+138> <_copyElementAtPositionCallback+5184> <___AXXMIGCopyElementAtPosition_block_invoke+79> <_handleNonMainThreadCallback+424> <_AXXMIGCopyElementAtPosition+670> <_XCopyElementAtPosition+521> <mshMIGPerform+1024> <__CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE1_PERFORM_FUNCTION__+41> <__CFRunLoopDoSource1+538> <__CFRunLoopRun+2671> <CFRunLoopRunSpecific+560> <GSEventRunModal+139> <-[UIApplication _run]+994> <UIApplicationMain+123> <__swift_memcpy93_8+12403> <__swift_memcpy93_8+12076> <__swift_memcpy195_8+14237> <$s21TextViewRepresentable0abC3AppV5$mainyyFZ+30> <main+9> 107c8d384
严重性分析
- 从调用栈看,问题出在辅助功能(Accessibility)相关的CoreGraphics路径绘制流程中,模拟器触发了NaN值传入,但CoreGraphics已主动忽略该无效值,不会导致应用崩溃。
- 仅在模拟器中出现、真机无复现,说明这大概率是模拟器的兼容性bug,不会影响线上用户的使用体验。
- 虽然当前不影响功能,但如果后续iOS版本更新或模拟器环境变化,不排除问题扩大的可能,建议尽量修复。
解决方法
1. 检查UITextViewRepresentable中的布局参数
确保配置UITextView时,所有和圆角、尺寸相关的参数没有计算出NaN值:
- 排查是否存在除以0的计算逻辑,比如动态计算圆角半径时的除数是否可能为0。
- 确保
contentInset、cornerRadius等属性的赋值都是有效的非NaN数值。
示例代码(避免NaN):
func makeUIView(context: Context) -> UITextView { let textView = UITextView() // 用max兜底避免动态值出现0或负数,确保圆角半径有效 textView.layer.cornerRadius = max(8, dynamicCornerValue) textView.contentInset = UIEdgeInsets(top: 8, left: 8, bottom: 8, right: 8) return textView }
2. 重写UIScrollView的accessibilityPath
调用栈指向UIScrollViewAccessibility的accessibilityPath方法,可自定义UITextView子类,重写该方法过滤NaN点:
class FixedAccessibilityTextView: UITextView { override var accessibilityPath: UIBezierPath? { guard let superPath = super.accessibilityPath else { return nil } let cleanedPath = UIBezierPath() superPath.forEach { element in switch element.type { case .moveToPoint: let point = element.points[0] if !point.x.isNaN && !point.y.isNaN { cleanedPath.move(to: point) } case .addLineToPoint: let point = element.points[0] if !point.x.isNaN && !point.y.isNaN { cleanedPath.addLine(to: point) } case .addCurveToPoint: let cp1 = element.points[0] let cp2 = element.points[1] let end = element.points[2] if !cp1.x.isNaN && !cp1.y.isNaN && !cp2.x.isNaN && !cp2.y.isNaN && !end.x.isNaN && !end.y.isNaN { cleanedPath.addCurve(to: end, controlPoint1: cp1, controlPoint2: cp2) } default: cleanedPath.append(element) } } return cleanedPath.isEmpty ? superPath : cleanedPath } }
之后在UITextViewRepresentable中使用该子类:
struct TextViewRepresentable: UIViewRepresentable { func makeUIView(context: Context) -> FixedAccessibilityTextView { FixedAccessibilityTextView() } func updateUIView(_ uiView: FixedAccessibilityTextView, context: Context) { // 你的更新逻辑 } }
3. 临时禁用模拟器辅助功能
如果暂时无法修复代码,可在模拟器中关闭辅助功能:
- 打开模拟器「设置」→「辅助功能」,关闭VoiceOver、Switch Control等选项,但这只是临时方案,无法从代码层面解决问题。
4. 更新Xcode和模拟器版本
该问题可能是旧版本模拟器的bug,尝试更新到最新的Xcode和iOS模拟器版本,看是否已被苹果修复。
内容的提问来源于stack exchange,提问作者reza23
相关产品推荐
相关产品推荐

