Esempio n. 1
0
        /// <summary>
        /// Extracts corners from the gradient image.  The method used here is one which uses the eigensystem at each
        /// pixel (computed from the smoothed second moments) to determine whether a corner is present.  A corner is
        /// one in which both eigenvalues are above the threshold.
        /// </summary>
        /// <param name="grad">Gradient image of source</param>
        /// <param name="threshold">Threshold used to determine corners</param>
        /// <returns>A list of corners</returns>
        public static unsafe Vector[] Extract(GradientImage grad, float threshold)
        {
            EigensystemImage eigen  = EigensystemImage.Compute(SecondMomentImage.Compute(grad));
            List <Vector>    points = new List <Vector>();
            int rows    = eigen.Rows;
            int columns = eigen.Columns;

            fixed(float *src = eigen.RawArray)
            {
                float *srcPtr   = src;
                int    channels = eigen.Channels;

                for (int r = 0; r < rows; r++)
                {
                    for (int c = 0; c < columns; c++, srcPtr += channels)
                    {
                        float lambda1 = srcPtr[0];
                        float lambda2 = srcPtr[1];
                        if (lambda1 > threshold && lambda2 > threshold)
                        {
                            points.Add(new DenseVector(new float[] { c, r }));
                        }
                    }
                }
            }

            return(points.ToArray());
        }
Esempio n. 2
0
        /// <summary>
        /// Computes the eigensystem image from the second moment image provided.
        /// </summary>
        /// <param name="moments">Contains the second moments used to compute the eigensystem image.</param>
        /// <param name="sigma">The sigma to use when convolving the second moment image</param>
        /// <returns>the eigensystem image</returns>
        public static unsafe EigensystemImage Compute(SecondMomentImage moments, float sigma)
        {
            moments = Convolution.ConvolveGaussian <SecondMomentImage>(moments, sigma);
            int rows    = moments.Rows;
            int columns = moments.Columns;

            float[, ,] data = new float[rows, columns, 6];
            fixed(float *src = moments.RawArray, dst = data)
            {
                float *srcPtr = src;
                float *dstPtr = dst;

                int length = rows * columns;

                while (length-- > 0)
                {
                    float a11  = *srcPtr++;
                    float a22  = *srcPtr++;
                    float a12  = *srcPtr++;
                    float a21  = a12;
                    float sqrt = (float)Math.Sqrt(4 * a12 * a21 + Math.Pow(a11 - a22, 2));
                    float sum  = a11 + a22;

                    float eigen1 = sum + sqrt;
                    float eigen2 = sum - sqrt;

                    float x1, y1;
                    findEigenvector(a11, a12, a21, a22, eigen1, out x1, out y1);

                    float x2, y2;
                    findEigenvector(a11, a12, a21, a22, eigen2, out x2, out y2);
                    *dstPtr++ = eigen1;
                    *dstPtr++ = eigen2;
                    *dstPtr++ = x1;
                    *dstPtr++ = y1;
                    *dstPtr++ = x2;
                    *dstPtr++ = y2;
                }
            }

            EigensystemImage image = new EigensystemImage();

            image.SetData(data);
            return(image);
        }