本文转载附上链接
本文提供了在图像旋转下的坐标转换公式,之后将对C++代码改成python版本。由于数据增强时需要旋转图片,同时还要找到标注的物体新的矩形框,之后将研究
图像中某点绕点旋转后的坐标,图像旋转坐标位置
在平面坐标上,任意点P(x1,y1),绕一个坐标点Q(x2,y2)旋转θ角度后,新的坐标设为(x, y)的计算公式:
-
x= (x1 - x2)*
cos(θ) - (y1 - y2)*
sin(θ) + x2 ;
-
y= (x1 - x2)*
sin(θ) + (y1 - y2)*
cos(θ) + y2 ;
这是在平面上的坐标旋转公式,但在图像中某个像素点旋转一个角度后的坐标不能用上述公式直接求出,因为图像(0,0)点的坐标的原点是在图像的左上角。
假设图像的宽度x高度为col x row,图像中某个像素P(x1,y1),绕某个像素点Q(x2,y2)旋转θ角度后,则该像素点的新坐标位置为(x, y),其计算公式为:
-
x1 = x1;
-
y1 = row - y1;
-
x2 = x2;
-
y2 = row - y2;
-
x = (x1 - x2)*
cos(pi /
180.0 * θ) - (y1 - y2)*
sin(pi /
180.0 * θ) + x2;
-
y = (x1 - x2)*
sin(pi /
180.0 * θ) + (y1 - y2)*
cos(pi /
180.0 * θ) + y2;
-
x=x;
-
y = row - y;
下面给出OpenCV的实现代码:原图像的大小500x577,像素点P(100,100),绕图像中心Q(250,288.5)旋转θ角度后,则该像素点的新坐标位置为(173, 60)
关于OpenCV实现图像旋转的方法,可参考本人的博客:《OpenCV图像旋转,指定填充背景颜色边界颜色》 http://blog.csdn.net/guyuealian/article/details/77993410
-
#include "stdafx.h"
-
#include <iostream>
-
#include<vector>
-
#include<algorithm>
-
#include <opencv2\opencv.hpp>
-
#include <opencv2\highgui\highgui.hpp>
-
using
namespace
std;
-
using
namespace cv;
-
#define pi 3.1415926
-
-
vector<cv::Point2i> getRotatePoint(cv::Mat srcImage,
vector<cv::Point2i> Points,
const cv::Point rotate_center,
const
double angle) {
-
vector<cv::Point2i> dstPoints;
-
int x1 =
0, y1 =
0;
-
int row = srcImage.rows;
-
for (
size_t i =
0; i < Points.size(); i++)
-
{
-
x1 = Points.at(i).x;
-
y1 = row - Points.at(i).y;
-
int x2 = rotate_center.x;
-
int y2 = row - rotate_center.y;
-
int x = cvRound((x1 - x2)*
cos(pi /
180.0 * angle) - (y1 - y2)*
sin(pi /
180.0 * angle) + x2);
-
int y = cvRound((x1 - x2)*
sin(pi /
180.0 * angle) + (y1 - y2)*
cos(pi /
180.0 * angle) + y2);
-
y = row - y;
-
dstPoints.push_back(Point2i(x, y));
-
}
-
return dstPoints;
-
}
-
-
int main() {
-
Mat src = imread(
"D:\\OpencvTest\\16.jpg");
-
Point2i point(100, 100);
-
vector<cv::Point2i> Points;
-
Points.push_back(point);
-
cv::circle(src, point,
2, cv::Scalar(
255,
0,
0),
2);
-
cv::imshow(
"src image ", src);
-
-
cv::Mat dst;
-
//旋转角度-20度
-
double angle =-
20;
-
//输出图像的尺寸与原图一样
-
cv::
Size dst_sz(src.cols, src.rows);
-
//指定旋转中心
-
cv::
Point2f center(src.cols / 2., src.rows / 2.);
-
-
//获取旋转矩阵(2x3矩阵)
-
cv::Mat rot_mat = cv::getRotationMatrix2D(center, angle,
1.0);
-
//设置选择背景边界颜色:绿色
-
cv::Scalar borderColor = Scalar(
0,
238,
0);
-
cv::warpAffine(src, dst, rot_mat, dst_sz, INTER_LINEAR, BORDER_CONSTANT, borderColor);
-
//cv::warpAffine(src, dst, rot_mat, dst_sz, INTER_LINEAR, BORDER_REPLICATE);
-
-
vector<cv::Point2i> dstPoints = getRotatePoint(dst, Points, center, angle);
-
cv::circle(dst, dstPoints.at(
0),
5, cv::Scalar(
0,
0,
255),
2);
-
cv::imshow(
"Rotation Image", dst);
-
waitKey(
0);
-
return
0;
-
}
-
【尊重原创,转载请注明出处】http://blog.csdn.net/guyuealian/article/details/78288131
图像中某点绕点旋转后的坐标,图像旋转坐标位置
在平面坐标上,任意点P(x1,y1),绕一个坐标点Q(x2,y2)旋转θ角度后,新的坐标设为(x, y)的计算公式:
-
x= (x1 - x2)*
cos(θ) - (y1 - y2)*
sin(θ) + x2 ;
-
y= (x1 - x2)*
sin(θ) + (y1 - y2)*
cos(θ) + y2 ;
这是在平面上的坐标旋转公式,但在图像中某个像素点旋转一个角度后的坐标不能用上述公式直接求出,因为图像(0,0)点的坐标的原点是在图像的左上角。
假设图像的宽度x高度为col x row,图像中某个像素P(x1,y1),绕某个像素点Q(x2,y2)旋转θ角度后,则该像素点的新坐标位置为(x, y),其计算公式为:
-
x1 = x1;
-
y1 = row - y1;
-
x2 = x2;
-
y2 = row - y2;
-
x = (x1 - x2)*
cos(pi /
180.0 * θ) - (y1 - y2)*
sin(pi /
180.0 * θ) + x2;
-
y = (x1 - x2)*
sin(pi /
180.0 * θ) + (y1 - y2)*
cos(pi /
180.0 * θ) + y2;
-
x=x;
-
y = row - y;
下面给出OpenCV的实现代码:原图像的大小500x577,像素点P(100,100),绕图像中心Q(250,288.5)旋转θ角度后,则该像素点的新坐标位置为(173, 60)
关于OpenCV实现图像旋转的方法,可参考本人的博客:《OpenCV图像旋转,指定填充背景颜色边界颜色》 http://blog.csdn.net/guyuealian/article/details/77993410
-
#include "stdafx.h"
-
#include <iostream>
-
#include<vector>
-
#include<algorithm>
-
#include <opencv2\opencv.hpp>
-
#include <opencv2\highgui\highgui.hpp>
-
using
namespace
std;
-
using
namespace cv;
-
#define pi 3.1415926
-
-
vector<cv::Point2i> getRotatePoint(cv::Mat srcImage,
vector<cv::Point2i> Points,
const cv::Point rotate_center,
const
double angle) {
-
vector<cv::Point2i> dstPoints;
-
int x1 =
0, y1 =
0;
-
int row = srcImage.rows;
-
for (
size_t i =
0; i < Points.size(); i++)
-
{
-
x1 = Points.at(i).x;
-
y1 = row - Points.at(i).y;
-
int x2 = rotate_center.x;
-
int y2 = row - rotate_center.y;
-
int x = cvRound((x1 - x2)*
cos(pi /
180.0 * angle) - (y1 - y2)*
sin(pi /
180.0 * angle) + x2);
-
int y = cvRound((x1 - x2)*
sin(pi /
180.0 * angle) + (y1 - y2)*
cos(pi /
180.0 * angle) + y2);
-
y = row - y;
-
dstPoints.push_back(Point2i(x, y));
-
}
-
return dstPoints;
-
}
-
-
int main() {
-
Mat src = imread(
"D:\\OpencvTest\\16.jpg");
-
Point2i point(100, 100);
-
vector<cv::Point2i> Points;
-
Points.push_back(point);
-
cv::circle(src, point,
2, cv::Scalar(
255,
0,
0),
2);
-
cv::imshow(
"src image ", src);
-
-
cv::Mat dst;
-
//旋转角度-20度
-
double angle =-
20;
-
//输出图像的尺寸与原图一样
-
cv::
Size dst_sz(src.cols, src.rows);
-
//指定旋转中心
-
cv::
Point2f center(src.cols / 2., src.rows / 2.);
-
-
//获取旋转矩阵(2x3矩阵)
-
cv::Mat rot_mat = cv::getRotationMatrix2D(center, angle,
1.0);
-
//设置选择背景边界颜色:绿色
-
cv::Scalar borderColor = Scalar(
0,
238,
0);
-
cv::warpAffine(src, dst, rot_mat, dst_sz, INTER_LINEAR, BORDER_CONSTANT, borderColor);
-
//cv::warpAffine(src, dst, rot_mat, dst_sz, INTER_LINEAR, BORDER_REPLICATE);
-
-
vector<cv::Point2i> dstPoints = getRotatePoint(dst, Points, center, angle);
-
cv::circle(dst, dstPoints.at(
0),
5, cv::Scalar(
0,
0,
255),
2);
-
cv::imshow(
"Rotation Image", dst);
-
waitKey(
0);
-
return
0;
-
}
-
【尊重原创,转载请注明出处】http://blog.csdn.net/guyuealian/article/details/78288131