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

Xcode 12.5及Swift 5+环境下WKWebView如何打开外部链接到Safari

解决方法

现有代码的问题

  • 未给WKWebView设置navigationDelegate,导致拦截跳转的代理方法无法触发
  • 跳转拦截方法内部存在重复执行的逻辑冲突,分支判断和外部执行语句重复调用了打开链接和decisionHandler方法,会导致逻辑异常

修改步骤

  1. 让当前ViewController遵守WKNavigationDelegate协议
  2. 初始化WKWebView时绑定navigationDelegate
  3. 清理拦截方法内的冗余逻辑,仅拦截http/https协议的外部跳转调用系统Safari打开,本地file协议的资源正常在WebView内加载

修正后完整代码

import UIKit
import WebKit
import PDFKit

// 遵守WKNavigationDelegate协议
class ViewController: UIViewController, WKUIDelegate, WKNavigationDelegate {
    
    var webView: WKWebView!
    
    override func loadView() {
        let webConfiguration = WKWebViewConfiguration()
        webView = WKWebView(frame: .zero, configuration: webConfiguration)
        webView.uiDelegate = self
        // 绑定navigationDelegate
        webView.navigationDelegate = self
        view = webView
    }

    override func viewDidLoad() {
        super.viewDidLoad()
        
        guard let url = Bundle.main.url(forResource: "index", withExtension: "html", subdirectory: "www") else { return }
        webView.loadFileURL(url, allowingReadAccessTo: url.deletingLastPathComponent())
        let request = URLRequest(url: url)
        webView.load(request)
    }
    
    // WKNavigationDelegate 跳转拦截方法
    func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
        // 仅拦截用户点击触发的链接跳转
        guard navigationAction.navigationType == .linkActivated,
              let url = navigationAction.request.url,
              let scheme = url.scheme else {
            decisionHandler(.allow)
            return
        }
        // 判断协议为http/https则跳系统Safari
        if scheme == "http" || scheme == "https" {
            UIApplication.shared.open(url)
            decisionHandler(.cancel)
            return
        }
        // 其他协议(比如本地的file协议)正常加载
        decisionHandler(.allow)
    }
}

说明

本地www文件夹内的资源使用file协议加载,不会被上述拦截逻辑命中,会正常在WebView内渲染,只有用户点击的外部http/https链接会被拦截跳转到系统Safari打开。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.05 16:39:03