日本黄色一级经典视频|伊人久久精品视频|亚洲黄色色周成人视频九九九|av免费网址黄色小短片|黄色Av无码亚洲成年人|亚洲1区2区3区无码|真人黄片免费观看|无码一级小说欧美日免费三级|日韩中文字幕91在线看|精品久久久无码中文字幕边打电话

當(dāng)前位置:首頁(yè) > 芯聞號(hào) > 充電吧
[導(dǎo)讀]做項(xiàng)目到現(xiàn)在都一直沒(méi)有理解LaunchMode有什么用,或許根本就沒(méi)真正花心思去看,所以今天把這部分整理下?! ≡O(shè)置Activity的LaunchMode屬性可以決定這個(gè)Activity是和當(dāng)前Tas

做項(xiàng)目到現(xiàn)在都一直沒(méi)有理解LaunchMode有什么用,或許根本就沒(méi)真正花心思去看,所以今天把這部分整理下。

  設(shè)置Activity的LaunchMode屬性可以決定這個(gè)Activity是和當(dāng)前Task保持關(guān)聯(lián),還是說(shuō)每次運(yùn)行這個(gè)Activity是新建一個(gè)實(shí)例,還是保持單例。

  Task和Back Stack簡(jiǎn)介

  task是一組Activities的集合,一組Activities被Stack(back stack)所管理。

  在一個(gè)應(yīng)用中,有3個(gè)activities,分別是activity1,activity2,activity3,首先activity1被start,此時(shí),如果應(yīng)用沒(méi)有創(chuàng)建task則創(chuàng)建,并把a(bǔ)ctivity1壓入棧頂,activity1觸發(fā)onCreate->onStart->onResume。

  

  接著activity1轉(zhuǎn)向到activity2時(shí),activity1先觸發(fā)onPause,activity2觸發(fā)onCreate->onStart->onResume,然后activity1觸發(fā)onPause->onStop,activity2壓入棧頂。

  

  以此類推,activity2轉(zhuǎn)向activity3也是一樣的步驟。那么當(dāng)前棧頂是activity3。

  

  當(dāng)我們按下手機(jī)上的返回鍵時(shí),棧頂?shù)腶ctivity3觸發(fā)onPause,activity2需要從狀態(tài)stop到pause,所以觸發(fā)了onPause->onStart->onResume,activity3觸發(fā)onStop->onDestory,因?yàn)閍ctivity3從棧頂彈出,所以觸發(fā)onDestory,此時(shí),activity2在棧頂。

  

  如果繼續(xù)按返回鍵,當(dāng)前棧頂?shù)腶ctivity彈出并被destory,直到home界面。當(dāng)所有的activity都彈出了,這個(gè)task也就消亡了。

  當(dāng)開始一個(gè)新的task時(shí),前一個(gè)task被設(shè)置為后臺(tái),在后臺(tái),所有的activity都處理stop狀態(tài),但是back stack保留了所有后臺(tái)activity的狀態(tài)信息,只是丟失了焦點(diǎn)。

  反復(fù)的在兩個(gè)activity之間切換,activity會(huì)產(chǎn)生多個(gè)獨(dú)立的實(shí)例。

  

  查閱有關(guān)Activity生命周期更多說(shuō)明。

  兩種方式設(shè)置LaunchMode屬性

  1.  在 manifest文件中設(shè)置


  2.  使用Intent flags設(shè)置

Intent?intent?=?new?Intent();
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setClass(ActivityA.this,?ActivityB.class);
startActivity(intent);

  四種LaunchMode說(shuō)明

  standard

   不做任何設(shè)置,默認(rèn)模式就是standard,activity在每次start時(shí),都會(huì)有一個(gè)新的實(shí)例被task管理。下面看下代碼實(shí)例。

//ActivityA.java
Intent?intent?=?new?Intent();
intent.setClass(ActivityA.this,?ActivityB.class);
startActivity(intent);

//ActivityB.java
Intent?intent?=?new?Intent();
intent.setClass(ActivityB.this,?ActivityA.class);
startActivity(intent);

?

 操作1:在ActivityA(藍(lán))和ActivityB(綠)之間重復(fù)切換,按返回鍵推到home界面。

  可以發(fā)現(xiàn)(藍(lán)色86和綠色79的taskID)ActivityA和ActivityB都在同一個(gè)task,并且每次resume的實(shí)例都是不一樣的。這說(shuō)明在一個(gè)activity可以有多個(gè)實(shí)例在同一個(gè)task中。

  在按返回按鍵時(shí),將依次彈出stack。

??singleTop

  和standard一樣,可以多次實(shí)例,但,如果處于當(dāng)前棧頂并且接受到一個(gè)與當(dāng)前activity一樣類型的intent,那么不會(huì)創(chuàng)建一個(gè)新實(shí)例,而是觸發(fā)onNewIntent()事件。

