Summary of mutual invocation between JS and native Oc/swift

Source: Internet
Author: User

The code address is as follows:
Http://www.demodashi.com/demo/12754.html

Js-oc-swift

JS and Oc/swift call each other, mainly summarizes the JS and OC interaction of three ways

1. Using UIWebView, use javascriptcore to achieve

2. Using Wkwebview, use wkscriptmessagehandler to achieve

3. Using a third-party framework Webviewjavascriptbridge implementation

Part

JavaScriptCore

JavaScriptCore Introduction

The JavaScriptCore framework is a wrapper based on the javascriptcore of the WebKit, which makes the direct interaction of objective-c and JavaScript code more simple and convenient, consisting mainly of the following classes.

1.JSContext
JS execution environment, but also through Jsvirtualmachine to manage the life cycle of all objects, each jsvalue is associated with jscontext and strong reference context. The corresponding jscontext can be obtained from WebView by [WebView valueforkeypath:@ "DocumentView.webView.mainFrame.javaScriptContext"].

2.JSValue
A strong reference to the JS object in Jsvirtualmachine is actually the Hybird object. Our operation of JS is through it. And each jsvalue is strongly referencing a context. At the same time, the conversion between OC and JS object is also through it.

3.JSManagedValue
Memory management helper Objects for JS and OC objects. Because JS memory management is garbage collection, and the object in JS is a strong reference, and OC is a reference count. If the two sides refer to each other, it is bound to cause a circular reference, which leads to memory leaks. We can use Jsmanagedvalue to save Jsvalue to avoid.

4.JSVirtualMachine
JS runs a virtual machine that has a separate heap space and garbage collection mechanism.

5.JSExport
A protocol, if the JS object wants to directly invoke the methods and properties inside the OC object, then this OC object can only implement this Jsexport protocol.

Get the context of JS in Swift

context = webView.value(forKeyPath: "documentView.webView.mainFrame.javaScriptContext") as? JSContext

Inject the desired object into JS, and the object name is consistent with what is used in HTML. self is to comply with the Jsexport agreement, but also other compliance with the object of the agreement.

context?.setObject(self, forKeyedSubscript:  "OC" as NSCopying & NSObjectProtocol)

JS calls Swift's method to implement the protocol in Swift

@objc protocol JSDelegate :JSExport {    //包含参数的func,需要注意参数名对函数名称的影响    func showMessageToYou(_ message:String)        /*     对应html中“showAAndB”,此方法包含两个参数,需要在参数前加“_”     func showA(_ aString: String, andB: String)     func showAAndB(_ aString:String,_ bStr:String)     以上两个方法等同     */    func showAAndB(_ aString:String,_ bStr:String)        func doActionCallBack()}

Method of Swift calling JS

let jsStr = String(format:"callback(‘%@‘)",(textField?.text)!)self.context?.evaluateScript(jsStr)

Block can be used in OC and implement the Jsexport protocol in two ways, code implementation:

JSContext *context = [self.webView valueForKeyPath:@"documentView.webView.mainFrame.javaScriptContext"];self.context = context;//注入JS需要的“OC”对象,该对象与html中的保持一致即可self.context[@"OC"] = self;
Wkscriptmessagehandler

After initializing the Wkwebview, add a bridge for JS to call Oc/swift, where name corresponds to name in Wkscriptmessage

webView.configuration.userContentController.add(_ scriptMessageHandler: WKScriptMessageHandler, name: String)

Abide by the protocol Wkscriptmessagehandler, the implementation of the following methods, JS can be implemented to send messages to Oc/swift.

func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage)

Oc/swift Call JS

let jsStr = String(format:"callback(‘%@‘)",(textField?.text)!)self.webView.evaluateJavaScript(jsStr as String, completionHandler: { (result:Any?, error:Error?) in       print("error:",error as Any) })
Webviewjavascriptbridge

Webviewjavascriptbridge is a third-party library that objective-c and JavaScript communicate with each other, which makes it easy to realize the functions of OC and JavaScript intermodulation. Webviewjavascriptbridge the process of intermodulation is also easy to understand, that is, in the OC environment and JavaScript environment each save a mutually called bridge object, each call has an ID and callbackid to find the corresponding processing of the two environments. After downloading the source from GitHub, you can see that the core classes are mainly comprised of the following:

Webviewjavascriptbridge_js: Bridge initialization and processing for JavaScript environments. is responsible for receiving the messages that OC sends to JavaScript, and sends the JavaScript environment message to OC.

Wkwebviewjavascriptbridge/webviewjavascriptbridge: primarily responsible for message processing in the OC environment, and sends messages from the OC environment to the JavaScript environment.

webviewjavascriptbridgebase: The main realization of the OC Environment Bridge initialization and processing.

Initialize Wkwebviewjavascriptbridge

self.webViewBridge = [WKWebViewJavascriptBridge bridgeForWebView:self.webView];[self.webViewBridge setWebViewDelegate:self];

JS calls OC need to register event

[self.webViewBridge registerHandler:@"handlerName" handler:^(id data, WVJBResponseCallback responseCallback) {   //code}];

OC Call JS

[self.webViewBridge callHandler:@"handlerName" data:@[textField.text] responseCallback:^(id responseData) {        NSLog(@"%@",responseData); }];

The following code needs to be placed in the HTML

/*这段代码是固定的,必须要放到js中*/function setupWebViewJavascriptBridge(callback) {    if (window.WebViewJavascriptBridge) { return callback(WebViewJavascriptBridge); }    if (window.WVJBCallbacks) { return window.WVJBCallbacks.push(callback); }    window.WVJBCallbacks = [callback];    var WVJBIframe = document.createElement(‘iframe‘);    WVJBIframe.style.display = ‘none‘;    WVJBIframe.src = ‘wvjbscheme://__BRIDGE_LOADED__‘;    document.documentElement.appendChild(WVJBIframe);    setTimeout(function() { document.documentElement.removeChild(WVJBIframe) }, 0)}/*与OC交互的所有JS方法都要放在此处注册,才能调用通过JS调用OC或者让OC调用这里的JS*/setupWebViewJavascriptBridge(function(bridge) {     bridge.registerHandler(‘callback‘, function(data, responseCallback) {        callback(data);        responseCallback(‘js执行过了‘+data);    })})
Project structure

Summary of mutual invocation between JS and native Oc/swift

The code address is as follows:
Http://www.demodashi.com/demo/12754.html

Note: This copyright belongs to the author, by the demo master, refused to reprint, reprint need the author authorization

Summary of mutual invocation between JS and native Oc/swift

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.