1. 程式人生 > >【Android】動態註冊廣播接收器

【Android】動態註冊廣播接收器

從本質來說,Android 系統的廣播機制是一種訊息訂閱/釋出機制,因此,使用這種訊息驅動模型的第一步便是訂閱訊息;而對 Android 應用程式來說,訂閱訊息其實就是註冊廣播接收器。

    註冊的方法有兩種,一種是靜態註冊,一種是動態註冊。在 Android 的廣播機制中,動態註冊的優先順序是要高於靜態註冊優先順序的,因此在必要的情況下,我們是需要動態註冊廣播接收器的。

    先回顧一下靜態註冊。所謂註冊,就是在 Manifest.xml 中去註冊廣播接收器

 <receiver android:name="" >
            <intent-filter android:priority="2147483647" >
                <action android:name="android.provider.Telephony.SMS_RECEIVED" >
                </action>
            </intent-filter>
        </receiver>
    然後再建立一個繼承 BroadcastReceiver 得類即可。在這裡要特意強調一下的是,intent-filter 標籤中的 priority 是設定廣播接收器的優先順序,網上很多資料都表示,優先順序的設定數值為1000~-1000,1000最大,但事實上,當 priority 值為integer 的最大值才時,才是優先順序最高的,即  2147483647;當然,“最高”只是限於靜態註冊。

    瞭解更多關於靜態註冊資訊,可參考《【Android】簡訊應用——簡訊資訊實時獲取》一文,其簡訊資訊的獲取就是運用了廣播接收器的靜態註冊。

    下面回到正題,如何動態註冊廣播接收器

    首先,我們來寫一個內部類,繼承 BroadcastReceiver。

private BroadcastReceiver myReceiver = new BroadcastReceiver() {

		@Override
		public void onReceive(Context context, Intent intent) {
			Toast.makeText(context, "myReceiver receive", Toast.LENGTH_SHORT)
					.show();
		}

	};
    onReveice 中我們寫一個 Toast,稍後用來檢測廣播接收器是否成功註冊。

    下面來看看如何去註冊廣播接收器。

private static final String ACTION = "cn.etzmico.broadcastreceiverregister.SENDBROADCAST";
IntentFilter filter = new IntentFilter();
				filter.addAction(ACTION);
				filter.setPriority(Integer.MAX_VALUE);
				registerReceiver(myReceiver, filter);

    我們在註冊的時候也來設定下優先順序,正如上面文章提到的,用 Integer  的最大值來獲得廣播機制中的最高優先順序。

    廣播註冊完畢,下面就是來做測試,來檢驗廣播接收器是否註冊個成功。

sendBroadcast(new Intent(ACTION));

    動態註冊廣播接收器還有一個特點,就是當用來註冊的 Activity 關掉後,廣播也就失效了。同時反映了靜態註冊的一個優勢,就是無需擔憂廣播接收器是否被關閉,只要裝置是開啟狀態,廣播接收器就是開啟著的。

    不過,我們可以通過將廣播接收器在 Service 中動態註冊,並設定開機自啟動,這樣一來,就不會擔心像Activity一樣的關閉問題了。但又如果要用“自啟動管家”等帶有管理開機自啟動程式功能的軟體講相關自啟動程式關閉時,廣播接收器也就無法成功註冊了。要想解決這個問題,就要看原始碼,是否能防止程式的自啟動被關閉。另外,現市場上有沒有程式能通過管理廣播接收器來關閉靜態註冊的廣播接收器,我還在調研,目前沒有發現,如果有知道的,歡迎留言說明~謝謝!

    後續的文章我會寫一篇關於通過動態註冊廣播接收器方法來實現有最高優先順序的簡訊攔截功能的文章。文章中會提到如何開機自啟動 Service 和 用 Service 動態註冊廣播接收器,敬請關注!謝謝~

PS:之前附加的資源有一個小BUG,給大家帶來了不便,不好意思!!!下面的連結是新上傳的……沒BUG的……I promise!