diff --git a/+cv/initUndistortRectifyMap.m b/+cv/initUndistortRectifyMap.m new file mode 100644 index 000000000..451bbfd9f --- /dev/null +++ b/+cv/initUndistortRectifyMap.m @@ -0,0 +1,63 @@ +%INITUNDISTORTRECTIFYMAP Computes the undistortion and rectification transformation map +% +% [map1, map2] = cv.initUndistortRectifyMap(cameraMatrix, distCoeffs, newCameraMatrix, siz) +% [...] = cv.initCameraMatrix2D(..., 'OptionName', optionValue, ...) +% +% ## Input +% * __cameraMatrix__ Input camera matrix A = [fx,0,cx;0,fy,cy;0,0,1] +% * __distCoeffs__ Input vector of distortion coefficients [k1, k2, p1, p2, +% k3, k4, k5, k6] of 4, 5, or 8 elements. If the vector is NULL/empty, +% the zero distortion coefficients are assumed. +% * __newCameraMatrix__ New camera matrix A' = [fx',0,cx';0,fy',cy';0,0,1] +% * __siz__ Undistorted image size. +% +% ## Output +% * __map1__ The first output map. +% * __map2__ The second output map. +% +% ## Options +% * __R__ rectification transformation in the object space (3x3 matrix). R1 +% or R2 , computed by cv.stereoRectify can be passed here. If the +% matrix is empty, the identity transformation is assumed. In +% cvInitUndistortMap R assumed to be an identity matrix. +% * __M1Type__ Type of the first output map that can be 'uint16' or +% 'single'. See cv.convertMaps. +% +% The function computes the joint undistortion and rectification +% transformation and represents the result in the form of maps for +% cv.remap. The undistorted image looks like original, as if it is captured +% with a camera using the camera matrix = newCameraMatrix and zero +% distortion. In case of a monocular camera, newCameraMatrix is usually +% equal to cameraMatrix, or it can be computed by +% cv.getOptimalNewCameraMatrix for a better control over scaling. In case +% of a stereo camera, newCameraMatrix is normally set to P1 or P2 computed +% by cv.stereoRectify. +% +% Also, this new camera is oriented differently in the coordinate space, +% according to R . That, for example, helps to align two heads of a stereo +% camera so that the epipolar lines on both images become horizontal and +% have the same y- coordinate (in case of a horizontally aligned stereo +% camera). +% +% The function actually builds the maps for the inverse mapping algorithm +% that is used by cv.remap. That is, for each pixel (u,v) in the +% destination (corrected and rectified) image, the function computes the +% corresponding coordinates in the source image (that is, in the original +% image from camera). +% +% In case of a stereo camera, this function is called twice: once for each +% camera head, after cv.stereoRectify, which in its turn is called after +% cv.stereoCalibrate. But if the stereo camera was not calibrated, it is +% still possible to compute the rectification transformations directly from +% the fundamental matrix using cv.stereoRectifyUncalibrated. For each +% camera, the function computes homography H as the rectification +% transformation in a pixel domain, not a rotation matrix R in 3D space. R +% can be computed from H as +% +% R = cameraMatrix^-1 * H * cameraMatrix +% +% where cameraMatrix can be chosen arbitrarily. +% +% See also cv.remap cv.convertMaps cv.getOptimalNewCameraMatrix +% cv.stereoRectify cv.stereoCalibrate cv.stereoRectifyUncalibrated +% diff --git a/src/+cv/initUndistortRectifyMap.cpp b/src/+cv/initUndistortRectifyMap.cpp new file mode 100644 index 000000000..742f6ba24 --- /dev/null +++ b/src/+cv/initUndistortRectifyMap.cpp @@ -0,0 +1,56 @@ +/** + * @file initUndistortRectifyMap.cpp + * @brief mex interface for initUndistortRectifyMap + * @author Kota Yamaguchi + * @date 2011 + */ +#include "mexopencv.hpp" +using namespace std; +using namespace cv; + +/** Type specification + */ +const ConstMap M1Type = ConstMap + ("uint16",CV_16U) + ("single",CV_32F); + +/** + * Main entry called from Matlab + * @param nlhs number of left-hand-side arguments + * @param plhs pointers to mxArrays in the left-hand-side + * @param nrhs number of right-hand-side arguments + * @param prhs pointers to mxArrays in the right-hand-side + */ +void mexFunction( int nlhs, mxArray *plhs[], + int nrhs, const mxArray *prhs[] ) +{ + // Check the number of arguments + if (nrhs<4 || ((nrhs%2)!=0) || nlhs>2) + mexErrMsgIdAndTxt("mexopencv:error","Wrong number of arguments"); + + // Argument vector + vector rhs(prhs,prhs+nrhs); + Mat cameraMatrix(rhs[0].toMat(CV_32F)); + Mat distCoeffs(rhs[1].toMat(CV_32F)); + Mat newCameraMatrix(rhs[2].toMat(CV_32F)); + Size size(rhs[3].toSize()); + Mat R; + int m1type = CV_32F; + for (int i=4; i1) + plhs[1] = MxArray(map2); +} diff --git a/test/unit_tests/TestInitUndistortRectifyMap.m b/test/unit_tests/TestInitUndistortRectifyMap.m new file mode 100644 index 000000000..cd99f9365 --- /dev/null +++ b/test/unit_tests/TestInitUndistortRectifyMap.m @@ -0,0 +1,19 @@ +classdef TestInitUndistortRectifyMap + %TestInitUndistortRectifyMap + properties (Constant) + end + + methods (Static) + + function test_error_1 + try + cv.initUndistortRectifyMap(); + throw('UnitTest:Fail'); + catch e + assert(strcmp(e.identifier,'mexopencv:error')); + end + end + end + +end +