public void FishEyeCalibrate() { var patternSize = new Size(10, 7); using (var image = Image("calibration/00.jpg")) using (var corners = new MatOfPoint2f()) { Cv2.FindChessboardCorners(image, patternSize, corners); var objectPointsArray = Create3DChessboardCorners(patternSize, 1.0f).ToArray(); var imagePointsArray = corners.ToArray(); using (var objectPoints = MatOfPoint3f.FromArray(objectPointsArray)) using (var imagePoints = MatOfPoint2f.FromArray(imagePointsArray)) using (var cameraMatrix = new MatOfDouble(Mat.Eye(3, 3, MatType.CV_64FC1))) using (var distCoeffs = new MatOfDouble()) { var rms = Cv2.FishEye.Calibrate(new[] { objectPoints }, new[] { imagePoints }, image.Size(), cameraMatrix, distCoeffs, out var rotationVectors, out var translationVectors, FishEyeCalibrationFlags.None); var distCoeffValues = distCoeffs.ToArray(); Assert.Equal(55.15, rms, 2); Assert.Contains(distCoeffValues, d => Math.Abs(d) > 1e-20); Assert.NotEmpty(rotationVectors); Assert.NotEmpty(translationVectors); } } }
public void Compute() { using (var model = ColorMomentHash.Create()) using (var img = Image("lenna.png")) using (var hash = new MatOfDouble()) { model.Compute(img, hash); Assert.Equal(1, hash.Rows); Assert.Equal(42, hash.Cols); Assert.Equal(MatType.CV_64FC1, hash.Type()); var hashArray = hash.ToArray(); Assert.Equal( new double[] { 0.00168799895166844, 9.73548985026306E-09, 7.12008515499876E-12, 1.58206172228354E-10, 5.28813826840171E-21, 1.29337857065483E-14, 4.79075399951684E-22, 0.00128609224067447, 9.52599959124291E-10, 3.93698021400622E-12, 7.14400696815386E-12, 3.78255159833954E-23, 1.97733914733847E-16, 2.16399836659832E-24, 0.000922260536104536, 3.65830493343832E-09, 7.661707706699E-13, 1.19445875901408E-12, -1.12767845932483E-24, -5.93217692337658E-17, -1.84467412783745E-25, 0.00132500752122349, 9.11756797244743E-09, 3.34535518270916E-12, 9.874171040899E-12, 1.58987320234562E-25, -9.15629498603106E-16, 5.67505900918754E-23, 0.000996616840904085, 1.90986702741479E-10, 1.81929041195046E-13, 1.60689960736751E-13, -2.7254690880086E-26, 1.04487497633728E-18, -3.47059704207128E-27, 0.00139981947147226, 2.27201044977745E-09, 4.41887540236722E-13, 7.28673251542401E-13, -4.09431968883588E-25, 3.10909057900972E-17, -5.77204894690052E-26 }, hashArray, new DoubleEqualityComparer(1E-12)); } }
public void Compute() { using (var model = ColorMomentHash.Create()) using (var img = Image("lenna.png")) using (var hash = new MatOfDouble()) { model.Compute(img, hash); Assert.Equal(1, hash.Rows); Assert.Equal(42, hash.Cols); Assert.Equal(MatType.CV_64FC1, hash.Type()); var hashArray = hash.ToArray(); Assert.Equal( new double[] { 0.00168819565895133, 9.69274323413482E-09, 7.15987637898653E-12, 1.58221230845821E-10, 5.30132640226369E-21, 1.29174445409783E-14, 5.05488594422795E-22, 0.00128582879665923, 9.54461083144018E-10, 3.93406825147193E-12, 7.14101055135503E-12, 3.77862605260528E-23, 1.97867503074794E-16, 2.18751322086428E-24, 0.000922420923231133, 3.66078199965787E-09, 7.66904362623121E-13, 1.19544776529889E-12, -1.12961325893555E-24, -5.93904771577414E-17, -1.84824480251793E-25, 0.00132532781142086, 9.1266053151516E-09, 3.35010536084133E-12, 9.88703855128973E-12, 1.52916239933584E-25, -9.17283073278845E-16, 5.69019311750733E-23, 0.00099662162473446, 1.90988729313945E-10, 1.81949836361996E-13, 1.60681443129224E-13, -2.72531646791605E-26, 1.04472248518881E-18, -3.4777107678675E-27, 0.00139982088736603, 2.27107975098039E-09, 4.41840703628873E-13, 7.2892000615472E-13, -4.0962177932807E-25, 3.10975156243194E-17, -5.77217024628191E-26 }, hashArray, new DoubleEqualityComparer(1E-12)); } }
/// <summary> /// converts rotation matrix to rotation vector using Rodrigues transformation /// </summary> /// <param name="matrix">Input rotation matrix (3x3).</param> /// <param name="vector">Output rotation vector (3x1).</param> /// <param name="jacobian">Optional output Jacobian matrix, 3x9, which is a matrix of partial derivatives of the output array components with respect to the input array components.</param> public static void Rodrigues(double[,] matrix, out double[] vector, out double[,] jacobian) { if (matrix == null) throw new ArgumentNullException("matrix"); if (matrix.GetLength(0) != 3 || matrix.GetLength(1) != 3) throw new ArgumentException("matrix must be double[3,3]"); using (var matrixM = new Mat(3, 3, MatType.CV_64FC1, matrix)) using (var vectorM = new MatOfDouble()) using (var jacobianM = new MatOfDouble()) { NativeMethods.calib3d_Rodrigues_MatToVec(matrixM.CvPtr, vectorM.CvPtr, jacobianM.CvPtr); vector = vectorM.ToArray(); jacobian = jacobianM.ToRectangularArray(); } }
/// <summary> /// composes 2 [R|t] transformations together. Also computes the derivatives of the result w.r.t the arguments /// </summary> /// <param name="rvec1">First rotation vector.</param> /// <param name="tvec1">First translation vector.</param> /// <param name="rvec2">Second rotation vector.</param> /// <param name="tvec2">Second translation vector.</param> /// <param name="rvec3">Output rotation vector of the superposition.</param> /// <param name="tvec3">Output translation vector of the superposition.</param> /// <param name="dr3dr1">Optional output derivatives of rvec3 or tvec3 with regard to rvec1, rvec2, tvec1 and tvec2, respectively.</param> /// <param name="dr3dt1">Optional output derivatives of rvec3 or tvec3 with regard to rvec1, rvec2, tvec1 and tvec2, respectively.</param> /// <param name="dr3dr2">Optional output derivatives of rvec3 or tvec3 with regard to rvec1, rvec2, tvec1 and tvec2, respectively.</param> /// <param name="dr3dt2">Optional output derivatives of rvec3 or tvec3 with regard to rvec1, rvec2, tvec1 and tvec2, respectively.</param> /// <param name="dt3dr1">Optional output derivatives of rvec3 or tvec3 with regard to rvec1, rvec2, tvec1 and tvec2, respectively.</param> /// <param name="dt3dt1">Optional output derivatives of rvec3 or tvec3 with regard to rvec1, rvec2, tvec1 and tvec2, respectively.</param> /// <param name="dt3dr2">Optional output derivatives of rvec3 or tvec3 with regard to rvec1, rvec2, tvec1 and tvec2, respectively.</param> /// <param name="dt3dt2">Optional output derivatives of rvec3 or tvec3 with regard to rvec1, rvec2, tvec1 and tvec2, respectively.</param> public static void ComposeRT(double[] rvec1, double[] tvec1, double[] rvec2, double[] tvec2, out double[] rvec3, out double[] tvec3, out double[,] dr3dr1, out double[,] dr3dt1, out double[,] dr3dr2, out double[,] dr3dt2, out double[,] dt3dr1, out double[,] dt3dt1, out double[,] dt3dr2, out double[,] dt3dt2) { if (rvec1 == null) throw new ArgumentNullException("rvec1"); if (tvec1 == null) throw new ArgumentNullException("tvec1"); if (rvec2 == null) throw new ArgumentNullException("rvec2"); if (tvec2 == null) throw new ArgumentNullException("tvec2"); using (var rvec1M = new Mat(3, 1, MatType.CV_64FC1, rvec1)) using (var tvec1M = new Mat(3, 1, MatType.CV_64FC1, tvec1)) using (var rvec2M = new Mat(3, 1, MatType.CV_64FC1, rvec2)) using (var tvec2M = new Mat(3, 1, MatType.CV_64FC1, tvec2)) using (var rvec3M = new MatOfDouble()) using (var tvec3M = new MatOfDouble()) using (var dr3dr1M = new MatOfDouble()) using (var dr3dt1M = new MatOfDouble()) using (var dr3dr2M = new MatOfDouble()) using (var dr3dt2M = new MatOfDouble()) using (var dt3dr1M = new MatOfDouble()) using (var dt3dt1M = new MatOfDouble()) using (var dt3dr2M = new MatOfDouble()) using (var dt3dt2M = new MatOfDouble()) { NativeMethods.calib3d_composeRT_Mat(rvec1M.CvPtr, tvec1M.CvPtr, rvec2M.CvPtr, tvec2M.CvPtr, rvec3M.CvPtr, tvec3M.CvPtr, dr3dr1M.CvPtr, dr3dt1M.CvPtr, dr3dr2M.CvPtr, dr3dt2M.CvPtr, dt3dr1M.CvPtr, dt3dt1M.CvPtr, dt3dr2M.CvPtr, dt3dt2M.CvPtr); rvec3 = rvec3M.ToArray(); tvec3 = tvec3M.ToArray(); dr3dr1 = dr3dr1M.ToRectangularArray(); dr3dt1 = dr3dt1M.ToRectangularArray(); dr3dr2 = dr3dr2M.ToRectangularArray(); dr3dt2 = dr3dt2M.ToRectangularArray(); dt3dr1 = dt3dr1M.ToRectangularArray(); dt3dt1 = dt3dt1M.ToRectangularArray(); dt3dr2 = dt3dr2M.ToRectangularArray(); dt3dt2 = dt3dt2M.ToRectangularArray(); } }
/// <summary> /// Decomposes the projection matrix into camera matrix and the rotation martix and the translation vector /// </summary> /// <param name="projMatrix">3x4 input projection matrix P.</param> /// <param name="cameraMatrix">Output 3x3 camera matrix K.</param> /// <param name="rotMatrix">Output 3x3 external rotation matrix R.</param> /// <param name="transVect">Output 4x1 translation vector T.</param> /// <param name="rotMatrixX">Optional 3x3 rotation matrix around x-axis.</param> /// <param name="rotMatrixY">Optional 3x3 rotation matrix around y-axis.</param> /// <param name="rotMatrixZ">Optional 3x3 rotation matrix around z-axis.</param> /// <param name="eulerAngles">ptional three-element vector containing three Euler angles of rotation in degrees.</param> public static void DecomposeProjectionMatrix(double[,] projMatrix, out double[,] cameraMatrix, out double[,] rotMatrix, out double[] transVect, out double[,] rotMatrixX, out double[,] rotMatrixY, out double[,] rotMatrixZ, out double[] eulerAngles) { if (projMatrix == null) throw new ArgumentNullException("projMatrix"); int dim0 = projMatrix.GetLength(0); int dim1 = projMatrix.GetLength(1); if (!((dim0 == 3 && dim1 == 4) || (dim0 == 4 && dim1 == 3))) throw new ArgumentException("projMatrix must be double[3,4] or double[4,3]"); using (var projMatrixM = new Mat(3, 4, MatType.CV_64FC1, projMatrix)) using (var cameraMatrixM = new MatOfDouble()) using (var rotMatrixM = new MatOfDouble()) using (var transVectM = new MatOfDouble()) using (var rotMatrixXM = new MatOfDouble()) using (var rotMatrixYM = new MatOfDouble()) using (var rotMatrixZM = new MatOfDouble()) using (var eulerAnglesM = new MatOfDouble()) { NativeMethods.calib3d_decomposeProjectionMatrix_Mat( projMatrixM.CvPtr, cameraMatrixM.CvPtr, rotMatrixM.CvPtr, transVectM.CvPtr, rotMatrixXM.CvPtr, rotMatrixYM.CvPtr, rotMatrixZM.CvPtr, eulerAnglesM.CvPtr); cameraMatrix = cameraMatrixM.ToRectangularArray(); rotMatrix = rotMatrixM.ToRectangularArray(); transVect = transVectM.ToArray(); rotMatrixX = rotMatrixXM.ToRectangularArray(); rotMatrixY = rotMatrixYM.ToRectangularArray(); rotMatrixZ = rotMatrixZM.ToRectangularArray(); eulerAngles = eulerAnglesM.ToArray(); } }