Jürgen Skrotzky 7 жил өмнө
parent
commit
82eac1dec4

+ 252 - 178
ESPAsyncWiFiManager.cpp

@@ -76,8 +76,8 @@ void AsyncWiFiManager::addParameter(AsyncWiFiManagerParameter *p) {
 }
 
 void AsyncWiFiManager::setupConfigPortal() {
- // dnsServer.reset(new DNSServer());
- // server.reset(new ESP8266WebServer(80));
+  // dnsServer.reset(new DNSServer());
+  // server.reset(new ESP8266WebServer(80));
 
   DEBUG_WM(F(""));
   _configPortalStart = millis();
@@ -128,8 +128,47 @@ void AsyncWiFiManager::setupConfigPortal() {
 
 }
 
+static const char HEX_CHAR_ARRAY[17] = "0123456789ABCDEF";
+/**
+* convert char array (hex values) to readable string by seperator
+* buf:           buffer to convert
+* length:        data length
+* strSeperator   seperator between each hex value
+* return:        formated value as String
+*/
+static String byteToHexString(uint8_t* buf, uint8_t length, String strSeperator="-") {
+  String dataString = "";
+  for (uint8_t i = 0; i < length; i++) {
+    byte v = buf[i] / 16;
+    byte w = buf[i] % 16;
+    if (i>0) {
+      dataString += strSeperator;
+    }
+    dataString += String(HEX_CHAR_ARRAY[v]);
+    dataString += String(HEX_CHAR_ARRAY[w]);
+  }
+  dataString.toUpperCase();
+  return dataString;
+} // byteToHexString
+
+String getESP32ChipID() {
+  uint64_t chipid;
+  chipid=ESP.getEfuseMac();//The chip ID is essentially its MAC address(length: 6 bytes).
+  int chipid_size = 6;
+  uint8_t chipid_arr[chipid_size];
+  for (uint8_t i=0; i < chipid_size; i++) {
+    chipid_arr[i] = (chipid >> (8 * i)) & 0xff;
+  }
+  return byteToHexString(chipid_arr, chipid_size, "");
+}
+
 boolean AsyncWiFiManager::autoConnect() {
-  String ssid = "ESP" + String(ESP.getChipId());
+  String ssid = "ESP";
+  #if defined(ESP8266)
+  ssid += String(ESP.getChipId());
+  #else
+  ssid += getESP32ChipID();
+  #endif
   return autoConnect(ssid.c_str(), NULL);
 }
 
@@ -157,108 +196,116 @@ boolean AsyncWiFiManager::autoConnect(char const *apName, char const *apPassword
 
 String AsyncWiFiManager::networkListAsString()
 {
-	String pager ;
-      //display networks in page
-      for (int i = 0; i < wifiSSIDCount; i++) {
-        if (wifiSSIDs[i].duplicate == true) continue; // skip dups
-        int quality = getRSSIasQuality(wifiSSIDs[i].RSSI);
-
-        if (_minimumQuality == -1 || _minimumQuality < quality) {
-          String item = FPSTR(HTTP_ITEM);
-          String rssiQ;
-          rssiQ += quality;
-          item.replace("{v}", wifiSSIDs[i].SSID);
-          item.replace("{r}", rssiQ);
-          if (wifiSSIDs[i].encryptionType != ENC_TYPE_NONE) {
-            item.replace("{i}", "l");
-          } else {
-            item.replace("{i}", "");
-          }
-          pager += item;
+  String pager ;
+  //display networks in page
+  for (int i = 0; i < wifiSSIDCount; i++) {
+    if (wifiSSIDs[i].duplicate == true) continue; // skip dups
+    int quality = getRSSIasQuality(wifiSSIDs[i].RSSI);
+
+    if (_minimumQuality == -1 || _minimumQuality < quality) {
+      String item = FPSTR(HTTP_ITEM);
+      String rssiQ;
+      rssiQ += quality;
+      item.replace("{v}", wifiSSIDs[i].SSID);
+      item.replace("{r}", rssiQ);
+#if defined(ESP8266)
+      if (wifiSSIDs[i].encryptionType != ENC_TYPE_NONE) {
+#else
+      if (wifiSSIDs[i].encryptionType != WIFI_AUTH_OPEN) {
+#endif
+        item.replace("{i}", "l");
+      } else {
+        item.replace("{i}", "");
+      }
+      pager += item;
 
-        } else {
-          DEBUG_WM(F("Skipping due to quality"));
-        }
+    } else {
+      DEBUG_WM(F("Skipping due to quality"));
+    }
 
-      }
-    return pager;
+  }
+  return pager;
 }
 
 String AsyncWiFiManager::scanModal()
 {
-	shouldscan=true;
-	scan();
-	String pager=networkListAsString();
-	return pager;
+  shouldscan=true;
+  scan();
+  String pager=networkListAsString();
+  return pager;
 }
 
 void AsyncWiFiManager::scan()
 {
-   if (!shouldscan) return;
-DEBUG_WM(F("About to scan()"));
-if (wifiSSIDscan)
-{
-  delay(100);
-}
+  if (!shouldscan) return;
+  DEBUG_WM(F("About to scan()"));
+  if (wifiSSIDscan)
+  {
+    delay(100);
+  }
 
-if (wifiSSIDscan)
-{
+  if (wifiSSIDscan)
+  {
     int n = WiFi.scanNetworks();
     DEBUG_WM(F("Scan done"));
     if (n == 0) {
       DEBUG_WM(F("No networks found"));
-     // page += F("No networks found. Refresh to scan again.");
+      // page += F("No networks found. Refresh to scan again.");
     } else {
 
 
-if (wifiSSIDscan)
-{
-/* WE SHOULD MOVE THIS IN PLACE ATOMICALLY */
-  if (wifiSSIDs) delete [] wifiSSIDs;
-  wifiSSIDs = new WiFiResult[n];
-  wifiSSIDCount = n;
-  
-  if (n>0)
-	  shouldscan=false;
+      if (wifiSSIDscan)
+      {
+        /* WE SHOULD MOVE THIS IN PLACE ATOMICALLY */
+        if (wifiSSIDs) delete [] wifiSSIDs;
+        wifiSSIDs = new WiFiResult[n];
+        wifiSSIDCount = n;
 
-  for (int i=0;i<n;i++)
-  {  
-       wifiSSIDs[i].duplicate=false;
+        if (n>0)
+        shouldscan=false;
 
-  	bool res=WiFi.getNetworkInfo(i, wifiSSIDs[i].SSID, wifiSSIDs[i].encryptionType, wifiSSIDs[i].RSSI, wifiSSIDs[i].BSSID, wifiSSIDs[i].channel, wifiSSIDs[i].isHidden);
-  }
-      
+        for (int i=0;i<n;i++)
+        {
+          wifiSSIDs[i].duplicate=false;
 
-      // RSSI SORT
-
-      // old sort
-      for (int i = 0; i < n; i++) {
-        for (int j = i + 1; j < n; j++) {
-          if (wifiSSIDs[j].RSSI > wifiSSIDs[i].RSSI) {
-            std::swap(wifiSSIDs[i], wifiSSIDs[j]);
-          }
+#if defined(ESP8266)
+          bool res=WiFi.getNetworkInfo(i, wifiSSIDs[i].SSID, wifiSSIDs[i].encryptionType, wifiSSIDs[i].RSSI, wifiSSIDs[i].BSSID, wifiSSIDs[i].channel, wifiSSIDs[i].isHidden);
+#else
+          bool res=WiFi.getNetworkInfo(i, wifiSSIDs[i].SSID, wifiSSIDs[i].encryptionType, wifiSSIDs[i].RSSI, wifiSSIDs[i].BSSID, wifiSSIDs[i].channel);
+#endif
         }
-      }
 
 
-      // remove duplicates ( must be RSSI sorted )
-      if (_removeDuplicateAPs) {
-        String cssid;
+        // RSSI SORT
+
+        // old sort
         for (int i = 0; i < n; i++) {
-          if (wifiSSIDs[i].duplicate == true) continue;
-          cssid = wifiSSIDs[i].SSID;
           for (int j = i + 1; j < n; j++) {
-            if (cssid == wifiSSIDs[j].SSID) {
-              DEBUG_WM("DUP AP: " +wifiSSIDs[j].SSID);              
-              wifiSSIDs[j].duplicate=true; // set dup aps to NULL
+            if (wifiSSIDs[j].RSSI > wifiSSIDs[i].RSSI) {
+              std::swap(wifiSSIDs[i], wifiSSIDs[j]);
             }
           }
         }
-      }
 
-}
-}
-}
+
+        // remove duplicates ( must be RSSI sorted )
+        if (_removeDuplicateAPs) {
+          String cssid;
+          for (int i = 0; i < n; i++) {
+            if (wifiSSIDs[i].duplicate == true) continue;
+            cssid = wifiSSIDs[i].SSID;
+            for (int j = i + 1; j < n; j++) {
+              if (cssid == wifiSSIDs[j].SSID) {
+                DEBUG_WM("DUP AP: " +wifiSSIDs[j].SSID);
+                wifiSSIDs[j].duplicate=true; // set dup aps to NULL
+              }
+            }
+          }
+        }
+
+      }
+    }
+  }
 }
 
 
@@ -267,27 +314,27 @@ void AsyncWiFiManager::startConfigPortalModeless(char const *apName, char const
   _modeless =true;
   _apName = apName;
   _apPassword = apPassword;
- 
+
   /*
   AJS - do we want this?
-  
+
   */
-  
+
   //setup AP
   WiFi.mode(WIFI_AP_STA);
   DEBUG_WM("SET AP STA");
 
   // try to connect
-	if (connectWifi("", "") == WL_CONNECTED)   {
-	DEBUG_WM(F("IP Address:"));
-	DEBUG_WM(WiFi.localIP());
-	//connected
-	// call the callback!
-	  _savecallback();
+  if (connectWifi("", "") == WL_CONNECTED)   {
+    DEBUG_WM(F("IP Address:"));
+    DEBUG_WM(WiFi.localIP());
+    //connected
+    // call the callback!
+    _savecallback();
+
+  }
 
-	}
 
-  
 
   //notify we entered AP mode
   if ( _apcallback != NULL) {
@@ -301,46 +348,46 @@ void AsyncWiFiManager::startConfigPortalModeless(char const *apName, char const
 }
 
 void AsyncWiFiManager::loop(){
-    dnsServer->processNextRequest();
-    if (_modeless)
+  dnsServer->processNextRequest();
+  if (_modeless)
+  {
+    if ( scannow==-1 || millis() > scannow + 60000)
     {
-		if ( scannow==-1 || millis() > scannow + 60000)
-		{
-		
-		scan();
-		scannow= millis() ;
-		}
-		if (connect) {
-		  connect = false;
-		  //delay(2000);
-		  DEBUG_WM(F("Connecting to new AP"));
-
-		  // using user-provided  _ssid, _pass in place of system-stored ssid and pass
-		  if (connectWifi(_ssid, _pass) != WL_CONNECTED) {
-			DEBUG_WM(F("Failed to connect."));
-		  } else {
-			//connected
-			// alanswx - should we have a config to decide if we should shut down AP?
-			// WiFi.mode(WIFI_STA);
-			//notify that configuration has changed and any optional parameters should be saved
-			if ( _savecallback != NULL) {
-			  //todo: check if any custom parameters actually exist, and check if they really changed maybe
-			  _savecallback();
-			}
-			return;
-		  }
-
-		  if (_shouldBreakAfterConfig) {
-			//flag set to exit after config after trying to connect
-			//notify that configuration has changed and any optional parameters should be saved
-			if ( _savecallback != NULL) {
-			  //todo: check if any custom parameters actually exist, and check if they really changed maybe
-			  _savecallback();
-			}
-			return;
-		  }
-		}
-   }
+
+      scan();
+      scannow= millis() ;
+    }
+    if (connect) {
+      connect = false;
+      //delay(2000);
+      DEBUG_WM(F("Connecting to new AP"));
+
+      // using user-provided  _ssid, _pass in place of system-stored ssid and pass
+      if (connectWifi(_ssid, _pass) != WL_CONNECTED) {
+        DEBUG_WM(F("Failed to connect."));
+      } else {
+        //connected
+        // alanswx - should we have a config to decide if we should shut down AP?
+        // WiFi.mode(WIFI_STA);
+        //notify that configuration has changed and any optional parameters should be saved
+        if ( _savecallback != NULL) {
+          //todo: check if any custom parameters actually exist, and check if they really changed maybe
+          _savecallback();
+        }
+        return;
+      }
+
+      if (_shouldBreakAfterConfig) {
+        //flag set to exit after config after trying to connect
+        //notify that configuration has changed and any optional parameters should be saved
+        if ( _savecallback != NULL) {
+          //todo: check if any custom parameters actually exist, and check if they really changed maybe
+          _savecallback();
+        }
+        return;
+      }
+    }
+  }
 }
 
 boolean  AsyncWiFiManager::startConfigPortal(char const *apName, char const *apPassword) {
@@ -363,16 +410,16 @@ boolean  AsyncWiFiManager::startConfigPortal(char const *apName, char const *apP
     //DNS
     dnsServer->processNextRequest();
 
-	//
-	//  we should do a scan every so often here
-	//
-	if ( millis() > scannow + 10000)
-	{
-	DEBUG_WM(F("About to scan()"));
-	shouldscan=true;  // since we are modal, we can scan every time
-	scan();
-	scannow= millis() ;
-	}
+    //
+    //  we should do a scan every so often here
+    //
+    if ( millis() > scannow + 10000)
+    {
+      DEBUG_WM(F("About to scan()"));
+      shouldscan=true;  // since we are modal, we can scan every time
+      scan();
+      scannow= millis() ;
+    }
 
 
     if (connect) {
@@ -407,8 +454,8 @@ boolean  AsyncWiFiManager::startConfigPortal(char const *apName, char const *apP
     yield();
   }
 
- // server.reset();
- // dnsServer.reset();
+  // server.reset();
+  // dnsServer.reset();
 
   return  WiFi.status() == WL_CONNECTED;
 }
@@ -424,20 +471,25 @@ int AsyncWiFiManager::connectWifi(String ssid, String pass) {
     DEBUG_WM(WiFi.localIP());
   }
   //fix for auto connect racing issue
-//  if (WiFi.status() == WL_CONNECTED) {
-//    DEBUG_WM("Already connected. Bailing out.");
-//    return WL_CONNECTED;
-//  }
+  //  if (WiFi.status() == WL_CONNECTED) {
+  //    DEBUG_WM("Already connected. Bailing out.");
+  //    return WL_CONNECTED;
+  //  }
   //check if we have ssid and pass and force those, if not, try with last saved values
   if (ssid != "") {
     WiFi.begin(ssid.c_str(), pass.c_str());
   } else {
     if (WiFi.SSID()) {
       DEBUG_WM("Using last saved values, should be faster");
+#if defined(ESP8266)
       //trying to fix connection in progress hanging
       ETS_UART_INTR_DISABLE();
       wifi_station_disconnect();
       ETS_UART_INTR_ENABLE();
+#else
+      //esp_wifi_disconnect();
+      WiFi.disconnect(false);
+#endif
 
       WiFi.begin();
     } else {
@@ -482,29 +534,36 @@ uint8_t AsyncWiFiManager::waitForConnectResult() {
 
 void AsyncWiFiManager::startWPS() {
   DEBUG_WM("START WPS");
+#if defined(ESP8266)
   WiFi.beginWPSConfig();
+#else
+  esp_wps_config_t config = WPS_CONFIG_INIT_DEFAULT(ESP_WPS_MODE);
+  esp_wifi_wps_enable(&config);
+  esp_wifi_wps_start(0);
+#endif
   DEBUG_WM("END WPS");
+
 }
 /*
-  String AsyncWiFiManager::getSSID() {
-  if (_ssid == "") {
-    DEBUG_WM(F("Reading SSID"));
-    _ssid = WiFi.SSID();
-    DEBUG_WM(F("SSID: "));
-    DEBUG_WM(_ssid);
-  }
-  return _ssid;
-  }
+String AsyncWiFiManager::getSSID() {
+if (_ssid == "") {
+DEBUG_WM(F("Reading SSID"));
+_ssid = WiFi.SSID();
+DEBUG_WM(F("SSID: "));
+DEBUG_WM(_ssid);
+}
+return _ssid;
+}
 
-  String AsyncWiFiManager::getPassword() {
-  if (_pass == "") {
-    DEBUG_WM(F("Reading Password"));
-    _pass = WiFi.psk();
-    DEBUG_WM("Password: " + _pass);
-    //DEBUG_WM(_pass);
-  }
-  return _pass;
-  }
+String AsyncWiFiManager::getPassword() {
+if (_pass == "") {
+DEBUG_WM(F("Reading Password"));
+_pass = WiFi.psk();
+DEBUG_WM("Password: " + _pass);
+//DEBUG_WM(_pass);
+}
+return _pass;
+}
 */
 String AsyncWiFiManager::getConfigPortalSSID() {
   return _apName;
@@ -593,10 +652,10 @@ void AsyncWiFiManager::handleWifi(AsyncWebServerRequest *request,boolean scan) {
   page += FPSTR(HTTP_HEAD_END);
 
   if (scan) {
-  wifiSSIDscan=false;
-  
-   
-  
+    wifiSSIDscan=false;
+
+
+
     DEBUG_WM(F("Scan done"));
     if (wifiSSIDCount==0) {
       DEBUG_WM(F("No networks found"));
@@ -610,7 +669,7 @@ void AsyncWiFiManager::handleWifi(AsyncWebServerRequest *request,boolean scan) {
       page += pager;
       page += "<br/>";
     }
-    
+
   }
   wifiSSIDscan=true;
 
@@ -746,18 +805,30 @@ void AsyncWiFiManager::handleWifiSave(AsyncWebServerRequest *request) {
 /** Handle the info page */
 String AsyncWiFiManager::infoAsString()
 {
-   String page;
+  String page;
   page += F("<dt>Chip ID</dt><dd>");
+#if defined(ESP8266)
   page += ESP.getChipId();
+#else
+  page += getESP32ChipID();
+#endif
   page += F("</dd>");
   page += F("<dt>Flash Chip ID</dt><dd>");
+#if defined(ESP8266)
   page += ESP.getFlashChipId();
+#else
+  page += F("N/A for ESP32");
+#endif
   page += F("</dd>");
   page += F("<dt>IDE Flash Size</dt><dd>");
   page += ESP.getFlashChipSize();
   page += F(" bytes</dd>");
   page += F("<dt>Real Flash Size</dt><dd>");
+#if defined(ESP8266)
   page += ESP.getFlashChipRealSize();
+#else
+  page += F("N/A for ESP32");
+#endif
   page += F(" bytes</dd>");
   page += F("<dt>Soft AP IP</dt><dd>");
   page += WiFi.softAPIP().toString();
@@ -775,7 +846,6 @@ String AsyncWiFiManager::infoAsString()
   page += WiFi.macAddress();
   page += F("</dd>");
   page += F("</dl>");
-  
   return page;
 }
 
@@ -788,16 +858,16 @@ void AsyncWiFiManager::handleInfo(AsyncWebServerRequest *request) {
   page += FPSTR(HTTP_STYLE);
   page += _customHeadElement;
   if (connect==true)
-  	page += F("<meta http-equiv=\"refresh\" content=\"5; url=/i\">");
+  page += F("<meta http-equiv=\"refresh\" content=\"5; url=/i\">");
   page += FPSTR(HTTP_HEAD_END);
   page += F("<dl>");
   if (connect==true)
   {
-  	page += F("<dt>Trying to connect</dt><dd>");
-  	page += WiFi.status();
-  	page += F("</dd>");
+    page += F("<dt>Trying to connect</dt><dd>");
+    page += WiFi.status();
+    page += F("</dd>");
   }
-  
+
   String pager = infoAsString();
   page +=pager;
   page += FPSTR(HTTP_END);
@@ -823,7 +893,11 @@ void AsyncWiFiManager::handleReset(AsyncWebServerRequest *request) {
 
   DEBUG_WM(F("Sent reset page"));
   delay(5000);
+  #if defined(ESP8266)
   ESP.reset();
+  #else
+  ESP.restart();
+  #endif
   delay(2000);
 }
 
@@ -831,12 +905,12 @@ void AsyncWiFiManager::handleReset(AsyncWebServerRequest *request) {
 
 //removed as mentioned here https://github.com/tzapu/AsyncWiFiManager/issues/114
 /*void AsyncWiFiManager::handle204(AsyncWebServerRequest *request) {
-  DEBUG_WM(F("204 No Response"));
-  request->sendHeader("Cache-Control", "no-cache, no-store, must-revalidate");
-  request->sendHeader("Pragma", "no-cache");
-  request->sendHeader("Expires", "-1");
-  request->send ( 204, "text/plain", "");
-  
+DEBUG_WM(F("204 No Response"));
+request->sendHeader("Cache-Control", "no-cache, no-store, must-revalidate");
+request->sendHeader("Pragma", "no-cache");
+request->sendHeader("Expires", "-1");
+request->send ( 204, "text/plain", "");
+
 }*/
 
 void AsyncWiFiManager::handleNotFound(AsyncWebServerRequest *request) {
@@ -867,7 +941,7 @@ void AsyncWiFiManager::handleNotFound(AsyncWebServerRequest *request) {
 boolean AsyncWiFiManager::captivePortal(AsyncWebServerRequest *request) {
   if (!isIp(request->host()) ) {
     DEBUG_WM(F("Request redirected to captive portal"));
-	AsyncWebServerResponse *response = request->beginResponse(302,"text/plain","");
+    AsyncWebServerResponse *response = request->beginResponse(302,"text/plain","");
     response->addHeader("Location", String("http://") + toStringIp(request->client()->localIP()));
     request->send ( response);
     return true;

+ 185 - 175
ESPAsyncWiFiManager.h

@@ -14,14 +14,24 @@
 #ifndef ESPAsyncWiFiManager_h
 #define ESPAsyncWiFiManager_h
 
-#include <ESP8266WiFi.h>
+#if defined(ESP8266)
+#include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#include "esp_wps.h"
+#define ESP_WPS_MODE WPS_TYPE_PBC
+#endif
 #include <ESPAsyncWebServer.h>
 #include <DNSServer.h>
 #include <memory>
 
+#if defined(ESP8266)
 extern "C" {
   #include "user_interface.h"
 }
+#else
+#include <rom/rtc.h>
+#endif
 
 const char WFM_HTTP_HEAD[] PROGMEM            = "<!DOCTYPE html><html lang=\"en\"><head><meta name=\"viewport\" content=\"width=device-width, initial-scale=1, user-scalable=no\"/><title>{v}</title>";
 const char HTTP_STYLE[] PROGMEM           = "<style>.c{text-align: center;} div,input{padding:5px;font-size:1em;} input{width:95%;} body{text-align: center;font-family:verdana;} button{border:0;border-radius:0.3rem;background-color:#1fa3ec;color:#fff;line-height:2.4rem;font-size:1.2rem;width:100%;} .q{float: right;width: 64px;text-align: right;} .l{background: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAMAAABEpIrGAAAALVBMVEX///8EBwfBwsLw8PAzNjaCg4NTVVUjJiZDRUUUFxdiZGSho6OSk5Pg4eFydHTCjaf3AAAAZElEQVQ4je2NSw7AIAhEBamKn97/uMXEGBvozkWb9C2Zx4xzWykBhFAeYp9gkLyZE0zIMno9n4g19hmdY39scwqVkOXaxph0ZCXQcqxSpgQpONa59wkRDOL93eAXvimwlbPbwwVAegLS1HGfZAAAAABJRU5ErkJggg==\") no-repeat left center;background-size: 1em;}</style>";
@@ -39,190 +49,190 @@ const char HTTP_END[] PROGMEM             = "</div></body></html>";
 #define WIFI_MANAGER_MAX_PARAMS 10
 
 class AsyncWiFiManagerParameter {
-  public:
-    AsyncWiFiManagerParameter(const char *custom);
-    AsyncWiFiManagerParameter(const char *id, const char *placeholder, const char *defaultValue, int length);
-    AsyncWiFiManagerParameter(const char *id, const char *placeholder, const char *defaultValue, int length, const char *custom);
-
-    const char *getID();
-    const char *getValue();
-    const char *getPlaceholder();
-    int         getValueLength();
-    const char *getCustomHTML();
-  private:
-    const char *_id;
-    const char *_placeholder;
-    char       *_value;
-    int         _length;
-    const char *_customHTML;
-
-    void init(const char *id, const char *placeholder, const char *defaultValue, int length, const char *custom);
-
-    friend class AsyncWiFiManager;
+public:
+  AsyncWiFiManagerParameter(const char *custom);
+  AsyncWiFiManagerParameter(const char *id, const char *placeholder, const char *defaultValue, int length);
+  AsyncWiFiManagerParameter(const char *id, const char *placeholder, const char *defaultValue, int length, const char *custom);
+
+  const char *getID();
+  const char *getValue();
+  const char *getPlaceholder();
+  int         getValueLength();
+  const char *getCustomHTML();
+private:
+  const char *_id;
+  const char *_placeholder;
+  char       *_value;
+  int         _length;
+  const char *_customHTML;
+
+  void init(const char *id, const char *placeholder, const char *defaultValue, int length, const char *custom);
+
+  friend class AsyncWiFiManager;
 };
 
 
 class WiFiResult
 {
 public:
-    bool duplicate;
-	String SSID;
-	uint8_t encryptionType;
-	int32_t RSSI;
-	uint8_t* BSSID;
-	int32_t channel;
-	bool isHidden;
-	
-	WiFiResult()
-	{
-	}
-	
-	
+  bool duplicate;
+  String SSID;
+  uint8_t encryptionType;
+  int32_t RSSI;
+  uint8_t* BSSID;
+  int32_t channel;
+  bool isHidden;
+
+  WiFiResult()
+  {
+  }
+
+
 };
 
 class AsyncWiFiManager
 {
-  public:
-    AsyncWiFiManager(AsyncWebServer * server, DNSServer *dns);
-
-    void          scan();
-    String        scanModal();
-    void          loop();
-    String        infoAsString();
-
-    boolean       autoConnect();
-    boolean       autoConnect(char const *apName, char const *apPassword = NULL);
-
-    //if you want to always start the config portal, without trying to connect first
-    boolean       startConfigPortal(char const *apName, char const *apPassword = NULL);
-    void startConfigPortalModeless(char const *apName, char const *apPassword);
-
-    // get the AP name of the config portal, so it can be used in the callback
-    String        getConfigPortalSSID();
-
-    void          resetSettings();
-
-    //sets timeout before webserver loop ends and exits even if there has been no setup.
-    //usefully for devices that failed to connect at some point and got stuck in a webserver loop
-    //in seconds setConfigPortalTimeout is a new name for setTimeout
-    void          setConfigPortalTimeout(unsigned long seconds);
-    void          setTimeout(unsigned long seconds);
-
-    //sets timeout for which to attempt connecting, usefull if you get a lot of failed connects
-    void          setConnectTimeout(unsigned long seconds);
-
-
-    void          setDebugOutput(boolean debug);
-    //defaults to not showing anything under 8% signal quality if called
-    void          setMinimumSignalQuality(int quality = 8);
-    //sets a custom ip /gateway /subnet configuration
-    void          setAPStaticIPConfig(IPAddress ip, IPAddress gw, IPAddress sn);
-    //sets config for a static IP
-    void          setSTAStaticIPConfig(IPAddress ip, IPAddress gw, IPAddress sn);
-    //called when AP mode and config portal is started
-    void          setAPCallback( void (*func)(AsyncWiFiManager*) );
-    //called when settings have been changed and connection was successful
-    void          setSaveConfigCallback( void (*func)(void) );
-    //adds a custom parameter
-    void          addParameter(AsyncWiFiManagerParameter *p);
-    //if this is set, it will exit after config, even if connection is unsucessful.
-    void          setBreakAfterConfig(boolean shouldBreak);
-    //if this is set, try WPS setup when starting (this will delay config portal for up to 2 mins)
-    //TODO
-    //if this is set, customise style
-    void          setCustomHeadElement(const char* element);
-    //if this is true, remove duplicated Access Points - defaut true
-    void          setRemoveDuplicateAPs(boolean removeDuplicates);
-
-  private:
-    DNSServer      *dnsServer;
-    AsyncWebServer *server;
-
-
-    boolean         _modeless;
-    int             scannow;
-    int             shouldscan;
-    
-    //const int     WM_DONE                 = 0;
-    //const int     WM_WAIT                 = 10;
-
-    //const String  HTTP_HEAD = "<!DOCTYPE html><html lang=\"en\"><head><meta name=\"viewport\" content=\"width=device-width, initial-scale=1\"/><title>{v}</title>";
-
-    void          setupConfigPortal();
-    void          startWPS();
-
-    const char*   _apName                 = "no-net";
-    const char*   _apPassword             = NULL;
-    String        _ssid                   = "";
-    String        _pass                   = "";
-    unsigned long _configPortalTimeout    = 0;
-    unsigned long _connectTimeout         = 0;
-    unsigned long _configPortalStart      = 0;
-
-    IPAddress     _ap_static_ip;
-    IPAddress     _ap_static_gw;
-    IPAddress     _ap_static_sn;
-    IPAddress     _sta_static_ip;
-    IPAddress     _sta_static_gw;
-    IPAddress     _sta_static_sn;
-
-    int           _paramsCount            = 0;
-    int           _minimumQuality         = -1;
-    boolean       _removeDuplicateAPs     = true;
-    boolean       _shouldBreakAfterConfig = false;
-    boolean       _tryWPS                 = false;
-
-    const char*   _customHeadElement      = "";
-
-    //String        getEEPROMString(int start, int len);
-    //void          setEEPROMString(int start, int len, String string);
-
-    int           status = WL_IDLE_STATUS;
-    int           connectWifi(String ssid, String pass);
-    uint8_t       waitForConnectResult();
-    
-	String networkListAsString();
-
-    void          handleRoot(AsyncWebServerRequest *);
-    void          handleWifi(AsyncWebServerRequest*,boolean scan);
-    void          handleWifiSave(AsyncWebServerRequest*);
-    void          handleInfo(AsyncWebServerRequest*);
-    void          handleReset(AsyncWebServerRequest*);
-    void          handleNotFound(AsyncWebServerRequest*);
-    void          handle204(AsyncWebServerRequest*);
-    boolean       captivePortal(AsyncWebServerRequest*);
-
-    // DNS server
-    const byte    DNS_PORT = 53;
-
-    //helpers
-    int           getRSSIasQuality(int RSSI);
-    boolean       isIp(String str);
-    String        toStringIp(IPAddress ip);
-
-    boolean       connect;
-    boolean       _debug = true;
-
-    WiFiResult    *wifiSSIDs;
-    int           wifiSSIDCount;
-    boolean       wifiSSIDscan;
-    
-    void (*_apcallback)(AsyncWiFiManager*) = NULL;
-    void (*_savecallback)(void) = NULL;
-
-    AsyncWiFiManagerParameter* _params[WIFI_MANAGER_MAX_PARAMS];
-
-    template <typename Generic>
-    void          DEBUG_WM(Generic text);
-
-    template <class T>
-    auto optionalIPFromString(T *obj, const char *s) -> decltype(  obj->fromString(s)  ) {
-      return  obj->fromString(s);
-    }
-    auto optionalIPFromString(...) -> bool {
-      DEBUG_WM("NO fromString METHOD ON IPAddress, you need ESP8266 core 2.1.0 or newer for Custom IP configuration to work.");
-      return false;
-    }
+public:
+  AsyncWiFiManager(AsyncWebServer * server, DNSServer *dns);
+
+  void          scan();
+  String        scanModal();
+  void          loop();
+  String        infoAsString();
+
+  boolean       autoConnect();
+  boolean       autoConnect(char const *apName, char const *apPassword = NULL);
+
+  //if you want to always start the config portal, without trying to connect first
+  boolean       startConfigPortal(char const *apName, char const *apPassword = NULL);
+  void startConfigPortalModeless(char const *apName, char const *apPassword);
+
+  // get the AP name of the config portal, so it can be used in the callback
+  String        getConfigPortalSSID();
+
+  void          resetSettings();
+
+  //sets timeout before webserver loop ends and exits even if there has been no setup.
+  //usefully for devices that failed to connect at some point and got stuck in a webserver loop
+  //in seconds setConfigPortalTimeout is a new name for setTimeout
+  void          setConfigPortalTimeout(unsigned long seconds);
+  void          setTimeout(unsigned long seconds);
+
+  //sets timeout for which to attempt connecting, usefull if you get a lot of failed connects
+  void          setConnectTimeout(unsigned long seconds);
+
+
+  void          setDebugOutput(boolean debug);
+  //defaults to not showing anything under 8% signal quality if called
+  void          setMinimumSignalQuality(int quality = 8);
+  //sets a custom ip /gateway /subnet configuration
+  void          setAPStaticIPConfig(IPAddress ip, IPAddress gw, IPAddress sn);
+  //sets config for a static IP
+  void          setSTAStaticIPConfig(IPAddress ip, IPAddress gw, IPAddress sn);
+  //called when AP mode and config portal is started
+  void          setAPCallback( void (*func)(AsyncWiFiManager*) );
+  //called when settings have been changed and connection was successful
+  void          setSaveConfigCallback( void (*func)(void) );
+  //adds a custom parameter
+  void          addParameter(AsyncWiFiManagerParameter *p);
+  //if this is set, it will exit after config, even if connection is unsucessful.
+  void          setBreakAfterConfig(boolean shouldBreak);
+  //if this is set, try WPS setup when starting (this will delay config portal for up to 2 mins)
+  //TODO
+  //if this is set, customise style
+  void          setCustomHeadElement(const char* element);
+  //if this is true, remove duplicated Access Points - defaut true
+  void          setRemoveDuplicateAPs(boolean removeDuplicates);
+
+private:
+  DNSServer      *dnsServer;
+  AsyncWebServer *server;
+
+
+  boolean         _modeless;
+  int             scannow;
+  int             shouldscan;
+
+  //const int     WM_DONE                 = 0;
+  //const int     WM_WAIT                 = 10;
+
+  //const String  HTTP_HEAD = "<!DOCTYPE html><html lang=\"en\"><head><meta name=\"viewport\" content=\"width=device-width, initial-scale=1\"/><title>{v}</title>";
+
+  void          setupConfigPortal();
+  void          startWPS();
+
+  const char*   _apName                 = "no-net";
+  const char*   _apPassword             = NULL;
+  String        _ssid                   = "";
+  String        _pass                   = "";
+  unsigned long _configPortalTimeout    = 0;
+  unsigned long _connectTimeout         = 0;
+  unsigned long _configPortalStart      = 0;
+
+  IPAddress     _ap_static_ip;
+  IPAddress     _ap_static_gw;
+  IPAddress     _ap_static_sn;
+  IPAddress     _sta_static_ip;
+  IPAddress     _sta_static_gw;
+  IPAddress     _sta_static_sn;
+
+  int           _paramsCount            = 0;
+  int           _minimumQuality         = -1;
+  boolean       _removeDuplicateAPs     = true;
+  boolean       _shouldBreakAfterConfig = false;
+  boolean       _tryWPS                 = false;
+
+  const char*   _customHeadElement      = "";
+
+  //String        getEEPROMString(int start, int len);
+  //void          setEEPROMString(int start, int len, String string);
+
+  int           status = WL_IDLE_STATUS;
+  int           connectWifi(String ssid, String pass);
+  uint8_t       waitForConnectResult();
+
+  String networkListAsString();
+
+  void          handleRoot(AsyncWebServerRequest *);
+  void          handleWifi(AsyncWebServerRequest*,boolean scan);
+  void          handleWifiSave(AsyncWebServerRequest*);
+  void          handleInfo(AsyncWebServerRequest*);
+  void          handleReset(AsyncWebServerRequest*);
+  void          handleNotFound(AsyncWebServerRequest*);
+  void          handle204(AsyncWebServerRequest*);
+  boolean       captivePortal(AsyncWebServerRequest*);
+
+  // DNS server
+  const byte    DNS_PORT = 53;
+
+  //helpers
+  int           getRSSIasQuality(int RSSI);
+  boolean       isIp(String str);
+  String        toStringIp(IPAddress ip);
+
+  boolean       connect;
+  boolean       _debug = true;
+
+  WiFiResult    *wifiSSIDs;
+  int           wifiSSIDCount;
+  boolean       wifiSSIDscan;
+
+  void (*_apcallback)(AsyncWiFiManager*) = NULL;
+  void (*_savecallback)(void) = NULL;
+
+  AsyncWiFiManagerParameter* _params[WIFI_MANAGER_MAX_PARAMS];
+
+  template <typename Generic>
+  void          DEBUG_WM(Generic text);
+
+  template <class T>
+  auto optionalIPFromString(T *obj, const char *s) -> decltype(  obj->fromString(s)  ) {
+    return  obj->fromString(s);
+  }
+  auto optionalIPFromString(...) -> bool {
+    DEBUG_WM("NO fromString METHOD ON IPAddress, you need ESP8266 core 2.1.0 or newer for Custom IP configuration to work.");
+    return false;
+  }
 };
 
 #endif

+ 4 - 5
examples/AutoConnect/AutoConnect.ino

@@ -1,4 +1,8 @@
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>
@@ -17,10 +21,8 @@ void setup() {
     AsyncWiFiManager wifiManager(&server,&dns);
     //reset saved settings
     //wifiManager.resetSettings();
-    
     //set custom ip for portal
     //wifiManager.setAPConfig(IPAddress(10,0,1,1), IPAddress(10,0,1,1), IPAddress(255,255,255,0));
-
     //fetches ssid and pass from eeprom and tries to connect
     //if it does not connect it starts an access point with the specified name
     //here  "AutoConnectAP"
@@ -28,13 +30,10 @@ void setup() {
     wifiManager.autoConnect("AutoConnectAP");
     //or use this for auto generated name ESP + ChipID
     //wifiManager.autoConnect();
-
-    
     //if you get here you have connected to the WiFi
     Serial.println("connected...yeey :)");
 }
 
 void loop() {
     // put your main code here, to run repeatedly:
-    
 }

+ 6 - 2
examples/AutoConnectWithFSParameters/AutoConnectWithFSParameters.ino

@@ -1,6 +1,10 @@
 #include <FS.h>                   //this needs to be first, or it all crashes and burns...
 
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>
@@ -89,7 +93,7 @@ void setup() {
 
   //set static ip
   wifiManager.setSTAStaticIPConfig(IPAddress(10,0,1,99), IPAddress(10,0,1,1), IPAddress(255,255,255,0));
-  
+
   //add all your parameters here
   wifiManager.addParameter(&custom_mqtt_server);
   wifiManager.addParameter(&custom_mqtt_port);
@@ -101,7 +105,7 @@ void setup() {
   //set minimu quality of signal so it ignores AP's under that quality
   //defaults to 8%
   //wifiManager.setMinimumSignalQuality();
-  
+
   //sets timeout until configuration portal gets turned off
   //useful to make it all retry or go to sleep
   //in seconds

+ 7 - 3
examples/AutoConnectWithFSParametersAndCustomIP/AutoConnectWithFSParametersAndCustomIP.ino

@@ -1,6 +1,10 @@
 #include <FS.h>                   //this needs to be first, or it all crashes and burns...
 
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>
@@ -10,7 +14,7 @@
 #include <ArduinoJson.h>          //https://github.com/bblanchon/ArduinoJson
 
 //define your default values here, if there are different values in config.json, they are overwritten.
-//length should be max size + 1 
+//length should be max size + 1
 char mqtt_server[40];
 char mqtt_port[6] = "8080";
 char blynk_token[33] = "YOUR_BLYNK_TOKEN";
@@ -116,7 +120,7 @@ void setup() {
   _sn.fromString(static_sn);
 
   wifiManager.setSTAStaticIPConfig(_ip, _gw, _sn);
-  
+
   //add all your parameters here
   wifiManager.addParameter(&custom_mqtt_server);
   wifiManager.addParameter(&custom_mqtt_port);
@@ -128,7 +132,7 @@ void setup() {
   //set minimu quality of signal so it ignores AP's under that quality
   //defaults to 8%
   wifiManager.setMinimumSignalQuality();
-  
+
   //sets timeout until configuration portal gets turned off
   //useful to make it all retry or go to sleep
   //in seconds

+ 7 - 3
examples/AutoConnectWithFeedback/AutoConnectWithFeedback.ino

@@ -1,4 +1,8 @@
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>
@@ -18,7 +22,7 @@ DNSServer dns;
 void setup() {
   // put your setup code here, to run once:
   Serial.begin(115200);
-  
+
   //WiFiManager
   //Local intialization. Once its business is done, there is no need to keep it around
   AsyncWiFiManager wifiManager(&server,&dns);
@@ -37,11 +41,11 @@ void setup() {
     //reset and try again, or maybe put it to deep sleep
     ESP.reset();
     delay(1000);
-  } 
+  }
 
   //if you get here you have connected to the WiFi
   Serial.println("connected...yeey :)");
- 
+
 }
 
 void loop() {

+ 5 - 1
examples/AutoConnectWithFeedbackLED/AutoConnectWithFeedbackLED.ino

@@ -1,4 +1,8 @@
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>
@@ -32,7 +36,7 @@ DNSServer dns;
 void setup() {
   // put your setup code here, to run once:
   Serial.begin(115200);
-  
+
   //set led pin as output
   pinMode(BUILTIN_LED, OUTPUT);
   // start ticker with 0.5 because we start in AP mode and try to connect

+ 4 - 0
examples/AutoConnectWithReset/AutoConnectWithReset.ino

@@ -1,6 +1,10 @@
 #include <FS.h>                   //this needs to be first, or it all crashes and burns...
 
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>

+ 7 - 3
examples/AutoConnectWithStaticIP/AutoConnectWithStaticIP.ino

@@ -1,6 +1,10 @@
 #include <FS.h>                   //this needs to be first, or it all crashes and burns...
 
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>
@@ -13,7 +17,7 @@ DNSServer dns;
 
 /**************************************************************************************
  * this example shows how to set a static IP configuration for the ESP
- * although the IP shows in the config portal, the changes will revert 
+ * although the IP shows in the config portal, the changes will revert
  * to the IP set in the source file.
  * if you want the ability to configure and persist the new IP configuration
  * look at the FS examples, which save the config to file
@@ -38,7 +42,7 @@ void setup() {
   //reset settings - for testing
   //wifiManager.resetSettings();
 
-  //set static ip 
+  //set static ip
   //the commented bit only works for ESP8266 core 2.1.0 or newer
   /*IPAddress _ip,_gw,_sn;
   _ip.fromString(static_ip);
@@ -48,7 +52,7 @@ void setup() {
   IPAddress _ip = IPAddress(10, 0, 1, 78);
   IPAddress _gw = IPAddress(10, 0, 1, 1);
   IPAddress _sn = IPAddress(255, 255, 255, 0);
-  
+
   wifiManager.setSTAStaticIPConfig(_ip, _gw, _sn);
 
 

+ 8 - 4
examples/AutoConnectWithTimeout/AutoConnectWithTimeout.ino

@@ -1,4 +1,8 @@
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>
@@ -13,7 +17,7 @@ DNSServer dns;
 void setup() {
   // put your setup code here, to run once:
   Serial.begin(115200);
-  
+
   //WiFiManager
   //Local intialization. Once its business is done, there is no need to keep it around
   AsyncWiFiManager wifiManager(&server,&dns);
@@ -24,7 +28,7 @@ void setup() {
   //useful to make it all retry or go to sleep
   //in seconds
   wifiManager.setTimeout(180);
-  
+
   //fetches ssid and pass and tries to connect
   //if it does not connect it starts an access point with the specified name
   //here  "AutoConnectAP"
@@ -35,11 +39,11 @@ void setup() {
     //reset and try again, or maybe put it to deep sleep
     ESP.reset();
     delay(5000);
-  } 
+  }
 
   //if you get here you have connected to the WiFi
   Serial.println("connected...yeey :)");
- 
+
 }
 
 void loop() {

+ 6 - 2
examples/ModelessConnect/ModelessConnect.ino

@@ -1,4 +1,8 @@
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>
@@ -17,7 +21,7 @@ void setup() {
     //Local intialization. Once its business is done, there is no need to keep it around
     //reset saved settings
     //wifiManager.resetSettings();
-    
+
     //set custom ip for portal
     //wifiManager.setAPConfig(IPAddress(10,0,1,1), IPAddress(10,0,1,1), IPAddress(255,255,255,0));
 
@@ -34,7 +38,7 @@ void setup() {
  server.on("/", HTTP_GET, [](AsyncWebServerRequest *request){
     request->send(200, "text/plain", "Hello World");
   });
-    
+
 }
 
 void loop() {

+ 7 - 3
examples/OnDemandConfigPortal/OnDemandConfigPortal.ino

@@ -1,4 +1,8 @@
+#if defined(ESP8266)
 #include <ESP8266WiFi.h>          //https://github.com/esp8266/Arduino
+#else
+#include <WiFi.h>
+#endif
 
 //needed for library
 #include <DNSServer.h>
@@ -10,7 +14,7 @@ AsyncWebServer server(80);
 DNSServer dns;
 
 // select wich pin will trigger the configuraton portal when set to LOW
-// ESP-01 users please note: the only pins available (0 and 2), are shared 
+// ESP-01 users please note: the only pins available (0 and 2), are shared
 // with the bootloader, so always set them HIGH at power-up
 #define TRIGGER_PIN 0
 
@@ -30,7 +34,7 @@ void loop() {
     //WiFiManager
     //Local intialization. Once its business is done, there is no need to keep it around
     AsyncWiFiManager wifiManager(&server,&dns);
-    
+
     //reset settings - for testing
     //wifiManager.resetSettings();
 
@@ -45,7 +49,7 @@ void loop() {
 
     //WITHOUT THIS THE AP DOES NOT SEEM TO WORK PROPERLY WITH SDK 1.5 , update to at least 1.5.1
     //WiFi.mode(WIFI_STA);
-    
+
     if (!wifiManager.startConfigPortal("OnDemandAP")) {
       Serial.println("failed to connect and hit timeout");
       delay(3000);

+ 4 - 4
library.properties

@@ -1,9 +1,9 @@
 name=ESP Async WiFi Manager
-version=0.12
+version=0.13
 author=alanswx
 maintainer=alanswx
-sentence=ESP8266 Async WiFi Connection manager with fallback web configuration portal
-paragraph=Library for configuring ESP8266 modules WiFi credentials at runtime.
+sentence=ESP8266 and ESP32 Async WiFi Connection manager with fallback web configuration portal
+paragraph=Library for configuring ESP8266 and ESP32 modules WiFi credentials at runtime.
 category=Communication
 url=https://github.com/alanswx/ESPAsyncWiFiManager.git
-architectures=esp8266
+architectures=esp8266,esp32