Android WebView实践

WebView在混合开发中很重要,如果做纯应用开发的话则很少接触他,这里来梳理一下WebView的知识。

一 基本用法

1.1 Android View的一种用来展示网页

  • 在布局中添加WebView
  • 使用WebView加载网页

1.2 基本组件

  • WebSettings:对WebView做各种设置
1.2.1 JS处理
  • setJavaScriptEnabled(true); //支持js
  • setPluginsEnabled(true); //支持插件
  • setJavaScriptCanOpenWindowsAutomatically(true); //支持通过JS打开新窗口
1.2.2 缩放处理
  • setUseWideViewPort(true); //将图片调整到适合webview的大小
  • setLoadWithOverviewMode(true); // 缩放至屏幕的大小
  • setSupportZoom(true); //支持缩放,默认为true。是下面那个的前提。
  • setBuiltInZoomControls(true); //设置内置的缩放控件。 这个取决于setSupportZoom(), 若setSupportZoom(false),则该WebView不可缩放,这个不管设置什么都不能缩放。
  • setDisplayZoomControls(false); //隐藏原生的缩放控件
1.2.3 内容布局
  • setLayoutAlgorithm(LayoutAlgorithm.SINGLE_COLUMN); //支持内容重新布局
  • supportMultipleWindows(); //多窗口
1.2.4 文件缓存
  • setCacheMode(WebSettings.LOAD_CACHE_ELSE_NETWORK); //关闭webview中缓存
  • setAllowFileAccess(true); //设置可以访问文件
1.2.5 其他设置
  • setNeedInitialFocus(true); //当webview调用requestFocus时为webview设置节点
  • setLoadsImagesAutomatically(true); //支持自动加载图片
  • setDefaultTextEncodingName("utf-8"); //设置编码格式
  • setPluginState(PluginState.OFF); //设置是否支持flash插件
  • setDefaultFontSize(20); //设置默认字体大小
  • WebViewClient:用来帮助WebView处理各种通知, 请求事件。继承它实现定制。
  • shouldOverrideUrlLoading(WebView view, String url) //在网页上的所有加载都经过这个方法,这个函数我们可以做很多操作。比如获取url,查看url.contains(“add”),进行添加操作
  • shouldOverrideKeyEvent(WebView view, KeyEvent event) //处理在浏览器中的按键事件。
  • onPageStarted(WebView view, String url, Bitmap favicon) //开始载入页面时调用的,我们可以设定一个loading的页面,告诉用户程序在等待网络响应。
  • onPageFinished(WebView view, String url) //在页面加载结束时调用, 我们可以关闭loading 条,切换程序动作。
  • onLoadResource(WebView view, String url) //在加载页面资源时会调用,每一个资源(比如图片)的加载都会调用一次。
  • onReceivedError(WebView view, int errorCode, String description, String failingUrl) //报告错误信息
  • doUpdateVisitedHistory(WebView view, String url, boolean isReload) //更新历史记录
  • onFormResubmission(WebView view, Message dontResend, Message resend) //应用程序重新请求网页数据
  • onReceivedHttpAuthRequest(WebView view, HttpAuthHandler handler, String host,String realm) //获取返回信息授权请求
  • onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) //让webview处理https请求。
  • onScaleChanged(WebView view, float oldScale, float newScale) //WebView发生改变时调用
  • onUnhandledKeyEvent(WebView view, KeyEvent event) //Key事件未被加载时调用
  • WebChromeClient:帮助WebView处理JS的对话框、网址图标、网址标题和加载进度等。
  • public void onProgressChanged(WebView view, int newProgress); //获得网页的加载进度,显示在右上角的TextView控件中
  • public void onReceivedTitle(WebView view, String title); //获取Web页中的title用来设置自己界面中的title, 当加载出错的时候,比如无网络,这时onReceiveTitle中获取的标题为"找不到该网页",
  • public void onReceivedIcon(WebView view, Bitmap icon); //获取Web页中的icon
  • public boolean onCreateWindow(WebView view, boolean isDialog, boolean isUserGesture, Message resultMsg);
  • public void onCloseWindow(WebView window);
  • public boolean onJsAlert(WebView view, String url, String message, JsResult result); //处理alert弹出框,html 弹框的一种方式
  • public boolean onJsPrompt(WebView view, String url, String message, String defaultValue, JsPromptResult result) //处理confirm弹出框
  • public boolean onJsConfirm(WebView view, String url, String message, JsResult result); //处理prompt弹出框

