22. 图片部件

一、图片部件

  图片部件可用于显示图片,其图片源可以是 C 语言数组格式的文件、二进制的.bin 文件以及图标字体。图片部件要显示 BMP、JPEG 等格式的图片,则必须经过解码。图片部件的组成部分仅有一个:主体LV_PART_MAIN)。

  LVGL 官方提供了一些与图片部件相关 API。

#define lv_img_create         lv_image_create
lv_obj_t * lv_image_create(lv_obj_t * parent);                  // 创建图片部件

#define lv_img_set_src        lv_image_set_src
void lv_image_set_src(lv_obj_t * obj, const void * src);        // 设置图片源

#define lv_img_get_src        lv_image_get_src
const void * lv_image_get_src(lv_obj_t * obj);                  // 获取图片的来源

#define lv_img_set_offset_x   lv_image_set_offset_x
void lv_image_set_offset_x(lv_obj_t * obj, int32_t x);          // 设置图片的x轴偏移量

#define lv_img_get_offset_x   lv_image_get_offset_x
int32_t lv_image_get_offset_x(lv_obj_t * obj);                  // 获取图片的x轴偏移量

#define lv_img_set_offset_y   lv_image_set_offset_y
void lv_image_set_offset_y(lv_obj_t * obj, int32_t y);          // 设置图片的y轴偏移量

#define lv_img_get_offset_y   lv_image_get_offset_y
int32_t lv_image_get_offset_y(lv_obj_t * obj);                  // 获取图片的y轴偏移量

#define lv_img_set_pivot      lv_image_set_pivot
void lv_image_set_pivot(lv_obj_t * obj, int32_t x, int32_t y);  // 设置图片的旋转中心点

#define lv_img_get_pivot      lv_image_get_pivot
void lv_image_get_pivot(lv_obj_t * obj, lv_point_t * pivot);    // 获取图片的旋转中心点

#define lv_img_set_angle      lv_image_set_rotation
void lv_image_set_rotation(lv_obj_t * obj, int32_t angle);      // 设置图片的旋转角度

#define lv_img_get_angle      lv_image_get_rotation
int32_t lv_image_get_rotation(lv_obj_t * obj);                  // 获取图片的旋转角度

#define lv_img_set_zoom       lv_image_set_scale
void lv_image_set_scale(lv_obj_t * obj, uint32_t zoom);         // 设置图片的缩放

#define lv_img_get_zoom       lv_image_get_scale
int32_t lv_image_get_scale(lv_obj_t * obj)                      // 获取图片的缩放系数

#define lv_img_set_antialias  lv_image_set_antialias
void lv_image_set_antialias(lv_obj_t * obj, bool antialias);    // 启用/禁用转换的抗锯齿功能

#define lv_img_get_antialias  lv_image_get_antialias
bool lv_image_get_antialias(lv_obj_t * obj);                    // 获取转换是否开启抗锯齿功能

  我们使用 lv_img_create() 函数 创建图片部件

/**
 * @brief 创建图片部件
 * 
 * @param parent 指向父部件的指针
 * @return lv_obj_t* 指向图片部件的指针
 */
lv_obj_t * lv_img_create(lv_obj_t * parent);

  在创建完图片部件后,我们可以使用 lv_img_set_src() 函数 设置图片源

/**
 * @brief 设置图片源
 * 
 * @param obj 指向图片部件的指针
 * @param src 图片源地址
 */
void lv_img_set_src(lv_obj_t * obj, const void * src);

  图片重新着色是指将一种特定的颜色与图片的每个像素进行混合,这可以用于显示图片的不同状态,例如选中、未激活、按下等。用户需要让图片重新着色,就必须要调用以下两个函数:lv_obj_set_style_img_recolor_opa()重着色透明度)和 lv_obj_set_style_img_recolor()颜色设置)。重着色透明度的范围是 0 ~ 255,在默认的情况下,该透明度为 0完全透明),因此,如果不改变该透明度,将看不到颜色混合效果。


/**
 * @brief 设置图片重着色
 * 
 * @param obj 指向部件的指针
 * @param value 颜色值
 * @param selector 刷选器,刷选部件
 */
#define lv_obj_set_style_img_recolor             lv_obj_set_style_image_recolor
void lv_obj_set_style_image_recolor(lv_obj_t * obj, lv_color_t value, lv_style_selector_t selector);

/**
 * @brief 设置图片的透明度
 * 
 * @param obj 指向部件的指针
 * @param value 透明度值
 * @param selector 刷选器,刷选部件
 */
