标签:service生命周期
本节学习Service的生命周期。 既然Activity有生命周期,那同理Service也有自己的生命周期。
和学习Activity一样,我们先贴出Google官网给Service下的定义,以及生命周期图
从图中可以看到,左面一路下来是我们第二节课中说的用StartServer启动服务的流程。右面一路下来的是第三节中说的用BindService启动服务的流程。
在上两节中都看到了如何启动服务,同时销毁服务。既然这年代是混搭的年代,那当然也需要这两种服务混搭起来使用。
先来看看MyActivity的代码:
public class MyActivity extends Activity { private Button btn_start; private Button btn_end; private Button btn_bind; private Button btn_unbind; private MyServiceConnection sConnection; @Override protected void onCreate(Bundle savedInstanceState) { // TODO Auto-generated method stub super.onCreate(savedInstanceState); setContentView(R.layout.activity_myservice); btn_start = (Button)findViewById(R.id.button1); btn_end = (Button)findViewById(R.id.button2); btn_bind = (Button)findViewById(R.id.button3); btn_unbind = (Button)findViewById(R.id.button4); btn_start.setOnClickListener(new OnClickListener() { @Override public void onClick(View arg0) { // 启动服务 Intent intent = new Intent(MyActivity.this, MyService.class); startService(intent); Log.i("MyActivity", "创建服务按钮被按下!"); } }); btn_end.setOnClickListener(new OnClickListener() { @Override public void onClick(View arg0) { // 销毁服务 Intent intent = new Intent(MyActivity.this, MyService.class); stopService(intent); Log.i("MyActivity", "销毁服务按钮被按下!"); } }); btn_bind.setOnClickListener(new OnClickListener() { @Override public void onClick(View arg0) { // 启动服务 Intent intent = new Intent(MyActivity.this, MyService.class); Log.i("MyActivity", "绑定服务按钮被按下!"); bindService(intent, sConnection, Service.BIND_AUTO_CREATE); } }); btn_unbind.setOnClickListener(new OnClickListener() { @Override public void onClick(View arg0) { // 启动服务 Intent intent = new Intent(MyActivity.this, MyService.class); Log.i("MyActivity", "解绑服务按钮被按下!"); unbindService(sConnection); } }); } public class MyServiceConnection implements ServiceConnection { @Override//当连接服务成功后调用 public void onServiceConnected(ComponentName arg0, IBinder arg1) { // TODO Auto-generated method stub Log.i("MyActivity", "onServiceConnected"); } @Override//当server所在的进程由于异常终止或者其他原因终止调用 public void onServiceDisconnected(ComponentName arg0) { // TODO Auto-generated method stub Log.i("MyActivity", "onServiceDisconnected"); } } }
public class MyService extends Service { private MyThread thread; private boolean stopFlag = false; @Override//必须实现的方法 public IBinder onBind(Intent arg0) { // TODO Auto-generated method stub //服务运行后,启动线程 if(!stopFlag) { thread.start(); thread.setFlag(true); } Log.i("MyService", "onBind------------"); return null; } @Override//被创建时的调用 public void onCreate() { // TODO Auto-generated method stub //服务创建时,实例化MyThread thread = new MyThread(); Log.i("MyService", "onCreate------------"); super.onCreate(); } @Override @Deprecated//OnStart方法现在被OnStartCommd已经取代,其实在OnStartCommand也调用了OnStart public void onStart(Intent intent, int startId) { // TODO Auto-generated method stub super.onStart(intent, startId); Log.i("MyService", "onStart------------"); } @Override//启动时会调用 public int onStartCommand(Intent intent, int flags, int startId) { // TODO Auto-generated method stub Log.i("MyService", "onStartCommand------------"); //服务运行后,启动线程 if(!stopFlag) { thread.start(); thread.setFlag(true); } return super.onStartCommand(intent, flags, startId); } @Override public void onDestroy() { // TODO Auto-generated method stub //服务销毁时,停止线程任务 thread.setFlag(false); Log.i("MyService", "onDestroy------------"); super.onDestroy(); } @Override public boolean onUnbind(Intent intent) { // TODO Auto-generated method stub Log.i("MyService", "onUnbind------------"); return super.onUnbind(intent); } class MyThread extends Thread { //设置flag public void setFlag(Boolean flag) { stopFlag = flag; } @Override public void run() { super.run(); while(stopFlag) { //设置时间的输出方式 SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); String time = format.format(new Date()); //显示时间 Log.i("MyService", time); try { //延迟一秒 Thread.sleep(1000); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } }
那既然要学习两者混搭,那就看有几种混搭的方式:
1: 用StartServer启动服务,然后再去用BindService绑定服务
可以看到是先StartServer启动服务,在用BindService绑定服务
接着,我们用stopservice停止服务
可以看到服务是无法停止的
那如果我们用unbindService先解绑服务
可以看到用解绑服务是可以停止服务 的。
2: 用BindService绑定服务,然后再去用StartServer启动服务
可以看到依然按停止服务是不行的,必须先解绑服务
那总结一下: 混合调用时,不论是先启动服务还是绑定服务,最后都需要解绑服务,不过不解绑服务,服务是停止不了的。
那再看一个现象,如果服务正在运行,我将当前Activity直接按Back键退出,会有怎么样的效果?
首先在MyActivity中增加如下方法
@Override public boolean onKeyDown(int keyCode, KeyEvent event) { // TODO Auto-generated method stub if(keyCode == KeyEvent.KEYCODE_BACK) { Log.i("MyActivity", "KEYCODE_BACK is pressed!"); } return super.onKeyDown(keyCode, event); } @Override protected void onDestroy() { Log.i("MyActivity", "onDestroy"); super.onDestroy(); }
1:用Startservice启动服务,然后退出Activity
可以看到当我按下back键后Activity是销毁了,但是我们的服务依然是运行的。这可以说明StartServer启动服务与Activity没有关系
如果停止服务,必须要设置->app->正在运行中停止服务
2:用BindService启动服务,然后退出
可以看到用BindService启动服务,当Activity退出时,服务就停止了。说明BindService启动的服务是和Actiivty是相关的。
那这个问题,看完后,我们再次回到我们的混搭service上。
如果,让我们用混搭的方式启动服务后, 而没有解绑,是直接退出Activity了。
因为bindService启动服务和Activity是有关联的,Activity销毁也会解绑的。但是我们中间有用StartServer启动服务,所以服务依旧在运行。关于直接退出有异常。我们可以在Activity退出的Destory方法中调用onunbindService
@Override protected void onDestroy() { Log.i("MyActivity", "onDestroy"); unbindService(sConnection); super.onDestroy(); }然后直接退出就不会有异常打印。
好,关于serive的生命周期就说到这里。
版权声明:本文为博主原创文章,未经博主允许不得转载。
标签:service生命周期
原文地址:http://blog.csdn.net/longwang155069/article/details/47002005