mirror of
https://github.com/opencv/opencv.git
synced 2024-11-24 19:20:28 +08:00
added centerPrincipalPoint=false to getOptimalNewCameraMatrix (ticket #1199)
This commit is contained in:
parent
38e0f84876
commit
5bb8076d7d
@ -780,11 +780,12 @@ getOptimalNewCameraMatrix
|
||||
-----------------------------
|
||||
Returns the new camera matrix based on the free scaling parameter.
|
||||
|
||||
.. ocv:function:: Mat getOptimalNewCameraMatrix( InputArray cameraMatrix, InputArray distCoeffs, Size imageSize, double alpha, Size newImageSize=Size(), Rect* validPixROI=0)
|
||||
.. ocv:function:: Mat getOptimalNewCameraMatrix( InputArray cameraMatrix, InputArray distCoeffs, Size imageSize, double alpha, Size newImageSize=Size(), Rect* validPixROI=0, bool centerPrincipalPoint=false)
|
||||
|
||||
.. ocv:pyfunction:: cv2.getOptimalNewCameraMatrix(cameraMatrix, distCoeffs, imageSize, alpha[, newImgSize]) -> retval, validPixROI
|
||||
.. ocv:pyfunction:: cv2.getOptimalNewCameraMatrix(cameraMatrix, distCoeffs, imageSize, alpha[, newImgSize[, centerPrincipalPoint]]) -> retval, validPixROI
|
||||
|
||||
.. ocv:cfunction:: void cvGetOptimalNewCameraMatrix( const CvMat* cameraMatrix, const CvMat* distCoeffs, CvSize imageSize, double alpha, CvMat* newCameraMatrix, CvSize newImageSize=cvSize(0, 0), CvRect* validPixROI=0, int centerPrincipalPoint=0)
|
||||
|
||||
.. ocv:cfunction:: void cvGetOptimalNewCameraMatrix( const CvMat* cameraMatrix, const CvMat* distCoeffs, CvSize imageSize, double alpha, CvMat* newCameraMatrix, CvSize newImageSize=cvSize(0, 0), CvRect* validPixROI=0 )
|
||||
.. ocv:pyoldfunction:: cv.GetOptimalNewCameraMatrix(cameraMatrix, distCoeffs, imageSize, alpha, newCameraMatrix, newImageSize=(0, 0), validPixROI=0) -> None
|
||||
|
||||
:param cameraMatrix: Input camera matrix.
|
||||
@ -800,6 +801,8 @@ Returns the new camera matrix based on the free scaling parameter.
|
||||
:param newImageSize: Image size after rectification. By default,it is set to ``imageSize`` .
|
||||
|
||||
:param validPixROI: Optional output rectangle that outlines all-good-pixels region in the undistorted image. See ``roi1, roi2`` description in :ocv:func:`StereoRectify` .
|
||||
|
||||
:param centerPrincipalPoint: Optional flag that indicates whether in the new camera matrix the principal point should be at the image center or not. By default, the principal point is chosen to best fit a subset of the source image (determined by ``alpha``) to the corrected image.
|
||||
|
||||
The function computes and returns
|
||||
the optimal new camera matrix based on the free scaling parameter. By varying this parameter, you may retrieve only sensible pixels ``alpha=0`` , keep all the original image pixels if there is valuable information in the corners ``alpha=1`` , or get something in between. When ``alpha>0`` , the undistortion result is likely to have some black pixels corresponding to "virtual" pixels outside of the captured distorted image. The original camera matrix, distortion coefficients, the computed new camera matrix, and ``newImageSize`` should be passed to
|
||||
|
@ -120,7 +120,8 @@ CVAPI(void) cvGetOptimalNewCameraMatrix( const CvMat* camera_matrix,
|
||||
CvSize image_size, double alpha,
|
||||
CvMat* new_camera_matrix,
|
||||
CvSize new_imag_size CV_DEFAULT(cvSize(0,0)),
|
||||
CvRect* valid_pixel_ROI CV_DEFAULT(0) );
|
||||
CvRect* valid_pixel_ROI CV_DEFAULT(0),
|
||||
int center_principal_point CV_DEFAULT(0));
|
||||
|
||||
/* Converts rotation vector to rotation matrix or vice versa */
|
||||
CVAPI(int) cvRodrigues2( const CvMat* src, CvMat* dst,
|
||||
@ -622,7 +623,7 @@ CV_EXPORTS_W float rectify3Collinear( InputArray cameraMatrix1, InputArray distC
|
||||
//! returns the optimal new camera matrix
|
||||
CV_EXPORTS_W Mat getOptimalNewCameraMatrix( InputArray cameraMatrix, InputArray distCoeffs,
|
||||
Size imageSize, double alpha, Size newImgSize=Size(),
|
||||
CV_OUT Rect* validPixROI=0);
|
||||
CV_OUT Rect* validPixROI=0, bool centerPrincipalPoint=false);
|
||||
|
||||
//! converts point coordinates from normal pixel coordinates to homogeneous coordinates ((x,y)->(x,y,1))
|
||||
CV_EXPORTS_W void convertPointsToHomogeneous( InputArray src, OutputArray dst );
|
||||
|
@ -2529,46 +2529,81 @@ void cvStereoRectify( const CvMat* _cameraMatrix1, const CvMat* _cameraMatrix2,
|
||||
void cvGetOptimalNewCameraMatrix( const CvMat* cameraMatrix, const CvMat* distCoeffs,
|
||||
CvSize imgSize, double alpha,
|
||||
CvMat* newCameraMatrix, CvSize newImgSize,
|
||||
CvRect* validPixROI )
|
||||
CvRect* validPixROI, int centerPrincipalPoint )
|
||||
{
|
||||
cv::Rect_<float> inner, outer;
|
||||
icvGetRectangles( cameraMatrix, distCoeffs, 0, cameraMatrix, imgSize, inner, outer );
|
||||
|
||||
newImgSize = newImgSize.width*newImgSize.height != 0 ? newImgSize : imgSize;
|
||||
|
||||
double M[3][3];
|
||||
CvMat matM = cvMat(3, 3, CV_64F, M);
|
||||
cvConvert(cameraMatrix, &matM);
|
||||
|
||||
double cx0 = M[0][2];
|
||||
double cy0 = M[1][2];
|
||||
double cx = (newImgSize.width-1)*0.5;
|
||||
double cy = (newImgSize.height-1)*0.5;
|
||||
|
||||
double s0 = std::max(std::max(std::max((double)cx/(cx0 - inner.x), (double)cy/(cy0 - inner.y)),
|
||||
(double)cx/(inner.x + inner.width - cx0)),
|
||||
(double)cy/(inner.y + inner.height - cy0));
|
||||
double s1 = std::min(std::min(std::min((double)cx/(cx0 - outer.x), (double)cy/(cy0 - outer.y)),
|
||||
(double)cx/(outer.x + outer.width - cx0)),
|
||||
(double)cy/(outer.y + outer.height - cy0));
|
||||
double s = s0*(1 - alpha) + s1*alpha;
|
||||
|
||||
M[0][0] *= s;
|
||||
M[1][1] *= s;
|
||||
M[0][2] = cx;
|
||||
M[1][2] = cy;
|
||||
cvConvert(&matM, newCameraMatrix);
|
||||
|
||||
if( validPixROI )
|
||||
if( centerPrincipalPoint )
|
||||
{
|
||||
inner = cv::Rect_<float>((float)((inner.x - cx0)*s + cx),
|
||||
(float)((inner.y - cy0)*s + cy),
|
||||
(float)(inner.width*s),
|
||||
(float)(inner.height*s));
|
||||
cv::Rect r(cvCeil(inner.x), cvCeil(inner.y), cvFloor(inner.width), cvFloor(inner.height));
|
||||
r &= cv::Rect(0, 0, newImgSize.width, newImgSize.height);
|
||||
*validPixROI = r;
|
||||
double cx0 = M[0][2];
|
||||
double cy0 = M[1][2];
|
||||
double cx = (newImgSize.width-1)*0.5;
|
||||
double cy = (newImgSize.height-1)*0.5;
|
||||
|
||||
icvGetRectangles( cameraMatrix, distCoeffs, 0, cameraMatrix, imgSize, inner, outer );
|
||||
double s0 = std::max(std::max(std::max((double)cx/(cx0 - inner.x), (double)cy/(cy0 - inner.y)),
|
||||
(double)cx/(inner.x + inner.width - cx0)),
|
||||
(double)cy/(inner.y + inner.height - cy0));
|
||||
double s1 = std::min(std::min(std::min((double)cx/(cx0 - outer.x), (double)cy/(cy0 - outer.y)),
|
||||
(double)cx/(outer.x + outer.width - cx0)),
|
||||
(double)cy/(outer.y + outer.height - cy0));
|
||||
double s = s0*(1 - alpha) + s1*alpha;
|
||||
|
||||
M[0][0] *= s;
|
||||
M[1][1] *= s;
|
||||
M[0][2] = cx;
|
||||
M[1][2] = cy;
|
||||
|
||||
if( validPixROI )
|
||||
{
|
||||
inner = cv::Rect_<float>((float)((inner.x - cx0)*s + cx),
|
||||
(float)((inner.y - cy0)*s + cy),
|
||||
(float)(inner.width*s),
|
||||
(float)(inner.height*s));
|
||||
cv::Rect r(cvCeil(inner.x), cvCeil(inner.y), cvFloor(inner.width), cvFloor(inner.height));
|
||||
r &= cv::Rect(0, 0, newImgSize.width, newImgSize.height);
|
||||
*validPixROI = r;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Get inscribed and circumscribed rectangles in normalized
|
||||
// (independent of camera matrix) coordinates
|
||||
icvGetRectangles( cameraMatrix, distCoeffs, 0, 0, imgSize, inner, outer );
|
||||
|
||||
// Projection mapping inner rectangle to viewport
|
||||
double fx0 = (newImgSize.width - 1) / inner.width;
|
||||
double fy0 = (newImgSize.height - 1) / inner.height;
|
||||
double cx0 = -fx0 * inner.x;
|
||||
double cy0 = -fy0 * inner.y;
|
||||
|
||||
// Projection mapping outer rectangle to viewport
|
||||
double fx1 = (newImgSize.width - 1) / outer.width;
|
||||
double fy1 = (newImgSize.height - 1) / outer.height;
|
||||
double cx1 = -fx1 * outer.x;
|
||||
double cy1 = -fy1 * outer.y;
|
||||
|
||||
// Interpolate between the two optimal projections
|
||||
M[0][0] = fx0*(1 - alpha) + fx1*alpha;
|
||||
M[1][1] = fy0*(1 - alpha) + fy1*alpha;
|
||||
M[0][2] = cx0*(1 - alpha) + cx1*alpha;
|
||||
M[1][2] = cy0*(1 - alpha) + cy1*alpha;
|
||||
|
||||
if( validPixROI )
|
||||
{
|
||||
icvGetRectangles( cameraMatrix, distCoeffs, 0, newCameraMatrix, imgSize, inner, outer );
|
||||
cv::Rect r = inner;
|
||||
r &= cv::Rect(0, 0, newImgSize.width, newImgSize.height);
|
||||
*validPixROI = r;
|
||||
}
|
||||
}
|
||||
|
||||
cvConvert(&matM, newCameraMatrix);
|
||||
}
|
||||
|
||||
|
||||
@ -3520,7 +3555,7 @@ bool cv::stereoRectifyUncalibrated( InputArray _points1, InputArray _points2,
|
||||
cv::Mat cv::getOptimalNewCameraMatrix( InputArray _cameraMatrix,
|
||||
InputArray _distCoeffs,
|
||||
Size imgSize, double alpha, Size newImgSize,
|
||||
Rect* validPixROI )
|
||||
Rect* validPixROI, bool centerPrincipalPoint )
|
||||
{
|
||||
Mat cameraMatrix = _cameraMatrix.getMat(), distCoeffs = _distCoeffs.getMat();
|
||||
CvMat c_cameraMatrix = cameraMatrix, c_distCoeffs = distCoeffs;
|
||||
@ -3530,7 +3565,7 @@ cv::Mat cv::getOptimalNewCameraMatrix( InputArray _cameraMatrix,
|
||||
|
||||
cvGetOptimalNewCameraMatrix(&c_cameraMatrix, &c_distCoeffs, imgSize,
|
||||
alpha, &c_newCameraMatrix,
|
||||
newImgSize, (CvRect*)validPixROI);
|
||||
newImgSize, (CvRect*)validPixROI, (int)centerPrincipalPoint);
|
||||
return newCameraMatrix;
|
||||
}
|
||||
|
||||
|
@ -1342,6 +1342,7 @@ GetOptimalNewCameraMatrix
|
||||
CvMat newCameraMatrix
|
||||
CvSize newImageSize cvSize(0,0)
|
||||
CvRect* validPixROI NULL
|
||||
int centerPrincipalPoint 0
|
||||
InitIntrinsicParams2D
|
||||
CvMat objectPoints
|
||||
CvMat imagePoints
|
||||
|
Loading…
Reference in New Issue
Block a user