#define lv_obj_set_style_img_opa                 lv_obj_set_style_image_opa
void lv_obj_set_style_image_opa(lv_obj_t * obj, lv_opa_t value, lv_style_selector_t selector);

  如果把图片部件的宽度或高度设置为 LV_SIZE_CONTENT,那它的大小将会根据图片源的大小而自动变化。

  图片偏移 是指对图片部件的内部所显示的图片进行偏移,值得注意的是,如果图片偏移出了图片部件的范围,则超出的部分会显示在与偏移方向相反的一侧。设置图片偏移可调用以下函数:

/**
 * @brief 设置图片的x轴偏移量
 * 
 * @param obj 指向图片部件的指针
 * @param x x轴偏移量
 */
void lv_img_set_offset_x(lv_obj_t * obj, int32_t x);

/**
 * @brief 设置图片的y轴偏移量
 * 
 * @param obj 指向图片部件的指针
 * @param y y轴偏移量
 */
void lv_img_set_offset_y(lv_obj_t * obj, int32_t y);

  在 LVGL 中,用户可调用 lv_img_set_zoom() 函数 设置图片的缩放。如果缩放的比例设置为 256LV_IMG_ZOOM_NONE,则表示 禁用缩放;如果缩放的比例设置为 128,则表示 缩放到原来的 1/2;如果缩放的比例设置为 512,则表示 放大 2 倍,示意图如下所示:

图片缩放比例

/**
 * @brief 设置图片的缩放
 * 
 * @param obj 指向图片部件的指针
 * @param zoom 缩放的比例
 */
void lv_img_set_zoom(lv_obj_t * obj, uint32_t zoom);

  图片旋转是指图片以某一点为中心,旋转一定的角度。在默认的情况下,旋转的中心点通常就是图片的中心。用户需要 旋转图片,可调用 lv_img_set_angle() 函数进行设置。

/**
 * @brief 设置图片的旋转角度
 * 
 * @param obj 指向图片部件的指针
 * @param angle 旋转的角度值,角度值/10 = 实际的旋转角度
 */
void lv_img_set_angle(lv_obj_t * obj, int32_t angle);

  如果用户需要 改变旋转的中心点,可以调用 lv_img_set_pivot() 函数。

/**
 * @brief 设置图片的旋转中心点
 * 
 * @param obj 指向图片部件的指针
 * @param x 旋转中心点的x轴坐标
 * @param y 旋转中心点的y轴坐标
 */
void lv_img_set_pivot(lv_obj_t * obj, int32_t x, int32_t y);

二、图片源选择

2.1、C语言数组

  图片部件的图片来源分为三种:C 语言数组存储在外部的图片文件图标字体

  采用 C 语言数组 的方式来显示图片是较为简单的,整个配置流程分为以下四步:

  第一步:生成图片相关的 C 语言数组。如果用户需要将 PNG、JPG 和 BMP 格式的图片转换成 C 语言数组,可以使用官方的在线转换工具进行格式转换,该在线工具的网址为:https://lvgl.io/tools/imageconverter

  进入到该界面后,首先点击上图中 “Select image file(s)” 按钮,导入所需要的图片,导入完成后,点击图中 Color format 选项,根据需求选择颜色格式,然后点击图中 Convert 选项,选择输出格式为“C array”,最后点击“Convert”按钮即可生成 C 语言数组相关的文件(文件路径自选)。

生成图片数据

  第二步:将 C 语言数组文件添加到工程当中,然后调用 LV_IMG_DECLARE(xxx) 宏定义对图片源进行声明

  第三步:调用 lv_img_create() 函数创建图片部件

  第四步:调用 lv_img_set_src() 函数设置图片源

这里推荐使用 png 格式的图片进行转化。

2.2、外部图片源文件

  第一步:生成外部源文件(.bin)。如果用户需要将 PNG、JPG和 BMP格式的图片转换成 bin 文件,官方的在线转换工具进行格式转换提供一个 Python 编写图片格式转换的 GitHub 仓库链接。

点击进入图片格式转换的python文件

下载转换文件

  下载完代码后,我们需要安装 pypng 和 lz4 模块,这里,我们在终端中使用 pip 指令安装 pypng 和 lz4 模块。

pip install pypng
pip install lz4

  如果由于网络原因导致下载出错,我们可以在后面加上 -i 镜像源 选项加速下载。

  安装完模块后,我们在终端中运行 Python 文件。

