Android网络连接网络

  categories:android资料  author:

来源:互联网

一. ConnectivityManager

在Android中,ConnectivityManager类代表网络连接服务,它被用来监控网络连接状态,配置失效重连,并控制网络天线等。获取Connectivity Manager实例的方法是使用getSystemService,并指定Context.CONNECTIVITY_SERVICE作为参数,代码片段如下:
    String cserviceName = Context.CONNECTIVITY_SERVICE; 
    ConnectivityManager cm = (ConnectivityManager) getSystemService(cserviceName); 

要使用Connectivity Manager来读写网络状态时,需要在AndroidManifest.xml文件中加入如下的许可:
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/> 
    <uses-permission android:name="android.permission.CHANGE_NETWORK_STATE"/> 

Connectivity Manager在较高层面提供了管理可用网络连接的接口,使用getActiveNetworkInfo和getNetworkInfo函数可以查询获取NetworkInfo对象,该对象包含了当前活动网络连接或者指定类型的不可用网络连接的详细信息。

1.1)设置首选网络

当任何认证的应用程序请求网络连接时,Android都会优先尝试使用首选网络连接。设置首选网络连接的函数是setNetworkPreference,代码片段如下:

    cm.setNetworkPreference(ConnectivityManager.TYPE_WIFI); 

当首选网络连接不可用或者连接丢失时,Android将自动尝试使用第二优先连接类型。

1.2)监控网络连接

ConnectivityManager最常用的一个功能就是当网络连接状态改变时通知应用程序,这是通过应用程序实现自己的Broadcast Receiver来监听ConnectivityManager.CONNECTIVITY_ACTION类型的intent来实现的。这个intent提供了以下几种extra来进一步明确发生改变的网络状态:

1)ConnectivityManager.EXTRA_IS_FAILOVER:值为true说明当前的连接是首选网络失效重连后的连接;

2)ConnectivityManager.EXTRA_NO_CONNECTIVITY:值为true表示当前设备没有连接到网络;

3)ConnectivityManager.EXTRA_REASON:如果当前的广播代表网络失效,则这个值包含了连接失效的原因描述;

4)ConnectivityManager.EXTRA_NETWORK_INFO:返回NetworkInfo对象,包含了当前连接事件相关的网络详细信息;

5)ConnectivityManager.EXTRA_OTHER_NETWORK_INFO:在一个网络断开连接时,这个值返回NetworkInfo对象,包含了可能的网络失效重连的详细信息;

6)ConnectivityManager.EXTRA_EXTRA_INFO:包含可选的网络连接的额外信息。

二. WifiManager

WifiManager代表Android中的Wi-Fi连接服务,它被用于配置Wi-Fi网络连接,管理当前Wi-Fi连接,扫描Wi-Fi接入点和监控Wi-Fi连接的状态改变。获取WifiManager的方法和Connectivity Manager类似,通过函数getSystemService,并提供参数Context.WIFI_SERVICE,代码片段如下:

    String wserviceName = Context.WIFI_SERVICE; 
    WifiManager wm = (WifiManager) getSystemService(wserviceName); 

同样的,需要在AndroidManifest.xml文件中指定访问许可:
    <uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/> 
    <uses-permission android:name="android.permission.CHANGE_WIFI_STATE"/> 

我们可以使用setWifiEnabled函数来设置使能和去使能Wi-Fi硬件,使用getWifiState和isWifiEnabled函数来查看当前Wi-Fi状态,代码片段如下:

    if (!wm.isWifiEnabled()) { 
        if (WifiManager.WIFI_STATE_ENABLING != wm.getWifiState()) { 
            wm.setWifiEnabled(true); 
        } 
    } 

2.1)监控Wi-Fi连接

在Wi-Fi网络连接状态改变时,Wi-Fi Manager将广播相应的intent,有如下几种:

1)WifiManager.WIFI_STATE_CHANGED_ACTION:标识Wi-Fi硬件状态改变,可能在enabling、enabled、disabling、disabled和unknown之间改变。它包含了两个额外的键值EXTRA_WIFI_STATE和EXTRA_PREVIOUS_STATE,分别表示新的和前一个Wi-Fi状态。

2)WifiManager.SUPPLICANT_CONNECTION_CHANGE_ACTION:Wi-Fi硬件和当前接入点之间的连接状态改变时,这个intent将被广播。额外的键值EXTRA_NEW_STATE用来表示是新的连接建立事件还是已存在的连接中断事件,为true表示新的连接建立。

3)WifiManager.NETWORK_STATE_CHANGED_ACTION:Wi-Fi连接状态改变时广播这个intent,包含两个额外的键值:一是EXTRA_NETWORK_INFO,它包含表示当前网络状态的NetworkInfo对象;一是EXTRA_BSSID,包含连接到的接入点的BSSID值。

