700字范文,内容丰富有趣,生活中的好帮手!
700字范文 > 【数字图像处理】图像几何变换之 图像的极坐标变化展开鱼眼图

【数字图像处理】图像几何变换之 图像的极坐标变化展开鱼眼图

时间:2022-04-21 13:49:11

相关推荐

【数字图像处理】图像几何变换之 图像的极坐标变化展开鱼眼图

(一)基础知识

极坐标变换及其反变换的关键在于,根据极坐标变换前的图像(我们称为“圆图”)确定极坐标变换后的图像(我们称为“方图”)上每个像素点的像素值。也即是找到“圆图”和“方图”间几何坐标的对应关系。

1、极坐标变换

原理:

如下图所示,实现极坐标变换的关键即在于找到圆图上任一点P(i,j),在方图上对应的点p(m,n),然后通过插值算法实现圆图上所有像素点的赋值。

方图上,其行列数分别为M、N,方图上的每一列对应为圆图上的每条半径,半径方向存在着一个长度缩放因子delta_r = M/R,圆周方向被分为N等分,即角度因子为delta_t = 2π/N;

圆图上,图像坐标(i,j)和世界坐标(x,y)有着如下变换关系:x = j - R, y = R - i;

那么,图中P点半径长度为r = sqrt(xx + yy),角度theta = arctan(y/x);

圆图上点P在方图上对应行数为r/delta_r;

圆图上点P在方图上对应的列数n = thata/delta_t。

图像变换过程可以参考

图像的极坐标变换图像极坐标变换虹膜图像处理程序

(二)软件设计

因为这个代码时应用于嵌入式平台必须考虑到计算速度的问题,所以这里我们自己实现三角函数的近似计算缺点在于,边界点可能会出现失真。

/*** @fn float fastSin(float x)** @brief 自定义快速变换 sin cos 函数 定义 而外精度 更高拟合效果 参考链接*/sun11086/archive//03/20/1417944.html** @author IRIS_Chen* @date /6/17** @param x The x coordinate** @return A float*///本质上是利用了一个已经拟合好的二次函数近似三角函数float fastSin(float x){float y;// 限定 x 在 -Pi 到 piwhile (x < - PI){x += (float)(2 * PI);}while (x > PI){x -= (float)(2 * PI);}const float B = 1.2732; // 4 / CV_PI;const float C = -0.4053; // -4 / (CV_PI*CV_PI);if(x>0){y = B * x + C * x * x;}else{y = -1*B * x + C * x * x;}return y;}/*** @fn float fastCos(float x)** @brief Fast cosine** @author IRIS_Chen* @date /6/17** @param x The x coordinate** @return A float*/float fastCos(float x){return fastSin(x + 1.5707);}

Mat creatMapMat(Mat src, int rows_c,int cols_c,double startdelta){Mat dst;int i,j;u8* inaddr;u8* outaddr;int polar_d =src.width;double polar_r = polar_d / 2.0;printf("1");dst=create("..\\picture\\test.bmp",cols_c,rows_c,3);double delta_r = polar_r / rows_c; //半径因子double delta_t = 2.0*PI / cols_c; //角度因子double center_polar_x = (polar_d - 1) / 2.0;double center_polar_y = (polar_d - 1) / 2.0;printf("2");for (i = 0; i < cols_c; i++){double theta_p = i * delta_t+startdelta; //方图第i列在圆图对应线的角度double sin_theta = fastSin(theta_p);double cos_theta = fastCos(theta_p);for (int j = 0; j < rows_c; j++){double temp_r = j * delta_r; //方图第j行在圆图上对应的半径长度int polar_x = (int)(center_polar_x + temp_r * cos_theta);int polar_y = (int)(center_polar_y - temp_r * sin_theta);if(i<dst.width&&j<dst.highth&&polar_x<src.width&&polar_y<=src.highth){inaddr=at(&dst,i,j);outaddr=at(&src,polar_x,polar_y);*inaddr=*outaddr;*(inaddr+1)=*(outaddr+1);*(inaddr+2)=*(outaddr+2);}}}return dst;}

(三)应用举例

/*************************************************Copyright © Yueyang Co. Ltd. -2029. All rights reserved.File name: cv.hAuthor: YueyangVersion: V1.0Description: LiteCV运行主函数Others: Log: 11.3 Yueyang*************************************************/#include <stdio.h>#include <stdlib.h>#include <string.h>#include <malloc.h>#include "bmp.h"#include "cv.h"#include "GeoTrans.h"#include "PointOr.h"#include "BasicGui.h"int main(){Mat src;Mat_Init();src=load("..\\picture\\hole.bmp");Mat dst=dst=creatMapMat(src, 500,500,PI/4);save("..\\picture\\test.bmp",&dst);show(&dst);destory(&src);destory(&dst);return 0; }

原图:

这是一张医学中使用的人的血管内壁照片:

变换后:

(四)写在后面

因为LiteCV项目才刚刚写了一个开头,代码中有错误的地方还望指出。我已经将项目同步到了github,我会实时更新这个代码仓库。

项目github地址:

LITECV

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。