esp-who/components/modules/lcd/who_lcd.c

143 lines
3.8 KiB
C
Raw Permalink Normal View History

2021-09-08 20:04:59 +08:00
#include "who_lcd.h"
#include "esp_camera.h"
2021-07-31 11:23:18 +08:00
#include <string.h>
2021-11-26 20:03:10 +08:00
#include "logo_en_240x240_lcd.h"
2021-07-31 11:23:18 +08:00
2021-09-08 20:04:59 +08:00
static const char *TAG = "who_lcd";
2021-07-31 11:23:18 +08:00
static scr_driver_t g_lcd;
static scr_info_t g_lcd_info;
2021-09-08 20:04:59 +08:00
static QueueHandle_t xQueueFrameI = NULL;
static QueueHandle_t xQueueFrameO = NULL;
static bool gReturnFB = true;
static void task_process_handler(void *arg)
{
camera_fb_t *frame = NULL;
while (true)
{
if (xQueueReceive(xQueueFrameI, &frame, portMAX_DELAY))
{
g_lcd.draw_bitmap(0, 0, frame->width, frame->height, (uint16_t *)frame->buf);
if (xQueueFrameO)
{
xQueueSend(xQueueFrameO, &frame, portMAX_DELAY);
}
else if (gReturnFB)
{
esp_camera_fb_return(frame);
}
else
{
free(frame);
}
}
}
}
esp_err_t register_lcd(const QueueHandle_t frame_i, const QueueHandle_t frame_o, const bool return_fb)
2021-07-31 11:23:18 +08:00
{
spi_config_t bus_conf = {
2021-09-08 20:04:59 +08:00
.miso_io_num = BOARD_LCD_MISO,
.mosi_io_num = BOARD_LCD_MOSI,
.sclk_io_num = BOARD_LCD_SCK,
2021-07-31 11:23:18 +08:00
.max_transfer_sz = 2 * 240 * 240 + 10,
};
spi_bus_handle_t spi_bus = spi_bus_create(SPI2_HOST, &bus_conf);
scr_interface_spi_config_t spi_lcd_cfg = {
.spi_bus = spi_bus,
2021-09-08 20:04:59 +08:00
.pin_num_cs = BOARD_LCD_CS,
.pin_num_dc = BOARD_LCD_DC,
2021-07-31 11:23:18 +08:00
.clk_freq = 40 * 1000000,
.swap_data = 0,
};
scr_interface_driver_t *iface_drv;
scr_interface_create(SCREEN_IFACE_SPI, &spi_lcd_cfg, &iface_drv);
esp_err_t ret = scr_find_driver(SCREEN_CONTROLLER_ST7789, &g_lcd);
if (ESP_OK != ret)
{
return ret;
ESP_LOGE(TAG, "screen find failed");
}
scr_controller_config_t lcd_cfg = {
.interface_drv = iface_drv,
2021-09-08 20:04:59 +08:00
.pin_num_rst = BOARD_LCD_RST,
.pin_num_bckl = BOARD_LCD_BL,
2021-07-31 11:23:18 +08:00
.rst_active_level = 0,
2021-09-08 20:04:59 +08:00
.bckl_active_level = 0,
2021-07-31 11:23:18 +08:00
.offset_hor = 0,
.offset_ver = 0,
.width = 240,
.height = 240,
.rotate = 0,
};
ret = g_lcd.init(&lcd_cfg);
if (ESP_OK != ret)
{
return ESP_FAIL;
ESP_LOGE(TAG, "screen initialize failed");
}
g_lcd.get_info(&g_lcd_info);
ESP_LOGI(TAG, "Screen name:%s | width:%d | height:%d", g_lcd_info.name, g_lcd_info.width, g_lcd_info.height);
2021-09-08 20:04:59 +08:00
app_lcd_set_color(0x000000);
2021-11-26 20:03:10 +08:00
vTaskDelay(pdMS_TO_TICKS(200));
2021-09-08 20:04:59 +08:00
app_lcd_draw_wallpaper();
2021-11-26 20:03:10 +08:00
vTaskDelay(pdMS_TO_TICKS(200));
2021-09-08 20:04:59 +08:00
xQueueFrameI = frame_i;
xQueueFrameO = frame_o;
gReturnFB = return_fb;
2021-11-26 20:03:10 +08:00
xTaskCreatePinnedToCore(task_process_handler, TAG, 4 * 1024, NULL, 5, NULL, 0);
2021-09-08 20:04:59 +08:00
2021-07-31 11:23:18 +08:00
return ESP_OK;
}
void app_lcd_draw_wallpaper()
{
scr_info_t lcd_info;
g_lcd.get_info(&lcd_info);
2021-11-26 20:03:10 +08:00
uint16_t *pixels = (uint16_t *)heap_caps_malloc((logo_en_240x240_lcd_width * logo_en_240x240_lcd_height) * sizeof(uint16_t), MALLOC_CAP_8BIT | MALLOC_CAP_SPIRAM);
2021-07-31 11:23:18 +08:00
if (NULL == pixels)
{
ESP_LOGE(TAG, "Memory for bitmap is not enough");
return;
}
2021-11-26 20:03:10 +08:00
memcpy(pixels, logo_en_240x240_lcd, (logo_en_240x240_lcd_width * logo_en_240x240_lcd_height) * sizeof(uint16_t));
g_lcd.draw_bitmap(0, 0, logo_en_240x240_lcd_width, logo_en_240x240_lcd_height, (uint16_t *)pixels);
2021-07-31 11:23:18 +08:00
heap_caps_free(pixels);
}
void app_lcd_set_color(int color)
{
scr_info_t lcd_info;
g_lcd.get_info(&lcd_info);
uint16_t *buffer = (uint16_t *)malloc(lcd_info.width * sizeof(uint16_t));
if (NULL == buffer)
{
2021-11-26 20:03:10 +08:00
ESP_LOGE(TAG, "Memory for bitmap is not enough");
2021-07-31 11:23:18 +08:00
}
else
{
for (size_t i = 0; i < lcd_info.width; i++)
{
buffer[i] = color;
}
for (int y = 0; y < lcd_info.height; y++)
{
g_lcd.draw_bitmap(0, y, lcd_info.width, 1, buffer);
}
free(buffer);
}
}