編輯:關於Android編程
最近研究HyBrid的兩種方式:
//啟動javascript webView = (WebView) findViewById(R.id.webView); //webView.setVerticalScrollbarOverlay(true); String uri = "file:///android_asset/js_test2.html"; webView.loadUrl(uri); // 添加客戶端支持 webView.setWebChromeClient(new WebChromeClient()); // 設置WebView支持JavaScript webView.getSettings().setJavaScriptEnabled(true);注釋比較清楚,不多解釋。
原生中代碼:
// 調用js中的函數:jsFun(msg) webView.loadUrl("javascript:jsFun('" + msg + "')");直接通過Url加載javascript:+方法名
js中對應代碼:
//在java中調用此方法 function jsFun(msg){ alert("我是js方法,被java調用,傳遞過來的參數是:"+msg); }
如此即可調用在native中調用js代碼:效果圖如下:
native中添加:
// 添加js交互接口 webView.addJavascriptInterface(new MyJava(this), "javaObject");addJavascriptInterface()源碼:
* @param object the Java object to inject into this WebView's JavaScript * context. Null values are ignored. * @param name the name used to expose the object in JavaScript */ public void addJavascriptInterface(Object object, String name) { checkThread(); mProvider.addJavascriptInterface(object, name); }第一個參數是Object對象:將Object對象注入到WebView的JavaScript的上下文中。
第二個參數name:在JavaScript暴露對象使用的名稱。
通俗點講:也就是用第二個參數名字在js中使用,來引用第一個java對象。
我們這個例子中自定義了一個MyJava對象:
private class MyJava { private Context mContext; public MyJava(Context context) { this.mContext = context; } // 在js中調用window.javaObject.javaFun(name),便會觸發此方法。 // api17版本以上加上注解 @JavascriptInterface public void javaFun(String name) { Toast.makeText(mContext, "我是java方法,被js調用,js傳遞過來的參數是:" + name, Toast.LENGTH_LONG).show(); } }構造方法直接忽略。這句注釋千萬不能忽略。
@JavascriptInterface涉及到4.2以上版本能否使用。4.2之前有個安全漏洞,4.2之後修復的方式,是js調用native的方法,方法上必須通過該注釋注明才可以調用。
方法javaFun很簡單,不多說,直接看js中如何調用。
js中添加:
function sendInfoToJava(){ //js調用java方法,並傳遞參數 var value = document.getElementById("name_input").value; window.javaObject.javaFun(value); }通過window.javaObject.javaFun(value)調用native的方法。之前已經解釋過javaObject引用MyJava對象。然後通過對象引用方法。
PS :JsBridge類庫地址。
查看類庫結構:
導入步驟:
此處上面的example就不要導入了。一個樣例,導入多余,還可能沖突。選擇finish。導入第三方完畢。
高興的太早了。主項目還調用不了這個導入的第三方包。
還需如下設置:
選擇之前的命名的第三方類庫,ok導入完畢。可以正常使用了。
PS:查閱了好多資料,之後總算是懂了。哎。好好學習,天天向上吧,少年。
通用部分:
xml:寫一個BridgeWebView
說明:
樣式很簡單:上面一個按鈕寫著:button 演示Java調用web。下面一個第三方自定義webView控件。
第一版資源文件demo.html:(Js看不懂,可以看完下面的描述再看)
Acitivity中:通過上面的Native按鈕發消息給H5:
Activity初始化JsBridge:
setContentView(R.layout.activity_main); webView = (BridgeWebView) findViewById(R.id.webView); webView.loadUrl("file:///android_asset/demo.html");只需要找到加載H5資源即可。Native點擊事件如下:
@Override public void onClick(View v) { webView.callHandler("functionInJs", "傳遞消息給H5", new CallBackFunction() { @Override public void onCallBack(String data) { } }); }H5如何能接收呢?如上注冊了一個functionInJs,那麼應該在H5中對應的寫法。
說到這,必須先說說
H5初始化JsBridge:
H5初始化JsBridge第一步:
connectWebViewJavascriptBridge(function(bridge) { bridge.init(function(message, responseCallback) { console.log('JS got a message', message); responseCallback(data); }); })
H5初始化JsBridge第二步:
function connectWebViewJavascriptBridge(callback) { if (window.WebViewJavascriptBridge) { callback(WebViewJavascriptBridge) } else { document.addEventListener( 'WebViewJavascriptBridgeReady' , function() { callback(WebViewJavascriptBridge) }, false ); } }知道在哪初始化了,那麼我就在[H5初始化JsBridge第一步]裡面注冊H5後如下:
connectWebViewJavascriptBridge(function(bridge) { bridge.init(function(message, responseCallback) { console.log('JS got a message', message); responseCallback(data); }); bridge.registerHandler("functionInJs", function(data, responseCallback) { document.getElementById("show").innerHTML = ("Native發來的消息是:" + data); var responseData = "Javascript Says Right back aka!"; responseCallback(responseData); }); })加上這一段代碼就對應注冊了functionInJs。
看看動圖效果圖:
第二版資源文件demo.html:
既然是H5調用Native:先看Js的點擊事件代碼:
function go(){ window.WebViewJavascriptBridge.callHandler( "Android", "Hello~", function(responseData){ document.getElementById('a').innerHTML = 'Native給我的數據: ' + responseData; } ); }三個參數分別是:第一個參數:注冊了一個Android。第二個參數:發送的消息內容是Hello~。第三個參數是一個回調。調用成功後,由Native返回responseData。
然後Native對應注冊Android:
webView.registerHandler("Android", new BridgeHandler() { @Override public void handler(String s, CallBackFunction callBackFunction) { Toast.makeText(MainActivity.this, "H5給我的數據:" + s, Toast.LENGTH_SHORT).show(); callBackFunction.onCallBack("fuck!"); } });這樣子,對應注冊完畢。
看個動圖效果圖:點擊1被點擊後,先彈出Native的Toast,然後回調了H5的內容文本。
正常來說,講到這兒,應該是講完了。但是這個第三方還自帶懶人功能:Native調用H5:不注冊參數。按照我們之前的例子來說就是不設置第一個參數functionInJs。反之,H5調用Native:不注冊參數也可以調用默認的Native功能。
寫一個類繼承默認處理類DefaultHandler
class MDefaultHandler extends DefaultHandler{ @Override public void handler(String data, CallBackFunction function) { super.handler(data, function); Log.d(TAG,data); Toast.makeText(MainActivity.this,data,Toast.LENGTH_SHORT).show(); } }
webView.setDefaultHandler(new MDefaultHandler());Js調用的時候如何調用?
直接上demo.html:
window.WebViewJavascriptBridge.send( "被傳遞的Data" , function(responseData) { document.getElementById("a").innerHTML = "H5默認調用Native" + responseData } );改變:只有兩個參數了。方法名變成了send。
看看Js初始化第一步:
connectWebViewJavascriptBridge(function(bridge) { bridge.init(function(message, responseCallback) { console.log('JS got a message', message); responseCallback(data); }); })
Native發送默認消息方式非常簡單:點擊事件裡面調用一下即可:
@Override public void onClick(View v) { webView.send("hello來自Native的默認消息"); }為了方便驗證:將Js初始化第一步改成如下:
connectWebViewJavascriptBridge(function(bridge) { bridge.init(function(message, responseCallback) { document.getElementById("a").innerHTML = "來自Native的:" + message; responseCallback(data); }); })也就是在id等於a的文本處展示。
動圖效果圖如下:
Over~打算再寫一章關於JsBridge的原理,看看我能不能讀懂大神的源碼吧。
首先,讓我們先看下實現的截圖:當有錄音文件存在時,會顯示在下面的ListView當中。下面給出實現的完整代碼:1.主程序代碼package irdc.ex07_11;im
MainActivity如下:package cc.textview5; import android.os.Bundle; import android.text.Te
上一篇文章中我們講解了android中內存對象的序列化方式。由於android開發涉及到不同Activity的數據傳遞,對於基本數據類型數據的傳遞是沒有問題的,但是一旦涉
先看下效果 1.首頁package com.yskj.jh.demopopupwindow;import android.content.Context;import a
目前Android平台上進行人臉特征識別非常火爆,本人研究生期間一直從事