您的位置:首页 > 其它

Activity的四种launchMode以及onNewIntent()的调用时机

2015-08-27 20:17 447 查看
Android的Activity一共有四种launchMode:standard、singleTop、singleTask、singleInstance,在AndroidManifest.xml中用来指定Activity的启动方式。

一、standard

activity的默认启动方式,未指定android:launchMode的属性时默认为standard。

public class MainActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Log.e("", "MainActivity: " + this.toString());
findViewById(R.id.start_new_activity).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
startActivity(new Intent(MainActivity.this, MainActivity.class));
}
});
}
}


三次点击start_new_activity,结果如下:

MainActivity: com.example.liuwei.myapplication.MainActivity@43090380
MainActivity: com.example.liuwei.myapplication.MainActivity@430aac80
MainActivity: com.example.liuwei.myapplication.MainActivity@430b67f0
MainActivity: com.example.liuwei.myapplication.MainActivity@430c1ab8


可以发现,同样的MainActivity创建了四个不同的实例,点击四次返回键,才可以退出整个APP。

standard启动模式中,不管有没有已经存在的实例,都会创建一个新的实例。

二、singleTop

指定launchMode为singleTop,重复执行上述操作,结果如下:

MainActivity: com.example.myapp.MainActivity@3c8362e9


同时APP并没有出现activity之间跳转的现象,点击返回键直接退出当前APP,说明当指定为singleTop时,栈中只有一个MainActivity的实例。在MainActivity中重写onNewIntent()方法,发现点击按钮时都会调用一次onNewIntent()方法。

创建一个新的Activity,执行其launchMode为singleTop。让MainActivity和AnotherActivity互相跳转。

代码如下:

public class AnotherActivity extends Activity {

@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Log.e("111111111111111", "AnotherActivity: " + this.toString());
findViewById(R.id.start_new_activity).setOnClickListener(
new View.OnClickListener() {
@Override
public void onClick(View v) {
startActivity(new Intent(AnotherActivity.this,
MainActivity.class));
}
});
}

@Override
protected void onNewIntent(Intent intent) {
// TODO Auto-generated method stub
super.onNewIntent(intent);
Log.e("111111111111", "onNewIntent()");
}
}


执行APP,点击跳转按钮,结果如下:

MainActivity: com.example.myapp.MainActivity@beaa115
AnotherActivity: com.example.myapp.AnotherActivity@2ceddcd
MainActivity: com.example.myapp.MainActivity@19f6f985
AnotherActivity: com.example.myapp.AnotherActivity@3c1fd43d
MainActivity: com.example.myapp.MainActivity@12c24df5
AnotherActivity: com.example.myapp.AnotherActivity@219346ad


在互相跳转的过程中,MainActivity和AnotherActivity每次都会创建一个新的实例,而没有使用原有的实例。

当launchMode指定为singleTop时,如果要启动的Activity正处于栈的顶端,则重复利用原有的Activity,不再创建新的实例。

三、singleTask

指定MainActivity和AnotherActivity的launchMode均为singleTask。

重复之前的操作,结果如下:

MainActivity: com.example.liuwei.myapplication.MainActivity@430902d0
AnotherActivity: com.example.liuwei.myapplication.AnotherActivity@430aae90
MainActivity:onNewIntent()
AnotherActivity: com.example.liuwei.myapplication.AnotherActivity@430b7d30
MainActivity:onNewIntent()
AnotherActivity: com.example.liuwei.myapplication.AnotherActivity@430c3bc0


MainActivity的实例只会创建一次,之后都是重用之前的实例,而AnotherActivity每次都会创建新的实例。

过程如下:

第一次创建一个MainActivity的实例;

然后创建一个AnotherActivity的实例;

再次进入MainActivity时,已经存在实例,直接使用,但是这时候会将栈顶MainActivity实例之后的所有activity出栈;

再次进入AnotherActivity时,已经找不到AnotherActivity的实例,无法复用,只能创建一个新的AnotherActivity的实例了。

在singleTask模式中,如果发现已经有activity的实例,则复用该实例,但此实例之上的其他实例都会出栈。

四、singleInstance

指定MainActivity和AnotherActivity的launchMode为singleInstance。重复之前的操作,结果如下:

MainActivity: com.example.liuwei.myapplication.MainActivity@43096180
AnotherActivity: com.example.liuwei.myapplication.AnotherActivity@430b0d80
MainActivity:onNewIntent()
AnotherActivity:onNewIntent()
MainActivity:onNewIntent()
AnotherActivity:onNewIntent()


MainActivity和AnotherActivity分别创建了一个实例,之后都是在复用之前创建的实例。点击返回键,两次就退出整个APP。

查阅资料发现,MainActivity和AnotherActivity的实例分别位于两个不同的栈中,栈中有实例的时候,直接复用实例。

指定为singleInstance的activity,创建时会进入一个新的栈并独占该栈,之后不会再创建实例,而是直接使用之前栈中的实例,除非该实例已经被销毁(比如执行了返回)。而新创建的其他activity的实例会进入到其他栈中,不会进入指定为singleInstance的activity创建的栈中。

五、onNewIntent(Intent intent)的调用时机

在上述代码中,可以看到,每次重用activity实例的时候,都会调用onNewIntent()。

重用实例的生命周期如下:

onNewIntent() –> onRestar() –> onStart() –> onResume()

注意:重用实例时如果涉及到通过Intent传递参数,那么在onNewIntent中一定执行一次setIntent(intent),否则会导致通过getInent()拿到的intent是旧数据,而不是最新的参数。

Note that getIntent() still returns the original Intent. You can use setIntent(Intent) to update it to this new Intent.
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: