Android 网络切换 发送多次广播问题

2023-05-16

最近发现做项目监听网络切换广播,根据网络条件切换一些设置.测试发现每次3G-WIFI 或者WIFI到3G,网络切换的广播都会发出多次.比如3G-->WIFI 

       会发送三个广播 1.连接wifi  2.关闭手机网络 3.连接wifi  有没有方法判断这个过程呢?那就来看一个类 

       http://www.androidcommunitydocs.com/reference/android/net/ConnectivityManager.html   (官方API 文档)

      public class

        ConnectivityManager  extends Object

            java.lang.Object
                ↳ android.net.ConnectivityManager

        Class that answers queries about the state of network connectivity. It also notifies applications when network connectivity changes. Get an instance of this class by calling                              Context.getSystemService(Context.CONNECTIVITY_SERVICE).

     

   The primary responsibilities of this class are to 该类主要职责:

  1. Monitor network connections (Wi-Fi, GPRS, UMTS, etc.)  监视网络连接
  2. Send broadcast intents when network connectivity changes  网络连接变化时发送广播
  3. Attempt to "fail over" to another network when connectivity to a network is lost  当当前网络不可用时尝试切换到其他网络
  4. Provide an API that allows applications to query the coarse-grained or fine-grained state of the available networks 提供API给应用查询粗略或精细的网络状态

      (http://developer.android.com/training/monitoring-device-state/connectivity-monitoring.html)

     有了这些接着我们打印一下,在接受到网络变化的广播时.传过来的网络状态与当前激活的网络状态有什么不同 代码如下 : 

 

@Override
public void onReceive(Context context, Intent intent) {
   String action = intent.getAction();
       Log.i("MyReceiver",  action);
        if(ConnectivityManager.CONNECTIVITY_ACTION.equals(action)){
            Bundle b = intent.getExtras();
           if(b == null){
                Log.i("MyReceiver",  "b == null ");
               return ;
             }
            NetworkInfo netInfo = (NetworkInfo) b.get(ConnectivityManager.EXTRA_NETWORK_INFO);
            NetworkInfo.State state = netInfo.getState();
             int netInfoType = netInfo.getType();
             
             ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
            if(cm == null){
                  Log.i("MyReceiver", "ConnectivityManager == null");
                 return ;
             }
            NetworkInfo activeNetInfo = cm.getActiveNetworkInfo();
             if(state != null){
                  Log.i("MyReceiver",  state.name());
                  Log.i("MyReceiver",  "state : " + netInfo.getTypeName() + " : " + netInfo.getType());
            }else{
                  Log.i("MyReceiver", "state == null");
            }
             
             
            if(activeNetInfo != null){
                int activeNetType = activeNetInfo.getType();
                 Log.i("MyReceiver",  activeNetInfo.getTypeName() + " : " + activeNetInfo.getType());
             }else{          
                   Log.i("MyReceiver", "activeNetInfo == null ");
             }
             
        }
 
     }

使用手机进行网络间切换,打印如下 : 

   

wifi ---> 3G
03-17 17:56:45.526: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 17:56:45.526: I/MyReceiver(13406): DISCONNECTED
03-17 17:56:45.526: I/MyReceiver(13406): state : mobile : 0
03-17 17:56:45.531: I/MyReceiver(13406): activeNetInfo == null

03-17 17:56:45.991: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 17:56:45.991: I/MyReceiver(13406): CONNECTED
03-17 17:56:45.991: I/MyReceiver(13406): state : WIFI : 1
03-17 17:56:45.991: I/MyReceiver(13406): activeNetInfo == null

03-17 17:56:49.491: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 17:56:49.496: I/MyReceiver(13406): DISCONNECTED
03-17 17:56:49.496: I/MyReceiver(13406): state : WIFI : 1
03-17 17:56:49.496: I/MyReceiver(13406): mobile : 0

03-17 17:56:49.966: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 17:56:49.966: I/MyReceiver(13406): CONNECTED
03-17 17:56:49.966: I/MyReceiver(13406): state : mobile : 0
03-17 17:56:49.966: I/MyReceiver(13406): mobile : 0

3G-->wifi

03-17 18:00:35.286: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:00:35.286: I/MyReceiver(13406): CONNECTED
03-17 18:00:35.286: I/MyReceiver(13406): state : WIFI : 1
03-17 18:00:35.291: I/MyReceiver(13406): WIFI : 1

03-17 18:00:40.641: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:00:40.641: I/MyReceiver(13406): DISCONNECTED
03-17 18:00:40.641: I/MyReceiver(13406): state : mobile : 0
03-17 18:00:40.641: I/MyReceiver(13406): WIFI : 1

03-17 18:00:41.506: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:00:41.506: I/MyReceiver(13406): CONNECTED
03-17 18:00:41.506: I/MyReceiver(13406): state : WIFI : 1
03-17 18:00:41.506: I/MyReceiver(13406): WIFI : 1


wifi --3G --WIFI
03-17 18:02:54.861: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:02:54.861: I/MyReceiver(13406): DISCONNECTED
03-17 18:02:54.861: I/MyReceiver(13406): state : WIFI : 1
03-17 18:02:54.861: I/MyReceiver(13406): WIFI : 1

03-17 18:02:55.331: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:02:55.331: I/MyReceiver(13406): CONNECTED
03-17 18:02:55.331: I/MyReceiver(13406): state : mobile : 0
03-17 18:02:55.331: I/MyReceiver(13406): WIFI : 1

03-17 18:02:56.771: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:02:56.771: I/MyReceiver(13406): CONNECTED
03-17 18:02:56.771: I/MyReceiver(13406): state : WIFI : 1
03-17 18:02:56.771: I/MyReceiver(13406): WIFI : 1

03-17 18:02:57.171: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:02:57.171: I/MyReceiver(13406): DISCONNECTED
03-17 18:02:57.171: I/MyReceiver(13406): state : mobile : 0
03-17 18:02:57.171: I/MyReceiver(13406): WIFI : 1

03-17 18:02:57.771: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:02:57.771: I/MyReceiver(13406): CONNECTED
03-17 18:02:57.771: I/MyReceiver(13406): state : WIFI : 1
03-17 18:02:57.771: I/MyReceiver(13406): WIFI : 1


关闭wifi
03-17 18:08:06.381: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:08:06.381: I/MyReceiver(13406): DISCONNECTED
03-17 18:08:06.381: I/MyReceiver(13406): state : WIFI : 1
03-17 18:08:06.386: I/MyReceiver(13406): activeNetInfo == null

关闭3G

03-17 18:09:23.366: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:09:23.366: I/MyReceiver(13406): DISCONNECTED
03-17 18:09:23.371: I/MyReceiver(13406): state : mobile : 0
03-17 18:09:23.371: I/MyReceiver(13406): activeNetInfo == null


打开wifi

03-17 18:09:52.096: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:09:52.096: I/MyReceiver(13406): CONNECTED
03-17 18:09:52.096: I/MyReceiver(13406): state : WIFI : 1
03-17 18:09:52.096: I/MyReceiver(13406): WIFI : 1

打开3G

03-17 18:10:42.976: I/MyReceiver(13406): android.net.conn.CONNECTIVITY_CHANGE
03-17 18:10:42.976: I/MyReceiver(13406): CONNECTED
03-17 18:10:42.976: I/MyReceiver(13406): state : mobile : 0
03-17 18:10:42.976: I/MyReceiver(13406): mobile : 0

根据这些状态,在网络切换的时候 我们可以总结出一些规律 :

 1.网络在切换之前处于断开状态时 activeNetInfo == null 

 2.当网络状态不同时一般处于中间状态

 3.网络切换有可能发送重复的广播 (是这样吗?求高手解答)

 加入一些判断然后测试代码如下 :

@Override
    public void onReceive(Context context, Intent intent) {
         String action = intent.getAction();
         Log.i("MyReceiver",  action);
        if(ConnectivityManager.CONNECTIVITY_ACTION.equals(action)){
            Bundle b = intent.getExtras();
            if(b == null){
                Log.i("MyReceiver",  "b == null ");
                return ;
            }
            NetworkInfo netInfo = (NetworkInfo) b.get(ConnectivityManager.EXTRA_NETWORK_INFO);
            NetworkInfo.State state = netInfo.getState();
            int netInfoType = netInfo.getType();
            if(MyApplication.cacheState == null){
                MyApplication.cacheState = state ;
                MyApplication.netType = netInfoType; // 移动网络 (2G/3G/4G 间切换)  or  wifi 
            }else if(MyApplication.cacheState == state && MyApplication.netType == netInfo.getType()){
                 Log.i("MyReceiver",  "state : " + state.name() +" -- " + netInfo.getTypeName() + " : " + netInfo.getType());
                 Log.i("MyReceiver",  " 相同 状态广播  ");
                return ;
            }
            ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
            if(cm == null){
                 Log.i("MyReceiver", "ConnectivityManager == null");
                return ;
            }
            NetworkInfo activeNetInfo = cm.getActiveNetworkInfo();
            if(activeNetInfo != null){
                int activeNetType = activeNetInfo.getType();
                Log.i("MyReceiver",  activeNetInfo.getTypeName() + " : " + activeNetInfo.getType());
                if(activeNetType != netInfoType){  // 类型不同  认为是中间状态 不处理 
                    Log.i("MyReceiver", "类型不同 判断处于中间状态  :  不处理 " );
                }else{
                     MyApplication.cacheState = state ;
                     MyApplication.netType = netInfoType;
                     Log.i("MyReceiver",  "当前操作   state : " + state.name() +" -- " + netInfo.getTypeName() + " : " + netInfo.getType());
                }
            }else{
                MyApplication.cacheState = state ;
                MyApplication.netType = netInfoType;
                Log.i("MyReceiver", "activeNetInfo == null ");
                 Log.i("MyReceiver",  "当前操作   state : " + state.name() +" -- " + netInfo.getTypeName() + " : " + netInfo.getType());
            }
            
        }

    }

}

