国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專(zhuān)欄INFORMATION COLUMN

Android四大組件之BroadcastReceiver

plus2047 / 2759人閱讀

摘要:作為的四大組件之二,其應(yīng)用場(chǎng)景非常多。作用可以監(jiān)聽(tīng)或接收應(yīng)用或系統(tǒng)發(fā)出的廣播消息,并做出響應(yīng)。可以指定獨(dú)立的進(jìn)程四大組件都可以通過(guò)此屬性指定自己的獨(dú)立進(jìn)程。對(duì)于應(yīng)用內(nèi)廣播的動(dòng)態(tài)注冊(cè)方式,回調(diào)中的返回值是。

前言

Hi,大家好,又雙見(jiàn)面啦,上一期我們講了如何使用Activity,肯定有不少小伙伴已經(jīng)創(chuàng)建了屬于自己的FirstActivity,那么這一期我們主要為大家介紹第二個(gè)重要組件BroadcastReceiver(廣播接收器)。作為Android的四大組件之二,其應(yīng)用場(chǎng)景非常多。下面,就詳細(xì)介紹下 BroadcastReceiver 的相關(guān)知識(shí)。

1. 定義

BroadcastReceiver(廣播接收器)即廣播,是一個(gè)全局的監(jiān)聽(tīng)器。

Android 廣播分為兩個(gè)角色:廣播發(fā)送者廣播接受者

2. 作用

可以監(jiān)聽(tīng)或接收應(yīng)用 App 或系統(tǒng)發(fā)出的廣播消息,并做出響應(yīng)。

3. 應(yīng)用場(chǎng)景

同一 App 內(nèi)部的同一組件內(nèi)的消息通信(單個(gè)或多個(gè)線程之間);

同一 App 內(nèi)部的不同組件之間的消息通信(單個(gè)進(jìn)程);

同一 App 具有多個(gè)進(jìn)程的不同組件之間的消息通信;

不同 App 之間的組件之間消息通信;

Android系統(tǒng)在特定情況下與App之間的消息通信,如:網(wǎng)絡(luò)變化、電池電量、屏幕開(kāi)關(guān)等。

4. 實(shí)現(xiàn)原理

Android中的廣播使用了觀察者模式:基于消息的發(fā)布 / 訂閱事件模型,將廣播的發(fā)送者接收者解耦,使得系統(tǒng)方便集成,更易擴(kuò)展。

消息的事件模型中有三個(gè)角色:

消息訂閱者(廣播接收者)

消息發(fā)布者(廣播發(fā)送者)

消息中心(AMS,即Activity Manager Service)

具體實(shí)現(xiàn)流程如下:

廣播接收者BroadcastReceiver通過(guò)Binder機(jī)制向AMS中進(jìn)行注冊(cè);

廣播發(fā)送者通過(guò)binder機(jī)制向AMS發(fā)送廣播;

AMS查找符合相應(yīng)條件(IntentFilter/Permission等)的BroadcastReceiver,將廣播發(fā)送到BroadcastReceiver(一般情況下是Activity)相應(yīng)的消息循環(huán)隊(duì)列中;

消息循環(huán)執(zhí)行拿到此廣播,回調(diào) BroadcastReceiver 中的 onReceive() 方法。

注意:廣播發(fā)送者和廣播接受者的執(zhí)行順序是異步的,發(fā)送者不會(huì)關(guān)心有無(wú)接收者及接收者是否接收。

5. 使用步驟
5.1 自定義廣播接收者BroadcastReceiver
//繼承BroadcastReceiver
public class MyBroadcaseReceiver extends BroadcastReceiver {   
    //接收到廣播后,則自動(dòng)調(diào)用該方法    
    @Override    
    public void onReceive(Context context, Intent intent) {
    }
}

