前言:

WKWebView 这是在iOS8.0之后增加的一个比UIWebView更加完善和强大的控件!看网上关于它的博客也是有许多的了,从各个方面总结一下这个WKWebView看网上说它主要是为了和JS做好交互产生的,我们也会相应的尝试一下。就先从它基本的说起!

一:和UIWebView相比它的不同处

1:和JS更好的做交互,也支持H5的一些新特性

2:加载进度条(下面会演示)

3:性能高,加载变得更快更可靠

二:从加载一张网页开始

1:使用这个WKWebView是要#import <WebKit/WebKit.h>

2:遵守协议,WKNavigationDelegate,WKUIDelegate,WKScriptMessageHandler(最后这个协议留神一下就知道视为JS准备的)

3:加载百度试一下

  1. WKWebView * webviwe = [[WKWebView alloc]initWithFrame:self.view.bounds];
  2. [webviwe loadRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:@"https://www.baidu.com"]]];
  3. [self.view addSubview:webviwe];

三:说说加载进度条

这个是利用KVO模式写的,WKWebView有一个  estimatedProgress 属性,利用它来监听加载的进度,下面的进度打印出来了,但具体的进度条就没有写出来,你们可以自己写一个 UIProgressView 放在导航栏的下面。

  1. // estimatedProgress WKWebView 这个属性添加观察者
  2. [webviwe addObserver:self forKeyPath:@"estimatedProgress" options:NSKeyValueObservingOptionNew context:nil];
  1. -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary<NSString *,id> *)change context:(void *)context
  2. {
  3. if (object == webviwe && [keyPath isEqualToString:@"estimatedProgress"] ) {
  4. // 这里就不写进度条了,把加载的进度打印出来,进度条可以自己加上去!
  5. CGFloat newProgress = [[change objectForKey:NSKeyValueChangeNewKey] floatValue];
  6. NSLog(@"%f",newProgress);
  7. }
  8. }

看看打印的进度信息:

2016-08-11 14:44:17.237 RaectiveCocoaTest[21054:252565] 页面开始加载

2016-08-11 14:44:17.724 RaectiveCocoaTest[21054:252565] 0.300000

2016-08-11 14:44:17.726 RaectiveCocoaTest[21054:252565] 内容正在加载当中

2016-08-11 14:44:18.000 RaectiveCocoaTest[21054:252565] 0.719984

2016-08-11 14:44:18.196 RaectiveCocoaTest[21054:252565] 1.000000

2016-08-11 14:44:18.196 RaectiveCocoaTest[21054:252565] 页面加载完成

四:详细的方法使用说明以及注释