//ActivityA.java
Intent?intent?=?new?Intent();
intent.setClass(ActivityA.this,?ActivityA.class);
startActivity(intent);

@Override
protected?void?onNewIntent(Intent?intent)?{
????logger.d("onNewIntent?"?+?this.hashCode()?+?"?taskID?"
????????????????+?this.getTaskId());
????super.onNewIntent(intent);
}


操作1:點(diǎn)擊ActivityA上的按鈕

  發(fā)現(xiàn)當(dāng)點(diǎn)擊按鈕是ActivityA->onPause->onNewIntent->onResume,沒(méi)有新建新的實(shí)例(藍(lán)62)。

  這個(gè)模式在這個(gè)場(chǎng)景下比較有用,比如:如果有一個(gè)其他的應(yīng)用想啟動(dòng)你的Activity(launch mode為singleTop),而你當(dāng)前的Activity正好在棧頂,那么就會(huì)調(diào)用到onNewIntent方法。原文貼上:If an instance of the activity already exists at the top of the current task, the system routes the intent to that instance through a call to its?onNewIntent()?method。

? singleTask

  系統(tǒng)會(huì)創(chuàng)建一個(gè)新task(如果沒(méi)有啟動(dòng)應(yīng)用)和一個(gè)activity新實(shí)例在新task根部,然后,如果activity實(shí)例已經(jīng)存在單獨(dú)的task中,系統(tǒng)會(huì)調(diào)用已經(jīng)存在activity的?onNewIntent()方法,而不是存在新實(shí)例,僅有一個(gè)activity實(shí)例同時(shí)存在。運(yùn)用實(shí)例:瀏覽器主界面。不管跳轉(zhuǎn)多少頁(yè)面,主界面只啟動(dòng)一次,其余都走onNewIntent,并清空主界面上的其他頁(yè)面。

              

?操作1:ActivityA->ActivityB->ActivityC->ActivityA->ActivityB->ActivityC

  

?  可以看到,當(dāng)再次進(jìn)入ActivityB時(shí),沒(méi)有onCreate,而是onNewIntent(綠55)。

   這里我們也可以發(fā)現(xiàn)一個(gè)現(xiàn)象,當(dāng)在調(diào)用到ActivityB的onNewIntent時(shí),之前的ActivityA和ActivityC都調(diào)用了onDestory。也就是說(shuō),系統(tǒng)發(fā)現(xiàn)棧中存在ActivityB的實(shí)例時(shí),ActivityA和ActivityB都彈棧了。

   列出Log日志(這里設(shè)ActivityA的LaunchMode為singleTask),ActivityB和ActivityC都在onNewIntent前后調(diào)用了onDestory。

  

  singleInstance

    和singleTask相似,除了系統(tǒng)不會(huì)讓其他的activities運(yùn)行在所有持有的task實(shí)例中,這個(gè)activity是獨(dú)立的,并且task中的成員只有它,任何其他activities運(yùn)行這個(gè)activity都將打開一個(gè)獨(dú)立的task。實(shí)例運(yùn)用:適合與程序分離的頁(yè)面,如鬧鈴提醒。

                  

?

 操作1:ActivityA->ActivityB->ActivityA

  

?

  可以發(fā)現(xiàn),兩個(gè)Activity是在不同的Task中,其次,當(dāng)調(diào)用到onNewIntent時(shí),ActivityB沒(méi)有被Destory,互不干涉。

  操作2:ActivityA->ActivityB->ActivityC,按返回鍵

  

?

  圖解:

  

  剛進(jìn)入應(yīng)用,創(chuàng)建TaskA,ActivityA為棧頂,從ActivityA到ActivityB,ActivityB進(jìn)入TaskB(如果再次進(jìn)入ActivityB,則不創(chuàng)建Task,調(diào)用onNewIntent),此時(shí)TaskB中的ActivityB為棧頂,從ActitivyB到ActivityC,ActivityC為棧頂。

  一直按返回鍵,先從TaskA中依次將Activity彈出,然后再?gòu)腡askB中將ActiviyB彈出。ActiviyC->ActivityA->ActivityB。

  這里分析一個(gè)問(wèn)題,瀏覽器的LaunchMode為singleTask,所以如果當(dāng)你點(diǎn)擊一個(gè)連接下載文件時(shí)(由一個(gè)activity來(lái)處理下載,launchmode為standard),如果再次進(jìn)入瀏覽器,那么下載頁(yè)面就被Destory了,那么這里我們可以把下載頁(yè)面LaunchMode設(shè)置為singleInstance可以解決這個(gè)問(wèn)題。

  Affinity定義

  Affinity更像是表明了activity屬于哪個(gè)task,默認(rèn)情況下,應(yīng)用所有的activities都有相同的affinity,所以都是在相同的task中。然后你可以編輯默認(rèn)的affinity。Activities定義在不同的應(yīng)用可以共享一個(gè)affinity,或者activities定義在相同的應(yīng)用中可以被不同的affinities所關(guān)聯(lián)。

  你可以編輯在activity的taskAffinity屬性。

  ?先看看兩種不同的情況下affinity的表現(xiàn):

