Skip to content

Commit

Permalink
lvgl: Upgrade to lvgl v9 and adjust example app
Browse files Browse the repository at this point in the history
LVGL 9 has a pretty significantly different API.
  • Loading branch information
alevy committed Oct 18, 2024
1 parent ff1517b commit 406d2fd
Show file tree
Hide file tree
Showing 5 changed files with 950 additions and 373 deletions.
66 changes: 33 additions & 33 deletions examples/lvgl/lvgl_driver.c
Original file line number Diff line number Diff line change
@@ -1,35 +1,34 @@
#include <libtock-sync/display/screen.h>
#include <libtock/sensors/touch.h>
#include <libtock/tock.h>
#include <libtock/services/alarm.h>
#include <lvgl/lvgl.h>

#include "lvgl_driver.h"

static lv_disp_draw_buf_t disp_buf;
static lv_disp_drv_t disp_drv;
static lv_disp_t* display_device;
#define PIXEL_SIZE 2 // 16 bit for RGB565

static lv_indev_drv_t indev_drv;
static lv_indev_t* touch_input_device;
static lv_display_t* display_device;

static lv_indev_t* indev;

static int touch_status = LIBTOCK_TOUCH_STATUS_UNSTARTED;
static uint16_t touch_x = 0, touch_y = 0;

static int buffer_size = 0;
static uint8_t* buffer;

/* screen driver */
static void screen_lvgl_driver(lv_disp_drv_t* disp, const lv_area_t* area,
__attribute__ ((unused)) lv_color_t* color_p) {
static void screen_lvgl_driver(lv_display_t* disp, const lv_area_t* area,
uint8_t* buffer) {
void* ud = lv_display_get_user_data(disp);
uint32_t buffer_size = (uint32_t)ud;
int32_t x, y;
x = area->x1;
y = area->y1;
int w = area->x2 - area->x1 + 1;
int h = area->y2 - area->y1 + 1;
libtocksync_screen_set_frame(x, y, w, h);
libtocksync_screen_write(buffer, buffer_size, (w * h) * sizeof(lv_color_t));
libtocksync_screen_write(buffer, buffer_size, (w * h) * PIXEL_SIZE);

lv_disp_flush_ready(disp); /* Indicate you are ready with the flushing*/
lv_display_flush_ready(disp); /* Indicate you are ready with the flushing*/
}

static void touch_event(int status, uint16_t x, uint16_t y) {
Expand All @@ -38,7 +37,7 @@ static void touch_event(int status, uint16_t x, uint16_t y) {
touch_y = y;
}

static void my_input_read(__attribute__((unused)) lv_indev_drv_t* drv, lv_indev_data_t* data) {
static void indev_cb(lv_indev_t*, lv_indev_data_t* data) {
if (touch_status == LIBTOCK_TOUCH_STATUS_PRESSED || touch_status == LIBTOCK_TOUCH_STATUS_MOVED) {
data->point.x = touch_x;
data->point.y = touch_y;
Expand All @@ -48,43 +47,44 @@ static void my_input_read(__attribute__((unused)) lv_indev_drv_t* drv, lv_indev_
}
}

static uint32_t tick_cb(void) {
uint32_t ticks;
libtock_alarm_command_read(&ticks);

uint32_t ms = libtock_alarm_ticks_to_ms(ticks);
return ms;
}

int lvgl_driver_init(int buffer_lines) {
uint32_t width, height;
int error = libtock_screen_get_resolution(&width, &height);
if (error != RETURNCODE_SUCCESS) return error;

buffer_size = width * buffer_lines * sizeof(lv_color_t);
uint32_t buffer_size = width * buffer_lines * PIXEL_SIZE;
uint8_t* buffer = NULL;
error = libtock_screen_buffer_init(buffer_size, &buffer);
if (error != RETURNCODE_SUCCESS) return error;

/* share the frame buffer with littlevgl */
lv_color_t* buf = (lv_color_t*) buffer;

/* initialize littlevgl */
lv_init();
lv_disp_drv_init(&disp_drv);
disp_drv.flush_cb = screen_lvgl_driver;
disp_drv.hor_res = width;
disp_drv.ver_res = height;
lv_disp_draw_buf_init(&disp_buf, buf, NULL, width * buffer_lines);
disp_drv.draw_buf = &disp_buf;
display_device = lv_disp_drv_register(&disp_drv);

display_device = lv_display_create(width, height);
lv_display_set_color_format(display_device, LV_COLOR_FORMAT_RGB565);
lv_display_set_flush_cb(display_device, screen_lvgl_driver);
lv_display_set_antialiasing(display_device, false);

lv_display_set_buffers(display_device, buffer, NULL, buffer_size, LV_DISPLAY_RENDER_MODE_PARTIAL);
lv_display_set_user_data(display_device, (void*)buffer_size);

lv_tick_set_cb(tick_cb);

int touches;
if (libtock_touch_get_number_of_touches(&touches) == RETURNCODE_SUCCESS && touches >= 1) {
libtock_touch_enable_single_touch(touch_event);
lv_indev_drv_init(&indev_drv);
indev_drv.type = LV_INDEV_TYPE_POINTER;
indev_drv.read_cb = my_input_read;
touch_input_device = lv_indev_drv_register(&indev_drv);
indev = lv_indev_create();
lv_indev_set_type(indev, LV_INDEV_TYPE_POINTER);
lv_indev_set_read_cb(indev, indev_cb);
}

return RETURNCODE_SUCCESS;
}

void lvgl_driver_event(int millis) {
lv_tick_inc(millis);
lv_task_handler();
}
41 changes: 22 additions & 19 deletions examples/lvgl/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -7,37 +7,42 @@

#include "lvgl_driver.h"

static uint32_t seconds = 0;

static void tick_cb(lv_timer_t* timer) {
seconds++;
lv_obj_t* label1 = lv_timer_get_user_data(timer);
lv_label_set_text_fmt(label1, "%lu", seconds);
}

static void event_handler(lv_event_t* e) {
lv_event_code_t code = lv_event_get_code(e);
unsigned int* seconds = (unsigned int*)lv_event_get_user_data(e);
uint32_t* secs = (uint32_t*)lv_event_get_user_data(e);

if (code == LV_EVENT_CLICKED) {
LV_LOG_USER("Clicked");
*seconds = 0;
*secs = 0;
} else if (code == LV_EVENT_VALUE_CHANGED) {
LV_LOG_USER("Toggled");
}
}

int main(void) {
unsigned int seconds = 0;

libtocksync_screen_set_brightness(100);
int status = lvgl_driver_init(5);
if (status == RETURNCODE_SUCCESS) {
/* LittlevGL's Hello World tutorial example */

lv_obj_t* scr = lv_disp_get_scr_act(NULL); /*Get the current screen*/
lv_obj_t* scr = lv_screen_active(); /*Get the current screen*/

lv_obj_t * obj1 = lv_obj_create(lv_screen_active());
lv_obj_set_width(obj1, lv_pct(100));
lv_obj_set_height(obj1, lv_pct(100));

/*Create a Label on the currently active screen*/
lv_obj_t* label1 = lv_label_create(scr);

/*Modify the Label's text*/
lv_label_set_text(label1, "Hello world!");
lv_label_set_text(label1, "0");

/* Align the Label to the center
* NULL means align on parent (which is the screen now)
* 0, 0 at the end means an x, y offset after alignment*/
lv_obj_align(label1, LV_ALIGN_CENTER, 0, 0);

lv_obj_t* btn1 = lv_btn_create(scr);
Expand All @@ -48,17 +53,15 @@ int main(void) {
lv_label_set_text(label, "Reset");
lv_obj_center(label);

/* main loop */
lv_timer_create(tick_cb, 1000, (void*)label1);

while (1) {
seconds++;
if (seconds % 200 == 0) {
char buffer[100];
snprintf(buffer, 99, "Seconds: %d", seconds / 200);
lv_label_set_text(label1, buffer);
while(1) {
uint32_t time_till_next = lv_timer_handler();
libtocksync_alarm_delay_ms(time_till_next);
}
libtocksync_alarm_delay_ms(5);
lvgl_driver_event(5);
}

} else {
printf("lvgl init error: %s\n", tock_strrcode(status));
}
Expand Down
35 changes: 4 additions & 31 deletions lvgl/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -2,39 +2,12 @@ TOCK_USERLAND_BASE_DIR ?= ..
LIBNAME := lvgl
$(LIBNAME)_DIR := $(TOCK_USERLAND_BASE_DIR)/$(LIBNAME)

$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/core/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/draw/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/layouts/flex/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/layouts/grid/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/themes/basic/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/themes/default/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/themes/mono/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/mono/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/animimg/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/calendar/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/chart/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/colorwheel/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/imgbtn/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/keyboard/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/led/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/list/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/meter/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/msgbox/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/span/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/spinbox/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/spinner/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/tabview/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/tileview/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/extra/widgets/win/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/font/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/gpu/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/hal/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/misc/*.c)
$(LIBNAME)_SRCS += $(wildcard $($(LIBNAME)_DIR)/lvgl/src/widgets/*.c)
$(LIBNAME)_SRCS += $(shell find $($(LIBNAME)_DIR)/lvgl/src -type f -name '*.S')
$(LIBNAME)_SRCS += $(shell find $($(LIBNAME)_DIR)/lvgl/src -type f -name '*.c')
$(LIBNAME)_SRCS += $(shell find $($(LIBNAME)_DIR)/lvgl/src -type f -name '*.cpp')

# Avoid failing in CI due to warnings in the library.
override CPPFLAGS_$(LIBNAME) += -Wno-error
override CPPFLAGS_$(LIBNAME) += -Wno-error -I$(LIBNAME)_DIR/lvgl

include $(TOCK_USERLAND_BASE_DIR)/TockLibrary.mk

Loading

0 comments on commit 406d2fd

Please sign in to comment.