AIDL 简单实现


实现步骤
1.建立一个aidl文件,在里面定义好接口,注意里面不能写public修饰符,同接口一样,包名要一致.

package com.systemset.aidl;
interface ILight {
    int getScreenBrightness();
    void setScreenBrightness(int value);
    int getScreenOffTimeout();
    void setScreenOffTimeout(int value);
}

2.实现服务端进程,提供对应的功能.

Build生成对应的java文件(自动生成的java文件在/gen/yourPackage中),里面包含了一个内部类Stub,写一个Service子类,并在内部继承Stub类,实现对应的功能.
// ILight.java

package com.systemset.aidl;
public interface ILight extends android.os.IInterface
{
/** Local-side IPC implementation stub class. */
public static abstract class Stub extends android.os.Binder implements com.systemset.aidl.ILight
{
private static final java.lang.String DESCRIPTOR = "com.systemset.aidl.ILight";
/** Construct the stub at attach it to the interface. */
public Stub()
{
this.attachInterface(this, DESCRIPTOR);
}
/**
* Cast an IBinder object into an com.systemset.aidl.ILight interface,
* generating a proxy if needed.
*/
public static com.systemset.aidl.ILight asInterface(android.os.IBinder obj)
{
if ((obj==null)) {
return null;
}
android.os.IInterface iin = obj.queryLocalInterface(DESCRIPTOR);
if (((iin!=null)&&(iin instanceof com.systemset.aidl.ILight))) {
return ((com.systemset.aidl.ILight)iin);
}
return new com.systemset.aidl.ILight.Stub.Proxy(obj);
}
@Override public android.os.IBinder asBinder()
{
return this;
}
@Override public boolean onTransact(int code, android.os.Parcel data, android.os.Parcel reply, int flags) throws android.os.RemoteException
{
switch (code)
{
case INTERFACE_TRANSACTION:
{
reply.writeString(DESCRIPTOR);
return true;
}
case TRANSACTION_getScreenBrightness:
{
data.enforceInterface(DESCRIPTOR);
int _result = this.getScreenBrightness();
reply.writeNoException();
reply.writeInt(_result);
return true;
}
case TRANSACTION_setScreenBrightness:
{
data.enforceInterface(DESCRIPTOR);
int _arg0;
_arg0 = data.readInt();
this.setScreenBrightness(_arg0);
reply.writeNoException();
return true;
}
case TRANSACTION_getScreenOffTimeout:
{
data.enforceInterface(DESCRIPTOR);
int _result = this.getScreenOffTimeout();
reply.writeNoException();
reply.writeInt(_result);
return true;
}
case TRANSACTION_setScreenOffTimeout:
{
data.enforceInterface(DESCRIPTOR);
int _arg0;
_arg0 = data.readInt();
this.setScreenOffTimeout(_arg0);
reply.writeNoException();
return true;
}
}
return super.onTransact(code, data, reply, flags);
}
private static class Proxy implements com.systemset.aidl.ILight
{
private android.os.IBinder mRemote;
Proxy(android.os.IBinder remote)
{
mRemote = remote;
}
@Override public android.os.IBinder asBinder()
{
return mRemote;
}
public java.lang.String getInterfaceDescriptor()
{
return DESCRIPTOR;
}
@Override public int getScreenBrightness() throws android.os.RemoteException
{
android.os.Parcel _data = android.os.Parcel.obtain();
android.os.Parcel _reply = android.os.Parcel.obtain();
int _result;
try {
_data.writeInterfaceToken(DESCRIPTOR);
mRemote.transact(Stub.TRANSACTION_getScreenBrightness, _data, _reply, 0);
_reply.readException();
_result = _reply.readInt();
}
finally {
_reply.recycle();
_data.recycle();
}
return _result;
}
@Override public void setScreenBrightness(int value) throws android.os.RemoteException
{
android.os.Parcel _data = android.os.Parcel.obtain();
android.os.Parcel _reply = android.os.Parcel.obtain();
try {
_data.writeInterfaceToken(DESCRIPTOR);
_data.writeInt(value);
mRemote.transact(Stub.TRANSACTION_setScreenBrightness, _data, _reply, 0);
_reply.readException();
}
finally {
_reply.recycle();
_data.recycle();
}
}
@Override public int getScreenOffTimeout() throws android.os.RemoteException
{
android.os.Parcel _data = android.os.Parcel.obtain();
android.os.Parcel _reply = android.os.Parcel.obtain();
int _result;
try {
_data.writeInterfaceToken(DESCRIPTOR);
mRemote.transact(Stub.TRANSACTION_getScreenOffTimeout, _data, _reply, 0);
_reply.readException();
_result = _reply.readInt();
}
finally {
_reply.recycle();
_data.recycle();
}
return _result;
}
@Override public void setScreenOffTimeout(int value) throws android.os.RemoteException
{
android.os.Parcel _data = android.os.Parcel.obtain();
android.os.Parcel _reply = android.os.Parcel.obtain();
try {
_data.writeInterfaceToken(DESCRIPTOR);
_data.writeInt(value);
mRemote.transact(Stub.TRANSACTION_setScreenOffTimeout, _data, _reply, 0);
_reply.readException();
}
finally {
_reply.recycle();
_data.recycle();
}
}
}
static final int TRANSACTION_getScreenBrightness = (android.os.IBinder.FIRST_CALL_TRANSACTION + 0);
static final int TRANSACTION_setScreenBrightness = (android.os.IBinder.FIRST_CALL_TRANSACTION + 1);
static final int TRANSACTION_getScreenOffTimeout = (android.os.IBinder.FIRST_CALL_TRANSACTION + 2);
static final int TRANSACTION_setScreenOffTimeout = (android.os.IBinder.FIRST_CALL_TRANSACTION + 3);
}
public int getScreenBrightness() throws android.os.RemoteException;
public void setScreenBrightness(int value) throws android.os.RemoteException;
public int getScreenOffTimeout() throws android.os.RemoteException;
public void setScreenOffTimeout(int value) throws android.os.RemoteException;
}
View Code

