ESP8266 NodeMCU Trình quản lý Wifi dừng mã hóa cứng thông tin đăng nhập WiFi

ESP8266 NodeMCU Trình quản lý Wifi dừng mã hóa cứng thông tin đăng nhập WiFi

Giới thiệu ESP8266 NodeMCU WiFi Manager

Với việc bổ sung trình quản lý WiFi với thư viện ESPAsyncWebServer, chúng tôi không còn phải cung cấp riêng SSID và mật khẩu của mạng cục bộ trong bản phác thảo Arduino của chúng tôi. Không cần mã hóa cứng. Chúng tôi sẽ có thể tự động kết nối qua các mạng khác (Điểm truy cập) với bảng ESP8266 của mình mà không gặp bất kỳ rắc rối nào khi nhập thủ công thông tin đăng nhập mạng mỗi lần. Nhiều kết nối SSID, cũng như các biến tùy chỉnh bổ sung, cũng có thể được thực hiện thông qua điều này.

Quy trình làm việc

  1. Ban đầu, ESP8266 của chúng tôi sẽ được thiết lập làm Điểm truy cập khi khởi động. Điều này là do bảng ESP8266 bắt đầu bằng việc đọc các tệp ssid.txt, pass.txt và ip.txt. Những thứ này sẽ trống rỗng vào lúc này.

  2. Tiếp theo, để kết nối với bo mạch ESP8266 hoạt động như một AP, chúng tôi sẽ kết nối với "ESP8266-WiFi-Manager" trên điện thoại thông minh của mình. Tại thời điểm này, điểm truy cập sẽ được đặt.

  3. Chúng tôi sẽ đi đến địa chỉ IP 192.168.4.1. Trang web trình quản lý WiFi ESP8266 sẽ mở ra. Ở đây chúng tôi sẽ cung cấp SSID, mật khẩu và địa chỉ IP có sẵn để kết nối. Chúng sẽ được lưu trong các tệp tương ứng của chúng: ssid.txt, pass.txt và ip.txt. Các cài đặt này sẽ được định cấu hình khi chúng tôi nhấn nút 'Gửi'.

  4. Các thông tin đăng nhập mạng này của mạng mà chúng tôi đã chọn, sẽ được lưu trong ESP8266 của chúng tôi.

  5. ESP8266 sẽ khởi động lại và bây giờ sẽ có thể kết nối với mạng chúng tôi đã chọn vì các tệp hiện chứa các tham số cần thiết để kết nối với chế độ trạm. Trong giai đoạn này, bảng ESP8266 hiện hoạt động ở chế độ Trạm.

  6. Bây giờ chúng ta sẽ nhập địa chỉ IP mà chúng ta vừa đặt trong một trang web mới và Máy chủ web Đầu ra GPIO Kiểm soát ESP8266 sẽ mở ra. Điều này sẽ cho phép chúng tôi điều khiển đèn LED trên bo mạch của bảng ESP8266 bằng cách nhấp vào hai nút BẬT và TẮT.

  7. Tuy nhiên, nếu kết nối không được thiết lập thành công, thì bo mạch ESP8266 lại chuyển sang chế độ AP và người dùng sẽ phải nhập lại các tham số mạng trên trang web ESP8266 WiFi Manager được truy cập tại địa chỉ IP 192.168.4.1.

Trình quản lý WiFi này có thể được thiết lập với bất kỳ dự án máy chủ Web ESP8266 có liên quan nào mà chúng tôi đã tạo. Vì mục đích đơn giản, chúng tôi đã chọn một máy chủ web kiểm soát một đầu ra GPIO duy nhất.

Thiết lập Arduino IDE

Để theo dõi dự án máy chủ web trình quản lý WiFi dựa trên LittleFS này, hãy đảm bảo rằng bạn đã cài đặt phiên bản Arduino IDE mới nhất và tiện ích bổ sung ESP8266 trên Arduino IDE của mình. Nếu bạn chưa cài đặt nó trước khi bạn có thể làm theo hướng dẫn này:

Ngoài ra, bạn sẽ phải tải xuống và cài đặt Plugin tải lên hệ thống tệp ESP8266 NodeMCU trong Arduino IDE của mình để bạn có thể tải lên các tệp LittleFS trên bảng NodeMCU ESP8266 của mình. Nếu chưa, bạn có thể làm theo hướng dẫn sau:

Cài đặt ESPAsyncWebServer Library và ESPAsyncThư viện TCP

Chúng tôi sẽ cần hai thư viện bổ sung để xây dựng máy chủ web của chúng tôi. Thư viện ESPAsyncWebServer sẽ giúp chúng tôi tạo máy chủ web của mình một cách dễ dàng. Với thư viện này, chúng tôi sẽ thiết lập một máy chủ HTTP không đồng bộ. ESPAsyncTCP là một thư viện khác mà chúng tôi sẽ kết hợp vì nó là một phụ thuộc cho thư viện ESPAsyncWebServer. Cả hai thư viện này đều không có sẵn trong trình quản lý thư viện Arduino, vì vậy chúng tôi sẽ phải tự tải xuống và tải chúng trong bảng NodeMCU ESP8266 của mình.

  • Để cài đặt miễn phí thư viện ESPAsyncWebServer Bạn sẽ tải xuống thư viện dưới dạng thư mục .zip mà bạn sẽ giải nén và đổi tên thành 'ESPAsyncWebServer.' Sau đó, chuyển thư mục này vào thư mục thư viện cài đặt trong Arduino IDE của bạn.

  • Để cài đặt thư viện ESPAsyncTCP miễn phí. Bạn sẽ tải xuống thư viện dưới dạng thư mục .zip mà bạn sẽ giải nén và đổi tên thành 'ESPAsyncTCP.' Sau đó, chuyển thư mục này vào thư mục thư viện cài đặt trong Arduino IDE của bạn.

