From c5edf4985a77c8ccd5f74dec5ca297094f2fa88c Mon Sep 17 00:00:00 2001 From: zhaohe Date: Sun, 28 Jan 2024 21:20:42 +0800 Subject: [PATCH] update --- README.md | 6 ++ app/app.uvoptx | 35 +--------- app/src/basic/ssd1306/driver_ssd1306_basic.c | 5 ++ app/src/basic/ssd1306/driver_ssd1306_basic.h | 2 + app/src/one_conduction/display_manager.c | 98 ++++++++++++++++++--------- app/src/one_conduction/one_conduction_board.c | 5 +- app/src/one_conduction/one_conduction_main.c | 91 ++++++++++++++++++++++--- app/src/one_conduction/zeeprom_fs.c | 2 +- libznordic | 2 +- 9 files changed, 164 insertions(+), 82 deletions(-) diff --git a/README.md b/README.md index a36ecc3..d6b7433 100644 --- a/README.md +++ b/README.md @@ -210,4 +210,10 @@ readData(){ 硬件异常: 1. eeprom读写失败 2. 电池电量低 +``` + +``` +编程注意事项: +1. 使用了app_timer后,如果在系统中某个位置延时时间过程,会导致系统重启 + ``` \ No newline at end of file diff --git a/app/app.uvoptx b/app/app.uvoptx index 38ad6a4..d69b009 100644 --- a/app/app.uvoptx +++ b/app/app.uvoptx @@ -148,40 +148,7 @@ UL2CM3(-S0 -C0 -P0 -FD20000000 -FC4000 -FN2 -FF0nrf52xxx -FS00 -FL0200000 -FF1nrf52xxx_uicr -FS110001000 -FL11000 -FP0($$Device:nRF52833_xxAA$Flash\nrf52xxx.flm) -FP1($$Device:nRF52833_xxAA$Flash\nrf52xxx_uicr.flm)) - - - 0 - 0 - 157 - 1 -
206788
- 0 - 0 - 0 - 0 - 0 - 1 - .\src\one_conduction\zeeprom_fs.c - - \\nrf52833_xxaa\src/one_conduction/zeeprom_fs.c\157 -
- - 1 - 0 - 495 - 1 -
192364
- 0 - 0 - 0 - 0 - 0 - 1 - .\src\one_conduction\zeeprom_fs.c - - \\nrf52833_xxaa\src/one_conduction/zeeprom_fs.c\495 -
-
+ 0 diff --git a/app/src/basic/ssd1306/driver_ssd1306_basic.c b/app/src/basic/ssd1306/driver_ssd1306_basic.c index d7ee073..62b6fdb 100644 --- a/app/src/basic/ssd1306/driver_ssd1306_basic.c +++ b/app/src/basic/ssd1306/driver_ssd1306_basic.c @@ -521,6 +521,11 @@ uint8_t ssd1306_basic_draw_screen(const char *img) { } return 0; } +uint8_t ssd1306_basic_clear_gram(void) { + memset(gs_handle.gram, 0, sizeof(gs_handle.gram)); + return 0; +} + uint8_t ssd1306_basic_gram_update() { return ssd1306_gram_update(&gs_handle); } #include "znordic.h" uint8_t ssd1306_basic_draw_one_chr(uint8_t xs, uint8_t ys, const char *str, FontLibrary_t *frontlib) { diff --git a/app/src/basic/ssd1306/driver_ssd1306_basic.h b/app/src/basic/ssd1306/driver_ssd1306_basic.h index 93e3397..4ac9369 100644 --- a/app/src/basic/ssd1306/driver_ssd1306_basic.h +++ b/app/src/basic/ssd1306/driver_ssd1306_basic.h @@ -212,6 +212,8 @@ uint8_t ssd1306_basic_draw_progress(uint8_t xs, uint8_t ys, uint16_t width, uint uint8_t ssd1306_basic_draw_line(uint8_t x1, uint8_t y1,uint8_t x2, uint8_t y2); +uint8_t ssd1306_basic_clear_gram(void); + /** * @} diff --git a/app/src/one_conduction/display_manager.c b/app/src/one_conduction/display_manager.c index ac1d8ca..5fd71dc 100644 --- a/app/src/one_conduction/display_manager.c +++ b/app/src/one_conduction/display_manager.c @@ -28,40 +28,9 @@ void dsp_mgr_schedule(void) {} PageState_t* dsp_mgr_get_state(void) { return NULL; } -void dsp_mgr_change_to_welcome() { - /** - * @brief 切换到欢迎界面 - * 1. 加载屏幕外设 - * 2. 打开屏幕电源 - * 3. 初始化开机页面 - */ - - // ssd1306_basic_string(0, 0, "123456789123456789123", 21, 0, SSD1306_FONT_12); - ssd1306_basic_draw_screen((const char*)gImage_logo_mono); - ssd1306_basic_gram_update(); - dsp_mgr_change_to_page(kPage_welcome); -} - int compute_x_pos_by_center(int16_t x, int16_t width) { return x - width / 2; } int compute_y_pos_by_center(int16_t y, int16_t height) { return y - height / 2; } -void dsp_mgr_change_to_main() { - int16_t batterylevel = 80; - int16_t hour = 12; - int16_t min = 32; - - ssd1306_basic_clear(); - uint8_t x = compute_x_pos_by_center(64, fontclocklib.widthPixel); - uint8_t y = compute_y_pos_by_center(32, fontclocklib.heightPixel * 5 + 1); - uint8_t xchange, ychange; - - ssd1306_basic_draw_str(x, y, &xchange, &ychange, fmt("%02d:%02d", hour, min), &fontclocklib); - x = x + 2 + xchange; - ssd1306_basic_draw_battery_level(x, y, &xchange, &ychange, batterylevel, 12, 22); - ssd1306_basic_gram_update(); - dsp_mgr_change_to_page(kPage_main); -} - void dsp_mgr_change_to_preparePage() { ssd1306_basic_clear(); uint8_t x = 0; @@ -159,6 +128,9 @@ void dsp_mgr_change_to_storagingSuc() { #define CHARGE_BATTERY_WIDTH (12 * 1.2) #define CHARGE_BATTERY_HEIGHT (22 * 1.2) +#define MAIN_PAGE_BATTERY_WIDTH (12) // 首页电池宽度 +#define MAIN_PAGE_BATTERY_HEIGHT (22) // 首页电池高度 + /******************************************************************************* * 充电页面 * *******************************************************************************/ @@ -211,6 +183,64 @@ void chargingPage_schedule() { // } /******************************************************************************* + * 欢迎页面 * + *******************************************************************************/ +void dsp_mgr_change_to_welcome() { + /** + * @brief 切换到欢迎界面 + * 1. 加载屏幕外设 + * 2. 打开屏幕电源 + * 3. 初始化开机页面 + */ + + // ssd1306_basic_string(0, 0, "123456789123456789123", 21, 0, SSD1306_FONT_12); + ssd1306_basic_draw_screen((const char*)gImage_logo_mono); + ssd1306_basic_gram_update(); + dsp_mgr_change_to_page(kPage_welcome); +} + +void welcomePage_schedule() {} + +/******************************************************************************* + * 首页 * + *******************************************************************************/ +static bool m_main_page_colon_state = false; + +void mainPage_show(bool colon_state) { + static ztm_t now; + int16_t batterylevel; + uint8_t xchange, ychange; + uint8_t x, y; + x = compute_x_pos_by_center(SCREEN_CENTER_X, fontclocklib.widthPixel * 5 + MAIN_PAGE_BATTERY_WIDTH); + y = compute_y_pos_by_center(SCREEN_CENTER_Y, fontclocklib.heightPixel + 1); + znordic_rtc_gettime(&now); + batterylevel = SingleLeadECG_battery_val(); + + ssd1306_basic_clear_gram(); + + // ZLOGI("mainPage_show %d %d", colon_state, x, y); + + ssd1306_basic_draw_str(x, y, &xchange, &ychange, fmt("%02d:%02d", now.tm_hour, now.tm_min), &fontclocklib); + x = x + 2 + xchange; + ssd1306_basic_draw_battery_level(x, y, &xchange, &ychange, batterylevel, MAIN_PAGE_BATTERY_WIDTH, MAIN_PAGE_BATTERY_HEIGHT); + ssd1306_basic_gram_update(); + m_main_page_colon_state = colon_state; + dsp_mgr_change_to_page(kPage_main); +} + +void dsp_mgr_change_to_main() { mainPage_show(true); } +void mainPage_updateState() { mainPage_show(!m_main_page_colon_state); } + +void mainPage_schedule() { + static uint32_t last_update_time = 0; + if (znordic_haspassed_ms(last_update_time) < 300) { + return; + } + last_update_time = znordic_getpower_on_ms(); + mainPage_updateState(); +} + +/******************************************************************************* * SCHEDULE * *******************************************************************************/ @@ -218,6 +248,10 @@ APP_TIMER_DEF(m_dsp_mgr_schedule_tmr); static void dsp_mgr_schedule_tmr_cb(void* p_context) { // if (g_pageState.page == kPage_chargingPage) { chargingPage_schedule(); + } else if (g_pageState.page == kPage_welcome) { + welcomePage_schedule(); + } else if (g_pageState.page == kPage_main) { + mainPage_schedule(); } } @@ -227,7 +261,7 @@ void dsp_mgr_init(void) { if (!timer_inited) { ZERROR_CHECK(app_timer_create(&m_dsp_mgr_schedule_tmr, APP_TIMER_MODE_REPEATED, dsp_mgr_schedule_tmr_cb)); } - ZERROR_CHECK(app_timer_start(m_dsp_mgr_schedule_tmr, APP_TIMER_TICKS(100), NULL)); + ZERROR_CHECK(app_timer_start(m_dsp_mgr_schedule_tmr, APP_TIMER_TICKS(101), NULL)); timer_inited = true; } void dsp_mgr_uninit(void) { diff --git a/app/src/one_conduction/one_conduction_board.c b/app/src/one_conduction/one_conduction_board.c index 84bbb40..0561847 100644 --- a/app/src/one_conduction/one_conduction_board.c +++ b/app/src/one_conduction/one_conduction_board.c @@ -213,7 +213,7 @@ void SingleLeadECG_ecg_io_init() { } uint32_t SingleLeadECG_ecg_nlod_get_connected_state() { return nrf_gpio_pin_read(ECG_NLOD_PIN); } -uint32_t SingleLeadECG_ecg_plod_get_connected_state() { return nrf_gpio_pin_read(ECG_PLOD_PIN); } +uint32_t SingleLeadECG_ecg_plod_get_connected_state() { return !nrf_gpio_pin_read(ECG_PLOD_PIN); } int16_t SingleLeadECG_ecg_plod_get_ecg_val() { return znrf_adc_channel_read_val(ECG_ADC_CHANNEL); } /******************************************************************************* @@ -288,7 +288,7 @@ void SingleLeadECG_eeprom_write(uint32_t addr, const uint8_t *data, uint16_t len // ZASSERT(len == EEPROM_PAGE); ZASSERT((addr % EEPROM_PAGE) == 0); - + ZLOGI_BLOCK("eeprom_write %d %d", addr, len); uint8_t deviceSelect = 0; assign_i2c_add(addr, true, &deviceSelect, &eeprom_cache[0], &eeprom_cache[1]); @@ -299,7 +299,6 @@ void SingleLeadECG_eeprom_write(uint32_t addr, const uint8_t *data, uint16_t len ZLOGE("nrf_drv_twi_tx error %x", ecode); NRF_LOG_INTERNAL_FLUSH(); } - nrf_delay_ms(10); } /** * @brief 用来检测读取整个eeprom是否正常 diff --git a/app/src/one_conduction/one_conduction_main.c b/app/src/one_conduction/one_conduction_main.c index 96ea901..4e24a21 100644 --- a/app/src/one_conduction/one_conduction_main.c +++ b/app/src/one_conduction/one_conduction_main.c @@ -101,14 +101,19 @@ static void app_event_process_cb(void* p_event_data, uint16_t event_size); *******************************************************************************/ // 导联连接状态事件生成器 -static void m_plod_state_event_detect_tmr_cb(void* p_context) { // +static uint32_t m_plod_state_disconnect_timepoint = 0; +static uint32_t m_plod_state_connect_timepoint = 0; +static bool m_plod_state_connected_state = false; +static uint32_t plod_state_has_disconnected_ms() { return znordic_haspassed_ms(m_plod_state_disconnect_timepoint); } +static bool plod_state_is_connected() {} +static void m_plod_state_event_detect_tmr_cb(void* p_context) { // static uint32_t connecte_state_trigger_cnt = 0; static uint32_t connecte_state_trigger_cnt_last_val = 0; static app_event_t appevent; memset(&appevent, 0, sizeof(appevent)); connecte_state_trigger_cnt_last_val = connecte_state_trigger_cnt; - if (!SingleLeadECG_ecg_plod_get_connected_state()) { + if (SingleLeadECG_ecg_plod_get_connected_state()) { connecte_state_trigger_cnt++; } else { connecte_state_trigger_cnt = 0; @@ -116,11 +121,15 @@ static void m_plod_state_event_detect_tmr_cb(void* p_context) { // if (connecte_state_trigger_cnt == 5) { // 连接事件 - appevent.eventType = kplod_connected_event; + appevent.eventType = kplod_connected_event; + m_plod_state_connect_timepoint = znordic_getpower_on_ms(); + m_plod_state_connected_state = true; app_sched_event_put(&appevent, sizeof(appevent), app_event_process_cb); } else if (connecte_state_trigger_cnt_last_val >= 5 && connecte_state_trigger_cnt == 0) { // 断开事件 - appevent.eventType = kplod_disconnected_event; + appevent.eventType = kplod_disconnected_event; + m_plod_state_connected_state = false; + m_plod_state_disconnect_timepoint = znordic_getpower_on_ms(); app_sched_event_put(&appevent, sizeof(appevent), app_event_process_cb); } else if (connecte_state_trigger_cnt >= 10 && connecte_state_trigger_cnt % 10 == 0) { // 连接持续事件 @@ -162,10 +171,12 @@ static void state_machine_driver_tmr_cb(void* p_context) { // static void state_machine_change_to_state(device_state_t state) { ZLOGI("change state from %s to %s", device_state_to_str(m_device_state), device_state_to_str(state)); m_device_state = state; - m_change_to_cur_state_tp = znordic_getpower_on_s(); + m_change_to_cur_state_tp = znordic_getpower_on_ms(); } -static void power_on() { +static uint32_t cur_state_haspassed_ms() { return znordic_haspassed_ms(m_change_to_cur_state_tp); } +static bool m_poweronflag; +static void power_on() { SingleLeadECG_adc_module_init(); SingleLeadECG_beep_init(); SingleLeadECG_led_init(); @@ -174,7 +185,7 @@ static void power_on() { sample_data_mgr_init(); dsp_mgr_init(); - + m_poweronflag = true; ZERROR_CHECK(app_timer_start(m_state_machine_driver_tmr, APP_TIMER_TICKS(5), NULL)); // 200HZ采样 } static void power_off() { @@ -186,9 +197,11 @@ static void power_off() { SingleLeadECG_led_deinit(); SingleLeadECG_beep_deinit(); SingleLeadECG_adc_module_deinit(); - ZERROR_CHECK(app_timer_stop(m_state_machine_driver_tmr)); } +/******************************************************************************* + * 状态切换方法 * + *******************************************************************************/ /** * @brief 切换到充电中状态 */ @@ -205,6 +218,33 @@ static void state_machine__change_to_charging_state() { // state_machine_change_to_state(kdevice_state_charging); } +/** + * @brief 切换到待机状态 + */ + +static void state_machine__change_to_standby_state() { + ZLOGI_BLOCK("change to standby"); + power_off(); + state_machine_change_to_state(kdevice_state_standby); +} + +/** + * @brief 切换到开机中画面 + */ +static void state_machine__change_to_poweroning_state() { + power_on(); + dsp_mgr_change_to_welcome(); + state_machine_change_to_state(kdevice_state_poweron); +} + +/** + * @brief 切换到首页 + */ +static void state_machine__change_to_home_state() { + state_machine_change_to_state(kdevice_state_home); + dsp_mgr_change_to_main(); +} + static void app_event_process_cb(void* p_event_data, uint16_t event_size) { if (!p_event_data) return; app_event_t* p_event = (app_event_t*)p_event_data; @@ -217,13 +257,32 @@ static void app_event_process_cb(void* p_event_data, uint16_t event_size) { // 切换到充电状态 state_machine__change_to_charging_state(); } + + if (p_event->eventType == kplod_connected_event) { + // 切换到开机状态 + state_machine__change_to_poweroning_state(); + } + } else if (m_device_state == kdevice_state_charging) { /******************************************************************************* * 充电状态 * *******************************************************************************/ if (!SingleLeadECG_battery_charge_get_state()) { - power_off(); - state_machine_change_to_state(kdevice_state_standby); + state_machine__change_to_standby_state(); + } + } else if (m_device_state == kdevice_state_poweron) { + /******************************************************************************* + * 开机中 * + *******************************************************************************/ + if (cur_state_haspassed_ms() >= 1500) { + state_machine__change_to_home_state(); + } + } else if (m_device_state == kdevice_state_home) { + /******************************************************************************* + * 首页 * + *******************************************************************************/ + if (!m_plod_state_connected_state && plod_state_has_disconnected_ms() >= 3000) { + state_machine__change_to_standby_state(); } } @@ -289,6 +348,7 @@ void one_conduction_main() { }; zble_module_init(&cfg); +#if 1 SingleLeadECG_ecg_io_init(); SingleLeadECG_battery_charge_detect_io_init(); ZERROR_CHECK(app_timer_create(&m_state_machine_driver_tmr, APP_TIMER_MODE_REPEATED, state_machine_driver_tmr_cb)); @@ -297,7 +357,16 @@ void one_conduction_main() { ZERROR_CHECK(app_timer_start(m_plod_state_event_detect_tmr, APP_TIMER_TICKS(100), NULL)); ZERROR_CHECK(app_timer_start(m_charge_event_detect_tmr, APP_TIMER_TICKS(100), NULL)); - znordic_loop(); +#endif + // ZERROR_CHECK(); + while (true) { + app_sched_execute(); + if (NRF_LOG_PROCESS() == false) { + nrf_pwr_mgmt_run(); + } + } + + // znordic_loop(); } // ZERROR_CHECK(app_timer_start(m_state_machine_driver_tmr, APP_TIMER_TICKS(5), NULL)); diff --git a/app/src/one_conduction/zeeprom_fs.c b/app/src/one_conduction/zeeprom_fs.c index 4219d71..42ee80a 100644 --- a/app/src/one_conduction/zeeprom_fs.c +++ b/app/src/one_conduction/zeeprom_fs.c @@ -51,7 +51,7 @@ int zeeprom_fs_init() { // return 0; } int zeeprom_fs_uinit() { // - zeeprom_write(0, (uint8_t*)&m_eeprom_header, sizeof(m_eeprom_header)); + // zeeprom_write(0, (uint8_t*)&m_eeprom_header, sizeof(m_eeprom_header)); SingleLeadECG_eeprom_uninit(); m_is_init = false; return 0; diff --git a/libznordic b/libznordic index 1b52996..0252fc4 160000 --- a/libznordic +++ b/libznordic @@ -1 +1 @@ -Subproject commit 1b529960c77d5fd828c1b3c8fcf975ed80de145c +Subproject commit 0252fc4554585e8924e6e8ba9b2749e0b29c59d3