android以编程方式打开wifi [英] android turning on wifi programmatically

查看:45
本文介绍了android以编程方式打开wifi的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试以编程方式添加 wifi 网络并连接到该网络.

如果 wi-fi 已经打开,我的代码就可以正常工作.

如果 wi-fi 关闭,我看到 wifimanager.addtonetwork() 失败,当我看到手机的 wifi 设置时,我可以看到状态为扫描

如果我再次尝试连接它工作正常.

请看下面的代码.请帮忙

private int changeNetwork(NetworkSetting setting) {//如果SSID为空,则抛出错误并返回if (setting.getSsid() == null || setting.getSsid().length() == 0) {返回 doError(R.string.wifi_ssid_missing);}//如果网络类型无效if (setting.getNetworkType() == NetworkType.NETWORK_INVALID) {返回 doError(R.string.wifi_type_incorrect);}//如果密码为空,这是一个未加密的网络if (setting.getPassword() == null||setting.getPassword().length() == 0||setting.getNetworkType() == null||setting.getNetworkType() == NetworkType.NETWORK_NOPASS) {返回 changeNetworkUnEncrypted(setting);}如果 (setting.getNetworkType() == NetworkType.NETWORK_WPA) {返回 changeNetworkWPA(setting);} 别的 {返回 changeNetworkWEP(setting);}}私有 int doError(int resource_string) {statusView.setText(resource_string);//放弃连接wifiManager.disconnect();如果(网络 ID > 0){wifiManager.removeNetwork(networkId);网络 ID = -1;}如果(接收者注册){取消注册接收器(wifi接收器);接收者注册 = 假;}返回-1;}私人 WifiConfiguration changeNetworkCommon(NetworkSetting input) {statusView.setText(R.string.wifi_creating_network);Log.d(TAG, "添加新配置:
SSID: " + input.getSsid()+ "
类型:" + input.getNetworkType());WifiConfiguration config = new WifiConfiguration();config.allowedAuthAlgorithms.clear();config.allowedGroupCiphers.clear();config.allowedKeyManagement.clear();config.allowedPairwiseCiphers.clear();config.allowedProtocols.clear();//Android API 坚持必须引用一个 ascii SSID 才能正确//处理.config.SSID = NetworkUtil.convertToQuotedString(input.getSsid());config.hiddenSSID = true;返回配置;}私有 int requestNetworkChange(WifiConfiguration 配置){statusView.setText(R.string.wifi_changed_network);返回更新网络(配置,假);}//添加 WEP 网络私有 int changeNetworkWEP(网络设置输入){WifiConfiguration config = changeNetworkCommon(input);String pass = input.getPassword();if (NetworkUtil.isHexWepKey(pass)) {config.wepKeys[0] = 通过;} 别的 {config.wepKeys[0] = NetworkUtil.convertToQuotedString(pass);}config.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.SHARED);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP104);config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);config.wepTxKeyIndex = 0;返回 requestNetworkChange(config);}//添加 WPA 或 WPA2 网络私有 int changeNetworkWPA(网络设置输入){WifiConfiguration config = changeNetworkCommon(input);String pass = input.getPassword();//64 位长的十六进制密码不能被引用.如果 (HEX_DIGITS_64.matcher(pass).matches()) {Log.d(TAG, "输入的 64 位十六进制密码.");config.preSharedKey = 通过;} 别的 {Log.d(TAG, "输入了一个普通密码:我引用了它.");config.preSharedKey = NetworkUtil.convertToQuotedString(pass);}config.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN);//用于 WPAconfig.allowedProtocols.set(WifiConfiguration.Protocol.WPA);//对于 WPA2config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);config.allowedProtocols.set(WifiConfiguration.Protocol.RSN);返回 requestNetworkChange(config);}//添加一个开放的、不安全的网络私有 int changeNetworkUnEncrypted(NetworkSetting 输入) {Log.d(TAG, "空密码提示简单账户设置");WifiConfiguration config = changeNetworkCommon(input);config.wepKeys[0] = "";config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);config.wepTxKeyIndex = 0;返回 requestNetworkChange(config);}/*** 如果设置中存在给定的 ssid 名称,则更改其密码* 到这里给出的那个,并保存** @param ssid*/私人 WifiConfiguration findNetworkInExistingConfig(String ssid) {列表现有配置 = wifiManager.getConfiguredNetworks();Log.i("开始比较","大小"+existingConfigs.size());for (WifiConfiguration existingConfig : existingConfigs) {Log.i("比较SSID", ssid + existingConfig.SSID);if (existingConfig.SSID.equals(ssid)) {Log.i("比较成功与SSID", ssid + existingConfig.SSID);返回现有配置;}}返回空;}@覆盖protected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);意图意图 = getIntent();/* 如果(意图 == 空||!intent.getAction().equals(Intents.WifiConnect.ACTION)) {结束();返回;} */String ssid = intent.getStringExtra("ssid");String password = intent.getStringExtra("password");String networkType = intent.getStringExtra("type");setContentView(R.layout.network);statusView = (TextView) findViewById(R.id.networkStatus);网络类型 networkT;如果(WPA".等于(网络类型)){networkT = NetworkType.NETWORK_WPA;} else if ("WEP".equals(networkType)) {networkT = NetworkType.NETWORK_WEP;} else if ("nopass".equals(networkType)) {networkT = NetworkType.NETWORK_NOPASS;} 别的 {networkT = NetworkType.NETWORK_INVALID;}//这在 onCreate 之前不可用wifiManager = (WifiManager) this.getSystemService(WIFI_SERVICE);//启动WiFi,否则什么都不会工作wifiManager.setWifiEnabled(true);//所以我们知道网络何时发生变化wifiReceiver = new WifiReceiver(wifiManager, this, statusView, ssid);//顺序很重要!mWifiStateFilter = 新的 IntentFilter(WifiManager.WIFI_STATE_CHANGED_ACTION);mWifiStateFilter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);mWifiStateFilter.addAction(WifiManager.SUPPLICANT_STATE_CHANGED_ACTION);mWifiStateFilter.addAction(WifiManager.NETWORK_STATE_CHANGED_ACTION);registerReceiver(wifiReceiver, mWifiStateFilter);接收者注册 = 真;如果(密码==空){密码 = "";}Log.d(TAG, "添加新配置:
SSID:" + ssid + "类型:"+ 网络T);NetworkSetting setting = new NetworkSetting(ssid, password, networkT);更改网络(设置);}@覆盖公共无效 onPause() {super.onPause();如果(接收者注册){取消注册接收器(wifi接收器);接收者注册 = 假;}}@覆盖公共无效 onResume() {super.onResume();if (wifiReceiver != null && mWifiStateFilter != null&&!receiverRegistered) {registerReceiver(wifiReceiver, mWifiStateFilter);接收者注册 = 真;}}@覆盖受保护的无效 onDestroy() {如果(wifiReceiver != null){如果(接收者注册){取消注册接收器(wifi接收器);接收者注册 = 假;}wifiReceiver = null;}super.onDestroy();}/*** 更新网络:创建新网络或修改现有网络* 网络** @param 配置* 新的网络配置* @param disableOthers* true 如果必须禁用其他网络* @return 已连接网络的网络 ID.*/私有 int updateNetwork(WifiConfiguration 配置,布尔值 disableOthers){WifiConfiguration found = findNetworkInExistingConfig(config.SSID);wifiManager.disconnect();如果(发现 == 空){Log.i("WIFI","SSID 未找到");statusView.setText(R.string.wifi_creating_network);} 别的 {statusView.setText(R.string.wifi_modifying_network);Log.d(TAG, "删除网络" + found.networkId);wifiManager.removeNetwork(found.networkId);wifiManager.saveConfiguration();}networkId = wifiManager.addNetwork(config);Log.d(TAG, "插入/修改的网络" + networkId);如果(网络 ID <0){wifiManager.setWifiEnabled(true);networkId = wifiManager.addNetwork(config);Log.d(TAG, "再次插入/修改网络" + networkId);返回 FAILURE_NO_NETWORK_ID;}//尝试禁用当前网络并启动一个新网络.如果(!wifiManager.enableNetwork(networkId,disableOthers)){networkId = FAILURE_NO_NETWORK_ID;返回 FAILURE_NO_NETWORK_ID;}错误计数 = 0;wifiManager.reassociate();返回网络ID;}

这是我的工作代码:(与我之前的代码不同)

 包 com.idg.project.utils;导入 java.util.List;导入 java.util.regex.Pattern;导入 android.net.wifi.WifiConfiguration;导入 android.net.wifi.WifiManager;导入 android.util.Log;/*** @author 维克拉姆·阿加瓦尔* @作者肖恩欧文*/公共最终类 WifiConfigManager {私有静态最终字符串标记 = WifiConfigManager.class.getSimpleName();private static final Pattern HEX_DIGITS = Pattern.compile("[0-9A-Fa-f]+");私人 WifiConfigManager() {}公共静态无效配置(最终 WifiManager wifiManager,最终的字符串 ssid,最终字符串密码,最终字符串 networkTypeString) {Runnable configureRunnable = new Runnable() {公共无效运行(){//启动WiFi,否则什么都不会工作如果(!wifiManager.isWifiEnabled()){Log.i(TAG, "启用 wi-fi...");如果(wifiManager.setWifiEnabled(真)){Log.i(TAG, "Wi-fi 已启用");} 别的 {Log.w(TAG, "无法启用 Wi-fi!");返回;}//这发生得很快,但需要等待它启用.有点忙等?整数计数 = 0;而 (!wifiManager.isWifiEnabled()) {如果(计数> = 10){Log.i(TAG, "启用 wi-fi 的时间太长, 正在退出");返回;}Log.i(TAG, "仍在等待 wi-fi 启用...");尝试 {线程睡眠(1000L);} catch (InterruptedException ie) {//继续}计数++;}}NetworkType networkType = NetworkType.forIntentValue(networkTypeString);如果(networkType == NetworkType.NO_PASSWORD){更改网络未加密(wifiManager,ssid);} 别的 {if (password == null || password.length() == 0) {抛出新的 IllegalArgumentException();}如果(网络类型 == 网络类型.WEP){更改网络WEP(wifiManager,ssid,密码);} else if (networkType == NetworkType.WPA) {更改网络WPA(wifiManager,ssid,密码);} }}};新线程(configureRunnable).start();}/*** 更新网络:创建新网络或修改现有网络* @param config 新的网络配置* @return 已连接网络的网络 ID.*/私有静态无效更新网络(WifiManager wifiManager,WifiConfiguration 配置){整数 foundNetworkID = findNetworkInExistingConfig(wifiManager, config.SSID);如果(foundNetworkID!= null){Log.i(TAG, "删除旧的网络配置" + config.SSID);wifiManager.removeNetwork(foundNetworkID);wifiManager.saveConfiguration();}int networkId = wifiManager.addNetwork(config);如果(网络 ID >= 0){//尝试禁用当前网络并启动一个新网络.如果(wifiManager.enableNetwork(networkId,true)){Log.i(TAG, "关联到网络" + config.SSID);wifiManager.saveConfiguration();} 别的 {Log.w(TAG, "启用网络失败" + config.SSID);}} 别的 {Log.w(TAG, "无法添加网络" + config.SSID);}}私有静态 WifiConfiguration changeNetworkCommon(String ssid) {WifiConfiguration config = new WifiConfiguration();config.allowedAuthAlgorithms.clear();config.allowedGroupCiphers.clear();config.allowedKeyManagement.clear();config.allowedPairwiseCiphers.clear();config.allowedProtocols.clear();//Android API 坚持必须引用 ascii SSID 才能正确处理.config.SSID = quoteNonHex(ssid);返回配置;}//添加 WEP 网络私有静态无效changeNetworkWEP(WifiManager wifiManager,字符串ssid,字符串密码){WifiConfiguration config = changeNetworkCommon(ssid);config.wepKeys[0] = quoteNonHex(password, 10, 26, 58);config.wepTxKeyIndex = 0;config.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.SHARED);config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP104);更新网络(wifiManager,配置);}//添加 WPA 或 WPA2 网络私有静态无效changeNetworkWPA(WifiManager wifiManager,字符串ssid,字符串密码){WifiConfiguration config = changeNetworkCommon(ssid);//64 位长的十六进制密码不能被引用.config.preSharedKey = quoteNonHex(密码, 64);config.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN);config.allowedProtocols.set(WifiConfiguration.Protocol.WPA);//用于 WPAconfig.allowedProtocols.set(WifiConfiguration.Protocol.RSN);//对于 WPA2config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_EAP);config.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.TKIP);config.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);更新网络(wifiManager,配置);}//添加一个开放的、不安全的网络私有静态无效changeNetworkUnEncrypted(WifiManager wifiManager,字符串ssid){WifiConfiguration config = changeNetworkCommon(ssid);config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);更新网络(wifiManager,配置);}私有静态整数 findNetworkInExistingConfig(WifiManager wifiManager, String ssid) {列表existingConfigs = wifiManager.getConfiguredNetworks();for (WifiConfiguration existingConfig : existingConfigs) {if (existingConfig.SSID.equals(ssid)) {返回 existingConfig.networkId;}}返回空;}private static String quoteNonHex(String value, int... allowedLengths) {返回 isHexOfLength(value, allowedLengths) ?值 : convertToQuotedString(value);}/*** 将传入的字符串括在双引号内,如果它尚未被引用.* @param string 输入字符串* @return 带引号的字符串,形式为input".如果输入字符串为空,则返回空* 也是.*/私有静态字符串 convertToQuotedString(String string) {if (string == null || string.length() == 0) {返回空;}//如果已经引用,则按原样返回if (string.charAt(0) == '"' && string.charAt(string.length() - 1) == '"') {返回字符串;}返回 '​​"' + 字符串 + '"';}/*** @param 值输入检查* @param allowedLengths 允许的长度,如果有的话* @return true 如果 value 是非空、非空的十六进制数字字符串,并且如果给定了允许的长度,则具有* 允许的长度*/私有静态布尔值 isHexOfLength(CharSequence value, int... allowedLengths) {if (value == null || !HEX_DIGITS.matcher(value).matches()) {返回假;}如果(allowedLengths.length == 0){返回真;}对于(整数长度:allowedLengths){if (value.length() == 长度) {返回真;}}返回假;}}包 com.idg.project.utils;枚举网络类型{WEP,水杨酸,NO_PASSWORD;静态 NetworkType forIntentValue(String networkTypeString) {如果(网络类型字符串 == 空){返回 NO_PASSWORD;}如果(WPA".equals(networkTypeString)){返还水杨酸;}if ("WEP".equals(networkTypeString)) {返回 WEP;}if ("nopass".equals(networkTypeString)) {返回 NO_PASSWORD;}抛出新的 IllegalArgumentException(networkTypeString);}}

解决方案

您需要创建wifiLock 使用 WIFI_MODE_FULL_HIGH_PERF 模式,基于文档,它只能在以下约束下工作:

<块引用><块引用>

  1. 该锁仅在设备连接到接入点时才有效.
  2. 锁定仅在屏幕开启时有效.
  3. 该锁仅在获取应用程序在前台运行时才处于活动状态.

I am trying to turn add a wifi network programmatically and to connect to that network.

My code works fine if the wi-fi is already turned on.

If wi-fi is off, what i see wifimanager.addtonetwork() fails and when i see the wifi settings for the phone, i can see the status as scanning

If i try to connect again it works fine.

Please see code below. Please help

private int changeNetwork(NetworkSetting setting) {
    // If the SSID is empty, throw an error and return
    if (setting.getSsid() == null || setting.getSsid().length() == 0) {
        return doError(R.string.wifi_ssid_missing);
    }
    // If the network type is invalid
    if (setting.getNetworkType() == NetworkType.NETWORK_INVALID) {
        return doError(R.string.wifi_type_incorrect);
    }

    // If the password is empty, this is an unencrypted network
    if (setting.getPassword() == null
            || setting.getPassword().length() == 0
            || setting.getNetworkType() == null
            || setting.getNetworkType() == NetworkType.NETWORK_NOPASS) {
        return changeNetworkUnEncrypted(setting);
    }
    if (setting.getNetworkType() == NetworkType.NETWORK_WPA) {
        return changeNetworkWPA(setting);
    } else {
        return changeNetworkWEP(setting);
    }
}

private int doError(int resource_string) {
    statusView.setText(resource_string);
    // Give up on the connection
    wifiManager.disconnect();
    if (networkId > 0) {
        wifiManager.removeNetwork(networkId);
        networkId = -1;
    }
    if (receiverRegistered) {
        unregisterReceiver(wifiReceiver);
        receiverRegistered = false;
    }
    return -1;
}

private WifiConfiguration changeNetworkCommon(NetworkSetting input) {
    statusView.setText(R.string.wifi_creating_network);
    Log.d(TAG, "Adding new configuration: 
SSID: " + input.getSsid()
            + "
Type: " + input.getNetworkType());
    WifiConfiguration config = new WifiConfiguration();

    config.allowedAuthAlgorithms.clear();
    config.allowedGroupCiphers.clear();
    config.allowedKeyManagement.clear();
    config.allowedPairwiseCiphers.clear();
    config.allowedProtocols.clear();

    // Android API insists that an ascii SSID must be quoted to be correctly
    // handled.
    config.SSID = NetworkUtil.convertToQuotedString(input.getSsid());
    config.hiddenSSID = true;
    return config;
}

private int requestNetworkChange(WifiConfiguration config) {
    statusView.setText(R.string.wifi_changing_network);
    return updateNetwork(config, false);
}

// Adding a WEP network
private int changeNetworkWEP(NetworkSetting input) {
    WifiConfiguration config = changeNetworkCommon(input);
    String pass = input.getPassword();
    if (NetworkUtil.isHexWepKey(pass)) {
        config.wepKeys[0] = pass;
    } else {
        config.wepKeys[0] = NetworkUtil.convertToQuotedString(pass);
    }
    config.allowedAuthAlgorithms
            .set(WifiConfiguration.AuthAlgorithm.SHARED);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP104);
    config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);
    config.wepTxKeyIndex = 0;
    return requestNetworkChange(config);
}

// Adding a WPA or WPA2 network
private int changeNetworkWPA(NetworkSetting input) {
    WifiConfiguration config = changeNetworkCommon(input);
    String pass = input.getPassword();
    // Hex passwords that are 64 bits long are not to be quoted.
    if (HEX_DIGITS_64.matcher(pass).matches()) {
        Log.d(TAG, "A 64 bit hex password entered.");
        config.preSharedKey = pass;
    } else {
        Log.d(TAG, "A normal password entered: I am quoting it.");
        config.preSharedKey = NetworkUtil.convertToQuotedString(pass);
    }
    config.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN);
    // For WPA
    config.allowedProtocols.set(WifiConfiguration.Protocol.WPA);
    // For WPA2
    config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
    config.allowedProtocols.set(WifiConfiguration.Protocol.RSN);
    return requestNetworkChange(config);
}

// Adding an open, unsecured network
private int changeNetworkUnEncrypted(NetworkSetting input) {
    Log.d(TAG, "Empty password prompting a simple account setting");
    WifiConfiguration config = changeNetworkCommon(input);
    config.wepKeys[0] = "";
    config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);
    config.wepTxKeyIndex = 0;
    return requestNetworkChange(config);
}

/**
 * If the given ssid name exists in the settings, then change its password
 * to the one given here, and save
 * 
 * @param ssid
 */
private WifiConfiguration findNetworkInExistingConfig(String ssid) {
    List<WifiConfiguration> existingConfigs = wifiManager
            .getConfiguredNetworks();
    Log.i("Start comparing","Size "+existingConfigs.size() );
    for (WifiConfiguration existingConfig : existingConfigs) {
        Log.i("Compare with SSID", ssid + existingConfig.SSID);
        if (existingConfig.SSID.equals(ssid)) {
            Log.i("Compare success with SSID", ssid + existingConfig.SSID);
            return existingConfig;
        }
    }
    return null;
}

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    Intent intent = getIntent();
/*  if (intent == null
            || !intent.getAction().equals(Intents.WifiConnect.ACTION)) {
        finish();
        return;
    } */

    String ssid = intent.getStringExtra("ssid");
    String password = intent.getStringExtra("password");
    String networkType = intent.getStringExtra("type");
    setContentView(R.layout.network);
    statusView = (TextView) findViewById(R.id.networkStatus);

    NetworkType networkT;
    if ("WPA".equals(networkType)) {
        networkT = NetworkType.NETWORK_WPA;
    } else if ("WEP".equals(networkType)) {
        networkT = NetworkType.NETWORK_WEP;
    } else if ("nopass".equals(networkType)) {
        networkT = NetworkType.NETWORK_NOPASS;
    } else {
        networkT = NetworkType.NETWORK_INVALID;
    }

    // This is not available before onCreate
    wifiManager = (WifiManager) this.getSystemService(WIFI_SERVICE);
    // Start WiFi, otherwise nothing will work
    wifiManager.setWifiEnabled(true);

    // So we know when the network changes
    wifiReceiver = new WifiReceiver(wifiManager, this, statusView, ssid);

    // The order matters!
    mWifiStateFilter = new IntentFilter(
            WifiManager.WIFI_STATE_CHANGED_ACTION);
    mWifiStateFilter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
    mWifiStateFilter.addAction(WifiManager.SUPPLICANT_STATE_CHANGED_ACTION);
    mWifiStateFilter.addAction(WifiManager.NETWORK_STATE_CHANGED_ACTION);
    registerReceiver(wifiReceiver, mWifiStateFilter);
    receiverRegistered = true;

    if (password == null) {
        password = "";
    }
    Log.d(TAG, "Adding new configuration: 
SSID: " + ssid + "Type: "
            + networkT);
    NetworkSetting setting = new NetworkSetting(ssid, password, networkT);

    changeNetwork(setting);
}