Tương tự như vậy, bạn cũng có thể vào Sketch > Include Library > Add .zip Library bên trong IDE để thêm các thư viện. Sau khi cài đặt các thư viện, hãy khởi động lại IDE của bạn.

Tạo tệp cho LittleFS

Để xây dựng máy chủ web trình quản lý WiFi ESP8266 của chúng tôi bằng LittleFS, chúng tôi sẽ tạo bốn tệp khác nhau: hai tệp HTML (chỉ mục.html cho trang web sẽ kiểm soát đèn LED và wifimanager tích hợp.html cho trang web trình quản lý WiFi khi ESP8266 của chúng tôi sẽ ở chế độ AP), bản phác thảo CSS và Arduino và sắp xếp chúng trong một thư mục dự án như hình dưới đây:

Trình quản lý Wi-Fi ESP tạo tệp SPIFFS / LittleFS

Lưu ý: Bạn nên đặt các tệp HTML và CSS bên trong thư mục dữ liệu. Nếu không, thư viện LittleFS sẽ không thể đọc các tệp này.

Tạo tệp HTML

Như đã đề cập trước khi dự án của chúng tôi bao gồm hai tệp HTML: index.html và wifimanager.html. Một người sẽ chịu trách nhiệm xây dựng máy chủ web ESP8266 điều khiển đèn LED tích hợp và người kia sẽ chịu trách nhiệm xây dựng trang web trình quản lý WiFi.

chỉ số.html

Bên trong tệp chỉ mục.html của chúng tôi, chúng tôi sẽ bao gồm tiêu đề, một đoạn văn cho trạng thái GPIO và hai nút bật / tắt.

Bây giờ, hãy tạo một tệp chỉ mục.html và sao chép mã được cung cấp bên dưới trong tệp đó.

<!DOCTYPE html>

<html>

 

<head>

  <title>ESP8266 WEB SERVER</title>

  <meta name="viewport" content="width=device-width, initial-scale=1">

  <link rel="icon" href="data:,">

  <link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.7.2/css/all.css"

    integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr" crossorigin="anonymous">

  <link rel="stylesheet" type="text/css" href="style.css">

</head>

 

<body>

  <h2>ESP8266 WEB SERVER</h2>

  <div class="content">

    <div class="card-grid">

      <div class="card">

        <p><i class="fas fa-lightbulb fa-2x" style="color:#c81919;"></i>     <strong>GPIO2</strong></p>

        <p>GPIO state: <strong> %GPIO_STATE%</strong></p>

        <p>

          <a href="/led2on"><button class="button">ON</button></a>

          <a href="/led2off"><button class="button button2">OFF</button></a>

        </p>

      </div>

    </div>

  </div>

</body>

 

</html>

wifimanager.html

Trang web trình quản lý WiFi bao gồm một máy chủ web không đồng bộ cho phép chúng tôi nhập các loại dữ liệu của 'chuỗi' thông qua các trường đầu vào. Bên trong trang web, sẽ có tiêu đề 'Trình quản lý WiFi ESP8266'. Bên dưới nó, sẽ có ba trường đầu vào để người dùng nhập và lưu các giá trị và nút 'Gửi'. Trường đầu vào đầu tiên sẽ lấy tên SSID, trường nhập thứ hai sẽ lấy mật khẩu và trường thứ ba sẽ lấy địa chỉ IP. Sau khi bạn nhấp vào nút gửi, các giá trị tương ứng sẽ được lưu trong các biến mà chúng tôi sẽ xác định trong mã chương trình Arduino.

<!DOCTYPE html>

<html>

<head>

  <title>ESP8266 Wi-Fi Manager</title>

  <meta name="viewport" content="width=device-width, initial-scale=1">

  <link rel="icon" href="data:,">

  <link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.7.2/css/all.css" integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr" crossorigin="anonymous">

  <link rel="stylesheet" type="text/css" href="style.css">

</head>

<body>

    <h1>ESP8266 Wi-Fi Manager</h1>

  </div>

  <div class="content">

    <div class="card-grid">

      <div class="card">

        <form action="/" method="POST">

          <p>

            <label for="ssid">SSID</label>

            <input type="text" id ="ssid" name="ssid"><br>

            <label for="pass">Password</label>

            <input type="text" id ="pass" name="pass"><br>

            <label for="ip">IP Address</label>

            <input type="text" id ="ip" name="ip">

            <input type ="submit" value ="Submit">

          </p>

        </form>

      </div>

    </div>

  </div>

</body>

</html>

Bên dưới tiêu đề, chúng tôi sẽ thêm các đầu vào của người dùng cần được điền. Đây sẽ là loại 'hình thức.' Chúng tôi sẽ định nghĩa hành động của nó là "/ POST" có nghĩa là một yêu cầu HTTP POST sẽ được gửi khi người dùng nhập các trường và nhấn nút gửi. Vì chúng tôi đang hiển thị ba trường đầu vào trên trang web của mình, do đó, chúng tôi sẽ xác định các nhãn và id riêng biệt cho chúng. Hộp nhập liệu đầu tiên lưu giá trị cho "ssid" và thuộc loại văn bản. Hộp nhập liệu thứ hai lưu giá trị cho "pass" và cũng thuộc loại văn bản. Cuối cùng, hộp nhập liệu thứ ba lưu giá trị cho "ip" và cũng là loại văn bản.

Về cơ bản, chúng tôi có ba trường đầu vào, mỗi loại văn bản cập nhật các biến tương ứng của chúng bất cứ khi nào một giá trị hợp lệ được nhập vào hộp và nút gửi được nhấn.

<form action="/" method="POST">

          <p>

            <label for="ssid">SSID</label>

            <input type="text" id ="ssid" name="ssid"><br>

            <label for="pass">Password</label>

            <input type="text" id ="pass" name="pass"><br>

            <label for="ip">IP Address</label>

            <input type="text" id ="ip" name="ip">

            <input type ="submit" value ="Submit">

          </p>

        </form>

Chúng tôi có một bài viết chuyên dụng, nơi chúng tôi đã thảo luận sâu về cách xây dựng một trang web với các trường đầu vào. Bạn có thể tham khảo bài viết từ đây

Tạo tệp CSS

Tiếp theo, tạo một tệp khác "kiểu.css" trong cùng thư mục với các tệp HTML và sao chép mã được cung cấp bên dưới trong tệp đó.

html {

  font-family: Arial, Helvetica, sans-serif; 

  display: inline-block; 

  text-align: center;

}

 

h1 {

  font-size: 1.8rem; 

  color: #070812;

 

}

 

p { 

  font-size: 1.4rem;

}

 

body {  

  margin: 0;

}

 

.content { 

  padding: 5%;

}

 

.card-grid { 

  max-width: 800px; 

  margin: 0 auto; 

  display: grid; 

  grid-gap: 2rem; 

  grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));

}

 

.card { 

  background-color: white; 

  box-shadow: 2px 2px 12px 1px rgba(140,140,140,.5);

}

 

 

input[type=submit] {

  border: none;

  color: #FEFCFB;

  background-color: #fa0505;

  padding: 15px 15px;

  text-align: center;

  text-decoration: none;

  display: inline-block;

  font-size: 16px;

  width: 100px;

  margin-right: 10px;

  border-radius: 4px;

  transition-duration: 0.4s;

  }

 

 

input[type=text], input[type=number], select {

  width: 50%;

  padding: 12px 20px;

  margin: 18px;

  display: inline-block;

  border: 1px solid #ccc;

  border-radius: 4px;

  box-sizing: border-box;

}

 

label {

  font-size: 1.2rem; 

}

.value{

  font-size: 1.2rem;

  color: #1282A2;  

}

 

 

.button {

  display: inline-block;

  background-color: #b30000; //red color

  border: none;

  border-radius: 4px;

  color: white;

  padding: 16px 40px;

  text-decoration: none;

  font-size: 30px;

  margin: 2px;

  cursor: pointer;

}

.button2 {

  background-color: #364cf4; //blue color

}

Bên trong tệp CSS của chúng tôi sẽ được sử dụng để cung cấp các kiểu cho trang web của chúng tôi, chúng tôi sẽ chỉ định các loại phông chữ, kích thước và màu sắc của các tiêu đề, đoạn văn và các nút. Chúng tôi sẽ đặt văn bản hiển thị thành loại phông chữ Arial và căn chỉnh nó ở giữa trang web.

Để hiểu thêm về kiểu dáng CSS, hãy tham khảo các bài viết trước đây của chúng tôi về Máy chủ web ESP.

Arduino Sketch ESP8266 Trình quản lý WiFi Máy chủ Web

Cuối cùng, chúng tôi sẽ tạo một tệp mới và lưu nó dưới dạng ESP_Wi-Fi_Manager_Web_Server. Sao chép mã được cung cấp bên dưới trong tệp đó.

#include <Arduino.h>

#include <ESP8266WiFi.h>

#include <ESPAsyncTCP.h>

#include <ESPAsyncWebServer.h>

#include "LittleFS.h"

 

AsyncWebServer server(80);

 

const char* input_parameter1 = "ssid";

const char* input_parameter2 = "pass";

const char* input_parameter3 = "ip";

 

//Variables to save values from HTML form

String ssid;

String pass;

String ip;

 

// File paths to save input values permanently

const char* SSID_path = "/ssid.txt";

const char* Password_path = "/pass.txt";

const char* IP_path = "/ip.txt";

 

boolean restart = false;

 

IPAddress localIP;

IPAddress gateway(192, 168, 1, 1);

IPAddress subnet(255, 255, 0, 0);

 

unsigned long previous_time = 0;

const long Delay = 10000; 

 

const int ledPin = 2;

String ledState;

 

// Read File from LittleFS

String readFile(fs::FS &fs, const char * path){

  Serial.printf("Reading file: %s\r\n", path);

 

  File file = fs.open(path,"r");

  if(!file || file.isDirectory()){

    Serial.println("- failed to open file for reading");

    return String();

  }

  

  String fileContent;

  while(file.available()){

    fileContent = file.readStringUntil('\n');

    break;     

  }

  file.close();

  return fileContent;

}

 

// Write file to LittleFS

void writeFile(fs::FS &fs, const char * path, const char * message){

  Serial.printf("Writing file: %s\r\n", path);

 

  File file = fs.open(path,"w");

  if(!file){

    Serial.println("- failed to open file for writing");

    return;

  }

  if(file.print(message)){

    Serial.println("- file written");

  } else {

    Serial.println("- frite failed");

  }

}

 

// Initialize WiFi

bool initialize_Wifi() {

  if(ssid=="" || ip==""){

    Serial.println("Undefined SSID or IP address.");

    return false;

  }

 

  WiFi.mode(WIFI_STA);

  localIP.fromString(ip.c_str());

 

  if (!WiFi.config(localIP, gateway, subnet)){

    Serial.println("STA Failed to configure");

    return false;

  }

  WiFi.begin(ssid.c_str(), pass.c_str());

  Serial.println("Connecting to WiFi...");

  delay(20000);

  if(WiFi.status() != WL_CONNECTED) {

    Serial.println("Failed to connect.");

    return false;

  }

 

  Serial.println(WiFi.localIP());

  return true;

}

 

// Replaces placeholder with LED state value

String processor(const String& var) {

  if(var == "GPIO_STATE") {

    if(digitalRead(ledPin)) {

      ledState = "OFF";

    }

    else {

      ledState = "ON";

    }

    return ledState;

  }

  return String();

}

 

void setup() {

  Serial.begin(115200);

 

  if (!LittleFS.begin()) {

    Serial.println("An error has occurred while mounting LittleFS");

  }

  else{

   Serial.println("LittleFS mounted successfully");

  }

 

  pinMode(ledPin, OUTPUT);

  digitalWrite(ledPin, HIGH);  // Initially ESP8266 onboard LED OFF

  

  ssid = readFile(LittleFS, SSID_path);

  pass = readFile(LittleFS, Password_path);

  ip = readFile(LittleFS, IP_path);

  Serial.println(ssid);

  Serial.println(pass);

  Serial.println(ip);

 

  if(initialize_Wifi()) {

    server.on("/", HTTP_GET, [](AsyncWebServerRequest *request) {

      request->send(LittleFS, "/index.html", "text/html", false, processor);

    });

    server.serveStatic("/", LittleFS, "/");

    

    server.on("/led2on", HTTP_GET, [](AsyncWebServerRequest *request) {

      digitalWrite(ledPin, LOW);

      request->send(LittleFS, "/index.html", "text/html", false, processor);

    });

 

    server.on("/led2off", HTTP_GET, [](AsyncWebServerRequest *request) {

      digitalWrite(ledPin, HIGH);

      request->send(LittleFS, "/index.html", "text/html", false, processor);

    });

    server.begin();

  }

  else {

    Serial.println("Setting Access Point");

    WiFi.softAP("ESP8266-WIFI-MANAGER", NULL);

 

    IPAddress IP = WiFi.softAPIP();

    Serial.print("AP IP address: ");

    Serial.println(IP); 

 

    // Web Server Root URL

    server.on("/", HTTP_GET, [](AsyncWebServerRequest *request){

      request->send(LittleFS, "/wifimanager.html", "text/html");

    });

    

    server.serveStatic("/", LittleFS, "/");

    

    server.on("/", HTTP_POST, [](AsyncWebServerRequest *request) {

      int params = request->params();

      for(int i=0;i<params;i++){

        AsyncWebParameter* p = request->getParam(i);

        if(p->isPost()){

          // HTTP POST ssid value

          if (p->name() == input_parameter1) {

            ssid = p->value().c_str();

            Serial.print("SSID set to: ");

            Serial.println(ssid);

            // Write file to save value

            writeFile(LittleFS, SSID_path, ssid.c_str());

          }

          // HTTP POST pass value

          if (p->name() == input_parameter2) {

            pass = p->value().c_str();

            Serial.print("Password set to: ");

            Serial.println(pass);

            // Write file to save value

            writeFile(LittleFS, Password_path, pass.c_str());

          }

          // HTTP POST ip value

          if (p->name() == input_parameter3) {

            ip = p->value().c_str();

            Serial.print("IP Address set to: ");

            Serial.println(ip);

            // Write file to save value

            writeFile(LittleFS, IP_path, ip.c_str());

          }

        }

      }

      restart = true;

      request->send(200, "text/plain", "Success. ESP8266 will now restart. Connect to your router and go to IP address: " + ip);

    });

    server.begin();

  }

}

 

void loop() {

   if (restart){

    delay(5000);

    ESP.restart();

  }

 

 

}

Mã hoạt động như thế nào?

Chúng tôi sẽ bắt đầu bằng cách bao gồm các thư viện có liên quan cần thiết cho dự án này. Vì chúng tôi phải kết nối ESP8266 của mình với mạng không dây, chúng tôi cần thư viện ESP8266WiFi.h cho mục đích đó. Các thư viện ESPAsyncWebServer và ESPAsyncTCP là những thư viện mà chúng tôi đã tải xuống gần đây và sẽ được yêu cầu xây dựng máy chủ web HTTP không đồng bộ. Ngoài ra, thư viện LittleFS sẽ cho phép chúng tôi truy cập hệ thống tệp bộ nhớ flash của lõi ESP8266 của chúng tôi.

#include <Arduino.h>

#include <ESP8266WiFi.h>

#include <ESPAsyncTCP.h>

#include <ESPAsyncWebServer.h>

#include "LittleFS.h"

