Description
I’m trying to get LVGL v9.2.1 working on a custom board running NuttX v12.8 with an 1.54" e-ink display (200x200px) with SSD1680 controller.
I have set the following:
LV_COLOR_DEPTH=1
LV_DRAW_SW_SUPPORT_I1=y
LV_NUTTX_LCD_SINGLE_BUFFER=y
LV_NUTTX_LCD_BUFFER_COUNT=1
LV_USE_NUTTX_LCD=y
In NuttX I have /dev/lcd0
registered which is using lcd_dev.c
driver. Also the SSD1680 is properly configured. I am certain of this because if I manually open /dev/lcd0
and write directly a buffer of 5000 bytes (200 x 200 / 8 = 5000) everything works correctly.
You can see the attached photo:
The code generating this is the following, where a bit of 1 means white and a bit of 0 means black.
The (0, 0) is in the pictures at bottom left. Given this, I believe my setup respects the requirements from Color Format I1 - Monochrome.
int fd = open("/dev/lcd0", 0);
uint8_t *data = malloc(5000);
uint8_t vals[] = {0x0f, 0xf0};
for (int i = 0; i < sizeof(vals); i++)
{
memset(data, vals[i], 5000);
struct lcddev_area_s area = {0};
area.row_start = 0 ;
area.row_end = 50;
area.col_start = 0;
area.col_end = 100;
area.stride = 25;
area.data = data;
ioctl(fd, LCDDEVIO_PUTAREA, (unsigned long) &area);
sleep(2);
}
close(fd);
The LVGL + NuttX LCD Glue Layer
I have doubled check (and made a few fixes) in LVGL NuttX LCD port, more specifically in drivers/nuttx/lv_nuttx_lcd.c
.
My flush callback has +8 to skip the palette:
static void flush_cb(lv_display_t * disp, const lv_area_t * area_p,
uint8_t * color_p)
{
lv_nuttx_lcd_t * lcd = disp->driver_data;
LV_LOG_TRACE("FLUSH CB");
lcd->area.row_start = area_p->y1;
lcd->area.row_end = area_p->y2;
lcd->area.col_start = area_p->x1;
lcd->area.col_end = area_p->x2;
lcd->area.data = (uint8_t *)color_p + 8;
ioctl(lcd->fd, LCDDEVIO_PUTAREA, (unsigned long) & (lcd->area));
lv_display_flush_ready(disp);
}
Also, the buffer size is correct in lcd_init()
function from the same file:
uint32_t buf_size = hor_res * ver_res * px_size / 8 + 8;
What MCU/Processor/Board and compiler are you using?
ESP32 + custom board.
What do you want to achieve?
I want to display a label with text.
What have you tried so far?
I have tried to simply display a label on the display but the output is garbage (very similar to the one below - also looks like a line).
I have also tried to not display anything, just do the LVGL init, with no objects, but the output still doesn’t look right. I was expecting to have nothing rendered in the frame buffer, but there appears to be something:
I have dumped the frame buffer received in the SSD1680 driver, and this is the only row that is not filled with 0x00
, row 0x19 → row 25. It corresponds to the white dotted line on the display ( (0,0) bottom-left).
ssd1680_update_all_and_redraw: 19: 0c 00 00 00 f4 bf 14 40 90 e1 fb 3f 32 00 00 00 14 00 00 00 84 e5 fb 3f 6c
Any help is really welcomed.
Shouldn’t the frame buffer be empty if no objects are added?
App code
int main(int argc, FAR char *argv[])
{
lv_nuttx_dsc_t info;
lv_nuttx_result_t result;
int ret;
lv_init();
lv_nuttx_dsc_init(&info);
info.input_path = NULL;
#ifdef CONFIG_LV_USE_NUTTX_LCD
info.fb_path = "/dev/lcd0";
#endif
lv_nuttx_init(&info, &result);
if (result.disp == NULL)
{
LV_LOG_ERROR("lv_demos initialization failure!");
return 1;
}
while (1)
{
uint32_t idle;
idle = lv_timer_handler();
/* Minimum sleep of 1ms */
idle = idle ? idle : 1;
usleep(idle * 1000);
}
return EXIT_SUCCESS;
}