@Override
public void onPause() {
    super.onPause();
    if (receiverRegistered) {
        unregisterReceiver(wifiReceiver);
        receiverRegistered = false;
    }
}

@Override
public void onResume() {
    super.onResume();
    if (wifiReceiver != null && mWifiStateFilter != null
            && !receiverRegistered) {
        registerReceiver(wifiReceiver, mWifiStateFilter);
        receiverRegistered = true;
    }
}

@Override
protected void onDestroy() {
    if (wifiReceiver != null) {
        if (receiverRegistered) {
            unregisterReceiver(wifiReceiver);
            receiverRegistered = false;
        }
        wifiReceiver = null;
    }
    super.onDestroy();
}

/**
 * Update the network: either create a new network or modify an existing
 * network
 * 
 * @param config
 *            the new network configuration
 * @param disableOthers
 *            true if other networks must be disabled
 * @return network ID of the connected network.
 */
private int updateNetwork(WifiConfiguration config, boolean disableOthers) {
    WifiConfiguration found = findNetworkInExistingConfig(config.SSID);
    wifiManager.disconnect();
    if (found == null) {
        Log.i("WIFI","SSID NOT FOUND");
        statusView.setText(R.string.wifi_creating_network);
    } else {
        statusView.setText(R.string.wifi_modifying_network);
        Log.d(TAG, "Removing network " + found.networkId);
        wifiManager.removeNetwork(found.networkId);
        wifiManager.saveConfiguration();
    }
    networkId = wifiManager.addNetwork(config);
    Log.d(TAG, "Inserted/Modified network " + networkId);
    if (networkId < 0) {
        wifiManager.setWifiEnabled(true);
        networkId = wifiManager.addNetwork(config);
        Log.d(TAG, "Again Inserted/Modified network " + networkId);
        return FAILURE_NO_NETWORK_ID;
    }

    // Try to disable the current network and start a new one.
    if (!wifiManager.enableNetwork(networkId, disableOthers)) {
        networkId = FAILURE_NO_NETWORK_ID;
        return FAILURE_NO_NETWORK_ID;
    }
    errorCount = 0;
    wifiManager.reassociate();
    return networkId;
}

Here is my working code : ( its different from my previous code )

    package com.idg.project.utils;


import java.util.List;
import java.util.regex.Pattern;

import android.net.wifi.WifiConfiguration;
import android.net.wifi.WifiManager;
import android.util.Log;



/**
 * @author Vikram Aggarwal
 * @author Sean Owen
 */
public final class WifiConfigManager {

  private static final String TAG = WifiConfigManager.class.getSimpleName();

  private static final Pattern HEX_DIGITS = Pattern.compile("[0-9A-Fa-f]+");

  private WifiConfigManager() {
  }

  public static void configure(final WifiManager wifiManager, 
                               final String ssid, 
                               final String password, 
                               final String networkTypeString) {
    Runnable configureRunnable = new Runnable() {
      public void run() {
        // Start WiFi, otherwise nothing will work
        if (!wifiManager.isWifiEnabled()) {
          Log.i(TAG, "Enabling wi-fi...");
          if (wifiManager.setWifiEnabled(true)) {
            Log.i(TAG, "Wi-fi enabled");
          } else {
            Log.w(TAG, "Wi-fi could not be enabled!");
            return;
          }
          // This happens very quickly, but need to wait for it to enable. A little busy wait?
          int count = 0;
          while (!wifiManager.isWifiEnabled()) {
            if (count >= 10) {
              Log.i(TAG, "Took too long to enable wi-fi, quitting");
              return;
            }
            Log.i(TAG, "Still waiting for wi-fi to enable...");
            try {
              Thread.sleep(1000L);
            } catch (InterruptedException ie) {
              // continue
            }
            count++;
          }
        }
        NetworkType networkType = NetworkType.forIntentValue(networkTypeString);
        if (networkType == NetworkType.NO_PASSWORD) {
          changeNetworkUnEncrypted(wifiManager, ssid);
        } else {
          if (password == null || password.length() == 0) {
            throw new IllegalArgumentException();
          }
          if (networkType == NetworkType.WEP) {
            changeNetworkWEP(wifiManager, ssid, password);
          } else if (networkType == NetworkType.WPA) {
            changeNetworkWPA(wifiManager, ssid, password);
          }        }
      }
    };
    new Thread(configureRunnable).start();
  }

