#include "led_strip.h" rmt_channel_handle_t led_chan = NULL; rmt_encoder_handle_t led_encoder = NULL; rmt_transmit_config_t tx_config = { .loop_count = 0, // no transfer loop }; // 颜色结构体 static rgb_color_t expression[EXAMPLE_LED_NUMBERS]; static rgb_color_t expression_lat[EXAMPLE_LED_NUMBERS] = {0}; // 延时计数 static uint16_t rgb_toggle_cnt[EXAMPLE_LED_NUMBERS] = {10,10}; static uint16_t rgb_toggle_cnt_lat[EXAMPLE_LED_NUMBERS] = {2000,2000}; static uint8_t led_strip_pixels[EXAMPLE_LED_NUMBERS * 3]; uint16_t toggle_cycle = 1000; // 翻转标志位 bool toggle_flag[EXAMPLE_LED_NUMBERS] = {true,true}; bool toggle_flag_lat[EXAMPLE_LED_NUMBERS] = {true,true}; rgb_color_t rgb_color_none = {0,0,0,0,0,1,0,RGB_COLOR_NONE}; rgb_color_t rgb_color_rad = {0,255,0,0,0,1,0,RGB_COLOR_RAD}; rgb_color_t rgb_color_orange = {0,255,80,0,0,1,0,RGB_COLOR_ORANGE}; rgb_color_t rgb_color_green = {0,0,255,0,0,1,0,RGB_COLOR_GREEN}; rgb_color_t rgb_color_blue = {0,0,0,255,0,1,0,RGB_COLOR_BLUE}; rgb_color_t rgb_color_cyan = {0,0,255,255,0,1,0,RGB_COLOR_CYAN}; rgb_color_t rgb_color_purple = {0,255,0,255,0,1,0,RGB_COLOR_PURPLE}; rgb_color_t rgb_color_white = {0,255,255,255,0,1,0,RGB_COLOR_WHITE}; rgb_color_t rgb_color_green_white = {0,0,255,0,0,2,20,RGB_COLOR_GREEN_WHITE}; rgb_color_t rgb_color_green_purple = {0,0,255,0,0,2,20,RGB_COLOR_GREEN_PURPLE}; void led_strip_init(void) { // ESP_LOGI(TAG, "Create RMT TX channel"); rmt_tx_channel_config_t tx_chan_config = { .clk_src = RMT_CLK_SRC_DEFAULT, // select source clock .gpio_num = RMT_LED_STRIP_GPIO_NUM, .mem_block_symbols = 64, // increase the block size can make the LED less flickering .resolution_hz = RMT_LED_STRIP_RESOLUTION_HZ, .trans_queue_depth = 4, // set the number of transactions that can be pending in the background }; ESP_ERROR_CHECK(rmt_new_tx_channel(&tx_chan_config, &led_chan)); // ESP_LOGI(TAG, "Install led strip encoder"); led_strip_encoder_config_t encoder_config = { .resolution = RMT_LED_STRIP_RESOLUTION_HZ, }; ESP_ERROR_CHECK(rmt_new_led_strip_encoder(&encoder_config, &led_encoder)); // ESP_LOGI(TAG, "Enable RMT TX channel"); ESP_ERROR_CHECK(rmt_enable(led_chan)); // ESP_LOGI(TAG, "Start LED rainbow chase"); rgb_color_change(0,RGB_COLOR_ORANGE); rgb_color_change(1,RGB_COLOR_ORANGE); } void led_strip_set_pixel(uint8_t pin, uint8_t index, uint8_t green, uint8_t blue, uint8_t red) { led_strip_pixels[0 + index * 3] = green; led_strip_pixels[1 + index * 3] = red; led_strip_pixels[2 + index * 3] = blue; ESP_ERROR_CHECK(rmt_transmit(led_chan, led_encoder, led_strip_pixels, sizeof(led_strip_pixels), &tx_config)); ESP_ERROR_CHECK(rmt_tx_wait_all_done(led_chan, portMAX_DELAY)); } void work_rgb_led_start(void) { led_strip_init(); /* 创建 shell 的接收任务 _work_sh() */ static os_work_t work_handler_rgb_led; os_work_create(&work_handler_rgb_led, "work-rgb-led", _work_rgb_led, NULL, OS_PRIORITY_NORMAL); os_work_submit(default_os_work_q_hdl, &work_handler_rgb_led, toggle_cycle * 0.5); } void _work_rgb_led(void *arg) { static uint16_t rgb_toggle_cnt_update[EXAMPLE_LED_NUMBERS] = {10,10}; if(!rgb_toggle_cnt_update[0]--) { rgb_toggle_cnt_update[0] = rgb_toggle_cnt[0]; rgb_toggle(0,&expression[0]); } if(!rgb_toggle_cnt_update[1]--) { rgb_toggle_cnt_update[1] = rgb_toggle_cnt[1]; rgb_toggle(1,&expression[1]); } os_work_later(WORD_TIME_MS); } void rgb_update_cyle(uint8_t index, uint16_t cyle) { toggle_flag[index] = (cyle == 888 ? false : true); rgb_toggle_cnt[index] = cyle / WORD_TIME_MS - 1; } void rgb_color_change(uint8_t index, uint8_t color) { static uint8_t rgb_color_lat[EXAMPLE_LED_NUMBERS] = {0}; if(rgb_color_lat[index] != color) { switch(color) { case RGB_COLOR_NONE: memcpy(&expression[index], &rgb_color_none, sizeof(rgb_color_none)); break; case RGB_COLOR_RAD: memcpy(&expression[index], &rgb_color_rad, sizeof(rgb_color_rad)); break; case RGB_COLOR_ORANGE: memcpy(&expression[index], &rgb_color_orange, sizeof(rgb_color_orange)); break; case RGB_COLOR_GREEN: memcpy(&expression[index], &rgb_color_green, sizeof(rgb_color_green)); break; case RGB_COLOR_WHITE: memcpy(&expression[index], &rgb_color_white, sizeof(rgb_color_white)); break; case RGB_COLOR_PURPLE: memcpy(&expression[index], &rgb_color_purple, sizeof(rgb_color_purple)); break; case RGB_COLOR_CYAN: memcpy(&expression[index], &rgb_color_cyan, sizeof(rgb_color_cyan)); break; case RGB_COLOR_BLUE: memcpy(&expression[index], &rgb_color_blue, sizeof(rgb_color_blue)); break; case RGB_COLOR_GREEN_WHITE: memcpy(&expression[index], &rgb_color_green_white, sizeof(rgb_color_green_white)); break; case RGB_COLOR_GREEN_PURPLE: memcpy(&expression[index], &rgb_color_green_purple, sizeof(rgb_color_green_purple)); break; default: break; } expression[index].index = index; rgb_color_lat[index] = color; } } void rgb_toggle(uint8_t index, rgb_color_t* rgb_color) { if(rgb_color->color_cnt > 1) { breathing_color_change(index,rgb_color); led_strip_set_pixel(0,rgb_color->index,rgb_color->green,rgb_color->blue,rgb_color->red); return; } if(rgb_color->toggle_flag == 0) led_strip_set_pixel(0,rgb_color->index,rgb_color->green,rgb_color->blue,rgb_color->red); else led_strip_set_pixel(0,rgb_color->index,0,0,0); if(toggle_flag[index] == true) rgb_color->toggle_flag = !rgb_color->toggle_flag; } uint8_t breathing_dispose(uint8_t index, rgb_color_t* rgb_color,int16_t* vel, uint8_t color_min, uint8_t color_max) { static int dir[EXAMPLE_LED_NUMBERS] = {1,1}, color_dir[EXAMPLE_LED_NUMBERS] = {1,1}, color_cnt[EXAMPLE_LED_NUMBERS] = {0,0}; *vel += dir[index] * rgb_color->colortoggle_speed; if(*vel > color_max){*vel = color_max; dir[index] = -1;} else if(*vel < color_min){*vel = color_min; dir[index] = 1; color_cnt[index] += color_dir[index];} if(color_cnt[index] >= rgb_color->color_cnt -1 ) color_dir[index] = -1; else if(color_cnt[index] <= 0) color_dir[index] = 1; return color_cnt[index]; } void breathing_color_change(uint8_t index, rgb_color_t* rgb_color) { static int16_t COLOR_SUM[EXAMPLE_LED_NUMBERS]; uint8_t color_cnt = breathing_dispose(index, rgb_color, &COLOR_SUM[index], 0, 255); switch (rgb_color->color_type) { case RGB_COLOR_GREEN_WHITE: { switch(color_cnt) { case 0: { rgb_color->red = 0; rgb_color->green = (uint8_t)COLOR_SUM[index]; rgb_color->blue = 0; break; } case 1: { rgb_color->red = (uint8_t)COLOR_SUM[index]; rgb_color->green = (uint8_t)COLOR_SUM[index]; rgb_color->blue = (uint8_t)COLOR_SUM[index]; break; } } break; } case RGB_COLOR_GREEN_PURPLE: { switch(color_cnt) { case 0: { rgb_color->red = 0; rgb_color->green = (uint8_t)COLOR_SUM[index]; rgb_color->blue = 0; break; } case 1: { rgb_color->red = (uint8_t)COLOR_SUM[index]; rgb_color->green = 0; rgb_color->blue = (uint8_t)COLOR_SUM[index]; break; } } break; } default: break; } } void rgb_Indicator_light_on(uint8_t index, uint8_t color, uint16_t cyle) { if(expression_lat[index].color_type == 0 && expression_lat[index].color_type != color) { memcpy(&expression_lat[index], &expression[index], sizeof(rgb_color_t)); rgb_color_change(index, color); } // 设置较大的时间计数,防止数值被轻易到达 if(rgb_toggle_cnt_lat[index] == 2000 ) { rgb_toggle_cnt_lat[index] = rgb_toggle_cnt[index]; printf("rgb_toggle_cnt[index]:%d\n",rgb_toggle_cnt[index]); rgb_update_cyle(index, cyle); } if(toggle_flag[index] == false) { toggle_flag_lat[index] = !toggle_flag_lat[index]; toggle_flag[index] = !toggle_flag[index]; } } void rgb_Indicator_light_off(uint8_t index) { rgb_color_change(index, expression_lat[index].color_type); rgb_update_cyle(index,(rgb_toggle_cnt_lat[index] + 1) * WORD_TIME_MS ); toggle_flag[index] = toggle_flag_lat[index]; memset(&expression_lat[index], 0, sizeof(rgb_color_t)); rgb_toggle_cnt_lat[index] = 2000; }