/// <summary>
        ///   Determine dominant orientation for the feature point.
        /// </summary>
        ///
        public double GetOrientation(SpeededUpRobustFeaturePoint point)
        {
            // Get rounded feature point data
            int x = (int)System.Math.Round(point.X, 0);
            int y = (int)System.Math.Round(point.Y, 0);
            int s = (int)System.Math.Round(point.Scale, 0);

            // Get the orientation (for rotation invariance)
            return(this.GetOrientation(x, y, s));
        }
        /// <summary>
        ///   Describes the specified point (i.e. computes and
        ///   sets the orientation and descriptor vector fields
        ///   of the <see cref="SpeededUpRobustFeaturePoint"/>.
        /// </summary>
        ///
        /// <param name="point">The point to be described.</param>
        ///
        public void Compute(SpeededUpRobustFeaturePoint point)
        {
            // Get rounded feature point data
            int x = (int)System.Math.Round(point.X, 0);
            int y = (int)System.Math.Round(point.Y, 0);
            int s = (int)System.Math.Round(point.Scale, 0);

            if (this.invariant)
            {
                // Get the orientation (for rotation invariance)
                point.Orientation = this.GetOrientation(x, y, s);
            }

            // Extract SURF descriptor
            point.Descriptor = this.GetDescriptor(x, y, s, point.Orientation);
        }
        /// <summary>
        ///   Determine dominant orientation for the feature point.
        /// </summary>
        /// 
        public double GetOrientation(SpeededUpRobustFeaturePoint point)
        {
            // Get rounded feature point data
            int x = (int)System.Math.Round(point.X, 0);
            int y = (int)System.Math.Round(point.Y, 0);
            int s = (int)System.Math.Round(point.Scale, 0);

            // Get the orientation (for rotation invariance)
            return this.GetOrientation(x, y, s);
        }
        /// <summary>
        ///   Describes the specified point (i.e. computes and
        ///   sets the orientation and descriptor vector fields
        ///   of the <see cref="SpeededUpRobustFeaturePoint"/>.
        /// </summary>
        /// 
        /// <param name="point">The point to be described.</param>
        /// 
        public void Compute(SpeededUpRobustFeaturePoint point)
        {
            // Get rounded feature point data
            int x = (int)System.Math.Round(point.X, 0);
            int y = (int)System.Math.Round(point.Y, 0);
            int s = (int)System.Math.Round(point.Scale, 0);

            if (this.invariant)
            {
                // Get the orientation (for rotation invariance)
                point.Orientation = this.GetOrientation(x, y, s);
            }

            // Extract SURF descriptor
            point.Descriptor = this.GetDescriptor(x, y, s, point.Orientation);
        }
        public void ProcessImageTest()
        {
            var bitmaps = BagOfVisualWordsTest.GetImages();

            foreach (Bitmap img in bitmaps)
            {

                bool upright = true;
                bool extended = false;

                List<SpeededUpRobustFeaturePoint> expected;
                List<SpeededUpRobustFeaturePoint> actual;

                // Create OpenSURF detector by Chris Evans
                {
                    // Create Integral Image
                    OpenSURFcs.IntegralImage iimg = OpenSURFcs.IntegralImage.FromImage(img);

                    // Extract the interest points
                    var pts = OpenSURFcs.FastHessian.getIpoints(0.0002f, 5, 2, iimg);

                    // Describe the interest points
                    OpenSURFcs.SurfDescriptor.DecribeInterestPoints(pts, upright, extended, iimg);

                    expected = new List<SpeededUpRobustFeaturePoint>();
                    foreach (var p in pts)
                    {
                        expected.Add(new SpeededUpRobustFeaturePoint(
                            p.x, p.y, p.scale,
                            p.laplacian, p.orientation,
                            p.response, p.descriptor.ToDouble()));
                    }
                }

                // Create the detector
                var surf = new SpeededUpRobustFeaturesDetector(0.0002f, 5, 2);

                // Extract interest points
                actual = surf.ProcessImage(img);

                // Describe the interest points
                var descriptor = surf.GetDescriptor();
                descriptor.Invariant = !upright;
                descriptor.Extended = extended;

                foreach (var expectedPoint in expected)
                {
                    var actualPoint = new SpeededUpRobustFeaturePoint(
                        expectedPoint.X,
                        expectedPoint.Y,
                        expectedPoint.Scale,
                        expectedPoint.Laplacian);

                    descriptor.Compute(actualPoint);

                    Assert.AreEqual(expectedPoint.X, actualPoint.X);
                    Assert.AreEqual(expectedPoint.Y, actualPoint.Y);
                    Assert.AreEqual(expectedPoint.Scale, actualPoint.Scale);
                    Assert.AreEqual(expectedPoint.Orientation, actualPoint.Orientation);
                    Assert.AreEqual(expectedPoint.Response, actualPoint.Response);
                    Assert.AreEqual(expectedPoint.Descriptor.Length, actualPoint.Descriptor.Length);

                    for (int i = 0; i < expectedPoint.Descriptor.Length; i++)
                    {
                        double e = expectedPoint.Descriptor[i];
                        double a = actualPoint.Descriptor[i];

                        double u = System.Math.Abs(e - a);
                        double v = System.Math.Abs(e);
                        Assert.AreEqual(e, a, 0.05);
                    }
                }
            }

        }