  /**
   * Update the network: either create a new network or modify an existing network
   * @param config the new network configuration
   * @return network ID of the connected network.
   */
  private static void updateNetwork(WifiManager wifiManager, WifiConfiguration config) {
    Integer foundNetworkID = findNetworkInExistingConfig(wifiManager, config.SSID);
    if (foundNetworkID != null) {
      Log.i(TAG, "Removing old configuration for network " + config.SSID);
      wifiManager.removeNetwork(foundNetworkID);
      wifiManager.saveConfiguration();
    }
    int networkId = wifiManager.addNetwork(config);
    if (networkId >= 0) {
      // Try to disable the current network and start a new one.
      if (wifiManager.enableNetwork(networkId, true)) {
        Log.i(TAG, "Associating to network " + config.SSID);
        wifiManager.saveConfiguration();
      } else {
        Log.w(TAG, "Failed to enable network " + config.SSID);
      }
    } else {
      Log.w(TAG, "Unable to add network " + config.SSID);
    }
  }

  private static WifiConfiguration changeNetworkCommon(String ssid) {
    WifiConfiguration config = new WifiConfiguration();
    config.allowedAuthAlgorithms.clear();
    config.allowedGroupCiphers.clear();
    config.allowedKeyManagement.clear();
    config.allowedPairwiseCiphers.clear();
    config.allowedProtocols.clear();
    // Android API insists that an ascii SSID must be quoted to be correctly handled.
    config.SSID = quoteNonHex(ssid);
    return config;
  }

  // Adding a WEP network
  private static void changeNetworkWEP(WifiManager wifiManager, String ssid, String password) {
    WifiConfiguration config = changeNetworkCommon(ssid);
    config.wepKeys[0] = quoteNonHex(password, 10, 26, 58);
    config.wepTxKeyIndex = 0;
    config.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.SHARED);
    config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP104);
    updateNetwork(wifiManager, config);
  }

  // Adding a WPA or WPA2 network
  private static void changeNetworkWPA(WifiManager wifiManager, String ssid, String password) {
    WifiConfiguration config = changeNetworkCommon(ssid);
    // Hex passwords that are 64 bits long are not to be quoted.
    config.preSharedKey = quoteNonHex(password, 64);
    config.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN);
    config.allowedProtocols.set(WifiConfiguration.Protocol.WPA); // For WPA
    config.allowedProtocols.set(WifiConfiguration.Protocol.RSN); // For WPA2
    config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);
    config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_EAP);
    config.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.TKIP);
    config.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
    config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
    updateNetwork(wifiManager, config);
  }

  // Adding an open, unsecured network
  private static void changeNetworkUnEncrypted(WifiManager wifiManager, String ssid) {
    WifiConfiguration config = changeNetworkCommon(ssid);
    config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);
    updateNetwork(wifiManager, config);
  }

  private static Integer findNetworkInExistingConfig(WifiManager wifiManager, String ssid) {
    List<WifiConfiguration> existingConfigs = wifiManager.getConfiguredNetworks();
    for (WifiConfiguration existingConfig : existingConfigs) {
      if (existingConfig.SSID.equals(ssid)) {
        return existingConfig.networkId;
      }
    }
    return null;
  }

  private static String quoteNonHex(String value, int... allowedLengths) {
    return isHexOfLength(value, allowedLengths) ? value : convertToQuotedString(value);
  }

  /**
   * Encloses the incoming string inside double quotes, if it isn't already quoted.
   * @param string the input string
   * @return a quoted string, of the form "input".  If the input string is null, it returns null
   * as well.
   */
  private static String convertToQuotedString(String string) {
    if (string == null || string.length() == 0) {
      return null;
    }
    // If already quoted, return as-is
    if (string.charAt(0) == '"' && string.charAt(string.length() - 1) == '"') {
      return string;
    }
    return '"' + string + '"';
  }

  /**
   * @param value input to check
   * @param allowedLengths allowed lengths, if any
   * @return true if value is a non-null, non-empty string of hex digits, and if allowed lengths are given, has
   *  an allowed length
   */
  private static boolean isHexOfLength(CharSequence value, int... allowedLengths) {
    if (value == null || !HEX_DIGITS.matcher(value).matches()) {
      return false;
    }
    if (allowedLengths.length == 0) {
      return true;
    }
    for (int length : allowedLengths) {
      if (value.length() == length) {
        return true;
      }
    }
    return false;
  }

}









    package com.idg.project.utils;



enum NetworkType {

  WEP,
  WPA,
  NO_PASSWORD;

  static NetworkType forIntentValue(String networkTypeString) {
    if (networkTypeString == null) {
      return NO_PASSWORD;
    }
    if ("WPA".equals(networkTypeString)) {
      return WPA;
    }
    if ("WEP".equals(networkTypeString)) {
      return WEP;
    }
    if ("nopass".equals(networkTypeString)) {
      return NO_PASSWORD;
    }
    throw new IllegalArgumentException(networkTypeString);
  }

}

解决方案

You need to create wifiLock with WIFI_MODE_FULL_HIGH_PERF mode, based on the docs it will only work with the following constraints:

  1. The lock is only active when the device is connected to an access point.
  2. The lock is only active when the screen is on.
  3. The lock is only active when the acquiring app is running in the foreground.

这篇关于android以编程方式打开wifi的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