Files
esp8266-set-wifi/wifi-config.ino
2024-10-17 21:42:18 +08:00

293 lines
7.0 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
#include <ESP8266WiFi.h>
#include <DNSServer.h>
#include <ESP8266WebServer.h>
#include <EEPROM.h>
#include <Arduino.h>
#include <WebSocketsServer_Generic.h>
#include <ArduinoJson.h>
//AP名称
const char* AP_NAME = "HOMEKIT-WIFI";
String nets;
//配网页面代码
const char* page_html = "\
<!DOCTYPE html>\r\n\
<html lang='en'>\r\n\
<head>\r\n\
<meta charset='UTF-8'>\r\n\
<meta name='viewport' content='width=device-width, initial-scale=1.0'>\r\n\
<title>网络配置</title>\r\n\
</head>\r\n\
<body>\r\n\
<form name='input' action='/' method='POST'>\r\n\
wifi名称: <br>\r\n\
<input type='text' name='ssid'><br>\r\n\
wifi密码:<br>\r\n\
<input type='text' name='password'><br>\r\n\
<input type='submit' value='保存'>\r\n\
</form>\r\n\
<form action='/reconfigure' method='GET'>\r\n\
<input type='submit' value='重新配置Wi-Fi'>\r\n\
</form>\r\n\
</body>\r\n\
</html>\r\n\
";
//DNS端口号
const byte DNS_PORT = 53;
//esp8266-AP-IP地址
IPAddress apIP(192, 168, 4, 1);
//创建dnsServer实例
DNSServer dnsServer;
//创建WebServer
ESP8266WebServer server(80);
//创建webSocketServer
WebSocketsServer webSocketServer = WebSocketsServer(81);
void webSocketEvent(uint8_t num, WStype_t type, uint8_t* payload, size_t length) {
IPAddress ip;
switch (type) {
case WStype_DISCONNECTED:
Serial.println("对端关闭");
ip = webSocketServer.remoteIP(num);
nets = String(ip[0]) + String(".") + String(ip[1]) + String(".") + String(ip[2]) + String(".") + String(ip[3]);
Serial.println(nets);
break;
case WStype_CONNECTED:
{
Serial.println("对端连接");
ip = webSocketServer.remoteIP(num);
nets = String(ip[0]) + String(".") + String(ip[1]) + String(".") + String(ip[2]) + String(".") + String(ip[3]);
Serial.println(nets);
}
break;
case WStype_TEXT:
Serial.println("收到消息");
showcpu(payload);
break;
}
}
void showcpu(uint8_t* payload) {
StaticJsonDocument<200> root;
deserializeJson(root, (const char*)payload);
String type = root["type"];
Serial.println("type-----" + String(type));
}
//访问主页回调函数
void handleRoot() {
server.send(200, "text/html", page_html);
}
void handleReset() {
for (int i = 0; i < 96; ++i) {
EEPROM.write(2048 + i, 0);
}
EEPROM.commit();
server.send(200, "text/html", "<meta charset='UTF-8'>清除WIFI配置信息成功");
delay(2000);
Serial.println("准备重启中...");
Serial.println();
//重启
ESP.reset();
}
//Post回调函数
void handleRootPost() {
Serial.println("接收POST数据");
String qsid = server.arg("ssid");
String qpass = server.arg("password");
Serial.println("POST-WIFI名称:");
Serial.println(qsid);
Serial.println("POST-WIFI密码:");
Serial.println(qpass);
Serial.println("");
if (qsid.length() > 0 && qpass.length() > 0) {
Serial.println("清除之前的账号密码开始");
for (int i = 0; i < 96; ++i) {
EEPROM.write(2048 + i, 0);
}
Serial.println("清除之前的账号密码完毕");
Serial.println("写入新的WIFI名称:");
for (int i = 0; i < qsid.length(); ++i) {
EEPROM.write(2048 + i, qsid[i]);
}
Serial.println("写入新的WIFI密码:");
for (int i = 0; i < qpass.length(); ++i) {
EEPROM.write(2048 + 32 + i, qpass[i]);
}
EEPROM.commit();
// 连接新的Wi-Fi
connectNewWifi();
// 返回保存成功页面和IP地址
String response = "<meta charset='UTF-8'>网络配置保存成功<br>";
response += "设备IP地址: " + WiFi.localIP().toString();
server.send(200, "text/html", response);
} else {
Serial.println("POST参数有误");
server.send(200, "text/html", "<meta charset='UTF-8'>POST参数有误");
return;
}
//返回保存成功页面
// server.send(200, "text/html", "<meta charset='UTF-8'>保存成功");
//重启
delay(2000);
Serial.println("准备重启中...");
Serial.println();
ESP.reset();
}
//初始化基础
void initBasic(void) {
Serial.begin(115200);
//设置设备名
// WiFi.hostname("HOMEKIT");
// 断开之前链接的WIFI
WiFi.disconnect();
// 初始化 EEPROM
// EEPROM = EEPROMClass(0x3FB);
EEPROM.begin(4096);
}
//初始化AP模式
void initSoftAP(void) {
WiFi.mode(WIFI_AP);
WiFi.softAPConfig(apIP, apIP, IPAddress(255, 255, 255, 0));
if (WiFi.softAP(AP_NAME)) {
Serial.println("AP模式设置成功");
}
}
//初始化WebServer
void initWebServer(void) {
//设置主页回调函数
server.on("/", HTTP_GET, handleRoot);
server.on("/reset", HTTP_GET, handleReset);
server.on("/reconfigure", HTTP_GET, handleReconfigure); // 添加重新配置路由
//设置无法响应的http请求的回调函数
server.onNotFound(handleRoot);
//设置Post请求回调函数
server.on("/", HTTP_POST, handleRootPost);
//启动WebServer
server.begin();
Serial.println();
Serial.println("HTTP服务启动成功!");
}
void handleReconfigure() {
Serial.println("正在重新配置Wi-Fi...");
if (WiFi.status() == WL_CONNECTED) { //如果连接上 就输出IP信息 防止未连接上break后会误输出
// 断开当前的Wi-Fi连接
WiFi.disconnect();
// 启动AP模式
initSoftAP();
initDNS();
// 返回配置页面
server.send(200, "text/html", page_html);
// server.stop();
}
}
//初始化DNS服务器
void initDNS(void) {
//判断将所有地址映射到esp8266的ip上是否成功
if (dnsServer.start(DNS_PORT, "*", apIP)) {
Serial.println("DNS服务器启动成功.");
} else {
Serial.println("DNS服务器启动失败.");
}
}
void connectNewWifi(void) {
Serial.println("读取本地缓存的WIFI名称");
String esid;
for (int i = 0; i < 32; ++i) {
esid += char(EEPROM.read(2048 + i));
}
Serial.println(esid);
Serial.println("读取本地缓存的WIFI密码");
String epass = "";
for (int i = 32; i < 96; ++i) {
epass += char(EEPROM.read(2048 + i));
}
Serial.println(epass);
// WiFi.hostname("esp8266_test");
WiFi.begin(esid, epass); // 链接WIFI
Serial.println("");
Serial.print("正在连接WIFI中");
int count = 0;
while (WiFi.status() != WL_CONNECTED) {
delay(1000);
count++;
if (count > 10) { //如果5秒内没有连上就开启Web配网 可适当调整这个时间
initSoftAP();
initDNS();
break; // 跳出 防止无限初始化
}
Serial.print(".");
}
Serial.println("");
if (WiFi.status() == WL_CONNECTED) { //如果连接上 就输出IP信息 防止未连接上break后会误输出
Serial.println("WIFI链接成功!");
Serial.println("IP地址如下:");
Serial.println(WiFi.localIP());
// server.stop();
}
}
void setup() {
initBasic();
initWebServer();
connectNewWifi();
webSocketServer.begin();
webSocketServer.onEvent(webSocketEvent);
Serial.println("webSocketServer start");
}
void loop() {
server.handleClient();
dnsServer.processNextRequest();
webSocketServer.loop();
delay(5);
}