You are currently viewing NodeMCU用於Web Server的AP架構

NodeMCU用於Web Server的AP架構

在本教程中,您將學習如何使用Arduino IDE將ESP8266 NodeMCU設置為Access Point(AP)。這使您無需無線路由器即可通過Wi-Fi直接連接到ESP8266。

要將ESP8266設置為AP,請使用WiFi.softAP(ssid, password);

ESP8266 Station和AP

在大多數ESP8266 NodeMCU Web Server項目中,我們將ESP8266連接到無線路由器。在這種配置下,我們可以通過區域網訪問ESP8266。

在這種情況下,路由器充當AP,ESP8266被設置為Station。因此,您需要連接到路由器(本地網絡)來控制ESP8266。

在某些情況下,這可能不是最佳配置(當您附近沒有路由器時)。但是,如果將ESP8266設置為AP(熱點),則可以使用任何具有Wi-Fi功能的設備將其連接到ESP8266,而無需連接到路由器。

簡而言之,將ESP8266設置為AP後,便會建立自己的Wi-Fi網絡,附近的Wi-Fi設備(Stations)可以連接到該網絡(如智能手機或計算機)。

本教程中,我們會向您展示如何在Web Server項目中將ESP8266設置為AP。這樣,您無需連接到路由器即可控制ESP8266。

由於ESP8266不會進一步連接到有線網絡(例如路由器),因此它稱為soft-AP(soft Access Point)。

意思是,如果您嘗試從Internet加載庫或使用套件,則將無法使用。如果您嘗試向Internet上的服務發出HTTP請求(例如將感測器讀數發佈到雲中),它也將不起作用。

為ESP8266安裝DHT庫

在範例中,我們將使用以前的Web Server項目,該項目顯示來自DHT感測器的讀取數據。

在Arduino IDE中安裝了ESP8266開發板以讀取DHT感測器後,我們將使用Adafruit的 DHT庫。要使用此庫,您還需要安裝 Adafruit Unified Sensor庫

請按照以下步驟安裝這兩個庫:

1.打開您的Arduino IDE,然後轉到草稿圖 匯入程式庫 > 管理程式庫。程式庫管理員會打開。

2.在“搜索”框中搜索“ DHT ”,然後從Adafruit安裝DHT庫。

3.從Adafruit安裝DHT庫後,在搜索框中鍵入“ Adafruit Unified Sensor ”。一直向下滾動以找到該庫並進行安裝。

安裝程式庫後,重新啟動Arduino IDE。

ESP8266 NodeMCU Access Point(AP)

以下範例中,我們將根據之前的教程修改ESP8266 Web Server以增加AP功能。這是我們將使用的項目示例:帶有Arduino IDE的ESP8266 DHT11 / DHT22溫濕度Web服務器。

我們在這裡向您展示的內容可以與任何ESP8266 Web Server範例一起使用。

上傳以下提供的草稿圖以將ESP8266設置為AP。

/*********
  Terry Lee
  完整說明請參閱 http://honeststore.com.tw/blog/esp8266_post/esp8266-nodemcu-access-point-ap-for-web-server/
  
  特此授予任何獲取副本的人授予許可此軟件和相關文檔文件。
  以上版權聲明和本許可通知應包括在內軟件的複製或大量部分。
*********/

// 導入所需的程式庫
#include <Arduino.h>
#include <ESP8266WiFi.h>
#include <Hash.h>
#include <ESPAsyncTCP.h>
#include <ESPAsyncWebServer.h>
#include <Adafruit_Sensor.h>
#include <DHT.h>

const char* ssid     = "ESP8266-Access-Point";
const char* password = "123456789";

#define DHTPIN 5     // 定義數位引腳連接到DHT感測器

// 取消註釋使用中的傳感器類型
//#define DHTTYPE    DHT11     // DHT 11
#define DHTTYPE    DHT22     // DHT 22 (AM2302)
//#define DHTTYPE    DHT21     // DHT 21 (AM2301)

DHT dht(DHTPIN, DHTTYPE);

// 定義temperature & humidity變數, 會持續更新
float t = 0.0;
float h = 0.0;

// 在端口80上建立asyncwebserver變數
AsyncWebServer server(80);

// 一般來說,您應該使用“unsigned long”來保持時間的變數
// 這樣int的值才不會快速變得太大
unsigned long previousMillis = 0;    // 會存放最新一次DHT更新值

// 每10秒更新DHT讀取數據
const long interval = 10000;  

const char index_html[] PROGMEM = R"rawliteral(
<!DOCTYPE HTML><html>
<head>
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <style>
    html {
     font-family: Arial;
     display: inline-block;
     margin: 0px auto;
     text-align: center;
    }
    h2 { font-size: 3.0rem; }
    p { font-size: 3.0rem; }
    .units { font-size: 1.2rem; }
    .dht-labels{
      font-size: 1.5rem;
      vertical-align:middle;
      padding-bottom: 15px;
    }
  </style>
</head>
<body>
  <h2>ESP8266 DHT Server</h2>
  <p>
    <span class="dht-labels">Temperature</span> 
    <span id="temperature">%TEMPERATURE%</span>
    <sup class="units">&deg;C</sup>
  </p>
  <p>
    <span class="dht-labels">Humidity</span>
    <span id="humidity">%HUMIDITY%</span>
    <sup class="units">%</sup>
  </p>
</body>
<script>
setInterval(function ( ) {
  var xhttp = new XMLHttpRequest();
  xhttp.onreadystatechange = function() {
    if (this.readyState == 4 && this.status == 200) {
      document.getElementById("temperature").innerHTML = this.responseText;
    }
  };
  xhttp.open("GET", "/temperature", true);
  xhttp.send();
}, 10000 ) ;