繼承 BroadcastReceivre 基類(lèi),重寫(xiě) onReceive() 方法。廣播接收器接收到相應(yīng)廣播后,會(huì)自動(dòng)回調(diào) onReceive() 方法,此方法中可與其他組件進(jìn)行交互,如發(fā)送通知、啟動(dòng)服務(wù)等。

默認(rèn)情況下,廣播接收器運(yùn)行在主線程中,所以,onReceive() 方法不能執(zhí)行耗時(shí)操作,否則會(huì)導(dǎo)致 ANR 異常。

5.2 注冊(cè)廣播接收器

廣播接收器的注冊(cè)分為兩種:靜態(tài)注冊(cè)、動(dòng)態(tài)注冊(cè)。

靜態(tài)注冊(cè):靜態(tài)注冊(cè)即在清單文件(AndroidManifest.xml)中為 BroadcastReceiver 進(jìn)行注冊(cè),使用< receiver >標(biāo)簽聲明,并在標(biāo)簽內(nèi)用 < intent-filter > 標(biāo)簽設(shè)置過(guò)濾器。這種形式的 BroadcastReceiver 的生命周期伴隨著整個(gè)應(yīng)用。如果這種方式處理的是系統(tǒng)廣播,那么不管應(yīng)用是否在運(yùn)行,該廣播接收器都能接收到該廣播。


    
        
    

android:exported ——此 BroadcastReceiver 能否接收其他 App 的發(fā)出的廣播,其默認(rèn)值是由 receiver 中有無(wú) intent-filter 決定的,如果有 intent-filter,默認(rèn)值為true,否則為false。(同樣的,activity/service中的此屬性默認(rèn)值一樣遵循此規(guī)則);
android:name —— 此 BroadcastReceiver 類(lèi)名;
android:permission ——如果設(shè)置,具有相應(yīng)權(quán)限的廣播發(fā)送方發(fā)送的廣播才能被此 BroadcastReceiver 所接收;
android:process —— BroadcastReceiver 運(yùn)行所處的進(jìn)程。默認(rèn)為 App 的進(jìn)程。可以指定獨(dú)立的進(jìn)程(Android四大組件都可以通過(guò)此屬性指定自己的獨(dú)立進(jìn)程)。

intent-filter/action ——用于指定此廣播接收器將接收的廣播類(lèi)型,本示例中給出的是用于接收網(wǎng)絡(luò)狀態(tài)改變時(shí)發(fā)出的廣播。

注冊(cè)示例:

    
            
            
    

當(dāng)此 App首次啟動(dòng)時(shí),系統(tǒng)會(huì)自動(dòng)實(shí)例化 MyBroadcaseReceiver 類(lèi),并注冊(cè)到系統(tǒng)中。

注意:Android 7.0版本開(kāi)始,對(duì)靜態(tài)注冊(cè)的廣播做了限制,導(dǎo)致靜態(tài)注冊(cè)失效。應(yīng)用無(wú)法使用清單注冊(cè)隱式廣播,仍然可以在運(yùn)行時(shí)動(dòng)態(tài)注冊(cè)這些廣播,并且可以使用清單注冊(cè)專(zhuān)門(mén)針對(duì)它們的顯式廣播。

具體可查看:https://developer.android.goo...

動(dòng)態(tài)注冊(cè):動(dòng)態(tài)注冊(cè) BroadcastReceiver 是在代碼中定義并設(shè)置好一個(gè) IntentFilter 對(duì)象,然后在需要注冊(cè)的地方調(diào)用 Context.registerReceiver() 方法,調(diào)用 Context.unregisterReceiver() 方法取消注冊(cè),此時(shí)就不需要在清單文件中注冊(cè) Receiver 了。

@Override
protected void onResume() {    
    super.onResume();    
    //1.實(shí)例化MyBroadcaseReceiver    
    MyBroadcaseReceiver myBroadcaseReceiver = new MyBroadcaseReceiver();    
    //2.設(shè)置廣播類(lèi)型    
    IntentFilter intentFilter = new IntentFilter();
    intentFilter.addAction("android.net.conn.CONNECTIVITY_CHANGE");    
    //3.動(dòng)態(tài)注冊(cè)廣播    
    registerReceiver(myBroadcaseReceiver, intentFilter);
}

