在上一篇文章Android IPC机制(二)用Messenger进行进程间通信中我们介绍了使用Messenger来进行进程间通信的方法。可是我们能发现Messenger是以串行的方式来处理client发来的信息,假设有大量的消息发到服务端,服务端仍然一个一个的处理再响应client显然是不合适的。另外,Messenger用来进程间进行数据传递可是却不能满足跨进程的方法调用。接下来我们来使用AIDL来实现跨进程方法调用,此前我们都是用Eclipse来实现的,这次我们看看在Android Studio中使用AIDL有什么不同。

1. 创建AIDL文件

我们将项目的文件夹结构调为Android模式,在java同级文件夹创建aidl文件夹,在文件夹中创建一个包名和应用包名一致的包

我们先创建一个IGameManager.aidl的文件。这里面有两个方法各自是addGame和getGameList。(IGameManager.aidl)

package com.example.liuwangshu.moonaidl;
import com.example.liuwangshu.moonaidl.Game;
interface IGameManager {
List<Game>getGameList();
void addGame(in Game game);
}

在AIDL文件里支持的数据类型包含:

  • 基本数据类型
  • String和CharSequence
  • List:仅仅支持ArrayList,里面的元素都必须被AIDL支持
  • Map:仅仅支持HashMap,里面的元素必须被AIDL 支持
  • 实现Parcelable接口的对象
  • 全部AIDL接口

在IGameManager.aidl中我们用到了Game这个类,这个类实现了Parcelable,在AIDL 文件里我们要import 进来。来看看Game类。

(Game.java)

package com.example.liuwangshu.moonaidl;
import android.os.Parcel;
import android.os.Parcelable;
public class Game implements Parcelable {
public String gameName;
public String gameDescribe;
public Game(String gameName,String gameDescribe){
this.gameName=gameName;
this.gameDescribe=gameDescribe;
} protected Game(Parcel in) {
gameName=in.readString();
gameDescribe=in.readString();
} public static final Creator<Game> CREATOR = new Creator<Game>() {
@Override
public Game createFromParcel(Parcel in) {
return new Game(in);
} @Override
public Game[] newArray(int size) {
return new Game[size];
}
}; @Override
public int describeContents() {
return 0;
} @Override
public void writeToParcel(Parcel dest, int flags) {
dest.writeString(gameName);
dest.writeString(gameDescribe);
}
}

在这里不去讲怎么去实现Parcelable 接口,在上面的IGameManager.aidl文件里我们用到了Game这个类,所以我们也要创建Game.aidl,来申明Game实现了parcelable 接口。(Game.aidl)

package com.example.liuwangshu.moonaidl;
parcelable Game;

这个时候我们又一次编译程序,工程就会自己主动生成IGameManager.aidl相应的接口文件,这个文件生成的位置和Eclipse的位置不同。我们将项目的文件夹结构调整为project模式,在app–>build–>generated–>soure–>aidl–>debug文件夹下我们找到自己的包名文件,在文件里有一个接口文件IGameManager。

IGameManager接口文件的代码这里就不说了,有兴趣的能够下载本项目的源代码去了解下。

2. 创建服务端

服务端我们在onCreate方法中创建了两个游戏的信息并创建Binder对象实现了AIDL的接口文件里的方法。并在onBind方法中将Binder对象返回。(AIDLService.java)

package com.example.liuwangshu.moonaidl;
import android.app.Service;
import android.content.Intent;
import android.os.Binder;
import android.os.IBinder;
import android.os.RemoteException;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
public class AIDLService extends Service{
private CopyOnWriteArrayList<Game> mGameList=new CopyOnWriteArrayList<Game>();
private Binder mBinder= new IGameManager.Stub() {
@Override
public List<Game> getGameList() throws RemoteException {
return mGameList;
} @Override
public void addGame(Game game) throws RemoteException {
mGameList.add(game);
}
}; @Override
public void onCreate() {
super.onCreate();
mGameList.add(new Game("九阴真经ol", "最好玩的武侠网游"));
mGameList.add(new Game("大航海时代ol","最好玩的航海网游")); }
@Override
public IBinder onBind(Intent intent) {
return mBinder;
}
}

当然我们不要忘了这个服务端应该执行在还有一个进程,在AndroidManifest.xml文件里配置service:

  <service android:name=".AIDLService" android:process=":remote"></service>

3. client调用

最后我们在clientonCreate方法中调用bindService方法绑定远程服务端。绑定成功后将返回的Binder对象转换为AIDL接口,这样我们就能够通过这个接口来调用远程服务端的方法了。(AIDLActivity.java)

package com.example.liuwangshu.moonaidl;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.IBinder;
import android.os.RemoteException;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import java.util.List;
public class AIDLActivity extends AppCompatActivity {
private final static String TAG="AIDLActivity";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_aidl);
Intent mIntent=new Intent(AIDLActivity.this,AIDLService.class);
bindService(mIntent,mServiceConnection, Context.BIND_AUTO_CREATE);
} private ServiceConnection mServiceConnection=new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
IGameManager iGameManager=IGameManager.Stub.asInterface(service);
Game game=new Game("月影传说","最好玩的武侠单机游戏");
try {
iGameManager.addGame(game);
List<Game> mList=iGameManager.getGameList();
for(int i=0;i<mList.size();i++){
Game mGame=mList.get(i);
Log.i(TAG,mGame.gameName+"---"+mGame.gameDescribe);
}
} catch (RemoteException e) {
e.printStackTrace();
}
} @Override
public void onServiceDisconnected(ComponentName name) { }
};
@Override
protected void onDestroy() {
super.onDestroy();
unbindService(mServiceConnection); }
}

