当前位置: 代码迷 >> Android >> Android Activity生命周期一探到底 及 主Activity里带Thread跳转时的注意事项
  详细解决方案

Android Activity生命周期一探到底 及 主Activity里带Thread跳转时的注意事项

热度:638   发布时间:2016-04-24 11:56:17.0
Android Activity生命周期一探究竟 及 主Activity里带Thread跳转时的注意事项

关注微信号:javalearns?? 随时随地学Java

或扫一扫

?

?

随时随地学Java

问题背景:
?
最近用到了主Activity里有一个Thread在处理数据,当跳转到第二个Activity时,希望Thread暂停。从第二个Activity回来时这个Thread再接着运行。今天得空顺着这个应用场景再过一下Activity的生命周期。
?
下面是一个小demo,主Activity里有个按钮,跳转到第二个Activity。在主Activity里有个UpdateThread在一直运行。第二个Activity里有个按钮,点击显示一个Dialog。下面是源码:
?
activity_main.xml
?
1
2
3
<relativelayout android:layout_height="match_parent"android:layout_width="match_parent"android:paddingbottom="@dimen/activity_vertical_margin"android:paddingleft="@dimen/activity_horizontal_margin"android:paddingright="@dimen/activity_horizontal_margin"android:paddingtop="@dimen/activity_vertical_margin"tools:context=".MainActivity"xmlns:android="http://schemas.android.com/apk/res/android"xmlns:tools="http://schemas.android.com/tools">
?
<textview android:id="@+id/textview_show"?android:layout_height="wrap_content"android:layout_width="wrap_content"?android:text="@string/hello_world"android:textsize="23dip"><button android:id="@+id/button_jump"android:layout_centerinparent="true"?android:layout_height="wrap_content"android:layout_width="wrap_content"?android:text="跳转"android:textsize="23dip"></button></textview></relativelayout>

?

activity_second.xml

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
????<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
????xmlns:tools="http://schemas.android.com/tools"
????android:layout_width="match_parent"
????android:layout_height="match_parent"
????android:paddingBottom="@dimen/activity_vertical_margin"
????android:paddingLeft="@dimen/activity_horizontal_margin"
????android:paddingRight="@dimen/activity_horizontal_margin"
????android:paddingTop="@dimen/activity_vertical_margin"
????tools:context=".SecondActivity"?>
?
????<TextView
????????android:layout_width="wrap_content"
????????android:layout_height="wrap_content"
????????android:text="@string/hello_world"?/>
????<Button
????????android:id="@+id/button_show_dialog"
????????android:layout_width="wrap_content"
????????android:layout_height="wrap_content"
????????android:layout_centerInParent="true"
????????android:text="显示Dialog"/>
?
</RelativeLayout>

