使用Cordova来解决HTML5制作的WebView手机不兼容的问题
Posted 阿秋SAMA
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了使用Cordova来解决HTML5制作的WebView手机不兼容的问题相关的知识,希望对你有一定的参考价值。
一:android 4.0WebView分析
(1)WebView API
主要提供给我们应用程序的接口,为了兼容向下版本,Android在高版本中也是对一层的API进行支持,
(2)Android WebView Framework
Android Framework:Android WebView是个特殊控件实现的支持需要Framework的代码主要在./frameworks/base/core/java/android/webkit目录下,在Android 4.0实现主要是在WebViewCore.java,BrowserFrame.java等文件。
(3)Android JNI
Android JNI:需要有Native代码支持,因此需要有JNI层实现,Android WebView 4.0的JNI层实现WebView相关代码在./external/webkit/Source/WebKit/android/jni/目录下,这一层起到承上启下的作用,链接Framework层以及WebKit层的桥梁,比如相关的一些实现在WebviewCore.cpp,WebCoreFrameBridge.cpp等。
(4)WebKit
WebKit: WebKit内核,其核心主要是解析W3C标准以及渲染排版网页,他是一个跨平台的内核引擎,那么需要支持各个平台,需要我们的平台实现层,在Android 4.0系统这一部分相关代码主要在./external/webkit/Source/WebKit/android/WebCoreSupport/目录下,比如FrameLoaderClientAndroid.cpp,ChromeClientAndroid.cpp,这一层负责WebCore与系统平台的桥接,具体在不同平台会有不同的实现。
二:Android 4.1–4.3 WebView的结构
Android 4.1–4.3版本WebView内核实现还是基于WebKit,但在WebView的Framework层发生了变化,引入了工厂模式,目地是为了将内核与上层API接口分离开来,分离的意义不仅仅是抽象接口,更重要的是将来能替换内核部分的实现。 在4.1–4.3这一系列版本native结构基本与4.0版本相同,下图呈现新的变化:
三:Android 4.4 WebView的结构
在Android 4.4系统上 Google已经将系统默认的Webkit内核替换成自己的开源项目chromium,通过之前的版本分析,我们可以看到Android 对WebView的Framework 结构进行调整使其更抽象,更重要的目的还是集成自己的开源chromium。下面我们来看看WebView的结构发生了什么样的变化:
在Android 4.0上已经默认开启硬件加速,因此WebView的渲染默认是基于硬件渲染的,通过本人分析其在WebView被隐藏的那一帧是采用软件渲染,目的是减少硬件占用,让其他UI能及时的响应。
为了将chromium项目集成到Android 中,chromium项目抽象出Android webview这一层,之前的接口抽离这时候已经变得很明显,Android Webview基于chromium content API这一层,第三方浏览器厂商也可以采用这种方式,目前所了解的厂商有Opera使用这种方式。Android 4.4WebView的渲染核心目前也没有发生太大变化,还是基于WebView的Canvas,将Chromium composit 结构绘制到WebView Canvas上。接入chromium内核,WebView浏览性能大幅度提升,但是和chrome for Android还是有些不同,主要体现在一下几点:
1. chrome浏览器是多进程架构,Chromium for Android Webview 是单进程架构。
2. chrome浏览器 内存占用比 Android WebView大的多。
3. chrome支持更多的html5 feature。
四:Android 5.0 WebView
Lollipop版本中WebView的内核实现采用Chromium 37版本,这个版本带来更多的安全性和稳定性。这个版本解决Android 4.4版本网页当中请求访问打开本地文件选择器问题,引入新的回调接口,onShowFileChooser方法,需要此功能的可以在5.0上接上这个回调接口,并实现功能。另外这个版本提供安全许可给用户选择,当网页需要访问特殊资源时,会通知我们的应用程序,请求允许,回调接口为onPermissionRequest。之前我们也提到这个版本使得WebView默认支持WebAudio,WebGL,WebRTC等标准。
另外Google Android 还将webview做为一个能动态更新的app,能不更新Android版本情况下,更新WebView内核。Android 5.0 Webview默认提供减少内存占用支持,并且智能选择需要绘制的HTML document部门来提供性能。 当然开发者可以在自己应用程序需要时关闭这个选项(enableSlowWholeDocumentDraw)。
五:使用Cordova
(1)Cordova概述
什么是Cordova?
*一个移动开发的框架
*将HTML,CSS,JS封装为原生App(Hybrid)(可以让一个前端工程师拥有研发Android App的能力)
*来自Adobe的PhoneGap产品,是当下很多Web开发框架的底层源码
(2)下载和安装Cordova框架
下载Cordova框架之前必须要先下Node.js,(注:Node.js是一个javascript运行环境(runtime)。实际上它是对Google V8引擎进行了封装。V8引 擎执行Javascript的速度非常快,性能非常好。Node.js对一些特殊用例进行了优化,提供了替代的API,使得V8在非浏览器环境下运行得更好。)
确认安装成功
在windows上安装Cordova
安装速度有点慢,还需要翻墙支持
下面的图表示安装成功
(3)安装ANT
输入网址:http://ant.apache.org/
在视图左边找到Download–Binary Distributions
选择对应的Zip文件进行下载
将解压的zip文件的bin目录添加到环境变量中
(4)Cordova的部分指令
在E盘创建一个”Cordova”文件夹
进入到E盘
进入之前创建的”Cordova”目录
创建自己的第一个项目
其中
hello 表示项目所在的文件夹
com.aqiu.sample 表示项目的包名
HelloWorld 表示入口类
进入到之前创建的hello文件夹
在hello项目文件夹中,为其搭建Android平台的环境
此时的platform–android中已经自动构建了可以在AS运行的代码块,使用AS打开即可
(5)项目文件中的文件目录
hooks:
存放的是我们自定义的扩展功能
platforms:是doc引入的运行平台,我们运行的是Android环境
www:表示的是HTML5的配置文件
注:这个地方将自己的HTML+CSS文件替换掉默认的文件,这样就可以显示自己写的HTML布局了
config.xml:配置文件,里面有起始页HelloWorld和项目名称”index.html”基础信息
六.Android Studio的集成Cordova项目
1.build构建成功的代码块
2.使用Cordova需要注意的问题
(1)在MainActiity中,没有WebView的布局,该布局在依赖库CordovaLib中通过代码构建
(2)在Activity的onCreate方法中,loadUrl(launchUrl)调用之后,CordovaLib中的WebView对象appView才有值,因此使用appView时,必须写在loadUrl的后面
(3)在Cordova中,appView是不能直接调用addJavascriptInterface()方法的,按照要求,在调用该方法之前,
需要加上一行代码:
WebView Wv = (WebView) appView.getEngine().getView();
(4)AS资源文件中,均加上了www文件夹,所以在使用路径下的图片时,在资源路径下要添加/www/路径
七:Cordova事件分发之返回键的使用
(1)在Cordova的CordovaWebViewImpl中,关于返回键的事件分发代码
着重要强调的是
engine.canGoBack():其作用是拦截Android原生的BackButton按钮,js无上一级时返回false,存在上一级返回true
engine.goBack:其作用的是使Android返回键在js页面跳转中有效,
也就是说,如果不需要进行js页面跳转,那么直接注释掉canGoBack()和goBack()方法即可
@Override
public Boolean onDispatchKeyEvent(KeyEvent event) {
int keyCode = event.getKeyCode();
boolean isBackButton = keyCode == KeyEvent.KEYCODE_BACK;
if (event.getAction() == KeyEvent.ACTION_DOWN) {
if (isBackButton && mCustomView != null) {//点击了返回键,并且js的历史栈中还有数据,那么页面时返回上一级
System.out.println("执行第一步!");
return true;//返回true表示拦截,即原生Android的返回不能调用本地的方法,而是调用js的代码
} else if (boundKeyCodes.contains(keyCode)) {
return true;
} else if (isBackButton) {
return engine.canGoBack();//作用是拦截Android原生的BackButton按钮
}
} else if (event.getAction() == KeyEvent.ACTION_UP) {
if (isBackButton && mCustomView != null) {
hideCustomView();
return true;
} else if (boundKeyCodes.contains(keyCode)) {
String eventName = null;
switch (keyCode) {
case KeyEvent.KEYCODE_VOLUME_DOWN:
eventName = "volumedownbutton";
break;
case KeyEvent.KEYCODE_VOLUME_UP:
eventName = "volumeupbutton";
break;
case KeyEvent.KEYCODE_SEARCH:
eventName = "searchbutton";
break;
case KeyEvent.KEYCODE_MENU:
eventName = "menubutton";
break;
case KeyEvent.KEYCODE_BACK:
eventName = "backbutton";
break;
}
if (eventName != null) {
sendJavascriptEvent(eventName);
return true;
}
} else if (isBackButton) {
return engine.goBack();
}
}
return null;
}
(2)在跳转下一个js页面时,清空之前栈内容
本地Java代码:
@JavascriptInterface
public void clearHistory() {
wV.postDelayed(new Runnable() {
@Override
public void run() {
wV.clearHistory();
}
}, 1000);
}
JavaScript跳转页面,并且调用方法
/**
* 退出登录
* @returns
*/
function logout(){
user = {};
window.js2java.clearHistory();
window.location.href="#login";
}
当我们跳转到”login”界面时,”login”界面之前的页面历史清空
以上是关于使用Cordova来解决HTML5制作的WebView手机不兼容的问题的主要内容,如果未能解决你的问题,请参考以下文章
我想利用ionic,cordova,angularjs来制作一个简单的app应用,想知道具体该如何开始,能在浏览器测试就好
我可以/我应该在 Cordova 应用程序中下载 html5 代码吗?