The broadcast receiver is used to receive and process broadcast notifications (broadcastannouncements ).
Most broadcasts are initiated by the system, such as region change, insufficient power, and incoming calls.
The program can have any number of broadcast receivers to respond to the notifications it deems important.
Broadcast receiver can notify users in multiple ways: Start activity, use icationicationmanager, enable background light, vibrate device, play sound, etc. The most typical is to display an icon in the status bar, in this way, you can click it to open the notification content.
Generally, an application or system will broadcast an intent temporarily in some events (insufficient battery or short message calls, we can register a broadcast receiver to listen to the intent and obtain the data in the intent.
Receive broadcast from the system in the program
Here is an example of a broadcast that accepts system date changes.
Create a new hellobroadcastreceiver. Java class, inherit from broadcastreceiver, and rewrite its onreceive method. In this way, a class is created to receive broadcasts.
package com.tianjf;import android.content.BroadcastReceiver;import android.content.Context;import android.content.Intent;import android.util.Log;public class HelloBroadcastReceiver extends BroadcastReceiver {@Overridepublic void onReceive(Context context, Intent intent) {Log.d("debug", "Date has been changed!"); Log.d("debug", ""+intent.getAction()); }}
However, the above broadcast receiver does not specify which broadcast to receive. to specify which broadcast a receiver receives, the receiver must be registered in androidmanifest. xml.
<? XML version = "1.0" encoding = "UTF-8"?> <Manifest xmlns: Android = "http://schemas.android.com/apk/res/android" package = "com. tianjf "Android: versioncode =" 1 "Android: versionname =" 1.0 "> <uses-SDK Android: minsdkversion =" 4 "/> <application Android: icon = "@ drawable/ic_launcher" Android: Label = "@ string/app_name"> <activity Android: Name = ". broadcastdemoactivity "Android: Label =" @ string/app_name "> <intent-filter> <action Android: Name =" android. intent. Action. Main "/> <category Android: Name =" android. Intent. Category. launcher "/> </intent-filter> </activity> <! -- Define the broadcast receiver to specify the listener's action (the system date changes the action) --> <receiver er Android: Name = "hellobroadcastreceiver"> <intent-filter> <action Android: Name = "android. intent. action. date_changed "/> </intent-filter> </receiver> </Application> </manifest>
OK. After running the command, change the system date and check that two lines of log are printed. (The two lines of log are sometimes played out, sometimes cannot be played out, and I don't know why)
Receives broadcast messages by yourself.
Directly Add code
Broadcastdemoactivity. Java
Package COM. tianjf; import android. app. activity; import android. content. intent; import android. OS. bundle; import android. view. view; import android. view. view. onclicklistener; import android. widget. button; public class broadcastdemoactivity extends activity implements onclicklistener {private button;/** called when the activity is first created. * // @ overridepublic void oncreate (bundle savedinstancestate) {super. oncreate (savedinstancestate); setcontentview (R. layout. main); button = (button) findviewbyid (R. id. button); button. setonclicklistener (this) ;}@ overridepublic void onclick (view v) {// define an intentintent intent = new intent (); intent. setaction ("my_broadcast_action"); intent. putextra ("Yaoyao", "Yaoyao is 189 days old, 27 weeks -- 2010-08-10"); // broadcast sendbroadcast (intent );}}
Hellobroadcastreceiver. Java
package com.tianjf;import android.content.BroadcastReceiver;import android.content.Context;import android.content.Intent;import android.util.Log;public class HelloBroadcastReceiver extends BroadcastReceiver {@Overridepublic void onReceive(Context context, Intent intent) {Log.d("debug", "" + intent.getAction());if (intent.getAction().equals("android.intent.action.DATE_CHANGED")) {Log.d("debug", "Date has been changed!");Log.d("debug", "" + intent.getAction());} else if (intent.getAction().equals("MY_BROADCAST_ACTION")) {Log.d("debug", "Say Hello to Yaoyao!");Log.d("debug", intent.getStringExtra("yaoyao"));}}}
Androidmanifest. xml
<? XML version = "1.0" encoding = "UTF-8"?> <Manifest xmlns: Android = "http://schemas.android.com/apk/res/android" package = "com. tianjf "Android: versioncode =" 1 "Android: versionname =" 1.0 "> <uses-SDK Android: minsdkversion =" 4 "/> <application Android: icon = "@ drawable/ic_launcher" Android: Label = "@ string/app_name"> <activity Android: Name = ". broadcastdemoactivity "Android: Label =" @ string/app_name "> <intent-filter> <action Android: Name =" android. intent. Action. Main "/> <category Android: Name =" android. Intent. Category. launcher "/> </intent-filter> </activity> <! -- Define the broadcast receiver to specify the listening action (system date changes the action and automatically defines the broadcast) --> <receiver er Android: Name = "hellobroadcastreceiver"> <intent-filter> <action Android: name = "my_broadcast_action"/> <action Android: Name = "android. intent. action. date_changed "/> </intent-filter> </receiver> </Application> </manifest>
Two Methods for registering Broadcast
Broadcastreceiver cannot be used before registering a broadcast address. A broadcastreceiver without a broadcast address is like a radio without a selection button. Although it is fully functional, it cannot receive signals from the radio station. There are two registration methods:
- Static registration. Configure in the androidmanifest. xml file (as described in the above two examples)
- Dynamic Registration. To dynamically specify the broadcast address in the Code and register it, we usually register a broadcast in activity or service.
For more information about static registration, see the preceding two examples.
For the dynamic registration method, let's look at the following example:
Modify the broadcastdemoactivity as follows:
Package COM. tianjf; import android. app. activity; import android. content. intent; import android. content. intentfilter; import android. OS. bundle; import android. view. view; import android. view. view. onclicklistener; import android. widget. button; public class broadcastdemoactivity extends activity implements onclicklistener {private button; hellobroadcastreceiver extends er;/** called when the activity is first created. * // @ overridepublic void oncreate (bundle savedinstancestate) {super. oncreate (savedinstancestate); setcontentview (R. layout. main); button = (button) findviewbyid (R. id. button); button. setonclicklistener (this); explorer = new hellobroadcastreceiver (); intentfilter filter = new intentfilter (); filter. addaction ("android. intent. action. date_changed "); filter. addaction ("my_broadcast_action"); registerreceiver (receiver, filter) ;}@ overridepublic void onclick (view v) {// define an intentintent intent = new intent (); intent. setaction ("my_broadcast_action"); intent. putextra ("Yaoyao", "Yaoyao is 189 days old, 27 weeks -- 2010-08-10"); // broadcast sendbroadcast (intent);} @ overrideprotected void ondestroy () {super. ondestroy (); unregisterreceiver (receiver );}}
Note: The method for dynamically registering a broadcast must be deregistered in the ondestory method. If the method is not deregistered, the system reports an exception (as shown below)
12-19 07:16:04.186: E/ActivityThread(23244): Activity com.tianjf.BroadcastDemoActivity has leaked IntentReceiver com.tianjf.HelloBroadcastReceiver@40cef150 that was originally registered here. Are you missing a call to unregisterReceiver()?
An exception also indicates that you want to cancel the broadcast.
The differences between the two Broadcast registration methods:
- The static registration method can receive broadcasts and handle them regardless of the application status or even exit the application. Of course, it is relatively power-consuming.
- Dynamic registration method, because Dynamic Registration must cancel the broadcast, so the application will not receive the broadcast after exiting. So it is power-saving.
Ordered Broadcast)
Ordered broadcast is special. It is only sent to the receiver with a higher priority each time, and then the receiver with a higher priority spreads to the receiver with a lower priority. The receiver with a higher priority can terminate the broadcast.
To demonstrate the orderly broadcast process, we create the code for three receivers, as shown below:
package com.tianjf;import android.content.BroadcastReceiver;import android.content.Context;import android.content.Intent;import android.os.Bundle;import android.util.Log;public class FirstBroadcastReceiver extends BroadcastReceiver {private static final String TAG = "TestOrderdBroadcastReceiver";@Overridepublic void onReceive(Context context, Intent intent) {String msg = intent.getStringExtra("msg");Log.i(TAG, "FirstBroadcastReceiver: " + msg);Bundle bundle = new Bundle();bundle.putString("msg", msg + "@FirstBroadcastReceiver");setResultExtras(bundle);}}
package com.tianjf;import android.content.BroadcastReceiver;import android.content.Context;import android.content.Intent;import android.os.Bundle;import android.util.Log;public class SecondBroadcastReceiver extends BroadcastReceiver {private static final String TAG = "TestOrderdBroadcastReceiver";@Overridepublic void onReceive(Context context, Intent intent) {String msg = getResultExtras(true).getString("msg");Log.i(TAG, "SecondBroadcastReceiver: " + msg);Bundle bundle = new Bundle();bundle.putString("msg", msg + "@SecondBroadcastReceiver");setResultExtras(bundle);}}
package com.tianjf;import android.content.BroadcastReceiver;import android.content.Context;import android.content.Intent;import android.util.Log;public class ThirdBroadcastReceiver extends BroadcastReceiver {private static final String TAG = "TestOrderdBroadcastReceiver";@Overridepublic void onReceive(Context context, Intent intent) {String msg = getResultExtras(true).getString("msg");Log.i(TAG, "ThirdBroadcastReceiver: " + msg);}}
We noticed that the setresultextras method was used in firstreceiver and secondreceiver to set a bundle object as a result set object and pass it to the next receiver, recipients with lower priority can use getresultextras to obtain the latest collection of processed information.
Then, we need to register the broadcast address for the three receivers. Let's modify the androidmainfest. xml file:
<receiver android:name=".FirstBroadcastReceiver" > <intent-filter android:priority="1000" > <action android:name="android.intent.action.MY_BROADCAST" /> <category android:name="android.intent.category.DEFAULT" /> </intent-filter> </receiver> <receiver android:name=".SecondBroadcastReceiver" > <intent-filter android:priority="999" > <action android:name="android.intent.action.MY_BROADCAST" /> <category android:name="android.intent.category.DEFAULT" /> </intent-filter> </receiver> <receiver android:name=".ThirdBroadcastReceiver" > <intent-filter android:priority="998" > <action android:name="android.intent.action.MY_BROADCAST" /> <category android:name="android.intent.category.DEFAULT" /> </intent-filter> </receiver>
We can see that the <intent-filter> of the three receivers has an Android: Priority attribute, which is reduced in turn. This attribute ranges from-1000 to 1000. A greater value indicates a higher priority.
Now, we need to write the code for sending broadcasts, as shown below:
Intent intent = new Intent("android.intent.action.MY_BROADCAST"); intent.putExtra("msg", "hello receiver."); sendOrderedBroadcast(intent, "myAndroid.permission.MY_BROADCAST_PERMISSION");
Note: When the sendorderedbroadcast method is used to send an ordered broadcast, a permission parameter is required. If it is null, the recipient is not required to declare the specified permission. If it is not null, it indicates that if the recipient wants to receive the broadcast, the specified permission must be declared. This is from the security perspective. For example, system text messages are in the form of ordered broadcasting. An application may be capable of intercepting spam messages, when a text message arrives, it can receive the text message broadcast first. If necessary, the broadcast transmission is terminated. Such software must declare the permission to receive the text message.
Therefore, we define a permission in androidmainfest. xml:
<permission android:name="myAndroid.permission.MY_BROADCAST_PERMISSION" android:protectionLevel="normal" />
Then the permission is declared:
<uses-permission android:name="myAndroid.permission.MY_BROADCAST_PERMISSION" />
Then, click the send button to send a broadcast. The console prints the following message:
12-20 08:13:45.978: I/TestOrderdBroadcastReceiver(29914): FirstBroadcastReceiver: hello receiver.12-20 08:13:46.088: I/TestOrderdBroadcastReceiver(29914): SecondBroadcastReceiver: hello receiver.@FirstBroadcastReceiver12-20 08:13:46.138: I/TestOrderdBroadcastReceiver(29914): ThirdBroadcastReceiver: hello receiver.@FirstBroadcastReceiver@SecondBroadcastReceiver
We can see that the receiving is in order. The first and second are added to the result set and passed to the lower-priority receiver.
Since it is sequential transfer, try to terminate this transfer and see how it works. Let's modify the firstreceiver code and add the following code in the last line of onreceive:
abortBroadcast();
Then run the program again. The console prints the following:
12-20 08:13:45.978: I/TestOrderdBroadcastReceiver(29914): FirstBroadcastReceiver: hello receiver.
This time, only the first receiver executes the broadcast, and neither of the other two fails because the broadcast is terminated by the first receiver.
Note: Only ordered broadcasts can be terminated using abortbroadcast (); other broadcasts have no effect.
Broadcastreceiver Lifecycle
Broadcastreceiver has a short life cycle, that is, the onreceive execution time. After onreceive is executed, the broadcastreceiver instance is destroyed (regardless of the registration method)
Broadcast action Overview
Android. Intent. Action. battery_changed
The charging status or the battery power changes.
Android. Intent. Action. boot_completed
This action is broadcast once (only once) after the system is started)
Android. Intent. Action. CFF
The call transfer status of the voice phone has changed
Android. Intent. Action. configuration_changed
The device configuration has changed. For more information, see resources. configuration.
Android. Intent. Action. data_activity
The data activity status (that is, the status of sending and receiving data) of the phone has changed.
Android. Intent. Action. data_state
The telephone data connection status has changed
Android. Intent. Action. date_changed
Date changed
Android. server. checkin. fota_cancel
Cancel all pending update downloads
Android. server. checkin. fota_install
The update has been confirmed and will be installed soon
Android. server. checkin. fota_ready
The update has been downloaded. You can start installation.
Android. server. checkin. fota_restart
Resume stopped update downloads
Android. server. checkin. fota_update
Download and install OS updates through OTA
Android. Intent. Action. mediabutton
The user presses "Media button"
Android. Intent. Action. media_bad_removal
The expansion media (expansion card) has been removed from the SD card slot, but the mount point has not been removed (unmount)
Android. Intent. Action. media_eject
The user wants to remove the expansion media (unplug the expansion card)
Android. Intent. Action. media_mounted
Extended media is inserted and mounted
Android. Intent. Action. media_removed
Extended media removed
Android. Intent. Action. media_scanner_finished
A directory of the scanned Media
Android. Intent. Action. media_scanner_started
Start scanning a directory of Media
Android. Intent. Action. media_shared
Unmount the extended media because it has been shared as a USB large-capacity storage.
Android. Intent. Action. media_unmounted
Extended media exists, but not mounted)
Android. Intent. Action. MWI
The phone message waiting (Voice Mail) status has changed
Android. Intent. Action. network_tickle_received
The device received a new network "Tickle" notification.
Android. Intent. Action. package_added
A new application package is installed on the device.
Android. Intent. Action. package_removed
An application package is deleted from the device.
Android. Intent. Action. phone_state
The phone status has changed
Android. Intent. Action. provider_changed
Update to be (true) installed
Android. Intent. Action. provisioning_check
Requires the polling of provisioning service to download the latest settings
Android. Intent. Action. screen_off
Screen disabled
Android. Intent. Action. screen_on
The screen has been opened.
Android. Intent. Action. service_state
The telephone service status has changed
Android. Intent. Action. sig_str
The telephone signal strength has changed
Android. Intent. Action. statistics_report
Require receivers to report its own statistics
Android. Intent. Action. statistics_state_changed
The status of the Statistics Service has changed
Android. Intent. Action. timezone_changed
The Time Zone has changed.
Android. Intent. Action. time_set
Time has changed (reset)
Android. Intent. Action. time_tick
The current time has changed (normal time elapsed)
Android. Intent. Action. ums_connected
The device enters the USB high-capacity storage mode.
Android. Intent. Action. ums_disconnected
The device exits from the USB high-capacity storage mode.
Android. Intent. Action. wallpaper_changed
The system wallpaper has changed
Android. Intent. Action. xmpp_connected
The XMPP connection has been established.
Android. Intent. Action. xmpp_di
The XMPP connection has been disconnected.