Android与Js互调之 - 使用WebViewJavascriptBridge

1. 概述


为加快项目开发效率,相信绝大部分公司都会采用H5与Native原生结合开发,使用H5去开发一些功能,这里肯定会涉及到Android与Js互相调用的问题,这里有2种方式,第一种是使用原生的addJavascriptInterface()来解决,不过存在一定的风险,有一种比较安全的方式来满足二者互调的问题,就是我们今天所要讲解的一个新的东西,WebViewJavascriptBridge。

如果对addJavascriptInterface方式不太了解的,可以看下我之前写的文章
Android与Js互调之 - 使用addJavascriptInterface()

2. WebViewJavascriptBridge定义是什么?


WebViewJavascriptBridge是Java与Js互相调用的桥梁,替代了WebView中自带的addJavascriptInterface接口,使得Java与Js交互更加灵活,也使得开发会更加安全。

3. 具体实现如下


这里没有直接使用 最原生的BridgeWebView,而是 基于JsBridge封装的高效的自带加载进度条的WebView,当然这个东西不是我自己封装的,我只是在网上找的一个大神的文章,然后自己手动的添加一些注释,有利于我们大家来更清楚的知道其中的用法,其实很简单,因为大神已经把其封装的很好了,然后我们这边需要做的就是直接仿照它里边是怎样写的就ok了,以下是大神博客,想详细了解的可以移步这里:
Android基于JsBridge封装的高效带加载进度的WebView

下边我就直接贴出具体代码,大家直接看下就ok,其中注释也是有的,里边有我们平时开发中所需要的一些东西

/**
 *  Email: 2185134304@qq.com
 *  Create JackChen 2018/4/3 11:11
 *  Version:
 *  Params:
 *  Description:   基于JsBridge封装的高效自带加载进度条的WebView
 */
public class MainActivity extends AppCompatActivity {

    // WebView
    private ProgressBarWebView mProgressBarWebView;
    // 用于存放Js代码中的所有方法名
    private ArrayList<String> mHandlers = new ArrayList<>();


    ValueCallback<Uri> mUploadMessage;
    private static CallBackFunction mfunction;

    int RESULT_CODE = 0;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        initWebView();
    }

    private void initWebView() {

        mProgressBarWebView = (ProgressBarWebView) findViewById(R.id.login_progress_webview);
        mProgressBarWebView.setWebViewClient(new CustomWebViewClient(mProgressBarWebView.getWebView()) {

            @Override
            public String onPageError(String url) {
                //指定网络加载失败时的错误页面
                return "file:///android_asset/error.html";
            }

            @Override
            public Map<String, String> onPageHeaders(String url) {

                // 可以加入header
                return null;
            }

            @SuppressWarnings("unused")
            public void openFileChooser(ValueCallback<Uri> uploadMsg, String AcceptType, String capture) {
                this.openFileChooser(uploadMsg);
            }

            @SuppressWarnings("unused")
            public void openFileChooser(ValueCallback<Uri> uploadMsg, String AcceptType) {
                this.openFileChooser(uploadMsg);
            }

            public void openFileChooser(ValueCallback<Uri> uploadMsg) {
                mUploadMessage = uploadMsg;
                pickFile();
            }
        });

        // 打开页面,也可以支持网络url
        mProgressBarWebView.loadUrl("file:///android_asset/demo.html");



        mHandlers.add("login");
        mHandlers.add("callNative");
        mHandlers.add("callJs");
        mHandlers.add("open");

        //回调js的方法     handlerName:Js中写的方法  responseData:Js返回的数据  function.onCallBack("我在上海"):回调给Js的数据
        mProgressBarWebView.registerHandlers(mHandlers, new JsHandler() {
            @Override
            public void OnHandler(String handlerName, String responseData, CallBackFunction function) {

                // 点击WebView中 登录 (Js中定义的login()方法)
                if (handlerName.equals("login")) {
                    Toast.makeText(MainActivity.this, responseData, Toast.LENGTH_SHORT).show();

                } else if (handlerName.equals("callNative")) {

                    Toast.makeText(MainActivity.this, responseData, Toast.LENGTH_SHORT).show();
                    function.onCallBack("我在上海");


                // 点击调用native
                } else if (handlerName.equals("callJs")) {

                    Toast.makeText(MainActivity.this, responseData, Toast.LENGTH_SHORT).show();

                    // 想调用你的方法:
                    function.onCallBack("好的 这是图片地址 :xxxxxxx");


                // 点击选择相册
                } if (handlerName.equals("open")) {

                    mfunction = function;
                    pickFile();
                }

            }
        });

        // 首先显示WebView,然后调用Js中的callNative()方法,jsResponseData是Js返回来的数据
        mProgressBarWebView.callHandler("callNative", "hello H5, 我是java", new JavaCallHandler() {
            @Override
            public void OnHandler(String handlerName, String jsResponseData) {
                Toast.makeText(MainActivity.this, "h5返回的数据:" + jsResponseData, Toast.LENGTH_SHORT).show();
            }
        });

        //发送消息给js
        mProgressBarWebView.send("哈喽", new CallBackFunction() {
            @Override
            public void onCallBack(String data) {
                Toast.makeText(MainActivity.this, data, Toast.LENGTH_SHORT).show();
            }
        });
    }

    public void pickFile() {
        Intent chooserIntent = new Intent(Intent.ACTION_GET_CONTENT);
        chooserIntent.setType("image/*");
        startActivityForResult(chooserIntent, RESULT_CODE);
    }

    @Override
    public void onActivityResult(int requestCode, int resultCode, Intent intent) {
        if (requestCode == RESULT_CODE) {
            if (null == mUploadMessage) {
                return;
            }
            Uri result = intent == null || resultCode != Activity.RESULT_OK ? null : intent.getData();
            mUploadMessage.onReceiveValue(result);
            mUploadMessage = null;

            mfunction.onCallBack(intent.getData().toString());

        }
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
        // 防止内存泄露
        if (mProgressBarWebView.getWebView() != null) {
            mProgressBarWebView.getWebView().destroy();
        }
    }
}

具体代码已上传至github:
https://github.com/shuai999/WebViewJavascriptBridge.git

©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容