矩阵按钮部件

在 LVGL中,按钮矩阵部件相当于一系列伪按钮的集合,它按一定的序列来排布这些按钮。
值得注意的是,这些伪按钮并不是真正的按钮部件(lv_btn),它们只是具有按钮外观的图形,
但这些图形具有和按钮一样的点击效果。伪按钮所占的内存非常小,一个伪按钮大概占用 8 个
字节,而一个普通按钮部件所占的内存大概为 100~150个字节,由此可见,当 GUI界面中使用
较多按钮时,按钮矩阵的优势就尤为明显了。

1 按钮矩阵部件的组成

按钮矩阵部件由两个部分组成:主体背景和按钮,示意图如下:

2 按钮矩阵部件的相关知识

13.2.1****按钮文本设置

在 LVGL中,按钮矩阵部件中的每个按钮都可以设置文本,如果用户想设置这些按钮文本,
则需要定义一个字符串数组(指针),并在该数组中传入所需的文本内容,最后通过
lv_btnmatrix_set_map 函数设置按钮文本,示例代码如下:

const char * map[] = { "btn1","btn2","btn3", "" };//定义了字符串数组,里面传入了 3 个按钮的对应文本,注意:该数组最后一个元素必须为空。
void lv_mainstart()
{
lv_obj_t * btnm1 = lv_btnmatrix_create(lv_scr_act());//再调用 lv_btnmatrix_create 函数创建按钮矩阵
lv_btnmatrix_set_map(btnm1, map);//通过 lv_btnmatrix_set_map 函数把字符串数组映射到按钮矩阵当中
}

13.2.2****按钮换行

const char * map[] = { "btn1","\n", "btn2","btn3", "" };//创建btn1后换行
void lv_mainstart()
{
lv_obj_t * btnm1 = lv_btnmatrix_create(lv_scr_act());
lv_btnmatrix_set_map(btnm1, map);
}

13.2.3****按钮索引

索引就相当于一个 ID,在按钮矩阵部件中,每一个按钮都有对应的索引。在上一小节的
示例中,我们添加了 3 个按钮,这些按钮对应的索引如下所示:


btn1 为第一个按钮,其索引为 0;btn2 为第二个按钮,其索引为 1,btn3 以 此类推。
注意:索引对于按钮的属性设置非常重要

13.2.4****按钮宽度

在默认情况下,按钮矩阵每一行按钮的宽度都是自动计算的,如果用户想改变按钮的宽度,
可以调用 lv_btnmatrix_set_btn_width 函数来进行设置。值得注意的是,在按钮矩阵部件中,按
钮只能设置相对宽度。

13.2.5****按钮属性

以调用 lv_btnmatrix_set_btn_ctrl 函数,为按钮添加、清除指定的属性
① LV_BTNMATRIX_CTRL_HIDDEN:将按钮隐藏;
② LV_BTNMATRIX_CTRL_NO_REPEAT:禁用长按;
③ LV_BTNMATRIX_CTRL_DISABLED:禁用按钮;
④ LV_BTNMATRIX_CTRL_CHECKABLE:启用按钮状态切换;
⑤ LV_BTNMATRIX_CTRL_CHECKED:选中按钮;
⑥ LV_BTNMATRIX_CTRL_POPOVER:按下此按钮时在弹出窗口中显示按钮标签;
⑦ LV_BTNMATRIX_CTRL_RECOLOR:启用按钮文本的重新着色功能。

const char * map[] = { "btn1","btn2","btn3", "" };//传入了 3 个按钮的对应文本,注意:该数组最后一个元素必须为空

void lv_mainstart_music(void)

