在学习图象处理的过程中,JPEG是我的第一个拦路虎。一直很想手写一下JPG的压缩和解压的过程,我在网上找到了一些代码或者文章,很多都是没有注释或者是解释不够清楚的。所以特地写这篇文章记录自己从无到有写一个JPEG_Encoder的过程,也能帮助其他学习图形或者音视频的童鞋。对于不想看文章的同学,这边直接上代码 https://github.com/Cheemion/JPEG_COMPRESS。 以下是JPEG的压缩流程。采样->>离散傅里叶变化->>量化->>哈夫曼压缩->>写入jpg文件. 在进行这些流程之前,必须从BMP文件中读取待压缩的图片文件。
图片引用自"Compressed Image File Formats JPEG, PNG, GIF, XBM, BMP - John Miano"[4]
1.BMP文件Format
[1]BMP文件
一个文件头BITMAPFILEHEADER,里面包含了文件的各种信息。
一个图片头BITMAPINFOHEADER,里面包含了图片信息。
一个RGBQUAD array,里面包含了像素的对应关系,比如1 代表 RGB(1,1,1)。因为我们用的都是24位图片,所以我们不会不考虑这一项。
一个Color-index,就是我们的图片的像素了。我们只考虑24位图像
BMP文件的字节是大端存储的
BMP图片的每一行像素所占的字节数必须是4字节的的整数倍
BMP数据的第一行像素存储的是图片的最后一行的数据(相当于图片在BMP中是倒置的)
2.BITMAPFILEHEADER(头文件格式)[2]头文件包含如下的字段
1 typedef struct tagBITMAPFILEHEADER { 2 WORD bfType; //文件类型 规定为'BM' 3 DWORD bfSize; //文件大小 4 WORD bfReserved1; //保留 5 WORD bfReserved2; //保留 6 DWORD bfOffBits; //数据起始地址距离首地址的位置 7 } BITMAPFILEHEADER, *LPBITMAPFILEHEADER, *PBITMAPFILEHEADER;