AIDL使用以及回调接口的实现

 

 

 


前言

因项目需求,需要提供跨进程接口给第三方应用使用,特对此进行一个小的总结,希望对大家有一定的帮助
 

 

一、AIDL是什么?

AIDL是一个缩写,全称是Android Interface Definition Language,也就是Android接口定义语言,是跨进程通讯的一种方式。

二、使用步骤

1.服务端创建

在main目录下创建aidl文件夹, 创建包com.xxx.xxx, 创建xx.aidl文件,定义需要的接口,因为需要服务端请求异步数据,所以需要定义个回调接口和数据类bean。

1.1 IDataProvide.aidl 创建

package com.xxx.xxx.aidl;

import com..xxx.xxx.aidl.InPackageInfo;
import com..xxx.xxx.aidl.InTaskCallback;
interface IDataProvider {
   void getPackages(String packageName);
   void registerCallback(InTaskCallback callback); //注册接口
   void unregisterCallBack();//移除接口
}

1.2 InPackageInfo 数据类

package com.xxx.xxx.aidl;

import android.os.Parcel;
import android.os.Parcelable;

public class InPackageInfo implements Parcelable {

    private String status = "";
    private String startDate = "";

    public InPackageInfo (String s, String date){
        super();
        status = s;
        startDate = date;
    }

    protected InPackageInfo(Parcel in) {
        status = in.readString();
        startDate = in.readString();
    }

    public String getStatus() {
        return status;
    }

    public void setStatus(String status) {
        this.status = status;
    }

    public String getStartDate() {
        return startDate;
    }

    public void setStartDate(String startDate) {
        this.startDate = startDate;
    }

    public static final Creator<InPackageInfo> CREATOR = new Creator<InPackageInfo>() {
        @Override
        public InPackageInfo createFromParcel(Parcel in) {
            return new InPackageInfo(in);
        }

        @Override
        public InPackageInfo[] newArray(int size) {
            return new InPackageInfo[size];
        }
    };

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel parcel, int i) {
        parcel.writeString(status);
        parcel.writeString(startDate);
    }
}

1.3  InPackageInfo.aidl 创建

package com.indibox.tv.aidl;

parcelable InPackageInfo;

1.4 InTaskCallback.aidl 回调创建

package com.xxx.xxx.aidl;

import com.indibox.tv.aidl.InPackageInfo;

interface InTaskCallback {
   void getPackages(inout List<InPackageInfo> packageName);
}

1.5 创建服务类 DataProviderService,

package com.xxx.xxx.aidl;

import android.app.Service;
import android.content.Intent;
import android.os.IBinder;

public class DataProviderService extends Service {

   private DataProvider mDataProvider = new DataProvider();

   public DataProviderService(){

   }

   @Override
   public IBinder onBind(Intent intent) {
      return mDataProvider;
   }

public class DataProvider extends IDataProvider.Stub {
   
   private static final String TAG = "DataProvider";
 
   @Override
   public void getPackages(String packageName) throws RemoteException {
  
      DataPackagesUtils.getInstance().getPackages(packageName);
   }

   @Override
   public void registerCallback(InTaskCallback callback) throws RemoteException {
      DataPackagesUtils.getInstance().setTaskCallback(callback);
   }

   @Override
   public void unregisterCallBack() throws RemoteException {
      DataPackagesUtils.getInstance().setTaskCallback(null);
   }
}}

注:记得要在AndroidManifest.xml 文件注册DataProviderService,设置action(启动服务的标识)

至此,服务端的准备工作已经完成了,接下来实现客户端。

 

2.客户端实现

2.1 为了确保不出错,建议直接把服务端的aidl文件夹拷贝

2.2 客户端调用

 

package com.xxx.aidldemo;

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.util.Log;

import com.xxx.xxx.aidl.IDataProvider;
import com.xxx.xxx.aidl.InPackageInfo;
import com.xxx.xxx.aidl.InTaskCallback;

import java.util.List;


public class XMAIDLManager {

    private Context mContext;
    private IDataProvider mDataProvider;
    private OnConnectionListener mListener;

    public XMAIDLManager(Context context, OnConnectionListener listener) {
        mContext = context;
        mListener = listener;
    }

    private ServiceConnection connection = new ServiceConnection() {
        @Override
        public void onServiceConnected(ComponentName name, final IBinder service) {
            Log.d("AIDL", "onServiceConnected");
            mDataProvider = IDataProvider.Stub.asInterface(service);
            try {
                mDataProvider.registerCallback(new TaskCallback()); //设置回调
                mDataProvider.getPackages("inditvpackage"); //启动请求
            } catch (RemoteException e) {
                e.printStackTrace();
            }
        }

        @Override
        public void onServiceDisconnected(ComponentName name) {
            mDataProvider = null;
        }
    };

    class TaskCallback extends InTaskCallback.Stub {

        @Override
        public void getPackages(List<InPackageInfo> packageName) throws RemoteException {
            Log.d("TaskCallback", "getPackages");
            //服务端异步请求数据回调接口
        }
    }

    public void startService() {
        //启动服务
        Intent intent = new Intent();
        intent.setAction("你的action");
        intent.setPackage("包名");
        mContext.bindService(intent, connection, Context.BIND_AUTO_CREATE);
    }

    public void stopService() {
        try {
            mDataProvider.unregisterCallBack();
            mContext.unbindService(connection);
        } catch (RemoteException e) {
            e.printStackTrace();
        }
    }

    public interface OnConnectionListener {
        void onConnection(List<InPackageInfo> packageInfos);
    }
}

到此AIDL的跨进程的服务端和客户端就实现了,可以进行数据类bean(可自定义)的传递以及服务端异步回调数据给客户端。


总结

使用过程中主要是数据类型的传递,如果是基本的数据类型可以直接传递,当传递特定对象时需要对这个对应对象进行Parcelable 序列化操作,对应记得传对象参数是,需要标识 in /out/ inout,否则编译会出错。整体AIDL使用还是比较方便的,希望此文章会对大家有帮助。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值