智能家居项目开发与测试全流程
1. 完成 AppSensorNode 类实现
当
m_reading_cb
成员变量被设置时,会以
reading
作为参数调用它,至此,
AppSensorNode
类的实现完成。
2. 实现 GUI
在开发板显示屏上实现 GUI,其界面设计在 SquareLine Studio 中完成,界面顶部有显示当前日期/时间的标签元素,下方两个面板分别显示光线和温度值,底部的复选框指示 MQTT 连接状态。
为实现 GUI,添加新的 C++ 头文件
main/AppUi.hpp
:
#pragma once
#include <mutex>
#include <vector>
#include <ctime>
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "freertos/timers.h"
#include "freertos/queue.h"
#include "esp_log.h"
#include "bsp_board.h"
#include "bsp_lcd.h"
#include "lvgl/lvgl.h"
#include "lv_port/lv_port.h"
#include "ui.h"
#include "AppCommon.hpp"
namespace app
{
class AppUi
{
private:
static std::mutex m_ui_access;
QueueHandle_t m_sensor_reading_queue;
static void lvglTask(void *arg);
void setSensorValues(const SensorReading_t &r);
static void updateDatetime(void *arg);
public:
void init(void)
{
m_sensor_reading_queue = xQueueCreate(1,
sizeof(SensorReading_t));
bsp_board_init();
lv_port_init();
ui_init();
xTaskCreatePinnedToCore(lvglTask, "lvgl", 6 * 1024,
this, 3, nullptr, 0);
bsp_lcd_set_backlight(true);
setenv("TZ", "GMT", 1);
tzset();
}
void updateSensorReading(const SensorReading_t &reading)
{
xQueueSendToBack(m_sensor_reading_queue, &reading, 0);
}
void updateMqttState(bool connected)
{
std::lock_guard<std::mutex> lock(m_ui_access);
if (connected)
{
lv_obj_add_state(ui_chkConnected,
LV_STATE_CHECKED);
lv_checkbox_set_text(ui_chkConnected,
"Connected");
}
else
{
lv_checkbox_set_text(ui_chkConnected,
"Disconnected");
lv_obj_clear_state(ui_chkConnected,
LV_STATE_CHECKED);
}
}
void start(void)
{
static TimerHandle_t timer{nullptr};
if (timer == nullptr)
{
timer = xTimerCreate("datetime",
pdMS_TO_TICKS(1000), pdTRUE, nullptr,
updateDatetime);
xTimerStart(timer, 0);
}
}
};
std::mutex AppUi::m_ui_access;
void AppUi::setSensorValues(const SensorReading_t &r)
{
lv_label_set_text(ui_txtLight,
std::to_string(r.light_intensity).c_str());
lv_label_set_text(ui_txtTemp,
std::to_string(r.temperature).substr(0, 4).c_str());
}
void AppUi::updateDatetime(void *arg)
{
std::lock_guard<std::mutex> lock(m_ui_access);
time_t now;
char strftime_buf[64]{0};
struct tm timeinfo;
time(&now);
localtime_r(&now, &timeinfo);
strftime(strftime_buf, sizeof(strftime_buf), "%c",
&timeinfo);
lv_label_set_text(ui_txtTime, strftime_buf);
}
void AppUi::lvglTask(void *arg)
{
AppUi *obj = reinterpret_cast<AppUi *>(arg);
while (true)
{
{
std::lock_guard<std::mutex> lock(m_ui_access);
SensorReading_t r;
if (xQueueReceive(obj->m_sensor_reading_queue, &r,
0) == pdTRUE)
{
obj->setSensorValues(r);
}
lv_task_handler();
}
vTaskDelay(pdMS_TO_TICKS(10));
}
}
}
以下是
AppUi
类的关键成员说明:
| 成员 | 说明 |
| ---- | ---- |
|
m_ui_access
| 控制对 LVGL 元素访问的互斥锁 |
|
m_sensor_reading_queue
| 用于传递传感器读数数据的 FreeRTOS 队列 |
|
lvglTask
| 用于更新显示屏的 FreeRTOS 任务函数 |
|
setSensorValues
| 根据给定的传感器读数更新 UI 元素 |
|
updateDatetime
| 每秒刷新屏幕上的日期/时间文本 |
3. 编写应用程序代码
在
main/sensor.cpp
文件中集成所有组件:
#include "AppDriver.hpp"
#include "AppSensorNode.hpp"
#include "AppUi.hpp"
namespace
{
app::AppDriver app_driver;
app::AppSensorNode app_sensor_node;
app::AppUi app_ui;
}
extern "C" void app_main(void)
{
app_driver.init();
app_ui.init();
app_sensor_node.init();
auto sensor_reading_handler = [](const app::SensorReading_t &r)
-> void
{
app_ui.updateSensorReading(r);
};
app_sensor_node.setReadingCb(sensor_reading_handler);
auto mqtt_state_handler = [](void *arg, esp_event_base_t
event_base, int32_t event_id, void *event_data) -> void
{
if (event_base != RMAKER_COMMON_EVENT)
{
return;
}
switch (event_id)
{
case RMAKER_MQTT_EVENT_CONNECTED:
app_ui.updateMqttState(true);
break;
case RMAKER_MQTT_EVENT_DISCONNECTED:
app_ui.updateMqttState(false);
break;
default:
break;
}
};
app_sensor_node.addRmakerEventHandler(mqtt_state_handler,
nullptr);
app_ui.start();
app_sensor_node.start();
app_driver.start();
}
4. 测试项目
测试插头应用程序
- 确保插头硬件准备就绪,ESP32 - C3 DevkitM - 1 与继电器模块连接。
- 进入插头 ESP - IDF 项目目录,在开发板上烧录应用程序:
$ idf.py erase - flash flash monitor
- 启动移动设备上的 RainMaker 应用程序,添加插头,完成配置向导后,点击“完成”按钮返回主屏幕。
- 插头添加后会显示在主屏幕上,点击插头图标左上角的开/关图标,测试继电器状态是否改变,开发板上的 LED 状态也会相应改变。
- 按下开发板上的按钮改变继电器状态,观察移动应用程序上插头状态是否更新。
测试多传感器应用程序
- 确保多传感器硬件准备就绪,ESP32 - S3 Box Lite 与 BME280 和 TSL2561 传感器连接。
- 进入多传感器 ESP - IDF 项目目录,在开发板上烧录应用程序:
$ idf.py erase - flash flash monitor - p /dev/ttyACM0
- 点击移动应用程序主屏幕上的“+”图标添加新设备,并按照说明操作。
- 多传感器应用程序添加后,其图标会显示在主屏幕上插头图标旁边。
- 多传感器图标右上角显示光线强度值,打开手机手电筒增加 TSL2561 上的光线水平,观察移动应用程序和多传感器显示屏上的光线强度值是否更新。
以下是测试流程的 mermaid 流程图:
graph LR
A[开始] --> B[测试插头应用程序]
B --> B1[准备插头硬件]
B --> B2[烧录插头应用程序]
B --> B3[添加插头到 RainMaker 应用]
B --> B4[测试插头开关状态]
B --> B5[按开发板按钮测试]
A --> C[测试多传感器应用程序]
C --> C1[准备多传感器硬件]
C --> C2[烧录多传感器应用程序]
C --> C3[添加多传感器到 RainMaker 应用]
C --> C4[测试光线强度更新]
B5 --> D[结束]
C4 --> D
5. 使用智能家居功能
智能家居产品通常具备比简单设备控制更多的功能,如定义自动化或定时操作,以及与语音服务集成等。RainMaker 移动应用程序提供了这些功能,下面将详细介绍如何使用这些功能:
定时功能
- 在主屏幕底部的图标列表中,点击“定时”图标,然后点击“添加定时”按钮。
- 为定时任务命名,将时间设置为当前时间之后 2 分钟,并在“操作”列表中选择将插头打开。
- 保存定时任务后,它将显示在定时任务列表中。等待 2 分钟,观察插头状态是否自动打开。
场景功能
- 点击底部的“场景”按钮,然后点击“添加场景”按钮,启动向导。
- 虽然当前设置中只有一个插头,但此功能允许在有多个设备(如智能百叶窗、智能灯泡和连接的音乐播放器)的情况下,将它们组合到一个场景中,通过一次点击改变它们的状态。
- 完成向导后,激活场景,观察设备状态是否按场景定义改变。
自动化功能
- 点击底部列表中的“自动化”按钮,然后点击“添加自动化”按钮。
- 为自动化任务命名,选择“传感器”,并将光线强度设置为高于当前值作为触发事件。
- 将“插头关闭”设置为触发后的操作。
- 保存自动化任务后,它将显示在列表中。使用手机手电筒将光线强度设置为高于事件阈值,观察如果插头当前处于打开状态,其状态是否变为关闭。
语音服务集成(以 Alexa 为例)
- 从底部列表中选择“设置”,然后在设置中点击“语音服务”。
- 从列表中选择“Amazon Alexa”。
- 按照向导完成与 Alexa 的账户关联。
- 打开手机上的 Alexa 应用程序,进入所有设备列表,观察“插头”和“传感器”是否列出。选择“插头”。
- 点击中间的开/关按钮,尝试打开和关闭插头。
以下是使用智能家居功能的操作步骤列表:
| 功能 | 操作步骤 |
| ---- | ---- |
| 定时功能 | 1. 点击“定时”图标和“添加定时”按钮;2. 命名定时任务,设置时间和操作;3. 保存并等待执行 |
| 场景功能 | 1. 点击“场景”和“添加场景”按钮;2. 完成向导;3. 激活场景 |
| 自动化功能 | 1. 点击“自动化”和“添加自动化”按钮;2. 命名自动化任务,设置触发事件和操作;3. 保存并触发事件观察结果 |
| 语音服务集成(Alexa) | 1. 进入设置选择“语音服务”;2. 选择“Amazon Alexa”;3. 完成账户关联;4. 在 Alexa 应用中操作设备 |
以下是智能家居功能使用流程的 mermaid 流程图:
graph LR
A[开始] --> B[定时功能]
B --> B1[点击定时图标和添加定时按钮]
B --> B2[设置定时任务]
B --> B3[保存并等待执行]
A --> C[场景功能]
C --> C1[点击场景和添加场景按钮]
C --> C2[完成向导]
C --> C3[激活场景]
A --> D[自动化功能]
D --> D1[点击自动化和添加自动化按钮]
D --> D2[设置自动化任务]
D --> D3[保存并触发事件]
A --> E[语音服务集成(Alexa)]
E --> E1[进入设置选择语音服务]
E --> E2[选择 Amazon Alexa]
E --> E3[完成账户关联]
E --> E4[在 Alexa 应用中操作设备]
B3 --> F[结束]
C3 --> F
D3 --> F
E4 --> F
通过以上步骤,我们完成了智能家居项目的开发、测试以及各种功能的使用,实现了设备的智能化控制和管理。
超级会员免费看
2万+

被折叠的 条评论
为什么被折叠?