{

lv_obj_t * btnm1 = lv_btnmatrix_create(lv_scr_act());

lv_btnmatrix_set_map(btnm1, map);

lv_obj_set_size(btnm1, 800, 480 / 4);//设置默认矩阵按键每个按键的大小

lv_btnmatrix_set_btn_ctrl(btnm1, 0, LV_BTNMATRIX_CTRL_HIDDEN);//第一个按键设置位隐藏属性

lv_btnmatrix_set_btn_ctrl(btnm1, 1, LV_BTNMATRIX_CTRL_DISABLED);//第二个按键设置成不可点击属性

lv_btnmatrix_set_btn_ctrl(btnm1, 2, LV_BTNMATRIX_CTRL_CHECKABLE);//第三个按下时切换按钮状态

lv_btnmatrix_set_btn_width(btnm1, 0, 2);//设置第一个按键是设置按键宽度的两倍

}

13.2.6****按钮互斥

调用 lv_btnmatrix_set_one_checked 函数

const char * map[] = { "btn1","btn2","btn3", "" };//传入了 3 个按钮的对应文本,注意:该数组最后一个元素必须为空

void lv_mainstart_music(void)

{

lv_obj_t* btnm1 = lv_btnmatrix_create(lv_scr_act());

lv_btnmatrix_set_map(btnm1, map);

lv_btnmatrix_set_btn_ctrl(btnm1, 0, LV_BTNMATRIX_CTRL_CHECKABLE);//第一个按键启用按钮状态切换

lv_btnmatrix_set_btn_ctrl(btnm1, 1, LV_BTNMATRIX_CTRL_CHECKABLE);

lv_btnmatrix_set_btn_ctrl(btnm1, 2, LV_BTNMATRIX_CTRL_CHECKABLE);

lv_btnmatrix_set_btn_width(btnm1, 2, 2);//

lv_btnmatrix_set_one_checked(btnm1, true);//开启三个按键互斥

}

实验效果:三个按键同一时间只能按下一个
13.2.7****按钮文本重着色
调用 lv_btnmatrix_set_btn_ctrl 函数,为按钮添加文本重着色的属性。

const char * map[] = { "#FF0000 btn1#", "btn2","btn3", "" };//按键1着色后为红色
void lv_mainstart()
{
lv_obj_t * btnm1 = lv_btnmatrix_create(lv_scr_act(), NULL);
lv_btnmatrix_set_map(btnm1, map);
lv_btnmatrix_set_btn_ctrl(btnm1, 0, LV_BTNMATRIX_CTRL_RECOLOR);//按键0启用文本着色功能
}
13.2.8****按钮矩阵部件的事件
① LV_EVENT_VALUE_CHANGED:当一个按钮被按下、释放或长按时发送。
② LV_EVENT_DRAW_PART_BEGIN:开始绘制按钮。

3 按钮矩阵部件的 API 函数

lv_btnmatrix_create() 创建按钮矩阵部件
lv_btnmatrix_set_map() 设置按钮
lv_btnmatrix_set_ctrl_map() 设置多个按钮属性
lv_btnmatrix_set_selected_btn() 设置选中的按钮
lv_btnmatrix_set_btn_ctrl() 设置一个按钮的属性
lv_btnmatrix_clear_btn_ctrl() 清除某个按钮的属性
lv_btnmatrix_set_btn_ctrl_all() 设置所有按钮的属性
lv_btnmatrix_clear_btn_ctrl_all() 清除所有按钮的属性
lv_btnmatrix_set_btn_width() 设置单个按钮的相对宽度
lv_btnmatrix_set_one_checked() 设置按钮互斥
lv_btnmatrix_get_map() 获取按钮相关映射
lv_btnmatrix_get_selected_btn() 获取用户最后点击的按钮的索引
lv_btnmatrix_get_btn_text() 获取按钮的文本
lv_btnmatrix_has_btn_ctrl() 获取按钮的状态
lv_btnmatrix_get_one_checked() 判断按钮互斥是否开启

详细描述如下

