天天看点

Android端使用lzyzsd/JsBridge笔记1.背景2.开发工具3.js_native_contact_demo

1.背景

之前只是用webview展示网页,和前端小伙伴没怎么联调过,传uid和token也是直接在链接后面拼,但实际复杂些项目中不可避免要和前端进行互相调用,今天重新看了一遍大佬写的JsBridge,写一个使用的小笔记

前排放入github传送门,星星最多的jsbridge! 7.4k ,同时感谢大佬

lzyzsd/JsBridge

2.开发工具

AndroidStudio

3.js_native_contact_demo

1.创建一个android项目,常规操作~ (ps:项目能跑起来没问题吧…)

Android端使用lzyzsd/JsBridge笔记1.背景2.开发工具3.js_native_contact_demo

2.新建一个assets文件夹,如上图所示,里面创建一个叫demo.html的文件,代码直接贴进去,复制粘贴才是王道,手敲都是异类(不接受反驳,小声xx~+邪笑.png)

<html xmlns:white-space="http://www.w3.org/1999/xhtml">
<head>
    <meta content="text/html; charset=utf-8" http-equiv="content-type">
    <!-- 网页适配手机页面-->
    <meta name="viewport"
          content="width=device-width, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0, user-scalable=no">
    <title>
        js调用java
    </title>
</head>

<body bgcolor="#f0ffff">
<div>
    <p id="show" style="background-color:white">
    </p>
    <pre id="init">
    </pre>
    <p>
        <input type="text" id="text1" value="username"/>
    </p>
    <p>
        <input type="text" id="text2" value="address"/>
    </p>
    <p>
        <input type="button" id="enter" value="无需分配handle方法名(默认的),直接发消息给native"
               onclick="jsToNativeDefault();"
        />
    </p>
    <p>
        <input type="button" id="enter1" value="通过submitFromWeb的handle方法名,调用native的同名方法"
               onclick="jsToNativeCustom();"
        />
    </p>
    <p>
        <input type="button" id="enter2" value="显示html" onclick="testDiv();"/>
    </p>
    <p>
        <input type="file" value="默认为type的input输入框,手机上没什么反应,在pc端会自动打开选择文件的窗口,点击文件会将文件名输入"/>
    </p>
    <xmp id='showHtml' style='background-color:white'/>
</div>
</body>
<script>


    // js发送native默认的消息
    function jsToNativeDefault() {
        var str1 = document.getElementById("text1").value;
        var str2 = document.getElementById("text2").value;

        //send message to native
        var data = {id: 1, content: "通过js页面点击,调用默认方法,发送该信息到手机端"};
        window.WebViewJavascriptBridge.send(
            data
            , function (responseData) {
                document.getElementById("show").innerHTML = "发消息给native,并收到了native的反馈如下\n" + responseData
            }
        );

    }

    // js发送native自定义名字的消息
    function jsToNativeCustom() {
        var str1 = document.getElementById("text1").value;
        var str2 = document.getElementById("text2").value;

        //call native method
        window.WebViewJavascriptBridge.callHandler(
            'submitFromWeb'
            , {'param': '通过js页面点击,调用submitFromWeb方法,发送该信息到手机端'}
            , function (responseData) {
                document.getElementById("show").innerHTML = "发消息给native,并收到了native的反馈如下\n" + responseData
            }
        );
    }

    // 将html标签下的所有代码贴入xmp标签里
    function testDiv() {
        document.getElementById("showHtml").innerHTML = document.getElementsByTagName("html")[0].innerHTML;
    }

    // 设置向native发送的回调
    function connectWebViewJavascriptBridge(callback) {
        if (window.WebViewJavascriptBridge) {
            callback(WebViewJavascriptBridge)
        } else {
            document.addEventListener(
                'WebViewJavascriptBridgeReady'
                , function () {
                    callback(WebViewJavascriptBridge)
                },
                false
            );
        }
    }

    // 获取native发送的消息
    connectWebViewJavascriptBridge(function (bridge) {
        bridge.init(function (message, responseCallback) {
            alert(message);
            document.getElementById("show").innerHTML = ("native通过默认方法给js发来的信息如下\n" + message);
            var data = {
                'JS Responds': 'js已经收到默认方法发送来的消息,native请知悉!'
            };

            if (responseCallback) {
                responseCallback(data);
            }
        });

        bridge.registerHandler("functionInJs", function (data, responseCallback) {
            alert(data); // typeof data  是  string
            document.getElementById("show").innerHTML = ("native通过functionInJs方法给js发来的信息如下\n" + data);
            var str1 = JSON.parse(data);
            document.getElementById("text1").value = str1.name;
            document.getElementById("text2").value = str1.location.address;
            if (responseCallback) {
                var responseData = "js已经收到functionInJs方法发送来的消息,native请知悉!";
                responseCallback(responseData);
            }
        });
    })
   
