您的位置:首页 > 其它

图像预处理第5步:倾斜度调整

2016-04-19 15:23 309 查看
//图像预处理第5步:倾斜度调整
void CChildView::OnImgprcAdjustSlope()
{
SlopeAdjust(m_hDIB);
//在屏幕上显示位图
CDC* pDC=GetDC();
DisplayDIB(pDC,m_hDIB);
}


/*********************************************************

* 函数名称:
*         SlopeAdjust()
*
* 参数:
*     HDIB   hDIB       -原图像的句柄
*
* 返回值:
*         无
*
* 功能:
*     通过对图像左右半边平均高度的统计来进行倾斜的调整
*
* 说明:
*      只能对2值图像进行处理
*
****************************************************************/
void SlopeAdjust(HDIB hDIB)
{
// 指向DIB的指针
LPSTR lpDIB=(LPSTR) ::GlobalLock((HGLOBAL)hDIB);

// 指向DIB象素指针
LPSTR    lpDIBBits;

// 找到DIB图像象素起始位置
lpDIBBits = ::FindDIBBits(lpDIB);

// 指向源图像的指针
unsigned char*    lpSrc;

// 循环变量
LONG    i;
LONG    j;

// 图像每行的字节数
LONG    lLineBytes;

//图像的长度
LONG    lWidth;

//图像的宽度
LONG    lHeight;

//获取图像的长度
lWidth=::DIBWidth ((char*)lpDIB);

//获取图像的宽度
lHeight=::DIBHeight ((char*)lpDIB);

// 计算图像每行的字节数
lLineBytes = WIDTHBYTES(lWidth * 8);

//图像左半边的平均高度
double leftaver=0.0;

//图像右半边的平均高度
double rightaver=0.0;

//图像的倾斜度
double slope;

//统计循环变量
LONG counts=0;

//扫描左半边的图像,求黑色象素的平均高度

//行
for (i=0;i<lHeight;i++)
{

//列
for (j=0;j<lWidth/2;j++)
{

//指向第i行第j个象素的指针
lpSrc=(unsigned char*)lpDIBBits + lLineBytes *  i + j;

//如果为黑点
if (*lpSrc == 0)
{

//对其高度进行统计叠加
counts +=lWidth/2 -j;
leftaver += i*(lWidth/2 -j);

}

}
}

//计算平均高度
leftaver /= counts;

//将统计循环变量重新赋值
counts =0;

//扫描右半边的图像,求黑色象素的平均高度

//行
for (i =0;i<lHeight;i++)
{

//列
for (j=lWidth/2;j<lWidth;j++)
{
//指向第i行第j个象素的指针
lpSrc=(unsigned char*)lpDIBBits + lLineBytes *  i + j;

//如果为黑点
if (*lpSrc == 0)
{

//进行统计叠加
counts +=lWidth -j;
rightaver += i*(lWidth -j);
}
}
}

//计算右半边的平均高度
rightaver /= counts;

//计算斜率
slope = (leftaver - rightaver) / (lWidth/2);

//指向新的图像象素起始位置的指针
LPSTR lpNewDIBBits;

//指向新图像的指针
LPSTR lpDst;

//新图像的句柄
HLOCAL nNewDIBBits=LocalAlloc(LHND,lLineBytes*lHeight);

//锁定内存
lpNewDIBBits=(char*)LocalLock(nNewDIBBits);

//指向新图像象素的指针
lpDst=(char*)lpNewDIBBits;

//为新图像赋初始值
memset(lpDst,(BYTE)255,lLineBytes*lHeight);

//象素点的灰度值
int gray;

//位置映射值
int i_src;

//根据斜率,把当前新图像的点映射到源图像的点

//行
for (i=0;i<lHeight;i++)
{
//列
for (j=0;j<lWidth;j++)
{
//计算映射位置
i_src=int(i - (j-lWidth/2)*slope);

//如果点在图像外,象素置白色
if (i_src <0 || i_src >=lHeight )
gray = 255;

else
{
//否则到源图像中找点,取得象素值

//指向第i_src行第j个象素的指针
lpSrc=(unsigned char *)lpDIBBits + lLineBytes *  i_src + j;
gray = *lpSrc;
}

//把新图像的点用得到的象素值填充
//指向第i行第j个象素的指针
lpDst = (char *)lpNewDIBBits + lLineBytes * i + j;
*lpDst=gray;
}
}

// 将新的图像的内容拷贝到旧的图像中
memcpy(lpDIBBits,lpNewDIBBits,lLineBytes*lHeight);

// 解除锁定
::GlobalUnlock ((HGLOBAL)hDIB);
}


运行效果:


调整前


调整后
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: