Android进程间通信


以前学习的时候在eclipse上使用过AIDL,最近想学习下PackageManager,就先对AIDL复习下。网上很多都是在同一个进程中的例子,这次是在Android Studio上进行开发的,而且久了忘了比较多,觉得还是自己整理一份出来,下次再用的时候不用太折腾。

一、创建服务端

服务端目录结构:


1. 创建main/aidl/com.scott.IPerson.aidl文件。创建之后clean Project就可以在下图目录中看到系统自动生成的IPerson接口文件。若未生成,可以检查Iperson.aidl文件的包名是否和目录结构的一致。


2.  创建main/java/com.scott.server.AIDLService文件。

public classAIDLService extendsService {
   
private static final StringTAG ="AIDLService";
   
IPerson.Stub stub= new IPerson.Stub() {
       
@Override
     
  public Stringgreet(Stringsomeone)throws RemoteException {
           
Log.i(TAG,"greet()called");
           
return "hello, " + someone;
       
}
   
};
   
@Override
   
public IBinderonBind(Intent intent) {
       
Log.i(TAG,"onBind()called");
       
return stub;
   
}
   
@Override
   
public boolean onUnbind(Intent intent) {
       
Log.i(TAG,"onUnbind()called");
       
return true;
    }
   
@Override
   
public void onDestroy() {
       
super.onDestroy();
       
Log.i(TAG,"onDestroy() called");
   
}
}

3.在AndroidManifest.xml中配置AIDLService。

<service android:name=".AIDLService">
    <intent-filter>
        <action android:name="android.intent.action.AIDLService" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</service>

 

二、创建客户端。

客户端目录结构:


1.      将/aidl/com.scott.IPerson.aidl整个目录结构复制到客户端的src/main/文件夹下,之后clean Project。你也可以自己手动创建/aidl/com.scott/目录结构,但必须注意该目录结构必须与服务端的目录结构相同,否则是连接不上的。这样就保证了服务端和客户端具有一致的协议了。

2.      在Activity中绑定&解绑服务AIDLServer。

public class ClientMainActivity extends AppCompatActivity {
    private Button bindBtn;
    private Button greetBtn;
    private Button unbindBtn;
    private IPerson person;
    private ServiceConnection conn = new ServiceConnection() {
        @Override
        public void onServiceConnected(ComponentName name, IBinder service) {
            Log.i("ServiceConnection", "onServiceConnected() called");
            person = IPerson.Stub.asInterface(service);
        }
        @Override
        public void onServiceDisconnected(ComponentName name) {
            //This is called when the connection with the service has been unexpectedly disconnected,
            //that is, its process crashed. Because it is running in our same process, we should never see this happen.
            Log.i("ServiceConnection", "onServiceDisconnected() called");
        }
    };

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_client_main);

        bindBtn = (Button) findViewById(R.id.bindBtn);
        bindBtn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent intent = new Intent("android.intent.action.AIDLService");
                intent.setPackage("com.scott.server");//Android5.0+要求隐式启动Service必须设置Package
                bindService(intent, conn, Context.BIND_AUTO_CREATE);
                bindBtn.setEnabled(false);
                greetBtn.setEnabled(true);
                unbindBtn.setEnabled(true);
            }
        });

        greetBtn = (Button) findViewById(R.id.greetBtn);
        greetBtn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                try {
                    String retVal = person.greet("scott");
                    Toast.makeText(ClientMainActivity.this, retVal, Toast.LENGTH_SHORT).show();
                } catch (RemoteException e) {
                    Toast.makeText(ClientMainActivity.this, "error", Toast.LENGTH_SHORT).show();
                }
            }
        });

        unbindBtn = (Button) findViewById(R.id.unbindBtn);
        unbindBtn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                unbindService(conn);
                bindBtn.setEnabled(true);
                greetBtn.setEnabled(false);
                unbindBtn.setEnabled(false);
            }
        });
    }
}

layout文件比较简单,就不上代码了。

Android手机是不允许Android两个包名一样的App的,所以本例中中Server的packageName为com.scott.server,Client的packageName为com.scott.client。但服务端和客户端aidl文件的文件路径必须一致。

本文主要代码还是参考http://blog.csdn.net/liuhe688/article/details/6400385,只是根据自己的理解方式进行一定整理。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值