1. 程式人生 > >Android Wifi --自動連線指定SSID(各種加密方式均可)

Android Wifi --自動連線指定SSID(各種加密方式均可)

Android Wifi API參考網站這裡寫連結內容
1.開始先加入wifi許可權

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

2.自動連線指定SSID實現程式碼
wificonnect.java


import java.util.List;
import android.content.Context;
import android.net.wifi.ScanResult;
import
android.net.wifi.WifiConfiguration; import android.net.wifi.WifiInfo; import android.net.wifi.WifiManager; import android.text.TextUtils; import android.util.Log; public class WifiConnect { private static final String TAG = "WifiConnect"; //定義WifiManager物件 private WifiManager mWifiManager; // 定義WifiInfo物件
private WifiInfo mWifiInfo; private AccessPoint mAccessPoint; private ScanResult mresult; private Context mcontext; //建構函式 public WifiConnect(Context context){ mcontext = context; // 取得WifiManager物件 mWifiManager = (WifiManager)context.getSystemService(Context.WIFI_SERVICE); // 取得WifiInfo物件 mWifiInfo = mWifiManager.getConnectionInfo(); } //開啟wifi功能 private boolean OpenWifi(){ boolean bRet = true; if (!mWifiManager.isWifiEnabled()){ bRet = mWifiManager.setWifiEnabled(true); } return bRet; } //從掃描結果中提取需要的wifi private boolean getScanResultsBySSID(String ssid){ List<ScanResult> list = mWifiManager.getScanResults(); for (ScanResult result : list){ if (TextUtils.equals(result.SSID, ssid)){ mresult=result; return true; } } return false; } //檢視以前是否也配置過這個網路 private WifiConfiguration IsExsits(String SSID){ List<WifiConfiguration> existingConfigs = mWifiManager.getConfiguredNetworks(); for (WifiConfiguration existingConfig : existingConfigs) { if (existingConfig.SSID.equals("\""+SSID+"\"")){ return existingConfig; } } return null; } //提供一個外部介面,傳入要連線的無線網 public boolean Connect(String SSID, String Password) { if(!this.OpenWifi()) { return false; } //開啟wifi功能需要一段時間(我在手機上測試一般需要1-3秒左右),所以要等到wifi //狀態變成WifiManager.WIFI_STATE_ENABLED的時候才能執行下面的語句 while( !(mWifiManager.getWifiState()==WifiManager.WIFI_STATE_ENABLED) ) { try{ //為了避免程式一直while迴圈,讓它睡個100毫秒在檢測…… Thread.currentThread(); Thread.sleep(100); } catch(InterruptedException ie){ } } Log.i(TAG, "---BeginScan-SSID---"); //等待掃描完wifi while( !getScanResultsBySSID(SSID) ) { try{ //為了避免程式一直while迴圈,讓它睡個100毫秒在檢測…… Thread.currentThread(); Thread.sleep(100); } catch(InterruptedException ie){ } } Log.i(TAG, "---EndScan-SSID---"); WifiConfiguration config = new WifiConfiguration(); mAccessPoint = new AccessPoint(mcontext,mresult); //判斷以前是否儲存過此WIFI環境 WifiConfiguration tempConfig = this.IsExsits(SSID); if(tempConfig != null){ mWifiManager.removeNetwork(tempConfig.networkId); } config = mAccessPoint.getConfig(Password, null, null); Log.i(TAG, "----wifi--config--"+config); int netID = mWifiManager.addNetwork(config); boolean bRet = mWifiManager.enableNetwork(netID,false); if(bRet){ //保持WIFI配置檔案 mWifiManager.saveConfiguration(); } Log.i(TAG, "------WifiConnectState---"+bRet); return bRet; } }

AccessPoint.java 此檔案是從Android Setting 原始碼中提取出來的

package com.example.wifihotinterface;

import static android.net.wifi.WifiConfiguration.INVALID_NETWORK_ID;
import android.content.Context;
import android.net.LinkProperties;
import android.net.NetworkInfo.DetailedState;
import android.net.wifi.ScanResult;
import android.net.wifi.WifiConfiguration;
import android.net.wifi.WifiConfiguration.AuthAlgorithm;
import android.net.wifi.WifiConfiguration.IpAssignment;
import android.net.wifi.WifiConfiguration.KeyMgmt;
import android.net.wifi.WifiInfo;
import android.net.wifi.WifiManager;
import android.os.Bundle;
import android.preference.Preference;
import android.security.Credentials;
import android.text.TextUtils;
import android.util.Log;
import com.example.wifihotinterface.R;


public class AccessPoint extends Preference {
    static final String TAG = "Settings.AccessPoint";

    private static final String KEY_DETAILEDSTATE = "key_detailedstate";
    private static final String KEY_WIFIINFO = "key_wifiinfo";
    private static final String KEY_SCANRESULT = "key_scanresult";
    private static final String KEY_CONFIG = "key_config";

    private static final String KEYSTORE_SPACE = WifiConfiguration.KEYSTORE_URI;


    /** These values are matched in string arrays -- changes must be kept in sync */
    static final int SECURITY_NONE = 0;
    static final int SECURITY_WEP = 1;
    static final int SECURITY_PSK = 2;
    static final int SECURITY_EAP = 3;

    enum PskType {
        UNKNOWN,
        WPA,
        WPA2,
        WPA_WPA2
    }

    String ssid;
    String bssid;
    int security;
    int networkId;
    boolean wpsAvailable = false;

    PskType pskType = PskType.UNKNOWN;

    private WifiConfiguration mConfig;
    /* package */ScanResult mScanResult;

    private int mRssi;
    private WifiInfo mInfo;
    private DetailedState mState;

    static int getSecurity(WifiConfiguration config) {
        if (config.allowedKeyManagement.get(KeyMgmt.WPA_PSK)) {
            return SECURITY_PSK;
        }
        if (config.allowedKeyManagement.get(KeyMgmt.WPA_EAP) ||
                config.allowedKeyManagement.get(KeyMgmt.IEEE8021X)) {
            return SECURITY_EAP;
        }
        return (config.wepKeys[0] != null) ? SECURITY_WEP : SECURITY_NONE;
    }

    private static int getSecurity(ScanResult result) {
        if (result.capabilities.contains("WEP")) {
            return SECURITY_WEP;
        } else if (result.capabilities.contains("PSK")) {
            return SECURITY_PSK;
        } else if (result.capabilities.contains("EAP")) {
            return SECURITY_EAP;
        }
        return SECURITY_NONE;
    }

    public boolean isLock() {
        return security != SECURITY_NONE;
    }

    private static PskType getPskType(ScanResult result) {
        boolean wpa = result.capabilities.contains("WPA-PSK");
        boolean wpa2 = result.capabilities.contains("WPA2-PSK");
        if (wpa2 && wpa) {
            return PskType.WPA_WPA2;
        } else if (wpa2) {
            return PskType.WPA2;
        } else if (wpa) {
            return PskType.WPA;
        } else {
            Log.w(TAG, "Received abnormal flag string: " + result.capabilities);
            return PskType.UNKNOWN;
        }
    }

    AccessPoint(Context context, WifiConfiguration config) {
        super(context);
        loadConfig(config);
    }

    AccessPoint(Context context, ScanResult result) {
        super(context);
        loadResult(result);
    }

    public void saveWifiState(Bundle savedState) {
        savedState.putParcelable(KEY_CONFIG, mConfig);
        savedState.putParcelable(KEY_SCANRESULT, mScanResult);
        savedState.putParcelable(KEY_WIFIINFO, mInfo);
        if (mState != null) {
            savedState.putString(KEY_DETAILEDSTATE, mState.toString());
        }
    }

    private void loadConfig(WifiConfiguration config) {
        ssid = (config.SSID == null ? "" : removeDoubleQuotes(config.SSID));
        bssid = config.BSSID;
        security = getSecurity(config);
        networkId = config.networkId;
        mRssi = Integer.MAX_VALUE;
        mConfig = config;
    }

    private void loadResult(ScanResult result) {
        ssid = result.SSID;
        bssid = result.BSSID;
        security = getSecurity(result);
        wpsAvailable = security != SECURITY_EAP && result.capabilities.contains("WPS");
        if (security == SECURITY_PSK)
            pskType = getPskType(result);
        networkId = -1;
        mRssi = result.level;
        mScanResult = result;
    }

    @Override
    public int compareTo(Preference preference) {
        if (!(preference instanceof AccessPoint)) {
            return 1;
        }
        AccessPoint other = (AccessPoint) preference;
        // Active one goes first.
        if (mInfo != null && other.mInfo == null) return -1;
        if (mInfo == null && other.mInfo != null) return 1;

        // Reachable one goes before unreachable one.
        if (mRssi != Integer.MAX_VALUE && other.mRssi == Integer.MAX_VALUE) return -1;
        if (mRssi == Integer.MAX_VALUE && other.mRssi != Integer.MAX_VALUE) return 1;

        // Configured one goes before unconfigured one.
        if (networkId != WifiConfiguration.INVALID_NETWORK_ID
                && other.networkId == WifiConfiguration.INVALID_NETWORK_ID) return -1;
        if (networkId == WifiConfiguration.INVALID_NETWORK_ID
                && other.networkId != WifiConfiguration.INVALID_NETWORK_ID) return 1;

        // Sort by signal strength.
        int difference = WifiManager.compareSignalLevel(other.mRssi, mRssi);
        if (difference != 0) {
            return difference;
        }
        // Sort by ssid.
        return ssid.compareToIgnoreCase(other.ssid);
    }

    @Override
    public boolean equals(Object other) {
        if (!(other instanceof AccessPoint)) return false;
        return (this.compareTo((AccessPoint) other) == 0);
    }

    @Override
    public int hashCode() {
        int result = 0;
        if (mInfo != null) result += 13 * mInfo.hashCode();
        result += 19 * mRssi;
        result += 23 * networkId;
        result += 29 * ssid.hashCode();
        return result;
    }

    boolean update(ScanResult result) {
        if (ssid.equals(result.SSID) && security == getSecurity(result)) {
            if (WifiManager.compareSignalLevel(result.level, mRssi) > 0) {
                int oldLevel = getLevel();
                mRssi = result.level;
                if (getLevel() != oldLevel) {
                }
            }
            // This flag only comes from scans, is not easily saved in config
            if (security == SECURITY_PSK) {
                pskType = getPskType(result);
            }
            return true;
        }
        return false;
    }
    void update(WifiInfo info, DetailedState state) {
        if (info != null && networkId != WifiConfiguration.INVALID_NETWORK_ID
                && networkId == info.getNetworkId()) {
            mRssi = info.getRssi();
            mInfo = info;
            mState = state;
        } else if (mInfo != null) {
            mInfo = null;
            mState = null;
        }
    }
    int getLevel() {
        if (mRssi == Integer.MAX_VALUE) {
            return -1;
        }
        return WifiManager.calculateSignalLevel(mRssi, 5);
    }
    WifiConfiguration getConfig() {
        return mConfig;
    }
    WifiInfo getInfo() {
        return mInfo;
    }
    DetailedState getState() {
        return mState;
    }
    static String removeDoubleQuotes(String string) {
        int length = string.length();
        if ((length > 1) && (string.charAt(0) == '"')
                && (string.charAt(length - 1) == '"')) {
            return string.substring(1, length - 1);
        }
        return string;
    }
    static String convertToQuotedString(String string) {
        return "\"" + string + "\"";
    }
    /**
     * Generate and save a default wifiConfiguration with common values.
     * Can only be called for unsecured networks.
     * @hide
     */
    protected void generateOpenNetworkConfig() {
        if (security != SECURITY_NONE)
            throw new IllegalStateException();
        if (mConfig != null)
            return;
        mConfig = new WifiConfiguration();
        mConfig.SSID = AccessPoint.convertToQuotedString(ssid);
        mConfig.allowedKeyManagement.set(KeyMgmt.NONE);
    }    
    public static boolean requireKeyStore(WifiConfiguration config) {
        if (config == null) {
            return false;
        }
        if (!TextUtils.isEmpty(config.key_id.value())) {
            return true;
        }
        String values[] = { config.ca_cert.value(), config.client_cert.value() };
        for (String value : values) {
            if (value != null && value.startsWith(KEYSTORE_SPACE)) {
                return true;
            }
        }
        return false;
    }
    public boolean isEqualAP(WifiInfo info) {
        if (info == null) {
            return false;
        }
        return ssid.equals(removeDoubleQuotes(info.getSSID()));
    }  
    public boolean hasValidNetworkId() {
        return networkId != INVALID_NETWORK_ID;
    }    
    public WifiConfiguration getConfig(String password, IpAssignment ipAssignment, LinkProperties linkProperties) {
        WifiConfiguration config = new WifiConfiguration();

        if (networkId == INVALID_NETWORK_ID) {
            config.SSID = AccessPoint.convertToQuotedString(ssid);
        } else {
            config.networkId = networkId;
        }
        switch (security) {
        case AccessPoint.SECURITY_NONE:
            config.allowedKeyManagement.set(KeyMgmt.NONE);
            break;
        case AccessPoint.SECURITY_WEP:
            config.allowedKeyManagement.set(KeyMgmt.NONE);
            config.allowedAuthAlgorithms.set(AuthAlgorithm.OPEN);
            config.allowedAuthAlgorithms.set(AuthAlgorithm.SHARED);
            if (password.length() != 0) {
                int length = password.length();
                // WEP-40, WEP-104, and 256-bit WEP (WEP-232?)
                if ((length == 10 || length == 26 || length == 58)
                        && password.matches("[0-9A-Fa-f]*")) {
                    config.wepKeys[0] = password;
                } else {
                    config.wepKeys[0] = '"' + password + '"';
                }
            }
            break;
        case AccessPoint.SECURITY_PSK:
            config.allowedKeyManagement.set(KeyMgmt.WPA_PSK);
            if (password.length() != 0) {
                if (password.matches("[0-9A-Fa-f]{64}")) {
                    config.preSharedKey = password;
                } else {
                    config.preSharedKey = '"' + password + '"';
                }
            }
            break;
        case AccessPoint.SECURITY_EAP:
            config.allowedKeyManagement.set(KeyMgmt.WPA_EAP);
            config.allowedKeyManagement.set(KeyMgmt.IEEE8021X);
            config.eap.setValue("");
            config.phase2.setValue("");
            config.ca_cert.setValue(Credentials.CA_CERTIFICATE);
            config.client_cert.setValue(Credentials.USER_CERTIFICATE);
            final boolean isEmptyKeyId = true;
            config.key_id.setValue("");
            config.engine
                    .setValue(isEmptyKeyId ? WifiConfiguration.ENGINE_DISABLE
                            : WifiConfiguration.ENGINE_ENABLE);
            config.engine_id.setValue(isEmptyKeyId ? ""
                    : WifiConfiguration.KEYSTORE_ENGINE_ID);
            config.identity.setValue("");
            config.anonymous_identity.setValue("");
            if (password.length() != 0) {
                config.password.setValue(password);
            }
            break;
        default:
            return null;
        }       
        if (ipAssignment != null) {
            config.ipAssignment = ipAssignment;
        }
        if (linkProperties != null) {
            config.linkProperties = new LinkProperties(linkProperties);
        }
        mConfig = config;
        return config;
    }
    public void invalidNetworkId() {
        networkId = INVALID_NETWORK_ID;
    }
    public String getStatus() {
        String result = "";
        Context context = getContext();
        if (mState != null) { // This is the active connection
            result = Summary.get(context, mState);
        } else if (mRssi == Integer.MAX_VALUE) { // Wifi out of range
            result = context.getString(R.string.wifi_not_in_range);
        } else if (mConfig != null && mConfig.status == WifiConfiguration.Status.DISABLED) {
            switch (mConfig.disableReason) {
                case WifiConfiguration.DISABLED_AUTH_FAILURE:
                    result = context.getString(R.string.wifi_disabled_password_failure);
                    break;
                case WifiConfiguration.DISABLED_DHCP_FAILURE:
                case WifiConfiguration.DISABLED_DNS_FAILURE:
                    result = context.getString(R.string.wifi_disabled_network_failure);
                    break;
                case WifiConfiguration.DISABLED_UNKNOWN_REASON:
                    result = context.getString(R.string.wifi_disabled_generic);
            }
        } else { // In range, not disabled.
            StringBuilder summary = new StringBuilder();
            if (mConfig != null) { // Is saved network
                summary.append(context.getString(R.string.wifi_remembered));
            }
            result = summary.toString();
        }
        return result;
    }
}

Summary.java 此檔案也是從Android Setting原始碼中提取

import com.example.wifihotinterface.R;
import android.content.Context;
import android.net.NetworkInfo.DetailedState;

public class Summary {
    static String get(Context context, String ssid, DetailedState state) {
        String[] formats = context.getResources().getStringArray((ssid == null)
                ? R.array.wifi_status : R.array.wifi_status_with_ssid);
        int index = state.ordinal();

        if (index >= formats.length || formats[index].length() == 0) {
            return null;
        }
        return String.format(formats[index], ssid);
    }

    static String get(Context context, DetailedState state) {
        if (state == DetailedState.VERIFYING_POOR_LINK)
            state = DetailedState.CONNECTED;
        return get(context, null, state);
    }
}
  1. 有些標籤需要自己新增。
  2. 此文自己學習總結,有錯請指出。