Ejemplo n.º 1
0
        //Find outer defect
        static void FindContour_and_outer_defect(Mat img, List <Point[]> contours_final, ref int nLabels, out int [,] stats, string mode)
        {
            // variable
            OpenCvSharp.Point[][] temp = new Point[1][];
            //0: 內圈 ; 1: 外圈
            OpenCvSharp.Point[] contour_now;
            if (mode == "inner")
            {
                contour_now = contours_final[0];
            }
            else
            {
                contour_now = contours_final[1];
            }
            // Convex hull


            var ellipsecontour = Cv2.FitEllipse(contour_now);

            Mat convex_mask_img = Mat.Zeros(img.Size(), MatType.CV_8UC1);

            Cv2.Ellipse(convex_mask_img, ellipsecontour, 255, -1);


            // Contour
            temp[0] = contour_now;
            Mat contour_mask_img = Mat.Zeros(img.Size(), MatType.CV_8UC1);

            Cv2.DrawContours(contour_mask_img, temp, -1, 255, -1);


            Mat diff_image = contour_mask_img ^ convex_mask_img;


            //Opening
            Mat kernel = Mat.Ones(4, 4, MatType.CV_8UC1);//改變凹角大小

            diff_image = diff_image.MorphologyEx(MorphTypes.Open, kernel);


            //=========================吃掉邊界=======================================
            //temp[0] = contour_now;
            //Cv2.DrawContours(diff_image, temp, -1, 0, 3);
            //================================================================
            convex_mask_img.SaveImage("./" + mode + "convex" + ".jpg");
            contour_mask_img.SaveImage("./" + mode + "contour" + ".jpg");
            diff_image.SaveImage("./" + mode + "mask" + ".jpg");
            //Connected Component
            var labelMat     = new MatOfInt();
            var statsMat     = new MatOfInt();// Row: number of labels Column: 5
            var centroidsMat = new MatOfDouble();

            nLabels = Cv2.ConnectedComponentsWithStats(diff_image, labelMat, statsMat, centroidsMat);

            var labels = labelMat.ToRectangularArray();

            stats = statsMat.ToRectangularArray();
            var centroids = centroidsMat.ToRectangularArray();
        }
Ejemplo n.º 2
0
        /// <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();
            }
        }
Ejemplo n.º 3
0
        /// <summary>
        /// converts rotation vector to rotation matrix using Rodrigues transformation
        /// </summary>
        /// <param name="vector">Input rotation vector (3x1).</param>
        /// <param name="matrix">Output rotation matrix (3x3).</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[] vector, out double[,] matrix, out double[,] jacobian)
        {
            if (vector == null)
                throw new ArgumentNullException("vector");
            if (vector.Length != 3)
                throw new ArgumentException("vector.Length != 3");

            using (var vectorM = new Mat(3, 1, MatType.CV_64FC1, vector))
            using (var matrixM = new MatOfDouble())
            using (var jacobianM = new MatOfDouble())
            {
                NativeMethods.calib3d_Rodrigues_VecToMat(vectorM.CvPtr, matrixM.CvPtr, jacobianM.CvPtr);
                matrix = matrixM.ToRectangularArray();
                jacobian = jacobianM.ToRectangularArray();
            }
        }
Ejemplo n.º 4
0
        /// <summary>
        /// projects points from the model coordinate space to the image coordinates. 
        /// Also computes derivatives of the image coordinates w.r.t the intrinsic 
        /// and extrinsic camera parameters
        /// </summary>
        /// <param name="objectPoints">Array of object points, 3xN/Nx3 1-channel or 
        /// 1xN/Nx1 3-channel, where N is the number of points in the view.</param>
        /// <param name="rvec">Rotation vector (3x1).</param>
        /// <param name="tvec">Translation vector (3x1).</param>
        /// <param name="cameraMatrix">Camera matrix (3x3)</param>
        /// <param name="distCoeffs">Input vector of distortion coefficients 
        /// (k_1, k_2, p_1, p_2[, k_3[, k_4, k_5, k_6]]) of 4, 5, or 8 elements. 
        /// If the vector is null, the zero distortion coefficients are assumed.</param>
        /// <param name="imagePoints">Output array of image points, 2xN/Nx2 1-channel 
        /// or 1xN/Nx1 2-channel</param>
        /// <param name="jacobian">Optional output 2Nx(10 + numDistCoeffs) jacobian matrix 
        /// of derivatives of image points with respect to components of the rotation vector, 
        /// translation vector, focal lengths, coordinates of the principal point and 
        /// the distortion coefficients. In the old interface different components of 
        /// the jacobian are returned via different output parameters.</param>
        /// <param name="aspectRatio">Optional “fixed aspect ratio” parameter. 
        /// If the parameter is not 0, the function assumes that the aspect ratio (fx/fy) 
        /// is fixed and correspondingly adjusts the jacobian matrix.</param>
        public static void ProjectPoints(IEnumerable<Point3d> objectPoints,
                                         double[] rvec, double[] tvec,
                                         double[,] cameraMatrix, double[] distCoeffs,
                                         out Point2d[] imagePoints,
                                         out double[,] jacobian,
                                         double aspectRatio = 0)
        {
            if (objectPoints == null)
                throw new ArgumentNullException("objectPoints");
            if (rvec == null)
                throw new ArgumentNullException("rvec");
            if (rvec.Length != 3)
                throw new ArgumentException("rvec.Length != 3");
            if (tvec == null)
                throw new ArgumentNullException("tvec");
            if (tvec.Length != 3)
                throw new ArgumentException("tvec.Length != 3");
            if (cameraMatrix == null)
                throw new ArgumentNullException("cameraMatrix");
            if (cameraMatrix.GetLength(0) != 3 || cameraMatrix.GetLength(1) != 3)
                throw new ArgumentException("cameraMatrix must be double[3,3]");

            Point3d[] objectPointsArray = EnumerableEx.ToArray(objectPoints);
            using (var objectPointsM = new Mat(objectPointsArray.Length, 1, MatType.CV_64FC3, objectPointsArray))
            using (var rvecM = new Mat(3, 1, MatType.CV_64FC1, rvec))
            using (var tvecM = new Mat(3, 1, MatType.CV_64FC1, tvec))
            using (var cameraMatrixM = new Mat(3, 3, MatType.CV_64FC1, cameraMatrix))
            using (var imagePointsM = new MatOfPoint2d())
            {
                var distCoeffsM = new Mat();
                if (distCoeffs != null)
                    distCoeffsM = new Mat(distCoeffs.Length, 1, MatType.CV_64FC1, distCoeffs);
                var jacobianM = new MatOfDouble();

                NativeMethods.calib3d_projectPoints_Mat(objectPointsM.CvPtr,
                    rvecM.CvPtr, tvecM.CvPtr, cameraMatrixM.CvPtr, distCoeffsM.CvPtr,
                    imagePointsM.CvPtr, jacobianM.CvPtr, aspectRatio);

                imagePoints = imagePointsM.ToArray();
                jacobian = jacobianM.ToRectangularArray();
            }
        }
