WKwebview 学习

<!doctype html>





WKWebview学习

WKWebview学习

WKWebView 是苹果在 iOS 8 中引入的新组件,目的是给出一个新的高性能的 Web View 解决方案,摆脱过去 UIWebView 的老旧笨重特别是内存占用量巨大的问题。

  1. 稳定、功能强大;
  2. 支持更多的H5;
  3. KVO;
  4. 支持高达 60 fps 的滚动刷新率,内置了手势探测;
  5. 14个类和3个协议

创建WKWebView

引入WebKit框架,首先配置WKWebView与网页交互的配置项WKWebViewConfiguration;

// 创建一个webiview的配置项
let configuretion = WKWebViewConfiguration()
//将TEST的ScriptMessageHandler注册到webiview的配置项中,这样在js中就可以向native传值     configuretion.userContentController.addScriptMessageHandler(self, name: "TEST")

初始化并配置WKWebView对象;

self.webview = WKWebView(frame: self.view.frame, configuration: configuretion)
self.webview.loadRequest(NSURLRequest(URL: NSURL(string: "http://www.baidu.com/")!))
self.view.addSubview(self.webview)

WKWebView的三个代理

WKNavigationDelegate:与页面导航加载相关

1、该代理提供的方法,可以用来追踪加载过程(页面开始加载、加载完成、加载失败)、决定是否执行跳转。

// 页面开始加载时调用
- (void)webView:(WKWebView *)webView didStartProvisionalNavigation:(WKNavigation *)navigation;
// 当内容开始返回时调用
- (void)webView:(WKWebView *)webView didCommitNavigation:(WKNavigation *)navigation;
// 页面加载完成之后调用
- (void)webView:(WKWebView *)webView didFinishNavigation:(WKNavigation *)navigation;
// 页面加载失败时调用
- (void)webView:(WKWebView *)webView didFailProvisionalNavigation:(WKNavigation *)navigation;

2、页面跳转的代理方法有三种,分为(收到跳转与决定是否跳转两种)


// 接收到服务器跳转请求之后调用
- (void)webView:(WKWebView *)webView didReceiveServerRedirectForProvisionalNavigation:(WKNavigation *)navigation;
// 在收到响应后,决定是否跳转
- (void)webView:(WKWebView *)webView decidePolicyForNavigationResponse:(WKNavigationResponse *)navigationResponse decisionHandler:(void (^)(WKNavigationResponsePolicy))decisionHandler;
// 在发送请求之前,决定是否跳转
- (void)webView:(WKWebView *)webView decidePolicyForNavigationAction:(WKNavigationAction *)navigationAction decisionHandler:(void (^)(WKNavigationActionPolicy))decisionHandler;
WKUIDelegate:与JS交互时的ui展示相关:三种提示框;
/**
 *  web界面中有弹出警告框时调用
 *
 *  @param webView           实现该代理的webview
 *  @param message           警告框中的内容
 *  @param frame             主窗口
 *  @param completionHandler 警告框消失调用
 */
- (void)webView:(WKWebView *)webView runJavaScriptAlertPanelWithMessage:(NSString *)message initiatedByFrame:(void (^)())completionHandler;
WKScriptMessageHandler:必须实现的方法,这个方法是提高App与web端交互的关键,它可以直接将接收到的JS脚本转为OC或Swift对象
// 从web界面中接收到一个脚本时调用
- (void)userContentController:(WKUserContentController *)userContentController didReceiveScriptMessage:(WKScriptMessage *)message;
使用 Safari 自带的 Web View 调试工具

使用步骤,打开Safari偏好设置--》高级--》在菜单栏中先睡“开发”菜单(最下侧);

显示弹窗

在 UIWebView 里,js 的 alert() 弹窗会自动以系统弹窗的形式展示,但是 WKWebview 把这个接口也暴露给了我们,让我们自己 handle js 传来的 alert()。 在控制台中输入alert(1)即可调用native中的提示框。

func webView(webView: WKWebView, runJavaScriptAlertPanelWithMessage message: String, initiatedByFrame frame: WKFrameInfo, completionHandler: () -> Void) {
        let ac = UIAlertController(title: webView.title, message: message, preferredStyle: UIAlertControllerStyle.Alert)
        ac.addAction(UIAlertAction(title: "OK", style: UIAlertActionStyle.Cancel, handler: { (aa) -> Void in
            completionHandler()
        }))
        self.presentViewController(ac, animated: true, completion: nil)
    }
}
网页向APP传数据、调用APP类方法

在初始化webview时已配置WKWebViewConfiguration;使用window.webkit.messageHandlers.TEST.postMessage()向APP传值;

苹果在 WKWebView 中的 js runtime 里事先注入了一个 window.webkit.messageHandlers.OOXX.postMessage() 方法,我们可以使用这个方法直接向 Native 层传值,异常方便

随便在控制台post一个数据便可在xcode控制台看到

//    func userContentController(userContentController: WKUserContentController, didReceiveScriptMessage message: WKScriptMessage) {
//        
//        print(message.name)
//        print(message.body.description)
//        
//    }

传js对象(js 对象的 键 不用加双引号)

在safari控制台中传输js对象,实现:在APP中获取js对象,并根据对象内容,获取相应的类与该类中的方法。

window.webkit.messageHandlers.TEST.postMessage({className: "ClassName", functionName: "ClassFunc"})

实现WKScriptMessageHandler代理中的方法

func userContentController(userContentController: WKUserContentController, didReceiveScriptMessage message: WKScriptMessage) {
//根据定义的key来判断message
    if message.name == "TEST" {
    //转换为字典,并获取key/value
        if let dic = message.body as? NSDictionary,
            className = dic["className"]?.description,
            functionName = dic["functionName"]?.description {
            //运行时获取指定类
            if let cls = NSClassFromString(NSBundle.mainBundle().objectForInfoDictionaryKey("CFBundleName")!.description + "." + className) as? NSObject.Type{
            //初始化类对象并调用其方法
                let obj = cls.init()
                let functionSelector = Selector(functionName)
                if obj.respondsToSelector(functionSelector) {
                    obj.performSelector(functionSelector)
                } else {
                    print("方法未找到!")
                }
            } else {
                print("类未找到!")
            }
        }
    }
}


//创建类以供js调用
class ClassName: NSObject {
    func ClassFuc() {
        print("js调用APP类方法")
    }
}
参考文档

WKWebView的新特性与使用

标哥的技术博客

吕文翰_JohnLui博客

转载于:https://www.cnblogs.com/OnNineMonkey/p/5405842.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值