详解 WKNavigationDelegate 代理方法,我们把它的代理方法使用代码以及注意点全都写出来,注意看下面的注释!

  1. #pragma mark - WKNavigationDelegate
  2. // 页面加载开始 Provisional临时的
  3. -(void)webView:(WKWebView *)webView didStartProvisionalNavigation:(WKNavigation *)navigation
  4. {
  5. NSLog(@"页面开始加载");
  6. }
  7. // 加载内容
  8. -(void)webView:(WKWebView *)webView didCommitNavigation:(WKNavigation *)navigation
  9. {
  10. NSLog(@"内容正在加载当中");
  11. }
  12. // 页面加载完成
  13. -(void)webView:(WKWebView *)webView didFinishNavigation:(WKNavigation *)navigation
  14. {
  15. NSLog(@"页面加载完成");
  16. }
  17. // 页面加载失败
  18. -(void)webView:(WKWebView *)webView didFailProvisionalNavigation:(WKNavigation *)navigation withError:(NSError *)error
  19. {
  20. NSLog(@"页面加载失败");
  21. }
  22. // 接收到服务器重新配置请求之后再执行
  23. -(void)webView:(WKWebView *)webView didReceiveServerRedirectForProvisionalNavigation:(WKNavigation *)navigation
  24. {
  25.  
  26. }
  27. // API是根据WebView对于即将跳转的HTTP请求头信息和相关信息来决定是否跳转
  28. -(void)webView:(WKWebView *)webView decidePolicyForNavigationAction:(WKNavigationAction *)navigationAction decisionHandler:(void (^)(WKNavigationActionPolicy))decisionHandler
  29. {
  30. NSURLRequest * request = navigationAction.request;
  31. NSLog(@"%@",request.URL.absoluteString);
  32.  
  33. // 判断请求头是否是 https://www.baidu.com 如果是就不在请求加载跳转
  34. WKNavigationActionPolicy actionPolicy = WKNavigationActionPolicyAllow;
  35. if ([request.URL.absoluteString hasPrefix:@"https://www.baidu.com"]) {
  36.  
  37. actionPolicy = WKNavigationActionPolicyCancel;
  38.  
  39. }
  40. // 必须这样执行,不然会崩
  41. decisionHandler(actionPolicy);
  42. }
  43. /**
  44. *
  45. 要是允许跳转,看下面的打印内容,注意加载的顺序!和下面的方法进行比较,区分它们的不同之处
  46. 2016-08-11 13:55:12.628 RaectiveCocoaTest[18155:211964] https://www.baidu.com/
  47. 2016-08-11 13:55:12.629 RaectiveCocoaTest[18155:211964] 页面开始加载
  48. 2016-08-11 13:55:13.725 RaectiveCocoaTest[18155:211964] 内容正在加载当中
  49. 2016-08-11 13:55:14.681 RaectiveCocoaTest[18155:211964] 页面加载完成
  50. *
  51. */
  52. // API是根据客户端受到的服务器响应头以及response相关信息来决定是否可以跳转
  53. -(void)webView:(WKWebView *)webView decidePolicyForNavigationResponse:(WKNavigationResponse *)navigationResponse decisionHandler:(void (^)(WKNavigationResponsePolicy))decisionHandler
  54. {
  55. NSLog(@"%@",navigationResponse.response);
  56. /**
  57. * 判断响应的数据里面的URL是https://www.baidu.com/开头的,要是就不让它加载跳转
  58. */
  59. WKNavigationResponsePolicy responsePolicy = WKNavigationResponsePolicyAllow;
  60. if ([navigationResponse.response.URL.absoluteString hasPrefix:@"https://www.baidu.com/"]) {
  61.  
  62. responsePolicy = WKNavigationResponsePolicyCancel;
  63. }
  64. decisionHandler(responsePolicy);
  65. }
  66. /**
  67. *
  68. 响应返回的的URL包含了https://www.baidu.com/,所以页面是不能被加载的,要是能加载就有下面的打印信息,注意和上面方法的区分对比!
  69. 2016-08-11 13:53:38.392 RaectiveCocoaTest[17961:209778] 页面开始加载
  70. 2016-08-11 13:53:38.675 RaectiveCocoaTest[17961:209778] https://www.baidu.com/
  71. 2016-08-11 13:53:38.678 RaectiveCocoaTest[17961:209778] 内容正在加载当中
  72. 2016-08-11 13:53:38.936 RaectiveCocoaTest[17961:209778] 页面加载完成
  73. */

五:说说WKUIDelegate和JS的简单交互

先看看 WKUIDelegate里面的代理方法都是用来做什么的,我们一个一个的解释这几个代理方法;

  1. // 创建方法,这个就不在多说了,重点放在下面几个
  2. -(nullable WKWebView *)webView:(WKWebView *)webView createWebViewWithConfiguration:(WKWebViewConfiguration *)configuration forNavigationAction:(WKNavigationAction *)navigationAction windowFeatures:(WKWindowFeatures *)windowFeatures
  3. {
  4. return nil;
  5. }
  6.  
  7. // ios 9 之后才有的方法
  8. -(void)webViewDidClose:(WKWebView *)webView
  9. {
  10.  
  11. }

下面这三个方法根据方法前面的字面意思就能区分记住!

