244 lines
8.5 KiB
C
244 lines
8.5 KiB
C
#include "if_standby.h"
|
|
|
|
#include <sys/time.h>
|
|
|
|
#include "esp_log.h"
|
|
#include "if_wifi.h"
|
|
#include "impl_lvgl.h"
|
|
|
|
#define LOG_TAG "IF_STANDBY"
|
|
|
|
#define IF_EVENT_WIFI_BUTTON 0
|
|
#define IF_EVENT_BAT_BUTTON 1
|
|
|
|
typedef struct {
|
|
if_standby_component_t component;
|
|
char payload[IF_STANDBY_PAYLOAD_LENGTH];
|
|
} if_standby_request_t;
|
|
|
|
static TaskHandle_t s_if_standby_handle;
|
|
static QueueHandle_t s_standby_screen_queue;
|
|
|
|
lv_obj_t *g_standby_screen;
|
|
|
|
void if_standby_event_handler(lv_event_t *ev) {
|
|
int button_event = (int)ev->user_data;
|
|
|
|
switch (button_event) {
|
|
case IF_EVENT_WIFI_BUTTON:
|
|
if_wifi_init(g_standby_screen);
|
|
break;
|
|
case IF_EVENT_BAT_BUTTON:
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
}
|
|
/**
|
|
* @brief Standby screen task, handles GUI element updates through a queue.
|
|
*
|
|
* @param pvParameters
|
|
*/
|
|
void if_standby_task(void *pvParameters) {
|
|
impl_lvgl_lock();
|
|
|
|
// Custom style.
|
|
lv_style_t container_style;
|
|
lv_style_init(&container_style);
|
|
lv_style_set_border_color(&container_style, lv_color_white());
|
|
lv_style_set_border_width(&container_style, 0);
|
|
lv_style_set_outline_width(&container_style, 0);
|
|
lv_style_set_pad_all(&container_style, 0);
|
|
|
|
// 1st line
|
|
lv_obj_t *top_container = lv_obj_create(g_standby_screen);
|
|
|
|
lv_obj_add_style(top_container, &container_style, 0);
|
|
|
|
lv_obj_set_size(top_container, 400, 50);
|
|
lv_obj_align(top_container, LV_ALIGN_TOP_MID, 0, 0);
|
|
lv_obj_set_flex_flow(top_container, LV_FLEX_FLOW_ROW);
|
|
|
|
lv_obj_t *network_status_obj = lv_btn_create(top_container);
|
|
lv_obj_t *weekday_obj = lv_obj_create(top_container);
|
|
lv_obj_t *date_obj = lv_obj_create(top_container);
|
|
lv_obj_t *battery_obj = lv_btn_create(top_container);
|
|
|
|
lv_obj_add_event_cb(network_status_obj, if_standby_event_handler, LV_EVENT_CLICKED, (void *)IF_EVENT_WIFI_BUTTON);
|
|
lv_obj_add_event_cb(battery_obj, if_standby_event_handler, LV_EVENT_CLICKED, (void *)IF_EVENT_BAT_BUTTON);
|
|
|
|
lv_obj_set_size(network_status_obj, 50, 50);
|
|
lv_obj_set_size(battery_obj, 50, 50);
|
|
|
|
lv_obj_set_height(weekday_obj, 50);
|
|
lv_obj_set_height(date_obj, 50);
|
|
|
|
lv_obj_set_flex_grow(weekday_obj, 1);
|
|
lv_obj_set_flex_grow(date_obj, 3);
|
|
|
|
// 2nd line
|
|
lv_obj_t *main_container = lv_obj_create(g_standby_screen);
|
|
|
|
lv_obj_add_style(main_container, &container_style, 0);
|
|
|
|
lv_obj_set_size(main_container, 400, 245);
|
|
lv_obj_align_to(main_container, top_container, LV_ALIGN_OUT_BOTTOM_MID, 0, 5);
|
|
lv_obj_set_flex_flow(main_container, LV_FLEX_FLOW_ROW);
|
|
|
|
lv_obj_t *time_obj = lv_obj_create(main_container);
|
|
|
|
lv_obj_set_height(time_obj, 245);
|
|
lv_obj_set_flex_grow(time_obj, 1);
|
|
|
|
// 2nd line, DHT column
|
|
lv_obj_t *dht_container = lv_obj_create(main_container);
|
|
|
|
lv_obj_add_style(dht_container, &container_style, 0);
|
|
|
|
lv_obj_set_size(dht_container, 100, 245);
|
|
lv_obj_set_flex_flow(dht_container, LV_FLEX_FLOW_COLUMN);
|
|
|
|
lv_obj_t *temp_obj = lv_obj_create(dht_container);
|
|
lv_obj_t *humid_obj = lv_obj_create(dht_container);
|
|
|
|
lv_obj_set_width(temp_obj, 100);
|
|
lv_obj_set_width(humid_obj, 100);
|
|
|
|
lv_obj_set_flex_grow(temp_obj, 1);
|
|
lv_obj_set_flex_grow(humid_obj, 1);
|
|
|
|
// Create labels
|
|
lv_obj_t *network_status_label = lv_label_create(network_status_obj);
|
|
lv_obj_t *weekday_label = lv_label_create(weekday_obj);
|
|
lv_obj_t *date_label = lv_label_create(date_obj);
|
|
lv_obj_t *battery_label = lv_label_create(battery_obj);
|
|
lv_obj_t *time_label = lv_label_create(time_obj);
|
|
lv_obj_t *temp_icon_label = lv_label_create(temp_obj);
|
|
lv_obj_t *temp_label = lv_label_create(temp_obj);
|
|
lv_obj_t *humid_icon_label = lv_label_create(humid_obj);
|
|
lv_obj_t *humid_label = lv_label_create(humid_obj);
|
|
|
|
lv_obj_set_style_text_font(network_status_label, &material_webfont_32, 0);
|
|
lv_obj_set_style_text_font(weekday_label, &bebas_neue_32, 0);
|
|
lv_obj_set_style_text_font(date_label, &bebas_neue_32, 0);
|
|
lv_obj_set_style_text_font(battery_label, &material_webfont_32, 0);
|
|
lv_obj_set_style_text_font(time_label, &bebas_neue_120, 0);
|
|
lv_obj_set_style_text_font(temp_icon_label, &material_webfont_32, 0);
|
|
lv_obj_set_style_text_font(temp_label, &bebas_neue_32, 0);
|
|
lv_obj_set_style_text_font(humid_icon_label, &material_webfont_32, 0);
|
|
lv_obj_set_style_text_font(humid_label, &bebas_neue_32, 0);
|
|
|
|
lv_label_set_text(network_status_label, "\U000F092D");
|
|
lv_label_set_text(battery_label, "\U000F007A");
|
|
lv_label_set_text(weekday_label, "SUN");
|
|
lv_label_set_text(date_label, "1970/01/01");
|
|
lv_label_set_text(time_label, "23:59");
|
|
lv_label_set_text(temp_icon_label, "\U000F0599");
|
|
lv_label_set_text(temp_label, "30.00");
|
|
lv_label_set_text(humid_icon_label, "\U000F058C");
|
|
lv_label_set_text(humid_label, "100.00");
|
|
|
|
lv_obj_set_align(network_status_label, LV_ALIGN_CENTER);
|
|
lv_obj_set_align(battery_label, LV_ALIGN_CENTER);
|
|
lv_obj_set_align(weekday_label, LV_ALIGN_CENTER);
|
|
lv_obj_set_align(date_label, LV_ALIGN_CENTER);
|
|
lv_obj_set_align(time_label, LV_ALIGN_CENTER);
|
|
lv_obj_align(temp_icon_label, LV_ALIGN_CENTER, 0, -16);
|
|
lv_obj_align(temp_label, LV_ALIGN_CENTER, 0, 16);
|
|
lv_obj_align(humid_icon_label, LV_ALIGN_CENTER, 0, -16);
|
|
lv_obj_align(humid_label, LV_ALIGN_CENTER, 0, 16);
|
|
|
|
impl_lvgl_unlock();
|
|
|
|
ESP_LOGI(LOG_TAG, "Standby screen created.");
|
|
|
|
if_standby_request_t update_request;
|
|
|
|
for (;;) {
|
|
// Read from queue for UI element updates.
|
|
xQueueReceive(s_standby_screen_queue, &update_request, portMAX_DELAY);
|
|
impl_lvgl_lock();
|
|
switch (update_request.component) {
|
|
case IF_STANDBY_COMPONENT_DATE:
|
|
lv_label_set_text(date_label, update_request.payload);
|
|
lv_obj_set_align(date_label, LV_ALIGN_CENTER);
|
|
break;
|
|
case IF_STANDBY_COMPONENT_HUMID:
|
|
lv_label_set_text(humid_label, update_request.payload);
|
|
lv_obj_align(humid_label, LV_ALIGN_CENTER, 0, 16);
|
|
break;
|
|
case IF_STANDBY_COMPONENT_HUMID_ICON:
|
|
lv_label_set_text(humid_icon_label, update_request.payload);
|
|
lv_obj_align(humid_icon_label, LV_ALIGN_CENTER, 0, -16);
|
|
break;
|
|
case IF_STANDBY_COMPONENT_TEMP:
|
|
lv_label_set_text(temp_label, update_request.payload);
|
|
lv_obj_align(temp_label, LV_ALIGN_CENTER, 0, 16);
|
|
break;
|
|
case IF_STANDBY_COMPONENT_TEMP_ICON:
|
|
lv_label_set_text(temp_icon_label, update_request.payload);
|
|
lv_obj_align(temp_icon_label, LV_ALIGN_CENTER, 0, -16);
|
|
break;
|
|
case IF_STANDBY_COMPONENT_TIME:
|
|
lv_label_set_text(time_label, update_request.payload);
|
|
lv_obj_set_align(time_label, LV_ALIGN_CENTER);
|
|
break;
|
|
case IF_STANDBY_COMPONENT_WEEKDAY:
|
|
lv_label_set_text(weekday_label, update_request.payload);
|
|
lv_obj_set_align(weekday_label, LV_ALIGN_CENTER);
|
|
break;
|
|
case IF_STANDBY_COMPONENT_WIFI:
|
|
lv_label_set_text(network_status_label, update_request.payload);
|
|
lv_obj_set_align(network_status_label, LV_ALIGN_CENTER);
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
impl_lvgl_unlock();
|
|
}
|
|
}
|
|
|
|
esp_err_t if_standby_init(void) {
|
|
impl_lvgl_lock();
|
|
g_standby_screen = lv_obj_create(NULL);
|
|
lv_disp_load_scr(g_standby_screen);
|
|
impl_lvgl_unlock();
|
|
|
|
s_standby_screen_queue = xQueueCreate(8, sizeof(if_standby_request_t));
|
|
if (s_standby_screen_queue == NULL) {
|
|
return ESP_FAIL;
|
|
}
|
|
|
|
if (xTaskCreate(if_standby_task, "IF_STBY", 4096, NULL, 6, &s_if_standby_handle) != pdPASS) {
|
|
return ESP_FAIL;
|
|
}
|
|
|
|
return ESP_OK;
|
|
}
|
|
|
|
/**
|
|
* @brief Update component content on standby screen.
|
|
*
|
|
* @param component if_standby_component_t
|
|
* @param fmt printf-style format
|
|
* @param ...
|
|
* @return esp_err_t
|
|
*/
|
|
esp_err_t if_standby_component_update(if_standby_component_t component, const char *fmt, ...) {
|
|
if_standby_request_t req;
|
|
va_list ap;
|
|
|
|
req.component = component;
|
|
|
|
va_start(ap, fmt);
|
|
vsnprintf(req.payload, IF_STANDBY_PAYLOAD_LENGTH, fmt, ap);
|
|
va_end(ap);
|
|
|
|
// Queue update command.
|
|
if (xQueueSendToBack(s_standby_screen_queue, &req, 0) != pdPASS) {
|
|
return ESP_FAIL;
|
|
}
|
|
|
|
return ESP_OK;
|
|
}
|