// LightService.java

package com.systemset.aidl;

import static android.util.Log.d;
import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.os.IBinder;
import android.os.RemoteException;
import android.provider.Settings;
import android.provider.Settings.SettingNotFoundException;

import com.apical.systemset.util.SetManager;

public class LightService extends Service {

    private static final String TAG = "debug";
    private LightServer mLightServer;

    public LightService() {
    }

    @Override
    public IBinder onBind(Intent intent) {
        if (mLightServer == null)
            mLightServer = new LightServer();
        d(TAG, "LightService: onBind");
        return mLightServer;
    }

    @Override
    public boolean onUnbind(Intent intent) {
        d(TAG, "LightService: onUnbind");
        mLightServer = null;
        return super.onUnbind(intent);
    }

    public class LightServer extends ILight.Stub {

        @Override
        public int getScreenBrightness() throws RemoteException {
            int value = SetManager.getInstance().getScreenBrightness(
                    LightService.this);
            d(TAG, "LightServer: call getScreenBrightness! return value is "
                    + value);
            return value;
        }

        @Override
        public void setScreenBrightness(int value) throws RemoteException {
            d(TAG, "LightServer: call setScreenBrightness.value is " + value);
            SetManager.getInstance().setScreenBrightness(LightService.this,
                    value);
        }

        @Override
        public int getScreenOffTimeout() throws RemoteException {
            int value = SetManager.getInstance().getScreenOffTimeout(
                    LightService.this);
            d(TAG, "LightServer: call getScreenOffTimeout! return value is "
                    + value);
            return value;
        }

        @Override
        public void setScreenOffTimeout(int value) throws RemoteException {
            d(TAG, "LightServer: call setScreenOffTimeout.value is " + value);
            SetManager.getInstance().setScreenOffTimeout(LightService.this,
                    value);
        }
    }

    public static int getScreenBrightness(Context context) {
        int light = 0;
        try {
            light = Settings.System.getInt(context.getContentResolver(),
                    Settings.System.SCREEN_BRIGHTNESS);
        } catch (SettingNotFoundException e) {
            d(TAG, "SystemManager:", e);
        }
        return light;
    }

    public static void setScreenBrightness(Context context, int value) {
        Settings.System.putInt(context.getContentResolver(),
                Settings.System.SCREEN_BRIGHTNESS, value);
    }