@Override
protected void onDestroy() {    
    super.onDestroy();    
    //銷(xiāo)毀在onResume()中注冊(cè)的廣播    
    unregisterReceiver(mBroadcastReceiver);
}

注意:對(duì)于動(dòng)態(tài)廣播,有注冊(cè)必須得有注銷(xiāo),否知會(huì)造成內(nèi)存泄露,重復(fù)注冊(cè)、重復(fù)注銷(xiāo)也不允許。

Android 中所有與觀察者模式有關(guān)的設(shè)計(jì)中,一旦涉及到 register,必定在相應(yīng)的時(shí)機(jī)需要 unregister。

5.3 廣播發(fā)送及廣播類(lèi)型

廣播發(fā)送:廣播的“發(fā)送”與“接收”,表面上看是廣播作為 Android 廣播機(jī)制中的實(shí)體,實(shí)際上這一實(shí)體本身是并不是以所謂的”廣播“對(duì)象存在的,而是以”意圖“(Intent)去表示。定義廣播的定義本質(zhì),實(shí)際就是相應(yīng)廣播”意圖“的定義過(guò)程,然后通過(guò)廣播發(fā)送者通過(guò) sendBroadcast() 方法將此”意圖“發(fā)送出去。

廣播類(lèi)型:根據(jù)廣播的發(fā)送方式,可以將其分為以下幾種類(lèi)型

1.普通廣播(Normal Broadcast)

開(kāi)發(fā)者自身定義 intent的廣播。發(fā)送廣播使用如下:

   Intent intent = new Intent();
   //對(duì)應(yīng)BroadcastReceiver中intentFilter的action
   intent.setAction("MY_BROADCAST_ACTION");
   //發(fā)送廣播
   sendBroadcast(intent);

被注冊(cè)了的廣播接收者中注冊(cè)時(shí) intentFilter 的 action 與上述匹配,就會(huì)接收此廣播,并回調(diào)onReceive()。如下的 BroadcastReceiver 則會(huì)接收上述廣播:

   
       
           
       
    

注意:若發(fā)送廣播有相應(yīng)權(quán)限,那么廣播接收者也需要相應(yīng)權(quán)限

2.系統(tǒng)廣播(System Broadcast)

Android系統(tǒng)中內(nèi)置了多個(gè)系統(tǒng)廣播,只要涉及到手機(jī)的基本操作,基本上都會(huì)發(fā)出相應(yīng)的系統(tǒng)廣播。如:開(kāi)機(jī)啟動(dòng),網(wǎng)絡(luò)狀態(tài)改變,拍照,屏幕關(guān)閉與開(kāi)啟,電量不足等等。

每個(gè)系統(tǒng)廣播都具有特定的 intent-filter,其中主要包括具體的 action,系統(tǒng)廣播發(fā)出后,將被相應(yīng)的BroadcastReceiver 接收。

當(dāng)使用系統(tǒng)廣播時(shí),只需在注冊(cè)廣播接收者時(shí)定義相關(guān)的action即可,不需要手動(dòng)發(fā)送廣播,當(dāng)系統(tǒng)有相關(guān)操作時(shí)會(huì)自動(dòng)進(jìn)行系統(tǒng)廣播的發(fā)送。

3.有序廣播(Ordered Broadcast)

有序廣播中的“有序”是針對(duì)廣播接收者而言的,指的是發(fā)送出去的廣播被 BroadcastReceiver 按照先后順序進(jìn)行接收。有序廣播的定義過(guò)程與普通廣播無(wú)異,只是其發(fā)送方式變?yōu)椋簊endOrderedBroadcast(intent);

