Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

此项目,主要演示Android的WebView视图中,Native Call JavaScript、以及JavaScript Call Native的几种方式。

Notifications You must be signed in to change notification settings

CoderMacro/AndroidJSInterface

Folders and files

NameName
Last commit message
Last commit date

Latest commit

History

2 Commits

Repository files navigation

AndroidJSInterface

此项目,主要演示Android的WebView视图中,Native Call JavaScript、以及JavaScript Call Native的几种方式。


写在前面: Hybrid不可避免使用Native和JS交互,本文主要总结一下Android和JavaScript交互的解决方方。

[TOC]

A、Native调用JavaScript

方案一:调用loadUrl执行一段js
mWebView.loadUrl("javascript:alert('hello world')");
方案二:调用evaluateJavascript异步执行一段js
String jsString = "sum(a, b)";
mWebView.evaluateJavascript(js, new ValueCallback<String>() {
 @Override
 public void onReceiveValue(String s) {
 // 这里可以处理被调用js方法的return
 }
});
方案三:引用JsBridge框架
  • Web首先初始化WebViewJavascriptBridge,注册事件监听。
  • Web然后初始化接收函数回调,分为默认接收指定接收,responseCallback回调给Native信息
  • Native 调用Webview.send()WebView.callHandler()
//注册事件监听,初始化
function setupWebViewJavascriptBridge(callback) {
	if (window.WebViewJavascriptBridge) {
		callback(WebViewJavascriptBridge)
	} else {
		document.addEventListener(
 'WebViewJavascriptBridgeReady',
 function() {
 callback(WebViewJavascriptBridge)
 },
 false
 );
 }
}
//回调函数,接收java发送来的数据
setupWebViewJavascriptBridge(function(bridge) {
 //默认接收
	bridge.init(function(message, responseCallback) {
		// 处理接收到消息
	});
	//指定接收,
	bridge.registerHandler("JSFUCN", function(data, responseCallback) {
		// 处理接收到消息
	});
})
 // 默认接收
 private void callJavaScriptDefaut() {
 mWebView.send("发送数据给js默认接收, new CallBackFunction() {
 @Override
 public void onCallBack(String data) { //处理js回传的数据

 });
 }
 // 指定接收
 private void callJavaScriptSpec() {


 mWebView.callHandler("JSFUCN", "发送数据给js指定接收", new CallBackFunction() {
 @Override
 public void onCallBack(String data) { //处理js回传的数据
 
 }
 });
 }

利用 webview调用js需要注意一下几点

  • WebSettings设置支持javascript
// 设置在类之前
@SuppressLint("SetJavaScriptEnabled") 
mWebView.getSettings().setJavaScriptEnabled(true);
  • 在运行Js脚本前,要有document对象,至少得load一个空白页
webView.loadData("","text/html","UTF-8");
  • 如果还是不行的话,就应该是因为第一个还没执行完呢 - 从界面按钮调用 - 延时调用 - 在onPageFinished中调用
webView.loadData("","text/html","UTF-8");
webView.loadUrl("javascript:alert('hello')");
  • 必须实现WebChromeClient、WebViewClient
webView.setWebViewClient(new WebViewClient());
webView.setWebChromeClient(new WebChromeClient());
  • 使用JSBridge不用实现WebViewClient

B、JavaScript调用Native

方案一:拦截跳转
  • WebViewClient重载shouldOverrideUrlLoading 拦截URL

Web代码

function openMyBlogNewTarget() {
 window.open('https://www.jianshu.com/u/263c210b047c')
}
function openMyBlog() {
 window.location.href = 'https://www.jianshu.com/u/263c210b047c'
}
<a href="http://www.baidu.com" title="baidu" target="_blank">新标签页打开百度</a>
<a href="http://www.baidu.com" title="baidu" >当前页打开百度</a>
<button onclick='openMyBlogNewTarget()'>新标签打开我的博客</button>
<button onclick="openMyBlog()">打开我的博客</button>

Android代码

private class MYWebViewClient extends WebViewClient {
	@Override
	public void onPageStarted(WebView view, String url, Bitmap favicon) {
		super.onPageStarted(view, url, favicon);
	}
	
	// 新方法 API21以后
	@Override
	public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
		super.shouldOverrideUrlLoading(view, request);
		
		// 拦截Request
		if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
			Log.d(TAG, "shouldOverrideUrlLoading: " + request.getUrl().toString());
 }
		return true;
	}
 
 // 旧方法 兼容API21之前
	@Override
	public boolean shouldOverrideUrlLoading(WebView view, String url) {
		super.shouldOverrideUrlLoading(view, url);
		// 拦截url
		Log.d(TAG, "shouldOverrideUrlLoading: " + url);
		return true;
	}
}
方案二:JSInterface
  • JS中使用window.objects.function语法调用Native,其中objects与Native中一直。
  • Native中定义Class,以及被调用的func用 public、@JavascriptInterface修饰。
  • Native中addJavascriptInterface(obj, name)
function callNative() {
	var amount = 123.5;
	var orderno = "FG1afsdakewqr";
	window.mobileApp.toPay(amount, orderno);
}
<button onclick="window.mobileApp.sendMessage('特斯拉 Model 3')">获取商品名</button>
<button onclick="callNative()">支付按钮</button>
mWebView.addJavascriptInterface(new JsInterface(tv), "mobileApp");
private class JsInterface {
	private TextView showText;
	
	public JsInterface(TextView tv) {
		showText = tv;
	}
	@JavascriptInterface
	public void sendMessage(String msg) {
		Log.d(TAG, "sendMessage: " + msg);
	}
 
 @JavascriptInterface
	public void toPay(float amount, String oderno) {
		Log.d(TAG, "sendMessage: " + amount);
 }
}
方案三:引用JsBridge框架
  • JS中调用window.WebViewJavascriptBridge.send 或者 window.WebViewJavascriptBridge.callHandler 向Native发消息
  • Native中注册指定接收WebView.registerHandler或者注册默认接收WebView.setDefaultHandler
//js传递数据给java
function jsCallNativeDefault() {
	window.WebViewJavascriptBridge.send({ 'param': "str1" },	function(responseData) { //处理java回传的数据
	});
}
function jsCallNativeSpec() {
	window.WebViewJavascriptBridge.callHandler(
	'Spec' //指定接收参数 submitFromWeb与java一致
	,'指定接收'
	,function(responseData) { //处理java回传的数据
	
	 });
}
mWebView.registerHandler("Spec", new BridgeHandler() {
	@Override
	public void handler(String data, CallBackFunction function) {
		Log.i("", "handler = submitFromWeb, data from web = " + data);
		function.onCallBack("submitFromWeb exe, response data 中文 from Java");
			showTextView.setText("指定接收:" + data);
		}
});
mWebView.setDefaultHandler(new DefaultHandler() {
	@Override
	public void handler(String data, CallBackFunction function) {
		Log.i("", "handler = submitFromWeb, data from web = " + data);
		function.onCallBack("submitFromWeb exe, response data 中文 from Java");
			showTextView.setText("默认接收:" + data);
		}
});

About

此项目,主要演示Android的WebView视图中,Native Call JavaScript、以及JavaScript Call Native的几种方式。

Topics

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

AltStyle によって変換されたページ (->オリジナル) /