LVGLImage.py [-h] [–ofmt {C,BIN,PNG}] [–cf {L8,I1,I2,I4,I8,A1,A2,A4,A8,ARGB8888,XRGB8888,RGB565,RGB565A8,ARGB8565,RGB888,AUTO}] [–compress {NONE,RLE,LZ4}] [–align [byte]] [–background [color]] [-o OUTPUT] [-v] input
  • -h--help: 显示使用脚本的帮助信息。
  • –ofmt {C,BIN,PNG}: 指定处理后图像的输出格式。
    • C: 作为 C 源代码(数组)输出。
    • BIN: 作为二进制文件输出。
    • PNG: 作为 PNG 图像输出(可能用于调试)。
  • –cf {L8,I1,I2,I4,I8,A1,A2,A4,A8,ARGB8888,XRGB8888,RGB565,RGB565A8,ARGB8565,RGB888,AUTO}:选择图像转换的颜色格式。
    • 选项包括不同位深度和色彩模式,如 L8(8 位灰度)、I1(1 位索引色)、ARGB8888(32 位真彩色带透明)、RGB565(16 位色彩),以及 AUTO 自动选择合适的格式。
  • –compress {NONE,RLE,LZ4}:确定用于图像数据的压缩方法。
    • NONE: 无压缩。
    • RLE: 行程长度编码,对有大块单一颜色区域的图像效果好。
    • LZ4: LZ4 压缩算法,平衡了压缩速度和压缩率。
  • –align [字节]:指定输出数据对齐到指定的字节边界,某些嵌入式系统对数据对齐有特定要求。
  • –background [color]:设置图像填充或转换为非透明格式时透明像素的背景色。
  • -o 输出文件:指定输出文件路径,如果不指定,默认输出在 output 文件夹下的同名 bin 文件。
  • -v:启用详细模式,在处理过程中提供更多信息。
  • input:输入文件,需要被处理的输入图像文件路径。

  这里,我们使用如下命令运行 Python 脚本生成 bin 文件。

python LVGLImage.py --ofmt BIN --cf RGB565 --align 1 --compress NONE image.png

  第二步:使能 LVGL 的文件系统

  第三步:拷贝 bin 文件到指定的 SD 卡目录中

  第四步:调用 lv_img_create() 函数创建图片部件

  第四步:调用 lv_img_set_src() 函数设置图片源

如果 GitHub 链接打不开,可以下载 Watt Toolkit(原名 Steam++),然后选择平台加速,勾选上 GitHub 进行加速。

这里推荐使用 png 格式的图片进行转化。

三、实验例程

#include "lvgl.h"
#include "lv_port_disp_template.h"
#include "lv_port_indev_template.h"

#include "image.c"

int main(void)
{
    LV_IMG_DECLARE(image);                                                      // 声明图片源

    HAL_Init();
    System_Clock_Init(8, 336, 2, 7);
    Delay_Init(168);

    SPI_Simulate_Init();
    // SRAM_Init();
    TIM_Base_Init(&g_tim6_handle, TIM6, 83, 999);
    __HAL_TIM_CLEAR_IT(&g_tim6_handle, TIM_IT_UPDATE);                          // 清除更新中断标志位
    HAL_TIM_Base_Start_IT(&g_tim6_handle);                                      // 使能更新中断,并启动计数器

    lv_init();
    lv_port_disp_init();
    lv_port_indev_init();

    // 测试代码
    lv_obj_t *img = lv_img_create(lv_scr_act());                                // 创建图片部件
    lv_img_set_src(img, &image);                                                // 设置图片部件的图片

    lv_obj_center(img);                                                         // 设置图片部件居中对齐
    lv_obj_set_style_img_recolor(img, lv_color_hex(0xFF1493), LV_PART_MAIN);    // 设置图片重新着色
    lv_obj_set_style_img_recolor_opa(img, 150, LV_PART_MAIN);                   // 设置图片的透明度

    lv_obj_update_layout(img);                                                  // 更新图片布局信息
    lv_img_set_pivot(img, 0, 0);                                                // 设置图片中心点

    lv_img_set_zoom(img, 300);                                                  // 设置图片所防止
    lv_img_set_angle(img, 300);                                                 // 设置图片旋转

    while (1)
    {
        lv_timer_handler();
        Delay_ms(5);
    }
  
    return 0;
}

  生成的 C 语言数组名字一般与文件名一致。

生成的图片数组名

posted @ 2024-08-07 21:24  星光映梦  阅读(24)  评论(0编辑  收藏  举报