BMP图像的读写(8位和24位)
8位、24位、32位图像数据转换
![8位、24位、32位图像数据转换](https://img.taocdn.com/s3/m/2a56517430b765ce0508763231126edb6f1a7605.png)
8位、24位、32位图像数据转换最近调⽤⼀个⼈体检测算法,算法要求输⼊的是图⽚的BGR数据,但是拿到的数据是32位Argb数据,算法⽆法正确进⾏⼈体检测,从⽹上百度⽂库中搜到⼀个C#代码,可以进⾏转换。
⽹上的代码有点乱,整理了⼀下,记录留存。
整理后的代码如下:1class BitmapConvertHelp2 {3struct BitmapFileHeader4 {5//位图⽂件头6public UInt16 bfType;7public UInt32 bfSize;8public UInt16 bfReserved1;9public UInt16 bfReserved2;10public UInt32 bfOffBits;11 }1213struct BitmapInfoHeader14 {15//位图信息头16public UInt32 biSize;17public UInt32 biWidth;18public UInt32 biHeight;19public UInt16 biPlanes;20public UInt16 biBitCount;21public UInt32 biCompression;22public UInt32 biSizeImage;23public UInt32 biXPelsPerMeter;24public UInt32 biYPelsPerMeter;25public UInt32 biClrUsed;26public UInt32 biClrImportant;27 }2829struct RGBQUAD30 {31//位图调⾊板项32public byte rgbBlue;33public byte rgbGreen;34public byte rgbRed;35public byte rgbReserved;36 }3738private string filepath = null;//需打开的位图的路径39private string savepath = null;//转换后位图的保存路径40private BitmapFileHeader bfh;41private BitmapInfoHeader bih;4243private void Save8Bits(Bitmap bmp)44 {45//为位图⽂件头赋值46 bfh.bfOffBits = 1078;47 bfh.bfReserved1 = 0;48 bfh.bfReserved2 = 0;49 bfh.bfSize = 14;50 bfh.bfType = 19778;51//为位图信息头赋值52 bih.biBitCount = 8;53 bih.biClrImportant = 0;54 bih.biClrUsed = 0;55 bih.biCompression = 0;56 bih.biHeight = (uint)bmp.Height;57 bih.biPlanes = 1;58 bih.biSize = 40;59 bih.biSizeImage = (uint)(bmp.Height * ((bmp.Width * 8 + 31) / 32 * 4));60 bih.biWidth = (uint)bmp.Width;61 bih.biXPelsPerMeter = 0;62 bih.biYPelsPerMeter = 0;63//构造256⾊的调⾊板,⾮索引图64 RGBQUAD[] pal = new RGBQUAD[256];65for (int i = 0; i < 256; i++)66 {67 pal[i].rgbBlue = (byte)i;68 pal[i].rgbGreen = (byte)i;69 pal[i].rgbRed = (byte)i;70 pal[i].rgbReserved = 0;71 }72 FileInfo f = new FileInfo(savepath);73using (BinaryWriter bw = new BinaryWriter(f.OpenWrite()))74 {75//写⼊⽂件头76 bw.Write(bfh.bfType);77 bw.Write(bfh.bfSize);78 bw.Write(bfh.bfReserved1);79 bw.Write(bfh.bfReserved2);80 bw.Write(bfh.bfOffBits);81//写⼊信息头82 bw.Write(bih.biSize);83 bw.Write(bih.biWidth);84 bw.Write(bih.biHeight);85 bw.Write(bih.biPlanes);86 bw.Write(bih.biBitCount);87 bw.Write(bih.biCompression);88 bw.Write(bih.biSizeImage);89 bw.Write(bih.biXPelsPerMeter);90 bw.Write(bih.biYPelsPerMeter);91 bw.Write(bih.biClrUsed);92 bw.Write(bih.biClrImportant);93//写⼊调⾊板94for (int i = 0; i < 256; i++)95 {96 bw.Write(pal[i].rgbBlue);97 bw.Write(pal[i].rgbGreen);98 bw.Write(pal[i].rgbRed);99 bw.Write(pal[i].rgbReserved);100 }101//位图上下翻转102 bmp.RotateFlip(RotateFlipType.Rotate180FlipX);103 BitmapData data = bmp.LockBits(new Rectangle(0, 0, bmp.Width, bmp.Height), ImageLockMode.ReadOnly, PixelFormat.Format8bppIndexed); 104unsafe105 {106byte* ptr = (byte*)data.Scan0.ToPointer();107//位图的指针108109byte[] line = new byte[data.Stride];110//保存位图的⼀⾏111for (int i = 0; i < data.Stride; i++)112 line[i] = 0;113for (int i = 0; i < bmp.Height; i++)114 {115for (int j = 0; j < bmp.Width; j++)116 {117 line[j] = *ptr++;118 }119 ptr += data.Stride - bmp.Width;//指针跳过对齐的字节120 bw.Write(line, 0, line.Length);//写⼊位图的⼀⾏121 }122 }123 bw.Close();124 bmp.UnlockBits(data);125 }126 }127128public void Bit8To24()129 {130 Bitmap bmp8 = new Bitmap(filepath);131 BitmapData data8 = bmp8.LockBits(new Rectangle(0, 0, bmp8.Width, bmp8.Height), ImageLockMode.ReadOnly, PixelFormat.Format8bppIndexed); 132 Bitmap bmp24 = new Bitmap(bmp8.Width, bmp8.Height, PixelFormat.Format24bppRgb);133 BitmapData data24 = bmp24.LockBits(new Rectangle(0, 0, bmp24.Width, bmp24.Height), ImageLockMode.WriteOnly, PixelFormat.Format24bppRgb); 134unsafe135 {136byte* ptr8 = (byte*)data8.Scan0.ToPointer();137byte* ptr24 = (byte*)data24.Scan0.ToPointer();138for (int i = 0; i < bmp8.Height; i++)139 {140for (int j = 0; j < bmp8.Width; j++)141 {142//⽤8位位图的灰度值填充24位位图的R、G、B值143 *ptr24++ = *ptr8;144 *ptr24++ = *ptr8;145 *ptr24++ = *ptr8++;146 }147 ptr8 += data8.Stride - bmp8.Width; //跳过对齐字节148 ptr24 += data24.Stride - bmp8.Width * 3; //跳过对齐字节149 }150 }151 bmp8.UnlockBits(data8);152 bmp24.UnlockBits(data24);153 bmp24.Save(savepath);154 }155156public void Bit8To32()157 {158 Bitmap bmp8 = new Bitmap(filepath);159 BitmapData data8 = bmp8.LockBits(new Rectangle(0, 0, bmp8.Width, bmp8.Height), ImageLockMode.ReadOnly, PixelFormat.Format8bppIndexed); 160 Bitmap bmp32 = new Bitmap(bmp8.Width, bmp8.Height, PixelFormat.Format32bppArgb);161 BitmapData data32 = bmp32.LockBits(new Rectangle(0, 0, bmp32.Width, bmp32.Height), ImageLockMode.WriteOnly, PixelFormat.Format32bppArgb); 162163unsafe164 {165byte* ptr8 = (byte*)data8.Scan0.ToPointer();166byte* ptr32 = (byte*)data32.Scan0.ToPointer();167for (int i = 0; i < bmp8.Height; i++)168 {169for (int j = 0; j < bmp8.Width; j++)170 {171//⽤8位位图的灰度值,填充32位位图的RGB值,透明度为100%172 *ptr32++ = *ptr8;173 *ptr32++ = *ptr8;174 *ptr32++ = *ptr8++;175 *ptr32++ = 255;176 }177 ptr8 += data8.Stride - bmp8.Width;178 ptr32 += data32.Stride - bmp8.Width * 4;179 }180 }181 bmp8.UnlockBits(data8);182 bmp32.UnlockBits(data32);183 bmp32.Save(savepath);184 }185186public void Bit24To8()187 {188 Bitmap bmp24 = new Bitmap(filepath);189 BitmapData data24 = bmp24.LockBits(new Rectangle(0, 0, bmp24.Width, bmp24.Height), ImageLockMode.ReadOnly, PixelFormat.Format24bppRgb); 190 Bitmap bmp8 = new Bitmap(bmp24.Width, bmp24.Height, PixelFormat.Format8bppIndexed);191 BitmapData data8 = bmp8.LockBits(new Rectangle(0, 0, bmp8.Width, bmp8.Height), ImageLockMode.WriteOnly, PixelFormat.Format8bppIndexed); 192193unsafe194 {195byte* ptr24 = (byte*)data24.Scan0.ToPointer();196byte* ptr8 = (byte*)data8.Scan0.ToPointer();197for (int i = 0; i < bmp8.Height; i++)198 {199for (int j = 0; j < bmp8.Width; j++)200 {201//⽤RGB值的均值作为8位位图的灰度值202 *ptr8++=(byte)(((int)(*ptr24++)+(int)(*ptr24++)+(int)(*ptr24++))/3);203 }204 ptr24 += data24.Stride - bmp8.Width * 3;205 ptr8 += data8.Stride - bmp8.Width;206 }207 }208 bmp8.UnlockBits(data8);209 bmp24.UnlockBits(data24);210 Save8Bits(bmp8);211 }212213public void Bit32To8()214 {215 Bitmap bmp32 = new Bitmap(filepath);216 BitmapData data32 = bmp32.LockBits(new Rectangle(0, 0, bmp32.Width, bmp32.Height), ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb); 217 Bitmap bmp8 = new Bitmap(bmp32.Width, bmp32.Height, PixelFormat.Format8bppIndexed);218 BitmapData data8 = bmp8.LockBits(new Rectangle(0, 0, bmp8.Width, bmp8.Height), ImageLockMode.WriteOnly, PixelFormat.Format8bppIndexed); 219unsafe220 {221byte* ptr32 = (byte*)data32.Scan0.ToPointer();222223byte* ptr8 = (byte*)data8.Scan0.ToPointer();224for (int i = 0; i < bmp8.Height; i++)225 {226for (int j = 0; j < bmp8.Width; j++)227 {228//⽤32位位图的RGB值的均值作为8位位图的灰度值229 *ptr8++ = (byte)(((int)(*ptr32++) + (int)(*ptr32++) + (int)(*ptr32++)) / 3);230 ptr32++;//跳过透明度字节231 }232 ptr32 += data32.Stride - bmp32.Width * 4;233 ptr8 += data8.Stride - bmp8.Width;234 }235 }236 bmp8.UnlockBits(data8);237 bmp32.UnlockBits(data32);238 Save8Bits(bmp8);239 }240241public void Bit32To24()242 {243 Bitmap bmp32 = new Bitmap(filepath);244 BitmapData data32 = bmp32.LockBits(new Rectangle(0, 0, bmp32.Width, bmp32.Height), ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb); 245 Bitmap bmp24 = new Bitmap(bmp32.Width, bmp32.Height, PixelFormat.Format24bppRgb);246 BitmapData data24 = bmp24.LockBits(new Rectangle(0, 0, bmp24.Width, bmp24.Height), ImageLockMode.WriteOnly, PixelFormat.Format24bppRgb); 247unsafe248 {249byte* ptr32 = (byte*)data32.Scan0.ToPointer();250byte* ptr24 = (byte*)data24.Scan0.ToPointer();251for (int i = 0; i < bmp24.Height; i++)252 {253for (int j = 0; j < bmp24.Width; j++)254 {255//将32位位图的RGB值赋值给24位位图的RGB值256 *ptr24++ = *ptr32++;257 *ptr24++ = *ptr32++;258 *ptr24++ = *ptr32++;259 ptr32++;//跳过透明度字节260 }261 ptr24 += data24.Stride - bmp24.Width * 3;262 ptr32 += data32.Stride - bmp32.Width * 4;263 }264 }265 bmp32.UnlockBits(data32);266 bmp24.UnlockBits(data24);267 bmp24.Save(savepath);268 }269270public void Bit24To32()271 {272 Bitmap bmp24 = new Bitmap(filepath);273 BitmapData data24 = bmp24.LockBits(new Rectangle(0, 0, bmp24.Width, bmp24.Height), ImageLockMode.ReadOnly, PixelFormat.Format24bppRgb); 274 Bitmap bmp32 = new Bitmap(bmp24.Width, bmp24.Height, PixelFormat.Format32bppArgb);275 BitmapData data32 = bmp32.LockBits(new Rectangle(0, 0, bmp32.Width, bmp32.Height), ImageLockMode.WriteOnly, PixelFormat.Format32bppArgb); 276unsafe277 {278byte* ptr24 = (byte*)data24.Scan0.ToPointer();279byte* ptr32 = (byte*)data32.Scan0.ToPointer();280for (int i = 0; i < bmp32.Height; i++)281 {282for (int j = 0; j < bmp32.Width; j++)283 {284//将24位位图的RGB值赋值给32位位图的RGB分量285 *ptr32++ = *ptr24++;286 *ptr32++ = *ptr24++;287 *ptr32++ = *ptr24++;288 *ptr32++ = 255;//设透明度为100%289 }290 ptr24 += data24.Stride - bmp24.Width * 3;291 ptr32 += data32.Stride - bmp32.Width * 4;292 }293 }294 bmp32.UnlockBits(data32);295 bmp24.UnlockBits(data24);296 bmp32.Save(savepath);297 }298 }。
完整程序_C语言对BMP图像的读和写和对像素的操作
![完整程序_C语言对BMP图像的读和写和对像素的操作](https://img.taocdn.com/s3/m/df4bc9d0240c844769eaee37.png)
#include <stdio.h>#include "Windows.h"BOOL readBmp(char *bmpName);BOOL saveBmp(char *bmpName, char *imgBuf, int width, int heigh, int biBitCount, RGBQUAD *pColorTable);char *pBmpBuf; //位图数据int bmpWidth; // 图像宽度int bmpHeight; //图像高度int biBiCount; //图像类型,每像素位数RGBQUAD *pColorTable; //位图颜色表指针int main(){char readName[] = "read.BMP";readBmp(readName);char writeName[] = "write.BMP";saveBmp(writeName, pBmpBuf, bmpWidth, bmpHeight, biBiCount, pColorTable);int lineByte = (bmpWidth*bmpHeight/8+3)/4*4;if (biBiCount == 8){for (int i = 0; i < bmpWidth/2; i++){for (int j = 0; j < bmpHeight/2; j++){*(pBmpBuf+i*lineByte+j) = 0;}}}else if (biBiCount == 24){/////对于24位真彩图,每个像素占三个字节分别存储R、G、B三个颜色分量的颜色值for (int i = 0; i < bmpWidth/2; i++){for (int j = 0; j < bmpHeight/2; j++){for (int k = 0; k < 3; k++)*(pBmpBuf+i*lineByte+j*3+k) = 0; //将rgb三个颜色分量设置成黑色}}}char Name[] = "copy.BMP";saveBmp(Name, pBmpBuf, bmpWidth, bmpHeight, biBiCount, pColorTable);delete []pBmpBuf;if (biBiCount == 8){delete []pColorTable;}return 0;}BOOL readBmp(char *bmpName ){FILE *pf = fopen(bmpName, "rb");if (pf == NULL) return FALSE;printf("read %s succeeded!\n", bmpName);fseek(pf, sizeof(BITMAPFILEHEADER), SEEK_SET);BITMAPINFOHEADER infoHeader;fread(&infoHeader, sizeof(BITMAPINFOHEADER), 1, pf);bmpWidth = infoHeader.biWidth;bmpHeight = infoHeader.biHeight;biBiCount = infoHeader.biBitCount;//图像每行的字节数,一定要是4的倍数int lineByte = (bmpWidth*bmpHeight/8+3)/4*4;pBmpBuf = new char[lineByte*bmpHeight];//灰度图像有颜色表if (biBiCount == 8){pColorTable = new RGBQUAD[256];fread(pColorTable, sizeof(RGBQUAD), 1, pf);}fread(pBmpBuf, lineByte*bmpHeight, 1, pf);fclose(pf); //关闭文件return TRUE;}BOOL saveBmp(char *bmpName, char *imgBuf, int width, int heigh, int biBitCount, RGBQUAD *pColorTable ){FILE *pf = fopen(bmpName, "wb");if (pf == NULL) return FALSE;printf("write %s succeeded!\n", bmpName);//写头文件int colorTableSize = 0;if (biBitCount == 8){colorTableSize = 1024;}int lineByte = (width*heigh/8+3)/4*4;BITMAPFILEHEADER filehead;filehead.bfOffBits = 54+colorTableSize;filehead.bfType = 0x4D42;filehead.bfSize = sizeof(BITMAPFILEHEADER)+sizeof(BITMAPINFOHEADER)+colorTableSize+lineByte*heig h;filehead.bfReserved1 = 0;filehead.bfReserved2 = 0;fwrite(&filehead, sizeof(BITMAPFILEHEADER), 1, pf);BITMAPINFOHEADER infoHead;infoHead.biBitCount = biBitCount;infoHead.biWidth = width;infoHead.biHeight = heigh;infoHead.biSize = 40;infoHead.biClrImportant = 0;infoHead.biSizeImage = lineByte*heigh;infoHead.biClrUsed = 0;infoHead.biPlanes = 1;infoHead.biXPelsPerMeter = 0;infoHead.biYPelsPerMeter = 0;fwrite(&infoHead,sizeof(BITMAPINFOHEADER), 1, pf);if (biBitCount == 8){fwrite(pColorTable, sizeof(RGBQUAD), 256, pf);}fwrite(pBmpBuf, lineByte*heigh, 1, pf);fclose(pf);return TRUE;}。
读取并在屏幕上显示24位bmp图像
![读取并在屏幕上显示24位bmp图像](https://img.taocdn.com/s3/m/c0d7443a763231126edb114e.png)
读取并在屏幕上显示24位bmp图像PS:本文非原创,code来自互联网。
代码如下:/*这里仅仅是一个简单的显示也可以写出适用于各种OpenGL使用例如设置我们甚至可以使用负的系数,使得整个图象进行水平方向或垂直方向的翻转(默认像素从左绘制到右,但翻转后将从右绘制到左。
默认像素从下绘制到上,但翻转后将从上绘制到下。
因此,*/ opengl#include <gl/#definestaticstaticstaticstaticstatic#include <stdio.h>#include <stdlib.h>void{////// glClear(GL_COLOR_BUFFER_BIT);//GL_glutSwapBuffers();}int{FILE* pFile = fopen(str,exit(fseek(pFile,fread(&ImageWidth,fread(&ImageHeight,PixelLength = ImageWidth *++PixelLength;PixelLength *= ImageHeight;exit(fseek(pFile,fread(fclose(pFile);glutInit(&argc, argv);glutInitDisplayMode(GLUT_glutInitWindowPosition(glutInitWindowSize(ImageWidth, ImageHeight);glutCreateWindow(FileName);glutDisplayFunc(&display);glutMainLoop();}显示结果截图如下:为方便理解程序,下面把网上找的关于部分bmp图像格式的说明也写在下面了,如果还想了解的更清楚,就自己再google下,很多相关资料的。
BMP文件是一种像素文件,它保存了一幅图象中所有的像素。
1 怎样读取BMP文件中的像素数据与显示位图
![1 怎样读取BMP文件中的像素数据与显示位图](https://img.taocdn.com/s3/m/306b2d07d1f34693dbef3e37.png)
怎样读取BMP位图的数据与显示位图计算机与信息工程系管庶安一 BMP位图文件的结构以24位BMP位图文件为例说明。
BMP位图文件结构如下表所示:位图数据◇逐行逐列记录各像素点的三基色分量。
◇每一像素点占用三个字节,分别表示蓝色分量B、绿色分量G、红色分量R的值。
◇ 设图像有n行、m列像素,行顺序为从下向上分别为第1行、第2行……;列顺序为从左向右分别为第1列、第2列……。
按此顺序将各像素的三基色值记录于BYTE型的一维数组中,如下图所示:注意:当一行占用的字节数不是4的整数倍时,应补充1~3个无效字节,使一行占用的字节数能被4整除。
无效字节可为任意值,不会影响图像内容。
二读取BMP位图数据(1)在MFC工程中的 .H文件中定义如下全局成员变量:BITMAPFILEHEADER FileHead; // 定义存放 .BMP 文件头的结构BITMAPINFOHEADER BmpInfo; // 定义存放 .BMP 信息头的结构LPBYTE lpImage; // 定义存放 .BMP文件中的位图数据的BYTE型指针typedef struct CCC{ // 定义能存放一个像素的3个基色值的结构类型BYTE B;BYTE G;BYTE R;};CCC C3 [480] [640];// 定义能存放一幅480行、640列像素的二维数组,以便图像处理与识别时运算(2)在.CPP文件中的类构造函数中,为lpImage指针申请内存:lpImage=(LPBYTE)new BYTE[640*480*3];在.CPP文件中的类析构函数中,为lpImage指针释放内存:delete[ ] lpImage;(3)在.CPP文件中的适当函数中打开.BMP文件,读取信息头和位图数据。
CFile f;BOOL OK;OK=f.Open( Bmp.PathName,CFile::modeRead|CFile::typeBinary|CFile::shareExcl usive,NULL);if(!OK) return(-1); //不能打开文件,返回失败标志-1f.Read(&FileHead,sizeof(FileHead)); //读文件头if(FileHead.bfType!=0x4d42) {f.Close();return -2; //不是BMP文件,返回失败标志-2 }short x,y,z;z=(BmpInfo.biWidth*3/4)*4+(BmpInfo.biWidth*3%4==0 ? 0 : 4);f.Read(&BmpInfo,sizeof(BmpInfo)); //读信息头f.Seek(FileHead.bfOffBits,0);f.Read(lpImage,BmpInfo.biHeight*z); //读全部位图数据f.Close();for(y=BmpInfo.biHeight-1;y>=0;y--){memcpy(C3[y],lpImage+(BmpInfo.biHeight-1-y)*z,z); //逐行将位图数据填写到C3数组中}return 1; //最后,返回成功标志1三显示位图1 先按上述方法读取位图数据,再将读取数据予以显示。
BMP24位位图格式总结
![BMP24位位图格式总结](https://img.taocdn.com/s3/m/7615ddcdb9f3f90f76c61b28.png)
图像BMP24位位图格式总结1、创建图片创建一张只有六个像素的图片(两行三列),每个像素的颜色RGB组合值如图1(示意图)所示:图12、windows系统下存储格式(使用WinHex打开)3、文件结构3.1 文件头(bmp file header),提供文件的格式、大小等信息,共14个字节,如图2所示。
图23.1.1 0-1字节(2个字节)0x42 0x4d = "BM",表示这是Windows支持的位图格式,如图3所示。
图33.1.2 2-5字节(4个字节),表示该bmp文件的大小,存储形式为图4所示,因为小端对齐形式存储,实际存储的16进制数为0x4e,转换为十进制为78,与我们直接查看此图片的属性所看到的文件大小一致。
注:对于arm,intel这种x86架构的复杂指令CPU,整数在内存中是倒着存放的,低地址放低位,高地址放高位,小端对齐,但对于unix服务器的CPU,更多是采用大端对齐的情况图43.1.3 6-9字节这是两个保留段,为0如图5所示。
图53.1.4 A-D字节如图6所示,存储数据为0x36,十进制为54,表示的意义为从文件头到位图数据需偏移54字节。
图63.2 位图信息头(bitmap information):提供图像数据的尺寸、位平面数、压缩方式、颜色索引等信息,40个字节,如图7所示。
图73.2.1 0E-11字节,如图8所示,存储数据为0x28,十进制为40,表示意义为:位图信息头的大小为40个字节。
图83.2.2 12-15字节,如图9所示,存储数据为0x03,十进制为3,表示意义为:图像宽为3个像素,与我们创建的图像一致。
图93.2.3 16-19字节,如图10所示,存储数据为0x02,十进制为2,表示意义为:图像高为2个像素,与我们创建的图像一致。
图103.2.4 1A-1B字节,如图11所示,存储数据为0x01,该值总为1,表示意义为位元面数。
BMP图像存储格式
![BMP图像存储格式](https://img.taocdn.com/s3/m/d41c3a8684868762caaed571.png)
维基百科的BMP定义BMP取自位图BitMaP的缩写,也称为DIB(与设备无关的位图),是微软视窗图形子系统(Graphics Device Interface)内部使用的一种位图图形格式,它是微软视窗平台上的一个简单的图形文件格式。
图像通常保存的颜色深度有2(1位)、16(4位)、256(8位)、65536(16位)和1670万(24位)种颜色(其中位是表示每点所用的数据位)。
8位图像可以是索引彩色图像外,也可以是灰阶图像。
表示透明的alpha通道也可以保存在一个类似于灰阶图像的独立文件中。
带有集成的alpha通道的32位版本已经随着Windows XP出现,它在视窗的登录和主题系统中都有使用。
文件大小计算BMP文件通常是不压缩的,所需存储空间比较大。
一个像素所占的字节数为n∕8字节,n是位深。
文件大小可以根据以下公式近似计算:BMP文件大小≈54+4*2n+(width*height*n)∕8;54是位图文件的文件头,4*2n是调色板的大小(对于没有调色板的位图文件,则不存在这一项),最后一项是像素数据。
由于存储算法决定的因素,实际文件大小和计算值可能有细微差别;因此使用的≈符号而不是等于号。
文件存储格式BMP图像自推出以后,几经演进,存储格式也有所变化。
下表详细描述了位图文件可能包含的数据。
结构体名称可选大小用途备注位图文件头否14字节存储位图文件通用信息仅在读取文件时有用DIB头否固定(存在7种不同版本)存储位图详细信息及像素格式紧接在位图文件头后附加位掩码是3或4 DWORD(12或16字节)定义像素格式仅在DIB头是BITMAPINFOHEADER时存在调色板见备注可变定义图像数据(像素数组)所用颜色色深≤ 8时不能省略填充区A是可变结构体对齐位图文件头中像素数组偏移量的产物像素数组否可变定义实际的像素数值像素数据在DIB头和附加位掩码中定义。
像素数组中每行均以4字节对齐填充区B 是可变结构体对齐DIB头中ICC色彩特性数据偏移量的产物ICC色彩特性数据是可变定义色彩特性可以包含外部文件路径,由该文件来定义色彩特性Remark:像素数组每行均以4字节对齐,这会影响我们怎么读取像素数据。
图像处理Bmp文件存储顺序
![图像处理Bmp文件存储顺序](https://img.taocdn.com/s3/m/af71f10479563c1ec5da71dd.png)
读写Bmp文件的方法步骤:读:1.读方式打开文件2.读入BITMAPFILEHEADER结构3.读入BITMAPINFOHEADER结构4.读入颜色表RGBQUAD结构5.读入位图数据6.关闭文件写:1.写方式打开文件2.填写BITMAPFILEHEADER结构并写入文件3.写入BITMAPINFHEADER结构并写入文件4.写颜色表进文件5.写位图数据进文件6.关闭文件①:位图文件头BITMAPFILEHEADER: (14字节)bfType :位图文件类型(0x4D42)bfSize :位图文件大小bfReserved1: Windows保留字1bfReserved2: Windows保留字2bfOffBits: 从文件头到实际位图数据的偏移字节数=文件头+ 信息头+调色板长度。
②:位图信息头(40字节)biSize: 本结构长度为40字节biWidth: 位图宽度,(像素为单位)biHeight: 位图的高度,(像素为单位)biPlanes: 设为1biCount: 位深度biCompression: 为0:不压缩;1:8位压缩;2:4位压缩。
biSizeImage:实际的位图数据占用的字节数biXPelsPerMeter:水平分辨率(像素/米)biYPelPerMeter: 垂直分辨率(像素/米)biClrCount:位图实际用到的颜色数(为0时,颜色数为2的biBitCount次幂)biClrImportant:位图显示过程中重要的颜色数(0:都是重要的)③:颜色表(4字节)rgbBlue:蓝色分量rgbGreen:绿色分量rgbRed: 红色分量rgbReserved:保留字节颜色表的大小:二值图像:大小=2*sizeof(RGBQUAD)=88位灰度图像:大小= 256*sizeof(RGBQUAD)= 102424位真彩色图像无颜色表④位图数据8位灰度图像ColorTablesize = 1024;lineByte =(bmpWidth * biBitCount / 8 + 3)/4 *4;1.申请位图文件头结构变量,并填写文件头信息BITMAPFILEHEADER fileHeader;fileHead.bfType = 0x4D42; //bmp类型//bfSize是图像文件4个组成部分之和fileHeader.bfSize = sizeof(BITMAPFILEHEADER) + sizeof(BITMAOINFOHEADER) + ColorTablesize + lineByte*Height;fileHeader.bfReserved1 = 0;fileHeader.bfReserved2 = 0;//bfOffBits是图像文件前3部分所需空间之和fileHead.bfOffBits = 54 + ColorTablesize;2.申请位图信息头结构变量,填写信息头信息BITMAPINFOHEADER head;head.biBitCount = biBitCount;head.biClrImportant = 0;head.biClrUsed = 0;head.biCompression = 0;head.biHeight = height;head.biSize = 40;head.biSizeImage = lineByte * height;head.biWidth = width;head.biXPelsPerMeter = 0;head.biYPelsPerMete = 0;3.写灰度图像的颜色表4.写位图数据进文件调色板句柄HPALETTE文件头指针LPBITMAFILEHEADER : m_lpDib信息头指针LPBITMAPINFOHEADER :m_lpBmpInfoHead 颜色表LPRGBQUAD : m_lpColorTable 信息指针LPBITMAPINFO :m_lpBmpInfo图像数据指针:m_pImgData (包括:信息头指针和颜色表)1读入一幅图像(即打开操作):将四部分都考虑进去(1,2,3,4);2写入一幅图像(即保存操作):将四部分都考虑进去(1,2,3,4)3显示一幅图像:只需将3部分考虑进去(2,3,4)4 处理一幅图像:只需将3部分考虑进去(2,3,4)位图显示和数据处理:将(位图信息头、颜色表)即:信息指针内容,位图数据指针依次写入,并进行操作。
BMP图片格式
![BMP图片格式](https://img.taocdn.com/s3/m/7c2d3968a45177232f60a202.png)
BMP图片格式简介:BMP是一种与硬件设备无关的图像文件格式,使用非常广。
它采用位映射存储格式,除了图像深度可选以外,不采用其他任何压缩,因此,BMP文件所占用的空间很大。
BMP文件的图像深度可选lbit、4bit、8bit及24bit。
BMP文件存储数据时,图像的扫描方式是按从左到右、从下到上的顺序。
由于BMP文件格式是Windows环境中交换与图有关的数据的一种标准,因此在Windows环境中运行的图形图像软件都支持BMP图像格式。
文件结构:典型的BMP图像文件由四部分组成:1:位图文件头数据结构,它包含BMP图像文件的类型、显示内容等信息;2:位图信息数据结构,它包含有BMP图像的宽、高、压缩方法,以及定义颜色等信息;3:调色板,这个部分是可选的,有些位图需要调色板,有些位图,比如真彩色图(24位的BMP)就不需要调色板;4:位图数据,这部分的内容根据BMP位图使用的位数不同而不同,在24位图中直接使用RGB,而其他的小于24位的使用调色板中颜色索引值。
位图的类型:位图一共有两种类型,即:设备相关位图(DDB)和设备无关位图(DIB)。
DDB位图在早期的Windows系统(Windows 3.0以前)中是很普遍的,事实上它也是唯一的。
然而,随着显示器制造技术的进步,以及显示设备的多样化,DDB位图的一些固有的问题开始浮现出来了。
比如,它不能够存储(或者说获取)创建这张图片的原始设备的分辨率,这样,应用程序就不能快速的判断客户机的显示设备是否适合显示这张图片。
为了解决这一难题,微软创建了DIB位图格式。
设备无关位图 (Device-Independent Bitmap)DIB位图包含下列的颜色和尺寸信息:*原始设备(即创建图片的设备)的颜色格式。
*原始设备的分辨率。
*原始设备的调色板*一个位数组,由红、绿、蓝(RGB)三个值代表一个像素。
*一个数组压缩标志,用于表明数据的压缩方案(如果需要的话)。
BMP图像的读写(8位和24位)
![BMP图像的读写(8位和24位)](https://img.taocdn.com/s3/m/c9e33f21763231126edb1153.png)
南通大学计算机科学与技术学院《数字图像处理》课程实验报告书实验名BMP文件的读写(8位和24位)班级计121姓名张进学号**********2014年6月16 日一、实验内容1、了解BMP文件的结构2、8位位图和24位位图的读取二、BMP图形文件简介BMP(Bitmap-File)图形文件是Windows采用的图形文件格式,在Windows环境下运行的所有图象处理软件都支持BMP图象文件格式。
Windows系统内部各图像绘制操作都是以BMP为基础的。
Windows 3.0以前的BMP图文件格式与显示设备有关,因此把这种BMP图象文件格式称为设备相关位图DDB(device-dependent bitmap)文件格式。
Windows 3.0以后的BMP图象文件与显示设备无关,因此把这种BMP图象文件格式称为设备无关位图DIB(device-independent bitmap)格式(注:Windows 3.0以后,在系统中仍然存在DDB位图,象BitBlt()这种函数就是基于DDB位图的,只不过如果你想将图像以BMP格式保存到磁盘文件中时,微软极力推荐你以DIB格式保存),目的是为了让Windows能够在任何类型的显示设备上显示所存储的图象。
BMP位图文件默认的文件扩展名是BMP或者bmp(有时它也会以.DIB或.RLE作扩展名)。
位图文件可看成由4个部分组成:位图文件头(bitmap-file header)、位图信息头(bitmap-information header)、彩色表(color table)和定义位图的字节阵列,它具有如下所示的形式。
位图文件结构内容摘要三、读写涉及的原理1、图像的二值化的基本原理图像的二值化处理就是讲图像上的点的灰度置为0或255,也就是讲整个图像呈现出明显的黑白效果。
即将256个亮度等级的灰度图像通过适当的阀值选取而获得仍然可以反映图像整体和局部特征的二值化图像。
bmp图像大小计算方法[精品]
![bmp图像大小计算方法[精品]](https://img.taocdn.com/s3/m/1da5ca3fcec789eb172ded630b1c59eef8c79aea.png)
BMP图像大小计算方法大小=分辨率*位深/8分辨率=宽*高(如:1024*768,640*480)位深:如24位,16位,8位/8计算的是字节数。
例如:一幅图像分辨率:1024*768,24位,则其大小计算如下:大小=1024*768824/8=2359296byte=2304KBBMP是一种与硬件设备无关的图像文件格式,使用非常广。
它采用位映射存储格式,除了图像深度可选以外,不采用其他任何压缩,因此,BMP文件所占用的空间很大。
BMP文件的图像深度可选lbit、4bit、8bit及24bit。
BMP文件存储数据时,图像的扫描方式是按从左到右、从下到上的顺序。
由于BMP文件格式是Windows环境中交换与图有关的数据的一种标准,因此在Windows环境中运行的图形图像软件都支持BMP图像格式。
典型的BMP图像文件由三部分组成:位图文件头数据结构,它包含BMP图像文件的类型、显示内容等信息;位图信息数据结构,它包含有BMP图像的宽、高、压缩方法,以及定义颜色等信息。
具体数据举例:如某BMP文件开头:424D 4690 0000 0000 0000 4600 0000 2800 0000 8000 0000 9000 0000 0100*1000 0300 0000 0090 0000 A00F 0000 A00F 0000 0000 0000 0000 0000*00F8 0000 E007 0000 1F00 0000 0000 0000*02F1 84F1 04F1 84F1 84F1 06F2 84F1 06F2 04F2 86F2 06F2 86F2 86F2 .... ....BMP文件可分为四个部分:位图文件头、位图信息头、彩色板、图像数据阵列,在上图中已用*分隔。
一、图像文件头1)1:(这里的数字代表的是"字",即两个字节,下同)图像文件头。
424Dh=’BM’,表示是Windows支持的BMP格式。
24位BMP图像
![24位BMP图像](https://img.taocdn.com/s3/m/d5d1e3e75ef7ba0d4a733b4f.png)
#include<stdio.h>#include<malloc.h>void main(){FILE *fpIn,*fpOut;///////////////////////////struct RGBQUAD{unsigned char rgbBlue;unsigned char rgbGreen;unsigned char rgbRed;unsigned char rgbReserved;} bicolor;char bfty[2];short bfreserved1,biplanes,bibitcount;long bfsize,bfoffbit,bisize,biwidth,biheight;long bicompression,bisizeimage,bix,biy,biclrused,biclrimportant;char *cR;int iCol,iRow;int i,j;int iWidth;char *lpsData;int iL;short sTemp;////////////////////////////////////fpIn=fopen("F:/课堂学习/遥感数字图像处理/data/AA","rb");fpOut=fopen("F:/课堂学习/遥感数字图像处理/data/Tm23.bmp","wb");//D:\??\??????????\Data\dataiCol=600;iRow=600;bfty[0]='B';bfty[1]='M';bfsize=54+iCol*iRow*3;bfreserved1=0;bfoffbit=54;/////////////////bisize=40;biwidth=iCol;biheight=iRow;biplanes=1;bibitcount=24;bicompression=0;bisizeimage=iRow*iCol*3;bix=0;biy=0;biclrused=0;biclrimportant=0;/////////////////////////fwrite(&bfty[0],1,1,fpOut);//fprintffwrite(&bfty[1],1,1,fpOut);fwrite(&bfsize,4,1,fpOut);fwrite(&bfreserved1,2,1,fpOut);fwrite(&bfreserved1,2,1,fpOut);fwrite(&bfoffbit,4,1,fpOut);///////////////////////////////////fwrite(&bisize,4,1,fpOut);fwrite(&biwidth,4,1,fpOut);fwrite(&biheight,4,1,fpOut);fwrite(&biplanes,2,1,fpOut);fwrite(&bibitcount,2,1,fpOut);fwrite(&bicompression,4,1,fpOut);fwrite(&bisizeimage,4,1,fpOut);fwrite(&bix,4,1,fpOut);fwrite(&biy,4,1,fpOut);fwrite(&biclrused,4,1,fpOut);fwrite(&biclrimportant,4,1,fpOut);////////////////////////////////////////////// ///////////////////////////////iWidth=(iCol*3+3)/4*4;//为什么?cR=(char *)malloc(iWidth*sizeof(char)*iRow); lpsData=(char *)malloc(600*sizeof(char));////////////////////////////fseek(fpIn,600*600*1,0);for(i=0;i<iRow;i++){fread(lpsData,1,600,fpIn);for(j=0;j<iCol;j++)//600{iL=(iRow-1-i)*iWidth+j*3;sTemp=lpsData[j];//[750+j*5+0];cR[iL]=sTemp*2;}}fseek(fpIn,600*600*2,0);for(i=0;i<iRow;i++){fread(lpsData,1,600,fpIn);for(j=0;j<iCol;j++)//600{iL=(iRow-1-i)*iWidth+j*3+1;sTemp=lpsData[j];//[750+j*5+0];cR[iL]=sTemp*2;}}fseek(fpIn,600*600*3,0);for(i=0;i<iRow;i++){fread(lpsData,1,600,fpIn);for(j=0;j<iCol;j++)//600{iL=(iRow-1-i)*iWidth+j*3+2;sTemp=lpsData[j];//[750+j*5+0];cR[iL]=sTemp*2;}}fwrite(cR,sizeof(char),iWidth*iRow,fpOut); free(cR);free(lpsData);fclose(fpOut);fclose(fpIn);}。
最新8位灰度图像BMP的保存汇总
![最新8位灰度图像BMP的保存汇总](https://img.taocdn.com/s3/m/d0ede82b01f69e3142329441.png)
8位灰度图像B M P的保存8位灰度图像BMP的保存[zz]2012-04-07 21:01在图像处理中,我们经常需要将真彩色图像转换为黑白图像。
严格的讲应该是灰度图,因为真正的黑白图像是二色,即只有纯黑,纯白二色。
开始之前,我们先简单补充一下计算机中图像的表示原理。
计算机中的图像大致可以分成两类:位图(Bitmap)和矢量图(Metafile)。
位图可以视为一个二维的网格,整个图像就是由很多个点组成的,点的个数等于位图的宽乘以高。
每个点被称为一个像素点,每个像素点有确定的颜色,当很多个像素合在一起时就形成了一幅完整的图像。
我们通常使用的图像大部分都是位图,如数码相机拍摄的照片,都是位图。
因为位图可以完美的表示图像的细节,能较好的还原图像的原景。
但位图也有缺点:第一是体积比较大,所以人们开发了很多压缩图像格式来储存位图图像,目前应用最广的是JPEG格式,在WEB上得到了广泛应用,另外还有GIF,PNG等等。
第二是位图在放大时,不可避免的会出现“锯齿”现象,这也由位图的本质特点决定的。
所以在现实中,我们还需要使用到另一种图像格式:矢量图。
同位图不同,矢量图同位图的原理不同,矢量图是利用数学公式通过圆,线段等绘制出来的,所以不管如何放大都不会出现变形,但矢量图不能描述非常复杂的图像。
所以矢量图都是用来描述图形图案,各种CAD软件等等都是使用矢量格式来保存文件的。
在讲解颜色转换之前,我们要先对位图的颜色表示方式做一了解。
位图中通常是用RGB三色方式来表示颜色的(位数很少时要使用调色板)。
所以每个像素采用不同的位数,就可以表示出不同数量的颜色。
如下图所示:每像素的位数一个像素可分配到的颜色数量12^1 = 222^2 = 442^4 = 1682^8 = 256162^16 = 65,536242^24 = 16,777,216从中我们可以看出,当使用24位色(3个字节)时,我们可以得到1600多万种颜色,这已经非常丰富了,应该已接近人眼所能分辨的颜色了。
三分钟解析24位真彩BMP格式文件 - 推酷
![三分钟解析24位真彩BMP格式文件 - 推酷](https://img.taocdn.com/s3/m/be34a06fddccda38376baf22.png)
请 输 入 评 论 内 容 ...
已发表评论数(0)
搜索文章
/articles/FvaIVj
登录后评论
4/7
15-4-9
相关站点
ITeye-博客
+ 订阅
相关主题
技术
三分钟解析24位真彩BMP格式文件 - 推酷
热门文章
1. 栈溢出的利用
2. 记一次tcmalloc分配内存引起的coredump
3. RapidJSON —— C++ 快速 JSON 解析器和生成器
4. C++学习之引用
/articles/FvaIVj
5/7
15-4-9
三分钟解析24位真彩BMP格式文件 - 推酷
5. 在 Visual Studio 本地引用 Boost 6. Exploiting CVE-2015-0311, Part II: Bypassing Control Flow Guard on Window..
/articles/FvaIVj
7/7
/articles/FvaIVj
1/7
15-4-9
三分钟解析24位真彩BMP格式文件 - 推酷
000000XX0h 是用来方面看数据的(也可以方便记数),比如数据表的第一行的第三个字节数 据 9E 的位置就是 00000000h + 2 = 00000002h ,这就是为什么在一些解释中定位中使用 000000XXXh 的原因。
因此在我们的读取数据中需要根据 BMP 图像的宽度来判断是否被补 0 ,判断方法就是先 判断一行的字节数是否可以被 4 整除,如果整除则不需要补 0 ,如果没有整除,则求出补的 0 的个数(具体计算方法是, bu_0_number = width( 像素 ) * 3 % 4 ),那么就知道在每 一行的末尾都补了 bu_0_number 个 0 ,因此我们在读取时绘制图片时就要忽略这些数据。 (补充:求每一行的字节数 size = width * 3 )
BMP是什么格式?BMP文件特点及打开方式
![BMP是什么格式?BMP文件特点及打开方式](https://img.taocdn.com/s3/m/30f51954793e0912a21614791711cc7930b7785d.png)
BMP是一种位图文件格式,也叫做设备无关位图格式(DIB),是由微软公司开发的一种图片文件格式。
BMP格式文件保存了每个像素点的RGB值,图像保留了细节和颜色信息,但是会占用较大的存储空间,不利于网络传输和储存。
BMP格式通常用于Windows系统中的图标、位图等图形文件的存储。
BMP格式的特点1. BMP格式采用无损压缩算法,保存了每个像素点的颜色信息,通过像素点映射可以对图像还原出非常精细的细节信息。
2. BMP格式支持多种颜色模式,能够处理24位色、16位色、8位色以及黑白两种颜色模式的图像。
3. BMP格式文件由于保存了每个像素点的信息,所以文件较大,在存储和传输时会占用较大的带宽和存储空间。
4. BMP格式文件结构比较简单,只需要保存每个像素点的信息、文件头和文件信息头即可,因此可以被多种不同类型的应用程序轻松支持和读取。
BMP格式是一种可靠、简单、易于编辑和处理的文件格式,但同时也具有文件大小较大的缺点。
BMP格式的优点1. BMP格式采用无损压缩算法,保存了每个像素点的颜色信息,保证了图像的质量,不损失像素的信息,更为精细得显示图像。
2. BMP格式保存的图像具有较高的色彩深度,可以保存具有更加丰富色彩的图像,更能满足高质量图片的需求。
3. BMP格式简单明了,存储图像时方便读写。
其文件结构非常简单,只需要保存每个像素点的信息、文件头和文件信息头即可,因此可以被多种不同类型的应用程序轻松支持和读取。
4. BMP格式被广泛应用于各种不同的平台和设备,特别是在Windows系统里经常使用。
无论是应用于基于Windows的PC机还是嵌入式应用在诸如ATM机端等各类设备,BMP格式都有着良好的兼容性与共通性。
综上所述,BMP格式具有不受损图像质量、高色深图像存储、简单明了以及广泛适用等优点,使得BMP格式被广泛应用于各类应用场景中。
BMP格式的缺点1. BMP格式文件通常比其他格式的图片文件要大,这意味着它对存储空间和网络传输会带来额外的负担。
颜色模式中8位,16位,24位,32位色彩是什么意思?会有什么区别?计算机颜色格式(8位1。。。
![颜色模式中8位,16位,24位,32位色彩是什么意思?会有什么区别?计算机颜色格式(8位1。。。](https://img.taocdn.com/s3/m/11a31836a4e9856a561252d380eb6294dd8822fc.png)
颜⾊模式中8位,16位,24位,32位⾊彩是什么意思?会有什么区别?计算机颜⾊格式(8位1。
颜⾊模式中8位,16位,24位,32位⾊彩是什么意思?会有什么区别简单地说这⾥说的位数和windows系统显⽰器设置中的颜⾊位数是⼀样的。
表⽰的是能够显⽰出来的颜⾊的多少。
8位的意思是说,能够显⽰出来的颜⾊的数量有8位数。
16、24都是⼀样的。
24位的颜⾊数量已经很多了,叫做“真彩⾊”,其实32位和24位颜⾊数量是⼀样多的。
32位多出来的8位数是⽤来表⽰透明度信息的,所以更加真实。
如果⼀有⼀张真彩⾊的照⽚,放到⼀个只有8位的显⽰器上的话,显⽰出来的效果就会很差。
所以当需常见的颜⾊有 8位 16位 24位 32位⾊,其中24位及以上称为真彩,是PC上最常⽤的颜⾊,其他基本⽤于嵌⼊式系统或⼀些⼯控领域,详情可查阅⼀下表格:Bit-深度⾊彩数1 2 (monochrome)2 4 (CGA)4 16 (EGA)8 256 (VGA)16 65,536 (High Color, XGA)24 16,777,216 (True Color/真彩⾊, SVGA)32 16,777,216 (True Color + Alpha Channel/控制透明度,-游戏特效)关于256⾊,早先的⼀些较为形象的解释是理解为256个油漆桶/256⾊调⾊板,分配给它们编号/索引号。
“叫到哪个颜⾊”哪个颜⾊就出来填充像素。
因为如16⾊、256⾊的⾊彩数有限所以这么解释很简单易理解。
然⽽电脑操作过程中必须经过数码编码,那么实际上256种颜⾊对应256个数码(⼆进制数值),也就是2^2 * 2^3 * 2^3 = 2^8 = 256。
256⾊模式下电脑没有必要去按24bit处理,在当时DOS时代,处理8bit⾊彩⽐24bit要容易多了。
当然256⾊中的任意⼀种颜⾊都可以⽤24bit表⽰,甚⾄可以⽤32bit,64bit表⽰。
但是不管如何,24bit模式就意味着 17.7million种颜⾊。
c++读取BMP文件(24位)
![c++读取BMP文件(24位)](https://img.taocdn.com/s3/m/f48b56283169a4517723a3dd.png)
char fname_bmp[128]; sprintf(fname_bmp, "%s.bmp", filename);
FILE *fp; if (!(fp = fopen(fname_bmp, "wb")))
return -1;
fwrite(header, sizeof(unsigned char), 54, fp);
****************************************************************************/ int youwritetobmp(RGBQUAD *pixarr, int xsize, int ysize, char *filename){
fclose(fp); return 0; }
void clonebmp(unsigned char *image,int xsize,int ysize) {
bmp_read(image, xsize, ysize, ".\\1"); bmp_write(image, xsize, ysize, ".\\2"); }
if (image == NULL) return -1;
clonebmp(image,xsize,ysize);
//功能一:实现一副图像的拷贝
//youwritetobmp(pixarray,xsize,ysize,"yourimage");//功能二:实现像素的精确绘制,像素值 在 pixarray 数组中
unsigned char header[54] ={ 0x42, 0x4d, 0, 0, 0, 0, 0, 0, 0, 0, 54, 0, 0, 0, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
1怎样读取BMP文件中的像素数据与显示位图
![1怎样读取BMP文件中的像素数据与显示位图](https://img.taocdn.com/s3/m/037a19ce77eeaeaad1f34693daef5ef7ba0d12f4.png)
1怎样读取BMP文件中的像素数据与显示位图怎样读取BMP位图的数据与显示位图计算机与信息工程系管庶安一 BMP位图文件的结构以24位BMP位图文件为例说明。
BMP位图文件结构如下表所示:二读取BMP位图数据(1)在MFC工程中的 .H文件中定义如下全局成员变量:BITMAPFILEHEADER FileHead;// 定义存放.BMP 文件头的结构BITMAPINFOHEADER BmpInfo;// 定义存放.BMP 信息头的结构LPBYTE lpImage;// 定义存放.BMP文件中的位图数据的BYTE 型指针typedef struct CCC{ // 定义能存放一个像素的3个基色值的结构类型BYTE B;BYTE G;BYTE R;};CCC C3 [480] [640];// 定义能存放一幅480行、640列像素的二维数组,以便图像处理与识别时运算(2)在.CPP文件中的类构造函数中,为lpImage指针申请内存:lpImage=(LPBYTE)new BYTE[640*480*3];在.CPP文件中的类析构函数中,为lpImage指针释放内存:delete[ ] lpImage;(3)在.CPP文件中的适当函数中打开.BMP文件,读取信息头和位图数据。
CFile f;BOOL OK;OK=f.Open( Bmp.PathName,CFile::modeRead|CFile::typeBinary|CFile::shareExclusive,NULL);if(!OK) return(-1); //不能打开文件,返回失败标志-1f.Read(&FileHead,sizeof(FileHead)); //读文件头if(FileHead.bfType!=0x4d42) {f.Close();return -2; //不是BMP文件,返回失败标志-2}short x,y,z;z=(BmpInfo.biWidth*3/4)*4+(BmpInfo.biWidth*3%4==0 ? 0 :4);f.Read(&BmpInfo,sizeof(BmpInfo)); //读信息头f.Seek(FileHead.bfOffBits,0);f.Read(lpImage,BmpInfo.biHeight*z); //读全部位图数据f.Close();for(y=BmpInfo.biHeight-1;y>=0;y--){memcpy(C3[y],lpImage+(BmpInfo.biHeight-1-y)*z,z); //逐行将位图数据填写到C3数组中}return 1; //最后,返回成功标志1三显示位图1 先按上述方法读取位图数据,再将读取数据予以显示。
BMP图像的读写(8位和24位)要点
![BMP图像的读写(8位和24位)要点](https://img.taocdn.com/s3/m/156cb829f111f18583d05af6.png)
南通大学计算机科学与技术学院《数字图像处理》课程实验报告书实验名 BMP文件的读写(8位和24位)班级计 121姓名张进学号 12130220162014年6月 16 日一、实验内容1、了解BMP文件的结构2、8位位图和24位位图的读取二、BMP图形文件简介BMP(Bitmap-File)图形文件是Windows采用的图形文件格式,在Windows环境下运行的所有图象处理软件都支持BMP图象文件格式。
Windows系统内部各图像绘制操作都是以BMP为基础的。
Windows 3.0以前的BMP图文件格式与显示设备有关,因此把这种BMP 图象文件格式称为设备相关位图DDB(device-dependent bitmap)文件格式。
Windows 3.0以后的BMP图象文件与显示设备无关,因此把这种BMP图象文件格式称为设备无关位图DIB(device-independent bitmap)格式(注:Windows 3.0以后,在系统中仍然存在DDB位图,象BitBlt()这种函数就是基于DDB位图的,只不过如果你想将图像以BMP格式保存到磁盘文件中时,微软极力推荐你以DIB格式保存),目的是为了让Windows能够在任何类型的显示设备上显示所存储的图象。
BMP位图文件默认的文件扩展名是BMP或者bmp(有时它也会以.DIB或.RLE作扩展名)。
位图文件可看成由4个部分组成:位图文件头(bitmap-file header)、位图信息头(bitmap-information header)、彩色表(color table)和定义位图的字节阵列,它具有如下所示的形式。
位图文件的组成结构名称符号位图文件头(bitmap-file header) BITMAPFILEHEADER bmfh位图信息头(bitmap-information header) BITMAPINFOHEADER bmih彩色表(color table) RGBQUAD aColors[]图象数据阵列字节BYTE aBitmapBits[]位图文件结构内容摘要偏移量域的名称大小内容图象文件头0000h 文件标识 2 bytes两字节的内容用来识别位图的类型:‘BM’: Windows 3.1x, 95, NT, …‘BA’:OS/2 Bitmap Array‘CI’:OS/2 Color Icon‘CP’:OS/2 Color Pointer‘IC’: OS/2 Icon‘PT’:OS/2 Pointer注:因为OS/2系统并没有被普及开,所以在编程时,你只需判断第一个标识“BM”就行。
24位真彩色位图(bmp)读取代码
![24位真彩色位图(bmp)读取代码](https://img.taocdn.com/s3/m/1f29a31853ea551810a6f524ccbff121dd36c51f.png)
BITMAP INFO* pBmpIn fo;BYTE * pBmpDa ta;BITMAP FILEH EADER bmpHea der;BITMAP INFOH EADER bmpInf o;CFilebmpFil e;CStrin g strFil eName;CStrin g strFil ter = "位图文件(*.bmp)|*.b mp|所有文件(*.*)|*.*|";CFileD ialog dlg(TRUE,NULL,NULL,NULL,strFil ter,this);if (!dlg.DoModa l() == IDOK) return;strFil eName = dlg.GetPat hName();/// 通过读取位图文件显示位图if(!bmpFil e.Open(strFil eName,CFile::modeRe ad|CFile::typeBi nary)) return;if (bmpFil e.Read(&bmpHea der,sizeof(BITMAP FILEH EADER)) != sizeof(BITMAP FILEH EADER)) {AfxMes sageB ox("read bmp header failed!");return;}if (bmpHea der.bfType != 0x4d42){AfxMes sageB ox("invali d file type!");return;}if (bmpFil e.Read(&bmpInf o,sizeof(BITMAP INFOH EADER)) != sizeof(BITMAP INFOH EADER)) {AfxMes sageB ox("read bmp inforheader failed!");return;}if (bmpInf o.biBitC ount!= 24){AfxMes sageB ox("File is not 24 bit.Applic ation doesn't suppor t this kind of file!");return;}pBmpIn fo = (BITMAP INFO*)new char[sizeof(BITMAP INFOH EADER)];if (!pBmpIn fo){AfxMes sageB ox("memory error!");return;}memcpy(pBmpIn fo,&bmpInf o,sizeof(BITMAP INFOH EADER));DWORDdataBy tes = bmpHea der.bfSize - bmpHea der.bfOffB its;pBmpDa ta = (BYTE*)new char[dataBy tes];if (!pBmpDa ta){AfxMes sageB ox("memory error!");delete pBmpDa ta;return;}if (bmpFil e.Read(pBmpDa ta,dataBy tes) != dataBy tes){AfxMes sageB ox("Read bmp data failed!");delete pBmpIn fo;delete pBmpDa ta;return;}bmpFil e.Close();CClien tDC *pDC = new CClien tDC(this);pDC->SetStr etchB ltMod e(COLORO NCOLO R);Stretc hDIBi ts(pDC->GetSaf eHdc(),0,0,bmpInf o.biWidt h,bmpInf o.biHeig ht,0,0,bmpInf o.biWidt h,bmpInf o.biHeig ht,pBmpDa ta,p BmpIn fo,DIB_RG B_COL ORS,SRCCOP Y);。
BMP文件结构与读写
![BMP文件结构与读写](https://img.taocdn.com/s3/m/6e362b0eba1aa8114431d9e0.png)
/luosha828/blog/item/032d0747bb9d74029313c6f8.html【转】 BMP文件结构与读写2011-02-12 10:43转载自qinshaoq最终编辑qinshaoqBMP文件结构1. BMP文件组成BMP文件由文件头、位图信息头、颜色信息和图形数据四部分组成。
文件头主要包含文件的大小、文件类型、图像数据偏离文件头的长度等信息.位图信息头包含图象的尺寸信息、图像用几个比特数值来表示一个像素、图像是否压缩、图像所用的颜色数等信息。
颜色信息包含图像所用到的颜色表,显示图像时需用到这个颜色表来生成调色板,但如果图像为真彩色,既图像的每个像素用24个比特来表示,文件中就没有这一块信息,也就不需要操作调色板。
文件中的数据块表示图像的相应的像素值,需要注意的是:图像的像素值在文件中的存放顺序为从左到右,从下到上,也就是说,在BMP文件中首先存放的是图像的最后一行像素,最后才存储图像的第一行像素,但对与同一行的像素,则是按照先左边后右边的的顺序存储的;另外一个需要关注的细节是:文件存储图像的每一行像素值时,如果存储该行像素值所占的字节数为4的倍数,则正常存储,否则,需要在后端补0,凑足4的倍数。
2. BMP文件头BMP文件头数据结构含有BMP文件的类型、文件大小和位图起始位置等信息。
其结构定义如下:typedef struct tagBITMAPFILEHEADER{WORD bfType; // 位图文件的类型,必须为BMDWORD bfSize; // 位图文件的大小,以字节为单位WORD bfReserved1; // 位图文件保留字,必须为0WORD bfReserved2; // 位图文件保留字,必须为0DWORD bfOffBits; // 位图数据的起始位置,以相对于位图文件头的偏移量表示,以字节为单位} BITMAPFILEHEADER;该结构占据14个字节。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
南通大学计算机科学与技术学院
《数字图像处理》课程实验
报告书
实验名 BMP文件的读写(8位和24位)
班级计 121
姓名张进
学号 1213022016
2014年6月 16 日
一、实验内容
1、了解BMP文件的结构
2、8位位图和24位位图的读取
二、BMP图形文件简介
BMP(Bitmap-File)图形文件是Windows采用的图形文件格式,在Windows环境下运行的所有图象处理软件都支持BMP图象文件格式。
Windows系统内部各图像绘制操作都是以BMP为基础的。
Windows 3.0以前的BMP图文件格式与显示设备有关,因此把这种BMP 图象文件格式称为设备相关位图DDB(device-dependent bitmap)文件格式。
Windows 3.0以后的BMP图象文件与显示设备无关,因此把这种BMP图象文件格式称为设备无关位图DIB(device-independent bitmap)格式(注:Windows 3.0以后,在系统中仍然存在DDB位图,象BitBlt()这种函数就是基于DDB位图的,只不过如果你想将图像以BMP格式保存到磁盘文件中时,微软极力推荐你以DIB格式保存),目的是为了让Windows能够在任何类型的显示设备上显示所存储的图象。
BMP位图文件默认的文件扩展名是BMP或者bmp(有时它也会以.DIB或.RLE作扩展名)。
位图文件可看成由4个部分组成:位图文件头(bitmap-file header)、位图信息头(bitmap-information header)、彩色表(color table)和定义位图的字节阵列,它具有如下所示的形式。
位图文件结构内容摘要
三、读写涉及的原理
1、图像的二值化的基本原理
图像的二值化处理就是讲图像上的点的灰度置为0或255,也就是讲整个图像呈现出明显的黑白效果。
即将256个亮度等级的灰度图像通过适当的阀值选取而获得仍然可以反映图像整体和局部特征的二值化图像。
在数字图像处理中,二值图像占有非常重要的地位,特别是在实用的图像处理中,以二值图像处理实现而构成的系统是很多的,要进行二值图像的处理与分析,首先要把灰度图像二值化,得到二值化图像,这样子有利于再对图像做进一步处理时,图像的集合性质只与像素值为0或255的点的位置有关,不再涉及像素的多级值,使处理变得简单,而且数据的处理和压缩量小。
为了得到理想的二值图像,一般采用封闭、连通的边界定义不交叠的区域。
所有灰度大于或等于阀值的像素被判定为属于特定物体,其灰度值为255表示,否则这些像素点被排除在物体区域以外,灰度值为0,表示背景或者例外的物体区域。
如果某特定物体在内部有均匀一致的灰度值,并且其处在一个具有其他等级灰度值的均匀背景下,使用阀值法就可以得到比较的分割效果。
如果物体同背景的差别表现不在灰度值上(比如纹理不同),可以将这个差别特征转换为灰度的差别,然后利用阀值选取技术来分割该图像。
动态调节阀值实现图像的二值化可动态观察其分割图像的具体结果。
2、图像的反色原理
对于彩色图像的R、G、B各彩色分量取反的技术就是图像的反色处理,这在处理二值化图像的连通区域选取的时候非常重要。
如物体连通域用黑色表示,而二值化后的物体连通域图像可那是白色的,而背景是黑色的,这时应手动选取图像的反色处理或有程序根据背景和物体连通域两种颜色的数量所占比例而自动选择是否选择选取图像的反色处理
四、读写转换代码
五、运行结果
24位位图24dog.bmp如下:
原图像的属性:
读取结果:
生成的新图片:
8位位图读取8dog.bmp如下
图片属性:
读取的结果:
生成的新图片:
六、心得体会
大一学的c++,现在却发现忘得差不多了,在程序实现上遇到了困难。
但是本次实验确实又再一次的让我接触了c语言。
这次实验掌握了BMP文件的读取,第一次对图像有这么深的认识了解。
对图像的组成不再是以前那种错误的认识,有收获。