www.pudn.com > Hough.rar > BMP.cpp


#include "stdafx.h" 
#include  
#include "BMPFormat.h" 
 
/**************************************************************************************  
* 函数名:ReadBinaryBMP 
* 功能:读二值BMP图像 
* 说明:1、从fullfilename文件中读取数据,把BMP头赋给headBMP, 把信息头赋给infoHead,  
*          把调色板数据读到pRgbPlates指定的内存块中, 
*          把图像数据读到pImgData指定的内存块中,图像数据的个数为dataCount, 
*          把剩余数据读到pLeftData指定的内存块中,剩余数据的个数为leftDataCount, 
*          出错信息赋给errorMsg, 状态信息赋给info 。 
*       2、在本函数内用malloc()函数分别为调色板、图像数据、其余数据分配了内存, 
*          并把相应指针赋给pRgbPlates、pImgData、pLeftData,在函数外部的适当地方 
*          应该用free()释放pRgbPlates、pImgData、pLeftData指向的内存。 
* 输入参数: 
*       fullfilename  --- 带路径的BMP文件名 
* 输出参数: 
*       headBMP       --- BMP头 
*       infoHead      --- 信息头 
*       pRgbPlates    --- 指向调色板 
*       rgbPlateDataCount --- 调色板所占的字节数 (对于8位图像,应该有256个调色板项,每项4个字节) 
*       pImgData      --- 指向图像数据内存块 
*       dataCount     --- 图像数据所占的字节数 
*       pLeftData     --- 图像文件中多余的字节数据 
*       leftDataCount --- 图像文件中多余的字节个数 
*       errorMsg      --- 错误信息 
*       info          --- 非错误信息 
* 返回值: 
*       未发生错误,返回TRUE; 发生错误,返回FALSE; 
*       当返回TRUE时,info中存放的是函数执行过程中的状态信息。 
*       当返回FALSE时,errorMsg中存放的是函数执行过程中的出错信息。 
****************************************************************************************/ 
 
BOOL ReadBinaryBMP(CString fullfilename, BmpHead& headBMP, InfoHead& infoHead,   
				   BYTE*& pRgbPlates, long& rgbPlateDataCount,  
				   BYTE*& pImgData, long& dataCount,  
				   /*BYTE*& pLeftData, long& leftDataCount, */ 
				   CString& errorMsg, CString& info) 
{ 
//     BmpHead  headBMP; 
//     InfoHead infoHead;  
    FILE* p; 
    p = fopen(fullfilename,"rb"); 
    if (p == NULL) 
    { 
        errorMsg.Format("*** Error: file %s open failed! *** \n", fullfilename); 
        return FALSE; 
    } 
 
    info.Format("file %s open success.\n",fullfilename);  
/**********   read BMP head ********************/ 
	WORD mark; 
	fread(&mark,1,2,p); 
    //fseek(p,2,SEEK_CUR); 
	if(mark != 19778)   //'BM' 
	{ 
		errorMsg = "*** Error: the picture is not of the format of bmp! *** \n"; 
		return FALSE; 
	} 
 
    fread(&headBMP,1,12,p); 
		//headBMP.show(); 
		CString msg; 
		msg.Format("Image Size:%d \n",headBMP.imageSize); 
		info += msg; 
		msg.Format("Image Data Start Position : %d \n",headBMP.startPosition); 
		info += msg; 
    fread(&infoHead,1,40,p); 
		if (infoHead.bitColor != 8)     
		{ 
			fclose(p); 
			errorMsg.Format("*** Error: This is not a picture of 8 bits *** \n"); 
			return FALSE; 
		} 
		if (infoHead.height > 0) 
		{ 
			// 倒向图像,图像数据存储从左到右,从下至上,即从左下角到右上角。大部分bmp图像都是倒向图像 
			msg.Format("Normal Image, That is, \n  The pixel data is stored from left to right, from bottom to top. \n"); 
		} 
		else 
		{ 
			// 正向图像,图像数据存储从左到右,从上到下,即从左上角到右下角 
			msg.Format("Special Image, That is, \n  The pixel data is stored form left to right, from top to bottom. \n"); 
		} 
		info += msg; 
		msg.Format("Image Size : %d * %d \n", infoHead.width, infoHead.height); 
		info += msg; 
		if ((infoHead.width % 4) != 0) 
		{ 
			// 当infoHead.width不是4的倍数时,在保存图像数据到文件中时,每一行的最后要补充0,使每一行的字节数为4的倍数。 
			msg.Format("The image width is not the multiple of 4, \n  so that zeros will be added at each end of the image row. \n"); 
			info += msg; 
		} 
		else 
		{ 
			msg.Format("The image width is the multiple of 4, \n  so that no zero was added at end of each row. \n"); 
		} 
/***********  read Palette     **************/ 
	rgbPlateDataCount = 256 * sizeof(RGBMixPlate); // 256个调色板项,每项4个字节 
	pRgbPlates = new BYTE[rgbPlateDataCount]; 
	fread(pRgbPlates, 1, rgbPlateDataCount, p); 
 
/***********  read Image Date  **************/ 
	if ((infoHead.realSize != 0) && ((infoHead.width % 4) == 0)) 
	{ 
		dataCount = infoHead.realSize;     
	} 
	else    // infoHead.realSize == 0 或 (infoHead.width % 4) != 0 
	{ 
		dataCount = infoHead.width * infoHead.height * (infoHead.bitColor/8); 
	} 
	pImgData = new BYTE[dataCount]; 
 
	if (infoHead.width % 4 == 0)    // 宽度(以像素计)是4的倍数,则图像数据区中的每一行末尾不用添加0 
	{ 
		fread(pImgData, 1, dataCount, p);    // 直接把所有数据读进内存 
		msg.Format("No zero need to be added at end of row. \n  Image data have been read at one time. \n"); 
		info += msg; 
	} 
	else   // 宽度(以像素计)不是4的倍数,则图像数据区中的每一行末尾要添加0,使每行的像素数是4的倍数    
	{ 
		// 在图像数据的每一行末尾要添加0的个数(以像素为单位) 
		int nAddedZerosCount = (infoHead.width/4 + 1) * 4 - infoHead.width; 
		msg.Format("At each end of row, %d byte of zeros have been added. \n", nAddedZerosCount); 
		info += msg; 
		for (int i=0; i