iOS,WKWebView加载HTML与JS交互。

由于项目使用到了oc与js混编,oc与js交互可以用UIWebView也可以用WKWebView,这里我说一下通过WKWebView加载HTML文件来进行交互,官方推荐在嵌入h5页面或者需要交互的时候都使用WKWebView而不是使用UIWebView。WKWebView需要最低系统为8.0。

一:加载HTML

加载wkWebView的时候可以设置很多配置参数。需要用到的地方会写。

 _webView = [[WKWebView alloc] initWithFrame:CGRectMake(0, 0, 10, 10)]; //设置代理用来获取加载状态等等信息...<WKUIDelegate,WKNavigationDelegate> _webView.UIDelegate = self; _webView.navigationDelegate = self; [self.view addSubview:_webView]; //加载本地html NSString *filePath = [[NSBundle mainBundle] pathForResource:@"testFunction" ofType:@"html"]; [_webView loadFileURL:[NSURL fileURLWithPath:filePath] allowingReadAccessToURL:[NSBundle mainBundle].resourceURL];

二:OC调用JS

oc如果需要调用js方法。需要在html加载完成的代理方法中实现。

//html加载失败- webView:(WKWebView *)webView didFailNavigation:(WKNavigation *)navigation withError:(NSError *)error{ NSLog(@"error message:%@",error);}//html开始加载- webView:(WKWebView *)webView didStartProvisionalNavigation:(WKNavigation *)navigation{ NSLog(@"begin load html");}//html加载完成- webView:(WKWebView *)webView didFinishNavigation:(WKNavigation *)navigation{ NSLog(@"finish load"); WEAKSELF; [webView evaluateJavaScript:@"" completionHandler:^(id _Nullable response, NSError * _Nullable error) { NSLog(@"response: %@ error: %@", response, error); }];}

这里大概3种情况。1.oc调用js无参数函数。2.oc调用js有参数函数。3.oc调用js函数后,有返回值。

<html lang="en"><head> <meta charset="UTF-8"> <title>walletProj</title></head><body> <script type="text/javascript"> //无参数函数 function testA() { alert; } //有参数函数 function testB { alert; } function testC { //返回值可以是很多类型。 //反馈字符串 return value + "value"; //返回对象,如果需要传递给oc的东西有很多,就可以构造一个这样的对象用来传输。 // var finalObj = {"name":"chaman","age":"18","sex":"male"}; // return finalObj; } </script></body></html>

注意:在wkwebView中如果html有弹框处理,oc这边是不能显示的,必须实现代理方法-
webView:(WKWebView *)webView
runJavaScriptAlertPanelWithMessage:(NSString *)message
initiatedByFrame:(WKFrameInfo *)frame
completionHandler:completionHandler。从中获取alert内容并做处理。

- webView:(WKWebView *)webView didFinishNavigation:(WKNavigation *)navigation{ NSLog(@"finish load"); //调用js无参函数 [webView evaluateJavaScript:@"testA()" completionHandler:^(id _Nullable response, NSError * _Nullable error) { //js函数调用return,这里才会有东西,否则无任何信息。 NSLog(@"response: %@ error: %@", response, error); }]; //调用js有参函数 [webView evaluateJavaScript:[NSString stringWithFormat:@"testB",@"show"] completionHandler:^(id _Nullable response, NSError * _Nullable error) { //js函数调用return,这里才会有东西,否则无任何信息。 NSLog(@"response: %@ error: %@", response, error); }]; //调用js有参函数并获得返回值 [webView evaluateJavaScript:[NSString stringWithFormat:@"testC",@"return value"] completionHandler:^(id _Nullable response, NSError * _Nullable error) { //js函数调用return,这里才会有东西,否则无任何信息。 NSLog(@"response: %@ error: %@", response, error); }];}

二:JS调用OC

比如我OC有一个方法叫”jsCallOc”,JS在某些场景需要调用OC的这个函数。1.oc需要注册”jsCallOc”这个方法,在初始化WKWebView的时候注入进去,这时候初始化WKWebView就应该这样写,需要实现WKScriptMessageHandler代理。

 //注册方法 WKUserContentController *userContentController = [[WKUserContentController alloc] init]; //需要实现<WKScriptMessageHandler>,可同时注册多个方法名字,但是记得在控制器销毁时候移除。 [userContentController addScriptMessageHandler:self name:@"jsCallOc"]; // WKWebView的配置 WKWebViewConfiguration *configuration = [[WKWebViewConfiguration alloc] init]; configuration.userContentController = userContentController; _webView = [[WKWebView alloc] initWithFrame:CGRectMake(0, 0, 10, 10) configuration:configuration]; //设置代理用来获取加载状态等等信息...<WKUIDelegate,WKNavigationDelegate> _webView.UIDelegate = self; _webView.navigationDelegate = self; [self.view addSubview:_webView]; //加载本地html NSString *filePath = [[NSBundle mainBundle] pathForResource:@"testFunction" ofType:@"html"]; [_webView loadFileURL:[NSURL fileURLWithPath:filePath] allowingReadAccessToURL:[NSBundle mainBundle].resourceURL];

2.实现代理方法获取js调用的操作。

- userContentController:(WKUserContentController *)userContentController didReceiveScriptMessage:(WKScriptMessage *)message{ //获取值 NSLog(@"data:%@", message.body); //获取函数名字 NSLog(@"data:%@", message.name);}

<head> <meta charset="UTF-8"> <title>walletProj</title></head><body> <script type="text/javascript"> //无参数函数 function testA() { window.webkit.messageHandlers.jsCallOc.postMessage; } //有参数函数 function testB { window.webkit.messageHandlers.jsCallOc.postMessage("call oc"); } function testC { var finalObj = { "name": "chaman", "age": "18", "sex": "male" }; window.webkit.messageHandlers.jsCallOc.postMessage; } </script></body></html>

- dealloc { [[_webView configuration].userContentController removeScriptMessageHandlerForName:@"jsCallOc"];}

相关文章