lv_btnmatrix_create() 创建按钮矩阵部件
lv_obj_t * lv_ btnmatrix_create ( lv_obj_t *parent);
lv_btnmatrix_set_map() 设置按钮
void lv_btnmatrix_set_map ( lv_obj_t * obj , const char * map [ ] );
lv_btnmatrix_set_ctrl_map() 设置多个按钮属性
void lv_btnmatrix_set_ctrl_map ( lv_obj_t * obj , const lv_btnmatrix_ctrl_t ctrl_map [ ] );
lv_btnmatrix_set_selected_btn() 设置选中的按钮
void lv_btnmatrix_set_selected_btn ( lv_obj_t * obj , uint16_t btn_id );
lv_btnmatrix_set_btn_ctrl() 设置一个按钮的属性
void lv_btnmatrix_set_btn_ctrl ( lv_obj_t * obj , uint16_t btn_id , lv_btnmatrix_ctrl_t ctrl );
lv_btnmatrix_clear_btn_ctrl() 清除某个按钮的属性
void lv_btnmatrix_clear_btn_ctrl ( lv_obj_t * obj , uint16_t btn_id , lv_btnmatrix_ctrl_t ctrl );
lv_btnmatrix_set_btn_ctrl_all() 设置所有按钮的属性
void lv_btnmatrix_set_btn_ctrl_all ( lv_obj_t * obj , lv_btnmatrix_ctrl_t ctrl );
lv_btnmatrix_clear_btn_ctrl_all() 清除所有按钮的属性
void lv_btnmatrix_clear_btn_ctrl_all ( lv_obj_t * obj , lv_btnmatrix_ctrl_t ctrl );
lv_btnmatrix_set_btn_width() 设置单个按钮的相对宽度
void lv_btnmatrix_set_btn_width ( lv_obj_t * obj , uint16_t btn_id , uint8_t width);
lv_btnmatrix_set_one_checked() 设置按钮互斥
void lv_btnmatrix_set_one_checked ( lv_obj_t * obj , bool en );
lv_btnmatrix_get_map() 获取按钮相关映射
lv_btnmatrix_get_selected_btn() 获取用户最后点击的按钮的索引
lv_btnmatrix_get_btn_text() 获取按钮的文本
lv_btnmatrix_has_btn_ctrl() 获取按钮的状态
lv_btnmatrix_get_one_checked() 判断按钮互斥是否开启

4 按钮矩阵部件的实验

