STM32F429IGT6驱动 RGB888 LCD —— LTDC+DMA2D
参考文章:https://www.cnblogs.com/mickey-double/p/14680844.html
https://blog.51cto.com/u_16099263/10773973
一、配置stm32cubemx
1、配置sys

2、配置RCC时钟

配置芯片时钟,并根据屏幕参数,配置LCD的时钟频率
我的屏幕参数推荐值为9M,这里我设置成9M。


3、配置DMA2D
这里只修改了RGB的模式,根据屏幕支持的格式选择即可。

注意:记得要开启DMA2D的中断

4、配置LTDC
按需选择RGB模式

修改相关参数,下面展示我自己屏幕的参数修改。


数据的存储地址一定要仔细仔细再仔细,一般芯片的内部RAM不够存储,这么大的屏幕数据。
屏幕数据 = W * H * (RGB位数)= 480 * 272 * 3 = 391680 ≈ 382k

注:stm32cubemx配置LTDC的时候,要注意RGB24位的引脚,跟原理图不匹配的引脚需要自己手动更改。stm32cubemx提供的不一定完全对上。
接下来就可以生成工程文件了!!
二、快速体验
工程创建完成后,可以使用固定的图像数据,进行测试,下面是具体流程。
1、找一张比例跟屏幕一样的图片

2、图像格式转化为bmp
推荐网页:https://z.pcgeshi.com/image-format-convert

3、制作图像数据数组
我使用的是正点原子软件包里的 “Image2Lcd 2.9(破解版)”。按保存后即可获取相关的.c文件。


4、修改LTDC数据地址
将c文件的数组复制到工程内

在 void MX_LTDC_Init(void)函数下,修改相关地址:

三、实现在屏幕上画点
正所谓只要能画点,那么画线、画图、写字都没有问题!!!
个人理解:LTDC就好比将整个屏幕的数据都保存在了一个巨大的数组中,一行接一行。只需要修改某个点的数据内容,那么屏幕上也会发生相应的变化。
#define LTDC_WIDTH 480
#define LTDC_HEIGHT 272
#define LTDC_TYPE 3 // 每个像素点占字节数
uint8_t ltdc_layer0[LTDC_WIDTH * LTDC_HEIGHT * LTDC_TYPE] = {0};/*__attribute__((at(LAYER0_ADDR)))*/ //定义最大屏分辨率时,LCD所需的帧缓存数组大小
按照我的屏幕来展示,480*272,rgb888,每个坐标占3个字节,即相关坐标的起始位置则为
LTDC_TYPE * ( LTDC_WIDTH * y + x )
往后顺延三个字节表示RGB,因为有大小端问题,颜色的修改可能会镜像一下,即:
ltdc_layer0[LTDC_TYPE * ( LTDC_WIDTH * y + x ) + 0] = color >> 0; // R
ltdc_layer0[LTDC_TYPE * ( LTDC_WIDTH * y + x ) + 1] = color >> 8; // G
ltdc_layer0[LTDC_TYPE * ( LTDC_WIDTH * y + x ) + 2] = color >> 16; // B
完整代码:
当前代码不可直接运行,因为单片机没有这么大空间的ram存储数组,可修改宏定义来进行测试使用,修改后出现部分花屏是正常的。
添加__attribute__这个函数,可以修改存储地址到外部sdram去,我也没尝试过。。。。。
#define LTDC_WIDTH 480
#define LTDC_HEIGHT 100
#define LTDC_TYPE 3 // 每个像素点占字节数
uint8_t ltdc_layer0[LTDC_WIDTH * LTDC_HEIGHT * LTDC_TYPE] = {0};/*__attribute__((at(LAYER0_ADDR)))*/ //定义最大屏分辨率时,LCD所需的帧缓存数组大小
/***************************************************************************************
* @brief 画点
* @input x,y:坐标 color:颜色 (低位在前,需要翻转 rgb->bgr)
* @return
***************************************************************************************/
void LCD_DrawPoint(uint16_t x, uint16_t y, uint32_t color)
{
// *(uint16_t*)((uint32_t)ltdc_layer0[0] + 2 * (LTDC_WIDTH * y + x)) = color;
ltdc_layer0[LTDC_TYPE * ( LTDC_WIDTH * y + x ) + 0] = color >> 0; // R
ltdc_layer0[LTDC_TYPE * ( LTDC_WIDTH * y + x ) + 1] = color >> 8; // G
ltdc_layer0[LTDC_TYPE * ( LTDC_WIDTH * y + x ) + 2] = color >> 16; // B
}
更多推荐



所有评论(0)