2026-07-31 18:05:23 +08:00
|
|
|
|
#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;
|
|
|
|
|
|
|
2026-07-31 18:49:03 +08:00
|
|
|
|
// 待机时钟界面闲置多久自动进入低功耗休眠的门限 (秒)
|
|
|
|
|
|
#define HOME_IDLE_SLEEP_SEC 10
|
|
|
|
|
|
|
|
|
|
|
|
// 本应用私有变量:累计未按任何键的秒数 (由 KEY_EVENT_SECOND_TICK 驱动,任意按键事件清零)
|
|
|
|
|
|
static u8 home_idle_sec = 0;
|
|
|
|
|
|
|
2026-07-31 18:05:23 +08:00
|
|
|
|
// 声明本应用的生命周期回调函数
|
|
|
|
|
|
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)
|
|
|
|
|
|
{
|
2026-07-31 18:49:03 +08:00
|
|
|
|
home_idle_sec = 0; // 重新进入待机主页 (开机/从菜单退回/休眠唤醒) 都清零闲置计数
|
2026-07-31 18:05:23 +08:00
|
|
|
|
current_state = STATE_NORMAL; // 系统切入正常待机状态
|
|
|
|
|
|
RF_SetMode(1); // 开启天线并置为接收模式,监听无线探测器
|
|
|
|
|
|
|
2026-07-31 19:54:18 +08:00
|
|
|
|
#if USE_PCF8563
|
2026-07-31 19:43:43 +08:00
|
|
|
|
// 尝试从 PCF8563 RTC 芯片中读取硬件时间与日期 (具备非阻塞防卡死保护)
|
2026-07-31 18:05:23 +08:00
|
|
|
|
if (PCF8563_Init()) {
|
2026-07-31 19:43:43 +08:00
|
|
|
|
PCF8563_ReadDateTime(¤t_hour, ¤t_min, ¤t_sec, ¤t_day, ¤t_month, ¤t_year);
|
|
|
|
|
|
Clock_RecalcWeekday(); // 读回的日期可能与软时钟不同,重新算一次星期
|
2026-07-31 18:05:23 +08:00
|
|
|
|
XTELL_LOG("[HomeApp] RTC Hardware Synced OK!\r\n");
|
|
|
|
|
|
} else {
|
|
|
|
|
|
XTELL_LOG("[HomeApp] RTC Hardware Offline, using system clock.\r\n");
|
|
|
|
|
|
}
|
2026-07-31 19:54:18 +08:00
|
|
|
|
#else
|
|
|
|
|
|
XTELL_LOG("[HomeApp] USE_PCF8563=0, running on software clock only.\r\n");
|
|
|
|
|
|
#endif
|
2026-07-31 18:05:23 +08:00
|
|
|
|
|
|
|
|
|
|
// 绘制并渲染待机时钟主页面画面
|
2026-07-31 19:43:43 +08:00
|
|
|
|
UI_ShowClockPage(current_state, current_hour, current_min, current_weekday, current_day, current_month);
|
2026-07-31 18:05:23 +08:00
|
|
|
|
|
|
|
|
|
|
// 关断/熄灭 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;
|
2026-07-31 19:43:43 +08:00
|
|
|
|
UI_ShowClockPage(current_state, current_hour, current_min, current_weekday, current_day, current_month);
|
2026-07-31 18:05:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* @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)
|
|
|
|
|
|
{
|
2026-07-31 18:49:03 +08:00
|
|
|
|
// 0. 整秒滴答:累计闲置秒数,达到门限就进入低功耗休眠
|
|
|
|
|
|
if (evt->key_event == KEY_EVENT_SECOND_TICK) {
|
|
|
|
|
|
home_idle_sec++;
|
|
|
|
|
|
if (home_idle_sec >= HOME_IDLE_SLEEP_SEC) {
|
|
|
|
|
|
home_idle_sec = 0;
|
|
|
|
|
|
current_state = STATE_SLEEP; // 系统置为休眠状态
|
|
|
|
|
|
Enter_Low_Power_Sleep(); // 阻塞函数,MCU 在此挂起,唤醒后自动继续往下执行
|
|
|
|
|
|
AppManager_SwitchToForeground(&home_app); // 强制重新走一遍 OnStart,刷新画面和背光
|
|
|
|
|
|
}
|
|
|
|
|
|
return EVENT_HANDLED;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 收到任意其它按键事件,说明用户仍在活动,清零闲置计数
|
|
|
|
|
|
home_idle_sec = 0;
|
|
|
|
|
|
|
2026-07-31 18:05:23 +08:00
|
|
|
|
// 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;
|
2026-07-31 19:43:43 +08:00
|
|
|
|
UI_ShowClockPage(current_state, current_hour, current_min, current_weekday, current_day, current_month);
|
2026-07-31 18:05:23 +08:00
|
|
|
|
return EVENT_HANDLED;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
return EVENT_IGNORED; // 其他未被关心的事件交由后台应用或丢弃
|
|
|
|
|
|
}
|