一个应用需要与另外一个通讯,实现方法有很多,android 简单记录下实现
1.为什么要使用Binder?
性能方面更加高效。Binder数据拷贝只需要一次,而管道、消息队列、Socket都需要2次,共享内存方式一次内存拷贝都不需要,但实现方式比较复杂。安全方面,Binder机制从协议本身就支持对通信双方做身份校检,因而大大提升了安全性。
2.为什么需要AIDL?
使用简单。客户端和服务端进行通讯,若直接使用Binder需先将请求转换成序列化的数据,然后调用transact()函数发送给服务端,并且控制参数顺序,服务端和客户端都必须一致,否则就会出错。这样的过程很麻烦,如果有上百个接口,并且都需要手动编写传输接口,那可就很麻烦了。AIDL调用服务端方法如调用自身方法一样简单快捷烦。
1、server:右键新建一个AIDl 文件 ,随便定义2个方法,方法定义完毕Build一下生成 IXmInterface.Stub
2.server:创建Server,并返回IBinder!!如果 xxx.Stub() 无法引入,你可能是没有Rebuild
public class XmServer extends Service {
@Nullable
@Override
public IBinder onBind(Intent intent) {
//2.返回实现操作类
return iBinder;
}
//1.创建IXmInterface的实现。。
private IBinder iBinder = new IXmInterface.Stub() {
//这里就是你要帮 client端实现的东西
@Override
public String getName() throws RemoteException {
return "aidl name";
}
@Override
public String getVersion() throws RemoteException {
return "v1.0.0";
}
};
}
3.服务端server:配置服务,在单独的进程使用服务,允许外部打开exported=true
<service
android:name=".server.XmServer"
android:exported="true"
android:process=":remote" />
4.client:将服务器的aild拷贝到 客户端里面来,aidl层级跟 Java同层,完事记得ReBuild下
5.client: 绑定并调用,并释放。
//在需要的地方,开启aidl服务
Intent intent = new Intent();
intent.setClassName("com.frank.ffmpeg",
"com.frank.ffmpeg.server.XmServer");
bindService(intent, mConnection, Context.BIND_AUTO_CREATE);
IXmInterface iXmInterface;
boolean isConnected;
private ServiceConnection mConnection = new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
iXmInterface = IXmInterface.Stub.asInterface(service);
try {
isConnected = true;
MLog.e("服务连接成功:服务名称" + iXmInterface.getName() + ",服务版本:" + iXmInterface.getVersion());
} catch (RemoteException e) {
e.printStackTrace();
}
}
@Override
public void onServiceDisconnected(ComponentName name) {
isConnected = false;
iXmInterface = null;
MLog.e("绑定结束");
}
};
@Override
protected void onDestroy() {
super.onDestroy();
if (isConnected) {
unbindService(mConnection);
}
}
ps:在targetSdkVersion>=30的时候可能出现绑定不成功,需要在Manifest添加该标签,预指我需要跟谁进行交互
<queries>
<package android:name="com.frank.ffmpeg" />
<!--如果有多个的话就添加多个标签-->
<package android:name="com.tencent.mm" />
</queries>