【问题标题】:Rotate a point around a point with OpenCV使用 OpenCV 围绕一个点旋转一个点
【发布时间】:2011-12-18 16:38:39
【问题描述】:

有谁知道我如何在 OpenCV 中围绕另一个点旋转一个点?

我正在寻找这样的功能:

Point2f rotatePoint(Point2f p1, Point2f center, float angle)
{
    /* MAGIC */
}

【问题讨论】:

    标签: c++ opencv rotation point


    【解决方案1】:

    这些是将一个点围绕另一个点旋转 alpha 角度所需的步骤:

    1. 按轴心点的负数平移该点
    2. 使用标准方程旋转点以进行 2 维(或 3 维)旋转
    3. 翻译回来

    旋转的标准方程是:

    x' = xcos(alpha) - ysin(alpha)

    y' = xsin(alpha) + ycos(alpha)

    我们以 Point(15,5) 为例,在 Point(2,2) 周围 45 度。

    首先,翻译:

    v = (15,5) - (2,2) = (13,3)

    现在旋转 45°:

    v = (13*cos 45° - 3*sin 45°, 13*sin 45° + 3*cos 45°) = (7.07.., 11.31..)

    最后,翻译回来:

    v = v + (2,2) = (9.07.., 13.31..)

    注意:角度必须以弧度表示,因此将度数乘以Pi / 180

    【讨论】:

    • 欢迎来到 Stack Overflow。如果答案解决了您的问题,您应该接受它。请read about accepting answers.
    • +1 是一个很好的答案,但我会避免使用 45° 作为测试用例,因为正弦和余弦是相同的。
    【解决方案2】:

    如果你已经有RotatedRect形式的点,你可以改变它的角度来旋转点。

    //RotatedRect myRect;
    Point2f oldPoints[4];
    myRect.points(oldPoints);  //gives existing points of the rectangle.
    myRect.angle = 0;          //change the angle.
    Point2f newPoints[4];
    myRect.points(newPoints);  //gives rotated points of the rectangle.
    

    【讨论】:

      【解决方案3】:

      这可能会有所帮助

      cv::Point2f rotate2d(const cv::Point2f& inPoint, const double& angRad)
      {
          cv::Point2f outPoint;
          //CW rotation
          outPoint.x = std::cos(angRad)*inPoint.x - std::sin(angRad)*inPoint.y;
          outPoint.y = std::sin(angRad)*inPoint.x + std::cos(angRad)*inPoint.y;
          return outPoint;
      }
      
      cv::Point2f rotatePoint(const cv::Point2f& inPoint, const cv::Point2f& center, const double& angRad)
      {
          return rotate2d(inPoint - center, angRad) + center;
      }
      

      【讨论】:

        【解决方案4】:

        将点p1 = (x1, y1) 围绕p (x0, y0) 旋转角度a

        x2 = ((x1 - x0) * cos(a)) - ((y1 - y0) * sin(a)) + x0;
        y2 = ((x1 - x0) * sin(a)) + ((y1 - y0) * cos(a)) + y0;
        

        其中(x2, y2) 是点p1 的新位置

        【讨论】:

          【解决方案5】:

          我正在寻找图像的任何像素坐标的转换,但我几乎无法通过谷歌搜索找到它。不知何故,我找到了一个可以正常工作并帮助我理解问题的 python 代码链接: https://cristianpb.github.io/blog/image-rotation-opencv

          下面是对应的C++代码,如果有人在找的话:

          // send the original angle and don't transform in radian
              cv::Point2f rotatePointUsingTransformationMat(const cv::Point2f& inPoint, const cv::Point2f& center, const double& rotAngle)
              {
                  cv::Mat rot = cv::getRotationMatrix2D(center, rotAngle, 1.0);
                  float cos = rot.at<double>(0,0);
                  float sin = rot.at<double>(0,1);
                  int newWidth = int( ((center.y*2)*sin) +  ((center.x*2)*cos) );
                  int newHeight = int( ((center.y*2)*cos) +  ((center.x*2)*sin) );
          
                  rot.at<double>(0,2) += newWidth/2.0 - center.x;
                  rot.at<double>(1,2) += newHeight/2.0 - center.y;
          
                  int v[3] = {static_cast<int>(inPoint.x),static_cast<int>(inPoint.y),1};
                  int mat3[2][1] = {{0},{0}};
          
                  for(int i=0; i<rot.rows; i++)
                  {
                      for(int j=0; j<= 0; j++)
                      {
                          int sum=0;
                          for(int k=0; k<3; k++)
                          {
                              sum = sum + rot.at<double>(i,k) * v[k];
                          }
                          mat3[i][j] = sum;
                      }
                  }
                  return Point2f(mat3[0][0],mat3[1][0]);
              }
          

          【讨论】:

            猜你喜欢
            • 2012-11-21
            • 1970-01-01
            • 2014-12-26
            • 2023-04-03
            • 2017-03-25
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多