You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

WKScriptMessage回调中执行performSegue报错,同VC其他场景正常求解

问题分析与解决方案

这个问题我之前做WKWebView交互时也碰到过,核心原因主要有两个,咱们一步步拆解:

1. JS消息回调不在主线程(最常见的坑)

WKWebView的userContentController(_:didReceive:)方法是在后台线程触发的,而iOS要求所有UI操作(包括Segue跳转)必须在主线程执行。而你提到的didStartProvisionalNavigation方法是WebKit在主线程回调的,所以那里执行跳转完全正常。

解决办法很简单,把Segue调用包裹到主线程队列里就行:

func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
    // 强制在主线程执行UI操作
    DispatchQueue.main.async {
        self.performSegue(withIdentifier: "segueError2", sender: self)
    }
}

2. 视图控制器的视图尚未加入窗口层级

如果加了主线程调用还是报错,那就要考虑:收到JS消息时,simpleBrowerVC的视图可能还没完全加载到应用窗口中(比如VC刚被push但还没完成展示,或者已经被弹出销毁了)。

可以加个安全检查,确保当前VC的视图确实在窗口层级里:

func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
    DispatchQueue.main.async {
        // 先确认视图已加载且在窗口中
        guard self.isViewLoaded, self.view.window != nil else {
            print("simpleBrowerVC的视图不在窗口层级,无法执行Segue")
            return
        }
        self.performSegue(withIdentifier: "segueError2", sender: self)
    }
}

额外小建议

  • 可以在viewDidAppear(_:)里加个标记位,比如private var isViewReady = false,在viewDidAppear里设为true,然后接收消息时先判断这个标记,避免在视图还没显示时触发跳转。
  • 如果JS消息是页面加载早期就发送的,建议调整JS逻辑,等页面完全加载完成后再给原生发消息,这样能避免时机问题。

内容的提问来源于stack exchange,提问作者Greensouth

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.26 10:47:54