</script>
</html>
           

3.引入jsbridge

project级build.gradle中加入jitpack的maven库

allprojects {
    repositories {
        google()
        jcenter()
        // jitpack
        maven { url "https://jitpack.io" }
    }
}
           

app级build.gradle中加入dependencies依赖项

dependencies {
    ...
    implementation 'com.google.code.gson:gson:2.8.6'
}
           

4.Android的xml页面代码,贴就完了

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1"
        android:background="@color/colorPrimary"
        android:orientation="vertical">
        <TextView
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="@color/colorPrimary"
            android:gravity="center"
            android:text="这里是原生⬇️"
            android:textStyle="bold" />
        <Button
            android:id="@+id/btnDefaultTest"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="向js发送默认handleName的消息"
            android:textAllCaps="false" />
        <Button
            android:id="@+id/btnCustomTest"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="向js发送定制handleName=functionInJs的消息"
            android:textAllCaps="false" />
        <TextView
            android:id="@+id/tvTextInfo"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:gravity="center"
            android:text=""
            android:textColor="#ffffff" />
    </LinearLayout>
    <TextView
        android:id="@+id/tvReloadUrl"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="#f0ffff"
        android:gravity="center"
        android:text="这里是网页⬇️"
        android:textStyle="bold" />
    <com.github.lzyzsd.jsbridge.BridgeWebView
        android:id="@+id/testWebView"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1" />
</LinearLayout>
           

布局截图

Android端使用lzyzsd/JsBridge笔记1.背景2.开发工具3.js_native_contact_demo

运行截图

Android端使用lzyzsd/JsBridge笔记1.背景2.开发工具3.js_native_contact_demo

5.activity中的代码,贯彻一直的“优良作风”粘代码(findById自己写- -)

static class Location {
        String address;

        public Location(String address) {
            this.address = address;
        }
    }

 static class User {
        String name;
        Location location;
        String testStr;

        public User(String name, Location location, String testStr) {
            this.name = name;
            this.location = location;
            this.testStr = testStr;
        }
    }

           
// 设置浏览器链接
        webView.setWebChromeClient(new WebChromeClient());
        // 加载url
        webView.loadUrl("file:///android_asset/demo.html");

        // 注册js监听回调,js通过默认方法发送消息给native时,可以在此处接收到
        webView.setDefaultHandler(new BridgeHandler() {
            @Override
            public void handler(String data, CallBackFunction function) {
                new AlertDialog.Builder(MainActivity.this).setMessage(data.toString()).show();
                tvTextInfo.setText(data.toString());
                function.onCallBack("Native已经收到了默认方法的消息,Js请知悉!");
            }
        });

        // 注册js监听回调,js通过 submitFromWeb 方法发送消息给native时,可以在此处接收到
        webView.registerHandler("submitFromWeb", new BridgeHandler() {
            @Override
            public void handler(String data, CallBackFunction function) {
                new AlertDialog.Builder(MainActivity.this).setMessage(data.toString()).show();
                tvTextInfo.setText(data.toString());
                function.onCallBack("Native已经收到了名为submitFromWeb方法的消息,Js请知悉!");
            }
        });

        // native主动发消息给js(默认handleName方法)
        btnDefaultTest.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                webView.send("这里是native向js发送的默认消息!", new CallBackFunction() {
                    @Override
                    public void onCallBack(String data) {
                        tvTextInfo.setText(data.toString());
                        new AlertDialog.Builder(MainActivity.this).setMessage("通过默认方法发消息给js,并收到了js的反馈如下\n" + data).show();
                    }
                });
            }
        });

        // native主动发消息给js(handleName = "functionInJs" 的方法)
        btnCustomTest.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                webView.callHandler("functionInJs", new Gson().toJson(new User("小白兔", new Location("大兴安岭"), "这里是native向js发送的名字叫做'functionInJs'消息!")), new CallBackFunction() {
                    @Override
                    public void onCallBack(String data) {
                        tvTextInfo.setText(data.toString());
                        new AlertDialog.Builder(MainActivity.this).setMessage("通过functionInJs方法发消息给js,并收到了js的反馈如下\n" + data).show();
                    }
                });
            }
        });

        // 重新加载网页
        tvReloadUrl.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                webView.loadUrl("file:///android_asset/demo.html");
            }
        });
           

有兴趣的建议跟着代码弄个项目出来,自己点点思路会很清晰

本来还想解释的,发现没啥好说的,注释写的挺清楚了,就这样吧,溜了!~