iOS

⌘K
  1. Home
  2. Docs
  3. iOS
  4. UI Controls
  5. Web Views (WKWebView)

Web Views (WKWebView)

What is WKWebView?

WKWebView is a powerful web rendering engine introduced in iOS 8 as part of the WebKit framework. It allows iOS apps to display web content efficiently while offering better performance and security than the deprecated UIWebView.


1. Key Features of WKWebView

Faster performance than UIWebView
✅ Supports JavaScript execution
✅ Offers enhanced security with sandboxing
✅ Allows communication between native Swift code and JavaScript
✅ Provides fine-grained control over web content


2. Adding WKWebView in Storyboard

  1. Drag & Drop a WKWebView from the Object Library.
  2. Set constraints to position it properly within the view.
  3. Create an IBOutlet for the WebView in the ViewController.
  4. Load a URL or HTML content programmatically.

3. Implementing WKWebView Programmatically

3.1 Basic Setup

import UIKit
import WebKit

class ViewController: UIViewController, WKNavigationDelegate {

    var webView: WKWebView!

    override func viewDidLoad() {
        super.viewDidLoad()
        
        // Initialize WKWebView
        webView = WKWebView(frame: view.bounds)
        webView.navigationDelegate = self
        view.addSubview(webView)

        // Load a URL
        if let url = URL(string: "https://www.apple.com") {
            let request = URLRequest(url: url)
            webView.load(request)
        }
    }
}

This creates a simple WebView that loads Apple’s website.


4. Loading Different Types of Web Content

4.1 Load a URL

let url = URL(string: "https://www.example.com")!
webView.load(URLRequest(url: url))

4.2 Load Local HTML File

if let localHTMLPath = Bundle.main.path(forResource: "index", ofType: "html") {
    let localURL = URL(fileURLWithPath: localHTMLPath)
    webView.loadFileURL(localURL, allowingReadAccessTo: localURL)
}

4.3 Load HTML String

let htmlString = "<html><body><h1>Hello, WKWebView!</h1></body></html>"
webView.loadHTMLString(htmlString, baseURL: nil)

5. Handling Web Navigation with WKNavigationDelegate

To monitor navigation events, conform to the WKNavigationDelegate protocol.

5.1 Detect Page Load Start & End

func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!) {
    print("Page is loading...")
}

func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
    print("Page loaded successfully!")
}

5.2 Handle Page Load Errors

func webView(_ webView: WKWebView, didFail navigation: WKNavigation!, withError error: Error) {
    print("Failed to load page: \(error.localizedDescription)")
}

6. Enabling JavaScript Execution

By default, WKWebView supports JavaScript, but additional configurations might be needed.

let webConfig = WKWebViewConfiguration()
webConfig.preferences.javaScriptEnabled = true
let webView = WKWebView(frame: .zero, configuration: webConfig)

7. Communicating Between Swift & JavaScript

7.1 Inject JavaScript into WebPage

webView.evaluateJavaScript("document.body.style.backgroundColor = 'lightgray'") { (result, error) in
    if let error = error {
        print("JavaScript Error: \(error.localizedDescription)")
    }
}

7.2 Send Data from JavaScript to Swift

1️⃣ Add a JavaScript message handler in Swift:

class ViewController: UIViewController, WKScriptMessageHandler {
    override func viewDidLoad() {
        let contentController = webView.configuration.userContentController
        contentController.add(self, name: "messageHandler")
    }
    
    func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
        print("Message from JavaScript: \(message.body)")
    }
}

2️⃣ Call the message handler from JavaScript:

window.webkit.messageHandlers.messageHandler.postMessage("Hello from JavaScript!");

This enables two-way communication between Swift and JavaScript.


8. Adding Navigation Controls

8.1 Adding a Toolbar with Back & Forward Buttons

let backButton = UIBarButtonItem(title: "Back", style: .plain, target: self, action: #selector(goBack))
let forwardButton = UIBarButtonItem(title: "Forward", style: .plain, target: self, action: #selector(goForward))

@objc func goBack() {
    if webView.canGoBack {
        webView.goBack()
    }
}

@objc func goForward() {
    if webView.canGoForward {
        webView.goForward()
    }
}

9. Handling Links Inside WebView

To control how URLs open, implement WKNavigationDelegate.

func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
    if let url = navigationAction.request.url, url.absoluteString.contains("external-site.com") {
        UIApplication.shared.open(url)  // Open in Safari
        decisionHandler(.cancel)
        return
    }
    decisionHandler(.allow)
}

This ensures external links open in Safari while keeping internal navigation inside WKWebView.


10. Caching & Performance Optimization

10.1 Enabling Cache for Faster Loading

let cachePolicy = URLRequest.CachePolicy.returnCacheDataElseLoad
let request = URLRequest(url: URL(string: "https://example.com")!, cachePolicy: cachePolicy, timeoutInterval: 10)
webView.load(request)

10.2 Clearing WebView Cache

let dataStore = WKWebsiteDataStore.default()
dataStore.fetchDataRecords(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes()) { records in
    records.forEach { dataStore.removeData(ofTypes: $0.dataTypes, for: [$0], completionHandler: {}) }
}

This prevents excessive data storage and ensures fresh content loading.


11. Common Issues & Fixes

❌ Issue: WebView Not Loading URL

Fix: Ensure the URL is valid and App Transport Security (ATS) allows non-HTTPS URLs.

Add this to Info.plist to allow HTTP URLs:

<key>NSAppTransportSecurity</key>
<dict>
    <key>NSAllowsArbitraryLoads</key>
    <true/>
</dict>

❌ Issue: JavaScript Not Running

Fix: Enable JavaScript in WKWebViewConfiguration.


12. Conclusion

✔️ WKWebView is the recommended way to embed web content in iOS apps.
✔️ Offers faster performance, better security, and full JavaScript support.
✔️ Provides customization options like navigation control, JavaScript execution, and message passing.
✔️ Supports modern web technologies like HTML5, CSS, and JavaScript frameworks.

Would you like a specific WKWebView feature implementation in your project? 🚀