重映射是把一幅图像中某位置的像素放置到另一个图片指定位置的过程。
通过重映射来表达每个像素的位置 (x, y): g(x, y) = f( h(x, y) )
g() 是目标图像,
f( ) 是源图像,
h(x, y) 是作用于(x,y)的映射方法函数。
例如:
若有一幅图像A,按照此条件作重映射: h(x, y) = (A.cols - x, y ),图像会按照 x 轴方向发生翻转。
remap( )函数根据指定的映射形式,将源图像进行重映射几何变换,式子如下:
void remap(InputArray src, OutputArray dst, InputArray map1, InputArray map2, int interpolation, int borderMode = BORDER_CONSTANT, const Scalar& borderValue = Scalar())
参数1,源图像,填Mat类的对象,且需为单通道8位或者浮点型图像。
参数2,OutputArray类型的dst,输出图像,需和源图片有一样的尺寸和类型。
参数3,InputArray类型的map1,有两种可能的表示对象。
表示点(x,y)的第一个映射。
表示CV_16SC2 , CV_32FC1 或CV_32FC2类型的X值。
参数4,InputArray类型的map2,有两种可能的表示对象,而且map2是根据map1来确定
表示那种对象。
若map1表示点(x,y)时。这个参数不代表任何值。
表示CV_16UC1 , CV_32FC1类型的Y值(第二个值)。
参数5,插值方式,之前的resize()函数中有讲到,注意,resize( )函数中提到的
INTER_AREA插值方式在这里是不支持的,可选的插值方式如下:
INTER_NEAREST -- 最近邻插值
INTER_LINEAR -- 双线性插值(默认值)
INTER_CUBIC -- 双三次样条插值(逾4×4像素邻域内的双三次插值)
INTER_LANCZOS4 -- Lanczos插值(逾8×8像素邻域的Lanczos插值)
参数6,边界模式,有默认值BORDER_CONSTANT,表示目标图像中“离群点(outliers)”
的像素值不会被此函数修改。
参数7,const Scalar&类型的borderValue,当有常数边界时使用的值,默认值Scalar( ),
即默认值为0。
显示效果:
代码:
//变量定义 Mat srcImage, dstImage; Mat map_x, map_y; //载入原始图 srcImage = imread("E:\\img\\logo6.png", 1); imshow("原始图srcImage", srcImage); //创建和原始图一样的效果图,x重映射图,y重映射图 dstImage.create(srcImage.size(), srcImage.type()); map_x.create(srcImage.size(), CV_32FC1); map_y.create(srcImage.size(), CV_32FC1); //双层循环,遍历每一个像素点,改变map_x & map_y的值 for (int j = 0; j < srcImage.rows; j++) { for (int i = 0; i < srcImage.cols; i++) { //改变map_x & map_y的值. map_x.at
(j, i) = static_cast (i); map_y.at (j, i) = static_cast (srcImage.rows - j); } } //进行重映射操作 remap(srcImage, dstImage, map_x, map_y, INTER_NEAREST, BORDER_CONSTANT, Scalar(0, 0, 0)); imshow("映射的图像dstImage", dstImage); 可以x翻转、y翻转、x y翻转 以及缩放。对map_x或者map_y进行更改。
map_x.at
(j, i) = static_cast (i);
map_y.at(j, i) = static_cast (srcImage.rows - j);