基于ESP-NOW的ESP32-box-lite飞控监测平台
开发软件: Arduino IDE
硬件:
ESP32-box-lite:飞控监测平台
ESP32-C3 无人机开发板
一、 项目介绍
本项目依托电子森林、得捷电子、硬禾学堂,基于ESP32-BOX-LITE,在ESP-NOW协议上实现了无人机飞控监测平台。本项目通过LCD屏幕、物理按键和实现了数据实时互传显示,取得了良好的效果,具有一定的价值。 项目任务: ESP32-BOX-LITE通过提供的ESP-NOW模块自组网 在ESP32-BOX-LITE屏上显示飞行状态、距离.... 通过在ESP32-BOX-LITE屏的按键能够实时发送信息给指定无人机的飞控板ESP32-C3
二、 设计思路
本项目设计围绕ESP32-BOX-LITE,首先对ESP32-BOX-LITE的板载硬件进行实验使用,初步掌握板载的IO硬件以及显示实现的功能与实际性能。再根据硬件的具体功能,实现设计。设计步骤如下:
-
配置ESP32-S3- BOX
2.逻辑思维图
三、 硬件介绍
ESP32-S3-BOX AI语音开发套件是乐鑫打造的一个智能语音设备开发平台
ESP32-S3-BOX 既可以用于构建智能音箱,也可以赋能更多物联网设备实现人机语音交互。同时,它还集触摸屏控制、传感器、红外控制器和智能网关等多功能于一体,能够作为全屋设备的控制中枢,支持用户通过语音命令控制或触屏控制,轻松实现圈内智能联动。
ESP32-S3-BOX-Lite 是目前对应的 AIoT 应用开发板,搭载支持 AI 加速的 ESP32-S3 Wi-Fi + Bluetooth 5 (LE) SoC。为用户提供了一个基于语音助手、传感器、红外控制器和智能 Wi-Fi 网关等功能开发和控制智能家居设备的平台。开发板出厂支持离线语音交互功能,用户通过乐鑫丰富的 SDK 和解决方案,能够轻松构建在线和离线语音助手、智能语音设备、HMI 人机交互设备、控制面板、多协议网关等多样的应用。
支持特性:
双麦克风支持远场语音交互 高唤醒率的离线语音唤醒 高识别率的离线中英文命令词识别 可动态配置 200+ 中英文命令词 连续识别和唤醒打断 灵活可复用的 GUI 框架 端到端一站式接入云平台 Pmod™ 兼容接口支持多种外设扩展
ESP32-S3-BOX-Lite 轻量级开发套件。它与 ESP32-S3-BOX 拥有类似的离、在线语音功能,取消了电容触摸面板和 Mute 按键,增加了 3 个由客户自定义的功能按键。
核心微控制器:ESP32-S3
ESP32-S3 是一款集成 2.4 GHz Wi-Fi 和 Bluetooth 5 (LE) 的 MCU 芯片,支持远距离模式 (Long Range)。ESP32-S3 搭载 Xtensa® 32 位 LX7 双核处理器,主频高达 240 MHz,内置 512 KB SRAM (TCM),具有 45 个可编程 GPIO 管脚和丰富的通信接口。ESP32-S3 支持更大容量的高速 Octal SPI flash 和片外 RAM,支持用户配置数据缓存与指令缓存。
Xtensa® 32 位 LX7 双核处理器,主频高达 240 MHz 内置 512 KB SRAM、384 KB ROM 存储空间,并支持多个外部 SPI、Dual SPI、 Quad SPI、Octal SPI、QPI、OPI flash 和片外 RAM 额外增加用于加速神经网络计算和信号处理等工作的向量指令 (vector instructions) 45 个可编程 GPIO,支持常用外设接口如 SPI、I2S、I2C、PWM、RMT、ADC、UART、SD/MMC 主机控制器和 TWAITM 控制器等 基于 AES-XTS 算法的 Flash 加密和基于 RSA 算法的安全启动,数字签名和 HMAC 模块,“世界控制器 (World Controller)”模块
四、 功能介绍
1.初始化开机界面:屏幕显示“Flighting Control Platform”标题及相关信息
2.过6秒自动进入主界面
3.屏幕上显示两架无人机的相关信息
4.程序逻辑会自动处理,无人机太远距离的回调指令发送
5.按指定的按键能让指定的无人机接收指令强行返回安全区
五、 主要代码
/*
This sketch targets the ESP32-S3-BOX board ONLY
It demonstrates a compatible Adafruit GFX Graphics Library benchmark sketch
*/
// Testing if the user has selected the right board in the menu
#ifndef TT21100_ADDR
#error Please select the right board in the Arduino IDE: ESP32-S3-Box
#endif
#include "ESP32_S3_Box_TFT.h"
#include <esp_now.h>
#include <WiFi.h>
// These constants won't change. They're used to give names to the pins used:
const int analogInPin = 1; // Analog input pin that the potentiometer is attached to
int sensorValue = 0; // value read from the pot
// 飞控机型一号MAC地址
uint8_t receiverMacAddress1[] = {0x7C,0xDF,0xA1,0xFF,0x31,0x81};
// 飞控机型二号
uint8_t receiverMacAddress2[] = {0x7C,0xDF,0xA1,0xFF,0x32,0x82};
//中文:凌 (这就是存储点阵变量,str_1可以修改成自己喜欢的名称,用函数drawBitmap()调用就可以了)
static const unsigned char PROGMEM str_1[] =
{
0x00,0x40,0x40,0x40,0x23,0xF8,0x20,0x40,0x00,0x40,0x07,0xFE,0x11,0x10,0x12,0x88,
0x24,0x84,0xE1,0xF0,0x23,0x10,0x24,0xA0,0x20,0x40,0x20,0xA0,0x23,0x10,0x0C,0x0C
};
struct MessageData
{
int xAxisValue;
int distance;
bool switchPressed;
int fanxiang;
};
MessageData messageData;
struct warningMessageData1
{
bool isReturn;
};
warningMessageData1 warningMessageData1;
struct warningMessageData2
{
bool isReturn;
};
warningMessageData2 warningMessageData2;
// callback function that will be executed when data is received
void OnDataRecv(const uint8_t * mac, const uint8_t *incomingData, int len)
{
if (len == 0)
{
return;
}
memcpy(&messageData, incomingData, sizeof(messageData));
String inputData ;
inputData = inputData + "values " + messageData.xAxisValue + " " + messageData.distance + " " + messageData.switchPressed + " " + messageData.fanxiang;
Serial.println(inputData);
}
//设备设置
ESP32S3BOX_TFT tft = ESP32S3BOX_TFT();
void setup() {
// put your setup code here, to run once:
Serial.begin(115200);
delay(500);
tft.init();
tft.setRotation(0); // Landscape orientation
tft.setTextSize(2);
Serial.println("TFT Initialized.");
// large block of text
tft.fillScreen(ST7789_BLACK);
tft.setTextWrap(true);
tft.setTextColor(ST7789_WHITE);
//设置标题:飞控监测平台
tft.setCursor(80, 2);
tft.setTextSize(3);
tft.print("Flighting");
tft.setCursor(20, 30);
tft.print("Control Platform");
//硬件相关信息
tft.setTextSize(2);
tft.setCursor(0, 80);
tft.print(" Chip Model: " + String(ESP.getChipModel()));
tft.setCursor(0, 110);
tft.print(" rotation: " + String(tft.getRotation()));
tft.setCursor(0, 140);
tft.print(" " + String(tft.width()) + " x " + String(tft.height()));
//显示中文测试
//tft.drawBitmap(26, 110, str_1, 16, 16, 1); //在坐标X:26 Y:110的位置显示中文字符凌
delay(7000);
Serial.println("Done!");
tft.fillScreen(ST7789_BLACK);
WiFi.mode(WIFI_STA);
// Init ESP-NOW 初始化
if (esp_now_init() != ESP_OK)
{
Serial.println("Error initializing ESP-NOW");
return;
}
else
{
Serial.println("Succes: inited ESP-NOW");
}
esp_now_register_recv_cb(OnDataRecv);
}
void loop() {
sensorValue = analogRead(analogInPin);
tft.fillRect(10, 90, 120, 22, ST7789_BLUE);
tft.fillRect(10, 210, 120, 22, ST7789_BLUE);
//飞控机型一号
if (10==messageData.xAxisValue){
tft.setCursor(0, 5);
tft.setTextColor(ST7789_YELLOW);
tft.setTextSize(2);
tft.println("-Aircraft type XYZ001-");
tft.fillRect(180, 35, 90, 28, ST7789_BLUE);
tft.fillRect(180, 60, 90, 28, ST7789_BLUE);
tft.setCursor(0, 40);
tft.setTextColor(ST7789_WHITE);
if (1==messageData.fanxiang)
tft.println(" Flying Status: Top ");
if (2==messageData.fanxiang)
tft.println(" Flying Status: Left ");
if (3==messageData.fanxiang)
tft.println(" Flying Status: Bottom");
if (4==messageData.fanxiang)
tft.println(" Flying Status: Right ");
tft.println(" ");
tft.println(" Line Distance: " + String(messageData.distance) + " m");
//安全距离预警
if(35==messageData.distance){
warningMessageData1.isReturn = 1;
esp_err_t result1 = esp_now_send(receiverMacAddress1, (uint8_t *) &warningMessageData1, sizeof(warningMessageData1));
if (result1 == ESP_OK)
{
Serial.println("Sent with success");
}
else
{
Serial.println("Error sending the data");
}
warningMessageData1.isReturn = 0;
}
}
//飞控机型二号
if (11==messageData.xAxisValue){
tft.setCursor(0, 120);
tft.setTextColor(ST7789_GREEN); tft.setTextSize(2);
tft.println("-Aircraft type ABC001-");
tft.fillRect(180, 155, 90, 28, ST7789_BLUE);
tft.fillRect(180, 180, 90, 28, ST7789_BLUE);
tft.setCursor(0, 160);
tft.setTextColor(ST7789_WHITE);
if (1==messageData.fanxiang)
tft.println(" Flying Status: Top ");
if (2==messageData.fanxiang)
tft.println(" Flying Status: Left ");
if (3==messageData.fanxiang)
tft.println(" Flying Status: Bottom");
if (4==messageData.fanxiang)
tft.println(" Flying Status: Right ");
tft.println(" ");
tft.println(" Line Distance: " + String(messageData.distance) + " m");
//安全距离预警
if(35==messageData.distance){
warningMessageData2.isReturn = 1;
esp_err_t result1 = esp_now_send(receiverMacAddress1, (uint8_t *) &warningMessageData2, sizeof(warningMessageData2));
if (result1 == ESP_OK)
{
Serial.println("Sent with success");
}
else
{
Serial.println("Error sending the data");
}
warningMessageData2.isReturn = 0;
}
}
//按下左键 发送消息给 飞控机型一号 强行返程
if ((2800<sensorValue) && (3500>sensorValue)){
Serial.println("Button Left");
warningMessageData1.isReturn = 1;
esp_err_t result1 = esp_now_send(receiverMacAddress1, (uint8_t *) &warningMessageData1, sizeof(warningMessageData1));
if (result1 == ESP_OK)
{
Serial.println("Sent with success");
}
else
{
Serial.println("Error sending the data");
}
tft.setCursor(0, 90);
tft.println(" Go Home!!!");
warningMessageData1.isReturn = 0;
}
//按下中键
if ((2000<sensorValue) && (2700>sensorValue)){
Serial.println("Button Middle");
}
//按下右键 发送消息给 飞控机型一号 强行返程
if ((500<sensorValue) && (1200>sensorValue)){
Serial.println("Button Right");
warningMessageData2.isReturn = 1;
esp_err_t result2 = esp_now_send(receiverMacAddress1, (uint8_t *) &warningMessageData2, sizeof(warningMessageData2));
if (result2 == ESP_OK)
{
Serial.println("Sent with success");
}
else
{
Serial.println("Error sending the data");
}
tft.setCursor(0, 210);
tft.println(" Go Home!!!");
warningMessageData2.isReturn = 0;
}
delay(600);
}
六、 活动总结与未来计划
通过对本项目的学习,我对esp32模块又有了进一步的了解,目前实现功能锻炼了我的动手能力和编程能力,对嵌入式开发有了新的体会,受益匪浅。计划后续还会针对项目加强改进,比如整合LGVL,语音指令等,未来期望再次参加活动,了解并学习更多的知识,掌握更多的技能,开拓电子芯片在生活中运用的视野,改变思维模式,在专业上有既定的发展方向。