Webview 形式的控件是實(shí)現(xiàn) Hybrid App 的唯一途徑邻梆,android 4.4 以后的 webview 簡直太好用了澡罚,4.4 以前也能通過集成 chrome 內(nèi)核解決兼容性問題比规。我們項(xiàng)目已經(jīng)把用戶注冊(cè)登錄和用戶反饋全部改成了
Webview 的方式肺孵,并且整個(gè)項(xiàng)目只有一個(gè) Activity 放置了 webview 控件待诅,那要怎么才能滿足多個(gè)業(yè)務(wù)需求了。
眾所周知 webview 里的 js 代碼和 java 代碼相互調(diào)用检碗, 需要把 java 的對(duì)象傳到 javascript,它通過 addJavascriptInterface 的方式添加码邻。所以可以在這個(gè) activity 里動(dòng)態(tài)設(shè)置 java 的對(duì)象后裸,但問題是, intent 傳遞 object 對(duì)象顯得比較麻煩冒滩,于是乎微驶,我用了一個(gè)單例存放需要調(diào)用的 java 對(duì)象。
public enum JsInvoke {
instance;
private HashMap<String, Object> objs;
public JsInvoke clear() {
if (objs == null)
objs = new HashMap<>();
else objs.clear();
return this;
}
public HashMap<String, Object> getObjs() {
return objs;
}
public void add(String key, Object obj) {
if (objs == null) return;
objs.put(key, obj);
}
}
當(dāng)我需要打開一個(gè) web 頁面時(shí)开睡,則通過下列方式傳遞 java 對(duì)象:
JsInvoke.instance.clear().add("time", new Date());
這樣就很方便傳遞對(duì)象了因苹。
接下來就是 js ,每次調(diào)用都會(huì)進(jìn)行一些判斷篇恒,比如:
if (typeof app !== 'undefined' && typeof app.hello !=='undefined'){
app.hello('hello world');
}
這就顯得比較繁瑣了扶檐,由于 java 調(diào)用對(duì)象會(huì)在 window 對(duì)象中注冊(cè),可以考慮從 window 對(duì)象中判斷胁艰,寫一個(gè)原生方法的 js 調(diào)用方法:
function nativeCall(ns, fn, paras) {
if (typeof window[ns] === 'undefined') return null;
if (typeof window[ns] !== 'object') return null;
if (typeof window[ns][fn] === 'undefined') return null;
if (typeof window[ns][fn] !== 'function') return null;
return window[ns][fn](paras);
}
接下來假設(shè) 需要調(diào)用的 java 對(duì)象的類名為 Test款筑,方法名為 demo,參數(shù)為字符串 hello world腾么,則只需要用下列代碼即可:
nativeCall('Test','demo','hello world');
這是無參返回的奈梳,有參返回的聲明一個(gè)變量接收杰克,夠簡單了吧 :)
本文在同步 公眾號(hào) 天兵公園 解虱,簡書同步發(fā)布攘须,如需轉(zhuǎn)載請(qǐng)事先聯(lián)系。