WKWebView小记

3 篇文章 0 订阅

1 额外的进程

WKWebView有额外的2个进程,Networking负责网络请求和WebContent负责内容渲染,所以性能较好,且内存占用低。虽然总的占用内存不变,但App占用的内存大幅下降,减小了被强杀的风险,而且额外进程的崩溃不会影响App。

2 与UIWebView的差异

WKWebView和UIWebView的代理方法发生了一些改变,WKWebView的流程更加细化了。例如之前UI结束请求后,会立刻渲染到webView上。而WKWebView则会在渲染到屏幕之前,会回调一个代理方法,代理方法决定是否渲染到屏幕上。这样就可以对请求下来的数据做一次校验,防止数据被更改,或验证视图是否允许被显示到屏幕上。
除此之外,WKWebView相对于UIWebView还多了一些定制化操作。
1,重定向的回调,可以在请求重定向时获取到这次操作。
当WKWebView进程异常退出时,可以通过回调获取。
自定义处理证书。
更深层的UI定制操作,将alert等UI操作交给原生层面处理,而UI方案UIAlertView是直接由webView显示的。

在这里插入图片描述

3 遇到的坑

坑1 打开新网页

不支持_blank,_blank用来打开一个新的网页,但WKWebView下却点击无反应。需要进行特殊处理,

-(WKWebView *)webView:(WKWebView *)webView createWebViewWithConfiguration:(WKWebViewConfiguration *)configuration forNavigationAction:(WKNavigationAction *)navigationAction windowFeatures:(WKWindowFeatures *)windowFeatures {
    if (!navigationAction.targetFrame.isMainFrame) {
        [webView loadRequest:navigationAction.request];
    }
    
    return nil;
}
坑2 电话

之前在UIWebView上正常的href=“tel:13764567708”,href=“mailto:think@126.com”,现在WKWebView上,无法呼起拨打电话/发邮件,需要在decidePolicyForNavigationAction里面判断URL的scheme(tel、mailto等等),然后用[UIApplication sharedApplication] openURL的方式来拨打电话。不止是电话,跳转App Store等也需要在端内特殊处理。

坑3 弹窗

之前在UIWebView下的alert弹窗,在WKWebView下无法显示,需要在runJavaScriptAlertPanelWithMessage里面进行处理,转换为UIAlertController然后进行展示,注意completionHandler在UIAlertController消失时一定要调用,否则crash。之前做的功能会在呼起正文时,dismiss掉所有的UIAlertController,但没料到这个是WKWebView的弹出UIAlertController,没有调用completionHandler而出现了crash。
不仅是alert弹窗,confirm和input类型的都需要实现协议,转化为Native来实现。

坑4 白屏

如果WKWebView加载内存占用过多的页面,会导致WebContent Process进程崩溃,进而页面出现白屏,出现白屏后,可以在

-(void)webViewWebContentProcessDidTerminate:(WKWebView *)webView

进行重新加载当前网页。
如果从其他App回来导致白屏问题,可以在视图将要显示的时候,判断webView.title是否为空。如果为空则重新加载当前网页。

坑5 属性默认值的不同

allowsLinkPreview在UIWebView默认为NO,而在WKWebView中为YES。

优化1

提前初始化WebView,需要时直接加载URL,能节省100ms时间。

优化2 设置Cookie

根据版本选择不同的方案。
在iOS 11 及以上,因为有了WKHTTPCookieStore,因此最简单,直接用这个类同步登录信息的cookie,来解决WKWebView的cookie的问题。用NSHTTPCookieStorage同步登录信息的cookie处理其他的情况。
在iOS11以下使用下面的方案:

1、请求时在reqeust的header中设置cookie,解决首个请求 Cookie 带不上的问题
2、通过WKUserScript进行注入JS注入,设置cookie,解决后续页面(同域)Ajax、iframe 请求的 Cookie 问题
3,在decidePolicyForNavigationAction,新建一个cookieWebView,在这个cookieWebView中,注入设置cookie的JS,然后加载一个相同域名的空html,同时这个cookieWebView和展示的WebView用一个ProcessPool。这样展示的WebView就有了这里设置的cookie。
4,用NSHTTPCookieStorage同步登录信息的cookie处理其他的情况。

HTTP小结
思想杂记之小总结
WKWebview 加载过程中的性能指标图解

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Protobuf是一种高效的序列化协议,可以用于数据交换和数据存储。它的主要优势是大小小,速度快,可扩展性强。下面是使用Protobuf的一些小记: 1. 定义消息格式 首先,需要定义消息格式,以便Protobuf可以将数据序列化和反序列化。消息格式定义在.proto文件中,使用protobuf语言编写。例如,下面是一个简单的消息格式定义: ``` syntax = "proto3"; message Person { string name = 1; int32 age = 2; } ``` 这个消息格式定义了一个名为Person的消息,包含两个字段:name和age。 2. 生成代码 一旦消息格式定义好,就可以使用Protobuf编译器生成代码。编译器将根据消息格式定义生成相应的代码,包括消息类、序列化和反序列化方法等。可以使用以下命令生成代码: ``` protoc --java_out=. message.proto ``` 这将生成一个名为message.pb.java的Java类,该类包含Person消息的定义以及相关方法。 3. 序列化和反序列化 一旦生成了代码,就可以使用Protobuf序列化和反序列化数据。例如,下面是一个示例代码,将一个Person对象序列化为字节数组,并将其反序列化为另一个Person对象: ``` Person person = Person.newBuilder() .setName("Alice") .setAge(25) .build(); byte[] bytes = person.toByteArray(); Person deserializedPerson = Person.parseFrom(bytes); ``` 这个示例代码创建了一个Person对象,将其序列化为字节数组,然后将其反序列化为另一个Person对象。在这个过程中,Protobuf使用生成的代码执行序列化和反序列化操作。 以上是使用Protobuf的一些基本步骤和注意事项,希望对你有所帮助!
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值