????????該部分主要記錄Activity,Service缎讼,BroadcastReceiver澎语,ContentProvider的基本知識(shí)和使用,關(guān)于高級(jí)部分后續(xù)將來不知道哪天的哪天可能或許會(huì)再寫一篇文章來記錄
Activity
????????對(duì)于Activity
的地位不再過多敘述萍膛,是一個(gè)應(yīng)用向外界展示信息所必須的一個(gè)組件吭服。
生命周期
經(jīng)典的生命周期圖
關(guān)于各個(gè)周期:
onCreate()
Activity
被創(chuàng)建時(shí)首先調(diào)用。onStart()
Activity
界面出現(xiàn)時(shí)蝗罗。onResume()
Activity
被完全顯示艇棕,可以與用戶交互時(shí)。onPause()
Activity
失去焦點(diǎn)但仍對(duì)用戶可見串塑,如顯示了一個(gè)彈窗沼琉。onStop()
Activity
被其他Activity
完全遮擋,對(duì)用戶不可見桩匪,如跳轉(zhuǎn)到新的Activity
或者退出程序打瘪,直接鎖屏。onDestory()
Activity
被銷毀時(shí)調(diào)用傻昙。onRestart()
Activity
對(duì)象再次被啟動(dòng)時(shí)調(diào)用闺骚。
-
正常啟動(dòng)生命周期
onCreate()->onStart()->onResume()->activity runing->onPause()->onStop()->onDestory()
-
被遮擋但可見不可操作又取消遮擋
onPause()->activity stop->onResume()->activity runing
-
不可見變?yōu)榭梢?/strong>
onPause()->onStop()->activity stop->onRestart()->onStart()->onResume()->activity runing
Activity示例代碼
啟動(dòng)模式
-
standard
標(biāo)準(zhǔn)模式。
Activity
默認(rèn)的啟動(dòng)模式妆档,Activity
每次啟動(dòng)都會(huì)在棧頂創(chuàng)建一個(gè)新的Activity
實(shí)例僻爽。
如果Activity
已經(jīng)位于棧頂,則Activity
啟動(dòng)時(shí)也將會(huì)重新創(chuàng)建新的實(shí)例贾惦。 -
singleTop
棧頂復(fù)用模式胸梆。
Activity
啟動(dòng)時(shí)判斷其是否在棧頂,如果在棧頂則直接復(fù)用须板,并且回調(diào)onNewIntent()方法乳绕,不會(huì)再重新創(chuàng)建新的Activity
實(shí)例。
如果未處于棧頂則重新創(chuàng)建新的Activity
實(shí)例逼纸。 -
singleTask
棧內(nèi)復(fù)用模式洋措。
1.Activity
被首次創(chuàng)建時(shí)首先檢測(cè)AndroidManifest.xml中相應(yīng)<activity />
節(jié)點(diǎn)下的android:taskAffinity="..."
屬性是否存在,如果不存在則在啟動(dòng)該Activity
的Activity
所在的任務(wù)棧上新建該Activity
杰刽,如果屬性值存在并與某一任務(wù)棧相同則在該任務(wù)棧中新建該Activity
菠发,如果屬性名與已存在的任務(wù)棧都不相同則新建與屬性名相同的任務(wù)棧并新建該Activity
王滤。
2.Activity
非首次創(chuàng)建啟動(dòng)時(shí)檢測(cè)活動(dòng)棧中是否已存在Activity
實(shí)例,如果存在則直接復(fù)用并將其之上的所有Activity
實(shí)例全部出棧滓鸠,并且回調(diào)onNewIntent()
方法雁乡,使該Activity
處于棧頂?shù)奈恢茫绻淮嬖趧t在棧頂創(chuàng)建新的Activity實(shí)例糜俗。 -
singleInstance
單實(shí)例模式踱稍。
該模式下Activity
會(huì)啟動(dòng)一個(gè)新的任務(wù)棧來管理Activity
實(shí)例,當(dāng)從其他任務(wù)棧中啟動(dòng)該Activity
時(shí)悠抹,該Activity
所在的任務(wù)棧珠月,將會(huì)轉(zhuǎn)移到前臺(tái)。
可以在不同的程序中共享一個(gè)Activity
異常狀態(tài)
當(dāng)系統(tǒng)資源配置發(fā)生改變或者內(nèi)存不足時(shí)Activity
會(huì)被殺死楔敌。
-
系統(tǒng)配置發(fā)生改變
系統(tǒng)配置發(fā)生改變Activity
會(huì)被殺死重建啤挎,經(jīng)典場(chǎng)景就是橫豎屏切換的時(shí)候。
此時(shí)的生命周期狀態(tài)轉(zhuǎn)換:
onSaveInstanceState()->onStop()->onDestory()->onCreate()->onStart()->onRestoreInstanceState()->onResume()->activity runing
這里出現(xiàn)了兩個(gè)方法
1.onSaveInstanceState()
當(dāng)Activity被異常狀態(tài)下終止時(shí)會(huì)調(diào)用該方法來將Activity
終止前的相關(guān)狀態(tài)保存在Bundle中用來重建時(shí)恢復(fù)狀態(tài)
2.onRestoreInstanceState()
當(dāng)Activity被在異常狀態(tài)下重建時(shí)回調(diào)該方法卵凑,該方法中的Bundle里保存了異常終止前Activity相關(guān)狀態(tài)庆聘。
此時(shí)可以通過在AndroidManifestl.xml文件中相應(yīng)的activity節(jié)點(diǎn)下配置android:configChanges="orientation|keyboardHidden"
屬性來禁止相應(yīng)的配置改變時(shí)activity的銷毀重建。但是此時(shí)會(huì)回調(diào)Activity中的onConfigurationChanged()
方法勺卢。 -
系統(tǒng)內(nèi)存不足
當(dāng)系統(tǒng)內(nèi)存不足時(shí)伙判,系統(tǒng)將會(huì)根據(jù)activity優(yōu)先級(jí)的高低,優(yōu)先殺死優(yōu)先級(jí)低的Activity
黑忱。
1.此時(shí)的生命周期:
activity runing->onPause()->onStop()->onDestory()
2.優(yōu)先級(jí):
前臺(tái)Activity
>可見非前臺(tái)Activity
>后臺(tái)Activity
Service
Service
是一個(gè)可以在后臺(tái)執(zhí)行長(zhǎng)時(shí)間運(yùn)行操作而不提供用戶界面的應(yīng)用組件澳腹。服務(wù)可由其他應(yīng)用組件啟動(dòng),而且即使用戶切換到其他應(yīng)用杨何,服務(wù)仍將在后臺(tái)繼續(xù)運(yùn)行酱塔。 此外,組件可以綁定到服務(wù)危虱,以與之進(jìn)行交互羊娃,甚至是執(zhí)行進(jìn)程間通信 (IPC)。 例如埃跷,服務(wù)可以處理網(wǎng)絡(luò)事務(wù)蕊玷、播放音樂,執(zhí)行文件 I/O 或與內(nèi)容提供程序交互弥雹,而所有這一切均可在后臺(tái)進(jìn)行垃帅。
生命周期
由上圖可知
Service
有兩種生命周期,分別對(duì)應(yīng)著Service
的兩種形式
Service形式
啟動(dòng)形式
????????如果應(yīng)用組件通過startService()
方法來啟動(dòng)服務(wù)時(shí)剪勿,該服務(wù)即處于啟動(dòng)狀態(tài)贸诚。
????????服務(wù)處于啟動(dòng)狀態(tài)后將開始在后臺(tái)無期限運(yùn)行,組件被銷毀也不會(huì)影響服務(wù)的運(yùn)行狀態(tài)。并且啟動(dòng)形式的服務(wù)與組件之間沒有很大的關(guān)聯(lián)并不會(huì)將服務(wù)結(jié)果返回給組件酱固。如通過啟動(dòng)一個(gè)服務(wù)來下載網(wǎng)絡(luò)資源械念。
????????啟動(dòng)的服務(wù)可以在組件中通過stopService()
或者在服務(wù)內(nèi)部通過stopSelf()
方法來停止服務(wù)。
onCreate()
服務(wù)首次被創(chuàng)建時(shí)运悲,系統(tǒng)將會(huì)調(diào)用該方法來進(jìn)行相關(guān)設(shè)置龄减。該方法只有在服務(wù)被創(chuàng)建時(shí)調(diào)用,如果服務(wù)已在運(yùn)行班眯,則該方法不會(huì)調(diào)用希停。
onStartCommand()
組件通過調(diào)用startService()
方法啟動(dòng)服務(wù)時(shí),該方法將會(huì)被調(diào)用署隘。該方法被調(diào)用后服務(wù)將會(huì)啟動(dòng)并將在后臺(tái)無限期運(yùn)行宠能,并且需要調(diào)用stopService()
或者stopSelf()
方法來停止服務(wù)。每次調(diào)用startService()
方法都會(huì)該方法都將會(huì)被調(diào)用定踱。在綁定狀態(tài)下不需要實(shí)現(xiàn)這個(gè)方法
onDestory()
當(dāng)服務(wù)不再使用并將被銷毀時(shí),系統(tǒng)將調(diào)用該方法恃鞋。來清理所有的資源崖媚,如線程、監(jiān)聽器恤浪、接收器等畅哑。
onBind()
無論啟動(dòng)服務(wù)還是綁定服務(wù)該方法必須實(shí)現(xiàn)。如果組件通過bindSercie()
方法綁定服務(wù)水由,則系統(tǒng)將調(diào)用該方法荠呐,該方法的最后需要一個(gè)IBinder
接口的實(shí)現(xiàn)類,用來供組件與服務(wù)進(jìn)行通信砂客。如果組件通過startService()
方法來啟動(dòng)服務(wù)則該方法返回null
泥张。
-
啟動(dòng)形式生命周期
onCreate()->onStartCommand()->Service runing->onDestroy()
啟動(dòng)形式服務(wù)示例代碼
綁定形式
????????如果應(yīng)用組件通過bindService()
方法綁定到服務(wù)時(shí),該服務(wù)即處于綁定狀態(tài)鞠值。組件與服務(wù)綁定后媚创,綁定服務(wù)提供了一個(gè)客戶端-服務(wù)器接口,允許組件與服務(wù)進(jìn)行交互彤恶、發(fā)送請(qǐng)求钞钙、獲取結(jié)果,甚至是利用進(jìn)程間通信(IPC)跨進(jìn)程執(zhí)行這些操作声离。通俗來講就是綁定服務(wù)后組件和服務(wù)就可以進(jìn)行方法調(diào)用芒炼,增強(qiáng)兩者之間的操作性。
????????組件與服務(wù)綁定后术徊,服務(wù)開始運(yùn)行本刽,一個(gè)服務(wù)可以綁定多個(gè)組件,當(dāng)綁定形式的服務(wù)與任何一個(gè)組件都失去綁定后該服務(wù)會(huì)被銷毀。
????????綁定的服務(wù)可以在組件中通過stopService()
或者在服務(wù)內(nèi)部通過stopSelf()
方法來停止服務(wù)盅安。
onCreate()
服務(wù)首次被創(chuàng)建時(shí)唤锉,系統(tǒng)將會(huì)調(diào)用該方法來進(jìn)行相關(guān)設(shè)置。該方法只有在服務(wù)被創(chuàng)建時(shí)調(diào)用别瞭,如果服務(wù)已在運(yùn)行窿祥,則該方法不會(huì)調(diào)用。
onBind()
無論啟動(dòng)服務(wù)還是綁定服務(wù)該方法必須實(shí)現(xiàn)蝙寨。如果組件通過bindSercie()
方法綁定服務(wù)晒衩,則系統(tǒng)將調(diào)用該方法,該方法的最后需要一個(gè)IBinder
接口的實(shí)現(xiàn)類墙歪,用來供組件與服務(wù)進(jìn)行通信听系。如果組件通過startService()
方法來啟動(dòng)服務(wù)則該方法返回null
。
onUnbind()
綁定狀態(tài)的服務(wù)被銷毀時(shí)調(diào)用
onDestory()
當(dāng)服務(wù)不再使用并將被銷毀時(shí)虹菲,系統(tǒng)將調(diào)用該方法靠胜。來清理所有的資源,如線程毕源、監(jiān)聽器浪漠、接收器等。
-
綁定形式生命周期
onCreate()->onBind()->Service runing->onUnbind()->onDestroy()
1霎褐、擴(kuò)展Binder類實(shí)現(xiàn)綁定服務(wù)
2址愿、使用AIDL來實(shí)現(xiàn)綁定服務(wù)
啟動(dòng)服務(wù)與綁定服務(wù)之間的轉(zhuǎn)換問題
一個(gè)服務(wù)可以同時(shí)是啟動(dòng)狀態(tài)和綁定狀態(tài)。但是系統(tǒng)只會(huì)為一個(gè)Service創(chuàng)建一個(gè)實(shí)例對(duì)象冻璃,所以啟動(dòng)服務(wù)和綁定服務(wù)操作的都是同一個(gè)Service實(shí)例响谓,但是由于兩者的執(zhí)行順序不同將會(huì)出現(xiàn)下列兩種情況:
-
先綁定服務(wù)后啟動(dòng)服務(wù)
狀態(tài)變化:綁定服務(wù)模式->啟動(dòng)服務(wù)模式
綁定服務(wù)將會(huì)轉(zhuǎn)換為啟動(dòng)服務(wù)運(yùn)行,此時(shí)如果之前綁定服務(wù)的組件被銷毀也不影響服務(wù)的運(yùn)行省艳。服務(wù)將會(huì)按照啟動(dòng)服務(wù)的模式運(yùn)行娘纷。 -
先啟動(dòng)服務(wù)后綁定服務(wù)
狀態(tài)變化:?jiǎn)?dòng)服務(wù)模式
服務(wù)不會(huì)轉(zhuǎn)換為綁定服務(wù),仍然以啟動(dòng)服務(wù)模式運(yùn)行跋炕。
但是還是會(huì)與組件綁定失驶,當(dāng)與組件解除綁定之后,對(duì)服務(wù)無影響枣购。
服務(wù)使用注意事項(xiàng)
注意:服務(wù)在其托管進(jìn)程的主線程中運(yùn)行嬉探,它既不創(chuàng)建自己的線程,也不在單獨(dú)的進(jìn)程中運(yùn)行(除非另行指定)棉圈。 這意味著涩堤,如果服務(wù)將執(zhí)行任何 CPU 密集型工作或阻止性操作(例如 MP3 播放或聯(lián)網(wǎng)),則應(yīng)在服務(wù)內(nèi)創(chuàng)建新線程來完成這項(xiàng)工作分瘾。通過使用單獨(dú)的線程胎围,可以降低發(fā)生“應(yīng)用無響應(yīng)”(ANR) 錯(cuò)誤的風(fēng)險(xiǎn),而應(yīng)用的主線程仍可繼續(xù)專注于運(yùn)行用戶與 Activity 之間的交互。
由此可知服務(wù)是托管在進(jìn)程的主線程中運(yùn)行白魂,所以如果服務(wù)要進(jìn)行耗時(shí)或者阻塞性操作汽纤,則應(yīng)該在服務(wù)內(nèi)創(chuàng)建新的線程來完成工作。
-
建議使用:IntentService
IntentService
是繼承并處理異步請(qǐng)求的一個(gè)類福荸,在IntentService
內(nèi)有一個(gè)工作線程來處理耗時(shí)操作
保證服務(wù)不被殺死
-
因內(nèi)存資源不足被殺死
可將onStartCommand()
方法的返回值設(shè)為START_STICKY
或START_REDELIVER_INTENT
蕴坪,該值表示服務(wù)在內(nèi)存資源緊張時(shí)被殺死后,在內(nèi)存資源足夠時(shí)再恢復(fù)敬锐。
也可將Service
設(shè)置為前臺(tái)服務(wù)背传,這樣就有比較高的優(yōu)先級(jí),在內(nèi)存資源緊張時(shí)也不會(huì)被殺掉台夺。 -
用戶通過 settings -> Apps -> Running -> Stop 方式殺死Service
該方法會(huì)執(zhí)行Service
的生命周期將會(huì)調(diào)用onDestory
径玖,所以可以在onDestory()
中發(fā)送廣播重新啟動(dòng)Service
。
也可以開啟兩個(gè)服務(wù)颤介,相互監(jiān)聽梳星,相互啟動(dòng)。
onStartCommand返回值
-
START_STICKY
返回此值時(shí)Service
被系統(tǒng)kill后滚朵,系統(tǒng)將會(huì)嘗試重新創(chuàng)建Service
冤灾,并調(diào)用onStartCommand()
方法,如果在此期間沒有新的命令被傳遞到Service
則參數(shù)Intent
為null
-
START_NOTE_STICKY
返回值為該值時(shí)始绍,如果Service
被系統(tǒng)kill則系統(tǒng)不會(huì)自動(dòng)重啟該服務(wù) -
START_REDELIVEER_INTENT
返回此值時(shí)瞳购,如果Service
被系統(tǒng)kill殺死话侄,系統(tǒng)將自動(dòng)重啟該服務(wù)亏推,并重新傳遞Intent
-
START_STICKY_COMPATIBILITY
START_STICKY
的兼容版本并不保證kill后一定能重啟
系統(tǒng)默認(rèn)返回START_STICKY