Ejemplo n.º 5
0
        /// <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();
            }
        }
Ejemplo n.º 6
0
        /// <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();
            }
        }
Ejemplo n.º 7
0
        /// <summary>
        /// Computes RQ decomposition of 3x3 matrix
        /// </summary>
        /// <param name="src">3x3 input matrix.</param>
        /// <param name="mtxR">Output 3x3 upper-triangular matrix.</param>
        /// <param name="mtxQ"> Output 3x3 orthogonal matrix.</param>
        /// <param name="qx">Optional output 3x3 rotation matrix around x-axis.</param>
        /// <param name="qy">Optional output 3x3 rotation matrix around y-axis.</param>
        /// <param name="qz">Optional output 3x3 rotation matrix around z-axis.</param>
        /// <returns></returns>
        public static Vec3d RQDecomp3x3(double[,] src, out double[,] mtxR, out double[,] mtxQ,
            out double[,] qx, out double[,] qy, out double[,] qz)
        {
            if (src == null)
                throw new ArgumentNullException("src");
            if (src.GetLength(0) != 3 || src.GetLength(1) != 3)
                throw new ArgumentException("src must be double[3,3]");

            using (var srcM = new Mat(3, 3, MatType.CV_64FC1))
            using (var mtxRM = new MatOfDouble())
            using (var mtxQM = new MatOfDouble())
            using (var qxM = new MatOfDouble())
            using (var qyM = new MatOfDouble())
            using (var qzM = new MatOfDouble())
            {
                Vec3d ret;
                NativeMethods.calib3d_RQDecomp3x3_Mat(srcM.CvPtr, 
                    mtxRM.CvPtr, mtxQM.CvPtr, qxM.CvPtr, qyM.CvPtr, qzM.CvPtr, 
                    out ret);
                mtxR = mtxRM.ToRectangularArray();
                mtxQ = mtxQM.ToRectangularArray();
                qx = qxM.ToRectangularArray();
                qy = qyM.ToRectangularArray();
                qz = qzM.ToRectangularArray();
                return ret;
            }
        }
Ejemplo n.º 8
0
        /// <summary>
        /// computes the connected components labeled image of boolean image. 
        /// image with 4 or 8 way connectivity - returns N, the total number of labels [0, N-1] where 0 
        /// represents the background label. ltype specifies the output label image type, an important 
        /// consideration based on the total number of labels or alternatively the total number of 
        /// pixels in the source image.
        /// </summary>
        /// <param name="image">the image to be labeled</param>
        /// <param name="connectivity">8 or 4 for 8-way or 4-way connectivity respectively</param>
        /// <returns></returns>
        public static ConnectedComponents ConnectedComponentsEx(
            InputArray image, PixelConnectivity connectivity = PixelConnectivity.Connectivity8)
        {
            using (var labelsMat = new MatOfInt())
            using (var statsMat = new MatOfInt())
            using (var centroidsMat = new MatOfDouble())
            {
                int nLabels = ConnectedComponentsWithStats(
                    image, labelsMat, statsMat, centroidsMat, connectivity, MatType.CV_32S);
                var labels = labelsMat.ToRectangularArray();
                var stats = statsMat.ToRectangularArray();
                var centroids = centroidsMat.ToRectangularArray();

                var blobs = new ConnectedComponents.Blob[nLabels];
                for (int i = 0; i < nLabels; i++)
                {
                    blobs[i] = new ConnectedComponents.Blob
                    {
                        Label = i,
                        Left = stats[i, 0],
                        Top = stats[i, 1],
                        Width = stats[i, 2],
                        Height = stats[i, 3],
                        Area = stats[i, 4],
                        Centroid = new Point2d(centroids[i, 0], centroids[i, 1]),
                    };
                }
                return new ConnectedComponents(blobs, labels, nLabels);
            }
        }