From 2a85442708ef1c0607c66ca74fad84040b5bdcff Mon Sep 17 00:00:00 2001 From: "kkoenig1@optonline.com" Date: Sat, 15 Jan 2022 07:22:46 -0500 Subject: [PATCH] added factory code, and the beginnings of styling --- radio/src/thirdparty/libopenui/src/button.cpp | 19 +++--- radio/src/thirdparty/libopenui/src/button.h | 4 +- radio/src/thirdparty/libopenui/src/form.cpp | 4 +- radio/src/thirdparty/libopenui/src/form.h | 8 +-- radio/src/thirdparty/libopenui/src/layer.h | 7 +-- .../thirdparty/libopenui/src/mainwindow.cpp | 5 ++ .../src/thirdparty/libopenui/src/mainwindow.h | 4 +- .../thirdparty/libopenui/src/modal_window.cpp | 6 +- .../src/thirdparty/libopenui/src/textedit.cpp | 61 +++++++++---------- radio/src/thirdparty/libopenui/src/window.cpp | 25 ++++++-- radio/src/thirdparty/libopenui/src/window.h | 9 ++- 11 files changed, 89 insertions(+), 63 deletions(-) diff --git a/radio/src/thirdparty/libopenui/src/button.cpp b/radio/src/thirdparty/libopenui/src/button.cpp index f5f61f1e0..5e5efa4ea 100644 --- a/radio/src/thirdparty/libopenui/src/button.cpp +++ b/radio/src/thirdparty/libopenui/src/button.cpp @@ -77,22 +77,22 @@ void Button::checkEvents() } +LvglWidgetFactory textButtonFactory = LvglWidgetFactory( + [](lv_obj_t *parent) { + return lv_btn_create(parent); +}); + TextButton::TextButton(FormGroup* parent, const rect_t& rect, std::string text, std::function pressHandler, WindowFlags windowFlags, LcdFlags textFlags) : - Button(parent, rect, std::move(pressHandler), windowFlags, textFlags), + Button(parent, rect, std::move(pressHandler), windowFlags, textFlags, &textButtonFactory), text(std::move(text)) { - if (lvobj != nullptr) { - lv_obj_del(lvobj); - } - lvobj = lv_btn_create(parent->getLvObj()); - lv_obj_set_pos(lvobj, rect.x, rect.y); /*Set its position*/ - lv_obj_set_size(lvobj, rect.w, rect.h); /*Set its size*/ + lv_obj_set_pos(lvobj, rect.x, rect.y); + lv_obj_set_size(lvobj, rect.w, rect.h); setTextFlags(textFlags | COLOR_THEME_PRIMARY1); -#if 1 auto color = COLOR_VAL(COLOR_THEME_PRIMARY2); auto r = GET_RED(color), g = GET_GREEN(color), b = GET_BLUE(color); @@ -106,8 +106,7 @@ TextButton::TextButton(FormGroup* parent, const rect_t& rect, std::string text, lv_label_set_text(label, this->text.c_str()); lv_obj_center(label); color = COLOR_VAL(this->getTextFlags()); - lv_obj_set_style_text_color(label, lv_color_make(GET_RED(color), GET_GREEN(color), GET_BLUE(color)), LV_PART_MAIN); -#endif + // lv_obj_set_style_text_color(label, lv_color_make(GET_RED(color), GET_GREEN(color), GET_BLUE(color)), LV_PART_MAIN); } TextButton::~TextButton() diff --git a/radio/src/thirdparty/libopenui/src/button.h b/radio/src/thirdparty/libopenui/src/button.h index fa8078329..0671359fd 100644 --- a/radio/src/thirdparty/libopenui/src/button.h +++ b/radio/src/thirdparty/libopenui/src/button.h @@ -30,8 +30,8 @@ class Button: public FormField public: Button(FormGroup* parent, const rect_t& rect, std::function pressHandler = nullptr, - WindowFlags windowFlags = 0, LcdFlags textFlags = 0) : - FormField(parent, rect, windowFlags, textFlags), + WindowFlags windowFlags = 0, LcdFlags textFlags = 0, LvglWidgetFactory *factory = nullptr) : + FormField(parent, rect, windowFlags, textFlags, factory), pressHandler(std::move(pressHandler)) { } diff --git a/radio/src/thirdparty/libopenui/src/form.cpp b/radio/src/thirdparty/libopenui/src/form.cpp index 6bfa3b07f..995238d31 100644 --- a/radio/src/thirdparty/libopenui/src/form.cpp +++ b/radio/src/thirdparty/libopenui/src/form.cpp @@ -21,8 +21,8 @@ #include "bitmapbuffer.h" #include "libopenui_config.h" -FormField::FormField(Window * parent, const rect_t & rect, WindowFlags windowFlags, LcdFlags textFlags, bool isScreen) : - Window(parent, rect, windowFlags, textFlags, isScreen) +FormField::FormField(Window * parent, const rect_t & rect, WindowFlags windowFlags, LcdFlags textFlags, LvglWidgetFactory *factory) : + Window(parent, rect, windowFlags, textFlags, factory) { if (!(windowFlags & NO_FOCUS)) { auto * form = dynamic_cast(parent); diff --git a/radio/src/thirdparty/libopenui/src/form.h b/radio/src/thirdparty/libopenui/src/form.h index 871189a5e..4fe22449a 100644 --- a/radio/src/thirdparty/libopenui/src/form.h +++ b/radio/src/thirdparty/libopenui/src/form.h @@ -30,7 +30,7 @@ constexpr WindowFlags FORM_FLAGS_LAST = FORM_NO_BORDER; class FormField: public Window { public: - FormField(Window * parent, const rect_t & rect, WindowFlags windowFlags = 0, LcdFlags textFlags = 0, bool isScreen = false); + FormField(Window * parent, const rect_t & rect, WindowFlags windowFlags = 0, LcdFlags textFlags = 0, LvglWidgetFactory *factory = nullptr); virtual void changeEnd(bool forceChanged = false) { @@ -128,7 +128,7 @@ class FormField: public Window class FormGroup: public FormField { public: - FormGroup(Window * parent, const rect_t & rect, WindowFlags windowflags = 0, bool isScreen = false) : + FormGroup(Window * parent, const rect_t & rect, WindowFlags windowflags = 0, LvglWidgetFactory *factory = nullptr) : FormField(parent, rect, windowflags) { } @@ -212,8 +212,8 @@ class FormGroup: public FormField class FormWindow: public FormGroup { public: - FormWindow(Window * parent, const rect_t & rect, WindowFlags windowFlags = 0, bool isScreen = false) : - FormGroup(parent, rect, windowFlags, isScreen) + FormWindow(Window * parent, const rect_t & rect, WindowFlags windowFlags = 0, LvglWidgetFactory *factory = nullptr) : + FormGroup(parent, rect, windowFlags, factory) { } diff --git a/radio/src/thirdparty/libopenui/src/layer.h b/radio/src/thirdparty/libopenui/src/layer.h index 3e57672d5..e3e9caf02 100644 --- a/radio/src/thirdparty/libopenui/src/layer.h +++ b/radio/src/thirdparty/libopenui/src/layer.h @@ -37,10 +37,9 @@ class Layer static void push(Window * window) { - // if (window->getLvObj()->parent != nullptr) { - // TRACE("Layers must have lvgl parent to be null"); - // return; - // } + if (window->getLvObj()->parent != nullptr) { + TRACE("Layers must have lvgl parent to be null"); + } if (!stack.empty()) { Layer & parentLayer = stack.back(); diff --git a/radio/src/thirdparty/libopenui/src/mainwindow.cpp b/radio/src/thirdparty/libopenui/src/mainwindow.cpp index 7d2de6336..ac717ea25 100644 --- a/radio/src/thirdparty/libopenui/src/mainwindow.cpp +++ b/radio/src/thirdparty/libopenui/src/mainwindow.cpp @@ -26,6 +26,11 @@ MainWindow * MainWindow::_instance = nullptr; +LvglWidgetFactory mainWindowFactory = LvglWidgetFactory([] (lv_obj_t *parent) { + return lv_obj_create(nullptr); +}); + + #if defined(HARDWARE_TOUCH) TouchState touchState; Keyboard * Keyboard::activeKeyboard = nullptr; diff --git a/radio/src/thirdparty/libopenui/src/mainwindow.h b/radio/src/thirdparty/libopenui/src/mainwindow.h index d02f9889c..2b0cdb427 100644 --- a/radio/src/thirdparty/libopenui/src/mainwindow.h +++ b/radio/src/thirdparty/libopenui/src/mainwindow.h @@ -23,12 +23,14 @@ #include "layer.h" #include "bitmapbuffer.h" +extern LvglWidgetFactory mainWindowFactory; + class MainWindow: public Window { protected: // singleton MainWindow(): - Window(nullptr, {0, 0, LCD_W, LCD_H}, 0, 0, true), + Window(nullptr, {0, 0, LCD_W, LCD_H}, 0, 0, &mainWindowFactory), invalidatedRect(rect) { Layer::push(this); diff --git a/radio/src/thirdparty/libopenui/src/modal_window.cpp b/radio/src/thirdparty/libopenui/src/modal_window.cpp index ee8c67fe4..37c9ec9b6 100644 --- a/radio/src/thirdparty/libopenui/src/modal_window.cpp +++ b/radio/src/thirdparty/libopenui/src/modal_window.cpp @@ -22,8 +22,12 @@ #include "font.h" #include "layer.h" +LvglWidgetFactory modalFactory = LvglWidgetFactory([] (lv_obj_t *parent) { + return lv_obj_create(nullptr); +}); + ModalWindow::ModalWindow(Window * parent, bool closeWhenClickOutside): - Window(parent->getFullScreenWindow(), {0, 0, LCD_W, LCD_H}, 0, 0, true), + Window(parent->getFullScreenWindow(), {0, 0, LCD_W, LCD_H}, 0, 0, &modalFactory), closeWhenClickOutside(closeWhenClickOutside) { Layer::push(this); diff --git a/radio/src/thirdparty/libopenui/src/textedit.cpp b/radio/src/thirdparty/libopenui/src/textedit.cpp index 74a087724..8dcf2055b 100644 --- a/radio/src/thirdparty/libopenui/src/textedit.cpp +++ b/radio/src/thirdparty/libopenui/src/textedit.cpp @@ -48,15 +48,13 @@ static void ta_event_cb(lv_event_t * e) lv_event_code_t code = lv_event_get_code(e); lv_obj_t * ta = lv_event_get_target(e); if(code == LV_EVENT_CLICKED || code == LV_EVENT_FOCUSED) { - /*Focus on the clicked text area*/ - if(kb != NULL) - lv_keyboard_set_textarea(kb, ta); - else { - /*Create a keyboard*/ + if (kb == nullptr) { kb = lv_keyboard_create(lv_scr_act()); lv_obj_set_size(kb, LV_HOR_RES, LV_VER_RES / 2); - lv_keyboard_set_textarea(kb, ta); } + + if(kb != NULL) + lv_keyboard_set_textarea(kb, ta); } else if (code == LV_EVENT_DEFOCUSED) { if (kb != nullptr) { @@ -64,47 +62,48 @@ static void ta_event_cb(lv_event_t * e) kb = nullptr; } } - else if(code == LV_EVENT_READY) { - LV_LOG_USER("Ready, current text: %s", lv_textarea_get_text(ta)); - } } + +LvglWidgetFactory textEditFactory = LvglWidgetFactory( + [] (lv_obj_t *parent) { + return lv_textarea_create(parent); + }, + [] (LvglWidgetFactory *factory) { + lv_style_set_border_width(&factory->style, 1); + lv_style_set_radius(&factory->style, 0); + lv_style_set_pad_top(&factory->style, 2); + lv_style_set_pad_bottom(&factory->style, 2); + lv_style_set_pad_left(&factory->style, 2); + lv_style_set_pad_right(&factory->style, 2); + lv_style_set_text_font(&factory->style, &lv_font_montserrat_14); + lv_style_set_text_line_space(&factory->style, 0); + + lv_style_set_bg_color(&factory->style, lv_color_make(10,10,10)); + } +); + + TextEdit::TextEdit(Window * parent, const rect_t & rect, char * value, uint8_t length, LcdFlags windowFlags, const char * _extra_chars) : - FormField(parent, rect, windowFlags), + FormField(parent, rect, windowFlags, 0, &textEditFactory), value(value), length(length) { - if (getLvObj() != nullptr) { - lv_obj_del(lvobj); - } - - lvobj = lv_textarea_create(parent->getLvObj()); lv_obj_add_event_cb(lvobj, ta_event_cb, LV_EVENT_ALL, NULL); - lv_obj_set_pos(lvobj, rect.x, rect.y); - lv_obj_set_size(lvobj, rect.w, rect.h); + lv_obj_add_style(lvobj, &textEditFactory.style, LV_PART_MAIN); + + lv_obj_set_style_bg_color(lvobj, lv_color_make(255,10,10), LV_PART_MAIN); + lv_obj_set_scrollbar_mode(lvobj, LV_SCROLLBAR_MODE_OFF); - lv_obj_set_style_border_width(lvobj, 0, LV_PART_MAIN); - lv_obj_set_style_radius(lvobj, 0, LV_PART_MAIN); - lv_obj_set_style_pad_top(lvobj, 2, LV_PART_MAIN); - lv_obj_set_style_pad_bottom(lvobj, 2, LV_PART_MAIN); - lv_obj_set_style_pad_left(lvobj, 4, LV_PART_MAIN); - lv_obj_set_style_pad_right(lvobj, 4, LV_PART_MAIN); - - lv_textarea_set_password_mode(lvobj, false); lv_textarea_set_one_line(lvobj, true); lv_textarea_set_text(lvobj, value); lv_textarea_set_placeholder_text(lvobj, "---"); lv_textarea_set_max_length(lvobj, length); - lv_obj_set_style_text_font(lvobj, &lv_font_montserrat_12, LV_PART_MAIN); - lv_obj_set_style_text_line_space(lvobj, 0, LV_PART_MAIN); - - auto color = COLOR_VAL(COLOR_THEME_SECONDARY1); auto label = lv_textarea_get_label(lvobj); - lv_obj_set_style_text_color(label, lv_color_make(GET_RED(color), GET_GREEN(color), GET_BLUE(color)), LV_PART_MAIN); - + lv_obj_set_style_text_color(label, makeLvColor(COLOR_THEME_SECONDARY1), LV_PART_MAIN); extra_chars = (_extra_chars) ? _extra_chars : extra_chars_default; } diff --git a/radio/src/thirdparty/libopenui/src/window.cpp b/radio/src/thirdparty/libopenui/src/window.cpp index 1ee864219..ea4cfdcb8 100644 --- a/radio/src/thirdparty/libopenui/src/window.cpp +++ b/radio/src/thirdparty/libopenui/src/window.cpp @@ -41,7 +41,18 @@ static void window_event_cb(lv_event_t * e) } } -Window::Window(Window * parent, const rect_t & rect, WindowFlags windowFlags, LcdFlags textFlags, bool isScreen) : +LvglWidgetFactory windowFactory = LvglWidgetFactory( + [] (lv_obj_t *parent) { + return lv_obj_create(parent); + }, + [] (LvglWidgetFactory *factory) { + lv_style_set_pad_all(&factory->style, 0); + lv_style_set_bg_opa(&factory->style, LV_OPA_TRANSP); + lv_style_set_border_width(&factory->style, 0); + lv_style_set_radius(&factory->style, 0); + }); + +Window::Window(Window * parent, const rect_t & rect, WindowFlags windowFlags, LcdFlags textFlags, LvglWidgetFactory *factory) : parent(parent), rect(rect), innerWidth(rect.w), @@ -49,14 +60,15 @@ Window::Window(Window * parent, const rect_t & rect, WindowFlags windowFlags, Lc windowFlags(windowFlags), textFlags(textFlags) { - lvobj = lv_obj_create(isScreen ? nullptr : parent != nullptr ? parent->lvobj : nullptr); + lv_obj_t *lvParent = parent != nullptr ? parent->lvobj : nullptr; + lvobj = (factory == nullptr) ? + windowFactory.construct(lvParent) : + factory->construct(lvParent); + + lv_obj_add_style(lvobj, &windowFactory.style, LV_PART_MAIN); lv_obj_set_pos(lvobj, rect.x, rect.y); lv_obj_set_size(lvobj, rect.w, rect.h); - lv_obj_set_style_pad_all(lvobj, 0, LV_PART_MAIN); - lv_obj_set_style_bg_opa(lvobj, LV_OPA_TRANSP, LV_PART_MAIN); - lv_obj_set_style_border_width(lvobj, 0, LV_PART_MAIN); - lv_obj_set_style_radius(lvobj, 0, LV_PART_MAIN); lv_obj_set_scrollbar_mode(lvobj, LV_SCROLLBAR_MODE_OFF); lv_obj_clear_flag(lvobj, LV_OBJ_FLAG_SCROLL_ELASTIC); lv_obj_add_event_cb(lvobj, window_event_cb, LV_EVENT_ALL, this); @@ -163,6 +175,7 @@ void Window::setFocus(uint8_t flag, Window * from) TRACE_WINDOWS("%s setFocus()", getWindowDebugString().c_str()); if (focusWindow != this) { + // lv_obj_add_state(lvobj, LV_STATE_FOCUSED); // scroll before calling focusHandler so that the window can adjust the scroll position if needed Window * parent = this->parent; while (parent && parent->getWindowFlags() & FORWARD_SCROLL) { diff --git a/radio/src/thirdparty/libopenui/src/window.h b/radio/src/thirdparty/libopenui/src/window.h index d8fcc5361..fe5747bc3 100644 --- a/radio/src/thirdparty/libopenui/src/window.h +++ b/radio/src/thirdparty/libopenui/src/window.h @@ -30,7 +30,7 @@ #include "libopenui_defines.h" #include "libopenui_helpers.h" #include "libopenui_config.h" -#include "../../lvgl/src/lvgl.h" +#include "LvglWrapper.h" typedef uint32_t WindowFlags; @@ -64,7 +64,7 @@ class Window friend class GridLayout; public: - Window(Window * parent, const rect_t & rect, WindowFlags windowFlags = 0, LcdFlags textFlags = 0, bool isScreen = false); + Window(Window * parent, const rect_t & rect, WindowFlags windowFlags = 0, LcdFlags textFlags = 0, LvglWidgetFactory *factory = nullptr); virtual ~Window(); @@ -133,6 +133,11 @@ class Window void setTextFlags(LcdFlags flags) { textFlags = flags; + + // lv integration for colors + auto textColor = COLOR_VAL(flags); + auto r = GET_RED(textColor), g = GET_GREEN(textColor), b = GET_BLUE(textColor); + lv_obj_set_style_text_color(getLvObj(), lv_color_make(r, g, b), LV_PART_MAIN); } void setCloseHandler(std::function handler)