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

📄 imageprocess.cpp

📁 医学图象处理系统
💻 CPP
📖 第 1 页 / 共 5 页
字号:
		{
			InputImage[i] = 0;
		}
	}
	if(r != NULL)          delete []r;
	if(mid != NULL)        delete []mid;
}
void Image_SUSAN_Principle(BYTE* InputImage , int ImgW , int ImgH ,int bt)
{
	int	 Imagesize = ImgW*ImgH;
	if (InputImage==NULL || Imagesize==0) return ;
	
	int    i, j, n, max_no=1850;
	int    Width=ImgW, Height=ImgH;
    int    *r  =new int[Imagesize];
	BYTE   *mid = new BYTE[Imagesize];
	BYTE   *in=InputImage;
	BYTE   *p,*cp,*bp,bbp[516];
    double temp; 
     
    bbp[0]=bbp[1]=bbp[515]=bbp[514]=0;
    bp=bbp+258;
   
    for(int k=-256;k<257;k++)
	{
        temp=((float)k)/((float)bt);
        temp=temp*temp;
		temp=temp*temp*temp;
        temp=100.0*exp(-temp)+0.5;
        bbp[k+258] = (BYTE)(temp);
	}
    memset (mid,100,Width*Height);
    memset (r,0,Width*Height * sizeof(int));

    for(i=3;i<Height-3;i++)
       for(j=3;j<Width-3;j++)
	   {
		   n=100;
           p=in + (i-3)*Width + j - 1;
           cp=bp + in[i*Width+j];

           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p);
           p+=Width-3; 

           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p);
           p+=Width-5;

           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p);
           p+=Width-6;

           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p);
           p+=2;
           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p);
           p+=Width-6;

           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p++);
		   n+=*(cp-*p++);
	       n+=*(cp-*p++);
		   n+=*(cp-*p);
		   p+=Width-5;

		   n+=*(cp-*p++);
		   n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p);
           p+=Width-3;

           n+=*(cp-*p++);
           n+=*(cp-*p++);
           n+=*(cp-*p);

           if (n<=max_no)
               r[i*Width+j] = max_no - n;
	   }
	int_to_uchar(r,InputImage,Imagesize);
	/*int max_r=r[0];
	int min_r=r[0];
	for (i=1; i<Imagesize; i++)
	{
		if ( r[i] > max_r )
			max_r=r[i];
		if ( r[i] < min_r )
			min_r=r[i];
	}

	max_r-=min_r;
	if(max_r!=0)
	{
	   for (i=0; i<Imagesize; i++)
	   {
		   temp=(r[i]-min_r)*255.0/max_r+0.5; 
		   InputImage[i] = (BYTE)(temp);
	   }
	}//*/
	if(mid!=NULL) delete []mid;
	if(r!=NULL) delete []r;
}
//***********************************************************
//函数类别: 图像的边缘细化
//函数名称:  
//           Image_SUSAN_Edge_Normal
//函数用途:
//           被Image_SUSAN_Edge_Normal函数调用;
//
//参数说明:
//           int    *r  图像的对象指针
//           int x_size
//           int y_size
//           BYTE   *mid    边缘信息的输出的指针
//说    明:
//           利用SUSAN边缘检测的原理编制的
//原始作者: 陆宏伟
//原始日期: 3/20/1999 
//***********************************************************
void Image_SUSAN_thin(int *r,BYTE *mid,int x_size,int y_size)
{
	int   l[9], centre, 
		  b01, b12, b21, b10,
		  p1, p2, p3, p4,
		  b00, b02, b20, b22,
		  m, n, a, b, x, y, i, j;
	BYTE *mp;

    for(i=4; i<y_size-4; i++)
	{
		for(j=4; j<x_size-4; j++)
		{
			if (mid[i*x_size+j]<8)
			{
				centre = r[i*x_size+j];
				//  count number of neighbours 
				mp=mid + (i-1)*x_size + j-1;
				n  =  (*mp<8) +
					  (*(mp+1)<8) +
					  (*(mp+2)<8) +
					  (*(mp+x_size)<8) +
					  (*(mp+x_size+2)<8) +
					  (*(mp+x_size+x_size)<8) +
					  (*(mp+x_size+x_size+1)<8) +
					  (*(mp+x_size+x_size+2)<8);

				// n==0 no neighbours - remove point 
				if (n==0)
				    mid[i*x_size+j]=100;
				// n==1 - extend line if I can  
				// extension is only allowed a few times - the value of mid is used to control this */
				if ( (n==1) && (mid[i*x_size+j]<6) )
				{
				/* find maximum neighbour weighted in direction opposite the
					neighbour already present. e.g.
					have: O O O  weight r by 0 2 3
					   X X O              0 0 4
					   O O O              0 2 3     //*/

					l[0]=r[(i-1)*x_size+j-1]; l[1]=r[(i-1)*x_size+j]; l[2]=r[(i-1)*x_size+j+1];
					l[3]=r[(i  )*x_size+j-1]; l[4]=0;                 l[5]=r[(i  )*x_size+j+1];
					l[6]=r[(i+1)*x_size+j-1]; l[7]=r[(i+1)*x_size+j]; l[8]=r[(i+1)*x_size+j+1];

					if (mid[(i-1)*x_size+j-1]<8)        { l[0]=0; l[1]=0; l[3]=0; l[2]*=2; 
														l[6]*=2; l[5]*=3; l[7]*=3; l[8]*=4; }
					else { if (mid[(i-1)*x_size+j]<8)   { l[1]=0; l[0]=0; l[2]=0; l[3]*=2; 
														l[5]*=2; l[6]*=3; l[8]*=3; l[7]*=4; }
					else { if (mid[(i-1)*x_size+j+1]<8) { l[2]=0; l[1]=0; l[5]=0; l[0]*=2; 
														l[8]*=2; l[3]*=3; l[7]*=3; l[6]*=4; }
					else { if (mid[(i)*x_size+j-1]<8)   { l[3]=0; l[0]=0; l[6]=0; l[1]*=2; 
														l[7]*=2; l[2]*=3; l[8]*=3; l[5]*=4; }
					else { if (mid[(i)*x_size+j+1]<8)   { l[5]=0; l[2]=0; l[8]=0; l[1]*=2; 
														l[7]*=2; l[0]*=3; l[6]*=3; l[3]*=4; }
					else { if (mid[(i+1)*x_size+j-1]<8) { l[6]=0; l[3]=0; l[7]=0; l[0]*=2; 
														l[8]*=2; l[1]*=3; l[5]*=3; l[2]*=4; }
					else { if (mid[(i+1)*x_size+j]<8)   { l[7]=0; l[6]=0; l[8]=0; l[3]*=2; 
														l[5]*=2; l[0]*=3; l[2]*=3; l[1]*=4; }
					else { if (mid[(i+1)*x_size+j+1]<8) { l[8]=0; l[5]=0; l[7]=0; l[6]*=2; 
														l[2]*=2; l[1]*=3; l[3]*=3; l[0]*=4; } }}}}}}}

					// find the highest point  
					for(m=0,y=0; y<3; y++)
					  for(x=0; x<3; x++)
						  if (l[y+y+y+x]>m) { m=l[y+y+y+x]; a=y; b=x; }

					if (m>0)
					{
						if (mid[i*x_size+j]<4)
						    mid[(i+a-1)*x_size+j+b-1] = 4;
						else
						    mid[(i+a-1)*x_size+j+b-1] = mid[i*x_size+j]+1;
						if ( (a+a+b) < 3 ) // need to jump back in image  
						{
						    i+=a-1;
						    j+=b-2;
						    if (i<4) i=4;
						    if (j<4) j=4;
						}
					}
				}
				if (n==2)
				{
				  // put in a bit here to straighten edges  
					b00 = mid[(i-1)*x_size+j-1]<8; // corners of 3x3 
					b02 = mid[(i-1)*x_size+j+1]<8;
					b20 = mid[(i+1)*x_size+j-1]<8;
					b22 = mid[(i+1)*x_size+j+1]<8;
					if ( ((b00+b02+b20+b22)==2) && ((b00|b22)&(b02|b20)))
					{  /* case: move a point back into line.
						e.g. X O X  CAN  become X X X
							 O X O              O O O
							 O O O              O O O    //*/
						if (b00) 
						{
						    if (b02) { x=0; y=-1; }
						    else     { x=-1; y=0; }
						}
						else
						{
						    if (b02) { x=1; y=0; }
						    else     { x=0; y=1; }
						}
						if (((float)r[(i+y)*x_size+j+x]/(float)centre) > 0.7)
						{
							if ( ( (x==0) && (mid[(i+(2*y))*x_size+j]>7) && (mid[(i+(2*y))*x_size+j-1]>7) && (mid[(i+(2*y))*x_size+j+1]>7) ) ||
							   ( (y==0) && (mid[(i)*x_size+j+(2*x)]>7) && (mid[(i+1)*x_size+j+(2*x)]>7) && (mid[(i-1)*x_size+j+(2*x)]>7) ) )
							{
							  mid[(i)*x_size+j]=100;
							  mid[(i+y)*x_size+j+x]=3;  // no jumping needed  
							}
						}
					}
					else
					{
						b01 = mid[(i-1)*x_size+j  ]<8;
						b12 = mid[(i  )*x_size+j+1]<8;
						b21 = mid[(i+1)*x_size+j  ]<8;
						b10 = mid[(i  )*x_size+j-1]<8;
						// right angle ends - not currently used  

#ifdef IGNORETHIS
					    if ( (b00&b01)|(b00&b10)|(b02&b01)|(b02&b12)|(b20&b10)|(b20&b21)|(b22&b21)|(b22&b12) )
						{ /* case; right angle ends. clean up.
							 e.g.; X X O  CAN  become X X O
								   O X O              O O O
								   O O O              O O O        //*/
							if ( ((b01)&(mid[(i-2)*x_size+j-1]>7)&(mid[(i-2)*x_size+j]>7)&(mid[(i-2)*x_size+j+1]>7)&
												((b00&((2*r[(i-1)*x_size+j+1])>centre))|(b02&((2*r[(i-1)*x_size+j-1])>centre)))) |
							   ((b10)&(mid[(i-1)*x_size+j-2]>7)&(mid[(i)*x_size+j-2]>7)&(mid[(i+1)*x_size+j-2]>7)&
												((b00&((2*r[(i+1)*x_size+j-1])>centre))|(b20&((2*r[(i-1)*x_size+j-1])>centre)))) |
							   ((b12)&(mid[(i-1)*x_size+j+2]>7)&(mid[(i)*x_size+j+2]>7)&(mid[(i+1)*x_size+j+2]>7)&
												((b02&((2*r[(i+1)*x_size+j+1])>centre))|(b22&((2*r[(i-1)*x_size+j+1])>centre)))) |
							   ((b21)&(mid[(i+2)*x_size+j-1]>7)&(mid[(i+2)*x_size+j]>7)&(mid[(i+2)*x_size+j+1]>7)&
												((b20&((2*r[(i+1)*x_size+j+1])>centre))|(b22&((2*r[(i+1)*x_size+j-1])>centre)))) )
							{
							    mid[(i)*x_size+j]=100;
							    if (b10&b20) j-=2;
							    if (b00|b01|b02) { i--; j-=2; }
							}
						}
#endif
						if ( ((b01+b12+b21+b10)==2) && ((b10|b12)&(b01|b21)) &&  ((b01&((mid[(i-2)*x_size+j-1]<8)|(mid[(i-2)*x_size+j+1]<8)))|(b10&((mid[(i-1)*x_size+j-2]<8)|(mid[(i+1)*x_size+j-2]<8)))|(b12&((mid[(i-1)*x_size+j+2]<8)|(mid[(i+1)*x_size+j+2]<8)))|(b21&((mid[(i+2)*x_size+j-1]<8)|(mid[(i+2)*x_size+j+1]<8)))) )
						{ /* case; clears odd right angles.
								 e.g.; O O O  becomes O O O
									   X X O          X O O
									   O X O          O X O     //*/
							mid[(i)*x_size+j]=100;
							i--;               // jump back  
							j-=2;
							if (i<4) i=4;
							if (j<4) j=4;
						}
					}
				}// end of if (n==2)
				//  n>2 the thinning is done here without breaking connectivity 

				if (n>2)
				{
					b01 = mid[(i-1)*x_size+j  ]<8;
					b12 = mid[(i  )*x_size+j+1]<8;
					b21 = mid[(i+1)*x_size+j  ]<8;
					b10 = mid[(i  )*x_size+j-1]<8;
					if((b01+b12+b21+b10)>1)
					{
						b00 = mid[(i-1)*x_size+j-1]<8;
						b02 = mid[(i-1)*x_size+j+1]<8;
						b20 = mid[(i+1)*x_size+j-1]<8;
						b22 = mid[(i+1)*x_size+j+1]<8;
						p1 = b00 | b01;
						p2 = b02 | b12;
						p3 = b22 | b21;
						p4 = b20 | b10;

						if( ((p1 + p2 + p3 + p4) - ((b01 & p2)+(b12 & p3)+(b21 & p4)+(b10 & p1))) < 2)
						{
							mid[(i)*x_size+j]=100;
							i--;
							j-=2;
							if (i<4) i=4;
							if (j<4) j=4;
						}
					} 
				}//end of if (n>2)
            }//end of if (mid[i*x_size+j]<8)
		}//end of for(j=4; j<x_size-4; j++)
	}//end of for(i=4; i<y_size-4; i++)
}

