service 是Android的四大组件之一,它是运行在后台的一个服务,运行在主线程。要会使用它,我们就应该明白它的运行过程。
一、Service的生命周期
Sevice的启动方式有两种
- 1.startService
startService
方式启动的服务,它的生命周期与启动它的组件的生命周期无关。它的生命周期为
onCreate()->onStartCommond()->onDestroy()
开启的时候,走onCreate()->onStartCommond()
如果Service已经启动,那么再次启动的时候,会走onStartCommond()
方法,不会再走onCreate()
方法。
结束的时候,通过自己调用stopSelf()
,或者其他组件顶用stopService(Intent intent)
方法进行停止服务
此时执行onDestroy()。
- 2.bindService
bindService
方式启动的服务,它的生命周期与启动它的组件的生命周期有关
(同生同灭)。它的生命周期为
onCreate()->onBind()->onUnbind()->onDestroy()
绑定的时候,会调用onCreate()->onBind()
在onBind()
中,我们可以返回我们客户端需要控制的类。
如果Service已经绑定,那么再次绑定的话,不会走任何方法方法。
解绑的时候,调用unbindService(ServiceConnection conn)
,此时会走onUnbind()->onDestroy()
二.混合使用
混合使用startService和bindService在我们开发中也是比较常用的,比如我们在做一个音频播放器的功能的时候,我们需要音频持续的能够在后台播放,同时我们需要它与我们的UI进行交互,此时我们就需要混合的使用这两种方法了。
思路是:通过startService()
让播放服务能够持续的在后台进行播放音频,然后通过bindService()
绑定我们需要监听或者控制的接口,这些都是通过UI控制的,因此当我们不需要显示这个UI界面的时候,是不需要与播放状态同步的,显示UI界面的时候,我们再去绑定我们的播放服务。
如果我们先调用了startService()
,此时生命周期为onCreate()->onStartCommond()
,接着我们调用bindService()此时,会调用onBind()
,如果此时我们调用stopService(),并不能销毁service,因为它还处于bind状态,只有调用stopService()
同时调用了unbindService()
的时候,才能彻底销毁service(反之一样)。
以下是代码:
Service代码:
public class PlayerService extends Service {
private final String TAG = "debug";
@Override
public void onCreate() {
super.onCreate();
Log.d(TAG, "--onCreate--");
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
Log.d(TAG, "--onStartCommand--");
return super.onStartCommand(intent, flags, startId);
}
private final IBinder mybinder = new MyBinder();
public class MyBinder extends Binder {
PlayerService getService() {
return PlayerService.this;
}
}
@Override
public IBinder onBind(Intent intent) {
Log.d(TAG, "--onBind--");
return mybinder;
}
@Override
public void onRebind(Intent intent) {
super.onRebind(intent);
Log.d(TAG, "--onRebind---");
}
@Override
public boolean onUnbind(Intent intent) {
Log.d(TAG, "--onUnbind---");
return true;
}
@Override
public void onDestroy() {
Log.d(TAG, "--onDestroy--");
super.onDestroy();
}
}
开启服务的方法
1.startService方式
private void startService() {
startService(new Intent(this, PlayerService.class));
}
2.bindService方式
private void bindService() {
bindService(new Intent(this, PlayerService.class), serviceConnection, Service.BIND_AUTO_CREATE);
}
PlayerService playerService;
private boolean connectied;
private ServiceConnection serviceConnection = new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
Log.d("debug", "--onServiceConnected--");
playerService = ((PlayerService.MyBinder) service).getService();
connectied = true;
}
@Override
public void onServiceDisconnected(ComponentName name) {
Log.d("debug", "--onServiceDisconnected--");
playerService = null;
}
};