⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 winpic.cpp

📁 用在X86芯片的,嵌入式系统中的自动更新程序
💻 CPP
字号:
// WinPic.cpp: implementation of the CWinPic class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "LCYImageProcess.h"
#include "WinPic.h"
#include "SuoFangDlg.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif



//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

CWinPic::CWinPic()
{
	m_ImageData = NULL;
	m_BmpFile = NULL;
	m_BiWidth = 0;
	m_BiHeight = 0;



}

CWinPic::~CWinPic()
{
	delete[] m_ImageData;
	delete m_BmpFile;

}



//打开BMP文件
int CWinPic::OpenFile(CString filepath)
{
	m_BmpFile=new CFile;
	if(!(m_BmpFile->Open(filepath,CFile::modeRead)))
	{
		return FILE_OPEN_FAILED;
	}
	m_BmpFile->SeekToBegin();
	m_BmpFile->Read(&m_FileHeader,sizeof(m_FileHeader));
	char* IsBmp;
	IsBmp=(char*)&(m_FileHeader.bfType);
	//如果不是BMP文件,或文件有错误
	if(IsBmp[0]!='B'||IsBmp[1]!='M'||m_FileHeader.bfSize!=m_BmpFile->GetLength())
	{
		return FILE_ERROR;
	}
	return INIT_SUCCESS;
}

RGBCOLOR* CWinPic::LoadImageData()
{ 


	
	
	if(!m_BmpFile)
	{
		return NULL;
	}
	m_BmpFile->SeekToBegin();
	m_BmpFile->Read(&m_FileHeader,sizeof(m_FileHeader));
	m_BmpFile->Read(&m_InfoHeader,sizeof(m_InfoHeader));
	//得到图象的宽度,高度和位深度
	m_BiWidth=m_InfoHeader.biWidth;
	m_BiHeight=m_InfoHeader.biHeight;
	m_BibitCount=m_InfoHeader.biBitCount;

    //为图象数据指针分配空间
	m_ImageData=(RGBCOLOR*)(new BYTE[m_BiWidth*m_BiHeight*3*10*10]);
    //读取图象数据
	switch(m_BibitCount)
	{
	case 1:
		if(ReadImageData_1())
		{
			return m_ImageData;
		}
		else
		{ 
			return NULL;
		}
	case 4:
		if(ReadImageData_4())
		{
			return m_ImageData;
		}
		else
		{
			return NULL;
		}
	case 8:
		if(ReadImageData_8())
		{
			return m_ImageData;
		}
		else
		{
			return NULL;
		}
	case 16:
		if(ReadImageData_16())
		{
			return m_ImageData;
		}
		else
		{
			return NULL;
		}
	case 24:
		if(ReadImageData_24())
		{
			return m_ImageData;
		}
		else
		{
			return NULL;
		}
	default:
		return NULL;

	}


}
/*////////////////////////
从深度为1的位图中获得每个象素点的RGB值
成功返回TRUE,失败返回FALSE
/////////////////////////*/

bool CWinPic::ReadImageData_1()
{
	//读取调色板2个
    RGBCOLOR* palette=new RGBCOLOR[2];
	m_BmpFile->Seek(54,CFile::begin);//Move the file pointer 54 bytes forward from the beginning of the file.
	m_BmpFile->Read(&palette[0].rgbBlue,1);//1-The maximum number of bytes to be read from the file
	m_BmpFile->Read(&palette[0].rgbGreen,1);
	m_BmpFile->Read(&palette[0].rgbRed,1);
	m_BmpFile->Seek(1,CFile::current); //1-  Move the file pointer 1 bytes from the current position in the file
    m_BmpFile->Read(&palette[1].rgbBlue,1);
	m_BmpFile->Read(&palette[1].rgbGreen,1);
	m_BmpFile->Read(&palette[1].rgbRed,1);
	//读取位图数据
	m_BmpFile->Seek(m_FileHeader.bfOffBits,CFile::begin);
	int width=m_BiWidth/8;
	if(m_BiWidth%8)
	{
		width++;
	}
	BYTE* data=new BYTE[width*m_BiHeight];
	for(int i=0;i<m_BiHeight;i++)
	{
		m_BmpFile->Read(&data[(m_BiHeight-i-1)*width],width);//width-The maximum number of bytes to be read from the file
		////如果存储图象每行象素的字节数不是4的倍数,每次读一行位图数据后要越过空白字符
		if(width%4)
		{
			m_BmpFile->Seek(4-width%4,CFile::current);
		}
	}
    //由位图数据和调色板获得每个象素点的RGB值
	for(i=0;i<m_BiHeight;i++)
	{
		int j=i*width;
		int n=0;
		for(int k=0;k<m_BiWidth;k++)
		{
			if(n==8)
			{
				n=0;
				j++;
			}
			BYTE temp;
			temp=data[j]&(0x80 >> n);
			n++;
			//位图数据错误
			if(m_InfoHeader.biClrUsed==1&&temp!=0)
			{
				delete[] data;
				delete[] palette;
				return false;     
			}
			RGBCOLOR* p=m_ImageData;
			if(temp)
			{
				p[i*m_BiWidth+k].rgbBlue=palette[1].rgbBlue;
				p[i*m_BiWidth+k].rgbGreen=palette[1].rgbGreen;
				p[i*m_BiWidth+k].rgbRed=palette[1].rgbRed;

			}
			else
			{
				p[i*m_BiWidth+k].rgbBlue=palette[0].rgbBlue;
				p[i*m_BiWidth+k].rgbGreen=palette[0].rgbGreen;
				p[i*m_BiWidth+k].rgbRed=palette[0].rgbRed;

			}

		}
	}
	delete[] data;
	delete[] palette;
	return true;
}


