📄 image.cpp
字号:
// Image.cpp: implementation of the CImage class.
//
//////////////////////////////////////////////////////////////////////
#include "stdafx.h"
#include "Image.h"
#include "cdib.h"
#include "imgprocessing.h"
#include "math.h"
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif
#define PI 3.1415926535
//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
CImage::CImage()
{
m_Height=0;
m_Width=0;
}
CImage::~CImage()
{
}
bool CImage::ReadBmpFile(CString& fileName,CDib& dib)
{
int i,j;
CFile file;
BYTE buf;
dib.Empty();//clear the CDib
//open the file
if (file.Open(fileName, CFile::modeRead)==FALSE) return false;
//read the bmp to CDib
if (dib.Read(&file) == FALSE) return false;
//set the CFaceImage
CSize ImageSize=dib.GetDimensions();
SetSize(ImageSize.cy,ImageSize.cx);
int supplement=(4-(m_Width%4))%4;
m_ImageBody.RemoveAll();//nessesary
m_ImageBody.SetSize(m_Height*m_Width);
for(i=0;i<m_Height;i++)
for(j=0;j<m_Width;j++)
{
switch(dib.m_lpBMIH->biBitCount)
{
case 8://8 bit color
buf=*(LPSTR)(dib.m_lpImage+i*(m_Width+supplement)+j);
break;
case 4://4 bit color
buf=*(LPSTR)(dib.m_lpImage+(i*(m_Width+supplement)+j)/2);
if((j%2)==1) buf=buf/16;
else buf=buf%16;
break;
default:
return false;
}
//transform the color to gray
//red=*(LPSTR)((LPSTR)dib.m_lpvColorTable+buf*4);
//green=*(LPSTR)((LPSTR)dib.m_lpvColorTable+buf*4+1);
//blue=*(LPSTR)((LPSTR)dib.m_lpvColorTable+ buf*4+2);
//buf=(BYTE)(0.30*red+0.59*green+0.11*blue);
m_ImageBody[(m_Height-i-1)*m_Width+j]=buf;
}
return true;
}
bool CImage::ReadImageFile(CString fileName)
{
//AfxMessageBox("Hello");
CFile* pFile=new CFile();
//open file
if(pFile->Open(fileName,CFile::modeRead)==NULL)
{
AfxMessageBox("File read error!");
pFile->Close();
return false;
}
//read the file flag
/* WORD filemark;
if(pFile->Read(&filemark,sizeof(WORD))!=sizeof(WORD))
{
AfxMessageBox("File read error!");
pFile->Close();
return false;
}
//check the file type
if(filemark!=IMG_HEADER_MARKER)
{
AfxMessageBox("File not a AFR file!");
pFile->Close();
return false;
}
*/ //read the infomation and image to CFaceImage
int width,height;
pFile->Read(&width,sizeof(DWORD));
pFile->Read(&height,sizeof(DWORD));
SetSize(height,width);
int i,j;
m_ImageBody.RemoveAll();//nessesary
m_ImageBody.SetSize(height*width);
BYTE* buf;
buf=new BYTE[height*width];
pFile->Read(buf,sizeof(BYTE)*height*width);
for(i=0;i<height;i++)
for(j=0;j<width;j++)
{
m_ImageBody[i*width+j]=buf[i*width+j];
}
pFile->Close();
delete buf;
delete pFile;
// m_Msg="The image infomation:\n";
// CString str;
// str.Format("The width : %d\nThe Height : %d\n",width,height);
// m_Msg+=str;
return true;
}
bool CImage::GetBmpData(CDib &mdib)
{
int i,j;
BYTE buf;
//set the CImage
CSize ImageSize=mdib.GetDimensions();//得到图像的大小
SetSize(ImageSize.cy,ImageSize.cx);
BYTE buf24[3];
int supplement=(4-(m_Width%4))%4;
m_ImageBody.RemoveAll();//nessesary
if(mdib.m_lpBMIH->biBitCount==24)
{
m_ImageBody.SetSize(m_Height*m_Width*3);
m_ImageBodyBlue.SetSize(m_Height*m_Width);
m_ImageBodyGreen.SetSize(m_Height*m_Width);
m_ImageBodyRed.SetSize(m_Height*m_Width);
}
else
m_ImageBody.SetSize(m_Height*m_Width);
for(i=0;i<m_Height;i++)
for(j=0;j<m_Width;j++)
{
switch(mdib.m_lpBMIH->biBitCount)
{
case 8://8 bit color
buf=*(LPSTR)(mdib.m_lpImage+i*(m_Width+supplement)+j);
break;
case 4://4 bit color
buf=*(LPSTR)(mdib.m_lpImage+(i*(m_Width+supplement)+j)/2);
if((j%2)==1) buf=buf/16;
else buf=buf%16;
break;
case 24://24 bit color
buf24[0] = *(LPSTR)(mdib.m_lpImage+(i*(m_Width+supplement)+j)*3);
buf24[1] = *(LPSTR)(mdib.m_lpImage+(i*(m_Width+supplement)+j)*3+1);
buf24[2] = *(LPSTR)(mdib.m_lpImage+(i*(m_Width+supplement)+j)*3+2);
break;
default:
return false;
}
if(mdib.m_lpBMIH->biBitCount==24)
{ //bmp图像数据区数据
m_ImageBody[((m_Height-i-1)*m_Width+j)*3]=buf24[0];
m_ImageBody[((m_Height-i-1)*m_Width+j)*3+1]=buf24[1];
m_ImageBody[((m_Height-i-1)*m_Width+j)*3+2]=buf24[2];
//分别存储RGB颜色值
m_ImageBodyBlue[(m_Height-i-1)*m_Width+j]=buf24[0];
m_ImageBodyGreen[(m_Height-i-1)*m_Width+j]=buf24[1];
m_ImageBodyRed[(m_Height-i-1)*m_Width+j]=buf24[2];
}
else
m_ImageBody[(m_Height-i-1)*m_Width+j]=buf;
}
return true;
}
void CImage::Copy(CImage& newimg)
{
int height=GetHeight();
int width=GetWidth();
newimg.SetSize(height,width);
CRect rect;
rect.SetRect(0,0,width,height);
Img_Seperate(m_ImageBody,newimg.m_ImageBody,
height,width,rect);
}
void CImage::Crop(CImage& newimg,CRect& rect)
{
CByteArray imgbuf;
if(&newimg.m_ImageBody==&m_ImageBody)
{
Img_Copy(m_ImageBody,imgbuf);
Img_Seperate(imgbuf,newimg.m_ImageBody,GetHeight(),GetWidth(),rect);
}
else
{
Img_Seperate(m_ImageBody,newimg.m_ImageBody,GetHeight(),GetWidth(),rect);
}
newimg.SetSize(rect.Height(),rect.Width());
}
void CImage::Zoom(CImage& newimg,int newheight,int newwidth)
{
CByteArray imgbuf;
if (&m_ImageBody==&newimg.m_ImageBody)
{
Img_Copy(m_ImageBody,imgbuf);
Img_ScaleTransform(imgbuf,newimg.m_ImageBody,
GetHeight(),GetWidth(),
newheight,newwidth);
}
else
Img_ScaleTransform(m_ImageBody,newimg.m_ImageBody,
GetHeight(),GetWidth(),
newheight,newwidth);
newimg.SetSize(newheight,newwidth);
}
int CImage::Threshold(CImage& newimg,int threshold)
{
int num;
CByteArray imgbuf;
if(&m_ImageBody==&newimg.m_ImageBody)
num=Img_Threshold(newimg.m_ImageBody,GetHeight(),
GetWidth(),threshold);
else
{
Img_Copy(m_ImageBody,newimg.m_ImageBody);
num=Img_Threshold(newimg.m_ImageBody,GetHeight(),GetWidth(),threshold);
}
newimg.SetSize(GetHeight(),GetWidth());
return num;
}
BOOL CImage::HoughTran(CImage& newimg)
{
long lWidth,lHeight;
lWidth=GetWidth() ;
lHeight=GetHeight() ;
// 图像每行的字节数
LONG lLineBytes;
lLineBytes=m_Width ;
//变换域的尺寸
int iMaxDist;
int iMaxAngleNumber;
//变换域的坐标
int iDist;
int iAngleNumber;
//循环变量
long i;
long j;
//存储变换域中的两个最大值
MaxValue MaxValue1;
MaxValue MaxValue2;
newimg.m_ImageBody.RemoveAll ();
//newimg.SetSize(GetHeight(),GetWidth());
newimg.m_ImageBody.SetSize(lWidth*lHeight);
//计算变换域的尺寸
//最大距离
iMaxDist = (int) sqrt((double)lWidth*lWidth + lHeight*lHeight);
//角度从0-180,每格2度
iMaxAngleNumber = 180;//90
for(j = 0; j <lHeight; j++)
{
for(i = 0;i <lWidth; i++)
{
// 指向源图像倒数第j行,第i个象素的指针
//目标图像中含有0和255外的其它灰度值
if(m_ImageBody[lLineBytes * j + i] != 255 && m_ImageBody[lLineBytes * j + i] != 0)
return FALSE;
//如果是黑点,则在变换域的对应各点上加1
if(m_ImageBody[lLineBytes * j + i] == 0)
{
//注意步长是2度
for(iAngleNumber=0; iAngleNumber<iMaxAngleNumber; iAngleNumber++)
{
iDist = (int) fabs(i*cos(iAngleNumber*2*PI/180.0) + \
j*sin(iAngleNumber*2*PI/180.0));
//变换域的对应点上加1
// *(lpTransArea+iDist*iMaxAngleNumber+iAngleNumber) = \
// *(lpTransArea+iDist*iMaxAngleNumber+iAngleNumber) +1;
newimg.m_ImageBody[iDist*iMaxAngleNumber+iAngleNumber] = newimg.m_ImageBody [iDist*iMaxAngleNumber+iAngleNumber] + 1;
}
}
}
}
//找到变换域中的两个最大值点
MaxValue1.Value=0;
MaxValue2.Value=0;
//找到第一个最大值点
for (iDist=0; iDist<iMaxDist;iDist++)
{
for(iAngleNumber=0; iAngleNumber<iMaxAngleNumber; iAngleNumber++)
{
if((int)newimg.m_ImageBody[iDist*iMaxAngleNumber+iAngleNumber]>MaxValue1.Value)
if((int)newimg.m_ImageBody [iDist*iMaxAngleNumber+iAngleNumber]>MaxValue1.Value)
{
MaxValue1.Value = (int)newimg.m_ImageBody[iDist*iMaxAngleNumber+iAngleNumber];
MaxValue1.Dist = iDist;
MaxValue1.AngleNumber = iAngleNumber;
}
}
}
//将第一个最大值点附近清零
for (iDist = -9;iDist < 10;iDist++)
{
for(iAngleNumber=-1; iAngleNumber<2; iAngleNumber++)
{
if(iDist+MaxValue1.Dist>=0 && iDist+MaxValue1.Dist<iMaxDist \
&& iAngleNumber+MaxValue1.AngleNumber>=0 && iAngleNumber+MaxValue1.AngleNumber<=iMaxAngleNumber)
{
newimg.m_ImageBody[(iDist+MaxValue1.Dist)*iMaxAngleNumber+\
(iAngleNumber+MaxValue1.AngleNumber)]=0;
}
}
}
//找到第二个最大值点
for (iDist=0; iDist<iMaxDist;iDist++)
{
for(iAngleNumber=0; iAngleNumber<iMaxAngleNumber; iAngleNumber++)
{
if((int)newimg.m_ImageBody[iDist*iMaxAngleNumber+iAngleNumber]>MaxValue2.Value)
{
MaxValue2.Value = (int)newimg.m_ImageBody [iDist*iMaxAngleNumber+iAngleNumber];
MaxValue2.Dist = iDist;
MaxValue2.AngleNumber = iAngleNumber;
}
}
}
//两直线平行,在缓存图像中重绘这两条直线
for(j = 0; j <lHeight; j++)
{
for(i = 0;i <lWidth; i++)
{
// 指向缓存图像倒数第j行,第i个象素的指针
//lpDst = (char *)lpNewDIBBits + lLineBytes * j + i;
//如果该点在某一条平行直线上,则在缓存图像上将该点赋为黑
//在第一条直线上
iDist = (int) fabs(i*cos(MaxValue1.AngleNumber*2*PI/180.0) + \
j*sin(MaxValue1.AngleNumber*2*PI/180.0));
if (iDist == MaxValue1.Dist)
newimg.m_ImageBody [lLineBytes * j + i] = (unsigned char)255;
//在第二条直线上
iDist = (int) fabs(i*cos(MaxValue2.AngleNumber*2*PI/180.0) + \
j*sin(MaxValue2.AngleNumber*2*PI/180.0));
if (iDist == MaxValue2.Dist)
newimg.m_ImageBody [lLineBytes * j + i] = (unsigned char)255;
}
}
/*
//两直线平行,在缓存图像中重绘这两条直线
for(j = 0; j <lHeight; j++)
{
for(i = 0;i <lWidth; i++)
{
// 指向缓存图像倒数第j行,第i个象素的指针
//newimg.m_ImageBody [lLineBytes * j + i];
//如果该点在某一条平行直线上,则在缓存图像上将该点赋为黑
//在第一条直线上
iDist = (int) fabs(i*cos(MaxValue1.AngleNumber*2*PI/180.0) + \
j*sin(MaxValue1.AngleNumber*2*PI/180.0));
if (iDist == MaxValue1.Dist)
newimg.m_ImageBody [lLineBytes * j + i] = (unsigned char)255;
}
}
*/
newimg.SetSize(512,512);
// 返回
return TRUE;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -