内容介绍
内容介绍
一、任务思路。
第十一期funpack活动,我完成的是第二个任务:读取SD卡中预先存入的图像,显示在屏幕上(OLED或LCD)。总体上思路是,单片机读取FAT格式的SD卡内的图片文件,解码,并通过SPI接口的彩屏显示出来。
二、代码解释
/* set BOD VBAT level to 1.65V */
POWER_SetBodVbatLevel(kPOWER_BodVbatLevel1650mv, kPOWER_BodHystLevel50mv, false);
CLOCK_EnableClock(kCLOCK_InputMux);
/* attach 12 MHz clock to FLEXCOMM0 (debug console) 将12MHz连接到FLEXCOMM0 */
CLOCK_AttachClk(BOARD_DEBUG_UART_CLK_ATTACH);
BOARD_InitPins(); // 开发板初始化引脚
BOARD_BootClockPLL150M(); // 开发板设置时钟为PLL 150MHz
BOARD_InitDebugConsole(); // 初始化调试控制台
代码片段1:初始化板卡基本外设。
LCD_Init();
LCD_Clear(BLUE);
if (sdcardWaitCardInsert() != kStatus_Success) // 检测卡插入 非独立引脚检测
{
return -1;
}
if (f_mount(&g_fileSystem, driverNumberBuffer, 0U)) // 挂载FatFs
{
PRINTF("Mount volume failed.\r\n");
return -1;
}
error = f_chdrive((char const *)&driverNumberBuffer[0U]); // 设置逻辑驱动器号 "2:/"
if (error)
{
PRINTF("Change drive failed.\r\n");
return -1;
}
代码片段2:初始化LCD彩屏并刷蓝色;初始化SD卡及FATFS。
if ((error = f_opendir(&directory, "2:/320240/bmp")) != FR_OK)
{
PRINTF("Read Directory Failed, Result = %d\r\n", (int)error);
}
PRINTF("Read Directory Success\r\n", (int)error);
while (true)
{
error = f_readdir(&directory, &fileInformation);
if (error != FR_OK || fileInformation.fname[0] == '\0')
break;
if (fileInformation.fattrib & AM_DIR)
{
PRINTF("Read Directory, Name: %s\r\n", fileInformation.fname);
}
else
{
PRINTF("Read File, Name: %s\r\n", fileInformation.fname);
LCD_ShowPicture(fileInformation.fname);
for (__IO uint32_t c = 0; c < 60000000; c++) { ; }
}
}
f_closedir(&directory);
代码片段3:遍历图片文件夹,并通过彩屏显示出来。
uint16_t rgb_24bit_to_16bit(const char *pColor)
{
uint16_t color = 0;
color = ((pColor[2] >> 3) << 11) | ((pColor[1] >> 2) << 5) | (pColor[0] >> 3);
return color;
}
void LCD_ShowPicture(const char *fileName)
{
FRESULT fr;
UINT br;
char fullPath[30] = "2:/320240/bmp/";
char buffer[240*3];
strcat(fullPath, fileName);
// 打开文件
fr = f_open(&g_fileObject, fullPath, FA_READ);
if (fr != FR_OK)
{
PRINTF("Read file %s Failed\r\n", fullPath);
return;
}
// 读取BMP文件格式标识
f_read(&g_fileObject, buffer, 2, &br); // ptr -> 2
if (strncmp(buffer, "BM", 2) != 0)
{
PRINTF("File Format Error\r\n");
goto FUNCTION_END;
}
PRINTF("File Format BMP\r\n");
// 获取位图数据偏移量
f_read(&g_fileObject, buffer, 12, &br); // 0x0E - 0x02 = 12, ptr -> 0x0E
uint32_t bitMapOffset = (buffer[11] << 24) | (buffer[10] << 16) | (buffer[9] << 8) | buffer[8];
f_read(&g_fileObject, buffer, bitMapOffset - 14, &br); // ptr -> bitMapAddr
PRINTF("BitMapOffset = %u\r\n", bitMapOffset);
for (uint32_t i = 0; i < 320; i++)
{
if ((fr = f_read(&g_fileObject, buffer, 240*3, &br)) != FR_OK) // One Line Data
{
PRINTF("Read File Failed\r\n");
goto FUNCTION_END;
}
// 画点
// for (uint32_t j = 0; j < 240; j++)
// {
// POINT_COLOR = rgb_24bit_to_16bit(buffer+j*3);
// LCD_DrawPoint(j, 320 - i - 1);
// }
// 画线
LCD_SetWindows(0, 320 - i - 1, 239, 320 - i - 1);
LCD_CS_CLR;
LCD_RS_SET;
for (uint32_t j = 0; j < 240; j++)
{
uint16_t color = rgb_24bit_to_16bit(buffer+j*3);
SPIv_WriteData(color >> 8);
SPIv_WriteData(color & 0xFF);
}
LCD_CS_SET;
}
FUNCTION_END:
f_close(&g_fileObject);
代码片段4:读取图片文件,解码,LCD彩屏通过打线方式显示出来。
三、效果展示
图1:显示汽车图片
图2:显示熊猫图片
四、感想
现在单片机的功能相较于几年前有了大幅度的提升,以前可能需要一个昂贵板卡才能实现的功能,现在放一个单片机就可以完成。希望硬禾能够多推广写性能强劲的单片机。
附件下载
LCD_SD_FATFS_PICTURE.7z
源代码
团队介绍
嵌入式工程师-陈海 来自山东
团队成员
Snapdragon
评论
0 / 100
查看更多
猜你喜欢
LPC55S69-EVK读取SD卡BMP图片并显示到OLED(Funpack第11期)本次设计使用LPC55S69-EVK开发板,实现了读取SD卡上BMP格式的图片,并显示到OLED单色屏。开发板依次读取3张图片,即NXP、DigiKey、硬禾学堂等3个logo,进行循环显示。
chinaking
1334
Funpack第11期-LPC55S69-SD卡JPEG图片浏览器本项目实现了Funpack第11期的任务二,即使用LPC55S69开发板读取SD卡上的图片文件并显示在屏幕上。
Geralt
1392
Funpack第11期-LPC55S69 基于SD卡的BMP图像LCD显示Funpack第11期活动,任务二将预先存储在SD卡中的图片显示在LCD当中
ZeBiner
1127