/*////////////////////////
从深度为4的位图中获得每个象素点的RGB值
成功返回TRUE,失败返回FALSE
/////////////////////////*/	
bool CWinPic::ReadImageData_4()
{
    //读取调色板16个//
	RGBCOLOR* palette=new RGBCOLOR[16];
	m_BmpFile->Seek(54,CFile::begin);
	for(int i=0;i<16;i++)
	{
		m_BmpFile->Read(&palette[i].rgbBlue,1);
		m_BmpFile->Read(&palette[i].rgbGreen,1);
		m_BmpFile->Read(&palette[i].rgbRed,1);
		m_BmpFile->Seek(1,CFile::current);
	}
	//读取位图数据
	m_BmpFile->Seek(m_FileHeader.bfOffBits,CFile::begin);
	int width=m_BiWidth/2+m_BiWidth%2;
	BYTE* data=new BYTE[width*m_BiHeight];
	for(i=0;i<m_BiHeight;i++)
	{
		m_BmpFile->Read(&data[(m_BiHeight-i-1)*width],width);
		if(width%4)
		{
			////如果存储图象每行象素的字节数不是4的倍数,每次读一行位图数据后要越过空白字符
			m_BmpFile->Seek(4-width%4,CFile::current);
		}
	}
    //由位图数据和调色板获得每个象素点的RGB值
	for(i=0;i<m_BiHeight;i++)
	{
		int j=i*width;
		for(int k=0;k<m_BiWidth;k++)
		{
			BYTE temp;
			if(k%2)
			{
				temp = data[j++] << 4;
				temp = temp >> 4;
			}
			else
			{
				temp = data[j] >> 4;
			}
			if(m_InfoHeader.biClrUsed && temp>m_InfoHeader.biClrUsed)
			{
				delete[] data;
				delete[] palette;
				return false;  //位图数据错误
			}
			m_ImageData[i*m_BiWidth+k].rgbBlue=palette[temp].rgbBlue;
			m_ImageData[i*m_BiWidth+k].rgbGreen=palette[temp].rgbGreen;
			m_ImageData[i*m_BiWidth+k].rgbRed=palette[temp].rgbRed;
		}
	}
	delete[] data;
	delete[] palette;
	return true;
}

bool CWinPic::ReadImageData_8()
{
	//读取调色板
	RGBCOLOR *palette = new RGBCOLOR[256];
	m_BmpFile->Seek(54, CFile::begin);
	for(int i=0; i<256; i++)
	{
		m_BmpFile->Read(&palette[i].rgbBlue, 1);
		m_BmpFile->Read(&palette[i].rgbGreen, 1);
		m_BmpFile->Read(&palette[i].rgbRed, 1);
		m_BmpFile->Seek(1, CFile::current);
	}

	//读取位图数据
	m_BmpFile->Seek(m_FileHeader.bfOffBits, CFile::begin);
    BYTE *data = new BYTE[m_BiHeight*m_BiWidth];
    for(i=0; i<m_BiHeight; i++)
	{
		m_BmpFile->Read(&data[(m_BiHeight-i-1)*m_BiWidth], m_BiWidth);

		//如果图象宽度不是4的倍数,每次读一行位图数据后要越过空白字符
		if(m_BiWidth%4)   
			m_BmpFile->Seek(4-m_BiWidth%4, CFile::current);
	}

	//由位图数据查位图颜色表,获得每个象素点颜色的R,G,B分量
	for(LONG j=0; j<m_BiHeight*m_BiWidth; j++)
	{
		if(m_InfoHeader.biClrUsed && data[j]>m_InfoHeader.biClrUsed)
		{
			delete[] data;
			delete[] palette;
			return false;  //位图数据错误
		}
	
		m_ImageData[j].rgbBlue  = palette[data[j]].rgbBlue;
		m_ImageData[j].rgbGreen = palette[data[j]].rgbGreen;
		m_ImageData[j].rgbRed   = palette[data[j]].rgbRed;
	}	
	delete[] data;
	delete[] palette;
	return true;
}

/*/////////////////////////////////////////
	从位深度为16的位图中获得每个象素点
	的RGB值,成功返回true,失败返回false
/////////////////////////////////////////*/
bool CWinPic::ReadImageData_16()
{
	m_BmpFile->Seek(m_FileHeader.bfOffBits, CFile::begin);
	WORD temp;
	for(int i=m_BiHeight-1; i>=0; i--)
	{
		for(int j=0; j<m_BiWidth; j++)
		{
			m_BmpFile->Read(&temp, 2);
			m_ImageData[i*m_BiWidth+j].rgbRed   = temp >> 10;
			m_ImageData[i*m_BiWidth+j].rgbGreen = (temp & 0x03E0) >> 5;
			m_ImageData[i*m_BiWidth+j].rgbBlue  = (temp & 0x001F);

			m_ImageData[i*m_BiWidth+j].rgbRed   *= 8;
			m_ImageData[i*m_BiWidth+j].rgbGreen *= 8;
			m_ImageData[i*m_BiWidth+j].rgbBlue  *= 8;

		}

		//如果图象宽度不是4的倍数,每次读一行位图数据后要越过空白字符
		if((m_BiWidth*2)%4)
		{
			m_BmpFile->Seek(4-(m_BiWidth*2)%4, CFile::current);
		}
	}
	return true;

}


/*/////////////////////////////////////////
	从位深度为24的位图中获得每个象素点
	的RGB值,成功返回true,失败返回false
/////////////////////////////////////////*/
bool CWinPic::ReadImageData_24()
{
	m_BmpFile->Seek(m_FileHeader.bfOffBits, CFile::begin);
	for(int i=m_BiHeight-1; i>=0; i--)
	{
		for(int j=0; j<m_BiWidth; j++)
		{
			m_BmpFile->Read(&(m_ImageData[i*m_BiWidth+j].rgbBlue), 1);
			m_BmpFile->Read(&(m_ImageData[i*m_BiWidth+j].rgbGreen), 1);
			m_BmpFile->Read(&(m_ImageData[i*m_BiWidth+j].rgbRed), 1);
		}

		//如果存储图象每行象素的字节数不是4的倍数,每次读一行位图数据后要越过空白字符
		if((m_BiWidth*3)%4)
			m_BmpFile->Seek(4-(m_BiWidth*3)%4, CFile::current);
	}
	return true;
}

//图象按比例缩放
void CWinPic::SuoFang(float zoom)
{
	long x_old,y_old,x_new,y_new;
	float num=(float)1.0/zoom;
	long w_old=m_BiWidth;
	long h_old=m_BiHeight;
	long w_new=(long) (w_old*zoom);
	long h_new=(long) (h_old*zoom);
	RGBCOLOR* rgb=(RGBCOLOR*)new BYTE[w_new*h_new*3];
    for(y_new=0;y_new<h_new;y_new++)
	{
		for(x_new=0;x_new<w_new;x_new++)
		{
			x_old=(long)(x_new*num);
			y_old=(long)(y_new*num);
			if((x_old>=0) && (x_old<w_old) && (y_old>=0) && (y_old<h_old))
			{
				//rgb[(h_new-y_new-1)*w_new+x_new].rgbRed=m_imageData[(h_old-y_old-1)*w_old+x_old].rgbRed;
			//	rgb[(h_new-y_new-1)*w_new+x_new].rgbGreen=m_imageData[(h_old-y_old-1)*w_old+x_old].rgbGreen;
			//	rgb[(h_new-y_new-1)*w_new+x_new].rgbBlue=m_imageData[(h_old-y_old-1)*w_old+x_old].rgbBlue;


                rgb[y_new*w_new+x_new].rgbRed=m_ImageData[y_old*w_old+x_old].rgbRed;
				rgb[y_new*w_new+x_new].rgbGreen=m_ImageData[y_old*w_old+x_old].rgbGreen;
				rgb[y_new*w_new+x_new].rgbBlue=m_ImageData[y_old*w_old+x_old].rgbBlue;
                

			}

		}

	}
	for(int i=0;i<w_new*h_new;i++)
	{
		m_ImageData[i].rgbRed=rgb[i].rgbRed;
		m_ImageData[i].rgbGreen=rgb[i].rgbGreen;
		m_ImageData[i].rgbBlue=rgb[i].rgbBlue;
	}
	m_BiWidth=w_new;
	m_BiHeight=h_new;

	delete[] rgb;

}

//图象不按比例缩放
void CWinPic::SuoFang1(float zoom1,float zoom2)
{
	long x_old,y_old,x_new,y_new;
	//得到新旧图象的转换系数
	float num1=(float)1.0/zoom1;
	float num2=(float)1.0/zoom2;

	long w_old=m_BiWidth;
	long h_old=m_BiHeight;
	//新图象的高宽
	long w_new=(long) (w_old*zoom1);
	long h_new=(long) (h_old*zoom2);
	//分配存储新图象的临时空间
	RGBCOLOR* rgb=(RGBCOLOR*)new BYTE[w_new*h_new*3];
    for(y_new=0;y_new<h_new;y_new++)
	{
		for(x_new=0;x_new<w_new;x_new++)
		{
			x_old=(long)(x_new*num1);
			y_old=(long)(y_new*num2);
			if((x_old>=0) && (x_old<w_old) && (y_old>=0) && (y_old<h_old))
			{
				rgb[y_new*w_new+x_new].rgbRed=m_ImageData[y_old*w_old+x_old].rgbRed;
				rgb[y_new*w_new+x_new].rgbGreen=m_ImageData[y_old*w_old+x_old].rgbGreen;
				rgb[y_new*w_new+x_new].rgbBlue=m_ImageData[y_old*w_old+x_old].rgbBlue;
                

			}

		}

	}
	for(int i=0;i<w_new*h_new;i++)
	{
		m_ImageData[i].rgbRed=rgb[i].rgbRed;
		m_ImageData[i].rgbGreen=rgb[i].rgbGreen;
		m_ImageData[i].rgbBlue=rgb[i].rgbBlue;
	}
	m_BiWidth=w_new;
	m_BiHeight=h_new;
    //删除临时空间
	delete[] rgb;

}

//图象平移
void CWinPic::Move(long xoff, long yoff)
{
	//原图象的高,宽
	long width=m_BiWidth;  
	long height=m_BiHeight;

    //新图象的高宽
	long width_new=width+xoff; 
	long height_new=height+yoff;
	long x0,y0,x1,y1;
	//分配存储新图象数据的临时空间
    RGBCOLOR* temp=(RGBCOLOR*)new BYTE[width_new*height_new*3];

    for(y1=0;y1<height_new;y1++)
	{
		for(x1=0;x1<width_new;x1++)
		{
			x0=x1-xoff;
			y0=y1-yoff;
			//将原图象数据复制到新图象
			if((y0>=0) && (y0<height) && (x0>=0) && (x0<width))
			{
				 temp[y1*width_new+x1].rgbRed=m_ImageData[y0*width+x0].rgbRed;
                 temp[y1*width_new+x1].rgbGreen=m_ImageData[y0*width+x0].rgbGreen;
                 temp[y1*width_new+x1].rgbBlue=m_ImageData[y0*width+x0].rgbBlue;
			}
			//对于原图象中没有的数据,直接赋值
			else
			{
                  temp[y1*width_new+x1].rgbRed=255;
                  temp[y1*width_new+x1].rgbGreen=255;
                  temp[y1*width_new+x1].rgbBlue=255;

			}
		}
		
	}
	m_BiWidth=width_new;
	m_BiHeight=height_new;
	//存储新图象的数据
	for(int i=0;i<width_new*height_new;i++)
	{
		m_ImageData[i].rgbRed=temp[i].rgbRed;
        m_ImageData[i].rgbGreen=temp[i].rgbGreen;
        m_ImageData[i].rgbBlue=temp[i].rgbBlue;

	}
    //删除临时空间
	delete[] temp;


}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -