Android 中的消息传递,详解广播机制

————————————广播机制简介————————————

我们先看一下什么是广播机制:

  1. Android中的广播机制非常灵活,Android中的每个应用程序都可以对自己感兴趣的广播进行注册,这个程序也只会收到自己所关心的广播内容,这些广播可能是来自于系统的,也可能是来自于其他应用程序的。

  2. Android提供了一套完整的API,允许应用程序自由地发送和接受广播。

  3. Android中的广播主要可以分为两种类型,标准广播有序广播

标准广播(Normal broadcasts):标准广播是一种 完全异步 执行的广播,在广播发出之后,所有的广播接收器几乎会在同一时刻接收到这条广播消息。这种广播效率比较高,但同时也意味着它是无法被截断的。

有序广播(Ordered broadcasts):有序广播则是一种 同步 执行的广播,在广播发出之后,同一时刻只会有一个广播接收器能够收到这条广播消息,当这个广播接收器中的逻辑执行完毕之后,广播才会继续传递。

————————————接受系统广播————————————

Android内置了很多系统级别的广播,可以在应用程序中通过监听这些广播来得到各种系统的状态信息。

手机开机完成后会发出一条广播,电池的电量发生变化会发出一条广播,时间改变也会发出一条广播……如果想要接受到这些广播,就需要使用广播接收器。

广播接收器可以自由地对自己感兴趣的广播进行注册,当有相应的广播发出时,广播接收器就能够收到该广播,并在内部处理相对应的逻辑。

我们来看一下两种注册方式:

  • 在代码中注册(动态注册)
  • 在 AndroidManifest.xml 中注册(静态注册)

创建广播接收器只需要新建一个类,让它继承自BroadcastReceiver,并重写父类的onReceiver()方法。当有消息通过广播传递过来时,onReceive()方法就会得到执行。

让我们先看第一种注册,动态注册监听网络变化:

看代码:

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);
    }

    //自定义内部类,继承自BroadcastReceiver
    public class NetworkChangeReceiver extends BroadcastReceiver {

        @Override
        public void onReceive(Context context, Intent intent) {
            //实现onReceive()方法的逻辑
            Toast.makeText(context, "网络状态改变", Toast.LENGTH_SHORT).show();
        }
    }
}

接下来让我们分析一下这段代码:

NetworkChangeReceiver extends BroadcastReceiver 这段代码就是在MainActivity中定义了一个内部类,并且继承了BroadcastReceiver,然后重写了父类的onReceive

IntentFilteraddAction() 方法中添加了一个值为 android.net.conn.CONNECTIVITY_CHANGEaction,用于接收系统对网络状态改变而发出的一条广播。(广播接收器想要监听什么广播,就在这里添加相应的action

调用 registerReceiver() 方法对广播接收器进行注册,将 networkChangeReceiver继承了BroadcastReceiver) 和 IntentFilter 的实例传递进去即可。

最后要记得,动态注册的广播接收器一定都要取消注册才行。通过调用 unregisterReceiver() 方法取消注册。

这样我们看起来这一段代码还是十分简单的。

我们现在只是提醒网络发生变换,但是这是不够人性化的,我们应该能直接准确的告诉用户有网络还是没有网络,这样我们对上面的代码进行优化:

修改 NetworkChangeReceiver 的 onReceiver() 方法,使之能够准确告诉用户当前网络状态:

Android系统规定,如果程序需要访问系统关键信息,必须在配置文件中声明权限才可以,否则程序直接崩溃。

这里查询网络状态需要声明权限,打开AndroidManifest.xml文件,为添加权限(之前),代码如下:

<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

修改 NetworkChangeReceiver 中的代码:

public class NetworkChangeReceiver extends BroadcastReceiver {

    @Override
    public void onReceive(Context context, Intent intent) {
        //connectivityManger是一个系统服务类,专门用于管理网络连接
        ConnectivityManager connectivityManager = (ConnectivityManager)
        getSystemService(Context.CONNECTIVITY_SERVICE);
        NetworkInfo networkInfo = connectivityManager.getActiveNetworkInfo();
        //调用NetworkInfo的isAvailable()方法判断是否联网
        if(networkInfo != null && networkInfo.isAvailable()){
            Toast.makeText(context,"网络已连接",Toast.LENGTH_SHORT).show();
        }else{
            Toast.makeText(context,"网络不可用",Toast.LENGTH_SHORT).show();
        }
    }
}
发布了11 篇原创文章 · 获赞 5 · 访问量 2065

猜你喜欢

转载自blog.csdn.net/skyline_lin/article/details/78736303