矩形区域边缘

        矩形区域合适边缘包括外边缘和内边缘,外边缘是指最大最小边界值;内边缘是指边缘最内点值。求取外边缘比较简单,这里只讲获取内边缘。
       方法:
       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;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

byxdaz

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值