廣播接收者
概念
Android中的廣播機制比我們日常生活中接觸的廣播更加靈活,Android中的每個應用程序都可以對自己感興趣的廣播進行註冊,這樣做的好處是我只接收我需要的廣播,其他廣播直接忽略。這些廣播可以是來自於系統也可以是用戶自定義的廣播。
廣播的類型:
標準廣播:一套完全異步執行的廣播,在廣播發出去之後,所有的廣播接收者幾乎同時收到廣播,接收者之間沒有先後順序的優先級之分。特點的效率高。有序廣播:同步執行的廣播,同一時刻只能有一個廣播接收者收到廣播,噹噹前廣播接收者執行完自己的邏輯之後,廣播纔會繼續向下傳遞。優先級越高的廣播接受者越先收到廣播,同時先收到的廣播接受者可以截斷廣播,阻止廣播繼續向下傳遞。
廣播的優先級設定:-1000-1000
有些情況下,某些廣播接受者必須要接收到廣播(防止其他優先級高的接收者阻攔),可以設置爲結果接收者(resultReceive):表示所有廣播接收者都接收到廣播之後,它才接收,並且一定會接收
定義方式:
定義一個類繼承BroadcastReceiver,重寫onReceive()方法即可,在該方法內部不要實現過多的邏輯或耗時操作,因爲廣播不能開啓子線程。在清單文件中配置該類,指定接收的廣播種類廣播是通過intent發送的,intent中會攜帶一個action,系統會在所有清單文件中尋找,看哪一個廣播接收者的intent-filter和廣播中的intent是匹配的,那麼這個廣播接收者就會收到這條廣播
廣播接收者所在進程即便沒有啓動,廣播發送出來時,系統也會啓動這個進程,然後把廣播交給廣播接收者
一個廣播接收者可以接受多種廣播,定義多個action即可
廣播接收者註冊:
清單文件註冊:廣播接收者永遠生效,除非卸載應用,或者手動停止進程。設置接收開啓啓動的廣播
<receiver
android:name=".MyReceiver"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED"/>
</intent-filter>
</receiver>
權限
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
使用代碼註冊:需要廣播接收者生效時,註冊它,不需要時,一定要反註冊它,反註冊之後,廣播接收者就失效了。private IntentFilter mIntentFilter;
private MyReceiver mReceiver;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mIntentFilter = new IntentFilter();
mIntentFilter.addAction("android.net.conn.CONNECTIVITY_CHANGE");
mReceiver = new MyReceiver();
registerReceiver(mReceiver, mIntentFilter);
}
class myReceive extends BroadcastReceiver{
@Override
public void onReceive(Context context, Intent intent) {
//實現邏輯
}
}
@Override
protected void onDestroy() {
super.onDestroy();
unregisterReceiver(mReceiver);
}
特殊廣播接收者,必須代碼註冊:屏幕開關、電量改變等在程序中動態註冊廣播必須要在代碼中取消註冊,一般情況下在Activity的onDestory()方法中取消註冊
靜態註冊廣播需要在Mainfest中進行配置,可以收到程序在沒有啓動狀態下的廣播接收
當一條廣播被髮送出來時,系統是在所有清單文件中遍歷,通過匹配意圖過濾器找到能接收這條廣播的廣播接收者
發送自定義廣播:
public class MyReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
//處理收到廣播的邏輯
}
}
<receiver
android:name=".MyReceiver"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="com.example.broadcasttest.MY_BROADCAST"/>
</intent-filter>
</receiver>
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Button button = (Button) findViewById(R.id.button);
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent("com.example.broadcasttest.MY_BROADCAST");
sendBroadcast(intent);
}
});
}
本地廣播
使用LocalBroadcastManager對廣播進行管理,並提供發送和註冊廣播接收器的方法。本地廣播無法通過靜態方式註冊,因爲靜態註冊就是爲了讓程序在未啓動的時候也能收到廣播,而發生本地廣播時,我們的程序是肯定啓動了。
本地廣播的優點:
可以明確地知道正在發送的廣播不會離開我們的程序,因此不必擔心機密數據泄露
其他的程序無法將廣播發送到我們程序的內部,因此不需要擔心會有安全問題
發送本地廣播比發送系統全局廣播將會更加高效
public class MainActivity extends AppCompatActivity {
private IntentFilter intentFilter;
private LocalReceiver localReceiver;
private LocalBroadcastManager localBroadcastManager;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
localBroadcastManager = LocalBroadcastManager.getInstance(this); // 獲取實例
Button button = (Button) findViewById(R.id.button);
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent("com.example.broadcasttest.LOCAL_BROADCAST");
localBroadcastManager.sendBroadcast(intent); // 發送本地廣播
}
});
intentFilter = new IntentFilter();
intentFilter.addAction("com.example.broadcasttest.LOCAL_BROADCAST");
localReceiver = new LocalReceiver();
localBroadcastManager.registerReceiver(localReceiver, intentFilter); // 註冊本地廣播監聽器
}
@Override
protected void onDestroy() {
super.onDestroy();
localBroadcastManager.unregisterReceiver(localReceiver);
}
class LocalReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Toast.makeText(context, "received local broadcast", Toast.LENGTH_SHORT).show();
}
}
}