/**************************** 第一部分 开始 ****************************/
/**
* @brief LVGL 演示
* @param 无
* @return 无
*/
void lv_mainstart(void)
{
lv_example_btnmatrix();
}
/**************************** 第一部分 结束 ****************************/
/**************************** 第二部分 开始 ****************************/
/**
* @brief 按钮矩阵事件回调
* @param *e :事件相关参数的集合,它包含了该事件的所有数据
* @return 无
*/
static void btnm_event_cb(lv_event_t* e)
{
uint8_t id;
lv_event_code_t code = lv_event_get_code(e); /* 获取事件类型 */
lv_obj_t *target = lv_event_get_target(e); /* 获取触发源 */
if (code == LV_EVENT_VALUE_CHANGED)
{
id = lv_btnmatrix_get_selected_btn(target); /* 获取按钮索引 */
/* 更新输入框标签文本 */
lv_label_set_text(label_input, lv_btnmatrix_get_btn_text(target, id));
/* 设置标签位置 */
lv_obj_align_to(label_input, obj_input, LV_ALIGN_CENTER, 0, 0);
}
}
/**
* @brief 密码输入界面
* @param 无
* @return 无
*/
static void lv_example_btnmatrix(void)
{
/* 根据屏幕宽度选择字体和图片缩放系数 */
if (scr_act_width() <= 480)
{
font = &lv_font_montserrat_14;
zoom_val = 128;
}
else
{
font = &lv_font_montserrat_30;
zoom_val = 256;
}
/* 图片显示 */
lv_obj_t *img = lv_img_create(lv_scr_act()); /* 创建图片部件 */
lv_img_set_src(img, &img_user); /* 设置图片源 */
lv_img_set_zoom(img, zoom_val); /* 设置图片缩放 */
/* 设置位置 */
lv_obj_align(img, LV_ALIGN_CENTER, -scr_act_width()/4,-scr_act_height()/7);
/* 设置重新着色 */
lv_obj_set_style_img_recolor(img, lv_color_hex(0xf2f2f2),0);
lv_obj_set_style_img_recolor_opa(img,100,0); /* 设置着色透明度 */
/* 用户标签 */
lv_obj_t *label_user = lv_label_create(lv_scr_act()); /* 创建标签 */
lv_label_set_text(label_user, "USER"); /* 设置文本 */
/* 设置字体 */
lv_obj_set_style_text_font(label_user, font, LV_PART_MAIN);
/* 设置文本居中 */
lv_obj_set_style_text_align(label_user, LV_TEXT_ALIGN_CENTER,
LV_PART_MAIN);
/* 设置位置 */
lv_obj_align_to(label_user, img, LV_ALIGN_OUT_BOTTOM_MID, 0, 10);
/* 输入框背景 */
obj_input = lv_obj_create(lv_scr_act());
/* 创建基础对象 */
/* 设置大小 */
lv_obj_set_size(obj_input, scr_act_width()/4, scr_act_height()/12);
/* 设置位置 */
lv_obj_align_to(obj_input, label_user, LV_ALIGN_OUT_BOTTOM_MID, 0,
scr_act_height()/20);
/* 设置背景颜色 */
lv_obj_set_style_bg_color(obj_input, lv_color_hex(0xcccccc),0);
lv_obj_set_style_bg_opa(obj_input, 150,0); /* 设置透明度 */
lv_obj_set_style_border_width(obj_input, 0 , 0); /* 去除边框 */
lv_obj_set_style_radius(obj_input, 20, 0); /* 设置圆角 */
lv_obj_remove_style(obj_input, NULL, LV_PART_SCROLLBAR); /* 移除滚动条 */
/* 输入框文本标签 */
label_input = lv_label_create(lv_scr_act()); /* 创建标签 */
lv_label_set_text(label_input, ""); /* 设置文本 */
/* 设置字体 */
lv_obj_set_style_text_font(label_input, font, LV_PART_MAIN);
lv_obj_set_style_text_align(label_input, LV_TEXT_ALIGN_CENTER,
LV_PART_MAIN); /* 设置文本居中 */
/* 设置位置 */
lv_obj_align_to(label_input, obj_input, LV_ALIGN_CENTER, 0, 0);
/* 分隔线 */
lv_obj_t *line = lv_line_create(lv_scr_act()); /* 创建线条 */
lv_line_set_points(line, points, 2);
/* 设置线条坐标点 */
lv_obj_align(line, LV_ALIGN_CENTER, 0, 0); /* 设置位置 */
/* 设置线条颜色 */
lv_obj_set_style_line_color(line, lv_color_hex(0xcdcdcd),0);
/* 按钮矩阵(创建) */
lv_obj_t *btnm = lv_btnmatrix_create(lv_scr_act()); /* 创建按钮矩阵 */
/* 设置大小 */
lv_obj_set_size(btnm, scr_act_width()* 2/5, scr_act_width()* 2/5);
/* 设置按钮 */
lv_btnmatrix_set_map(btnm, num_map);
/* 设置位置 */
lv_obj_align(btnm, LV_ALIGN_RIGHT_MID, -scr_act_width()/16, 0);
/* 设置字体 */
lv_obj_set_style_text_font(btnm, font, LV_PART_ITEMS);
/* 按钮矩阵(优化界面) */
lv_obj_set_style_border_width(btnm, 0, LV_PART_MAIN); /* 去除主体边框 */
lv_obj_set_style_bg_opa(btnm, 0, LV_PART_MAIN); /* 设置主体背景透明度 */
lv_obj_set_style_bg_opa(btnm, 0, LV_PART_ITEMS); /* 设置按钮背景透明度 */
lv_obj_set_style_shadow_width(btnm, 0, LV_PART_ITEMS); /* 去除按钮阴影 */
/* 设置按钮矩阵回调 */
lv_obj_add_event_cb(btnm, btnm_event_cb, LV_EVENT_VALUE_CHANGED, NULL);
}
/**************************** 第二部分 结束 ****************************/

