本帖最后由 zongyu123 于 2014-12-17 19:25 编辑
此图为原图
此图为解码后显示到LCD的图。
硬件:STM32F072的CPU。解码用的是ChaN的解码,原子迷你版的代码。结果出来就是这样子。
差距为什么这么大呢?求大神指点!谢谢。
代码如下:
/********************COPYRIGHT (C) 2013 Creator Lab of embedded systems *******************************
* 文件名 :main.c
* 描述 :结合FATFS文件系统与TjpgDec图片解码系统,实现最基本的图片显示功能
* 实验平台:MINI开发板,MINI自带的2.4寸TFTLCD屏幕
* 库版本 :ST3.5.0
* 调试方法:在SD卡中存储短文件名的JPG图片,图片直接放入SD卡中,不需要建立文件夹。
程序烧进板子以后,插上SD卡,然后复位一下板子,就可以在2.4寸的TFTLCD上
看到存储进SD卡中的图片了。
* 备注说明:图片应使用短文件名(8.3格式),且图片类型必须是JPG/JPEG类型,且图片须
为240像素宽度的图片,图片的高度如果过高,请不要超过320像素太多,不然图
片显示不完全。
********************************************************************************************************/
#include "takepic.h"
#include "stm32f0xx.h"
#include "jpeg_lcd.h"
//全局变量定义
uint8_t res,Counts_A,SiJi;
uint8_t fname_temp[32];
//有关文件的全局变量
FIL fsrc,fdst; //文件结构体
//FATFS fs; //文件系统工作区注册信息结构体
//UINT br,bw; //文件读写字节数
//DIR dir; //目录结构体
FILINFO fileInfo; //文件信息结构体,包含文件名称及修改日期等信息,在读取目录的时候可以得到这些信息
/*--------------------------------------------------------------------
* 函数名:main
* 描述 :主函数
* 输入 :无
* 输出 :无
---------------------------------------------------------------------*/
int main(void)
{
system_init();
while(1)
{
res= f_opendir(&dir,"0:");//读取文件夹信息,即打开一级目录
if(res==FR_OK) //打开目录成功,则开始循环显示图片
{
while(1)
{
res =f_readdir(&dir,&fileInfo);//读取目录中其中一个目录项的信息,即从目录中读取一个文件的信息
if(res!=0||fileInfo.fname[0]==0)break;//目录读取完,或者目录读取出现错误,则跳出循环,重新读取目录
if(fileInfo.fname[0]=='.')continue ;//文件名中的第一个字符是个点,则忽略这个文件,读取下一个文件
strcpy(fname_temp,"0:/");
strcat(fname_temp,fileInfo.fname);//处理二级目录的名称,即图片文件的路径:“0:/fileInfo.fname”,也是文件名
res=STM32_JPEG_DISPLAY(&fsrc,fname_temp);
// delay_ms(55555);
// LCD_Set_Window(0,0,319,239);
// LCD_Fill(0,0,319,239,WHITE);
}
}
}
}
/******************** COPYRIGHT (C) 2013 Creator Lab of embedded systems *******************************/
/********************COPYRIGHT (C) 2013 Creator Lab of embedded systems *******************************
* 文件名 :main.c
* 描述 :
* 实验平台:MINI开发板
* 库版本 :ST3.5.0
* 调试方法:
********************************************************************************************************/
#include "jpeg_lcd.h"
UINT Height_Of_Jpeg=0;//记录图片高度的全局变量
BYTE Buff[4096] __attribute__ ((aligned(4))); //定义全局数组变量,作为输入的缓冲区,强制4字节对齐
/*********************************************************************************************
函数名称: STM32_in_func
函数功能: 用户自定义的用于输入文件数据的功能函数
入口参数: 见函数头
出口参数: 读取或者删除的数据量
全局变量: 无
备注说明: 本函数在解码准备工作中用于读取文件头信息
*********************************************************************************************/
UINT STM32_in_func (
JDEC* jd, /*储存待解码的对象信息的结构体 */
BYTE* buff, /* 输入数据缓冲区 (NULL:删除数据) */
UINT nd /*需要从输入数据流读出/删除的数据量*/
)
{
UINT rb;
FIL * dev = (FIL *)jd->device; /* 待解码的文件的信息,使用FATFS中的FIL结构类型进行定义 */
if (buff) /*读取数据有效,开始读取数据 */
{
f_read(dev, buff, nd, &rb); //调用FATFS的f_read函数,用于把jpeg文件的数据读取出来
return rb; /* 返回读取到的字节数目*/
}
else
{
return (f_lseek(dev, f_tell(dev) + nd) == FR_OK) ? nd : 0;/* 重新定位数据点,相当于删除之前的n字节数据 */
}
}
/*********************************************************************************************
函数名称: STM32_out_func
函数功能: 用户自定义的用于输出RGB位图数据的功能函数
入口参数: 见函数头
出口参数: 1:令解码函数继续执行
全局变量: 无
备注说明: 无
*********************************************************************************************/
UINT STM32_out_func (
JDEC* jd, /*储存待解码的对象信息的结构体*/
void* bitmap, /* 指向等待输出的RGB位图数据 的指针*/
JRECT* rect /* 等待输出的矩形图像的参数 */
)
{
jd = jd; /* 说明:输出函数中JDEC结构体没有用到 */
STM32_Display(rect->left, rect->right, rect->top, rect->bottom, (uint16_t*)bitmap);
return 1; /*返回1,使解码工作继续执行 */
}
/*********************************************************************************************
函数名称: STM32_Display
函数功能: 在TFTLCD屏幕上显示图片
入口参数: 见函数头
出口参数: 无
全局变量: 无
备注说明: 无
*********************************************************************************************/
void STM32_Display(
int left, /*图片左方起始点,即一行的起始点 */
int right, /*图片右方的结束点,即一行的结束点*/
int top, /* 图片上方的起始点,即一列的起始点 */
int bottom, /*图像下方的结束点,即一列的结束点 */
const uint16_t * RGB_Data_Pointer /* 待显示的图像数据,RGB格式*/
)
{
int height_jpeg=0,width_jpeg=0,x_width=0,lines_change=0;
uint32_t width_clip=0; //变量一定要初始化,不然会遇到意想不到的麻烦
if (left > right || top > bottom)
{
return; //起始点错误,不执行显示功能
}
if (left > Mask_Right || right < Mask_Left || top > Mask_Bottom || bottom < Mask_Top)
{
return; // 图像超出屏幕的显示范围,则不执行显示功能
}
//开始对图片的宽度和高度进行裁剪和修改
height_jpeg = bottom - top + 1; // 计算图像的高度
width_jpeg = right - left + 1; //计算图像的宽度
if (top < Mask_Top) // 裁减掉在图片顶部超出显示范围的部分数据
{
RGB_Data_Pointer += width_jpeg * (Mask_Top- top); //计算出需要删除的数据量
height_jpeg-= Mask_Top- top;
top = Mask_Top;
}
if (bottom > Mask_Bottom) // 裁减掉在图片底部超出显示范围的部分数据
{
height_jpeg-= bottom - Mask_Bottom;
bottom = Mask_Bottom;
}
if (left < Mask_Left) // 裁减掉在图片左边超出显示范围的部分数据
{
RGB_Data_Pointer += Mask_Left - left; //水平方向的数据指针右移
width_jpeg -= Mask_Left - left; //水平宽度减小
width_clip+= Mask_Left - left;//记录裁减掉的宽度
left = Mask_Left;
}
if (right > Mask_Right) // 裁减掉在图片右边超出显示范围的部分数据
{
width_jpeg -= right - Mask_Right;
width_clip+=right - Mask_Right;
right = Mask_Right;
}
if(Height_Of_Jpeg<TFTLCD_HEIGHT)//当图片的高度小于LCD显示屏的高度时,使图片能够居中显示
lines_change=(TFTLCD_HEIGHT-Height_Of_Jpeg)/2;//调整图片高度
//设置TFTLCD显示屏的显示参数
LCD_SetWindow(left,top+lines_change,right,bottom+lines_change);//在此处加入设置TFTLCD屏幕显示图片的窗口的功能函数,设置矩形显示区域
LCD_WR_REG_DATA(R32,left);
LCD_WR_REG_DATA(R33,top+lines_change); //在此处加入设置TFTLCD光标位置的功能函数,把像素点定位到起始点(左上角)
//向TFTLCD显示屏控制器写入数据
LCD_WR_REG(R34); //在此处加入开始写入TFTLCD的GRAM功能的函数,
//根据TFTLCD的控制器的特性,接下来可以连续地向上面设置好的矩形区域丢数据
while(height_jpeg--) //控制显示区域的高度
{
x_width=width_jpeg;
//在此处加入向TFTLCD写入数据的功能函数,在水平方向输出矩形区域一行的数据
while(x_width--) LCD_WR_DATA(*RGB_Data_Pointer++);
//图片的水平方向的调整,去除裁减掉的像素数据
RGB_Data_Pointer+= width_clip;
}
}
/*********************************************************************************************
函数名称: STM32_JPEG_DISPLAY
函数功能: 在主函数中调用的JPEG图片显示函数
入口参数: f_Jpeg:指向JPEG图片文件的指针,其值不定
filename:JPEG图片文件的名称
出口参数: 0:函数执行成功
其他:函数执行失败
全局变量: 无
备注说明: 无
*********************************************************************************************/
uint32_t STM32_JPEG_DISPLAY(FIL* f_Jpeg,const char* filename)
{
FRESULT Res_FatFs;//FATFS系统函数返回值
JDEC jd; /* 待解码的对象的信息记录表 */
JRESULT Res_TjpgDec; // TjpgDec系统函数返回值
BYTE scale; //图像输出比例
//使用FATFS的f_open函数以读方式打开文件
Res_FatFs = f_open(f_Jpeg,filename,FA_READ);
if(Res_FatFs!= FR_OK) //打开文件失败,返回
{
delay_ms(1000);
f_close(f_Jpeg);
return Res_FatFs;
}
//执行解码的准备工作,调用TjpgDec模块的jd_prepare函数
Res_TjpgDec = jd_prepare(&jd,STM32_in_func,Buff,sizeof(Buff),f_Jpeg);
Height_Of_Jpeg=jd.height;//保存图片的高度数据
if (Res_TjpgDec == JDR_OK)
{
for (scale = 0; scale < 3; scale++) //确定输出图像的比例因子
{
//if ((jd.width >> scale) <= 240 && (jd.height >> scale) <= 320) break;
if ((jd.width >> scale) <= lcddev.width && (jd.height >> scale) <= lcddev.height) break;
}
if(scale)scale--; //处理标准240宽度的图片时,对于高度过高的情况进行降低一级比例的处理
//执行解码工作,调用TjpgDec模块的jd_decomp函数
Res_TjpgDec = jd_decomp(&jd, STM32_out_func, scale);
}
else //解码的准备工作失败,关闭文件,返回
{
delay_ms(1000);
f_close(f_Jpeg);
return Res_TjpgDec; //返回错误代码
}
//解码工作执行成功,返回0
f_close(f_Jpeg);
return 0;
}
/******************** COPYRIGHT (C) 2013 Creator Lab of embedded systems *******************************/
/********************COPYRIGHT (C) 2013 Creator Lab of embedded systems *******************************
* 文件名 :main.c
* 调试方法:
********************************************************************************************************/
#include <stdio.h>
#include "stm32f0xx.h"
#include "uart2.h"
#include "delay.h"
#include "ff.h"
#include "tjpgd.h"
#include "lcd.h"
typedef struct {
FIL *fp; /*指向输入文件的指针(JPEG文件)*/ //
BYTE *fbuf; /*指向输出缓冲区的指针*///
UINT wfbuf; /*输出缓冲区的宽度[pix] *///
} IODEV;
//有关TFTLCD的尺寸的定义
#define TFTLCD_WIDTH 240 //2.4寸TFTLCD屏幕的宽度
#define TFTLCD_HEIGHT 320 //2.4寸TFTLCD屏幕的高度
static int Mask_Left = 0; //TFTLCD最左边的起始点
static int Mask_Right = TFTLCD_WIDTH - 1; //TFTLCD最右边的结束点
static int Mask_Top = 0; //TFTLCD最上方的起始点
static int Mask_Bottom= TFTLCD_HEIGHT - 1; //TFTLCD最下方的结束点
//函数声明
UINT STM32_in_func ( JDEC* jd,BYTE* buff,UINT nd) ;
UINT STM32_out_func (JDEC* jd,void* bitmap,JRECT* rect);
void STM32_Display( int left,int right,int top,int bottom,const uint16_t * RGB_Data_Pointer);
uint32_t STM32_JPEG_DISPLAY(FIL* f_Jpeg,const char* filename);
/******************** COPYRIGHT (C) 2013 Creator Lab of embedded systems *******************************/
|
|