Android进程间通信AIDL

AIDL

AIDL:Android interface define language,用与实现Android应用之间的通信。

1.服务端


Android进程之间不能共享内存,进城之间要进行通信(IPC)就要使用AIDL。

在服务端的manifest0.xml文件中添加service

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.aidl.server"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="8"
        android:targetSdkVersion="18" />

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
        <service android:name="RemoteService">
            <intent-filter >
                <action android:name="com.example.aidl.webpage"/>
            </intent-filter>
        </service>
    </application>

</manifest>
    可以看到服务端的包名为:com.braincol.aidl.server,且该服务端只需一个service组件提供AIDL服务,service组件的名称为RemoteService,这是待会要实现的Service子类。其中<action android:name="com.braincol.aidl.remote.webpage"/> 指定了action名称为"com.braincol.aidl.remote.webpage", 客户端会通过该action的名称来找到并连接该服务端。

1.2创建AIDL文件

    在包com.example.aidl.server;中创建AIDL文件,eclipse会自动在/gen目录下对应的包中生成对应的RemoteWebpage.java文件

package com.example.aidl.server;
interface RemoteWebpage{
  String getCurrentPageUrl() ;
}


1.3编写Java实现

    编写Java实现RemoteService.Java继承RemoteWebpage中的内部类Stub,实现在AIDL文件中声明的方法getCurrentPageUrl()。

package com.example.aidl.server;

import android.app.Service;
import android.content.Intent;
import android.os.IBinder;
import android.os.RemoteException;
import android.util.Log;

public class RemoteService extends Service {
	private final static String TAG = "RemoteService" ;
	@Override
	public IBinder onBind(Intent intent) {
		// TODO Auto-generated method stub
		Log.i(TAG, "onBind") ;
		return new MyBinder();
	}
	private class MyBinder extends RemoteWebpage.Stub
	{

		@Override
		public String getCurrentPageUrl() throws RemoteException {
			// TODO Auto-generated method stub
			return "www.baidu.com";
		}
		
	}
}

总结

     1. 创建.aidl文件:

        该文件(YourInterface.aidl)定义了客户端可用的方法和数据的接口

     2. 实现这个接口:

        Android SDK将会根据你的.aidl文件产生AIDL接口。生成的接口包含一个名为Stub的抽象内部类,该类声明了所有.aidl中描述的方法,你必须在代码里继承该Stub类并且实 现.aidl中定义的方法。

     3.向客户端公开服务端的接口:

        实现一个Service,并且在onBinder方法中返回第2步中实现的那个Stub类的子类(实现类)。


2.客户端

2.1拷贝AIDL文件

    将服务端的AIDL文件拷贝到客户端下相同的位置,相同的位置意味着包名AIDL文件名都要相同:com.example.aidl.server.RemoteWebpage.aidl。

2.2建立连接

    继承ServiceConnection,重写onServiceConnected(ComponentName name, IBinder service),onServiceDisconnected(ComponentName name)函数建立与服务端的连接。

package com.example.aidl.client;

import com.example.aidl.server.RemoteWebpage;

import android.support.v7.app.ActionBarActivity;
import android.content.ComponentName;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import android.os.RemoteException;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;


public class MainActivity extends ActionBarActivity implements OnClickListener{
	private final static String TAG = "AIDLClient" ;
	private Button btn_bind =null , btn_getinfo = null ;
	private TextView tv = null ;
	private RemoteWebpage remoteWebpage = null ; 
	private String actionName = "com.example.remote.webpage" ;
	private String urlInfo = null ;
	private Boolean isBind = false ;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        btn_bind = (Button) findViewById(R.id.btu_bind) ;
        btn_getinfo = (Button) findViewById(R.id.btu_getinfo) ;
        tv = (TextView) findViewById(R.id.text) ;
        btn_bind.setOnClickListener(this) ;
        btn_getinfo.setOnClickListener(this) ;
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.main, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle action bar item clicks here. The action bar will
        // automatically handle clicks on the Home/Up button, so long
        // as you specify a parent activity in AndroidManifest.xml.
        int id = item.getItemId();
        if (id == R.id.action_settings) {
            return true;
        }
        return super.onOptionsItemSelected(item);
    }
    private class MyServiceConnect implements ServiceConnection
    {

		@Override
		public void onServiceConnected(ComponentName name, IBinder service) {
			// TODO Auto-generated method stub
			Log.i(TAG, "connection.......") ;
			remoteWebpage = RemoteWebpage.Stub.asInterface(service) ;
			if(remoteWebpage == null )
			{
				tv.setText("connection failed!!") ;
				return ;
			}
			else
			{
				isBind = true ;
				btn_bind.setText("断开") ;
				tv.setText("connected") ;
				try {
					urlInfo = remoteWebpage.getCurrentPageUrl() ;
					System.out.println(urlInfo);
				} catch (RemoteException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
				btn_getinfo.setEnabled(true) ;
			}
		}

		@Override
		public void onServiceDisconnected(ComponentName name) {
			// TODO Auto-generated method stub
			Log.i(TAG, "service is disconnected") ;
		}
    	
    }
    MyServiceConnect conn = new MyServiceConnect() ;
	@Override
	public void onClick(View v) {
		// TODO Auto-generated method stub
		switch (v.getId()) {
		case R.id.btu_bind:
			if(!isBind)
			{
				Intent intent = new Intent(actionName) ;
				bindService(intent, conn, BIND_AUTO_CREATE) ;
			}
			else
			{
				Log.i(TAG, "disconnect") ;
				unbindService(conn) ;
				btn_getinfo.setEnabled(false) ;
				btn_bind.setText("连接") ;
				isBind = false ;
				tv.setText("disconnected") ;
			}
			break;
		case R.id.btu_getinfo :
			tv.setText(urlInfo) ;
 		default:
			break;
		}
	}
}

    先运行服务端然后运行客户端,客户端就可以获取服务端的信息。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值