WKWebview js injection

38 Views Asked by At

I need to inject js to handle close button in webpage, but it works only in inital page, If I go to another page in website, it just not handling. It stop working after navigation to some other page, even if I navigate back. It not working anymore

What actually I do:

  1. Configure webview

     let preferences = WKPreferences()
     preferences.javaScriptEnabled = true
    
     let configuration = WKWebViewConfiguration()
     configuration.preferences = preferences
     let userContentController = WKUserContentController()
    
     let source =  """
         if (document.getElementById('closeWebApp')) {
             document.getElementById('closeWebApp').addEventListener('click', function() { window.webkit.messageHandlers.ios.postMessage('closeWebApp'); });
         }
     """
     let script = WKUserScript(source: source, injectionTime: .atDocumentStart, forMainFrameOnly: false)
    
     userContentController.addUserScript(script)
     userContentController.add(self, name: "ios")
    
     configuration.userContentController = userContentController
    
     webView = WKWebView(frame: view.bounds, configuration: configuration)
     webView.navigationDelegate = self`
    
  2. load website.

if let url = URL(string: "https://example.com/new") {
            webView.load(URLRequest(url: url))
        }
  1. In delegate method handle closeWebApp element event click
func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
        webView.evaluateJavaScript("""
        
        document.getElementById('closeWebApp').addEventListener('click', function() {
                    window.webkit.messageHandlers.ios.postMessage('Close button clicked');
                });
        """)
  1. Also wrote inside didStartProvisionalNavigation
    func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!) {
        webView.evaluateJavaScript("""
            if (document.getElementById('closeWebApp')) {
                document.getElementById('closeWebApp').addEventListener('click', function() { window.webkit.messageHandlers.ios.postMessage('closeWebApp'); });
            }
        """) { (result, error) in
            if let error = error {
                print("JavaScript evaluation error: \(error.localizedDescription)")
            } else {
                print("JS evaluated successfull")
            }
        }
    }
    
    func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
        if navigationAction.navigationType == .backForward {
            onBackPassed = true
        }
        decisionHandler(.allow)
    }
  1. Also handling
func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
        
        guard let buttonId = message.name as? String else {
            return
        }
        
        if buttonId == "ios" {
            onBackPassed = true
            DispatchQueue.main.async {
                self.onBackPressed()
            }
        }
    }
0

There are 0 best solutions below