WebView中js和android互動遇到的坑
阿新 • • 發佈:2019-01-31
js呼叫Android程式碼
//android程式碼
private int load_state = -1;//記錄當前的載入狀態
private WebView mWebView;
@SuppressLint("JavascriptInterface")
private void initView() {
mWebView = findViewById(R.id.mWebView);
final WebSettings webSettings = mWebView.getSettings();
webSettings.setJavaScriptEnabled(true );
//js程式碼中通過AndroidApp物件呼叫android的函式
mWebView.addJavascriptInterface
(new JsCallAndroid(), "AndroidApp");
mWebView.setWebViewClient(new WebViewClient() {
@Override
public void onPageFinished(final WebView view, String url) {
Log.e(TAG, "onPageFinished==========" + card_state);
UiHandler.runOnUiThread(new Runnable() {
@Override
public void run() {
if (!mBaseExit) {
mWebView.dismissLoadMessageView();//隱藏等待載入頁面
if (load_state == -1) {//因為如果正常的話回到檢視牌義介面、card_state=1
// handleLoadError();
}
}
}
});
}
} catch (Exception e) {
e.printStackTrace();
}
}*/
////////載入錯誤處理//////////////////
@Override
public void onReceivedError(WebView view, WebResourceRequest request, WebResourceError error) {
Log.e(TAG, "onReceivedError==========");
super.onReceivedError(view, request, error);
handleLoadError();
}
@Override
public void onReceivedHttpError(WebView view, WebResourceRequest request, WebResourceResponse errorResponse) {
super.onReceivedHttpError(view, request, errorResponse);
Log.e(TAG, "onReceivedHttpError==========");
handleLoadError();
}
@Override
public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {
super.onReceivedSslError(view, handler, error);
Log.e(TAG, "onReceivedSslError=============");
handleLoadError();
}
////////載入錯誤處理//////////////////
});
webSettings.setDefaultTextEncodingName("utf-8");
mWebView.loadUrl("https://www.demo.test/index.html");
}
/**
* 載入錯誤處理
*/
private void handleLoadError() {
Log.e(TAG, "handleLoadError==========" + load_state );
UiHandler.runOnUiThread(new Runnable() {
@Override
public void run() {
mWebView.setVisibility(View.GONE);
errorView.setVisibility(View.VISIBLE);//這裡可以顯示你的載入錯誤的頁面
}
});
}
private class JsCallAndroid {
/**
* 設定app的標題
*
* @param title
* @param state
*/
// 被JS呼叫的方法必須加入@JavascriptInterface註解
@JavascriptInterface
public void AppSetTitle(final String title, int state) {
LogCustom.e(TAG, "AppSetTitle==title=====" + title + ",state=====" + state);
}
}
三星galaxy5上顯示為白屏
坑1 沒有寫type=”text/javascript”
如何debug呢?網頁上彈出窗可以跟蹤程式碼執行到了那裡。call函式會彈出一個窗。
//index.html中程式碼
//寫一個全域性的js函式
function call(value){
alert(value);
}
<script >
call("aaaa")
AndroidApp.AppSetTitle("載入中...", 5);//這句就是js呼叫android中的函式
call("bbb")
</script>
測試的時候發現上述程式碼在其他手機上可以正常執行,但是在三星galaxy5顯示的是空白
在其他手機上可以正常的彈出aaaa和bbb,代表成功的執行了AndroidApp.AppSetTitle(“載入中…”, 5)
後來修改程式碼如下:
<script type="text/javascript">
call("aaaa")
AndroidApp.AppSetTitle("載入中...", 5);//這裡就是js呼叫android中的函式AppSetTitle函式
call("value===2")
</script>
也就是加了一句 type=”text/javascript”之後,三星galaxy5也可以正常的顯示了。所以程式碼還是要規範。
坑2 在ajax中函式呼叫引數沒有寫全
//定義函式如下
function $ajax(url, methods, postData, callback, booleans,errorCallback) {
$.ajax({
url: url,
type: methods,
data: postData,
success: callback,
headers: obj,
async : booleans,
beforeSend: function (request) {
},
error: function () {
},
complete: function () {
}
});
}
//引數不全的呼叫,在部分手機上顯示為白屏
$ajax(testIndex, "get",
{
user_name: user_name,
user_id: user_id,
},
function (res) {
var repData = true
if (res.data.can_test == true) {
window.location.href = "animateOpen.html?" + hrefs
} else {
window.location.href = "result.html?" + hrefs
}
}
);
//引數補全的呼叫,相容性更好
$ajax(testIndex, "get",
{
user_name: user_name,
user_id: user_id,
},
function (res) {
var repData = true
if (res.data.can_test == true) {
window.location.href = "animateOpen.html?" + hrefs
} else {
window.location.href = "result.html?" + hrefs
}
}, true,function (res) {
}
);
總結
webview使用中有很多坑,寫程式碼一定要規範,這樣相容性會好很多。