MainActivity.java

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
????package?com.example.activitylife;
?
import?android.app.Activity;
import?android.content.Intent;
import?android.os.Bundle;
import?android.util.Log;
import?android.view.Menu;
import?android.view.View;
import?android.widget.Button;
import?android.widget.TextView;
?
public?class?MainActivity?extends?Activity {
????TextView mTextView =?null;
????Button mBtutton =?null;
????boolean?allowRun =?true;
????boolean?allowUpdate =?true;
????private?static?final?String tag =?"yan";
????@Override
????protected?void?onCreate(Bundle savedInstanceState) {
????????super.onCreate(savedInstanceState);
????????setContentView(R.layout.activity_main);
????????initUI();
????????Log.i(tag,?"onCreate...");
????????mTextView.setText("..................."?+ "
");
????????mTextView.append("onCreate..."?+ "
");
????????new?<a title="Thread"?href="http://www.android-study.com/pingtaikaifa/568.html">Thread</a>(new?Update<a title="Thread"href="http://www.android-study.com/pingtaikaifa/568.html">Thread</a>()).start();
????}
?????
?
????@Override
????protected?void?onStart() {
????????// TODO Auto-generated method stub
????????super.onStart();
????????Log.i(tag,?"onStart...");
????????mTextView.append("onStart..."?+ "
");
????}
?
?
????@Override
????protected?void?onRestart() {
????????// TODO Auto-generated method stub
????????super.onRestart();
????????Log.i(tag,?"onRestart...");
????????mTextView.append("onRestart..."?+ "
");
????}
?
?
????@Override
????protected?void?onResume() {
????????// TODO Auto-generated method stub
????????super.onResume();
????????Log.i(tag,?"onResume...");
????????mTextView.append("onResume..."?+ "
");
????}
?
?
????@Override
????protected?void?onPause() {
????????// TODO Auto-generated method stub
????????super.onPause();
????????Log.i(tag,?"onPause...");
????????mTextView.append("onPause..."?+ "
");
????}
?
?
????@Override
????protected?void?onStop() {
????????// TODO Auto-generated method stub
????????super.onStop();
????????Log.i(tag,?"onStop...");
????}
?
?
????@Override
????protected?void?onDestroy() {
????????// TODO Auto-generated method stub
????????Log.i(tag,?"onDestroy...");
????????super.onDestroy();
????}
?
?
????@Override
????public?boolean?onCreateOptionsMenu(Menu menu) {
????????// Inflate the menu; this adds items to the action bar if it is present.
????????getMenuInflater().inflate(R.menu.main, menu);
????????return?true;
????}
????public?void?initUI(){
????????mTextView = (TextView)findViewById(R.id.textview_show);
????????mBtutton = (Button)findViewById(R.id.button_jump);
????????mBtutton.setOnClickListener(new?View.OnClickListener() {
?????????????
????????????@Override
????????????public?void?onClick(View v) {
????????????????// TODO Auto-generated method stub
????????????????Intent intent =?new?Intent(MainActivity.this, SecondActivity.class);
//????????????? allowRun = false;
//????????????? allowUpdate = false;
????????????????startActivity(intent);
????????????}
????????});
????}
????class?Update<a title="Thread"?href="http://www.android-study.com/pingtaikaifa/568.html">Thread</a>?implements?Runnable{
?
????????@Override
????????public?void?run() {
????????????// TODO Auto-generated method stub
????????????while(allowRun){
????????????????if(allowUpdate){
????????????????????try?{
????????????????????????<a title="Thread"?href="http://www.android-study.com/pingtaikaifa/568.html">Thread</a>.sleep(1000);
????????????????????????Log.i(tag,?"Update<a title="Thread" href="http://www.android-study.com/pingtaikaifa/568.html">Thread</a>....");
????????????????????}?catch?(InterruptedException e) {
????????????????????????// TODO Auto-generated catch block
????????????????????????e.printStackTrace();
????????????????????}
?????????????????????
????????????????}
????????????}
????????}
?????????
????}
}

SecondActivity.java

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
????package?com.example.activitylife;
?
import?android.app.Activity;
import?android.app.AlertDialog;
import?android.app.Dialog;
import?android.content.Context;
import?android.content.DialogInterface;
import?android.content.DialogInterface.OnClickListener;
import?android.os.Bundle;
import?android.util.Log;
import?android.view.Menu;
import?android.view.View;
import?android.widget.Button;
?
public?class?SecondActivity?extends?Activity {
????private?final?static?String tag =?"yan";
????Button mShowDialogBtn =?null;
????@Override
????protected?void?onCreate(Bundle savedInstanceState) {
????????super.onCreate(savedInstanceState);
????????setContentView(R.layout.activity_second);
????Log.i(tag,?"SecondActivity:OnCreate...");
????mShowDialogBtn = (Button)findViewById(R.id.button_show_dialog);
????mShowDialogBtn.setOnClickListener(new?View.OnClickListener() {
?????????
????????@Override
????????public?void?onClick(View v) {
????????????// TODO Auto-generated method stub
????????????showAlertDialog(SecondActivity.this);
????????}
????});
????}
?
????@Override
????protected?void?onStart() {
????????// TODO Auto-generated method stub
????????super.onStart();
????????Log.i(tag,?"SecondActivity:onStart...");
????}
?
????@Override
????protected?void?onRestart() {
????????// TODO Auto-generated method stub
????????super.onRestart();
????????Log.i(tag,?"SecondActivity:onRestart...");
????}
?
????@Override
????protected?void?onResume() {
????????// TODO Auto-generated method stub
????????super.onResume();
????????Log.i(tag,?"SecondActivity:onResume...");
????}
?
????@Override
????protected?void?onPause() {
????????// TODO Auto-generated method stub
????????super.onPause();
????????Log.i(tag,?"SecondActivity:onPause...");
????}
?
????@Override
????protected?void?onStop() {
????????// TODO Auto-generated method stub
????????super.onStop();
????????Log.i(tag,?"SecondActivity:onStop...");
????}
?
????@Override
????protected?void?onDestroy() {
????????// TODO Auto-generated method stub
????????super.onDestroy();
????????Log.i(tag,?"SecondActivity onDestroy...");
????}
?
????@Override
????public?boolean?onCreateOptionsMenu(Menu menu) {
????????// Inflate the menu; this adds items to the action bar if it is present.
????????getMenuInflater().inflate(R.menu.second, menu);
????????return?true;
????}
?????
????public?void?showAlertDialog(Context c){
????????Dialog dialog =?new?AlertDialog.Builder(c)
????????.setTitle("通知")
????????.setMessage("专注才能深入 ")
????????.setIcon(android.R.drawable.ic_dialog_email)
????????.setPositiveButton("确定",?new?OnClickListener() {
?????????????
????????????@Override
????????????public?void?onClick(DialogInterface dialog,?int?which) {
????????????????// TODO Auto-generated method stub
????????????????dialog.dismiss();
????????????}
????????})
????????.create();
????????dialog.show();
????}
?
}

运行界面:

下面是得到的结论:
?
1、一个正常的Activity的流程:onCreate------onStart-----------onResume, onResume的时候就可以看到这个Activity,并跟这个Activity进行交互。之后如果正常退出的话,流程是:onPause--------onStop---------onDestroy.什么时候进行onPause的状态呢?在Activity不在是最前端,但依然可见时这个状态是onPause。所以切换到SecondActivity时,主Activity先进行onPause,当SecondActivity onResume可见时,主Activity进行onStop,表示彻底不可见。 (正常的流程可简化记忆为:CS R, PS D. 有CS和PS打头 ?不会记混淆吧。)
?
2、如果不做特别处理,主Activity切换到SecondActivity后,只进行到onStop,如果自己写了finish(),那么从SecondActivity按返回键时就直接退出了,否则的话主Activity进行onRestart--------onStart-----onResume.恢复正常。
?
3、当主Activity里有个UpdateThread一直在运行时,即使切换到SecondActivity,它依旧没有被释放,并正常运行。
?
如果需要切换到第二个Activity时,UpdateThread停止运行,让allowUpdate = false。当切换回来时,让allowUpdate = true就ok了。
?
4、从SecondActivity按返回键时,SecondActivity自动进行了onDestroy.
?
5、如果不对主Activity做额外操作,当按返回键后,虽然他执行了onDestroy,但是UpdateThread一直在运行。这点比较奇葩,呵呵。所以要退出主程序时,一定让allowRun = false,确保Thread停止.
?
6、当在主Activity复写了OnBackPressed()时:
?
1
2
3
4
5
6
7
????@Override
public?void?onBackPressed() {
????// TODO Auto-generated method stub
????super.onBackPressed();
????MainActivity.this.finish();
}

?

虽然finish()了,但是UpdateThread依旧在运行。
7、如果对主Activity进行锁屏,它从onResume-----切换到onPause---onStop的状态,不用说,UpdateThread依旧在运行。
?
8、当在SecondActivity按显示Dialog时,如上面第三幅图时,对SecondActivity的状态没有任何影响。这一点跟咱家之前的观念还不大一样,往后要更正了。其实可以这样理解,因为Dialog显示的时候,SecondActivity首先是可见的所以肯定不是onStop状态。再者,虽然SecondActivity貌似不在最前端了,但事实上他依旧可以合用户进行交互,在屏幕周围可以响应点击等事件。在本例中,如果不按Dialog的确定按键,而是点击屏幕其他区域一样可以让Dialog消失,所以SecondActivity没有进入onPause状态,而依旧是OnResume.
?
链接http://blog.csdn.net/lamp_zy/article/details/7703893说当按锁屏键时,原Activity只执行onPause而不执行onStop这是胡扯。此链接中还说,当有Dialog显示时,当前Activity会进入onPause状态而不进入OnStop状态,这亦是胡扯,真实情况是当有Dialog显示时,原Activity依旧是onResume状态。
这下Activity的生命周期终于真相大白了!!!

关注微信号:javalearns?? 随时随地学Java

或扫一扫

?

?

随时随地学Java

  相关解决方案