廣播接受者接收廣播的順序規(guī)則(同時(shí)面向靜態(tài)和動(dòng)態(tài)注冊(cè)的廣播接受者):按照 Priority 屬性值從大-小排序,Priority屬性相同者,動(dòng)態(tài)注冊(cè)的廣播優(yōu)先。

特點(diǎn):接收廣播按順序接收;先接收的廣播接收者可以對(duì)廣播進(jìn)行截?cái)啵春蠼邮盏膹V播接收者不再接收到此廣播;先接收的廣播接收者也可以對(duì)廣播進(jìn)行修改,那么后接收的廣播接收者將接收到被修改后的廣播。當(dāng)然,一般情況下,不建議對(duì)有序廣播進(jìn)行此類(lèi)操作,尤其是針對(duì)系統(tǒng)中的有序廣播。

4.App應(yīng)用內(nèi)廣播(Local Broadcast)

由于 Android 中的廣播可以跨 App 直接通信(exported對(duì)于有intent-filter情況下默認(rèn)值為true),可能會(huì)出現(xiàn)相應(yīng)安全隱患

a. 其他 App 針對(duì)性發(fā)出與當(dāng)前 App intent-filter 相匹配的廣播,由此導(dǎo)致當(dāng)前 App 不斷接收廣播并處理;

b. 其他 App 注冊(cè)與當(dāng)前 App 一致的 intent-filter 用于接收廣播,獲取廣播具體信息;即會(huì)出現(xiàn)安全性 & 效率性的問(wèn)題。

解決方案

方案1:將全局廣播設(shè)置成局部廣播

a. 對(duì)于同一 App 內(nèi)部發(fā)送和接收廣播,將 exported 屬性設(shè)置成false,使得非本 App 內(nèi)部發(fā)出的此廣播不被接收;

b. 在廣播發(fā)送和接收時(shí),都增加上相應(yīng)的permission,用于權(quán)限驗(yàn)證;

c. 發(fā)送廣播時(shí),指定特定廣播接收器所在的包名,具體是通過(guò) intent.setPackage(packageName) 指定,這樣此廣播將只會(huì)發(fā)送到此包中的 App 內(nèi)與之相匹配的有效廣播接收器中。

方案2:使用App應(yīng)用內(nèi)廣播(LocalBroadcastManager類(lèi))

App應(yīng)用內(nèi)廣播可理解為一種局部廣播,廣播的發(fā)送者和接收者都同屬于一個(gè)App。相比于全局廣播(普通廣播),App應(yīng)用內(nèi)廣播優(yōu)勢(shì)體現(xiàn)在:安全性高 & 效率高。

使用封裝好的 LocalBroadcastManager 類(lèi)使用方式上與全局廣播幾乎相同,只是注冊(cè)/取消注冊(cè)廣播接收器和發(fā)送廣播時(shí)將參數(shù)的 context 變成了 LocalBroadcastManager 的單一實(shí)例。

注意:對(duì)于LocalBroadcastManager方式發(fā)送的應(yīng)用內(nèi)廣播,只能通過(guò)LocalBroadcastManager動(dòng)態(tài)注冊(cè),不能靜態(tài)注冊(cè)。

   //注冊(cè)應(yīng)用內(nèi)廣播接收器
   //1:實(shí)例化MyBroadcaseReceiver 
   MyBroadcaseReceiver myBroadcaseReceiver = new MyBroadcaseReceiver(); 
   //2:實(shí)例化IntentFilter、設(shè)置接收廣播的類(lèi)型 
   IntentFilter intentFilter = new IntentFilter(); 
   intentFilter.addAction("android.net.conn.CONNECTIVITY_CHANGE");
   //3:實(shí)例化LocalBroadcastManager
   LocalBroadcastManager localBroadcastManager = LocalBroadcastManager.getInstance(this);
   //4:調(diào)用LocalBroadcastManager的registerReceiver()方法進(jìn)行動(dòng)態(tài)注冊(cè) 
   localBroadcastManager.registerReceiver(myBroadcaseReceiver, intentFilter);
   
   
   //取消注冊(cè)應(yīng)用內(nèi)廣播接收器
   localBroadcastManager.unregisterReceiver(myBroadcaseReceiver);
   
   
   //發(fā)送應(yīng)用內(nèi)廣播
   Intent intent = new Intent();
   intent.setAction("MY_BROADCAST_ACTION");
   localBroadcastManager.sendBroadcast(intent);

