2016-11-23 177 views
5

我想从UIWebView中的JavaScript函数调用Swift在iOS 10中进行调用。我已经设置了一个非常基本的项目,只是为了试着让它工作,代码如下。从UIWebView对Swift进行Javascript调用

import UIKit 

class ViewController: UIViewController, UIWebViewDelegate {  
    @IBOutlet var webView: UIWebView! 

    override func viewDidLoad() { 
     super.viewDidLoad() 

     let url = Bundle.main.url(forResource: "products", withExtension: "html") 
     let request = NSURLRequest(url: url! as URL) 
     webView.loadRequest(request as URLRequest) 
    } 

    @IBAction func closeDocumentViewer() { 
     displayView.isHidden = true; 
    } 

    override func didReceiveMemoryWarning() { 
     super.didReceiveMemoryWarning() 
    } 
} 

如果我只是一个接收来自javascript函数的字符串,那么我将不得不添加到上面?

回答

1

您必须自定义URL Schememyawesomeapp和拦截请求它使用:

func webView(webView: UIWebView, shouldStartLoadWithRequest request: NSURLRequest, navigationType: UIWebViewNavigationType) -> Bool 

消防使用window.location=myawesomeapp://hello=world本机代码的调用,而params你request.URL.query在本机代码通过得到查询。

欲了解更多信息,请参阅我的问题有关UIWebView在这儿:JavaScript synchronous native communication to WKWebView

9

我会建议寻找到使用WKWebView代替UIWebView。然后您将不需要注册自定义URL方案。此外,UIWebView已经过时,WKWebView具有很多优点,特别是性能和渲染,因为它在单独的过程中运行。

链接到苹果的文档和信息,建议使用WKWebView https://developer.apple.com/reference/webkit/wkwebview/

重要

中的iOS 8.0和OS X 10.10开始,使用WKWebView Web内容添加到您>应用程序。不要使用UIWebView或WebView。

这就是说,它的设置非常简单的一个原生的JavaScript桥:

import WebKit 

class ViewController: UIViewController, WKScriptMessageHandler { 
    var webView: WKWebView? 
    override func loadView() { 
     super.loadView() 

     webView = WKWebView(frame: self.view.frame) 
     webView?.configuration.userContentController.add(self, name: "scriptHandler") 

     self.view.addSubview(webView!) 
    } 

    public func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) { 
     print("Message received: \(message.name) with body: \(message.body)") 
    } 
// rest of code 
} 

然后在你的JavaScript代码,调用它:

window.webkit.messageHandlers["scriptHandler"].postMessage("hello"); 

我写了一个利用库这并增加了一些花哨的JavaScript语法。 https://github.com/tmarkovski/BridgeCommander

要使用它,只是参考的项目(或添加快捷和JavaScript文件到您的Xcode项目),并调用

webView = WKWebView(frame: self.view.frame) 
    let commander = SwiftBridgeCommander(webView!) 

    commander.add("echo") { 
     command in 
     command.send(args: "You said: \(command.args)") 
    } 

然后,您就可以使用回调的语法在JavaScript这样

var commander = new SwiftBridgeCommander(); 
commander.call("echo", "Hello", function(args) { 
     // success callback 
    }, function(error) { 
     // error callback 
}); 
+0

我正在使用wkwebview,但wkwebview可能会导致死角。就像它不是将cookie与nshttpcookiestrorage同步 – Atif

+0

是的,这是WKWebView的一个缺点。它在独立进程中运行Web引擎,无法访问运行时内存。 –

+0

使用WKWebView检查WKWebsiteDataStore文档的cookie管理 - https://developer.apple.com/documentation/webkit/wkwebsitedatastore –