LVGL2.zip
(5.27 MB)
(下载次数: 19, 2022-12-26 09:59 上传)
LVGL1.zip
(20 MB)
(下载次数: 23, 2022-12-26 09:59 上传)
分别改名字为LVGL.zip.001和LVGL.zip.00解压
打开projectsn32g45x_EVALexamplesUSARTPrintfMDK-
ARMPrintf.uvprojx即可。
前言
前一篇我们完成了TFT的驱动,这一篇我们就可以开始LVGL的移植了。
参考《【国民技术N32项目移植】驱动SPI接口TFT屏》
https://bbs.elecfans.com/jishu_2325154_1_1.html
准备
git clone https://github.com/lvgl/lvgl.git
下载代码到Src目录下
移植过程
配置文件lv_conf.h
复制
lvgl/lv_conf_template.h
改名字为lv_conf.h
将#if 0改为1,即直接#include “lv_conf.h”
将lv_conf.h添加到工程头文件包含路径。
底层驱动模板下有对应的模板文件,分别是显示,文件系统和输入设备的驱动模板。
lv_port_disp_template.c/h
lv_port_fs_template.c/h
lv_port_indev_template.c/h
暂时只移植显示,所以复制lv_port_disp_template.c/h到src下
改名字为
lv_port_disp.c/h
将.c和.h里面的#if 0改为1
.c中#include "lv_port_disp_template.h"改为#include "lv_port_disp.h"
HAL层模板lvgl/src/hal
下
我们直接使用不修改
lv_hal_disp.c/h
lv_hal_indev.c/h
lv_hal_tick.c/h
lv_hal.h
添加文件如下
srccore下所有文件
srcdraw下所有文件和sw子文件夹
srcfont下所有文件
srchal下所有文件
srclayouts所有子文件夹文件
srclibs所有子文件夹文件
srcmisc下所有文件
srcothers所有子文件夹文件
srcthemes下所有文件和所有子文件夹
srcwidgets所有子文件夹文件
需要移植的代码移植比较简单,直接使用底层驱动模板根据实际实现修改lv_port_disp.c,并配置lv_conf.h即可。
头文件包含模式需要在工程中定义宏
#define LV_LVGL_H_INCLUDE_SIMPLE 1
这样需要将lvgl.h所在路径配置为工程头文件包含路径。
代码中直接#include "lvgl.h"即可
否则是#include "../../lvgl.h"
分辨率配置lv_port_disp.h中
#define MY_DISP_HOR_RES 240
#define MY_DISP_VER_RES 240
初始化lv_port_disp.c中
实现disp_init
即调用自己的初始化函数,如果在其他地方初始化了,该函数实现为空函数体即可。
缓冲区lv_port_disp.c中
lv_port_disp_init
注释掉/* Example for 2) */
/* Example for 3) also set disp_drv.full_refresh = 1 below*/对应的代码
使用/* Example for 1) */
lv_port_disp_init
该函数调用disp_init实现初始化
刷新显示lv_port_disp.c中包含#include "lcd.h"
disp_flush
/*put_px(x, y, color_p)/改为
lcd_draw_point(x,y,color_p->full);
颜色深度lv_conf.h中
#define LV_COLOR_DEPTH 16
typedef LV_CONCAT3(lv_color, LV_COLOR_DEPTH, _t) lv_color_t;
则lv_color_t类型为lv_color_16_t
堆大小配置lv_conf.h中
#define LV_MEM_SIZE (10U * 1024U) /* [bytes] */
按需提供堆大小,过大可能编译不过,过小可能影响创建对象。
时间滴答如果在lv_conf.h中指定LV_TICK_CUSTOM为1则需要用户提供相关接口
LV_TICK_CUSTOM_SYS_TIME_EXPR用于获取当前毫秒值
和头文件LV_TICK_CUSTOM_INCLUDE
否则使用lvgl/src/hal/lv_hal_tick.c的实现
每隔x毫秒调用lv_tick_inc(x),使用内部计数器定时。
周期调用lv_tick_inc更新时间滴答,比如专门硬件定时器回调中调用,如果1ms周期则
lv_tick_inc(1);
这里使用systick
main.c中#include "lvgl.h"
/* PA2 */
RCC_EnableAPB2PeriphClk(RCC_APB2_PERIPH_GPIOA,ENABLE);
GPIO_InitStructure.Pin = GPIO_PIN_2;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_InitPeripheral(GPIOA, &GPIO_InitStructure);
GPIO_SetBits(GPIOA, GPIO_PIN_2);
void SysTick_Handler(void)
{
lv_tick_inc(1);
if(GPIO_ReadOutputDataBit(GPIOA, GPIO_PIN_2))
{
GPIO_ResetBits(GPIOA, GPIO_PIN_2);
}
else
{
GPIO_SetBits(GPIOA, GPIO_PIN_2);
}
}
注释掉n32g45x_it.c中的
/**
*
@Brief This function handles SysTick Handler.
*/
//void SysTick_Handler(void)
//{
//}
初始化
SysTick_Config(144000);
NVIC_EnableIRQ(SysTick_IRQn);
以上使用PA2在sysyick中断中翻转,测试定时是否正确
逻辑分析仪测试PA2看到非常准确
日志lv_conf.h中
#define LV_USE_LOG 0
改为
#define LV_USE_LOG 1使能日志
#define LV_LOG_LEVEL LV_LOG_LEVEL_TRACE设置日志,等级
LV_LOG_LEVEL_TRACE表示所有信息都打印
如果#define LV_LOG_PRINTF 0
则需要调用设置lv_log_register_print_cb()打印函数
否则使用printf
#define LV_LOG_USE_TIMESTAMP 1
使能打印时间
其他的模块打印使能
字体配置lv_conf.h
中按需使能对应的字体,如果有对应编译错误信息根据提示使能
#define LV_FONT_MONTSERRAT_12 1
#define LV_FONT_MONTSERRAT_14 1
#define LV_FONT_MONTSERRAT_16 1
工程配置使用gnu11
如果提示.ObjectsPrintf.axf: Error: L6218E: Undefined symbol __aeabi_assert (referred from qrcodegen.o).
则可以不勾选Use MicroLIB库
或者勾选了则自己实现
__aeabi_assert函数
__attribute__((weak))
void abort(void) {
for (;;);
}
__attribute__((weak,noreturn))
void __aeabi_assert (const char *expr, const char *file, int line) {
char str[12], *p;
fputs("*** assertion failed: ", stderr);
fputs(expr, stderr);
fputs(", file ", stderr);
fputs(file, stderr);
fputs(", line ", stderr);
p = str + sizeof(str);
*--p = '