setInterval(function ( ) {
  var xhttp = new XMLHttpRequest();
  xhttp.onreadystatechange = function() {
    if (this.readyState == 4 && this.status == 200) {
      document.getElementById("humidity").innerHTML = this.responseText;
    }
  };
  xhttp.open("GET", "/humidity", true);
  xhttp.send();
}, 10000 ) ;
</script>
</html>)rawliteral";

// Replaces placeholder with DHT values
String processor(const String& var){
  //Serial.println(var);
  if(var == "TEMPERATURE"){
    return String(t);
  }
  else if(var == "HUMIDITY"){
    return String(h);
  }
  return String();
}


void setup(){
  // Serial port for debugging purposes
  Serial.begin(115200);
  dht.begin();
  
  Serial.print("Setting AP (Access Point)…");
  // 如果希望打開AP,請刪除密碼參數
  WiFi.softAP(ssid, password);

  IPAddress IP = WiFi.softAPIP();
  Serial.print("AP IP address: ");
  Serial.println(IP);

  // 列出ESP8266區域IP Address
  Serial.println(WiFi.localIP());

  // root / web page的路由器
  server.on("/", HTTP_GET, [](AsyncWebServerRequest *request){
    request->send_P(200, "text/html", index_html, processor);
  });
  server.on("/temperature", HTTP_GET, [](AsyncWebServerRequest *request){
    request->send_P(200, "text/plain", String(t).c_str());
  });
  server.on("/humidity", HTTP_GET, [](AsyncWebServerRequest *request){
    request->send_P(200, "text/plain", String(h).c_str());
  });

  // Start server
  server.begin();
}
 
void loop(){  
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= interval) {
    // 保存最後一次更新的DHT值
    previousMillis = currentMillis;
    // 讀取攝氏溫度(預設)
    float newT = dht.readTemperature();
    // 讀取華氏溫度(isFahrenheit = true)
    //float newT = dht.readTemperature(true);
    // 如果溫度讀取失敗,就不要更改newT值
    if (isnan(newT)) {
      Serial.println("Failed to read from DHT sensor!");
    }
    else {
      t = newT;
      Serial.println(t);
    }
    // Read Humidity
    float newH = dht.readHumidity();
    // 如果讀取溼度失敗,就不要更改newH值
    if (isnan(newH)) {
      Serial.println("Failed to read from DHT sensor!");
    }
    else {
      h = newH;
      Serial.println(h);
    }
  }
}

自定義SSID和密碼

您需要定義一個SSID名稱和一個密碼才能訪問ESP8266。在本例中,我們將ESP8266 SSID名稱設置為ESP8266-Access-Point,但是您可以將名稱修改為所需的名稱。密碼是123456789,但您也可以對其進行修改。

const char* ssid     = "ESP8266-Access-Point";
const char* password = "123456789";

將ESP8266設置為Access Point(AP)

setup()的有一個部分可以使用softAP() 方法將ESP8266設置為Access Point :

WiFi.softAP(ssid, password);

您還可以將其他可選參數傳遞給 softAP()方法。下面是所有參數:

.softAP(const char* ssid, const char* password, int channel, int ssid_hidden, int max_connection)
  • ssid (之前定義):最多31個字元
  • password(先前定義):至少8個字元。如果未指定,則AP將打開(最多63個字元)
  • channel:Wi-Fi頻道編號(1-13)。預設為1
  • ssid_hidden:如果設置為true將隱藏SSID
  • max_connection:最大同時連接工作站數,從0到8

接下來,使用 softAPIP() 方法取得AP IP address並在序列監視器中印出來。

IPAddress IP = WiFi.softAPIP();
Serial.print("AP IP address: ");
Serial.println(IP);

注意:預設AP的IP地址為192.168.4.1

這些是您需要在Web Server草稿圖中包含的程式碼片段,以將ESP8266設置為soft access point。

要了解完整的Web Server程式碼如何工作,請閱讀:ESP8266 NodeMCU DHT11 / DHT22帶Arduino IDE的溫度和濕度Web服務器。

所需零件

要繼續本教程,您需要以下部分:

  • ESP8266開發板 
  • DHT22 或 DHT11 溫濕度感測器
  • 4.7k歐姆電阻
  • 麵包板
  • 跳線

原理圖、示意圖

按照下一個示意圖組裝所有零件:

連接到ESP8266 Access Point

讓ESP8266運行草稿圖時,在手機中開啟Wi-Fi設置並點擊 ESP8266-AP 網絡:

Screenshot_20210128-222629

輸入您定義的密碼。

Screenshot_20210128-223702

打開Web瀏覽器,然後輸入IP地址http://192.168.4.1。Web Server頁面會自動重載:

Screenshot_20210128-230654

Web Server頁面與原始Web服務器有些不同。該Web服務器在溫度和濕度旁邊顯示兩個圖標。這些圖標是從Font Awesome網站加載的。但是,由於ESP8266充當軟訪問點(未連接到互聯網),因此我們無法加載這些圖標。

總結

在本教程中,您學習了如何將ESP8266設置為soft AP。這樣您可以直接通過Wi-Fi連接到ESP8266 Web Server,而無需連接到路由器。

但是,請注意,ESP8266未連接到互聯網,因此您無法向其他服務發出HTTP請求以發布傳感器數據或從互聯網獲取數據(例如加載圖標)。

  • ESP8266 Web服務器控件輸出
  • 使用SPIFFS(SPI Flash文件系統)的ESP8266 Web服務器– NodeMCU
  • 可視化來自世界各地的傳感器讀數(ESP32 / ESP8266 + MySQL + PHP)
  • 使用ESP8266的家庭自動化(課程)

謝謝閱讀。

發佈留言