复制代码
/**************************** 第一部分 开始 ****************************/
/**
* @brief LVGL 演示
* @param 无
* @return 无
*/
void lv_mainstart(void)
{

lv_example_btnmatrix();
}
/**************************** 第一部分 结束 ****************************/
/**************************** 第二部分 开始 ****************************/
/**
* @brief 按钮矩阵事件回调
* @param *e :事件相关参数的集合,它包含了该事件的所有数据
* @return 无
*/
static void btnm_event_cb(lv_event_t* e)
{

uint8_t id;

lv_event_code_t code = lv_event_get_code(e); /* 获取事件类型 */

lv_obj_t *target = lv_event_get_target(e); /* 获取触发源 */

if (code == LV_EVENT_VALUE_CHANGED)

{

id = lv_btnmatrix_get_selected_btn(target); /* 获取按钮索引 */
/* 更新输入框标签文本 */

lv_label_set_text(label_input, lv_btnmatrix_get_btn_text(target, id));
/* 设置标签位置 */

lv_obj_align_to(label_input, obj_input, LV_ALIGN_CENTER, 0, 0);

}
}
/**
* @brief 密码输入界面
* @param 无
* @return 无
*/
static void lv_example_btnmatrix(void)
{

/* 根据屏幕宽度选择字体和图片缩放系数 */

if (scr_act_width() <= 480)

{

font = &lv_font_montserrat_14;

zoom_val = 128;

}

else

{

font = &lv_font_montserrat_30;

zoom_val = 256;

}

/* 图片显示 */

lv_obj_t *img = lv_img_create(lv_scr_act()); /* 创建图片部件 */

lv_img_set_src(img, &img_user); /* 设置图片源 */
lv_img_set_zoom(img, zoom_val); /* 设置图片缩放 */
/* 设置位置 */
lv_obj_align(img, LV_ALIGN_CENTER, -scr_act_width()/4,-scr_act_height()/7);
/* 设置重新着色 */

lv_obj_set_style_img_recolor(img, lv_color_hex(0xf2f2f2),0);

lv_obj_set_style_img_recolor_opa(img,100,0); /* 设置着色透明度 */

/* 用户标签 */

lv_obj_t *label_user = lv_label_create(lv_scr_act()); /* 创建标签 */
lv_label_set_text(label_user, "USER"); /* 设置文本 */
/* 设置字体 */
lv_obj_set_style_text_font(label_user, font, LV_PART_MAIN);
/* 设置文本居中 */

lv_obj_set_style_text_align(label_user, LV_TEXT_ALIGN_CENTER,
LV_PART_MAIN);

/* 设置位置 */

lv_obj_align_to(label_user, img, LV_ALIGN_OUT_BOTTOM_MID, 0, 10);

/* 输入框背景 */
obj_input = lv_obj_create(lv_scr_act());
/* 创建基础对象 */
/* 设置大小 */
lv_obj_set_size(obj_input, scr_act_width()/4, scr_act_height()/12);
/* 设置位置 */

lv_obj_align_to(obj_input, label_user, LV_ALIGN_OUT_BOTTOM_MID, 0,
scr_act_height()/20);

/* 设置背景颜色 */

lv_obj_set_style_bg_color(obj_input, lv_color_hex(0xcccccc),0);

lv_obj_set_style_bg_opa(obj_input, 150,0); /* 设置透明度 */

lv_obj_set_style_border_width(obj_input, 0 , 0); /* 去除边框 */

lv_obj_set_style_radius(obj_input, 20, 0); /* 设置圆角 */

lv_obj_remove_style(obj_input, NULL, LV_PART_SCROLLBAR); /* 移除滚动条 */

/* 输入框文本标签 */

label_input = lv_label_create(lv_scr_act()); /* 创建标签 */
lv_label_set_text(label_input, ""); /* 设置文本 */
/* 设置字体 */

lv_obj_set_style_text_font(label_input, font, LV_PART_MAIN);

lv_obj_set_style_text_align(label_input, LV_TEXT_ALIGN_CENTER,
LV_PART_MAIN); /* 设置文本居中 */

/* 设置位置 */

lv_obj_align_to(label_input, obj_input, LV_ALIGN_CENTER, 0, 0);

/* 分隔线 */

lv_obj_t *line = lv_line_create(lv_scr_act()); /* 创建线条 */

lv_line_set_points(line, points, 2);
/* 设置线条坐标点 */
lv_obj_align(line, LV_ALIGN_CENTER, 0, 0); /* 设置位置 */
/* 设置线条颜色 */

lv_obj_set_style_line_color(line, lv_color_hex(0xcdcdcd),0);

/* 按钮矩阵(创建) */
lv_obj_t *btnm = lv_btnmatrix_create(lv_scr_act()); /* 创建按钮矩阵 */
/* 设置大小 */
lv_obj_set_size(btnm, scr_act_width()* 2/5, scr_act_width()* 2/5);
/* 设置按钮 */
lv_btnmatrix_set_map(btnm, num_map);
/* 设置位置 */
lv_obj_align(btnm, LV_ALIGN_RIGHT_MID, -scr_act_width()/16, 0);
/* 设置字体 */

lv_obj_set_style_text_font(btnm, font, LV_PART_ITEMS);

/* 按钮矩阵(优化界面) */

lv_obj_set_style_border_width(btnm, 0, LV_PART_MAIN); /* 去除主体边框 */

lv_obj_set_style_bg_opa(btnm, 0, LV_PART_MAIN); /* 设置主体背景透明度 */

lv_obj_set_style_bg_opa(btnm, 0, LV_PART_ITEMS); /* 设置按钮背景透明度 */
lv_obj_set_style_shadow_width(btnm, 0, LV_PART_ITEMS); /* 去除按钮阴影 */
/* 设置按钮矩阵回调 */

lv_obj_add_event_cb(btnm, btnm_event_cb, LV_EVENT_VALUE_CHANGED, NULL);
}
/**************************** 第二部分 结束 ****************************/
相关推荐
12.=0.3 小时前
【stm32_2.2】【快速入门】对GPIO解析、外设的初始化和配置、细节分析GPIO
stm32·单片机·嵌入式硬件
我是标同学3 小时前
单片机IO增强电流驱动能力的三极管几种接法
单片机·嵌入式硬件
心语星愿113 小时前
STM32单片机高级篇-物联网通信之CAN通讯(学习笔记)
stm32·单片机·物联网
爱喝纯牛奶的柠檬5 小时前
【已验证】STM32+MPU6050 姿态解算 + 运动状态识别 + 四阶段摔倒检测
stm32·单片机·嵌入式硬件
戏舟的嵌入式开源笔记5 小时前
STM32 RS485读取SHT20
stm32·单片机·嵌入式硬件
LCG元7 小时前
噪声检测系统:STM32F4驱动MEMS麦克风,FFT频谱分析实战
stm32·单片机·嵌入式硬件
charlie1145141917 小时前
嵌入式C++教程实战之Linux下的单片机编程:从零搭建 STM32 开发工具链(2) —— HAL 库获取、启动文件坑位与目录搭建
linux·开发语言·c++·stm32·单片机·学习·嵌入式
v先v关v住v获v取7 小时前
多功能割草装置的结构设计8张cad+三维图+设计说明书
科技·单片机·51单片机
leiming67 小时前
信号量为什么“不占CPU“
单片机·嵌入式硬件