Exemplo n.º 1
0
        /// <summary>
        /// Returns the angle between 0 and 2*pi between the two vectors given.
        /// </summary>
        /// <param name="v1"></param>
        /// <param name="v2"></param>
        /// <returns></returns>
        public static Radian Angle(VectorF2D v1, VectorF2D v2)
        {
            double size_v1 = v1.Size;
            double size_v2 = v2.Size;

            double dot   = VectorF2D.Dot(v1, v2);
            double cross = VectorF2D.Cross(v1, v2);

            // filter out the vectors that are parallel.
            if (v1[0] == v2[0] &&
                v1[1] == v2[1])
            {
                return(0);
            }
            else if (v1[0] == v2[0] &&
                     v1[1] == -v2[1])
            {
                return(System.Math.PI / 2.0f);
            }
            else if (v1[0] == -v2[0] &&
                     v1[1] == v2[1])
            {
                return(-System.Math.PI / 2.0f);
            }
            else if (v1[0] == -v2[0] &&
                     v1[1] == -v2[1])
            {
                return(System.Math.PI);
            }

            // split per quadrant.
            double angle;

            if (dot > 0)
            {     // dot > 0
                if (cross > 0)
                { // dot > 0 and cross > 0
                    // Quadrant 1
                    angle = (double)System.Math.Asin(cross / (size_v1 * size_v2));
                    if (angle < System.Math.PI / 4f)
                    { // use cosine.
                        angle = (double)System.Math.Acos(dot / (size_v1 * size_v2));
                    }
                    // angle is ok here for quadrant 1.
                }
                else
                { // dot > 0 and cross <= 0
                    // Quadrant 4
                    angle = (double)(System.Math.PI * 2.0f) + (double)System.Math.Asin(cross / (size_v1 * size_v2));
                    if (angle > (double)(System.Math.PI * 2.0f) - System.Math.PI / 4f)
                    { // use cosine.
                        angle = (double)(System.Math.PI * 2.0f) - (double)System.Math.Acos(dot / (size_v1 * size_v2));
                    }
                    // angle is ok here for quadrant 1.
                }
            }
            else
            {     // dot <= 0
                if (cross > 0)
                { // dot > 0 and cross > 0
                    // Quadrant 2
                    angle = (double)System.Math.PI - (double)System.Math.Asin(cross / (size_v1 * size_v2));
                    if (angle > System.Math.PI / 2f + System.Math.PI / 4f)
                    { // use cosine.
                        angle = (double)System.Math.Acos(dot / (size_v1 * size_v2));
                    }
                    // angle is ok here for quadrant 2.
                }
                else
                { // dot > 0 and cross <= 0
                    // Quadrant 3
                    angle = -(-(double)System.Math.PI + (double)System.Math.Asin(cross / (size_v1 * size_v2)));
                    if (angle < System.Math.PI + System.Math.PI / 4f)
                    { // use cosine.
                        angle = (double)(System.Math.PI * 2.0f) - (double)System.Math.Acos(dot / (size_v1 * size_v2));
                    }
                    // angle is ok here for quadrant 3.
                }
            }
            return(angle);
        }
Exemplo n.º 2
0
        public static Radian Angle(VectorF2D v1, VectorF2D v2)
        {
            double size1 = v1.Size;
            double size2 = v2.Size;
            double num1  = VectorF2D.Dot(v1, v2);
            double num2  = VectorF2D.Cross(v1, v2);

            if (v1[0] == v2[0] && v1[1] == v2[1])
            {
                return((Radian)0.0);
            }
            if (v1[0] == v2[0] && v1[1] == -v2[1])
            {
                return((Radian)(System.Math.PI / 2.0));
            }
            if (v1[0] == -v2[0] && v1[1] == v2[1])
            {
                return((Radian)(-1.0 * System.Math.PI / 2.0));
            }
            if (v1[0] == -v2[0] && v1[1] == -v2[1])
            {
                return((Radian)System.Math.PI);
            }
            double num3;

            if (num1 > 0.0)
            {
                if (num2 > 0.0)
                {
                    num3 = System.Math.Asin(num2 / (size1 * size2));
                    if (num3 < System.Math.PI / 4.0)
                    {
                        num3 = System.Math.Acos(num1 / (size1 * size2));
                    }
                }
                else
                {
                    num3 = 2.0 * System.Math.PI + System.Math.Asin(num2 / (size1 * size2));
                    if (num3 > 7.0 * System.Math.PI / 4.0)
                    {
                        num3 = 2.0 * System.Math.PI - System.Math.Acos(num1 / (size1 * size2));
                    }
                }
            }
            else if (num2 > 0.0)
            {
                num3 = System.Math.PI - System.Math.Asin(num2 / (size1 * size2));
                if (num3 > 3.0 * System.Math.PI / 4.0)
                {
                    num3 = System.Math.Acos(num1 / (size1 * size2));
                }
            }
            else
            {
                num3 = -(System.Math.Asin(num2 / (size1 * size2)) - System.Math.PI);
                if (num3 < 5.0 * System.Math.PI / 4.0)
                {
                    num3 = 2.0 * System.Math.PI - System.Math.Acos(num1 / (size1 * size2));
                }
            }
            return((Radian)num3);
        }