Đối tượng AsyncWebServer sẽ được sử dụng để thiết lập máy chủ web ESP8266. Chúng ta sẽ truyền cổng HTTP mặc định là 80, làm đầu vào cho hàm xây dựng. Đây sẽ là cổng nơi máy chủ sẽ lắng nghe các yêu cầu HTTP đến.

AsyncWebServer server(80);

Xác định biến

Bây giờ, chúng ta sẽ tạo ba biến toàn cục cho mỗi trường đầu vào. Chúng sẽ được sử dụng để theo dõi nếu nhận được yêu cầu HTTP POST từ các trường đầu vào. Nếu đúng như vậy thì các giá trị cập nhật mới sẽ được lưu trong mỗi biến tương ứng. Đầu tiên là input_parameter1 với giá trị 'ssid' được lưu. Biến thứ hai được input_parameter2 với giá trị 'vượt qua' được lưu. Cuối cùng, cái thứ ba được input_parameter3 với giá trị 'ip' được lưu. Các biến này sẽ được cập nhật bất cứ khi nào người dùng nhập giá trị vào trường nhập tương ứng và nhấn nút gửi trên máy chủ web trình quản lý WiFi.

const char* input_parameter1 = "ssid";

const char* input_parameter2 = "pass";

const char* input_parameter3 = "ip";

Tiếp theo, chúng tôi sẽ xác định ba biến chuỗi sẽ giữ các giá trị cho SSID, mật khẩu và địa chỉ IP do người dùng nhập vào biểu mẫu.

String ssid;

String pass;

String ip;

Ba biến toàn cục tiếp theo sẽ giữ đường dẫn cho các tệp .txt địa chỉ SSID, mật khẩu và địa chỉ IP trong hệ thống tệp ESP8266.

const char* SSID_path = "/ssid.txt";

const char* Password_path = "/pass.txt";

const char* IP_path = "/ip.txt";

Các dòng mã sau đây sẽ xác định cổng và địa chỉ IP mạng con.

IPAddress localIP;

IPAddress gateway(192, 168, 1, 1);

IPAddress subnet(255, 255, 0, 0);

Tiếp theo, xác định ledPin biến để đặt tên tượng trưng cho chân GPIO2 mà qua đó đèn LED trên bo mạch sẽ được kết nối. Biến ledState sẽ được sử dụng để lưu trữ trạng thái LED hiện tại sẽ được sử dụng sau này trong mã chương trình.

 

const int ledPin = 2;

String ledState;

Các hàm readFile() và writeFile() sau đây sẽ được sử dụng để đọc và ghi các tập tin vào LittleFS.

// Read File from LittleFS

String readFile(fs::FS &fs, const char * path){

  Serial.printf("Reading file: %s\r\n", path);

 

  File file = fs.open(path,"r");

  if(!file || file.isDirectory()){

    Serial.println("- failed to open file for reading");

    return String();

  }

  

  String fileContent;

  while(file.available()){

    fileContent = file.readStringUntil('\n');

    break;     

  }

  file.close();

  return fileContent;

}

 

// Write file to LittleFS

void writeFile(fs::FS &fs, const char * path, const char * message){

  Serial.printf("Writing file: %s\r\n", path);

 

  File file = fs.open(path,"w");

  if(!file){

    Serial.println("- failed to open file for writing");

    return;

  }

  if(file.print(message)){

    Serial.println("- file written");

  } else {

    Serial.println("- frite failed");

  }

}

initialize_Wifi()

Chức năng sau sẽ khởi tạo WiFi. Nó sẽ thiết lập bảng ESP8266 ở chế độ trạm và kết nối bảng với thông tin đăng nhập mạng (ssid và pass) do người dùng nhập trên biểu mẫu. Điều này đạt được bằng cách sử dụng hàm WiFi.begin() và truyền ssid.c_str() và pass.c_str() làm tham số bên trong nó. Sau khi bo mạch ESP8266 kết nối thành công với các tham số mạng, địa chỉ IP sẽ được hiển thị trong màn hình Nối tiếp. Lưu ý rằng nó sẽ là cùng một địa chỉ IP mà người dùng sẽ nhập vào biểu mẫu. Hàm initialize_Wifi() sẽ cho biết mô-đun ESP8266 có thể kết nối thành công với mạng hay không.

// Initialize WiFi

bool initialize_Wifi() {

  if(ssid=="" || ip==""){

    Serial.println("Undefined SSID or IP address.");

    return false;

  }

 

  WiFi.mode(WIFI_STA);

  localIP.fromString(ip.c_str());

 

  if (!WiFi.config(localIP, gateway, subnet)){

    Serial.println("STA Failed to configure");

    return false;

  }

  WiFi.begin(ssid.c_str(), pass.c_str());

  Serial.println("Connecting to WiFi...");

  delay(20000);

  if(WiFi.status() != WL_CONNECTED) {

    Serial.println("Failed to connect.");

    return false;

  }

 

  Serial.println(WiFi.localIP());

  return true;

}

Bộ xử lý()

Bên trong hàm processor(), chúng ta sẽ thay thế chỗ dành sẵn %GPIO_STATE% bằng trạng thái LED (1 hoặc 0). Một loạt các câu lệnh if-else sẽ kiểm tra xem trình giữ chỗ có thực sự là trình giữ chỗ mà chúng ta đã tạo trong tệp HTML của mình hay không. Nếu có, sau đó nó sẽ kiểm tra các ledPin biến đổi trong đó chỉ định GPIO2 kết nối với đèn LED trên tàu. Nếu trạng thái là 1 (CAO) thì biến ledState sẽ được lưu dưới dạng 'TẮT' nếu không nó sẽ được lưu dưới dạng 'BẬT.' Do đó, biến này sẽ được trả về và sẽ thay thế GPIO_STATE bằng giá trị ledState.

Lưu ý: Đối với ESP8266, đèn LED tích hợp hoạt động theo logic ngược lại so với ESP32. Để BẬT đèn LED trên bo mạch, một tín hiệu thấp sẽ được gửi đi và để TẮT nó, một tín hiệu cao sẽ được gửi đi. Điều này ngược lại trong trường hợp của ESP32.

// Replaces placeholder with LED state value

String processor(const String& var) {

  if(var == "GPIO_STATE") {

    if(digitalRead(ledPin)) {

      ledState = "OFF";

    }

    else {

      ledState = "ON";

    }

    return ledState;

  }

  return String();

}

thiết lập()

Bên trong hàm setup(), chúng ta sẽ mở một kết nối nối tiếp với tốc độ truyền là 115200. Bằng cách sử dụng hàm pinMode (), ledPin sẽ được truyền dưới dạng tham số bên trong hàm sẽ được định cấu hình làm chân đầu ra.

 Serial.begin(115200);

 pinMode(ledPin, OUTPUT);

Những dòng mã này sẽ khởi tạo LittleFS.

 if (!LittleFS.begin()) {

    Serial.println("An error has occurred while mounting LittleFS");

  }

  else{

   Serial.println("LittleFS mounted successfully");

  }

Ngoài ra, hãy đặt trạng thái ledPin thành CAO để ban đầu đèn LED trên bo mạch sẽ TẮT.

digitalWrite(ledPin, HIGH);  // Initially ESP8266 onboard LED OFF

SSID, mật khẩu và địa chỉ IP sẽ được đọc từ các tệp tương ứng của chúng trong LittleFS và được lưu trong chuỗi varaibles 'ssid, "pass' và 'ip.' Ngoài ra, ba tham số này cũng sẽ được in trong màn hình nối tiếp.

  ssid = readFile(LittleFS, SSID_path);

  pass = readFile(LittleFS, Password_path);

  ip = readFile(LittleFS, IP_path);

  Serial.println(ssid);

  Serial.println(pass);

  Serial.println(ip);

Chế độ trạm ESP8266

Nếu hàm initialize_Wifi() trả về đúng nghĩa là ESP8266 hiện đã được kết nối ở chế độ trạm thì chúng ta sẽ xử lý các yêu cầu http nhận được từ máy khách. Chúng tôi có thể định cấu hình Máy chủ web Async để lắng nghe các yêu cầu HTTP cụ thể dựa trên các tuyến được định cấu hình và thực thi chức năng cụ thể bất cứ khi nào nhận được yêu cầu HTTP trên tuyến đường đó.

Xử lý yêu cầu

Chúng ta sẽ sử dụng phương thức on() trên đối tượng server để lắng nghe các HTTP request đến và thực thi các hàm cho phù hợp.

Phương thức send() sử dụng để trả về phản hồi HTTP. File index.html sẽ gửi đến client, bất cứ khi nào server sẽ nhận được request trên URL "/". Chúng ta sẽ thay thế chỗ dành sẵn bằng giá trị được lưu trong biến ledState vì chúng ta sẽ sử dụng processor làm đối số cuối cùng của hàm send().

Như bạn đã biết, khi người dùng nhấp vào nút BẬT / TẮT, trang web sẽ chuyển hướng đến URL / led2on hoặc / led2off. Do đó, phần mã này đề cập đến những gì xảy ra khi một trong hai nút được nhấp vào.

Bất cứ khi nào yêu cầu HTTP POST được thực hiện trên một trong hai / led2on hoặc / led2off, đèn LED tích hợp của mô-đun ESP8266 sẽ BẬT hoặc TẮT và trang HTML sẽ được gửi để phản hồi cho máy khách.

  if(initialize_Wifi()) {

    server.on("/", HTTP_GET, [](AsyncWebServerRequest *request) {

      request->send(LittleFS, "/index.html", "text/html", false, processor);

    });

    server.serveStatic("/", LittleFS, "/");

    

    server.on("/led2on", HTTP_GET, [](AsyncWebServerRequest *request) {

      digitalWrite(ledPin, LOW);

      request->send(LittleFS, "/index.html", "text/html", false, processor);

    });

 

    server.on("/led2off", HTTP_GET, [](AsyncWebServerRequest *request) {

      digitalWrite(ledPin, HIGH);

      request->send(LittleFS, "/index.html", "text/html", false, processor);

    });

    server.begin();

  }

 

ESP8266 Chế độ AP

Nếu bo mạch ESP8266 không kết nối với mạng ở chế độ trạm thì nó sẽ được thiết lập ở chế độ AP.