runJavaScriptAlert 方法注意点

1.在JS端调用alert函数时,会触发此代理方法。

2.JS端调用alert时所传的数据可以通过message,打印message信息读取出JS端给你的信息。

3.在原生得到结果后,需要回调给JS,通过completionHandler 回调给JS

4.completionHandler 回调的参数和返回值都是空

  1. /**
  2. 下面这三个方法根据前面的字面意思就能区分记住!
  3. */
  4. // runJavaScriptAlert
  5. // 在JS端调用alert函数时,会触发此代理方法。
  6. // JS端调用alert时所传的数据可以通过message,打印message信息读取出JS端给你的信息。
  7. // 在原生得到结果后,需要回调给JS,通过completionHandler 回调给JS
  8. // completionHandler 回调的参数和返回值都是空
  9. -(void)webView:(WKWebView *)webView runJavaScriptAlertPanelWithMessage:(NSString *)message initiatedByFrame:(WKFrameInfo *)frame completionHandler:(void (^)(void))completionHandler
  10. {
  11.  
  12. UIAlertController *alert = [UIAlertController alertControllerWithTitle:@"alert"message:@"JS调用alert"preferredStyle:UIAlertControllerStyleAlert];
  13. [alert addAction:[UIAlertAction actionWithTitle:@"确定" style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) {
  14.  
  15. }]];
  16.  
  17. [self presentViewController:alert animated:YES completion:NULL];
  18. NSLog(@"%@", message);
  19.  
  20. }

runJavaScriptTextInput 注意点

1.要求用户输入一段文字

3.在原生输入得到文本内容后,通过completionHandler回调给JS

4.大家注意这个回调的completionHandler参数是字符串

  1. // runJavaScriptTextInput
  2. // 要求用户输入一段文本
  3. // 在原生输入得到文本内容后,通过completionHandler回调给JS 大家注意这个回调的completionHandler参数是字符串
  4. -(void)webView:(WKWebView *)webView runJavaScriptTextInputPanelWithPrompt:(NSString *)prompt defaultText:(NSString *)defaultText initiatedByFrame:(WKFrameInfo *)frame completionHandler:(void (^)(NSString * _Nullable))completionHandler
  5. {
  6.  
  7. }

runJavaScriptConfirmPane(ConfirmPane字面意思是确认框)

1.JS端调用confirm函数时,会触发此方法

2.通过message可以拿到JS端所传给我们数据

3.在iOS端显示原生alert得到YES/NO后,通过completionHandler回调给JS端

4.注意这个completionHandler回调的参数是BOOL类型的

  1. -(void)webView:(WKWebView *)webView runJavaScriptConfirmPanelWithMessage:(NSString *)message initiatedByFrame:(WKFrameInfo *)frame completionHandler:(void (^)(BOOL))completionHandler
  2. {
  3.  
  4. }

要有什么问题或者发现错误的地方,及时留言联系我,立马改正!

