java和javascript配合,让Java和Javascript更加亲密

在移动App开发中,为了快速迭代,通常都会使用Native+Web的模式开发。具体来说就是使用Java提供接口,使用WebView控件嵌套Web页面来实现UI和交互。

在Android中,Java可以很方便的提供接口给WebView中的Js进行调用,只要以下一行代码就能搞定:

mWebView.addJavascriptInterface(new JavascriptInterface(), "custom_name");

这样,JavascriptInterface的所有声明为public的方法,都能被mWebView中的Js通过以下方式调用:

window.custom_name.xxx();//xxx为JavascriptInterface的公有方法

而Java需要调用Js时,则是通过WebView实例的loadUrl方法调用:

mWebView.loadUrl("javascript:xxx(yyy)");

这其实跟你在浏览器的地址栏敲下“javascript:alert(1)”的原理是一样的。

一切看起来都是那么的美好,只是……

当Java需要传递大量字符串给Js时,URL就力不从心了。另外,从URL执行的Js,在页面没加载完成时,是有可能导致页面出现undefined错误(因为要执行的那个方法可能还没有声明呢),会引发各种奇形怪状的错误。

那要怎么办呢?

再回看上面Js调用Java接口的地方,可以发现,Js是可以直接调用Java方法并取得Java给的返回值的(必须是可序列化的数据)。那么,为何不试试把Java需要执行的Js方法,保存起来,让Js来读取、执行、并把结果写回?

步骤如下:

Java把Js调用(命令)和回调缓存,如保存到ArrayList;

Js定时轮询Java提供的getCommandList接口;

Js读取到要执行命令,执行它,并把结果通过setResult写回给Java;

Java把对应命令的回调取出并执行。

如此即完成了Java调用Js的流程。

为了方便使用,简单的封装了下,名为AndroidJavascriptBridge,可移步到Github查看源码和示例(MainActivity.java和test.js )。

使用方法

Android端调用, 加入com.imatlas.jsb 和 com.imatlas.util包, 按如下步骤调用

//1. 创建JavascriptBridge实例

final JavascriptBridge jsb = new JavascriptBridge(webView);

//2. 调用Javascript方法

Bundle params = new Bundle();

params.putString("asdfasdf", "123123");

jsb.require("alert", params, new JavascriptBridge.Callback() {

@Override

public void onComplate(JSONObject response, String cmd, Bundle params) {

Log.i("js response",response.toString());

}

});

//3. 提供Java方法给Javascript调用

//添加个 messagebox 方法给js

jsb.addJavaMethod("messagebox", new JavascriptBridge.Function() {

@Override

public Object execute(JSONObject params) {

Toast.makeText(getApplicationContext(), params.toString(), Toast.LENGTH_LONG)

.show();

return "{\"ret\":123}";

}

});

Javascript端的调用, 须先引入web/js/jsb.js, 之后按如下方式调用

//1. 调用Java方法

jsb.require('messagebox', {'text': '你好, messagebox!'}, function(response){

alert('调用messagebox回来啦\n' + JSON.stringify(response));

});

//2. 提供Javascript方法给Java调用

jsb.addJavascriptMethod('alert', function(params){

alert( '------\n' + JSON.stringify(params) + '\n========\n');

return {'text': 'alert ok'};

});

IOS的话就要反过来了,要改成由Objective-C来轮询Js,来实现Js对Native的调用。

嗯,等改天有时间了,就把IOS也封装进来,用起来就简单多了。

转载:http://www.alloyteam.com/2013/02/java-with-javascript-more-intimate/

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值