else {

    Serial.println("Setting Access Point");

    WiFi.softAP("ESP8266-WIFI-MANAGER", NULL);

 

    IPAddress IP = WiFi.softAPIP();

    Serial.print("AP IP address: ");

    Serial.println(IP); 

 

    // Web Server Root URL

    server.on("/", HTTP_GET, [](AsyncWebServerRequest *request){

      request->send(LittleFS, "/wifimanager.html", "text/html");

    });

    

    server.serveStatic("/", LittleFS, "/");

    

    server.on("/", HTTP_POST, [](AsyncWebServerRequest *request) {

      int params = request->params();

      for(int i=0;i<params;i++){

        AsyncWebParameter* p = request->getParam(i);

        if(p->isPost()){

          // HTTP POST ssid value

          if (p->name() == input_parameter1) {

            ssid = p->value().c_str();

            Serial.print("SSID set to: ");

            Serial.println(ssid);

            // Write file to save value

            writeFile(LittleFS, SSID_path, ssid.c_str());

          }

          // HTTP POST pass value

          if (p->name() == input_parameter2) {

            pass = p->value().c_str();

            Serial.print("Password set to: ");

            Serial.println(pass);

            // Write file to save value

            writeFile(LittleFS, Password_path, pass.c_str());

          }

          // HTTP POST ip value

          if (p->name() == input_parameter3) {

            ip = p->value().c_str();

            Serial.print("IP Address set to: ");

            Serial.println(ip);

            // Write file to save value

            writeFile(LittleFS, IP_path, ip.c_str());

          }

        }

      }

      restart = true;

      request->send(200, "text/plain", "Success. ESP8266 will now restart. Connect to your router and go to IP address: " + ip);

    });

    server.begin();

  }

Chức năng WiFi.softAP ("ESP8266-WIFI-MANAGER", NULL) tạo một điểm truy cập mở có tên "ESP8266-WIFI_Manager." Chức năng WiFi.softAPIP() được sử dụng để lấy địa chỉ IP của ESP8266 mà qua đó chúng ta sẽ truy cập vào máy chủ web. Dòng này lưu giá trị địa chỉ IP trong một biến 'IP'. Sau đó, hàm Serial.print() in giá trị IP của địa chỉ trong màn hình nối tiếp.

    Serial.println("Setting Access Point");

    WiFi.softAP("ESP8266-WIFI-MANAGER", NULL);

 

    IPAddress IP = WiFi.softAPIP();

    Serial.print("AP IP address: ");

    Serial.println(IP); 

Sau khi bảng ESP8266 được thiết lập ở chế độ AP, chúng tôi sẽ mở trang web trình quản lý WiFi. Điều này sẽ được truy cập từ điểm truy cập. Tệp .html wifimanager sẽ được gửi dưới dạng phản hồi.

Xử lý yêu cầu

Bất cứ khi nào người dùng nhập dữ liệu vào các trường đầu vào và nhấn nút gửi, một yêu cầu HTTP POST sẽ được gửi trên URL tuyến đường. Các giá trị SSID, mật khẩu và địa chỉ IP do người dùng nhập sẽ được lưu trong các biến tương ứng của họ. Sau đó, các giá trị sẽ được ghi vào các tệp tương ứng trên LittleFS.

// Web Server Root URL

    server.on("/", HTTP_GET, [](AsyncWebServerRequest *request){

      request->send(LittleFS, "/wifimanager.html", "text/html");

    });

    

    server.serveStatic("/", LittleFS, "/");

    

    server.on("/", HTTP_POST, [](AsyncWebServerRequest *request) {

      int params = request->params();

      for(int i=0;i<params;i++){

        AsyncWebParameter* p = request->getParam(i);

        if(p->isPost()){

          // HTTP POST ssid value

          if (p->name() == input_parameter1) {

            ssid = p->value().c_str();

            Serial.print("SSID set to: ");

            Serial.println(ssid);

            // Write file to save value

            writeFile(LittleFS, SSID_path, ssid.c_str());

          }

          // HTTP POST pass value

          if (p->name() == input_parameter2) {

            pass = p->value().c_str();

            Serial.print("Password set to: ");

            Serial.println(pass);

            // Write file to save value

            writeFile(LittleFS, Password_path, pass.c_str());

          }

          // HTTP POST ip value

          if (p->name() == input_parameter3) {

            ip = p->value().c_str();

            Serial.print("IP Address set to: ");

            Serial.println(ip);

            // Write file to save value

            writeFile(LittleFS, IP_path, ip.c_str());

          }

        }

      }

      restart = true;

      request->send(200, "text/plain", "Success. ESP8266 will now restart. Connect to your router and go to IP address: " + ip);

    });

    server.begin();  

Khi người dùng nhấp vào nút submit thì phương thức send() sẽ được sử dụng để trả về phản hồi HTTP. Nó có ba tham số. Tham số đầu tiên là mã phản hồi mà chúng ta sẽ chỉ định là 200. Nó là mã phản hồi HTTP cho ok. Tham số thứ hai là kiểu nội dung của phản hồi mà chúng ta sẽ chỉ định là "text / html" và tham số thứ ba là thông báo thực tế sẽ được gửi dưới dạng phản hồi HTTP. Điều này được đặt là "Thành công. ESP8266 bây giờ sẽ khởi động lại. Kết nối với bộ định tuyến của bạn và đi đến địa chỉ IP: "+ ip". Toán tử mũi tên sẽ được sử dụng để gọi phương thức gửi trên đối tượng AsyncWebServerRequest.

 request->send(200, "text/plain", "Success. ESP32 will now restart. Connect to your router and go to IP address: " + ip);

Hơn nữa, biến boolean, 'khởi động lại' sẽ được đặt thành true.

restart = true;