4)WifiManager.RSSI_CHANGED_ACTION:监听这个intent可以使应用程序监控当前Wi-Fi连接的信号强度。包含一个额外键值EXTRA_NEW_RSSI,包含了当前信号强度。使用这个信号强度,需要使用静态函数calculateSignalLevel将这个值按指定的缩放转换为整型值。

2.2)创建和管理Wi-Fi连接和配置

使用WiFi Manager可以进行网络配置,控制连接到哪个网络。当连接建立后,可以进一步获取活动网络连接的额外配置信息。使用函数getConfiguredNetworks可获得当前网络配置信息的列表,返回值是WifiConfiguration对象,包含了网络ID、SSID和其他配置信息。

要使用某一网络连接,可使用enableNetwork函数,传入网络ID并设置disableAllOthers参数为true即可,代码片段如下:

    // Get a list of available configurations 
    List<WifiConfiguration> configurations = wm.getConfiguredNetworks(); 
    // Get the network ID for the first one 
    if (configurations.size() > 0) { 
        int netID = configurations.get(0).networkId; 
        // Enable the network 
        boolean disableAllOthers = true; 
        wm.enableNetwork(netID, disableAllOthers); 
    } 

一旦连接建立,就可以使用getConnectionInfo函数来返回连接的状态,返回的是WifiInfo对象,包含了当前接入点的BSSID、Mac地址、IP地址,以及当前链路速度和信号强度。

下面的代码片段用于查询当前活动Wi-Fi连接并显示获取的相关信息:

    WifiInfo info = wm.getConnectionInfo(); 
    if (null != info.getBSSID()) { 
        int strength = WifiManager.calculateSignalLevel(info.getRssi(), 5); 
        int speed = info.getLinkSpeed(); 
        String units = WifiInfo.LINK_SPEED_UNITS; 
        String ssid = info.getSSID(); 
        String toastText = String.format("Connected to {0} at {1}{2}. Strength {3}/5", ssid, speed, units, strength); 
        Toast.makeText(this.getApplicationContext(), toastText, Toast.LENGTH_LONG); 
    } 

2.3)扫描Wifi热点

我们可以使用startScan函数进行Wifi接入点的扫描,当扫描结束且结果可用时,WifiManager将发送SCAN_RESULTS_AVAILABLE_ACTIONL类型的intent。使用getScanResults函数可以获取扫描的结果信息,并保存中ScanResult对象中。ScanResult对象中存放了检测到的每个接入点的详细信息,包括链路速度、信号强度、SSID和支持的认证技术。下面代码片段显示了Wifi热点扫描的过程:

      // Register a broadcast receiver that listens for scan results 
      registerReceiver(new BroadcastReceiver() { 
    @Override 
    public void onReceive(Context context, Intent intent) { 
        List<ScanResult> results = wifi.getScanResults(); 
        ScanResult bestSignal = null; 
        for (ScanResult result : results) { 
            if (null == bestSignal || 
                    WifiManager.compareSignalLevel(bestSignal.level, result.level) < 0) { 
                bestSignal = result; 
            } 
        } 
        String toastText = String.format("{0} networks found. {1} is the strongest.",  
                results.size(), bestSignal.SSID); 
        Toast.makeText(getApplicationContext(), toastText, Toast.LENGTH_LONG); 
    } 
      }, new IntentFilter(WifiManager.SCAN_RESULTS_AVAILABLE_ACTION)); 
      //Initiate a scan 
      wifi.startScan(); 

要连接到网络,需要创建和注册WiFi配置,通常用户可以使用Android系统原生的WiFi配置程序,但我们也可以在自己的应用程序中提供相同的功能,设置完全替代原生的WiFi配置程序,这就要用到保存网络配置信息的WifiConfiguration类了。每个WiFi配置一般都会包含以下几个公共的数据项:

1)BSSID:指明接入点的BSSID;

2)SSID:某一特定网络的SSID;

3)networkId:用来唯一标识当前设备使用的网络配置的id;

4)priority:选择连接哪个接入点时要使用的每个网络配置的优先权;

5)status:当前网络连接的状态,取值如下:

WifiConfiguration.Status.ENABLED,WifiConfiguration.Status.DISABLED,

WifiConfiguration.Status.CURRENT。

WifiConfiguration对象中还包括支持的认证技术以及用于与接入点进行认证的密钥。

使用addNetwork函数可以将新的WiFi配置添加到当前WiFi列表中,类似的,updateNetwork函数可以用于更新某个已存在的WiFi配置的某些信息;removeNetwork函数用于移除配置信息。要保存网络配置的任何变化,需要调用saveConfiguration函数。



快乐成长 每天进步一点点      京ICP备18032580号-1