當(dāng)運(yùn)行一個(gè)activity包含了FLAG_ACTIVITY_NEW_TASK標(biāo)記

//ActivityA.java
Intent?intent?=?new?Intent();????
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setClass(ActivityA.this,?ActivityB.class);
startActivity(intent);

         

操作1:不同的affinity值,ActivityA->ActivityB

如果已經(jīng)存在相同affinity,那么新activity運(yùn)行在這個(gè)task中,否則,系統(tǒng)創(chuàng)建新task。

操作2:相同的affinity值,ActivityA->ActivityB

         

可以看出ActivityA和ActivityB都運(yùn)行在同一個(gè)task中。

?

當(dāng)Activity的allowTaskReparenting的屬性設(shè)為'true'

  使用來(lái)表示是否允許activity重新附屬其他Task,還是舉例說(shuō)明吧。

  有兩個(gè)應(yīng)用,Demo1和Demo2,Demo1中有2個(gè)Activity(ActivityA,ActivityC),ActivityA可以轉(zhuǎn)向到ActivityC,Demo2中有一個(gè)Activity(ActivityB),也可以轉(zhuǎn)向到ActivityC。

  操作1:設(shè)置ActivityC的allowTaskReparenting屬性為true。

      運(yùn)行Demo2,轉(zhuǎn)向到ActivityC,在ActivityC中打印信息,返回到HOME界面,運(yùn)行Demo1。

//Demo1?
//ActivityA.java
Intent?intent?=?new?Intent();
intent.setClass(ActivityA.this,?ActivityC.class);
startActivity(intent);

//ActivityC.java
tv.setText(ActivityC.this.toString());

//Demo2
//ActivityB.java
Intent?intent?=?new?Intent();
intent.setClassName("com.android.demo","com.android.demo.activity.ActivityC");
ActivityB.this.startActivity(intent);

//Demo1

//Demo2

?運(yùn)行結(jié)果:(黃色Demo1,綠色Demo2)

  

?  ?ActivityB轉(zhuǎn)向到ActivityC,此時(shí)ActivityC就關(guān)聯(lián)到Demo2的Task中,TaskID都為231。在運(yùn)行Demo1時(shí),看到是ActivityC而不是ActivityA。當(dāng)再次進(jìn)入Demo2時(shí)就看不到ActivityC了。

  操作2:將ActivityC的taskAffinity設(shè)置為"com.android.demo.activityc"。

      運(yùn)行Demo2,轉(zhuǎn)向到ActivityC,在ActivityC中打印信息,返回到HOME界面,運(yùn)行Demo1。

//Demo1

?運(yùn)行結(jié)果:

  

?  從結(jié)果中可以看出,Demo1和Demo2都擁有ActivityC,也就是說(shuō)有2個(gè)Task里存在ActivityC,分別被Demo1和Demo2所使用。

  操作3:將ActivityC和ActivityB的taskAffinity都設(shè)為"com.android.demo.activityc"。

      運(yùn)行Demo2,轉(zhuǎn)向到ActivityC,在ActivityC中打印信息,返回到HOME界面,運(yùn)行Demo1。

//Demo2            //Demo1        

  運(yùn)行結(jié)果:

  

?  和操作1相反,再進(jìn)入Demo2時(shí)看到是ActivityC,進(jìn)入Demo1都是看到ActivityA。

?

  寫到最后越來(lái)越崩潰了,如果有什么地方寫的不對(duì)或不清楚請(qǐng)指明。

  轉(zhuǎn)帖請(qǐng)說(shuō)明原文出處:http://www.cnblogs.com/SteveMing/archive/2012/04/24/2459575.html?

另一篇 圖文并茂?http://www.androidchina.net/3173.html?

兩種設(shè)置方式:

1) XML



2)在java代碼中設(shè)置intent.setFlags()


Intent?intent?=?new?Intent();
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setClass(this,ActivitySub.ckass);
startActivity(intent);
本站聲明: 本文章由作者或相關(guān)機(jī)構(gòu)授權(quán)發(fā)布,目的在于傳遞更多信息,并不代表本站贊同其觀點(diǎn),本站亦不保證或承諾內(nèi)容真實(shí)性等。需要轉(zhuǎn)載請(qǐng)聯(lián)系該專欄作者,如若文章內(nèi)容侵犯您的權(quán)益,請(qǐng)及時(shí)聯(lián)系本站刪除( 郵箱:macysun@21ic.com )。
換一批
延伸閱讀
關(guān)閉