Để start server, chúng ta sẽ gọi begin() trên đối tượng server của chúng ta.

 server.begin();

vòng lặp()

Bên trong hàm loop() chúng ta sẽ kiểm tra xem biến khởi động lại có đúng hay không. Nếu đúng như vậy thì sau khi trì hoãn 5 giây, chúng tôi sẽ khởi động lại ESP8266 của mình.

 

void loop() {

   if (restart){

    delay(5000);

    ESP.restart();

  }

}

Demonstration

Sau khi bạn đã lưu tất cả các tệp, hãy chuyển đến Sketch > Show Sketch Folder và tạo một thư mục mới. Đặt cả tệp HTML và CSS bên trong thư mục đó và lưu thư mục dưới dạng 'dữ liệu'.

Đảm bảo rằng bạn chọn đúng bảng và cổng COM trước khi tải mã của mình lên bảng. Đi tới Bảng > Công cụ và chọn NodeMCU1.0.

chọn bảng ESP8266 NodeMCU

Tiếp theo, đi tới Công cụ > Cổng và chọn cổng thích hợp mà qua đó bảng của bạn được kết nối.

Cổng COM ESP8266

Bây giờ, chúng tôi sẽ tải các tệp lên bảng ESP8266 của chúng tôi. Đi tới Công cụ > Tải lên dữ liệu ESP8266 LittleFS. Sau một lúc, các tệp sẽ được tải lên.

Tải dữ liệu phác thảo LittleFS lên hệ thống tệp esp8266

Tiếp theo, nhấp vào nút tải lên để tải mã lên bảng phát triển ESP8266.

Sau khi bạn đã tải mã của mình và các tệp lên bảng phát triển ESP8266, hãy nhấn nút RST của nó.

Nút đặt lại ESP8266 NodeMCU

Trong Arduino IDE của bạn, hãy mở màn hình nối tiếp và bạn sẽ có thể thấy rằng điểm truy cập đã được đặt. Điều này là do các tệp chưa được tạo.

ESP8266 Wi-Fi Manager màn hình nối tiếp 1

Bây giờ để kết nối điểm truy cập, hãy mở tùy chọn WiFi trên thiết bị di động của bạn và tìm kiếm các mạng WiFi khả dụng. Bạn sẽ thấy tên "ESP8266-WIFI-Manager".

Trình quản lý Wi-Fi ESP8266 kết nối với AP

Khi chúng tôi định cấu hình nó như một điểm truy cập mở để bạn có thể kết nối với nó mà không cần bất kỳ mật khẩu nào.

Trình quản lý Wi-Fi ESP8266 kết nối với AP 2

Bây giờ hãy truy cập trình duyệt web của thiết bị di động của bạn và tìm kiếm với địa chỉ IP được hiển thị trong màn hình nối tiếp. Trang web trình quản lý WiFi sẽ mở ra.

Trang web Trình quản lý Wi-Fi ESP8266

 

Bây giờ chỉ định SSID và mật khẩu của mạng của bạn cùng với một địa chỉ IP có sẵn và nhấn nút Gửi. Trang web sau đây sẽ mở ra cho biết thành công.

ESP8266 Trình quản lý Wi-Fi gửi trang web

Bây giờ bảng ESP8266 khởi động lại và bạn có thể xem nó trong Màn hình nối tiếp. Các tệp được đọc lại và cả ba tham số được chỉ định trong màn hình nối tiếp. Ngoài ra, ESP8266 hiện kết nối với địa chỉ IP do người dùng gửi và chuyển sang chế độ trạm.

ESP8266 Wi-Fi Manager màn hình nối tiếp 2

Bây giờ hãy mở một trang web mới và nhập địa chỉ IP vào thanh tìm kiếm và nhấn enter. Máy chủ web ESP8266 mở ra cho phép người dùng điều khiển đèn LED tích hợp trên bo mạch của họ.

ESP8266 Điều khiển máy chủ web LED trên bo mạch

Bây giờ, hãy nhấn các nút BẬT và TẮT và đèn LED trên bo mạch sẽ bật và tắt tương ứng. Trạng thái GPIO trên máy chủ web cũng sẽ thay đổi và được cập nhật.

ESP8266 Điều khiển máy chủ web LED trên bo mạch BẬT và TẮT

Bằng cách sử dụng trình quản lý WiFi, chúng tôi không phải mã hóa cứng thông tin đăng nhập mạng của mình trong tập lệnh Arduino của chúng tôi. WiFi-Manager đặt ESP8266 ở chế độ điểm truy cập mềm và cho phép người dùng chỉ định SSID, mật khẩu và địa chỉ IP khả dụng. Khi bo mạch ESP8266 của bạn được kết nối với mạng, nó sẽ tự động hoạt động ở chế độ trạm.

>>> 100+ Mã Sản Phẩm Dây Rút: https://mecsu.vn/san-pham/day-rut-nhua.5op

>>> 1000+ Mã Sản Phẩm Đầu Cosse: https://mecsu.vn/san-pham/dau-cosse.Q1j

Bài viết cùng chuyên mục

NHANH

NHANH

Vì Đổi mới liên tục nên Nhanh hơn

ĐÚNG

ĐÚNG

Coi trọng và ưu tiên việc làm Đúng

ĐỦ

ĐỦ

Tìm và mua Đủ Đơn hàng hơn

KỊP THỜI

KỊP THỜI

Hiệu suất tối ưu bởi Kịp Thời hơn