生命周期

  • onResume(): WebView为活跃状态时回调,可以正常执行网页的响应。
  • onPause(): WebView被切换到后台时回调, 页面被失去焦点, 变成不可见状态,onPause动作通知内核暂停所有的动作,比如DOM的解析、plugin的执行、JavaScript执行。
  • pauseTimers(): 当应用程序被切换到后台时回调,该方法针对全应用程序的WebView,它会暂停所有webview的layout,parsing,javascripttimer。降低CPU功耗。
  • resumeTimers(): 恢复pauseTimers时的动作。
  • destroy():关闭了Activity时回调, WebView调用destory时, WebView仍绑定在Activity上.这是由于自定义WebView构建时传入了该Activity的context对象, 因此需要先从父容器中移除WebView, 然后再销毁webview。


页面导航

页面跳转

当我们在WebView点击链接时, 默认的WebView会直接跳转到别的浏览器中, 如果想要实现在WebView内跳转就需要设置WebViewClient

WebView、WebViewClient、WebChromeClient三者的区别
  • WebView: 主要负责解析和渲染网页
  • WebViewClient: 辅助WebView处理各种通知和请求事件
  • WebChromeClient: 辅助WebView处理JavaScript中的对话框, 网址图标和标题等
控制不同链接的跳转方式

继承WebViewClient重写shouldOverrideUrlLoading()方法



方法的两点说明

  • 方法返回值
    返回true: Android 系统会处理URL, 一般是唤起系统浏览器。 返回false: 当前 WebView 处理URL。
  • 方法deprecated问题
    API >= 24时被标记deprecated, 它的替代方法是


页面回退

重写onKeyEvent()方法


页面滑动
  • 三个判断高度的方法
    getScrollY();当前内容滚动的距离
    getHeight(); getBottom();都返回当前WebView这个容器的高度
    getContentHeight(); 整个html的高度, 但并不等同于当前整个页面的高度。因为WebView有缩放功能, 所以当前整个页面的高度实际上应该是原始html的高度 再乘上缩放比例.
  • 判断WebView是否滚动到顶部或底部



    API 17开始, mWebView.getScale()被标记为deprecate,获取新的Scale。


    image
缓存实现
  • 加载html页面时, 会在/data/data/包名目录下生成database与cache两个文件夹。
  • 请求的url记录是保存在WebViewCache.db, 而url的内容是保存在WebViewCache文件夹下。
  • 控制缓存行为


清除缓存

本地资源访问

  • html内容先下载到本地,然后使用loadDataWithBaseURL加载html。这样就可以在html中使用 [file:///android_asset/xxx.png](file:///android_asset/xxx.png)的链接来引用包里 面assets下的资源了。
  • 注意事项
    从网络上下载html的过程应放在工作线程中
    html下载成功后渲染出html的步骤应放在UI主线程,不然WebView会报错
    html下载失败则可以使用我们前面讲述的方法来显示自定义错误界面

二 代码交互

Android原生方案
  • JavaScript代码和Android代码是通过addJavascriptInterface()来建立连接的
1. 设置WebView支持JavaScript
2. webView.getSettings().setJavaScriptEnabled(true);
3. 在Android工程里定义一个接口WebAppInterface
4. API >= 17时, 被JavaScript调用的Android方法前添加@JavascriptInterface注解, 否则将无法识别。
5.  Android代码中将该接口添加到WebView
    webView.addJavascriptInterface(new WebAppInterface(this), "Android");
    "Android"就是我们为这个接口取的别名, 在JavaScript就可以通过Android.showToast(toast)这种方式来调用此方法。
  • 在JavaScript中调用Android方法
    JavaScript中我们不用再去实例化WebAppInterface接口


  • 由于addJavascriptInterface()给予了JS代码控制应用的能力, 这是一项非常有用的特性, 但同时也带来了安全上的隐患,

jockeyjs开源方案

  • jockeyjs是一套IOS/Android双平台的Native和JS交互方法, 比较适合用在项目中
  • jockeyjs对Native和JS的交互做了优美的封装, 事件的发送与接收都可以通过send()和on()来完成。

三 性能优化

  • 优化网页加载速度
    原因:webkit解析网页各个节点,当有图片加载时会影响css或者js文件加载
    解决办法: 设置WebView, 先禁止加载图片



    覆写WebViewClient的onPageFinished()方法, 页面加载结束后再加载图片



    4.4以上系统在onPageFinished时再恢复图片加载时,如果存在多张图片引用的是相同的src时,会只有一个image标签得到加载,因而对于这样的系统我们就先直接加载。
  • 硬件加速页面闪烁问题
    原因:当WebView视图被整体遮住一块,然后突然恢复时(比如使用SlideMenu将WebView从侧边 滑出来时),这个过渡期会出现白块同时界面闪烁。
    解决办法:在过渡期前将WebView的硬件加速临时关闭,过渡期后再开启



    过度后开启硬件加速



以上就是我对webView的总结。

你可能感兴趣的:(Android WebView实践)