Service比Activity具有更高的优先级
Service 除了可以实现后台服务功能,还可以用于进程间通信
Service的生命周期
image.png
Service的使用方式

  1. 启动方式:不能获取service实例,也就不能调用service中的任何函数
  2. 绑定方式
    使用通过服务链接(Connction)实现
    使用Service的组件通过Context.bindService()建立连接,通过Context.unbindService()断开连接

如何实现Service()?

public class RandomService extends Service{
    
    @Override
    public void onCreate() {
        super.onCreate();
       //实现代码
    }
    
    @Override
    public void onStart(Intent intent, int startId) {
          super.onStart(intent, startId);
         //实现代码
    }
    
    @Override
    public void onDestroy() {
         super.onDestroy();
        //实现代码 
    }
     
    //onBind()函数是在Service被绑定后调用的函数,能够返回Service的对象实例
    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }

}

Service被绑定后调用的函数,能够返回Service的对象实例:

public IBinder onBind(Intent intent){
return Service的对象实例
}

Service的对象实例怎么写?

完成Service类需要在AndroidManifest.xml注册服务

<service android:name=".RandomService"/>

在其他组件启动服务

显示启动

final Intent serviceIntent = new Intent(this, RandomService.class);
startService(serviceIntent);
stopService(serviceIntent);

隐式启动

final Intent serviceIntent = new Intent();
serviceIntent.setAction("edu.hrbeu.RandomService");//传递参数是Service 的包名位置

除此之外还要在AndroidManifest.xml声明,让启动找到相应的服务

<service android:name=".RandomService">
    <intent-filter>
          <action android:name="edu.hrbeu.RandomService"/> 
    </intent-filter>
</service>

Activity,Service,BroadcastReceiver都是工作在主线程
如何创建子线程?

  1. 实现java的Runnable接口,重载run()函数

    private Runnable backgroundWork=new Runnable(){
         @Override
         public void run(){
             //过程代码
         }
    }
  2. 创建Thread对象,将Runnable对象作为参数传递给Thread对象
private Thread WorkThread;
workThread = new Thread(null,backgroundWork,"WorkThread");//第三个参数是线程名
  1. 启动线程是Thread对象调用start()方法;

    workThread.start();
  2. 如何终止线程?调用interrupt()方法;

    workThread.interrupt();
  3. 查询线程是否被中断

    Thread.interrupted();

    如何使用线程中的数据更新用户界面?

    用Handler更新用户界面

    新建Handler实例,通过post()方法将Runnable对象从后台线程发送到GUI线程的消息队列

    private static Handler handler = new Handler();
    public static void UpdateGUI(double refreshDouble){
         randomDouble = refreshDouble;
         handler.post(RefreshLable);
     }
     
     private static Runnable RefreshLable = new Runnable(){
         @Override
         public void run() {
             labelView.setText(String.valueOf(randomDouble));
         }
     };
  4. 如何让普通函数可以变成线程函数?实现接口Runnable()中对应的run()方法,函数的实现的方法写在run()中。
  5. 启动线程需要创建Thread对象,将线程函数作为参数传递给Thread对象,通过Thread对象操纵线程的启动和暂停
  6. 将线程中的数据更新到用户界面,就是借助Handler,先创建一个Handler实例,handler()通过post()方法:handelr.post([线程函数名]) ,将线程函数作为参数传递过去,这样线程函数就会被加入到GUI的线程消息队列中,等待被执行。

如何绑定服务?

为了使服务支持绑定,必须在Service类中重载onBind()方法,并在onBind()方法中返回service实例

public class MathService extends Service{

    private final IBinder mBinder = new LocalBinder();

    public class LocalBinder extends Binder{
        MathService getService() {
            return MathService.this;
        }
    }

    @Override
    public IBinder onBind(Intent intent) {
        return mBinder;
    }
    
    @Override
    public boolean onUnbind(Intent intent){
        return false;
    }
    
    public long Add(long a, long b){
        return a+b;
    }
    
}

绑定服务
bindService()的第二个参数是ServiceConnection,一旦绑定成功,Android系统会调用ServiceConnection的onServiceConnected(),获取服务实例,之后程序就可以用这个服务实例调用服务里面的方法。

final Intent serviceIntent = new Intent(SimpleMathServiceDemoActivity.this,MathService.class);
bindService(serviceIntent,mConnection,Context.BIND_AUTO_CREATE);

private ServiceConnection mConnection = new ServiceConnection() {
        @Override
        public void onServiceConnected(ComponentName name, IBinder binder) {
            mathService = ((MathService.LocalBinder)binder).getService();
        }

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

远程服务


自由自在像小鸟
4 声望1 粉丝