WKWebView的使用与JS交互详细解读的更多相关文章

  1. UIWebView和WKWebView的使用及js交互

    UIWebView和WKWebView的使用及js交互 web页面和app直接的交互是很常见的东西,之前尝试过flex和js的相互调用以及android和js的相互调用,却只有ios没试过,据说比较复 ...

  2. WKWebView新特性及JS交互

    引言 一直听说WKWebView比UIWebView强大许多,可是一直没有使用到,今天花了点时间看写了个例子,对其API的使用有所了解,为了日后能少走弯路,也为了让大家更容易学习上手,这里写下这篇文章 ...

  3. iOS(WKWebView)OC与JS交互 之三

      随着H5功能愈发的强大,没进行过混合开发的小伙们都不好意思说自己能够独立进行iOS的app开发,在iOS7操作系统下,常用的native,js交互框架有easy-js,WebViewJavascr ...

  4. iOS(UIWebView 和WKWebView)OC与JS交互 之二

    在iOS应用的开发过程中,我们经常会使用到WebView,当我们对WebView进行操作的时候,有时会需要进行源生的操作.那么我记下来就与大家分享一下OC与JS交互. 首先先说第一种方法,并没有牵扯O ...

  5. 记录使用WKWebView进行OC与JS交互所踩过的坑

    目录: 1.页面cookie缓存 2.允许弹出JS的弹框 3.在webview页面加载的时候,添加加载进度条 4.禁止掉webview页面的长按复制粘贴功能 5.设置webview的userAgent ...

  6. ios WKWebView 与 JS 交互实战技巧

    一.WKWebView 由于Xcode8发布之后,编译器开始不支持iOS 7了,这样我们的app也改为最低支持iOS 8.0,既然需要与web交互,那自然也就选择使用了 iOS 8.0之后 才推出的新 ...

  7. Node.js API 初解读(一)

    Node.JS API 初解读 Version: NodeJs v6.2.0 一. Assert 1.简介 Assert模块主要用于断言.如果表达式不符合预期,就抛出一个错误. 该模块用于编写程序的单 ...

  8. Node.js API 初解读(三)

    目录 Node.JS API 初解读三 Node.JS API 初解读三 Version: NodeJs v6.2.0 一. DNS (Domain Name Server) [域名服务器] 1.简介 ...

  9. Android BLE蓝牙详细解读

    代码地址如下:http://www.demodashi.com/demo/15062.html 随着物联网时代的到来,越来越多的智能硬件设备开始流行起来,比如智能手环.心率检测仪.以及各式各样的智能家 ...

随机推荐

  1. Appium的安装和使用

    <!DOCTYPE html><html><head><title>Appium的安装和使用</title><meta http-eq ...

  2. Linux下mysql数据库的命令

    连接数据库命令:mysql -u 用户名 -p 密码 要求你输入要连接数据库的用户名和密码.用户名默认root密码不方便输入时,可以只输入:mysql -u 用户名 -p 然后回车,此时提示你输入密码 ...

  3. 《SpringMVC数据绑定入门》笔记

    基本类型 最好使用封装类型 简单多数据&多层级对象 简单多数据 单个对象,直接使用属性名=值即可 多层级对象 属性.属性=值即可 同属性多对象 WebDataBinder只在当前类中生效,不是 ...

  4. sql数据库中查询第几条到第几条的数据

    通用方法: select top 500 * from (select top 1000 * from UserSearchDatas order by ID) a order by ID desc ...

  5. phpcms的网页替换

    //替换首页header:loge里面的首页不用替换<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" ...

  6. Struts2配置dtd约束

    Struts2和Struts1的区别: 一.elclipse-ee开发 搭建环境eclipse-ee 1.加入jar包  apps/struts2-blank.war解压 2.在web.xml文件中配 ...

  7. linux 安装jdk及tomcat指定jdk版本推荐

    方法1:用yum命令安装 1.   查看当前jdk版本:Java –version,或者是:rpm -qa | grep jdk 2.   删除当前jdk:yum -y remove java-1.6 ...

  8. 一段神奇的代码-关于PHP字符变量奇怪现象的解释

    首先神奇的PHP是支持字符数据类型的,有同学就写了这样一段代码: for ($c = 'a'; $c <= 'z'; $c++) { echo $c . ' '; } 然而结果却不是他想要的a到 ...

  9. python中numpy对函数进行矢量化转换

    在对numpy的数组进行操作时,我们应该尽量避免循环操作,尽可能利用矢量化函数来避免循环. 但是,直接将自定义函数应用在numpy数组之上会报错,我们需要将函数进行矢量化转换. def Theta(x ...

  10. 关于IE6、IE7、IE8实现盒子阴影shadow的几个注意点

    通常,我们实现盒阴影都是通过这段代码来实现的 -moz-box-shadow: 3px 3px 4px #000; -webkit-box-shadow: 3px 3px 4px #000; box- ...