    public static int getScreenOffTimeout(Context context) {
        int time = 0;
        try {
            time = Settings.System.getInt(context.getContentResolver(),
                    Settings.System.SCREEN_OFF_TIMEOUT);
        } catch (SettingNotFoundException e) {
            d(TAG, "SystemManager:", e);
        }
        return time;
    }

    public static void setScreenOffTimeout(Context context, int value) {
        Settings.System.putInt(context.getContentResolver(),
                Settings.System.SCREEN_OFF_TIMEOUT, value);
    }
}


// 在AndroidManifest.xml中注册服务

<service
android:name="com.systemset.aidl.LightService"
android:process=":remote"
android:exported="true" >
<intent-filter>
<action android:name="com.apical.systemset.aidl.LightService" />
</intent-filter>
</service>
View Code

3.实现客户端进程,提供对应的功能.
  将aidl文件拷贝到客户端进程中,注意包名需要一致.同样Build之后,会生成对应的java文件.使用bindService启动服务,在ServiceConnection的
onServiceConnected函数中使用Stub.asInterface(binder)取得对象.


Intent intent = new Intent();
intent.setAction("com.apical.systemset.aidl.LightService");
// 不能调用setPackage,否则会出现如下错误
// Unable to start service Intent { act=com.apical.systemset.aidl.LightService pkg=com.diysoul.aidlclient } U=0: not found
// intent.setPackage(getPackageName());
boolean bindResult = bindService(intent, mServiceConnection,
Context.BIND_AUTO_CREATE);
// ServiceConnection对象定义如下
private ServiceConnection mServiceConnection = new ServiceConnection() {
@Override
public void onServiceDisconnected(ComponentName componentName) {
d(TAG, "ServiceConnection componentName:" + componentName);
mLight = null;
}
@Override
public void onServiceConnected(ComponentName componentName,
IBinder binder) {
d(TAG, "ServiceConnection componentName:" + componentName);
mLight = ILight.Stub.asInterface(binder);
try {
int screenBrightness = mLight.getScreenBrightness();
int ScreenOffTimeout = mLight.getScreenOffTimeout();
d(TAG, "client getScreenBrightness = " + screenBrightness);
d(TAG, "client getScreenOffTimeout = " + ScreenOffTimeout);
} catch (RemoteException e) {
d(TAG, "", e);
}
}
};

// MainActivity.java

package com.diysoul.aidlclient;

import android.app.Activity;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import android.os.RemoteException;
import static android.util.Log.d;
import com.systemset.aidl.ILight;

public class MainActivity extends Activity {
    
    private static final String TAG = "debug";
    private ILight mLight;
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        Intent intent = new Intent();
        intent.setAction("com.apical.systemset.aidl.LightService");
        // Unable to start service Intent { act=com.apical.systemset.aidl.LightService pkg=com.diysoul.aidlclient } U=0: not found
        // intent.setPackage(getPackageName());
        boolean bindResult = bindService(intent, mServiceConnection,
                Context.BIND_AUTO_CREATE);
        d(TAG, "bindResult:" + bindResult);
        d(TAG, "mLight:" + mLight);
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        unbindService(mServiceConnection);
    }

    private ServiceConnection mServiceConnection = new ServiceConnection() {

        @Override
        public void onServiceDisconnected(ComponentName componentName) {
            d(TAG, "ServiceConnection componentName:" + componentName);
            mLight = null;
        }

        @Override
        public void onServiceConnected(ComponentName componentName,
                IBinder binder) {
            d(TAG, "ServiceConnection componentName:" + componentName);
            mLight = ILight.Stub.asInterface(binder);
            try {
                int screenBrightness = mLight.getScreenBrightness();
                int ScreenOffTimeout = mLight.getScreenOffTimeout();
                d(TAG, "client getScreenBrightness = " + screenBrightness);
                d(TAG, "client getScreenOffTimeout = " + ScreenOffTimeout);
            } catch (RemoteException e) {
                d(TAG, "", e);
            }
        }
    };
}
原文地址:https://www.cnblogs.com/diysoul/p/5288877.html