现在的位置: 首页 > 综合 > 正文

基于opencv的双线性插值的实现(一)

2013年03月26日 ⁄ 综合 ⁄ 共 2680字 ⁄ 字号 评论关闭
#include <cv.h>
#include <highgui.h>

#include <iostream>

using namespace std;

float Abs(float f);
void zoom(IplImage* src, IplImage* dst);

int main() {

	// read an image
	IplImage* src = cvLoadImage("E://pic//view.jpg");
    IplImage* dst = cvCreateImage(cvSize(1000,1000), src->depth, src->nChannels);
    zoom(src, dst);

	cvShowImage("src", src);
	cvShowImage("dst", dst);
	cvWaitKey(0);

	return 1;
}
/****************************
*返回绝对值
*****************************/
float Abs(float f)
{
    return f>=0 ? f : -f;
}
/****************************
*目标: 实现图像的缩放,
        使用了双线性插值的算法

*参数: src源图像
        dst生成图像

*返回值:无
*****************************/
void zoom(IplImage* src, IplImage* dst)
{
    int srcWidth = src->width;
    int srcHeight = src->height;
    int dstWidth = dst->width;
    int dstHeight = dst->height;

    //源图像与目标图像的宽高比例,这里减1很重要,否则有时报错,有时不报错。这点困扰了我很久
    const float tx = (srcWidth-1.0f)/(dstWidth-1.0f);
    const float ty = (srcHeight-1.0f)/(dstHeight-1.0f);

    CvPoint2D32f uv;//存储源图像的浮点坐标
    CvPoint3D32f f1;
    CvPoint3D32f f2;

    for (int j=0; j<dstHeight-1; j++)
     {
         for (int i=0; i<dstWidth-1; i++)
         {
			uv.x = i*tx;
			uv.y = j*ty;

			int iu = (int)uv.x;
            int iv = (int)uv.y;

			f1.x = ((uchar*)(src->imageData + src->widthStep*iv))[iu*3+0] * (1-Abs(uv.x-iu))+
				((uchar*)(src->imageData + src->widthStep*iv))[(iu+1)*3+0] * (uv.x-iu);
			f1.y = ((uchar*)(src->imageData + src->widthStep*iv))[iu*3+1] * (1-Abs(uv.x-iu))+
				((uchar*)(src->imageData + src->widthStep*iv))[(iu+1)*3+1] * (uv.x-iu);
			f1.z = ((uchar*)(src->imageData + src->widthStep*iv))[iu*3+2] * (1-Abs(uv.x-iu))+
				((uchar*)(src->imageData + src->widthStep*iv))[(iu+1)*3+2] * (uv.x-iu);

			f2.x = ((uchar*)(src->imageData + src->widthStep*(iv+1)))[iu*3] * (1-Abs(uv.x-iu))
                    +((uchar*)(src->imageData + src->widthStep*(iv+1)))[(iu+1)*3] * (uv.x-iu);
			f2.y = ((uchar*)(src->imageData + src->widthStep*(iv+1)))[iu*3+1] * (1-Abs(uv.x-iu))+
				((uchar*)(src->imageData + src->widthStep*(iv+1)))[(iu+1)*3+1] * (uv.x-iu);
			f2.z = ((uchar*)(src->imageData + src->widthStep*(iv+1)))[iu*3+2] * (1-Abs(uv.x-iu))+
				((uchar*)(src->imageData + src->widthStep*(iv+1)))[(iu+1)*3+2] * (uv.x-iu);

            ((uchar*)(dst->imageData + dst->widthStep*j))[i*3] = f1.x*(1-Abs(uv.y-iv))+f2.x*(Abs(uv.y-iv));
			((uchar*)(dst->imageData + dst->widthStep*j))[i*3+1] = f1.y*(1-Abs(uv.y-iv))+f2.y*(Abs(uv.y-iv));
			((uchar*)(dst->imageData + dst->widthStep*j))[i*3+2] = f1.z*(1-Abs(uv.y-iv))+f2.z*(Abs(uv.y-iv));
         }
         //这里添加上最后一列
         ((uchar*)(dst->imageData + dst->widthStep*j))[(dstWidth-1)*3] = ((uchar*)(dst->imageData + dst->widthStep*j))[(dstWidth-2)*3];
         ((uchar*)(dst->imageData + dst->widthStep*j))[(dstWidth-1)*3+1] = ((uchar*)(dst->imageData + dst->widthStep*j))[(dstWidth-2)*3+1];
         ((uchar*)(dst->imageData + dst->widthStep*j))[(dstWidth-1)*3+2] = ((uchar*)(dst->imageData + dst->widthStep*j))[(dstWidth-2)*3+2];
    }
    //这里添加上最后一行
    for(int i=0; i<dstWidth*3; i++)
    {
        ((uchar*)(dst->imageData + dst->widthStep*(dstHeight-1)))[i] = ((uchar*)(dst->imageData + dst->widthStep*(dstHeight-2)))[i];
    }
}

效果图:

抱歉!评论已关闭.