BOOL Image_Binary_HoughTransform(BYTE* InputImage , int ImgW , int ImgH ,BYTE TargetGray)
{
	int	 Imagesize=ImgW*ImgH;
	if (InputImage==NULL || Imagesize==0) return FALSE;

	int i,j;
	int  *Hough    = new int[Imagesize];
    int **TargetRowAddress = new int*[ImgH];
	BYTE **SourceRowAddress = new BYTE*[ImgH]; 
	//initialize 
	memset(Hough, 0, Imagesize*sizeof(int));
	SourceRowAddress[0] = InputImage;
	TargetRowAddress[0] = Hough;
	for(i=1 ; i<ImgH ;i++)
	{
		SourceRowAddress[i] = SourceRowAddress[i-1] + ImgW;
		TargetRowAddress[i] = TargetRowAddress[i-1] + ImgW;
	}
	double theta,   dtheta = 2*3.1415926/ImgW;
	
	CProgressDlg * MsgHandler = new CProgressDlg();
    MsgHandler->Create(NULL);
    MsgHandler->SetStatus("Binary Hough Transform Process");
	
	int nG,  angle;
	for(j=0; j<ImgH; j++)
	{		
		for(i=0; i<ImgW; i++)
		{
			if(SourceRowAddress[j][i]==TargetGray)
			{
				for(theta=0.0,angle=0;angle<ImgW;angle++)
				{
					nG=int(i*cos(theta)+j*sin(theta) + 0.5);
					if(nG>=0&&nG<ImgH)
						TargetRowAddress[nG][angle]++;   
                    theta += dtheta;
				}
			}
		}
		MsgHandler->SetPos(100 * j /ImgH );
		if(MsgHandler->m_bCancel) break;
	}
	if(!MsgHandler->m_bCancel) 
		int_to_uchar(Hough,InputImage,Imagesize);
	if(Hough!=NULL)  delete []Hough;
	if(TargetRowAddress!=NULL)  delete []TargetRowAddress;
	if(SourceRowAddress!=NULL)  delete []SourceRowAddress;
	MsgHandler->DestroyWindow();
    delete  MsgHandler;
	return TRUE;
}
BOOL Image_Binary_RadonTransform(BYTE* InputImage , int ImgW , int ImgH ,BYTE TargetGray)
{
	int	 Imagesize=ImgW*ImgH;
	if (InputImage==NULL || Imagesize==0) return FALSE;
	
	int i, x0=ImgW/2,y0=ImgH/2,x ;
	int  *Hough    = new int[Imagesize];
    int **TargetRowAddress = new int*[ImgH];
	BYTE **SourceRowAddress = new BYTE*[ImgH]; 
	//initialize 
	memset(Hough, 0, Imagesize*sizeof(int));
	SourceRowAddress[0] = InputImage;
	TargetRowAddress[0] = Hough;
	for(i=1 ; i<ImgH ;i++)
	{
		SourceRowAddress[i] = SourceRowAddress[i-1] + ImgW;
		TargetRowAddress[i] = TargetRowAddress[i-1] + ImgW;
	}
	double theta,   dtheta = 2*PI/ImgH;
	double *LutSin = new double[ImgH];
	double *LutCos = new double[ImgH];
	BYTE   *lpTmp, *bTest = new BYTE[ImgH+ImgW];
	for(theta=0.0, i=0; i<ImgH; i++)
	{
		LutCos[i] = cos(theta);
		LutSin[i] = sin(theta);
		theta += dtheta;
	}
	int  angle,  length , wx, wy;
	double rx, ry;
	
	CProgressDlg * MsgHandler = new CProgressDlg();
    MsgHandler->Create(NULL);
    MsgHandler->SetStatus("Binary Radon Transform Process");

	for(angle=0;angle<ImgH;angle++)
	{  
		for(i=0; i<ImgW; i++)
		{
			x = i/2; 
			rx = x*LutCos[angle];
			ry = x*LutSin[angle];
			length = int(sqrt(x0*x0 - x*x));
			lpTmp = bTest;
			memset(bTest, 0, ImgH+ImgW);
			for(int r=-length; r<=length;  r++)
			{
				wx = int(rx - r*LutSin[angle] + x0 + 0.5);
				wy = int(ry + r*LutCos[angle] + y0 + 0.5);
				if(wx>=0&&wx<ImgW&&wy>=0&&wy<ImgH)
				{
					if(SourceRowAddress[wy][wx]==TargetGray)
						*lpTmp = 1;
				}
				lpTmp++;
			}
			int templength , step =40 , number , threshold, k, iLineIntegral;
			templength = 2*(length+1);
			threshold = int(step*0.75);
			lpTmp = bTest;
			for(iLineIntegral =0, r=0; r<templength;  r+=step)
			{
				for(number=0, k=0; k<step; k++)
				{
					if(*lpTmp++) number++;
				}
				if(number>threshold) iLineIntegral += number;
			}
			TargetRowAddress[angle][i] = iLineIntegral;
		}	    
		MsgHandler->SetPos(100 * angle /ImgH );
		if(MsgHandler->m_bCancel) break;
	}
	if(!MsgHandler->m_bCancel) int_to_uchar(Hough,InputImage,Imagesize);
	if(bTest !=NULL)            delete []bTest;
	if(Hough !=NULL)            delete []Hough;
	if(LutSin!=NULL)			delete []LutSin;
	if(LutCos!=NULL)			delete []LutCos;
	if(TargetRowAddress!=NULL)  delete []TargetRowAddress;
	if(SourceRowAddress!=NULL)  delete []SourceRowAddress;
	MsgHandler->DestroyWindow();
    delete  MsgHandler;
	return TRUE;
}

//***********************************************************
//函数类别: 二值图像的处理
//函数名称:                       
//           Image_Binary_Erosion
//函数用途:
//           进行二值图腐蚀运算
//
//参数说明:
//调用函数:
//           
//被调函数: 
//           some function , at all,  I don't know 
//原始作者: 陆宏伟
//原始日期: 21/4/1999 

⌨️ 快捷键说明

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