From 13a00fbe1b8f1ffecb69590fbd5d822be243c69b Mon Sep 17 00:00:00 2001 From: Ivan Li Date: Fri, 24 Feb 2023 21:29:15 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=94=AF=E6=8C=81=E8=AF=AD=E9=9F=B3?= =?UTF-8?q?=E6=A8=A1=E5=9D=97=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .vscode/settings.json | 9 +++- main/CMakeLists.txt | 2 +- main/Kconfig.projbuild | 39 ++++++++++---- main/ambient_light.c | 6 ++- main/ci_03t.c | 113 ++++++++++++++++++++++++++++++++++++++++ main/config_key.h | 26 +++++++++ main/embedded_display.c | 35 +++++++++++++ main/light.c | 1 + main/main.c | 10 ++-- main/mqtt.c | 63 +++++++++++++++++++++- main/temperature.c | 5 +- main/ui_input.c | 43 +-------------- 12 files changed, 290 insertions(+), 62 deletions(-) create mode 100644 main/ci_03t.c create mode 100644 main/config_key.h diff --git a/.vscode/settings.json b/.vscode/settings.json index 915bf19..9dfdd6c 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -47,6 +47,13 @@ "string.h": "c", "i2c.h": "c", "esp_log.h": "c", - "queue.h": "c" + "queue.h": "c", + "optional": "c", + "istream": "c", + "ostream": "c", + "ratio": "c", + "functional": "c", + "tuple": "c", + "type_traits": "c" } } diff --git a/main/CMakeLists.txt b/main/CMakeLists.txt index 646c31b..a18d2df 100644 --- a/main/CMakeLists.txt +++ b/main/CMakeLists.txt @@ -1,2 +1,2 @@ -idf_component_register(SRCS "ui_input.c" "asr_pro.c" "ambient_light.c" "temperature.c" "embedded_display.c" "mqtt.c" "main.c" "wifi.c" "light.c" "mqtt.c" +idf_component_register(SRCS "asr_pro.c" "ci_03t.c" "ui_input.c" "ambient_light.c" "temperature.c" "embedded_display.c" "mqtt.c" "main.c" "wifi.c" "light.c" "mqtt.c" INCLUDE_DIRS ".") \ No newline at end of file diff --git a/main/Kconfig.projbuild b/main/Kconfig.projbuild index 6a7d7bc..ab9cd5f 100644 --- a/main/Kconfig.projbuild +++ b/main/Kconfig.projbuild @@ -67,38 +67,38 @@ endmenu menu "Encoder Configuration" config ENCODER_0_CLK_PIN int "encoder 0 click GPIO" - range 1 32 + range 0 32 default 2 help Encoder 0 clock pin config ENCODER_0_DT_PIN int "encoder 0 data GPIO" - range 1 32 + range 0 32 default 3 help Encoder 0 clock data config ENCODER_0_SW_PIN int "encoder 0 switch GPIO" - range 1 32 + range 0 32 default 4 help Encoder 0 switch pin config ENCODER_1_CLK_PIN int "encoder 1 click GPIO" - range 1 32 + range 0 32 default 5 help Encoder 1 clock pin config ENCODER_1_DT_PIN int "encoder 1 data GPIO" - range 1 32 + range 0 32 default 6 help Encoder 1 clock data config ENCODER_1_SW_PIN int "encoder 1 switch GPIO" - range 1 32 + range 0 32 default 7 help Encoder 1 switch pin @@ -108,13 +108,13 @@ endmenu menu "I2C Configuration" config I2C_SCL int "I2C SCL GPIO" - range 1 32 + range 0 32 default 8 help I2C SCL GPIO config I2C_SDA int "I2C SDA GPIO" - range 1 32 + range 0 32 default 10 help I2C SDA GPIO @@ -124,4 +124,25 @@ menu "I2C Configuration" default 0 help I2C NUM -endmenu \ No newline at end of file +endmenu + +menu "UART Configuration" + config UART_TX + int "UART TX GPIO" + range 0 32 + default 21 + help + UART TX GPIO + config UART_RX + int "UART RX GPIO" + range 0 32 + default 20 + help + UART RX GPIO + config UART_NUM + int "UART NUM" + range 0 1 + default 0 + help + UART NUM +endmenu diff --git a/main/ambient_light.c b/main/ambient_light.c index 6e710cf..142b0e7 100644 --- a/main/ambient_light.c +++ b/main/ambient_light.c @@ -124,6 +124,7 @@ esp_err_t apds_9930_read_word(uint8_t command, uint8_t* data_l, } void ambient_light_fetch(void* arg) { + ESP_LOGI(AMBIENT_LIGHT_TAG, "ambient_light_fetch"); esp_err_t error; uint16_t als_ch0_raw; uint16_t als_ch1_raw; @@ -183,11 +184,12 @@ void ambient_light_fetch(void* arg) { } void ambient_light_auto_fetch() { - xTaskCreate(ambient_light_fetch, "ui_input_event", 2048, NULL, 10, NULL); + xTaskCreate(ambient_light_fetch, "ambient-light", 2048, NULL, 10, NULL); } void ambient_light_init() { - esp_log_level_set(AMBIENT_LIGHT_TAG, ESP_LOG_ERROR); + ESP_LOGI(AMBIENT_LIGHT_TAG, "Initializing APDS-9930"); + // esp_log_level_set(AMBIENT_LIGHT_TAG, ESP_LOG_ERROR); ESP_ERROR_CHECK(apds_9930_write(APDS_9930_CMD_REPEATED | APDS_9930_REG_ATIME, APDS_9930_ATIME_VALUE)); ESP_ERROR_CHECK(apds_9930_write(APDS_9930_CMD_REPEATED | APDS_9930_REG_PTIME, diff --git a/main/ci_03t.c b/main/ci_03t.c new file mode 100644 index 0000000..ee8f322 --- /dev/null +++ b/main/ci_03t.c @@ -0,0 +1,113 @@ +#pragma once +#include "driver/gpio.h" +#include "driver/uart.h" +#include "esp_log.h" +#include "esp_system.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "light.c" +#include "string.h" + +static const int UART_1_RX_BUF_SIZE = 1024; + +#define CI_03T_TXD_PIN (CONFIG_UART_TX) +#define CI_03T_RXD_PIN (CONFIG_UART_RX) +#define CI_03T_UART_NUM (CONFIG_UART_NUM) +#define SEND_DATA_FRAME_HEAD \ + (uint8_t[]) { 0xaa, 0x55 } +#define SEND_DATA_FRAME_TAIL \ + (uint8_t[]) { 0x55, 0xaa } + +#define CI_O3T_LOG_TAG "CI_03T" + +// emtpy buffer for sending data +uint8_t ci_03t_tx_buffer[20] = {0}; + +int ci_03t_send_data(const uint8_t *data, uint8_t data_len) { + memcpy(ci_03t_tx_buffer, SEND_DATA_FRAME_HEAD, sizeof(SEND_DATA_FRAME_HEAD)); + memcpy(ci_03t_tx_buffer + sizeof(SEND_DATA_FRAME_HEAD), data, data_len); + memcpy(ci_03t_tx_buffer + sizeof(SEND_DATA_FRAME_HEAD) + data_len, + SEND_DATA_FRAME_TAIL, sizeof(SEND_DATA_FRAME_TAIL)); + const int len = + sizeof(SEND_DATA_FRAME_HEAD) + data_len + sizeof(SEND_DATA_FRAME_TAIL); + + const int txBytes = uart_write_bytes(CI_03T_UART_NUM, ci_03t_tx_buffer, len); + ESP_LOGI(CI_O3T_LOG_TAG, "Wrote %d bytes", txBytes); + ESP_LOG_BUFFER_HEXDUMP(CI_O3T_LOG_TAG, ci_03t_tx_buffer, len, ESP_LOG_INFO); + + return txBytes; +} + +int sendData(const char *data) { + const int len = strlen(data); + const int txBytes = uart_write_bytes(CI_03T_UART_NUM, data, len); + ESP_LOGI("TEST", "Wrote %d bytes", txBytes); + return txBytes; +} + +static void tx_task(void *arg) { + static const char *TX_TASK_TAG = "TX_TASK"; + esp_log_level_set(TX_TASK_TAG, ESP_LOG_INFO); + while (1) { + vTaskDelay(100 / portTICK_PERIOD_MS); + // sendData(TX_TASK_TAG, "Hello world"); + } +} + +static void rx_task(void *arg) { + static const char *RX_TASK_TAG = "RX_TASK"; + esp_log_level_set(RX_TASK_TAG, ESP_LOG_INFO); + uint8_t *data = (uint8_t *)malloc(UART_1_RX_BUF_SIZE + 1); + uint8_t tx_buff[4] = {0}; + while (1) { + const int rxBytes = uart_read_bytes( + CI_03T_UART_NUM, data, UART_1_RX_BUF_SIZE, 100 / portTICK_PERIOD_MS); + if (rxBytes > 0) { + data[rxBytes] = 0; + ESP_LOGI(RX_TASK_TAG, "Read %d bytes: '%s'", rxBytes, data); + ESP_LOG_BUFFER_HEXDUMP(RX_TASK_TAG, data, rxBytes, ESP_LOG_INFO); + + if (data[0] == 0x11 && rxBytes >= 2) { + if (data[1] <= 6) { + light_mode = data[1]; + } + tx_buff[0] = data[0]; + tx_buff[1] = light_mode; + uart_write_bytes(CI_03T_UART_NUM, tx_buff, 2); + } else if (data[0] == 0x12 && rxBytes >= 2) { + tx_buff[0] = 0x12; + tx_buff[1] = data[1]; + led_strip_set_brightness(data[1]); + uart_write_bytes(CI_03T_UART_NUM, tx_buff, 2); + } else if (data[0] == 0x13 && rxBytes >= 2) { + tx_buff[0] = 0x12; + tx_buff[1] = display_ambient_lighting_level + (int8_t)data[1]; + led_strip_set_brightness(tx_buff[1]); + uart_write_bytes(CI_03T_UART_NUM, tx_buff, 2); + } + } + } + free(data); +} + +void ci_03t_init() { + const uart_config_t uart_config = { + .baud_rate = 115200, + .data_bits = UART_DATA_8_BITS, + .parity = UART_PARITY_ODD, + .stop_bits = UART_STOP_BITS_1, + .flow_ctrl = UART_HW_FLOWCTRL_DISABLE, + .source_clk = UART_SCLK_APB, + }; + // We won't use a buffer for sending data. + uart_driver_install(CI_03T_UART_NUM, UART_1_RX_BUF_SIZE * 2, 0, 0, NULL, 0); + uart_param_config(CI_03T_UART_NUM, &uart_config); + uart_set_pin(CI_03T_UART_NUM, CI_03T_TXD_PIN, CI_03T_RXD_PIN, + UART_PIN_NO_CHANGE, UART_PIN_NO_CHANGE); + + xTaskCreate(rx_task, "uart_rx_task", 1024 * 2, NULL, configMAX_PRIORITIES, + NULL); + // xTaskCreate(tx_task, "uart_tx_task", 1024 * 2, NULL, configMAX_PRIORITIES - + // 1, + // NULL); +} \ No newline at end of file diff --git a/main/config_key.h b/main/config_key.h new file mode 100644 index 0000000..b248e9c --- /dev/null +++ b/main/config_key.h @@ -0,0 +1,26 @@ +#pragma once + +typedef enum e_ui_input_key { + ui_input_key_display_0_brightness = 0, + ui_input_key_display_1_brightness = 1, + ui_input_key_computer_volume = 2, + ui_input_key_display_ambient_lighting_level = 3, + ui_input_key_display_ambient_lighting_mode = 4, + ui_input_key_display_0_mode = 5, + ui_input_key_display_1_mode = 6, +} e_ui_input_key_t; + +typedef struct s_ui_input { + e_ui_input_key_t key; + int16_t value; +} s_ui_input_t; + +typedef enum e_ui_input_raw_key { + ui_input_raw_key_encoder_0 = 0, + ui_input_raw_key_encoder_1 = 1, +} e_ui_input_raw_key_t; + +typedef struct s_ui_input_raw { + e_ui_input_raw_key_t key; + uint8_t value; +} s_ui_input_raw_t; \ No newline at end of file diff --git a/main/embedded_display.c b/main/embedded_display.c index eb9f698..217fa7b 100644 --- a/main/embedded_display.c +++ b/main/embedded_display.c @@ -1,8 +1,10 @@ #pragma once #include #include +#include #include "codetab.h" +#include "config_key.h" #include "driver/i2c.h" #include "esp_log.h" @@ -102,3 +104,36 @@ void init_display() { display_fill(0x00); display_set_pos(0, 0); } + +void gui_update_config_uint8(uint8_t key, uint8_t value) { + char changing_str[12] = "NC"; + switch (key) { + case ui_input_key_display_0_brightness: + sprintf(changing_str, "Dis0: % 3d", value); + break; + case ui_input_key_display_1_brightness: + sprintf(changing_str, "Dis1: % 3d", value); + break; + case ui_input_key_computer_volume: + sprintf(changing_str, "CVol: % 3d", value); + break; + case ui_input_key_display_ambient_lighting_level: + sprintf(changing_str, "ALLv: % 3d", value); + break; + case ui_input_key_display_ambient_lighting_mode: + sprintf(changing_str, "ALMd: % 3d", value); + break; + case ui_input_key_display_0_mode: + sprintf(changing_str, "Dis0M: % 2d", value); + break; + case ui_input_key_display_1_mode: + sprintf(changing_str, "Dis1M: % 2d", value); + break; + + default: + strcpy(changing_str, "NC"); + break; + } + display_fill_rect(0, 6, 128, 8, 0); + display_print8_str(8, 6, changing_str); +} \ No newline at end of file diff --git a/main/light.c b/main/light.c index 5c65a06..b9f69da 100644 --- a/main/light.c +++ b/main/light.c @@ -154,6 +154,7 @@ void light_for_init() { ESP_ERROR_CHECK(light_led_strip->refresh(light_led_strip, 100)); vTaskDelay(pdMS_TO_TICKS(10)); } + vTaskDelay(pdMS_TO_TICKS(100)); } while (light_mode == light_mode_init); } diff --git a/main/main.c b/main/main.c index 60bad3e..642175d 100644 --- a/main/main.c +++ b/main/main.c @@ -1,5 +1,5 @@ #include "ambient_light.c" -#include "asr_pro.c" +#include "ci_03t.c" #include "driver/i2c.h" #include "esp_log.h" #include "freertos/FreeRTOS.h" @@ -44,17 +44,18 @@ void init_i2c() { static const char *TAG = "DisplayAmbientLight"; void app_main(void) { - light_init_strip(); + // light_init_strip(); init_i2c(); init_display(); display_print8_str(0, 0, "Ambient Light"); + ci_03t_init(); ambient_light_init(); ambient_light_auto_fetch(); auto_fetch_temperature(); ui_input_init(); - xTaskCreate(mqtt_publish_ui_input, "ui_input_event", 2048, NULL, 10, NULL); + xTaskCreate(mqtt_publish_ui_input, "mqtt_publish_ui_input", 2048, NULL, 10, + NULL); vTaskDelay(pdMS_TO_TICKS(10)); - asr_pro_init(); light_play(light_mode_connection_wifi); if (connect_wifi()) { light_play(light_mode_idle); @@ -69,5 +70,6 @@ void app_main(void) { } while (waiting_and_get_colors()) { light_play_colors(NUMBER_OF_LEDS * 3, mqtt_colors_buffer); + vTaskDelay(pdMS_TO_TICKS(10)); } } diff --git a/main/mqtt.c b/main/mqtt.c index 62958b7..b317ddf 100644 --- a/main/mqtt.c +++ b/main/mqtt.c @@ -3,6 +3,8 @@ #include #include "cJSON.h" +#include "ci_03t.c" +#include "embedded_display.c" #include "esp_bit_defs.h" #include "esp_event.h" #include "esp_log.h" @@ -30,6 +32,7 @@ #define MQTT_DESKTOP_KEY_PREFIX "display-ambient-light/desktop/" #define MQTT_ONLINE_SUFFIX "online" #define MQTT_COLORS_SUFFIX "colors" +#define MQTT_CMD_SUFFIX "cmd" #define MQTT_ALL_SUFFIX "#" #define MQTT_KEY_BOARD_ONLINE MQTT_BOARD_KEY_PREFIX MQTT_ONLINE_SUFFIX @@ -38,9 +41,16 @@ #define MQTT_KEY_DESKTOP_COLORS MQTT_DESKTOP_KEY_PREFIX MQTT_COLORS_SUFFIX #define MQTT_KEY_DESKTOP_ALL MQTT_DESKTOP_KEY_PREFIX MQTT_ALL_SUFFIX +#define MQTT_KEY_BOARD_CMD MQTT_BOARD_KEY_PREFIX MQTT_CMD_SUFFIX +#define MQTT_KEY_DESKTOP_DISPLAY_0_BRIGHTNESS \ + MQTT_DESKTOP_KEY_PREFIX "display0/brightness" +#define MQTT_KEY_DESKTOP_DISPLAY_1_BRIGHTNESS \ + MQTT_DESKTOP_KEY_PREFIX "display1/brightness" + static const char *MQTT_TAG = "DisplayAmbientLight_MQTT"; static EventGroupHandle_t s_mqtt_event_group; +static xQueueHandle mqtt_cmd_event = NULL; static esp_mqtt_client_handle_t client = NULL; typedef struct colors { @@ -100,8 +110,24 @@ static void mqtt_event_handler(void *handler_args, esp_event_base_t base, xEventGroupSetBits(s_mqtt_event_group, MQTT_DESKTOP_SENDING_BIT | MQTT_COLORS_STAND_BY_BIT); } else { - printf("TOPIC=%.*s\r\n", event->topic_len, event->topic); - printf("DATA=%.*s\r\n", event->data_len, event->data); + if (strncmp(event->topic, MQTT_KEY_DESKTOP_DISPLAY_0_BRIGHTNESS, + event->topic_len) == 0) { + s_ui_input_t mqtt_event = { + .key = ui_input_key_display_0_brightness, + .value = (uint16_t)(event->data[0] << 8 | event->data[1]), + }; + xQueueSend(mqtt_cmd_event, &mqtt_event, NULL); + } else if (strncmp(event->topic, MQTT_KEY_DESKTOP_DISPLAY_1_BRIGHTNESS, + event->topic_len) == 0) { + s_ui_input_t mqtt_event = { + .key = ui_input_key_display_1_brightness, + .value = (uint16_t)(event->data[0] << 8 | event->data[1]), + }; + xQueueSend(mqtt_cmd_event, &mqtt_event, NULL); + } else { + printf("TOPIC=%.*s\r\n", event->topic_len, event->topic); + printf("DATA=%.*s\r\n", event->data_len, event->data); + } } break; case MQTT_EVENT_ERROR: @@ -124,9 +150,42 @@ static void mqtt_event_handler(void *handler_args, esp_event_base_t base, } } +static void mqtt_cmd_event_handler(void *arg) { + s_ui_input_t event; + + for (;;) { + if (xQueueReceive(mqtt_cmd_event, &event, portMAX_DELAY)) { + ESP_LOGI(MQTT_TAG, "mqtt_cmd_event_handler"); + + gui_update_config_uint8(ui_input_key_display_0_brightness, + (uint8_t)(event.value & 0xFF)); + switch (event.key) { + case ui_input_key_display_0_brightness: { + ESP_LOGI(MQTT_TAG, "ui_input_key_display_0_brightness %x", + event.value); + uint8_t data[] = {0x02, (uint8_t)(event.value & 0xFF)}; + ci_03t_send_data(data, sizeof(data)); + break; + } + case ui_input_key_display_1_brightness: { + ESP_LOGI(MQTT_TAG, "ui_input_key_display_0_brightness %x", + event.value); + uint8_t data[] = {0x03, (uint8_t)(event.value & 0xFF)}; + ci_03t_send_data(data, sizeof(data)); + break; + } + default: + break; + } + } + } +} + static void mqtt_app_start() { mqtt_colors_buffer = (uint8_t *)malloc(sizeof(uint8_t) * NUMBER_OF_LEDS * 3); s_mqtt_event_group = xEventGroupCreate(); + mqtt_cmd_event = xQueueCreate(10, sizeof(s_ui_input_t)); + xTaskCreate(mqtt_cmd_event_handler, "mqtt_cmd_event", 2048, NULL, 10, NULL); const esp_mqtt_client_config_t mqtt_cfg = { .uri = MQTT_BROKER_URL, diff --git a/main/temperature.c b/main/temperature.c index 22b764c..50b2f59 100644 --- a/main/temperature.c +++ b/main/temperature.c @@ -22,12 +22,14 @@ #define TEMPERATURE_TAG "temperature" void fetch_temperature(void* arg) { + ESP_LOGI(TEMPERATURE_TAG, "fetch_temperature"); esp_err_t error; float temperature = DEFAULT_TEMPERATURE; char temperature_str[10]; uint8_t temperature_buffer[] = {0, 0}; display_fill_rect(0, 0, 128, 2, 0x00); for (;;) { + ESP_LOGI(TEMPERATURE_TAG, "fetching temperature"); i2c_cmd_handle_t cmd = i2c_cmd_link_create(); i2c_master_start(cmd); i2c_master_write_byte(cmd, GX21M15_ADDRESS | I2C_MASTER_WRITE, @@ -70,5 +72,6 @@ void fetch_temperature(void* arg) { } void auto_fetch_temperature() { - xTaskCreate(fetch_temperature, "ui_input_event", 2048, NULL, 10, NULL); + ESP_LOGI(TEMPERATURE_TAG, "auto_fetch_temperature"); + xTaskCreate(fetch_temperature, "temperature", 2048, NULL, 10, NULL); } diff --git a/main/ui_input.c b/main/ui_input.c index 49e6caa..01b00e4 100644 --- a/main/ui_input.c +++ b/main/ui_input.c @@ -4,6 +4,7 @@ #include #include +#include "config_key.h" #include "driver/gpio.h" #include "embedded_display.c" #include "freertos/FreeRTOS.h" @@ -35,41 +36,11 @@ static const char *UI_INPUT_TAG = "UiInput"; -typedef enum e_ui_input_key { - ui_input_key_display_0_brightness = 0, - ui_input_key_display_1_brightness = 1, - ui_input_key_computer_volume = 2, - ui_input_key_display_ambient_lighting_level = 3, - ui_input_key_display_ambient_lighting_mode = 4, - ui_input_key_display_0_mode = 5, - ui_input_key_display_1_mode = 6, -} e_ui_input_key_t; - -typedef struct s_ui_input { - e_ui_input_key_t key; - int16_t value; -} s_ui_input_t; - -typedef enum e_ui_input_raw_key { - ui_input_raw_key_encoder_0 = 0, - ui_input_raw_key_encoder_1 = 1, -} e_ui_input_raw_key_t; - -typedef struct s_ui_input_raw { - e_ui_input_raw_key_t key; - uint8_t value; -} s_ui_input_raw_t; - static xQueueHandle ui_input_event = NULL; static xQueueHandle ui_input_raw_event = NULL; static int8_t rising_edge_rotation_direction = NOT_ROTATING; static int8_t falling_edge_rotation_direction = NOT_ROTATING; -static uint8_t display_0_brightness = 20; -static uint8_t display_1_brightness = 20; -static uint8_t computer_volume = 30; - -static s_ui_input_t current_ui_input = {}; uint8_t input_key; @@ -232,18 +203,6 @@ static void ui_input_raw_handler(void *arg) { void ui_input_init(void) { // zero-initialize the config structure. gpio_config_t io_conf = {}; - // disable interrupt - io_conf.intr_type = GPIO_INTR_DISABLE; - // set as output mode - io_conf.mode = GPIO_MODE_OUTPUT; - // bit mask of the pins that you want to set,e.g.GPIO18/19 - io_conf.pin_bit_mask = GPIO_OUTPUT_PIN_SEL; - // disable pull-down mode - io_conf.pull_down_en = 0; - // disable pull-up mode - io_conf.pull_up_en = 0; - // configure GPIO with the given settings - gpio_config(&io_conf); io_conf.mode = GPIO_MODE_INPUT; io_conf.pull_up_en = 1;