-
Notifications
You must be signed in to change notification settings - Fork 16
Description
I'd like to use a LVGL designer like EEZ Studio to generate the more complex pages, widgets, etc. and use the yaml syntax for the simpler stuff like simple pages/widgets, event handling, setup, etc.
Do you have any suggestions on how one might inject code within the generated pages and widgets blocks? Lambdas don't appear to be supported right now.
I've gotten pretty far by adding the generated code from EEZ Studio to the esphome includes: yaml. EEZ generates simple methods for each of the screens and child components (e.g. create_screen_main()) that registers a handle to a global objects struct.
Here is an example of an EEZ Studio generated create function:
void create_screen_main() {
lv_obj_t *obj = lv_obj_create(0);
objects.main = obj;
lv_obj_set_pos(obj, 0, 0);
lv_obj_set_size(obj, 240, 135);
lv_obj_clear_flag(obj, LV_OBJ_FLAG_SCROLLABLE);
{
lv_obj_t *parent_obj = obj;
{
// label_1
lv_obj_t *obj = lv_label_create(parent_obj);
objects.label_1 = obj;
lv_obj_set_pos(obj, 0, 0);
lv_obj_set_size(obj, LV_SIZE_CONTENT, LV_SIZE_CONTENT);
lv_label_set_long_mode(obj, LV_LABEL_LONG_CLIP);
lv_label_set_text(obj, "Hello, world!");
lv_obj_set_style_align(obj, LV_ALIGN_CENTER, LV_PART_MAIN | LV_STATE_DEFAULT);
}
}
}Using an empty page/widgets block:
lvgl:
pages:
- id: test_page
widgets:The LVGL component generates the following:
test_page = new LvPageType();
lvgl_component->add_init_lambda([=](lv_disp_t * lv_disp) {
lvgl_component->add_page(test_page);
test_page->index = 0;
test_page->page = lv_obj_create(nullptr);
test_page->skip = false;
lvgl_component->set_page_wrap(true);
});If I could just replace or later reassign test_page->page = lv_obj_create(nullptr); I think I could use most of the generate code from EEZ Studio. The problem, is I can't find a good way to inject the code:
// Needs to be injected after lvgl_component->add_init_lambda
lv_obj_clean(test_page->page);
create_screen_main();
test_page->page = objects.main;Placing this in a on_boot: lambda injects the code way too early in setup(). And trying to put it in on_loop: seems to be too late to have an effect.
It would be nice if I could do something like this for "external" pages/widgets along with yaml-only delcared pages/widgets:
lvgl:
style_definitions:
- id: custom_style
lambda: |-
...
return style;
pages:
- id: test_page
lambda: |-
create_screen_main();
return objects.main;
- id: another_page
widgets:
- label:
align: CENTER
id: lbl_id
styles: custom_style
recolor: true
text: "#FF0000 write# #00FF00 colored# #0000FF text#"
- id: custom_widget
lambda: |-
...
return widget; And so on for the other LVGL types.
But I could be looking at this all the wrong way... Do you have a better idea on how to streamline the UI design process using this esphome component? While it's great to do simple stuff, the yaml->compile->upload->test cycle is very slow - lots trial/error and waiting?