/// <summary>
        /// Uses the Andrew variant of the Graham formula for calculating
        /// convex hulls.
        /// </summary>
        /// <param name="points"></param>
        /// <returns></returns>
        public Point[] CalculateConvexHull(Point[] points)
        {
            if (points.Length < 3)
            {
                return(points);
            }

            // TODO: Implement a quicksort algorithm, and find cut off point for switching algorithms.
            points = BubblesortPoints(points);

            List <Point> upper = new List <Point>();

            upper.Add(points[0]);
            upper.Add(points[1]);

            for (int i = 2; i < points.Length; i++)
            {
                upper.Add(points[i]);
                while (upper.Count > 2 && !ExtraMath.IsRightTurn(upper[upper.Count - 3], upper[upper.Count - 2], upper[upper.Count - 1]))
                {
                    upper.RemoveAt(upper.Count - 2);
                }
            }

            List <Point> lower = new List <Point>();

            lower.Add(points[points.Length - 1]);
            lower.Add(points[points.Length - 2]);

            for (int i = points.Length - 3; i >= 0; i--)
            {
                lower.Add(points[i]);
                while (lower.Count > 2 && !ExtraMath.IsRightTurn(lower[lower.Count - 3], lower[lower.Count - 2], lower[lower.Count - 1]))
                {
                    lower.RemoveAt(lower.Count - 2);
                }
            }
            Point[] retPoints = new Point[upper.Count + lower.Count];
            for (int i = 0; i < upper.Count; i++)
            {
                retPoints[i] = upper[i];
            }
            for (int i = 0; i < lower.Count; i++)
            {
                retPoints[i + upper.Count] = lower[i];
            }
            return(retPoints);
        }