广播作为Android四大组件之一,其重要程度无需多言,本文主要介绍Android中的广播是怎么来发送和接收的。
分类
Android中的广播主要可以分为两大类:标准广播和有序广播
标准广播:是一种完全异步执行的广播,即广播发出后所有的广播接收器几乎会在同一时间收到这条广播信息,没有任何先后之分,所以这种广播效率比较高,但同时也意味着这样的广播不可以被截断。
有序广播:是一种同步执行的广播,在广播发出后,同一时刻只会有一个广播接收器收到这条广播信息,只有当第一个收到广播的广播接收器处理完对应的逻辑之后才会继续传递给下一个广播接收器,并且优先级高的广播可以截断广播的传递。
广播的注册方式
动态注册:在代码中注册
静态注册:在AndroidManifest.xml中注册
用动态注册的方式来监听网络变化情况
public class MainActivity extends AppCompatActivity {
private IntentFilter intentFilter;
private NetworkChangeReceiver networkChangeReceiver;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
intentFilter = new IntentFilter();
intentFilter.addAction("android.net.conn.CONNECTIVITY_CHANGE");
networkChangeReceiver = new NetworkChangeReceiver();
//注册广播接收器
registerReceiver(networkChangeReceiver,intentFilter);
}
@Override
protected void onDestroy() {
super.onDestroy();
//取消注册
unregisterReceiver(networkChangeReceiver);
}
class NetworkChangeReceiver extends BroadcastReceiver{
@Override
public void onReceive(Context context, Intent intent) {
ConnectivityManager connectivityManager = (ConnectivityManager) getSystemService(
Context.CONNECTIVITY_SERVICE);
NetworkInfo networkInfo = connectivityManager.getActiveNetworkInfo();
if (networkInfo != null && networkInfo.isAvailable()) {
Toast.makeText(context, "network is available", Toast.LENGTH_SHORT).show();
}else {
Toast.makeText(context, "network is unavailable", Toast.LENGTH_SHORT).show();
}
}
}
}
因为所有的广播必须要有广播接收器 创建广播接收器也非常简单,创建一个类继承自BroadcastReceiver并重写onReceive方法这样当网络发生变化时就会执行该方法,而系统中网络发生变化时发出的广播就是”android.net.conn.CONNECTIVITY_CHANGE”,当我们去改变手机网络时还需要添加权限在AndroidManifest.xml中添加
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
最后动态注册的广播接收器一定要取消注册。
静态注册监听开机启动
Android启动完成后会发出”android.intent.action.BOOT_COMPLETED”的广播。建立一个广播接收器
public class BootCompleteReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Toast.makeText(context,"Boot Complete",Toast.LENGTH_SHORT).show();
}
}
目前我们还是无法接收到开机的广播的还需要在AndroidManifest.xml中添加权限并且将该广播接收器
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
<receiver
android:name=".BootCompleteReceiver"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED"/>
</intent-filter>
</receiver>
发送一条标准广播
首先仍然需要一个广播接收器,不然发出来的广播没人接收就等于白发了
public class MyBroadcastReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Toast.makeText(context,"received in MyBroadcastReceiver",Toast.LENGTH_SHORT).show();
abortBroadcast();
}
}
别忘了在AndroidManifest.xml中注册这个广播接收器
<receiver android:name=".MyBroadcastReceiver"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="xykj.com.broadcasttest.MY_BROADCAST"/>
</intent-filter>
</receiver>
编写MainActivity中的代码
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
findViewById(R.id.button).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent("xykj.com.broadcasttest.MY_BROADCAST");
sendBroadcast(intent);
}
});
}
}
运行程序并点击按钮就会收到received in MyBroadcastReceiver的提示了。
使用本地广播,以上所使用的广播在任何一个项目中都可以接收者显然不是我们需要的。因此我们可以使用本地广播,本地广播只能在应用程序的内部传递,广播接收器也只能接收来自本应用的广播。
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);
findViewById(R.id.button).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent("xykj.com.broadcasttest.LOCAL_BROADCAST");
//发送本地广播
localBroadcastManager.sendBroadcast(intent);
}
});
intentFilter = new IntentFilter();
intentFilter.addAction("xykj.com.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 in local broadcast",Toast.LENGTH_SHORT).show();
}
}
}