Esp8266实现手机扫码传递wifi配置信息

Esp8266实现扫码获取可用wifi配置信息


   首先我们需要一块带有屏幕的esp866板子,如下图。有屏了,我们才能在上面玩我们做的东西

Esp8266实现手机扫码传递wifi配置信息_第1张图片

一、流程

  1. ESP从flash中读取wifi信息。
  2. 读取成功,跳转到步骤9
  3. 读取失败,跳转到步骤4
  4. ESP8266创建带有默认密码的热点,并创建一个websocket服务器
  5. 将热点名称、密码、ip和端口生成二维码,显示在屏幕上
  6. 通过手机APP扫描屏幕上的二维码,根据二维码的信息,连接wifi热点
  7. wifi热点连接成功后,连上websocket服务器并将可用的wifi信息传递给esp8266
  8. esp8266成功获取到信息后,断开热点。
  9. 连接真实的wifi
  10. 连接wifi失败,返回到步骤1,
  11. 连接wifi成功,将wifi信息保存到flash中。跳转到步骤12
  12. 做自己想做的事情了

二、所需的库

    我们可以在arduino常用集合中找到我们所需要的库,

    WebSocket:https://github.com/Links2004/arduinoWebSockets

    SSD1306:https://github.com/ThingPulse/esp8266-oled-ssd1306

    qrcode:https://github.com/anunpanya/ESP8266_QRcode

    EEPROM:https://www.arduino.cc/en/Reference/EEPROM

    将下载的库,拷贝到arduino的库目录下面(xxx/Arduino/library)。你也可以通过arduino库管理进行下载,这样可以不用另外拷贝

三、实现代码

  • ESP从flash中读取wifi信息。这里我们通过EEPROM库来从flash读取

    #define EEPROM_HEAD_LEN 6   //头长度,这里需要定义下,如果不定义。无法判断当前读取的是不是你存储的配置
    #define EEPROM_SSID_LEN 32   //wifi ssid
    #define EEPROM_PWD_LEN 32   //wifi pwd
    #define EEPROM_URL_LEN 64   //服务器ip地址或域名
    #define EEPROM_PORT_LEN 4   //端口
    #define EEPROM_PATH_LEN 12  //服务器websocket路径

   #define EEPROM_SIZE (EEPROM_HEAD_LEN+EEPROM_SSID_LEN+EEPROM_PWD_LEN+EEPROM_URL_LEN+EEPRO    M_PORT_LEN+EEPROM_PATH_LEN)

    const char *eeprom_head = "ssid";

    struct ConfigInfo{
        char head[EEPROM_HEAD_LEN];
        char sta_ssid[EEPROM_SSID_LEN];
        char sta_pwd[EEPROM_PWD_LEN];
        char url[EEPROM_URL_LEN];
        int port;
        char path[EEPROM_PATH_LEN];
    };

    boolean readConfig() 
    {
      char tmp[EEPROM_SIZE]={0};
      stepId = IOT_STEP_STA_ING;
      Serial.println("Reading EEPROM...");
      EEPROM.begin(EEPROM_SIZE);
      memset(&config,0,EEPROM_SIZE);
  
      for (int i = 0; i < EEPROM_HEAD_LEN; i++)
      {
          tmp[i] = char(EEPROM.read(i));
      }

      if(strncmp(eeprom_head,tmp,strlen(eeprom_head))==0)
      {
        for(int i=EEPROM_HEAD_LEN;i        {
            tmp[i] = char(EEPROM.read(i));
        }

        memcpy(&config,tmp,EEPROM_SIZE);
        drawText("succ to read config!");
        return true;
      }
      else 
      {
        Serial.println("Config not found.");
        drawText("fail to read config");
        return false;
      }

    }

  • 将数据保存到flash中

    void writeConfig(ConfigInfo info)
    {
        char tmp[EEPROM_SIZE]={0};
        memcpy(tmp,&info,EEPROM_SIZE);
    
        for(int i=0;i        {
          EEPROM.write(i, tmp[i]);
        }
    
        EEPROM.commit();
    }

  • 创建AP热点

    const char *ssid_head = "maxi";
    const char *password = "12345678";

    WiFi.mode(WIFI_AP);
    WiFi.macAddress(mac);
    sprintf(ssid,"%s%02x%02x%02x%02x%02x%02x",ssid_head,mac[0],mac[1],mac[2],mac[3],mac[4],mac[5]);
    WiFi.softAPConfig(ap_ip, ap_ip, ap_netmask); // configure ip address for softAP 

    WiFi.softAP(ssid,password);

  • 创建websocket服务器

    WebSocketsServer webServer = WebSocketsServer(WEBSOCKET_PORT);

    webServer.begin();
    webServer.onEvent(webSocketEvent_config);

  • 生成二维码

#ifdef OLED_QRCODE
  sprintf(buf,"{\"ssid\":\"%s\",""\"pw\":\"%s\",\"ip\":\"%s\",\"port\":\"%d\"}",ssid,password,ap_ip.toString().c_str(),WEBSOCKET_PORT);
  String str(buf);
  display.clear();
  qrcode.init();
  qrcode.create(str);
  display.display();

#endif

四、总结

    思想知道了,这个项目实现起来,还是很简单的。由于项目中内容比较多,这里就不提取代码了。如果有需要,可以共同讨论


你可能感兴趣的:(IOT)