1. 程式人生 > >Android Html互動_二_ JS與App互相呼叫

Android Html互動_二_ JS與App互相呼叫

Android Html互動<二> JS與App互相呼叫

@(Android系統原始碼解析)[Android, html]

宣告:轉載請註明出處,知識有限,如有錯誤,請多多交流指正!

場景:html網頁中JS與App相互呼叫,相互傳輸資料,互相呼叫;

效果圖

程式碼主要分為2部分Android和Html程式碼,為了方便測試將index_js.html放在App專案assets資料夾下面,再通過WebView載入頁面,效果圖如下:
這裡寫圖片描述

網頁Html端程式碼

<!DOCTYPE html>
<html>

    <head
>
<meta charset="UTF-8"> <title>JS和Android互動</title> // 樣式 <style> button { height: 36px; width: 100%; background: #98bf21; } </style> </head>
<body> <p>JS和Android互動</p> <button onclick="invokeAppMethod()">JS呼叫App方法(不帶引數)</button> <br/> <br/> <button onclick="sendInfoToJava()">JS呼叫App方法(帶引數)</button> <script> // 傳送訊息到Android客戶端
function sendInfoToJava() { //呼叫android程式中的方法,並傳遞引數 var name = '我是JS'; window.AndroidWebView.showInfoFromJs(name); } // 直接呼叫Android客戶端中的showInfoFromJs方法 function invokeAppMethod() { window.AndroidWebView.showInfoFromJs(); } //在Android程式碼中呼叫此方法 function showInfoFromApp(msg) { alert("來自App的資訊:" + msg); } //在Android程式碼中呼叫此方法,不傳遞資訊 function showInfoFromApp() { alert("通過App呼叫JS"); }
</script> </body> </html>

Android端程式碼

  1. 如果Html在伺服器,需要新增網路許可權:
 <uses-permission android:name="android.permission.INTERNET" />
  1. 佈局程式碼
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:focusable="true"
    android:focusableInTouchMode="true"
    android:orientation="vertical"
    android:padding="8dp"
    tools:context=".MainActivity">

    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="一、Android呼叫Html中JS程式碼:" />


    <EditText
        android:id="@+id/input_et"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="請輸入App傳送給JS的資訊" />

    <Button
        android:id="@+id/btn_invoke_js"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="App呼叫JS(帶資料)" />

    <Button
        android:id="@+id/btn_invoke_js2"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="App呼叫JS(不帶資料)" />


    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginTop="8dp"
        android:text="二、Html中JS呼叫Android程式碼:" />

    <WebView
        android:id="@+id/webView"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />

</LinearLayout>
  1. 主要邏輯程式碼
/**
 * js與Android互調,互動
 */
public class AndroidJsActivity extends AppCompatActivity {
    private WebView webView;


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_android_js);
        webView = (WebView) findViewById(R.id.webView);

        webView.setVerticalScrollbarOverlay(true);
        //設定WebView支援JavaScript
        webView.getSettings().setJavaScriptEnabled(true);

        // 載入本地網頁
        webView.loadUrl("file:///android_asset/index_js.html");

        //在js中呼叫本地java方法
        webView.addJavascriptInterface(new JsInterface(this), "AndroidWebView");

        //新增客戶端支援
        webView.setWebChromeClient(new WebChromeClient());

        //設定監聽
        onInvokeJs();
        onInvokeJs2();
    }

    /**
     * App呼叫JS程式碼
     */
    private void onInvokeJs() {
        findViewById(R.id.btn_invoke_js).setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                String msg = ((EditText) findViewById(R.id.input_et)).getText().toString();
                //呼叫js中的函式:showInfoFromApp(msg)
                webView.loadUrl("javascript:showInfoFromApp('" + msg + "')");
            }
        });
    }

    /**
     * App呼叫JS程式碼
     */
    private void onInvokeJs2() {
        findViewById(R.id.btn_invoke_js2).setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                //呼叫js中的函式:showInfoFromApp()
                webView.loadUrl("javascript:showInfoFromApp()");
            }
        });
    }

}
  1. JS呼叫Android的類
/**
 * Author: river
 * Date: 2016/3/29 14:30
 * Description: js呼叫
 */
class JsInterface {
    private Context mContext;

    public JsInterface(Context context) {
        this.mContext = context;
    }

    /**
     * 在js中呼叫window.AndroidWebView.showInfoFromJs(name),便會觸發此方法。
     * 此方法名稱一定要和js中showInfoFromJava方法一樣
     *
     * @param name
     */
    @JavascriptInterface
    public void showInfoFromJs(String name) {
        Toast.makeText(mContext, "來自js的資訊:" + name, Toast.LENGTH_SHORT).show();
    }

    @JavascriptInterface
    public void showInfoFromJs(){
        Toast.makeText(mContext, "JS呼叫App方法", Toast.LENGTH_SHORT).show();
    }
}

解釋

  1. Android呼叫JS
    通過Android程式碼中webView.loadUrl("javascript:showInfoFromApp()");javascript:showInfoFromApp()與js中的function showInfoFromApp()方法名稱一致,必須相同名稱;同理有引數的呼叫的是function showInfoFromApp(msg)

  2. JS呼叫Android
    通過JS中window.AndroidWebView關聯到Android中WebView的name是AndroidWebView,Android端webView.addJavascriptInterface(new JsInterface(this), "AndroidWebView");方法關聯到JS,這樣JS就可以通過window.AndroidWebView.showInfoFromJs()中關聯到Android中JsInterface#showInfoFromJs()

  3. 兩者互調主要是名稱要一致,否則無法關聯上去