Android跨程序通訊AIDL詳解(附原始碼)
概述
AIDL:Android Interface Definition Language,即Android介面定義語言,記住,它是一門語言,設計它的目的就是為了實現跨程序通訊,我們知道Android的每一個程序都執行在獨立的記憶體中,程序之間程式碼是不能愉快的呼叫的,但是在我們開發中難免會有一些場景是需要實時進行程序間方法呼叫和資料傳遞。
AIDL支援的資料型別
JAVA的基本資料型別(byte、short、int、long、float、double、boolean、char)
String和Charsequence
List,只支援ArrayList,其中的物件必須序列化
Map、只支援HashMap,其中物件必須序列化
實現android.os.Parcelable 介面的物件
AIDL自動生成的介面
AIDL實現步驟
第一步:建立工程
由於AIDL是程序間通訊,所以先要定義兩個工程,我們定義為:
客戶端:AIDLClientDmeo
服務端:AIDLServerDmeo (服務端需要實現Service服務)
建立工程很簡單,這裡忽略這個過程;
第二步:定義AIDL介面
通過Android Studio建立一個以.aidl結尾的檔案,為了實現2個程序能相互呼叫,定義2個aidl:IFirstAidlInterface.aidl和ICallbackInterface.aidl
package com.ailian.study;
interface IServerListener {
void backByServer(String param);
}
package com.ailian.study;
import com.ailian.study.IServerListener;//注意這邊需要手動引入
interface IFirstAidlInterface {
void callServer(String type,IServerListener callback);
}
定義AIDL介面注意點:
- AIDL介面在相互通訊的兩個程序都要定義,而且檔案路徑和檔名都需要一致,這一點很重要,否則將無法進行通訊;
第三步:編譯
在定義完AIDL介面後,需要先編譯工程,因為在編譯後IDE會自動為我們在app/build/generated/source/aidl/debug/目錄生成同名的JAVA檔案,不需要關注這個檔案是如何生成的,自動生成的檔案是readOnly的不可以修改,我們這裡不解釋裡面生成的內容;
第四步:AIDLServerDmeo實現Service
上面步驟中我們已經在2個工程中都定義好了AIDL介面,現在可以在Server端實現Service,並暴露出來讓其他程序bind;
package com.ailian.study.aidlserverdemo;
import android.app.Service;
import android.content.Intent;
import android.os.IBinder;
/**
* Created by ailian on 2018/6/9/009.
*/
public class AidlService extends Service {
private AidlServiceSub mServiceStub;
@Override
public void onCreate() {
super.onCreate();
mServiceStub = new AidlServiceSub();
}
@Override
public IBinder onBind(Intent intent) {
/**
* 這裡會返回一個binder物件,在Client獲取到這個物件
*/
return mServiceStub;
}
@Override
public boolean onUnbind(Intent intent) {
return super.onUnbind(intent);
}
}
onBind方法中有個返回值IBinder物件,Client通過bindService通過介面可以獲取到這個IBinder物件,AidlServiceSub需要繼承IFirstAidlInterface自動生成的IFirstAidlInterface.Stub物件:
package com.ailian.study.aidlserverdemo;
import android.os.RemoteException;
import android.util.Log;
import com.ailian.study.IFirstAidlInterface;
import com.ailian.study.IServerListener;
/**
* Created by ailian on 2018/6/9/330.
*/
public class AidlServiceSub extends IFirstAidlInterface.Stub {
@Override
public void callServer(String type, IServerListener callback) throws RemoteException {
Log.d("AidlServiceSub", "Client發過來的資訊:" + type);
callback.backByServer("黃河黃河,我也是黃河");
}
}
第五步:AIDLServerDmeo實現Service
在AIDLServerDemo的AndroidManifest.xml中宣告第四步建立的Service
android:exported=”true” //執行其他APP啟動
android:process=”:remote”//執行在單獨的程序
//需要自定義一個action其他程序啟動該服務就通過這個aciton:
<service
android:name=".AidlService"
android:exported="true"
android:process=":remote">
<intent-filter>
<action android:name="android.ailian.aidl.test" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</service>
第六步:AIDLClientDmeo啟動Service
上面的五步後,Client端就可以通過bindService與Server端建立通訊通道了:
Intent it = new Intent();
it.setAction("android.ailian.aidl.test");
it.setPackage("com.ailian.study.aidlserverdemo");
bindService(it, mserviceConnection, BIND_AUTO_CREATE);
這裡有個mserviceConnection,是呼叫bindService的一個回撥
ServiceConnection mserviceConnection = new ServiceConnection() {
@Override
public void onServiceDisconnected(ComponentName name) {
/**
* 繫結失敗的回撥
*/
bindServiceTip.setText("服務繫結失敗,請重新繫結");
clientContent.setText("");
}
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
/**
* 繫結成功的回撥,這裡獲取到了IBinder物件,我們就是通過這個IBinder實現與Server進行通訊
*/
bindServiceTip.setText("服務繫結成功,可以通訊了");
clientContent.setText("");
executeService = IFirstAidlInterface.Stub.asInterface(service);
}
};
搞定啦,我們來測試一下吧
驗證結果
我們將2個APP同時安裝在同一臺手機中
通過手機直接測試,測試成功可以相互通訊;
沒有原始碼的步驟講解都是耍流氓
附上原始碼下載地址,希望對您有所幫助: