一、LVGL 中组件加载步骤
-
分配内存与初始化:
- 首先,通过调用相应组件的创建函数来分配内存并初始化组件对象。例如,若要创建一个按钮组件,可使用
lv_XXX_create
函数。这些创建函数会返回一个指向新创建组件对象(lv_obj_t
类型)的指针。在创建过程中,会依据组件类型分配适当的内存空间,用于存储该组件的各种属性,如位置、大小、状态等。
- 首先,通过调用相应组件的创建函数来分配内存并初始化组件对象。例如,若要创建一个按钮组件,可使用
-
设置组件属性:
- 在创建组件后,需设置其各种属性,包括位置(
lv_obj_set_pos
)、大小(lv_obj_set_size
)、样式(lv_obj_set_style
)等。以设置按钮的位置为例,通过指定x
和y
坐标,可将按钮放置在屏幕或父容器的特定位置。样式属性能够控制组件的外观,如背景颜色、文本颜色、边框样式等。对这些属性的设置可使组件符合应用程序的设计要求。
- 在创建组件后,需设置其各种属性,包括位置(
-
添加到父容器(如果有):
- 许多 LVGL 组件需要添加到一个父容器中才能正确显示。例如,按钮可以添加到一个屏幕对象或者一个容器对象中。通过
lv_obj_add_child
函数,可将新创建的组件添加到父容器。父容器负责管理其内部子组件的布局和显示顺序。在添加组件到父容器时,LVGL 会根据父容器的布局规则(如线性布局、网格布局等)来确定子组件的最终位置和大小。
- 许多 LVGL 组件需要添加到一个父容器中才能正确显示。例如,按钮可以添加到一个屏幕对象或者一个容器对象中。通过
二、样例:创建一个滑动组件并实时记录滑动位置
以下是创建一个滑动组件并实时记录滑动位置的代码示例:
lv_obj_t *label; /*Label to display the slider value*/
lv_obj_t *slider1; /*Slider object*/slider1 = lv_slider_create(lv_scr_act());
lv_slider_set_range(slider1, 0, 100);
lv_slider_set_left_value(slider1, 50, LV_ANIM_ON);
lv_obj_center(slider1);// 设置样式
static lv_style_t style1;
lv_style_init(&style1);
lv_style_set_bg_color(&style1, lv_color_hex(0xa03080));
lv_style_set_border_width(&style1, 2);
lv_obj_add_style(slider1, &style1, LV_PART_MAIN | LV_STATE_DEFAULT);label = lv_label_create(lv_scr_act());lv_obj_align_to(label, slider1, LV_ALIGN_OUT_TOP_MID, 0, -15); /*Align top of the slider*/
lv_obj_add_event_cb(slider1, slider_event_cb, LV_EVENT_VALUE_CHANGED, NULL); /*Assign an event function*/
添加滑动时值改变的信号LV_EVENT_VALUE_CHANGED
并注册回调函数slider_event_cb
,设置文本的值:
static void slider_event_cb(lv_event_t *e)
{lv_obj_t *slider = lv_event_get_target(e);if (e->code == LV_EVENT_VALUE_CHANGED){/*Refresh the text*/lv_label_set_text_fmt(label, "%" LV_PRId32, lv_slider_get_value(slider));lv_obj_align_to(label, slider1, LV_ALIGN_OUT_TOP_MID, 0, -15); /*Align top of the slider*/}
}
通过上述代码,可以实现一个实时滑动显示滑动进度的滑动条组件。效果如下:
三、滑动条具体实现
调用函数lv_slider_create(lv_scr_act());
,该函数如下:
lv_obj_t * lv_slider_create(lv_obj_t * parent)
{LV_LOG_INFO("begin");lv_obj_t * obj = lv_obj_class_create_obj(MY_CLASS, parent);lv_obj_class_init_obj(obj);return obj;
}
在这个函数中,根据lv_slider_class
(MY_CLASS
)的属性,创建了一个以parent
为父节点的slider
元素。lv_slider_class
签名如下:
const lv_obj_class_t lv_slider_class = {.constructor_cb = lv_slider_constructor,.event_cb = lv_slider_event,.editable = LV_OBJ_CLASS_EDITABLE_TRUE,.group_def = LV_OBJ_CLASS_GROUP_DEF_TRUE,.instance_size = sizeof(lv_slider_t),.base_class = &lv_bar_class
};
lv_slider_class
中指定了组件的初始化、事件触发回调、编辑状态、组定义、大小以及基类信息。
-
lv_obj_class_create_obj
:该方法申请内存,构建出一个lv_obj_t
对象,并且指定当前显示的父节点。(如果父节点为NULL
,则显示在默认的显示对象上)。 -
lv_obj_class_init_obj
:这个函数负责初始化一个对象,具体步骤如下:lv_obj_mark_layout_as_dirty
:标记对象的布局为脏,使得重新计算对象布局。lv_obj_enable_style_refresh
:禁用样式刷新,这样在初始化过程中不会立即应用样式。lv_theme_apply
:将当前主题应用到对象上。lv_obj_construct
:构造对象。lv_obj_enable_style_refresh
:启用样式刷新,允许对象应用样式。lv_obj_refresh_style
:刷新对象的样式,确保所有部分和属性都更新。lv_obj_refresh_self_size
:刷新对象的自身大小,确保大小信息是最新的。lv_group_add_obj
:这部分代码检查是否存在默认组,并且对象是否应该属于该组。如果是,则将对象添加到默认组中。lv_event_send
:发送LV_EVENT_CHILD_CHANGED
和LV_EVENT_CHILD_CREATED
事件给父对象,通知父对象有新的子对象。如果对象不是屏幕(即没有父对象),它会使对象的区域无效,这可能会触发布局更新。lv_obj_invalidate
:这个组件只在父对象的区域内显示,超出部分不显示。