绑定成功后我们创建了一个新的Game然后调用远程服务端的addGame方法将新游戏加入进去,然后调用循环将远端服务中的全部的游戏在打印出来。我们执行程序

打印出了远程服务端的全部的游戏,这样我们就成功的在client通过AIDL来调用远程服务端的方法了。

github源代码下载

Android IPC机制(三)在Android Studio中使用AIDL实现跨进程方法调用的更多相关文章

  1. Android IPC机制(三)使用AIDL实现跨进程方法调用

    上一篇文章中我们介绍了使用Messenger来进行进程间通信的方法,但是我们能发现Messenger是以串行的方式来处理客户端发来的信息,如果有大量的消息发到服务端,服务端仍然一个一个的处理再响应客户 ...

  2. Android中使用ContentProvider进行跨进程方法调用

    原文同一时候发表在我的博客 点我进入还能看到很多其它 需求背景 近期接到这样一个需求,须要和别的 App 进行联动交互,比方下载器 App 和桌面 App 进行联动.桌面的 App 能直接显示下载器 ...

  3. 【起航计划 037】2015 起航计划 Android APIDemo的魔鬼步伐 36 App->Service->Remote Service Binding AIDL实现不同进程间调用服务接口 kill 进程

    本例和下个例子Remote Service Controller 涉及到的文件有RemoteService.java ,IRemoteService.aidl, IRemoteServiceCallb ...

  4. Android IPC机制—Binder的工作机制

    进程和线程的关系 IPC机制即为跨进程通信,是inter-Process Communication的缩写.是指两个进程之间进行通信.在说进程通信之前,我们的弄明白什么是线程,什么是进程.进程和线程是 ...

  5. Android四大组件应用系列5——使用AIDL实现跨进程调用Service

    一.问题描述 Android应用程序的四大组件中Activity.BroadcastReceiver.ContentProvider.Service都可以进行跨进程.在上一篇我们通过ContentPr ...

  6. Wayland中的跨进程过程调用浅析

    原文地址:http://blog.csdn.net/jinzhuojun/article/details/40264449 Wayland协议主要提供了Client端应用与Server端Composi ...

  7. Android IPC机制全解析<一>

    概要 多进程概念及多进程常见注意事项 IPC基础:Android序列化和Binder 跨进程常见的几种通信方式:Bundle通过Intent传递数据,文件共享,ContentProvider,基于Bi ...

  8. Android IPC机制基础

    概要 多进程概念及多进程常见注意事项 IPC基础:Android序列化和Binder 跨进程常见的几种通信方式:Bundle通过Intent传递数据,文件共享,ContentProvider,基于Bi ...

  9. android IPC 机制 (开发艺术探索)

    一.IPC 机制介绍 IPC是Inter-Process Communication的缩写,含义就是进程间通信或者跨进程通信,是指两个进程之间进行数据交换的过程.那么什么是进程,什么是线程,进程和线程 ...

随机推荐

  1. MongoDB学习笔记(二)--Capped集合 && GridFS存储文件

    Capped集合                                                            Capped集合的大小是固定的,如果空间都被用完了,新添加的对象 ...

  2. 《House of Cards》观后感

    <House of Cards>,首先我得说好看,36个赞,比我以前看的那些美剧都要好看,虽然我是个屌丝程序员,但是我还是希望我自己看书不只看专业的书那种,虽然我是个屌丝程序员,工科男,所 ...

  3. Ext 弹出窗体显示到iframe之外

    主要是这句话 var _win = new top.Ext.Window({});即可完成需要功能 var _win = new top.Ext.Window({           title: ' ...

  4. centos+apache+mod_ssl

    参考网站:配置Apache建立openssl证书实现SSL访问:http://blog.51yip.com/apachenginx/958.html用ca工具生成证书的方法:http://hi.bai ...

  5. IOS学习笔记44--ASIRequestHttp之BUG(一)

    其实这也是无意间看到的,大家看看是不是这么回事 BUG:当下载线程数超过2时,就会影响到主线程响应用户请求的速度了 看ASIRequestHttp.m--requestFinished代码 - (vo ...

  6. more命令(转)

    原文:http://www.cnblogs.com/peida/archive/2012/11/02/2750588.html more命令,功能类似 cat ,cat命令是整个文件的内容从上到下显示 ...

  7. Servlet一(web基础学习笔记二十)

    一.Servlet简介 Servlet是sun公司提供的一门用于开发动态web资源的技术. Sun公司在其API中提供了一个servlet接口,用户若想用发一个动态web资源(即开发一个Java程序向 ...

  8. 微信小程序-开发入门(一)

    微信小程序已经火了一段时间了,之前一直也在关注,就这半年的发展来看,相对原生APP大部分公司还是不愿意将主营业务放到微信平台上,以免受制于腾讯,不过就小程序的应用场景(用完即走和二维码分发等)还是很值 ...

  9. java—(2)maven基本命令

    均在含pom.xml文件的路径下执行 maven命令执行是按阶段执行的.如执行mvn package.则实际上已经执行了例如以下命令: watermark/2/text/aHR0cDovL2Jsb2c ...

  10. nginx高性能webserver具体解释(1)--安装nginx

    1. 下载 本次使用nginx-0.1.2.3 版本号,下载地址 http://nginx.org/en/download.html  新公布版本号 http://nginx.org/download ...