OC与JS交互的几种方法
1.JavaScriptCore
2.WebViewJavascriptBridge
3.WKWebview
JavaScriptCore
通过JSContext实现OC与JS的交互
1.在webViewDidFinishLoad方法中创建JSContext对象,获取该UIWebview的javascript执行环境
1 | - (void)webViewDidFinishLoad:(UIWebView *)webView { |
2.OC调用JS方法并传递一个参数
JS方法:1
2
3function getImg(path){
//document.getElementById("test").src=path;
}
OC通过evaluateScript
调用JS方法:1
2NSString *alertJS=[NSString stringWithFormat:@"getImg('%@')",@"abc"]; //准备执行的js代码
[self.jsContext evaluateScript:alertJS];
3.JS调用OC方法并传递一个参数
OC方法:1
2
3- (void)getImg:(NSString *)source{
NSLog(@"%@",source);
}
JS通过OCModel
调用OC方法:1
2
3function getGalleryImg(){
OCModel.getImg('gallery');
}
通过request的URL实现交互
JS代码:1
2
3
4
5
6
7
8
9
10
11<script>
//触发该方法,调用OC中webview的`shouldStartLoadWithRequest`方法实现与OC交互
function goCamera(){
window.location.href="js-call://camera/cameraCallback";
}
//OC回调的JS方法
function cameraCallback(data) {
//获取到OC传递过来的参数
alert(data);
}
</script>
OC代码:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType
{
NSString *requestString = [[request URL] absoluteString];
//jS协议头
NSString *protocol = @"js-call://";
//请求的字符串符合协议头
if ([requestString hasPrefix:protocol]) {
//从协议头后的位置截取字符串到最后
NSString *requestContent = [requestString substringFromIndex:[protocol length]];
//将/分隔的字符串转换成数组
NSArray *vals = [requestContent componentsSeparatedByString:@"/"];
if ([[vals objectAtIndex:0] isEqualToString:@"camera"]) {
//获取到回调方法:cameraCallback
callback = [vals objectAtIndex:1];
//OC回调JS方法,并传递一个参数
[_webView stringByEvaluatingJavaScriptFromString:[NSString stringWithFormat:@"%@('%@');", callback, @"abc"]];
}
else {
[webView stringByEvaluatingJavaScriptFromString:@"alert('未定义');"];
}
return NO;
}
return YES;
}
WebViewJavascriptBridge
1.通过cocoapods或手动导入WebViewJavascriptBridge框架
2.OC端:创建webview,与bridge对象建立联系
1 | // 开启日志 |
3.JS端:创建setupWebViewJavascriptBridge
1 | <script> |
4.JS调用OC方法
bridge通过registerHandler
注册提供给JS调用的方法
OC端通过responseCallback回调JS,JS就可以得到所需要的数据
OC方法:1
2
3
4
5
6
7[self.bridge registerHandler:@"JSCallOC" handler:^(id data, WVJBResponseCallback responseCallback) {
NSLog(@"%@", data); //js-oc,abc
if (responseCallback) {
// 回调给JS
responseCallback(@{@"oc-js": @"123"});
}
}];
JS调用OC方法:1
2
3bridge.callHandler('JSCallOC', {'js-oc': 'abc'}, function(responseData) {
alert(responseData) //oc-js,123
})
5.OC调用JS方法
JS方法:1
2
3
4
5/*JS给ObjC提供公开的API,在ObjC端可以手动调用JS的这个API。接收ObjC传过来的参数,且可以回调ObjC*/
bridge.registerHandler('OCCallJS', function(data, responseCallback) {
alert(data) //oc-js,123
responseCallback({'a': '1', 'b': '2'})
})
OC调用JS方法:1
2
3[self.bridge callHandler:@"OCCallJS" data:@{@"oc-js": @"123"} responseCallback:^(id responseData) {
NSLog(@"%@", responseData); //'a': '1', 'b': '2'
}];
WKWebview
1.添加JS交互方法
1 | //添加JS交互方法 |
2.创建WKWebview
1 | WKWebViewConfiguration *config = [[WKWebViewConfiguration alloc] init]; |
3.添加WKWebView属性的监听
1 | // 添加KVO监听 |
4.WKScriptMessageHandler
1 | #pragma mark - WKScriptMessageHandler |
5.WKUIDelegate
1 | - (void)webViewDidClose:(WKWebView *)webView { |
6.WKNavigationDelegate
1 | #pragma mark - WKNavigationDelegate |
7.dealloc
1 | - (void)dealloc { |
8.JS端代码
1 | <!DOCTYPE html> |
9.总结
- JS调用OC方法:
JS端:1
window.webkit.messageHandlers.userLogin.postMessage({body: 'xiaoming'});
OC端:1
2
3
4
5
6
7- (void)userContentController:(WKUserContentController *)userContentController
didReceiveScriptMessage:(WKScriptMessage *)message {
if ([message.name isEqualToString:@"userLogin"]){
NSLog(@"%@", message.body);
}
//else if ...
}
- OC调用JS方法:
OC端:1
2
3
4
5
6NSString *username = @"xiaoming";
NSString *js = [NSString stringWithFormat:@"callJsUserName('%@')",username];
[self.webView evaluateJavaScript:js completionHandler:^(id _Nullable response, NSError * _Nullable error) {
NSLog(@"response: %@ error: %@", response, error);
NSLog(@"call js username by native");
}];
JS端:1
2
3
4function callJsUserName(username){
document.getElementById('jsParamFuncSpan').innerHTML
= username;
}
清除webview缓存
1 | //清除cookies |
1 | //清除webView的缓存 |
1 | //不加载缓存 |
参考文章:WKWebView与Js实战(OC版)