«

Android---45---使用AIDL Service传递复杂数据

时间:2024-3-2 18:12     作者:韩俊     分类: Android




该实例所传输的数据类型是自定义类型。


Android 要求调用远程Service的参数和返回值都需要实现Parcelable接口。


实现Parcelable接口相当于Android提供的一种自定义序列化机制。


实现Parcelable接口不仅要求实现该接口里定义的方法,而且要求在实现类中定义一个名为CREATOR
类型为Parcelable.Creator的静态Filed。除此之外,还要求使用AIDL代码来定义这些自定义类型。



服务端:

自定义两个类型:Person与Pet,其中Person对象作为调用远程Service的参数,而Pet将作为返回值。

Person 和 Pet类都必须实现 Parcelable接口,并在实现类中定义一个名为CREATOR的静态Filed。


要定义Person类,先要AIDL来定义Person类:


parcelable Person;

接下来定义Person实现Parcelable的类


public class Person implements Parcelable {

    private Integer id;
    private String name;
    private String pass;

    public Person() {
        super();
        // TODO Auto-generated constructor stub
    }

    public Person(Integer idInteger, String name, String pass) {
        super();
        this.id = idInteger;
        this.name = name;
        this.pass = pass;
    }

    public Integer getIdInteger() {
        return id;
    }

    public void setIdInteger(Integer idInteger) {
        this.id = idInteger;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getPass() {
        return pass;
    }

    public void setPass(String pass) {
        this.pass = pass;
    }

    @Override
    public int hashCode() {
        // TODO Auto-generated method stub
        final int prime = 31;
        int result = 1;
        result = prime * result + ((name == null) ? 0 : name.hashCode());
        result = prime * result + ((pass == null) ? 0 : pass.hashCode());
        return result;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) {
            return true;
        }
        if (o == null) {
            return false;
        }
        if (getClass() != o.getClass()) {
            return false;
        }
        Person other = (Person) o;
        if (name == null) {
            if (other.name != null) {
                return false;
            }
        } else if (!name.equals(other.name)) {
            return false;
        }

        if (pass == null) {
            if (other.pass != null) {
                return false;
            }
        } else if (!pass.equals(other.pass)) {
            return false;
        }
        return true;
    }

    // 实现Parcelable必须要实现的方法
    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel dest, int flags) {
        // 把该对象所包含的数据写到Parcel
        dest.writeInt(id);
        dest.writeString(name);
        dest.writeString(pass);
    }

    public static final Parcelable.Creator<Person> CREATOR = new Parcelable.Creator<Person>() {

        @Override
        public Person createFromParcel(Parcel source) {
            // 从Parcel中读取数据,返回Person对象
            return new Person(source.readInt(), source.readString(),
                    source.readString());
        }

        @Override
        public Person[] newArray(int size) {
            // TODO Auto-generated method stub
            return new Person[size];
        }
    };

}


然后是Pet类,也是先定义AIDL中的Pet:

parcelable Pet; 



然后是定义Pet类实现Parcelable:


public class Pet implements Parcelable {
    private String name;
    private double weight;

    public Pet(String name, double weight) {
        super();
        this.name = name;
        this.weight = weight;
    }

    public Pet() {
        super();
        // TODO Auto-generated constructor stub
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public double getWeight() {
        return weight;
    }

    public void setWeight(double weight) {
        this.weight = weight;
    }

    @Override
    public int describeContents() {
        // TODO Auto-generated method stub
        return 0;
    }

    @Override
    public String toString() {
        return "Pet [name=" + name + ", weight=" + weight + "]";
    }

    @Override
    public void writeToParcel(Parcel dest, int flags) {
        dest.writeString(name);
        dest.writeDouble(weight);
    }

    // 添加一个静态成员,名为CREATOR,该对象实现了Parcelable.Creator接口
    public static final Parcelable.Creator<Pet> CREATOR = new Parcelable.Creator<Pet>() {

        @Override
        public Pet createFromParcel(Parcel source) {
            // 从Parcel中读取数据,返回Pet对象
            return new Pet(source.readString(), source.readDouble());

        }

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

}


有了Person和Pet自定义的类,接下来就要定义用于通信的接口了:IPet


还是先是AIDL中定义:


package com.example.complexaidlservice;
import com.example.complexaidlservice.Pet;
import com.example.complexaidlservice.Person;
//定义一个Person对象作为传入对象
interface IPet{

    List<Pet> getPets (in Person owner );
}


接下来就是开发Service类了:


public class ComplexService extends Service {

    private PetBinder petBinder;
    private static Map<Person, List<Pet>> pets = new HashMap<Person, List<Pet>>();

    static {
        ArrayList<Pet> list1 = new ArrayList<Pet>();
        list1.add(new Pet("旺财", 4.3));
        list1.add(new Pet("来福", 5.4));
        pets.put(new Person(1, "sun", "sun"), list1);

        ArrayList<Pet> list2 = new ArrayList<Pet>();
        list2.add(new Pet("Kitty", 2.3));
        list2.add(new Pet("garfiled", 3.1));
        pets.put(new Person(2, "bai", "bai"), list2);

    }

    @Override
    public void onCreate() {
        super.onCreate();
        petBinder = new PetBinder();
    }

    @Override
    public IBinder onBind(Intent intent) {
        // TODO Auto-generated method stub
        return petBinder;
    }

    // 继承Stub,也就是实现了IPet接口,并实现了IBinder接口
    public class PetBinder extends Stub {

        @Override
        public List<Pet> getPets(Person owner) throws RemoteException {
            // TODO Auto-generated method stub
            return pets.get(owner);
        }

    }

    @Override
    public void onDestroy() {
    }
}




接下来该写客户端的代码了:

还记得在上一篇中写到的,需要把服务端的AIDL接口复制过来,传递复杂数据的时候,不仅仅只将IPet复制过来
同时也要将 Person.java,Person.aidl Pet.aidl,Pet.java 一起复制到客户端。

还是按照之前绑定远程Service的方式即可,并在ServiceConnection实现类的onServiceConnected方法中
获取远程Service的onBind方法返回的代理对象即可。



public class ComplexClient extends Activity {
    private IPet petService;
    private Button get;
    EditText personView;
    ListView showView;

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

        personView = (EditText) findViewById(R.id.person);
        showView = (ListView) findViewById(R.id.show);
        get = (Button) findViewById(R.id.get);

        Intent intent = new Intent();
        intent.setAction("com.example.complexaidlservice.COMPLEXSERVICE");

        // 绑定远程Service
        bindService(intent, conn, Service.BIND_AUTO_CREATE);
        get.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {

                try {
                    String personName = personView.getText().toString();
                    // 调用远程Service的方法
                    List<Pet> pets = petService.getPets(new Person(1,
                            personName, personName));
                    // 将程序返回的List包装成ArrayAdapterpter
                    ArrayAdapter<Pet> adapter = new ArrayAdapter<>(
                            ComplexClient.this,
                            android.R.layout.simple_list_item_1, pets);

                    showView.setAdapter(adapter);

                } catch (RemoteException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
            }
        });

    }
    @Override
    protected void onDestroy() {
        // TODO Auto-generated method stub
        super.onDestroy();
        this.unbindService(conn);
    }

    private ServiceConnection conn = new ServiceConnection() {

        @Override
        public void onServiceConnected(ComponentName name, IBinder service) {
            // 获取远程Service的onBind方法返回的对象的代理
            petService = IPet.Stub.asInterface(service);
        }

        @Override
        public void onServiceDisconnected(ComponentName name) {
            // TODO Auto-generated method stub
            petService = null;
        }

    };

}











标签: android

热门推荐