浏览器探究——Framework层基本架构

Framework层的主要功能

Framework层的webkik主要起到提供给APP层一个WebView控件,WebSettings设置,WebViewClient回调,WebChromeClient回调。这些用于上层APP实现浏览网页的功能。

而对于下层,通过native的接口与c++层的WebKit对接,把上层需求传递给WebKit,把WebKit的回调返回给上层或者自己做一些处理,因为一些跟平台相关的东西WebKit中也会回调到java层,让java层做处理,比如上传功能需要从其他模块获取上传文件的资源。

在android 2.3及其之前的版本中,html页面的请求是通过java层调用http接口来实现下载的,但是到了android4.0时html页面的请求在c++的WebKit层直接通过chromium的net部分发送http请求了。这里要额外注意的是,在android4.0中,对于java层的请求代码仍然保留(实际上可以通过配置c++层的WebKit来恢复使用java层请求html)。所以android4.0上的framework层的webkit代码是有些冗余的。另外还添加了部分对html5的支持,这些部分暂时都不研究了。

几个重要的类

WebView

WebView是提供给app层的控件,它必须运行在主线程也即UI线程中。

WebView中可以通过发消息给WebViewCore来请求功能,WebView中创建了CallbackProxy这个Handler的子类,用于让其他线程发消息给WebView所在的主线程,可以实现其他功能线程回调请求给WebView.

WebViewCore

这里要区分下WebViewCore类与WebViewCore线程。

WebViewCore类是与WebViewCore线程做交互的一个代理类,是WebView中创建的一个成员,用于让WebView向WebViewCore线程发消息和WebViewCore线程回调信息给WebView用。

而WebViewCore线程则是个单例的线程,负责接收WebView发来的请求功能的消息,即功能请求从app发给WebView,WebView把请求发给WebViewCore线程,然后WebView就返回了,这样不会影响到UI线程的阻塞。

其实这里可以模糊掉WebViewCore类与WebViewCore线程的区别,可以认为WebViewCore就是一个单独的服务类,并且是个单例的(虽然事实不是这样),模糊掉WebViewCore是WebView成员这个关系,认为WebView就是向WebViewCore发消息来实现功能请求的就可以了,这样就比较清晰他们的关系。

该类主要通过Message,Handler的机制在WebView与WebViewCore线程之间通讯的WebView向WebViewCore线程发的每个消息相当于一个请求的任务,而这个WebViewCore线程相当于一个服务,它在消息循环中不停的接收任务(消息),然后处理任务,然后再接收下一个任务(消息)。

基于这个模型可以把WebView看做客户端,把WebViewCore线程看做服务端。双方各自运行在各自的线程中,相互通过消息来通讯。

CallbackProxy

如上所说CallbackProxy 继承自Handler,由WebView创建,用于让其他线程的功能模块回调信息给WebView所在的主线程的。CallbackProxy 把收到的消息具体分发到WebView,WebViewClient,WebChromeClient中。

BrowserFrame

BrowserFrame是在WebViewCore线程中创建的,并且是WebViewCore的成员,它对应c层WebKit的Frame,这个Frame是一个具体的页面的概念。

BrowserFrame中也有CallbackProxy的引用,这样可以通过CallbackProxy回调消息给WebView.

这几个类的关系操作流程如下

浏览器探究——Framework层基本架构_第1张图片
但是这里要注意,WebView,WebViewCore,BrowserFrame都是一对一的关系,即新建一个WebView都会建立对应的WebViewCore和BrowserFrame。同时在WebView中都有一个CallbackProxy。WebViewCore和BrowserFrame中也都有对应的CallbackProxy的引用。

而WebViewCore线程却是全局唯一的一个。

这几个类的组织关系如下

浏览器探究——Framework层基本架构_第2张图片

 

这几个类的基本操作流程

可以看到很多操作都基于上述关系得到的流程,即请求先从APP发到WebView,在Framework层看来WebView是个客户端,WebViewCore是个服务端,那么请求会从WebView通过消息发给WebViewCore。WebViewCore会把处理通过自身的jni或者通过其成员BrowserFrame的jni发给C层的WebKit。

回调时,首先从C层的WebKit回调到WebViewCore或者BrowserFrame中,再通过成员引用CallbackProxy发消息给WebView所在的主线程,CallbackProxy中的消息处理中会决定把信息回调给WebView还是WebViewClient还是WebChromeClient。如果是后两者则App中实现该接口,就会收到回调信息了(实际代码中位于Tab.java中)。

这里通过loadUrl的操作来看下上述的这个流程。

loadUrl的例子

App执行WebView的loadUrl接口。

WebView的loadUrl中把一些信息保存为消息的参数,然后发出LOAD_URL消息给WebViewCore线程。以上完成了WebView向WebViewCore线程请求功能的过程。

接着WebViewCore线程收到消息,进行消息处理,对于LOAD_URL消息,首先取出消息中附带的参数信息,然后交给成员BrowserFrame来处理。

BrowserFrame通过jni接口把功能请求传递到c层的WebKit中,由WebKit做具体的处理。以上完成了整个功能的请求过程。

接下来是回调流程,当页面开始加载时首先在BrowserFrame中收到c层WebKit回调的函数loadStarted。此时回调操作是在WebViewCore线程中。

BrowserFrame通过CallbackProxy向主线程发消息PAGE_STARTED。以上完成了WebViewCore线程向WebView线程回调信息的过程。

CallbackProxy的消息处理循环位于主线程中,在消息处理函数中,分别向WebView和WebViewClient执行回调函数,其中WebViewClient执行的是onPageStarted回调函数。

WebViewClient本身定义成一套接口,在APP层实现了接口,所以APP层对WebViewClient实现的onPageStarted就会被调用,这样APP层就收到了回调(实际代码在Tab.java中)。以上便完成了整个功能的回调过程。

 

设置的流程

Framework 层提供的WebView的设置是WebSettings。但是WebSettings并不是在WebView中维护的,而是在WebViewCore中维护的。

WebSettings中有各个具体设置项的成员变量,

在app层进行WebSettings中某个设置项的设置后,如果该设置项的内容与之前的不同,则会用新的值来填充对应的成员变量,然后向WebViewCore线程发送消息SYNC,请求c层的WebKit同步设置内容。

读取设置项时,就直接从成员变量中读取就可以了。

 浏览器探究——Framework层基本架构_第3张图片

Framework层与C层的 几个主要的JNI类对应关系

浏览器探究——Framework层基本架构_第4张图片

你可能感兴趣的:(java,android,浏览器,jni,webkit)