現在,通常,為了讓手機連上一個WiFi熱點,基本上都是打開手機設置里面的WiFi設置功能,然后會看到里面有個WiFi熱點列表,然后選擇你要的連接上。 基本上你只要打開手機連接WiFi功能,都會發現附近有超級多的各種來路不明的WiFi熱點(連接有風險需謹慎),那么手機是怎么知道附近的WiFi的呢?通常,無線網絡提供的WiFi熱點,大部分都開放了SSID廣播(WiFi熱點也可以隱藏的),Scan WiFi的功能就是掃描出所有附近的WiFi熱點的SSID信息,這樣一來,客戶端就可以根據需要選擇不同的SSID連入對應的無線網絡中
scan WiFi功能
一般掃描網絡需要幾百毫秒才能完成。
而掃描WiFi過程包括:
觸發掃描過程
等待完成
提供結果
那么Scan WiFi庫提供了兩種方式實現上面的掃描過程:
1. 同步掃描:通過單個函數在一次運行中完成,需要等待完成所有操作才能繼續運行下面的操作
2. 異步掃描:把上面的過程分成幾個步驟,每個步驟由一個單獨函數完成,我們可以在掃描過程中執行其他任務
ESP8266WiFiScan庫
ESP8266WiFiScan庫,大家使用的時候不需要 #include <ESP8266WiFiSTA.h>
只需要引入 #include<ESP8266WiFi.h>
對於Scan類庫的描述,可以拆分為兩個部分:
1. 第一部分方法,掃描操作;
2. 第二部分方法,獲取掃描結果;

掃描操作方法
語法:
int scanNetworks(bool async = false, bool show_hidden = false, uint8 channel = 0, uint8* ssid = NULL); //掃描周邊有效wifi網絡
async 是否啟動異步掃描
true 異步掃描
false 同步掃描---默認
show_hidden 是否掃描隱藏網絡
channel 是否掃描特定通道
ssid 是否掃描特定的SSID
返回值:找到的個數
實例--同步掃描
//同步掃描 #include <ESP8266WiFi.h> #define AP_SSID "jia" #define AP_PSW "lm654321" void setup() { Serial.begin(115200); delay(2000); WiFi.begin(AP_SSID, AP_PSW); Serial.print(String("連接到:")+AP_SSID); while (WiFi.status() != WL_CONNECTED){ delay(500); Serial.print("."); } Serial.println(""); int n = WiFi.scanNetworks();//同步掃描,同步掃描,等待返回結果---不需要填任何參數
Serial.println("掃描完成"); if (n == 0) { Serial.println("沒有找到熱點網絡"); }else { Serial.printf("找到了%d個網絡",n); } } void loop() { }
實例---異步掃描
//異步掃描 #include <ESP8266WiFi.h> #define AP_SSID "jia" #define AP_PSW "lm654321" void setup() { WiFi.mode(WIFI_STA); WiFi.disconnect();//斷開網絡 Serial.begin(115200); delay(2000); WiFi.begin(AP_SSID, AP_PSW); Serial.print(String("連接到:")+AP_SSID); while (WiFi.status() != WL_CONNECTED){ delay(500); Serial.print("."); } Serial.println(""); Serial.println("連接成功"); WiFi.scanNetworks(true);//異步掃描 delay(3000);//掃描需要一段時間,所以等待一會兒 int n = WiFi.scanComplete(); //返回異步掃描找到的個數 if(n >= 0){ Serial.printf("%d個網絡找到\n", n); for (int i = 0; i < n; i++){ Serial.printf("%d: %s, Ch:%d (%ddBm) %s\n", i+1, WiFi.SSID(i).c_str(), WiFi.channel(i), WiFi.RSSI(i), WiFi.encryptionType(i) == ENC_TYPE_NONE ? "open" : ""); //WiFi.SSID(i) 返回賬號 WiFi.channel(i) 返回通道 //WiFi.RSSI(i) 返回信號強度 WiFi.encryptionType(i) 返回加密類型 } WiFi.scanDelete(); //從內存中刪掉最近掃描結果
//注意點:如果不刪除,將會疊加上次掃描的結果;
}else{ Serial.println("沒有找到網絡"); } } void loop() { }
uint8_t encryptionType(uint8_t networkItem); 獲取wifi網絡加密方式
AUTH_OPEN ----> ENC_TYPE_WEP = 5
AUTH_WEP ----> ENC_TYPE_TKIP = 2
AUTH_WPA_PSK ----> ENC_TYPE_CCMP = 4
AUTH_WPA2_PSK ----> ENC_TYPE_NONE = 7
AUTH_WPA_WPA2_PSK ----> ENC_TYPE_AUTO = 8
void scanNetworksAsync(回調函數名, bool show_hidden = false); //異步掃描周邊wifi網絡,並回調結果 ---個人推進
//異步掃描 #include <ESP8266WiFi.h> #define AP_SSID "jia" #define AP_PSW "lm654321" void setup() { WiFi.mode(WIFI_STA); WiFi.disconnect();//斷開網絡 Serial.begin(115200); delay(2000); WiFi.begin(AP_SSID, AP_PSW); Serial.print(String("連接到:")+AP_SSID); while (WiFi.status() != WL_CONNECTED){ delay(500); Serial.print("."); } Serial.println(""); Serial.println("連接成功"); WiFi.scanNetworksAsync(prinScanResult); //異步掃描周邊wifi網絡,並回調結果 //參數 回調函數 } void loop() { } void prinScanResult(int networksFound){ //回調函數,參數找到網絡的個數 Serial.printf("找到%d個網絡\n", networksFound); for (int i = 0; i < networksFound; i++){ Serial.printf("%d: %s, Ch:%d (%ddBm) %s\n", i + 1, WiFi.SSID(i).c_str(), WiFi.channel(i), WiFi.RSSI(i), WiFi.encryptionType(i) == ENC_TYPE_NONE ? "open" : ""); } }
String BSSIDstr(uint8_t networkItem); 獲取wifi網絡mac地址
bool getNetworkInfo(uint8_t networkItem, String &ssid, uint8_t &encryptionType, int32_t &RSSI, uint8_t*&BSSID, int32_t &channel, bool &isHidden);
//獲取整體網絡信息,名字,信號強度等
注意點:入參前面多數加了&,意味着調完函數后外面獲取到詳細信息;
bool isHidden(uint8_t networkItem); 判斷wifi網絡是否是隱藏網絡
天子驕龍