测试了一下,已经满足了我的要求.只是看起来方法有点笨. 应该会有更加简洁准确的方法,希望有知道的朋友提供一下思路。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Android 网络切换 发送多次广播问题 的相关文章

随机推荐

  • NSURLCache使用的坑

    NSURLCache使用有许多限制 xff0c 苹果限制的 1 只能用在get请求里面 xff0c post可以洗洗睡了 2 缓存机制选择 NSURLRequestReturnCacheDataElseLoad 有缓存从缓存取数据 xff0
  • Volley源码解析

    概述 本文基于Volley 1 1 1版本的源码 Volley是Google官方出的一套小而巧的异步请求库 xff0c 该框架封装的扩展性很强 xff0c 支持HttpClient HttpUrlConnection xff0c 甚至支持O
  • Android Volley源码分析(1)

    1 Volley newRequestQueue 我们从Volley中RequestQueue的初始化入手 xff0c 开始进行分析 应用利用Volley java的静态方法 xff0c 获取RequestQueue xff0c 开启使用V
  • Android Volley源码分析(2)

    1 RequestQueue的add接口 我们从RequestQueue的add接口入手 xff1a public lt T gt Request lt T gt add Request lt T gt request Tag the re
  • 删除git remote

    目前项目中有两个remote git remote v origin https github com test test git fetch origin https github com test test git push test
  • 当 git pull 碰到拒绝合并无关历史

    问题描述 很久之前在 github 上建了个仓库 xff0c 里面只有一个 README md 文件 突然有天 xff0c 我想把本地的一个项目传上去 xff0c 然后就碰到了这样一个问题 xff01 当我 添加远程仓库 后准备提交代码时
  • rxjava2源码解析(一)基本流程分析

    从基本使用入手 首先随便写一个rxjava2的基本用法 xff0c 我们根据这个简单的示例来看看rxjava2整个流程是什么样的 Observable create new ObservableOnSubscribe lt String g
  • rxjava2源码解析(二)线程切换分析

    使用方法 还是先从最基本的使用开始看 xff1a Observable create new ObservableOnSubscribe lt String gt 64 Override public void subscribe Obse
  • rxjava2源码解析(三)observeOn线程池原理分析

    observeOn 还是先说observeOn 直接看源码 xff1a public ObservableObserveOn ObservableSource lt T gt source Scheduler scheduler boole
  • RxJava 2.x 源码分析 之 FlatMap

    FlatMap 官方定义 xff1a 把被观察者发射出去的事件转化成新的子被观察者 xff0c 然后把这些发射量展开平铺后统一放到一个被观察者中 官方文档 简单来讲就是把被观察者每次发射的事件转化成一个子被观察者 xff0c 然后通过合并
  • Transformer 在RxJava中的使用

    Transformer 用途 Transformer xff0c 顾名思义是转换器的意思 早在 RxJava1 x 版本就有了Observable Transformer Single Transformer和Completable Tra
  • 彻底理解kubernetes CNI

    kubernetes各版本离线安装包 CNI接口很简单 xff0c 特别一些新手一定要克服恐惧心里 xff0c 和我一探究竟 xff0c 本文结合原理与实践 xff0c 认真读下来一定会对原理理解非常透彻 环境介绍 我们安装kubernet
  • 将本地项目上传到远程Git服务器

    1 先进入项目文件夹 通过命令 git init 把这个目录变成git可以管理的仓库 git init 2 把文件添加到版本库中 xff0c 使用命令git add 添加到暂存区里面去 xff0c 小数点 34 34 意为添加文件夹下的所有
  • 解决Manifest merger failed : Attribute application@appComponentFactory

    在将butterknife升级到10 0 0的时候遇到问题 xff0c 编译无法通过 Manifest merger failed Attribute application 64 appComponentFactory value 61
  • bindService不能触发onServiceConnected方法的原因

    在android项目中用到AIDL xff0c bindService service connection BIND AUTO CREATE 之后一直不调用 connection中的onServiceConnected方法 可能原因1 1
  • Android应用被浅杀和深杀

    onTaskRemoved 方法在当用户移除应用的一个Task栈时被调用 也就是当用户在最近任务界面把该应用的一个task划掉时 xff0c 或者在最近任务界面进行清理时 这两种情况下onTaskRemoved 都会被调用 xff0c 但在
  • java.lang.OutOfMemoryError: Could not allocate JNI Env

    最近有一些OOM的错误上报 java lang OutOfMemoryError Could not allocate JNI Env 极少量的 java lang OutOfMemoryError pthread create 1040K
  • RecycleView4种定位滚动方式演示

    概述 相信大家在项目中使用RecyclerView时 xff0c 经常会遇到这样的需求 xff1a 将RecyclerView滑动到指定位置 xff0c 或者检索RecyclerView的某一项 xff08 各个项的高度不确定 xff09
  • Java/Android中的引用类型及WeakReference应用实践

    一 背景 一般意义上而言 xff0c Java Android中的引用类型包括强引用 软引用 弱引用 虚引用 不同的引用类型具有各自适用的应用场景 xff0c 并与JVM的GC直接相关 作为Java Android中的引用类型之一 xff0
  • Android 网络切换 发送多次广播问题

    最近发现做项目监听网络切换广播 xff0c 根据网络条件切换一些设置 测试发现每次3G WIFI 或者WIFI到3G xff0c 网络切换的广播都会发出多次 比如3G gt WIFI 会发送三个广播 1 连接wifi 2 关闭手机网络 3