Android之Activity LaunchMode
来源:互联网 发布:最新在线报名系统源码 编辑:程序博客网 时间:2024/05/22 13:07
背景:
在众多Activity开发中,有可能是自己应用之间的Activity跳转,可能希望跳转到原来某个Activity实例,而不是产生大量重复的Activity实例。
这种需求需要通过配置Activity的LaunchMode来实现。
Activity有四种加载模式:
1.standard(标准模式,此项是默认的加载模式)
在此种模式情况下的Activity会每次都生成新的实例
我们首先定义了A这个Activity,然后它的内容如下:
import android.app.Activity;import android.content.Intent;import android.os.Bundle;import android.view.View;import android.view.View.OnClickListener;import android.widget.Button;import android.widget.TextView;public class A extends Activity implements OnClickListener {private TextView textView01;private Button btn01;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_a);textView01 = (TextView) findViewById(R.id.tv_01);btn01 = (Button) findViewById(R.id.button1);btn01.setOnClickListener(this);//获取当前Activity的任务栈IDint taskID = A.this.getTaskId();//获取当前Activity实例的详细信息String objectMsg = A.this.toString();//将信息输出到屏幕上textView01.setText("当前任务栈ID:" + taskID + "\r\n" + "当前Activity实例信息:"+ objectMsg);}@Overridepublic void onClick(View v) {switch (v.getId()) {case R.id.button1://开始跳转ActivityIntent intent = new Intent(A.this, A.class);startActivity(intent);break;default:break;}}}
观察发现:这三个A同属于一个任务栈,因为栈的ID都相同,但是他们的实例名称都不一样,说明这个任务栈中现在已经存在了三个不同的A实例;如果此时点击手机上的《返回》按键,那么需要连续点击三次才能退出程序。
将以上总结为流程图如下:
2.singleTop模式
在此种模式下,
如果A在任务栈顶,那么A跳转到A将不生成新的实例,直接跳转到现在的栈顶A;
如果A不在任务栈顶,那么其他的Activity去跳转到A,将生成新的A实例;
我们在代码中定义两个Activity,分别是A和B,以上是这两个Activity的定义,其中A的launchMode属性被设置为singleTop。
import android.app.Activity;import android.content.Intent;import android.os.Bundle;import android.view.View;import android.view.View.OnClickListener;import android.widget.Button;import android.widget.TextView;public class A extends Activity implements OnClickListener {private TextView textView01;private Button btn01;private Button btn02;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_a);textView01 = (TextView) findViewById(R.id.tv_01);btn01 = (Button) findViewById(R.id.button1);btn01.setOnClickListener(this);btn02 = (Button) findViewById(R.id.button2);btn02.setOnClickListener(this);//获取当前Activity的任务栈IDint taskID = A.this.getTaskId();//获取当前Activity实例的详细信息String objectMsg = A.this.toString();//将信息输出到屏幕上textView01.setText("当前任务栈ID:" + taskID + "\r\n" + "当前Activity实例信息:"+ objectMsg);}@Overridepublic void onClick(View v) {switch (v.getId()) {case R.id.button1://A--->AIntent intent01 = new Intent(A.this, A.class);startActivity(intent01);break;case R.id.button2://A---->BIntent intent02 = new Intent(A.this, B.class);startActivity(intent02);break;default:break;}}}
import android.app.Activity;import android.content.Intent;import android.os.Bundle;import android.view.View;import android.view.View.OnClickListener;import android.widget.Button;import android.widget.TextView;public class B extends Activity implements OnClickListener {private TextView textView01;private Button btn01;private Button btn02;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_a);textView01 = (TextView) findViewById(R.id.tv_01);btn01 = (Button) findViewById(R.id.button1);btn01.setOnClickListener(this);btn02 = (Button) findViewById(R.id.button2);btn02.setOnClickListener(this);//获取当前Activity的任务栈IDint taskID = B.this.getTaskId();//获取当前Activity实例的详细信息String objectMsg = B.this.toString();//将信息输出到屏幕上textView01.setText("当前任务栈ID:" + taskID + "\r\n" + "当前Activity实例信息:"+ objectMsg);}@Overridepublic void onClick(View v) {switch (v.getId()) {case R.id.button1://B--->AIntent intent01 = new Intent(B.this, A.class);startActivity(intent01);break;case R.id.button2://B---->BIntent intent02 = new Intent(B.this, B.class);startActivity(intent02);break;default:break;}}}
在程序运行后,我们点击跳转到A,界面不会有任何变化,说明当A在任务栈顶时,你发送跳转到A的Intent,那么这个Intent会发送给栈顶的A实例;
以下三张图片展示的流程是A---->B---->A:
观察发现:这三个Activity实例是不同的实例,但是他们同属一个任务栈,因为他们的任务栈ID相同;我们这里可以很明显的发现,当B在栈顶的时候,跳转到A,会生成新的A实例。
将以上总结为流程图如下:
3.singleTask模式
在此种模式,任务栈中只能有一个A实例,不管它在任务栈的什么位置;
这里我们应当注意:当A在栈顶时,直接跳转到A实例;当A不在栈顶时,将会发生的事情是,在A之上的所有Activity实例被弹出任务栈,直至A到达栈顶。
本次仍然沿用上一次的代码,只是在manifest中将A的launchMode配置为singleTask,在B中添加一个Button跳转到C,然后C中只有一个按钮,这个按钮的作用是跳转到A。
以下四张图片展示了A---->B---->C---->A:
观察以上结果我们可以发现:总共有三个实例,A、B、C各一个,当C在栈顶的时候,跳转到A,我们会返现,Intent会直接发送到栈底的A实例,并且将B、C两个实例弹栈。
将以上总结为流程图如下:
4.singleInstance模式
此Activity加载模式是为了解决这样一类问题:
在同一App中,当有一个Activity需要被多个Activity共享(即是多个Activity可以跳转到这个Activity),那么我们肯定希望此Activity长期处于Alive状态,并且是同一个实例(这样更能节省手机资源),但是同一app中,所有的Activity实例都在同一个任务栈中,我们会发现,经常性的压栈和弹栈使我们无法确定此Activity会在什么时候被弹栈销毁掉了,这个时候我们可以通过将此Activity的加载模式设置为singleInstance来满足这样的需求,当设置为此模式后,此Activity被单独在一个任务栈中维护,而不受主任务栈中频繁的压栈和弹栈操作的影响。
其实写到这个地方我觉得文字的表现力始终不及图形,首先我们来看一下,将B的launchmode设置为singleInstance,然后再来分析以下的图片结果:
分析以上结果我们会发现:B实例的任务栈ID,与A实例所在的任务栈ID不相同,说明他们处于不同的任务栈中;
并且这只是一种情况,实际这里有好几种情况,我将其总结到下面这张图中,希望能够对读者真的产生帮助;
写这篇文章的时候我想起了古人的一句话,纸上得来终觉浅,绝知此事要躬行,网上流行一篇讲LaunchMode的文章,全是用蓝色的图解,实际上我很受益于这篇文章,但是当我写这篇文章的时候我发现“我认为以前的我完全懂了”是不全面的,我对LauchMode似乎有了新的认识,感谢实践!!!
下面来本篇最后一张我绘的流程图:
例行公事,把代码链接放这里:
Android Activity LaunchMode
- Android之Activity LaunchMode
- Android基础之Activity launchMode详解
- Android开发之Activity launchMode启动模式
- Android之Activity(三)Task和LaunchMode
- activity之launchMode
- Android Activity LaunchMode 验证
- Android Activity的launchMode
- Android Activity launchMode Test
- android activity launchmode
- android activity launchmode
- Android Activity launchMode研究
- Android Activity的LaunchMode
- android Activity launchMode
- Android Activity LaunchMode
- Activity的android:launchMode
- Android Activity的LaunchMode
- [Android基础]Android之android:launchMode(Activity启动模式)
- Android Activity之launchMode四种加载方式
- 盒子模型与定位
- 第一章 笔记
- 单例模式
- [基本实验] 预编译语句的防御作用
- 黄洁:Intel Spark应用优化和实践经验
- Android之Activity LaunchMode
- hdu 4291(矩阵快速幂 + 循环节)
- 浓浓新华情 温暖大家庭
- 软考总计之白盒测试中的覆盖
- cc1plus.exe: out of memory allocating 3355443200 bytes
- [Java]交换排序
- 【AOP】借助容器将服务与代理类分离
- leetcode Maximum Gap
- 二叉树的遍历(前序+中序+后序)