http://blog.csdn.net/byxdaz/article/details/4200752
矩形區域合適邊緣包括外邊緣和內邊緣,外邊緣是指最大最小邊界值;內邊緣是指邊緣最內點值。求取外邊緣比較簡單,這裡只講獲取內邊緣。
方法:
1、掃描圖像法。
2、中心點向邊界掃描,求得此時的邊界點,按照四個象限求取與邊界最靠近的點。
//求取矩形區域合適邊緣(內邊緣)
//參數說明:rectEdge,表示邊緣;pBinData2,表示二值圖像數據;nWidth,表示圖像寬度;nHeight,表示圖像高度;nSaveFlag,表示圖像中邊界的標記值;innerEdge,表示內邊緣
void GetInnerEdge(RECT rectEdge,BYTE *pBinData2,long nWidth,long nHeight,int nSaveFlag,RECT & innerEdge)
{
LONG iMinLeft = -1,iMinTop = -1,iMinRight = 65535,iMinBottom = 65535,nX = 5,nY = 5,k = 0;
POINT ptCenter;
ptCenter.x = (rectEdge.right+rectEdge.left)/2;
ptCenter.y = (rectEdge.bottom+rectEdge.top)/2;
nX = fabs((rectEdge.right-rectEdge.left)/4);
nY = fabs((rectEdge.bottom-rectEdge.top)/4);
RECT initRegion;
initRegion.left = (ptCenter.x-nX)>=0?(ptCenter.x-nX):0;
initRegion.right = (ptCenter.x+nX)<=rectEdge.right?(ptCenter.x+nX):rectEdge.right;
initRegion.top = (ptCenter.y-nY)>=0?(ptCenter.y-nY):0;
initRegion.bottom = (ptCenter.y+nY)<=rectEdge.bottom?(ptCenter.y+nY):rectEdge.bottom;
BOOL bFindLeft = FALSE;
double d1 = 0.0,d2 = 0.0,dMax = 20;
POINT ptLeft,ptRight,ptTop,ptBottom;
LONG nOutInnerMax = 150;//內外邊緣大致距離范圍
BOOL bBreak = FALSE;
j = ptCenter.y;
for(i=ptCenter.x;i>=rectEdge.left;i--)
{
ioffset = j * nWidth + i;
if(pBinData2[ioffset]==nSaveFlag && (i-rectEdge.left)<nOutInnerMax)
{
bBreak = TRUE;
break;
}
}
if(bBreak)
{
ptLeft.x = i;
ptLeft.y = j;
}
else
{
ptLeft.x = rectEdge.left;
ptLeft.y = j;
}
bBreak = FALSE;
i = ptCenter.x;
for(j=ptCenter.y;j>=rectEdge.top;j--)
{
ioffset = j * nWidth + i;
if(pBinData2[ioffset]==nSaveFlag && (j-rectEdge.top)<nOutInnerMax)
{
bBreak = TRUE;
break;
}
}
if(bBreak)
{
ptTop.x = i;
ptTop.y = j;
}
else
{
ptTop.x = rectEdge.top;
ptTop.y = j;
}
bBreak = FALSE;
j = ptCenter.y;
for(i=ptCenter.x;i<=rectEdge.right;i++)
{
ioffset = j * nWidth + i;
if(pBinData2[ioffset]==nSaveFlag && (rectEdge.right-i)<nOutInnerMax)
{
bBreak = TRUE;
break;
}
}
if(bBreak)
{
ptRight.x = i;
ptRight.y = j;
}
else
{
ptRight.x = rectEdge.right;
ptRight.y = j;
}
bBreak = FALSE;
i = ptCenter.x;
for(j=ptCenter.y;j<rectEdge.bottom;j++)
{
ioffset = j * nWidth + i;
if(pBinData2[ioffset]==nSaveFlag)
{
if((rectEdge.bottom-j)<nOutInnerMax)
{
bBreak = TRUE;
break;
}
}
}
if(bBreak)
{
ptBottom.x = i;
ptBottom.y = j;
}
else
{
ptBottom.x = i;
ptBottom.y = rectEdge.bottom;
}
for(j=rectEdge.top;j<=rectEdge.bottom;j++)
{
for(i=rectEdge.left;i<rectEdge.right;i++)
{
ioffset = j * nWidth + i;
if(pBinData2[ioffset]==nSaveFlag)
{
if(i>=ptLeft.x && i<ptCenter.x && j>ptCenter.y && j<=ptBottom.y) //第3象限
{
d1 = fabs(i-ptLeft.x);
d2 = fabs(j-ptBottom.y);
if(d1<=d2)//靠近左邊
{
if(iMinLeft<i && d1<dMax)
{
iMinLeft = i;
}
}
else //靠近下邊
{
if(iMinBottom>j && d2<dMax)
{
iMinBottom = j;
}
}
}
else if(i>=ptLeft.x && i<ptCenter.x && j>=ptTop.y && j<ptCenter.y)//第4象限
{
d1 = fabs(i-ptLeft.x);
d2 = fabs(j-ptTop.y);
if(d1<=d2)//靠近左邊
{
if(iMinLeft<i && d1<dMax)
{
iMinLeft = i;
}
}
else//靠近上邊
{
if(iMinTop<j && d2<dMax)
{
iMinTop = j;
}
}
}
else if(i>ptCenter.x && i<=ptRight.x && j>=ptTop.y && j<ptCenter.y)//第1象限
{
d1 = fabs(ptRight.x-i);
d2 = fabs(j-ptTop.y);
if(d1<=d2)//靠近右邊
{
if(iMinRight>i && d1<dMax)
{
iMinRight = i;
}
}
else//靠近上邊
{
if(iMinTop<j && d2<dMax)
{
iMinTop = j;
}
}
}
else if(i>ptCenter.x && i<=ptRight.x && j>ptCenter.y && j<ptBottom.y)//第2象限
{
d1 = fabs(ptRight.x-i);
d2 = fabs(ptBottom.y-j);
if(d1<=d2)//靠近右邊
{
if(iMinRight>i && d1<dMax)
{
iMinRight = i;
}
}
else//靠近下邊
{
if(iMinBottom>j && d2<dMax)
{
iMinBottom = j;
}
}
}
else
{
continue;
}
}
}
}
innerEdge.left = (iMinLeft!=-1)?iMinLeft:rectEdge.left;
innerEdge.right = (iMinRight!=65535)?iMinRight:rectEdge.right;
innerEdge.top = (iMinTop!=-1)?iMinTop:rectEdge.top;
innerEdge.bottom = (iMinBottom!=65535)?iMinBottom:rectEdge.bottom;
}