5.粘性廣播(Sticky Broadcast)

由于在 Android 5.0 & API 21 中已經(jīng)失效,所以不建議使用,在這里不作闡述。

6. 特別注意

對(duì)于不同注冊(cè)方式的廣播接收器回調(diào) onReceive(Context context,Intent intent)中的context返回值是不一樣的:

1.對(duì)于靜態(tài)注冊(cè)(全局+應(yīng)用內(nèi)廣播),回調(diào) onReceive(context, intent) 中的 context 返回值是:ReceiverRestrictedContext

2.對(duì)于全局廣播的動(dòng)態(tài)注冊(cè),回調(diào)onReceive(context, intent)中的context返回值是:Activity Context

3.對(duì)于應(yīng)用內(nèi)廣播的動(dòng)態(tài)注冊(cè)(LocalBroadcastManager方式),回調(diào)onReceive(context, intent)中的context返回值是:Application Context

4.對(duì)于應(yīng)用內(nèi)廣播的動(dòng)態(tài)注冊(cè)(LocalBroadcastManager方式),回調(diào)onReceive(context, intent)中的context返回值是:Application Context

結(jié)語(yǔ)

作為Android的四大組件之二,并且項(xiàng)目開(kāi)發(fā)過(guò)程中一些場(chǎng)景下經(jīng)常被使用到,小伙伴們趕緊上手實(shí)操,把它靈活的運(yùn)用到項(xiàng)目中,結(jié)合上一期的Activity實(shí)現(xiàn)有趣的交互吧。
PS:如果還有未看懂的小伙伴,歡迎加入我們的QQ技術(shù)交流群:892271582,里面有各種大神回答小伙伴們遇到的問(wèn)題哦~

文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請(qǐng)注明本文地址:http://m.specialneedsforspecialkids.com/yun/76163.html

相關(guān)文章

  • Android四大組件BroadcastReceiver全解析

    摘要:但是,一定會(huì)被執(zhí)行,從而保證了廣播在死亡前一定會(huì)被注銷(xiāo),從而防止內(nèi)存泄露。對(duì)于應(yīng)用內(nèi)廣播的動(dòng)態(tài)注冊(cè)非方式,回調(diào)中的返回值是 前言 BroadcastReceiver(廣播接收器),屬于Android四大組件之一 在Android開(kāi)發(fā)中,BroadcastReceiver的應(yīng)用場(chǎng)景非常多 今天,我將詳細(xì)講解關(guān)于BroadcastReceiver的一切相關(guān)知識(shí) 目錄 showImg(...

    yearsj 評(píng)論0 收藏0
  • Broadcast 使用詳解

    摘要:靜態(tài)注冊(cè)廣播的方法動(dòng)態(tài)注冊(cè)廣播在中動(dòng)態(tài)注冊(cè)廣播,通常格式如下動(dòng)態(tài)注冊(cè)廣播動(dòng)態(tài)注冊(cè)監(jiān)聽(tīng)滅屏點(diǎn)亮屏幕的廣播在廣播中動(dòng)態(tài)注冊(cè)廣播請(qǐng)注意一定要使用,防止為空,引起空指針異常。綁定模式此模式通過(guò)綁定組件等調(diào)用啟動(dòng)此服務(wù)隨綁定組件的消亡而解除綁定。 showImg(https://segmentfault.com/img/remote/1460000019975019?w=157&h=54); 極...

    Y3G 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

最新活動(dòng)
閱讀需要支付1元查看
<