refactor(app): App-per-screen navigation, remove menu_level entirely
Splits the ad-hoc menu_level state machine into standalone Apps with a uniform parent/child exit convention (long-press CONFIRM -> parent): clock_app renamed to home_app (boot-default), new set_clock_app extracted from home_app's time-edit mode, new ipc_bind_app extracted from menu_app's old level-2 screen, and the sensor-type selection step merged into pair_app as its new initial state. menu_app now only holds the 4-item top-level list (language toggle inline). Also makes both menu_app and pair_app's up/down navigation cyclic (wraps at both ends).
This commit is contained in:
@@ -175,7 +175,7 @@ static void AlarmApp_onClose(void)
|
||||
static EventResult AlarmApp_onEvent(SystemEvent *evt)
|
||||
{
|
||||
if (evt->key_event != KEY_EVENT_NONE) {
|
||||
AppManager_SwitchToForeground(&clock_app); // 清除报警并切回时钟待机页
|
||||
AppManager_SwitchToForeground(&home_app); // 清除报警并切回时钟待机页
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
return EVENT_IGNORED;
|
||||
|
||||
204
App/app_clock.c
204
App/app_clock.c
@@ -1,204 +0,0 @@
|
||||
#include "app_manager.h"
|
||||
#include "clock.h"
|
||||
#include "xtell.h"
|
||||
#include "ui.h"
|
||||
#include "rgb.h"
|
||||
#include "event.h"
|
||||
#include "system.h"
|
||||
#include "../Drivers/rf.h"
|
||||
#include "../Drivers/lcd.h"
|
||||
#include "../Drivers/pcf8563.h"
|
||||
|
||||
// 外部引用的全局系统状态变量
|
||||
extern SystemState current_state;
|
||||
extern volatile u16 ms_tick;
|
||||
|
||||
// 待机时钟应用内特有的编辑时间私有变量
|
||||
static u8 time_edit_active = 0; // 标识当前是否正在编辑修改时间中 (1:是, 0:否)
|
||||
static u8 time_edit_field = 1; // 标识当前聚焦在哪一个参数上进行微调 (1:修改小时, 2:修改分钟)
|
||||
static u8 time_edit_blink_on = 1; // 时钟修改时光标闪烁周期状态位
|
||||
|
||||
// 声明本应用的生命周期回调函数
|
||||
static void ClockApp_OnStart(void);
|
||||
static void ClockApp_onRun(void);
|
||||
static void ClockApp_onClose(void);
|
||||
static EventResult ClockApp_onEvent(SystemEvent *evt);
|
||||
|
||||
// 实体化定义待机时钟应用控制块
|
||||
WristbandApp clock_app = {
|
||||
APP_ID_CLOCK,
|
||||
"Clock",
|
||||
ClockApp_OnStart,
|
||||
ClockApp_onRun,
|
||||
ClockApp_onClose,
|
||||
ClockApp_onEvent
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief 触发启动时间设置状态机,准备修改时钟
|
||||
*/
|
||||
void Start_Time_Edit(void)
|
||||
{
|
||||
time_edit_active = 1;
|
||||
time_edit_field = 1;
|
||||
time_edit_blink_on = 1;
|
||||
current_state = STATE_SET_TIME; // 系统切入时间设置状态
|
||||
|
||||
// FCOB 幻彩灯条双灯珠均显示蓝色常亮 (R=0, G=0, B=180),进行模式视觉区分
|
||||
RGB_Send(0, 0, 180, 0, 0, 180);
|
||||
|
||||
// 振动马达单次短震 50 毫秒,提供触觉反馈
|
||||
MOTOR = 1;
|
||||
Delay_ms(50);
|
||||
MOTOR = 0;
|
||||
|
||||
// 渲染显示时间编辑界面,默认高亮编辑小时字段,消隐位开启
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, 1);
|
||||
XTELL_LOG("[ClockApp] Time edit started.\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief ClockApp 启动回调
|
||||
*/
|
||||
static void ClockApp_OnStart(void)
|
||||
{
|
||||
time_edit_active = 0;
|
||||
current_state = STATE_NORMAL; // 系统切入正常待机状态
|
||||
RF_SetMode(1); // 开启天线并置为接收模式,监听无线探测器
|
||||
|
||||
// 尝试从 PCF8563 RTC 芯片中读取硬件时间 (具备非阻塞防卡死保护)
|
||||
if (PCF8563_Init()) {
|
||||
PCF8563_ReadTime(¤t_hour, ¤t_min, ¤t_sec);
|
||||
XTELL_LOG("[ClockApp] RTC Hardware Synced OK!\r\n");
|
||||
} else {
|
||||
XTELL_LOG("[ClockApp] RTC Hardware Offline, using system clock.\r\n");
|
||||
}
|
||||
|
||||
// 绘制并渲染待机时钟主页面画面
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
|
||||
// 关断/熄灭 FCOB 双灯条
|
||||
RGB_Send(0, 0, 0, 0, 0, 0);
|
||||
|
||||
XTELL_LOG("[ClockApp] Started\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief ClockApp 轮询主回调
|
||||
*/
|
||||
static void ClockApp_onRun(void)
|
||||
{
|
||||
if (time_edit_active)
|
||||
{
|
||||
// ====== 时间设置闪烁动画 (周期 500ms) ======
|
||||
u8 blink = (ms_tick / 500) % 2;
|
||||
if (blink != time_edit_blink_on)
|
||||
{
|
||||
time_edit_blink_on = blink;
|
||||
// 每次闪烁状态发生变化,重新刷写屏幕数值
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, time_edit_blink_on);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// 软时钟发生分钟改变,需要通知屏幕重画时钟主页
|
||||
if (clock_updated) {
|
||||
clock_updated = 0;
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief ClockApp 退出清理回调
|
||||
*/
|
||||
static void ClockApp_onClose(void)
|
||||
{
|
||||
time_edit_active = 0;
|
||||
RGB_Send(0, 0, 0, 0, 0, 0); // 关闭灯条
|
||||
XTELL_LOG("[ClockApp] Closed\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief ClockApp 接收事件处理回调 (按键导航与布撤防交互)
|
||||
*/
|
||||
static EventResult ClockApp_onEvent(SystemEvent *evt)
|
||||
{
|
||||
if (time_edit_active)
|
||||
{
|
||||
// ====== 处于时间设置状态下的按键拦截处理机 ======
|
||||
if (evt->key_event == KEY_EVENT_UP_CLICK)
|
||||
{
|
||||
// 短按 ▲ 键增加数值 (小时/分钟循环相加)
|
||||
if (time_edit_field == 1) {
|
||||
current_hour = (current_hour + 1) % 24;
|
||||
} else {
|
||||
current_min = (current_min + 1) % 60;
|
||||
}
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, 1);
|
||||
return EVENT_HANDLED; // 吞掉并消化事件
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_DOWN_CLICK)
|
||||
{
|
||||
// 短按 ▼ 键减小数值
|
||||
if (time_edit_field == 1) {
|
||||
current_hour = (current_hour == 0) ? 23 : (current_hour - 1);
|
||||
} else {
|
||||
current_min = (current_min == 0) ? 59 : (current_min - 1);
|
||||
}
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, 1);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_LONG)
|
||||
{
|
||||
// 长按 ■ 确认键切换调节字段 (在修改小时与修改分钟间跳转)
|
||||
if (time_edit_field == 1) {
|
||||
time_edit_field = 2;
|
||||
} else {
|
||||
time_edit_field = 1;
|
||||
}
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, 1);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_CLICK)
|
||||
{
|
||||
// 短按 ■ 确认键保存最新时钟配置并退出编辑模式
|
||||
time_edit_active = 0;
|
||||
current_state = STATE_NORMAL;
|
||||
RGB_Send(0, 0, 0, 0, 0, 0); // 熄灭蓝色指示灯
|
||||
|
||||
// 同步将最新时间 (hour, min, 0秒) 写入 PCF8563 芯片寄存器
|
||||
PCF8563_WriteTime(current_hour, current_min, 0);
|
||||
|
||||
// 退出短振反馈
|
||||
MOTOR = 1; Delay_ms(50); MOTOR = 0;
|
||||
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
return EVENT_HANDLED; // 在时间设置模式下屏蔽拦截其他一切无关按键事件
|
||||
}
|
||||
|
||||
// ====== 正常时钟待机状态下的按键拦截处理 ======
|
||||
|
||||
// 1. 长按 ■ 确认键,打开设置主菜单 MenuApp
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_LONG) {
|
||||
AppManager_SwitchToForeground(&menu_app);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
|
||||
// 2. 长按 ▲ 键,一键切换系统的 布防 (ARMED) 和 撤防 (DISARMED) 状态
|
||||
if (evt->key_event == KEY_EVENT_UP_LONG) {
|
||||
if (current_state == STATE_ARMED) {
|
||||
current_state = STATE_DISARMED;
|
||||
} else {
|
||||
current_state = STATE_ARMED;
|
||||
}
|
||||
// 布撤防状态切换成功后进行 100ms 短震确认,并重新刷写时钟待机页
|
||||
MOTOR = 1; Delay_ms(100); MOTOR = 0;
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
|
||||
return EVENT_IGNORED; // 其他未被关心的事件交由后台应用或丢弃
|
||||
}
|
||||
103
App/app_home.c
Normal file
103
App/app_home.c
Normal file
@@ -0,0 +1,103 @@
|
||||
#include "app_manager.h"
|
||||
#include "clock.h"
|
||||
#include "xtell.h"
|
||||
#include "ui.h"
|
||||
#include "rgb.h"
|
||||
#include "event.h"
|
||||
#include "system.h"
|
||||
#include "../Drivers/rf.h"
|
||||
#include "../Drivers/lcd.h"
|
||||
#include "../Drivers/pcf8563.h"
|
||||
|
||||
// 外部引用的全局系统状态变量
|
||||
extern SystemState current_state;
|
||||
extern volatile u16 ms_tick;
|
||||
|
||||
// 声明本应用的生命周期回调函数
|
||||
static void HomeApp_OnStart(void);
|
||||
static void HomeApp_onRun(void);
|
||||
static void HomeApp_onClose(void);
|
||||
static EventResult HomeApp_onEvent(SystemEvent *evt);
|
||||
|
||||
// 实体化定义待机时钟主页应用控制块 (开机默认显示的首屏)
|
||||
WristbandApp home_app = {
|
||||
APP_ID_HOME,
|
||||
"Home",
|
||||
HomeApp_OnStart,
|
||||
HomeApp_onRun,
|
||||
HomeApp_onClose,
|
||||
HomeApp_onEvent
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief HomeApp 启动回调
|
||||
*/
|
||||
static void HomeApp_OnStart(void)
|
||||
{
|
||||
current_state = STATE_NORMAL; // 系统切入正常待机状态
|
||||
RF_SetMode(1); // 开启天线并置为接收模式,监听无线探测器
|
||||
|
||||
// 尝试从 PCF8563 RTC 芯片中读取硬件时间 (具备非阻塞防卡死保护)
|
||||
if (PCF8563_Init()) {
|
||||
PCF8563_ReadTime(¤t_hour, ¤t_min, ¤t_sec);
|
||||
XTELL_LOG("[HomeApp] RTC Hardware Synced OK!\r\n");
|
||||
} else {
|
||||
XTELL_LOG("[HomeApp] RTC Hardware Offline, using system clock.\r\n");
|
||||
}
|
||||
|
||||
// 绘制并渲染待机时钟主页面画面
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
|
||||
// 关断/熄灭 FCOB 双灯条
|
||||
RGB_Send(0, 0, 0, 0, 0, 0);
|
||||
|
||||
XTELL_LOG("[HomeApp] Started\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief HomeApp 轮询主回调
|
||||
*/
|
||||
static void HomeApp_onRun(void)
|
||||
{
|
||||
// 软时钟发生分钟改变,需要通知屏幕重画时钟主页
|
||||
if (clock_updated) {
|
||||
clock_updated = 0;
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief HomeApp 退出清理回调
|
||||
*/
|
||||
static void HomeApp_onClose(void)
|
||||
{
|
||||
RGB_Send(0, 0, 0, 0, 0, 0); // 关闭灯条
|
||||
XTELL_LOG("[HomeApp] Closed\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief HomeApp 接收事件处理回调 (按键导航与布撤防交互)
|
||||
*/
|
||||
static EventResult HomeApp_onEvent(SystemEvent *evt)
|
||||
{
|
||||
// 1. 长按 ■ 确认键,打开设置主菜单 MenuApp
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_LONG) {
|
||||
AppManager_SwitchToForeground(&menu_app);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
|
||||
// 2. 长按 ▲ 键,一键切换系统的 布防 (ARMED) 和 撤防 (DISARMED) 状态
|
||||
if (evt->key_event == KEY_EVENT_UP_LONG) {
|
||||
if (current_state == STATE_ARMED) {
|
||||
current_state = STATE_DISARMED;
|
||||
} else {
|
||||
current_state = STATE_ARMED;
|
||||
}
|
||||
// 布撤防状态切换成功后进行 100ms 短震确认,并重新刷写时钟待机页
|
||||
MOTOR = 1; Delay_ms(100); MOTOR = 0;
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
|
||||
return EVENT_IGNORED; // 其他未被关心的事件交由后台应用或丢弃
|
||||
}
|
||||
85
App/app_ipc_bind.c
Normal file
85
App/app_ipc_bind.c
Normal file
@@ -0,0 +1,85 @@
|
||||
#include "app_manager.h"
|
||||
#include "xtell.h"
|
||||
#include "ui.h"
|
||||
#include "rgb.h"
|
||||
#include "event.h"
|
||||
#include "system.h"
|
||||
#include "../Drivers/rf.h"
|
||||
|
||||
// 外部引用的全局系统状态变量
|
||||
extern SystemState current_state;
|
||||
extern volatile u16 ms_tick;
|
||||
|
||||
// 本应用私有变量
|
||||
static u16 last_bind_tx_ms = 0; // 记录上一次绑定发射的时间戳
|
||||
|
||||
// 声明本应用的生命周期回调函数
|
||||
static void IpcBindApp_OnStart(void);
|
||||
static void IpcBindApp_onRun(void);
|
||||
static void IpcBindApp_onClose(void);
|
||||
static EventResult IpcBindApp_onEvent(SystemEvent *evt);
|
||||
|
||||
// 实体化定义摄像头一键绑定应用控制块 (从 menu_app 的"LIAISON"选项进入)
|
||||
WristbandApp ipc_bind_app = {
|
||||
APP_ID_IPC_BIND,
|
||||
"IpcBind",
|
||||
IpcBindApp_OnStart,
|
||||
IpcBindApp_onRun,
|
||||
IpcBindApp_onClose,
|
||||
IpcBindApp_onEvent
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief IpcBindApp 启动回调
|
||||
*/
|
||||
static void IpcBindApp_OnStart(void)
|
||||
{
|
||||
last_bind_tx_ms = ms_tick; // 记录初始发射时间
|
||||
current_state = STATE_IPC_BIND; // 系统设为 IPC 绑定状态
|
||||
UI_ShowBindingPage(CLONED_ADDR); // 绘制相机绑定信息页
|
||||
XTELL_LOG("[IpcBindApp] Started\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief IpcBindApp 轮询主回调
|
||||
*/
|
||||
static void IpcBindApp_onRun(void)
|
||||
{
|
||||
// ====== 控制青色双灯珠同步呼吸效果 (呼吸周期 1000ms) ======
|
||||
u16 breath = ms_tick % 1000;
|
||||
u8 val = (breath < 500) ? (breath * 2 / 5) : ((1000 - breath) * 2 / 5); // 亮度映射 0~200
|
||||
RGB_Send(0, val, val, 0, val, val); // 渲染青色 (G+B)
|
||||
|
||||
// ====== 控制无线发射,每 500ms 广播一次配对数据 ======
|
||||
if (ms_tick - last_bind_tx_ms >= 500 || ms_tick < last_bind_tx_ms)
|
||||
{
|
||||
last_bind_tx_ms = ms_tick; // 备份当前时间戳
|
||||
RF_SetMode(2); // 暂时切换射频芯片为发射调制模式
|
||||
EV1527_Transmit(CLONED_ADDR, 0x01); // 调制发射手环克隆 ID + 绑定数据码 0x01
|
||||
RF_SetMode(0); // 切回关闭状态,避免产生噪声
|
||||
XTELL_LOG("[IpcBindApp] Binding frame emitted\r\n");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief IpcBindApp 退出清理回调
|
||||
*/
|
||||
static void IpcBindApp_onClose(void)
|
||||
{
|
||||
RGB_Send(0, 0, 0, 0, 0, 0); // 熄灭 RGB
|
||||
XTELL_LOG("[IpcBindApp] Closed\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief IpcBindApp 接收按键事件处理回调
|
||||
*/
|
||||
static EventResult IpcBindApp_onEvent(SystemEvent *evt)
|
||||
{
|
||||
// 长按 ■ 确认键,取消绑定,退出发射并返回主菜单 (父 App)
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_LONG) {
|
||||
current_state = STATE_PAIR_MENU;
|
||||
AppManager_SwitchToForeground(&menu_app);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
return EVENT_IGNORED;
|
||||
}
|
||||
@@ -180,9 +180,11 @@ u8 AppManager_GetActiveAppID(void)
|
||||
// 供遗留代码兼容性引用的 API:StartApp 映射至 SwitchToForeground 动态方式
|
||||
void AppManager_StartApp(AppID app_id)
|
||||
{
|
||||
if (app_id == APP_ID_CLOCK) AppManager_SwitchToForeground(&clock_app);
|
||||
if (app_id == APP_ID_HOME) AppManager_SwitchToForeground(&home_app);
|
||||
else if (app_id == APP_ID_MENU) AppManager_SwitchToForeground(&menu_app);
|
||||
else if (app_id == APP_ID_SET_CLOCK) AppManager_SwitchToForeground(&set_clock_app);
|
||||
else if (app_id == APP_ID_PAIR) AppManager_SwitchToForeground(&pair_app);
|
||||
else if (app_id == APP_ID_IPC_BIND) AppManager_SwitchToForeground(&ipc_bind_app);
|
||||
else if (app_id == APP_ID_ALARM) AppManager_SwitchToForeground(&alarm_app);
|
||||
else if (app_id == APP_ID_SOS) AppManager_SwitchToForeground(&sos_app);
|
||||
}
|
||||
|
||||
@@ -67,9 +67,11 @@ u8 AppManager_GetActiveAppID(void);
|
||||
void AppManager_StartApp(AppID app_id);
|
||||
|
||||
// ====== 系统中各独立 App 实例的外包声明 (各 App 内部进行实体定义) ======
|
||||
extern WristbandApp clock_app;
|
||||
extern WristbandApp home_app;
|
||||
extern WristbandApp menu_app;
|
||||
extern WristbandApp set_clock_app;
|
||||
extern WristbandApp pair_app;
|
||||
extern WristbandApp ipc_bind_app;
|
||||
extern WristbandApp alarm_app;
|
||||
extern WristbandApp sos_app;
|
||||
extern WristbandApp rf_monitor_app; // 后台射频监控应用
|
||||
|
||||
140
App/app_menu.c
140
App/app_menu.c
@@ -8,40 +8,21 @@
|
||||
#include "language.h"
|
||||
#include "../Drivers/rf.h"
|
||||
|
||||
// 二级传感器对码菜单中,各类传感器显示名称的字符串 ID,实际文案由 Lang_Get() 按当前语言取出
|
||||
const StringID device_menu_ids[5] = {
|
||||
STR_DEV_PORTE, // 0: 门磁探测器
|
||||
STR_DEV_PIR, // 1: 红外探测器
|
||||
STR_DEV_FUMEE, // 2: 烟雾传感器
|
||||
STR_DEV_GAZ, // 3: 燃气探测器
|
||||
STR_DEV_EAU // 4: 水浸探测器
|
||||
};
|
||||
|
||||
// 外部全局变量引用
|
||||
extern SystemState current_state;
|
||||
extern u8 menu_select;
|
||||
extern u8 captured_type;
|
||||
extern volatile u16 ms_tick;
|
||||
|
||||
// 菜单应用私有变量
|
||||
static u8 menu_level = 0; // 0-主菜单, 1-二级传感器选择菜单, 2-IPC绑定一键发射
|
||||
static u16 last_bind_tx_ms = 0; // 记录上一次绑定发射的时间戳
|
||||
|
||||
// 引入外部时钟调节接口
|
||||
extern void Start_Time_Edit(void);
|
||||
|
||||
// 声明本应用的生命周期回调函数
|
||||
static void MenuApp_OnStart(void);
|
||||
static void MenuApp_onRun(void);
|
||||
static void MenuApp_onClose(void);
|
||||
static EventResult MenuApp_onEvent(SystemEvent *evt);
|
||||
|
||||
// 实体化定义菜单应用控制块
|
||||
// 实体化定义菜单应用控制块 (顶层 4 项列表:语言切换/时间设置/传感器配对/摄像头绑定)
|
||||
WristbandApp menu_app = {
|
||||
APP_ID_MENU,
|
||||
"Menu",
|
||||
MenuApp_OnStart,
|
||||
MenuApp_onRun,
|
||||
NULL,
|
||||
MenuApp_onClose,
|
||||
MenuApp_onEvent
|
||||
};
|
||||
@@ -51,72 +32,39 @@ WristbandApp menu_app = {
|
||||
*/
|
||||
static void MenuApp_OnStart(void)
|
||||
{
|
||||
menu_level = 0;
|
||||
menu_select = 0;
|
||||
current_state = STATE_PAIR_MENU; // 系统运行状态设为对码配置菜单
|
||||
RF_SetMode(0); // 关闭射频接收芯片,防止接收杂波干扰屏幕绘制
|
||||
UI_ShowMainMenu(menu_select); // 初始化绘制一级主菜单
|
||||
UI_ShowMainMenu(menu_select); // 绘制主菜单
|
||||
RGB_Send(0, 0, 0, 0, 0, 0); // 熄灭所有灯条
|
||||
XTELL_LOG("[MenuApp] Started\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief MenuApp 轮询主回调
|
||||
*/
|
||||
static void MenuApp_onRun(void)
|
||||
{
|
||||
if (menu_level == 2)
|
||||
{
|
||||
// ====== 控制青色双灯珠同步呼吸效果 (呼吸周期 1000ms) ======
|
||||
u16 breath = ms_tick % 1000;
|
||||
u8 val = (breath < 500) ? (breath * 2 / 5) : ((1000 - breath) * 2 / 5); // 亮度映射 0~200
|
||||
RGB_Send(0, val, val, 0, val, val); // 渲染青色 (G+B)
|
||||
|
||||
// ====== 控制无线发射,每 500ms 广播一次配对数据 ======
|
||||
if (ms_tick - last_bind_tx_ms >= 500 || ms_tick < last_bind_tx_ms)
|
||||
{
|
||||
last_bind_tx_ms = ms_tick; // 备份当前时间戳
|
||||
RF_SetMode(2); // 暂时切换射频芯片为发射调制模式
|
||||
EV1527_Transmit(CLONED_ADDR, 0x01); // 调制发射手环克隆 ID + 绑定数据码 0x01
|
||||
RF_SetMode(0); // 切回关闭状态,避免产生噪声
|
||||
XTELL_LOG("[MenuApp] IPC Binding frame emitted\r\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief MenuApp 退出清理回调
|
||||
*/
|
||||
static void MenuApp_onClose(void)
|
||||
{
|
||||
menu_level = 0;
|
||||
RGB_Send(0, 0, 0, 0, 0, 0); // 熄灭 RGB
|
||||
RF_SetMode(1); // 重新开启无线接收模式
|
||||
XTELL_LOG("[MenuApp] Closed\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief MenuApp 接收按键与控制事件回调
|
||||
* @brief MenuApp 接收按键与控制事件回调 (0-语言切换, 1-HORLOGE, 2-APPAIRAGE, 3-LIAISON)
|
||||
*/
|
||||
static EventResult MenuApp_onEvent(SystemEvent *evt)
|
||||
{
|
||||
if (menu_level == 0)
|
||||
{
|
||||
// ====== 处于一级主菜单层 (0-语言切换, 1-HORLOGE, 2-APPAIRAGE, 3-LIAISON) ======
|
||||
if (evt->key_event == KEY_EVENT_UP_CLICK) {
|
||||
// 短按 ▲ 键向上移动焦点
|
||||
if (menu_select > 0) {
|
||||
menu_select--;
|
||||
// 短按 ▲ 键向上移动焦点,允许循环切换 (到顶绕到底)
|
||||
menu_select = (menu_select == 0) ? 3 : (menu_select - 1);
|
||||
UI_ShowMainMenu(menu_select);
|
||||
}
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_DOWN_CLICK) {
|
||||
// 短按 ▼ 键向下移动焦点
|
||||
if (menu_select < 3) {
|
||||
menu_select++;
|
||||
// 短按 ▼ 键向下移动焦点,允许循环切换 (到底绕到顶)
|
||||
menu_select = (menu_select == 3) ? 0 : (menu_select + 1);
|
||||
UI_ShowMainMenu(menu_select);
|
||||
}
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_CLICK) {
|
||||
@@ -129,77 +77,21 @@ static EventResult MenuApp_onEvent(SystemEvent *evt)
|
||||
MOTOR = 1; Delay_ms(50); MOTOR = 0; // 短震反馈,与其它确认操作风格一致
|
||||
UI_ShowMainMenu(menu_select);
|
||||
} else if (menu_select == 1) {
|
||||
// 功能 1:设置时间。启动待机时钟应用,并调用微调编辑入口
|
||||
AppManager_SwitchToForeground(&clock_app);
|
||||
Start_Time_Edit();
|
||||
// 功能 1:设置时间。切换到独立的时间设置子 App
|
||||
AppManager_SwitchToForeground(&set_clock_app);
|
||||
} else if (menu_select == 2) {
|
||||
// 功能 2:传感器学习。进入二级传感器类别选择菜单
|
||||
menu_level = 1;
|
||||
menu_select = 0;
|
||||
UI_ShowPairMenuPage(menu_select); // 绘制二级设备分类页
|
||||
// 功能 2:传感器学习。切换到独立的对码子 App (类型选择是它的第一个状态)
|
||||
AppManager_SwitchToForeground(&pair_app);
|
||||
} else if (menu_select == 3) {
|
||||
// 功能 3:相机配对。进入摄像机一键绑定发射状态
|
||||
menu_level = 2;
|
||||
last_bind_tx_ms = ms_tick; // 记录初始发射时间
|
||||
current_state = STATE_IPC_BIND; // 系统设为 IPC 绑定状态
|
||||
UI_ShowBindingPage(CLONED_ADDR); // 绘制相机绑定信息页
|
||||
// 功能 3:相机配对。切换到独立的摄像头绑定子 App
|
||||
AppManager_SwitchToForeground(&ipc_bind_app);
|
||||
}
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_LONG) {
|
||||
// 长按 ■ 确认键,退出设置菜单直接返回待机时钟
|
||||
AppManager_SwitchToForeground(&clock_app);
|
||||
// 长按 ■ 确认键,退出设置菜单直接返回待机主页
|
||||
AppManager_SwitchToForeground(&home_app);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
}
|
||||
else if (menu_level == 1)
|
||||
{
|
||||
// ====== 处于二级传感器对码类型菜单层 (0-门磁, 1-PIR, 2-烟感, 3-气感, 4-水浸) ======
|
||||
if (evt->key_event == KEY_EVENT_UP_CLICK) {
|
||||
// 上移焦点
|
||||
if (menu_select > 0) {
|
||||
menu_select--;
|
||||
UI_ShowPairMenuPage(menu_select);
|
||||
}
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_DOWN_CLICK) {
|
||||
// 下移焦点
|
||||
if (menu_select < 4) {
|
||||
menu_select++;
|
||||
UI_ShowPairMenuPage(menu_select);
|
||||
}
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_CLICK) {
|
||||
// 确认选择:缓存用户选好的传感器类别,短震反馈并加载对码应用 (PairApp)
|
||||
captured_type = menu_select;
|
||||
MOTOR = 1;
|
||||
Delay_ms(100);
|
||||
MOTOR = 0;
|
||||
AppManager_SwitchToForeground(&pair_app); // 切换至 PairApp 对码
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_DOWN_LONG) {
|
||||
// 长按 ▼ 键,从二级菜单退回到一级主菜单
|
||||
menu_level = 0;
|
||||
menu_select = 2; // 回到 APPAIRAGE 选项上
|
||||
UI_ShowMainMenu(menu_select);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
}
|
||||
else if (menu_level == 2)
|
||||
{
|
||||
// ====== 处于摄像机配对一键绑定发送层 ======
|
||||
// 长按 ■ 确认键 或 长按 ▼ 键,均表示取消绑定,退出发射并返回一级主菜单
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_LONG || evt->key_event == KEY_EVENT_DOWN_LONG) {
|
||||
menu_level = 0;
|
||||
menu_select = 3; // 回到 LIAISON 选项上
|
||||
current_state = STATE_PAIR_MENU;
|
||||
RGB_Send(0, 0, 0, 0, 0, 0); // 关闭呼吸灯
|
||||
UI_ShowMainMenu(menu_select);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
}
|
||||
return EVENT_IGNORED;
|
||||
}
|
||||
|
||||
@@ -12,10 +12,21 @@
|
||||
extern SystemState current_state;
|
||||
extern u8 captured_type;
|
||||
extern u32 captured_addr;
|
||||
extern u8 menu_select;
|
||||
extern volatile u16 ms_tick;
|
||||
|
||||
// 二级传感器对码菜单中,各类传感器显示名称的字符串 ID,实际文案由 Lang_Get() 按当前语言取出
|
||||
const StringID device_menu_ids[5] = {
|
||||
STR_DEV_PORTE, // 0: 门磁探测器
|
||||
STR_DEV_PIR, // 1: 红外探测器
|
||||
STR_DEV_FUMEE, // 2: 烟雾传感器
|
||||
STR_DEV_GAZ, // 3: 燃气探测器
|
||||
STR_DEV_EAU // 4: 水浸探测器
|
||||
};
|
||||
|
||||
// 对码状态机定义
|
||||
enum {
|
||||
PAIR_STATE_SELECT_TYPE, // 选择要学习的传感器类型 (门磁/PIR/烟感/气感/水浸)
|
||||
PAIR_STATE_WAIT, // 等待射频探测器触发 (扩散雷达页面)
|
||||
PAIR_STATE_CONFIRM, // 已捕获,进入分配防区确认页面
|
||||
PAIR_STATE_SUCCESS, // 对码绑定成功界面 (SUCCESS)
|
||||
@@ -48,13 +59,10 @@ WristbandApp pair_app = {
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief PairApp 启动回调
|
||||
* @brief 进入雷达搜索等待阶段 (选定传感器类型之后)
|
||||
*/
|
||||
static void PairApp_OnStart(void)
|
||||
static void PairApp_EnterWait(void)
|
||||
{
|
||||
// 1. 为了防止后台射频监听与对码射频接收冲突,将后台射频监听应用暂时卸载
|
||||
AppManager_DetachFromBackground(&rf_monitor_app);
|
||||
|
||||
pair_state = PAIR_STATE_WAIT;
|
||||
last_radar_sec = 99; // 强制刷写
|
||||
current_state = STATE_PAIR_WAIT;
|
||||
@@ -69,7 +77,25 @@ static void PairApp_OnStart(void)
|
||||
// 开启白色幻彩双灯珠常亮 (R=150, G=150, B=150),作为对码状态视觉指示
|
||||
RGB_Send(150, 150, 150, 150, 150, 150);
|
||||
|
||||
XTELL_LOG("[PairApp] Started (WAIT)\r\n");
|
||||
XTELL_LOG("[PairApp] Entering WAIT\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief PairApp 启动回调
|
||||
*/
|
||||
static void PairApp_OnStart(void)
|
||||
{
|
||||
// 为了防止后台射频监听与对码射频接收冲突,将后台射频监听应用暂时卸载
|
||||
AppManager_DetachFromBackground(&rf_monitor_app);
|
||||
|
||||
pair_state = PAIR_STATE_SELECT_TYPE;
|
||||
menu_select = 0;
|
||||
current_state = STATE_PAIR_MENU;
|
||||
RF_SetMode(0); // 选类型阶段暂不需要天线,防止接收杂波干扰屏幕绘制
|
||||
UI_ShowPairMenuPage(menu_select); // 绘制传感器类型选择页
|
||||
RGB_Send(0, 0, 0, 0, 0, 0);
|
||||
|
||||
XTELL_LOG("[PairApp] Started (SELECT_TYPE)\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -142,14 +168,14 @@ static void PairApp_onRun(void)
|
||||
else RGB_Send(0, 0, 0, 0, 0, 0);
|
||||
}
|
||||
else if (pair_state == PAIR_STATE_SUCCESS) {
|
||||
// ====== 成功展示状态:延时 2 秒自动返回二级设置菜单 ======
|
||||
// ====== 成功展示状态:延时 2 秒自动返回主菜单 ======
|
||||
u8 elapsed = (current_sec >= success_start_sec) ? (current_sec - success_start_sec) : (60 + current_sec - success_start_sec);
|
||||
if (elapsed >= 2) {
|
||||
AppManager_SwitchToForeground(&menu_app);
|
||||
}
|
||||
}
|
||||
else if (pair_state == PAIR_STATE_FAIL) {
|
||||
// ====== 失败展示状态:延时 5 秒自动返回二级设置菜单 ======
|
||||
// ====== 失败展示状态:延时 5 秒自动返回主菜单 ======
|
||||
u8 elapsed = (current_sec >= fail_start_sec) ? (current_sec - fail_start_sec) : (60 + current_sec - fail_start_sec);
|
||||
if (elapsed >= 5) {
|
||||
AppManager_SwitchToForeground(&menu_app);
|
||||
@@ -177,6 +203,30 @@ static void PairApp_onClose(void)
|
||||
*/
|
||||
static EventResult PairApp_onEvent(SystemEvent *evt)
|
||||
{
|
||||
if (pair_state == PAIR_STATE_SELECT_TYPE) {
|
||||
if (evt->key_event == KEY_EVENT_UP_CLICK) {
|
||||
// 短按 ▲ 键上移焦点,允许循环切换 (到顶绕到底)
|
||||
menu_select = (menu_select == 0) ? 4 : (menu_select - 1);
|
||||
UI_ShowPairMenuPage(menu_select);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_DOWN_CLICK) {
|
||||
// 短按 ▼ 键下移焦点,允许循环切换 (到底绕到顶)
|
||||
menu_select = (menu_select == 4) ? 0 : (menu_select + 1);
|
||||
UI_ShowPairMenuPage(menu_select);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_CLICK) {
|
||||
// 确认选择:缓存用户选好的传感器类别,短震反馈并进入雷达搜索阶段
|
||||
captured_type = menu_select;
|
||||
MOTOR = 1;
|
||||
Delay_ms(100);
|
||||
MOTOR = 0;
|
||||
PairApp_EnterWait();
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
}
|
||||
|
||||
if (pair_state == PAIR_STATE_CONFIRM) {
|
||||
if (evt->key_event == KEY_EVENT_UP_CLICK) {
|
||||
// 短按 ▲ 键增加目标分配防区号 (上限 99)
|
||||
@@ -212,16 +262,10 @@ static EventResult PairApp_onEvent(SystemEvent *evt)
|
||||
XTELL_LOG("[PairApp] Sensor saved successfully.\r\n");
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_LONG) {
|
||||
// 长按 ■ 确认键放弃本次捕获,直接返回二级主菜单
|
||||
RGB_Send(0, 0, 0, 0, 0, 0);
|
||||
AppManager_SwitchToForeground(&menu_app);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
}
|
||||
|
||||
// 在对码搜寻或确认防区期间,长按 ▼ 键均代表强行取消对码直接退回菜单页
|
||||
if (evt->key_event == KEY_EVENT_DOWN_LONG) {
|
||||
// 在任何阶段,长按 ■ 确认键或长按 ▼ 键都代表放弃/取消对码,统一退回主菜单 (父 App)
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_LONG || evt->key_event == KEY_EVENT_DOWN_LONG) {
|
||||
RGB_Send(0, 0, 0, 0, 0, 0);
|
||||
AppManager_SwitchToForeground(&menu_app);
|
||||
return EVENT_HANDLED;
|
||||
|
||||
133
App/app_set_clock.c
Normal file
133
App/app_set_clock.c
Normal file
@@ -0,0 +1,133 @@
|
||||
#include "app_manager.h"
|
||||
#include "clock.h"
|
||||
#include "xtell.h"
|
||||
#include "ui.h"
|
||||
#include "rgb.h"
|
||||
#include "event.h"
|
||||
#include "system.h"
|
||||
#include "../Drivers/pcf8563.h"
|
||||
|
||||
// 外部引用的全局系统状态变量
|
||||
extern SystemState current_state;
|
||||
extern volatile u16 ms_tick;
|
||||
|
||||
// 本应用私有的时间编辑状态
|
||||
static u8 time_edit_field = 1; // 标识当前聚焦在哪一个参数上进行微调 (1:修改小时, 2:修改分钟)
|
||||
static u8 time_edit_blink_on = 1; // 时钟修改时光标闪烁周期状态位
|
||||
|
||||
// 声明本应用的生命周期回调函数
|
||||
static void SetClockApp_OnStart(void);
|
||||
static void SetClockApp_onRun(void);
|
||||
static void SetClockApp_onClose(void);
|
||||
static EventResult SetClockApp_onEvent(SystemEvent *evt);
|
||||
|
||||
// 实体化定义时间设置应用控制块 (从 menu_app 的"HORLOGE"选项进入)
|
||||
WristbandApp set_clock_app = {
|
||||
APP_ID_SET_CLOCK,
|
||||
"SetClock",
|
||||
SetClockApp_OnStart,
|
||||
SetClockApp_onRun,
|
||||
SetClockApp_onClose,
|
||||
SetClockApp_onEvent
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief SetClockApp 启动回调
|
||||
*/
|
||||
static void SetClockApp_OnStart(void)
|
||||
{
|
||||
time_edit_field = 1;
|
||||
time_edit_blink_on = 1;
|
||||
current_state = STATE_SET_TIME; // 系统切入时间设置状态
|
||||
|
||||
// FCOB 幻彩灯条双灯珠均显示蓝色常亮 (R=0, G=0, B=180),进行模式视觉区分
|
||||
RGB_Send(0, 0, 180, 0, 0, 180);
|
||||
|
||||
// 振动马达单次短震 50 毫秒,提供触觉反馈
|
||||
MOTOR = 1;
|
||||
Delay_ms(50);
|
||||
MOTOR = 0;
|
||||
|
||||
// 渲染显示时间编辑界面,默认高亮编辑小时字段,消隐位开启
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, 1);
|
||||
XTELL_LOG("[SetClockApp] Started\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief SetClockApp 轮询主回调
|
||||
*/
|
||||
static void SetClockApp_onRun(void)
|
||||
{
|
||||
// ====== 时间设置闪烁动画 (周期 500ms) ======
|
||||
u8 blink = (ms_tick / 500) % 2;
|
||||
if (blink != time_edit_blink_on)
|
||||
{
|
||||
time_edit_blink_on = blink;
|
||||
// 每次闪烁状态发生变化,重新刷写屏幕数值
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, time_edit_blink_on);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief SetClockApp 退出清理回调
|
||||
*/
|
||||
static void SetClockApp_onClose(void)
|
||||
{
|
||||
RGB_Send(0, 0, 0, 0, 0, 0); // 关闭灯条
|
||||
XTELL_LOG("[SetClockApp] Closed\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief SetClockApp 接收按键事件处理回调
|
||||
*/
|
||||
static EventResult SetClockApp_onEvent(SystemEvent *evt)
|
||||
{
|
||||
if (evt->key_event == KEY_EVENT_UP_CLICK)
|
||||
{
|
||||
// 短按 ▲ 键增加数值 (小时/分钟循环相加)
|
||||
if (time_edit_field == 1) {
|
||||
current_hour = (current_hour + 1) % 24;
|
||||
} else {
|
||||
current_min = (current_min + 1) % 60;
|
||||
}
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, 1);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_DOWN_CLICK)
|
||||
{
|
||||
// 短按 ▼ 键减小数值
|
||||
if (time_edit_field == 1) {
|
||||
current_hour = (current_hour == 0) ? 23 : (current_hour - 1);
|
||||
} else {
|
||||
current_min = (current_min == 0) ? 59 : (current_min - 1);
|
||||
}
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, 1);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_LONG)
|
||||
{
|
||||
// 长按 ■ 确认键切换调节字段 (在修改小时与修改分钟间跳转)
|
||||
if (time_edit_field == 1) {
|
||||
time_edit_field = 2;
|
||||
} else {
|
||||
time_edit_field = 1;
|
||||
}
|
||||
UI_ShowSetTimePage(current_hour, current_min, time_edit_field, 1);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
if (evt->key_event == KEY_EVENT_CONFIRM_CLICK)
|
||||
{
|
||||
// 短按 ■ 确认键保存最新时钟配置,退出到主菜单 (父 App)
|
||||
current_state = STATE_PAIR_MENU;
|
||||
|
||||
// 同步将最新时间 (hour, min, 0秒) 写入 PCF8563 芯片寄存器
|
||||
PCF8563_WriteTime(current_hour, current_min, 0);
|
||||
|
||||
// 退出短振反馈
|
||||
MOTOR = 1; Delay_ms(50); MOTOR = 0;
|
||||
|
||||
AppManager_SwitchToForeground(&menu_app);
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
return EVENT_HANDLED; // 在时间设置模式下屏蔽拦截其他一切无关按键事件
|
||||
}
|
||||
@@ -127,7 +127,7 @@ static void SOSApp_onClose(void)
|
||||
static EventResult SOSApp_onEvent(SystemEvent *evt)
|
||||
{
|
||||
if (evt->key_event != KEY_EVENT_NONE) {
|
||||
AppManager_SwitchToForeground(&clock_app); // 退出 SOS,返回时钟
|
||||
AppManager_SwitchToForeground(&home_app); // 退出 SOS,返回时钟
|
||||
return EVENT_HANDLED;
|
||||
}
|
||||
return EVENT_IGNORED;
|
||||
|
||||
@@ -108,9 +108,11 @@ typedef enum {
|
||||
|
||||
/* ====== 应用程序 ID 枚举 ====== */
|
||||
typedef enum {
|
||||
APP_ID_CLOCK, // 待机时钟应用程序 (首屏)
|
||||
APP_ID_MENU, // 系统设置与操作主菜单应用程序
|
||||
APP_ID_PAIR, // 无线传感器对码学习应用程序
|
||||
APP_ID_HOME, // 待机时钟主页应用程序 (开机默认首屏)
|
||||
APP_ID_MENU, // 系统设置主菜单应用程序 (顶层 4 项列表)
|
||||
APP_ID_SET_CLOCK, // 时间设置应用程序 (menu_app 子应用)
|
||||
APP_ID_PAIR, // 无线传感器对码学习应用程序 (menu_app 子应用)
|
||||
APP_ID_IPC_BIND, // 摄像头一键绑定应用程序 (menu_app 子应用)
|
||||
APP_ID_ALARM, // 报警接收与波形反馈应用程序
|
||||
APP_ID_SOS, // 紧急呼救与无线发射应用程序
|
||||
APP_ID_MAX // 应用程序最大数量上限,用于数组大小
|
||||
|
||||
14
App/main.c
14
App/main.c
@@ -15,7 +15,7 @@
|
||||
SystemState current_state = STATE_NORMAL; // 系统整体的当前运行状态,默认为正常时钟待机页
|
||||
|
||||
|
||||
u8 menu_select = 0; // 主菜单当前选中的行高亮索引 (0~2)
|
||||
u8 menu_select = 0; // 当前菜单高亮的选中项索引 (menu_app 0~3,pair_app 传感器类型选择 0~4)
|
||||
u32 captured_addr = 0; // 配对或报警时,捕获到的传感器 24 位 EV1527 射频物理地址
|
||||
u8 captured_type = 0; // 正在对码或触发警报的传感器设备类型 (0:门磁, 1:PIR...)
|
||||
u8 alarm_sensor_slot = 0; // 触发警报的传感器在 sensor_list 数组中的索引槽位号
|
||||
@@ -162,21 +162,21 @@ void Debug_ProcessCommand(char cmd)
|
||||
}
|
||||
} else if (cmd == '1') {
|
||||
// 模拟切换至 正常撤防 (NORMAL) 状态并刷新时钟
|
||||
if (AppManager_GetActiveAppID() == APP_ID_CLOCK) {
|
||||
if (AppManager_GetActiveAppID() == APP_ID_HOME) {
|
||||
current_state = STATE_NORMAL;
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
}
|
||||
Uart_SendString("[UART] State: NORMAL\r\n");
|
||||
} else if (cmd == '2') {
|
||||
// 模拟切换至 已布防 (ARMED) 状态,普通门磁可触发警报
|
||||
if (AppManager_GetActiveAppID() == APP_ID_CLOCK) {
|
||||
if (AppManager_GetActiveAppID() == APP_ID_HOME) {
|
||||
current_state = STATE_ARMED;
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
}
|
||||
Uart_SendString("[UART] State: ARMED\r\n");
|
||||
} else if (cmd == '3') {
|
||||
// 模拟切换至 已撤防 (DISARMED) 状态,忽略普通报警
|
||||
if (AppManager_GetActiveAppID() == APP_ID_CLOCK) {
|
||||
if (AppManager_GetActiveAppID() == APP_ID_HOME) {
|
||||
current_state = STATE_DISARMED;
|
||||
UI_ShowClockPage(current_state, current_hour, current_min);
|
||||
}
|
||||
@@ -267,7 +267,7 @@ void main(void)
|
||||
/* 步骤 1: 初始化事件环形缓冲区队列 */
|
||||
EventQueue_Init();
|
||||
|
||||
/* 步骤 2+5: 初始化应用管理器并登记所有前台应用,默认加载 ClockApp */
|
||||
/* 步骤 2+5: 初始化应用管理器并登记所有前台应用,默认加载 HomeApp */
|
||||
AppManager_Init();
|
||||
|
||||
/* 启动并挂载后台射频监控应用,开始侦听无线传感器信号 */
|
||||
@@ -277,7 +277,7 @@ void main(void)
|
||||
Timer1_Init();
|
||||
|
||||
/* 开机自动加载并运行待机时钟前台活跃应用 */
|
||||
AppManager_StartApp(APP_ID_CLOCK);
|
||||
AppManager_StartApp(APP_ID_HOME);
|
||||
|
||||
Uart_SendString("[SYS] Event-driven framework ready\r\n");
|
||||
|
||||
@@ -309,7 +309,7 @@ void main(void)
|
||||
current_state = STATE_SLEEP; // 系统置为休眠状态
|
||||
Enter_Low_Power_Sleep(); // 该函数是阻塞的,MCU 将在此挂起。唤醒后将自动从其后继续执行
|
||||
current_state = STATE_NORMAL; // 唤醒后重新置为正常待机状态
|
||||
AppManager_StartApp(APP_ID_CLOCK); // 重新开启时钟应用以刷新画面和背光
|
||||
AppManager_StartApp(APP_ID_HOME); // 重新开启时钟应用以刷新画面和背光
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -375,9 +375,14 @@
|
||||
<FilePath>.\App\clock.c</FilePath>
|
||||
</File>
|
||||
<File>
|
||||
<FileName>app_clock.c</FileName>
|
||||
<FileName>app_home.c</FileName>
|
||||
<FileType>1</FileType>
|
||||
<FilePath>.\App\app_clock.c</FilePath>
|
||||
<FilePath>.\App\app_home.c</FilePath>
|
||||
</File>
|
||||
<File>
|
||||
<FileName>app_set_clock.c</FileName>
|
||||
<FileType>1</FileType>
|
||||
<FilePath>.\App\app_set_clock.c</FilePath>
|
||||
</File>
|
||||
<File>
|
||||
<FileName>app_menu.c</FileName>
|
||||
@@ -389,6 +394,11 @@
|
||||
<FileType>1</FileType>
|
||||
<FilePath>.\App\app_pair.c</FilePath>
|
||||
</File>
|
||||
<File>
|
||||
<FileName>app_ipc_bind.c</FileName>
|
||||
<FileType>1</FileType>
|
||||
<FilePath>.\App\app_ipc_bind.c</FilePath>
|
||||
</File>
|
||||
<File>
|
||||
<FileName>app_alarm.c</FileName>
|
||||
<FileType>1</FileType>
|
||||
|
||||
Reference in New Issue
Block a user