예제 #1
0
        /// <summary>
        /// Testing whether 2 line segments overlapped
        /// </summary>
        /// <param name="lineSegment1">First line segment</param>
        /// <param name="lineSegment2">Second line segment</param>
        /// <param name="overlappedSegment">The resulting overlapped line segment</param>
        /// <param name="mode">The enumeration of the result</param>
        /// <returns></returns>
        public static bool overlap(LineSegment3D lineSegment1, LineSegment3D lineSegment2, out LineSegment3D overlappedSegment, out LineSegmentOverlapEnum mode)
        {
            mode = LineSegmentOverlapEnum.Undefined;
            overlappedSegment = lineSegment1;

            // First check whether they have the same lineDirection (absolute: -v = +v for overlap test)
            if (!Line3D.parallel(lineSegment1.baseLine, lineSegment2.baseLine))
            {
                return(false);
            }

            // The lines are parallel, now check whether there is at least one point falls in the segment
            // Test points in line 2 on line 1
            LineSegmentOnSegmentEnum p1l1_s, p2l1_s;
            LineSegmentOnSegmentEnum p1l2_s, p2l2_s;

            bool p1l1 = isInSegment(lineSegment1, lineSegment2.startPoint, out p1l1_s);
            bool p2l1 = isInSegment(lineSegment1, lineSegment2.endPoint, out p2l1_s);

            if (p1l1 && p2l1)
            {
                if ((p1l1_s == p2l1_s && p2l1_s == LineSegmentOnSegmentEnum.InsideSegment) ||
                    (p1l1_s == LineSegmentOnSegmentEnum.CoincideEndSegment && p2l1_s == LineSegmentOnSegmentEnum.InsideSegment) ||
                    (p1l1_s == LineSegmentOnSegmentEnum.InsideSegment && p2l1_s == LineSegmentOnSegmentEnum.CoincideEndSegment))
                {
                    mode = LineSegmentOverlapEnum.SubSegment;
                }
                if (p1l1_s == p2l1_s && p1l1_s == LineSegmentOnSegmentEnum.CoincideEndSegment)
                {
                    mode = LineSegmentOverlapEnum.ExactlyOverlap;
                }
                overlappedSegment = lineSegment2;
                return(true);
            }
            else if (p1l1 || p2l1)
            {
                if (p1l1_s == LineSegmentOnSegmentEnum.CoincideEndSegment || p2l1_s == LineSegmentOnSegmentEnum.CoincideEndSegment)
                {
                    mode = LineSegmentOverlapEnum.Touch;
                    // Zero lenth line segments = a point, a valid data
                    if (p1l1)
                    {
                        overlappedSegment = new LineSegment3D(lineSegment2.startPoint, lineSegment2.startPoint);
                    }
                    if (p2l1)
                    {
                        overlappedSegment = new LineSegment3D(lineSegment2.endPoint, lineSegment2.endPoint);
                    }
                }
                if (p1l1_s == LineSegmentOnSegmentEnum.InsideSegment || p2l1_s == LineSegmentOnSegmentEnum.InsideSegment)
                {
                    bool p1l2 = isInSegment(lineSegment2, lineSegment1.startPoint, out p1l2_s);
                    bool p2l2 = isInSegment(lineSegment2, lineSegment1.endPoint, out p2l2_s);
                    if (p1l1_s == LineSegmentOnSegmentEnum.InsideSegment && p1l2_s == LineSegmentOnSegmentEnum.InsideSegment)
                    {
                        overlappedSegment = new LineSegment3D(lineSegment2.startPoint, lineSegment1.startPoint);
                    }
                    if (p2l1_s == LineSegmentOnSegmentEnum.InsideSegment && p1l2_s == LineSegmentOnSegmentEnum.InsideSegment)
                    {
                        overlappedSegment = new LineSegment3D(lineSegment2.endPoint, lineSegment1.startPoint);
                    }
                    if (p1l1_s == LineSegmentOnSegmentEnum.InsideSegment && p2l2_s == LineSegmentOnSegmentEnum.InsideSegment)
                    {
                        overlappedSegment = new LineSegment3D(lineSegment2.startPoint, lineSegment1.endPoint);
                    }
                    if (p2l1_s == LineSegmentOnSegmentEnum.InsideSegment && p2l2_s == LineSegmentOnSegmentEnum.InsideSegment)
                    {
                        overlappedSegment = new LineSegment3D(lineSegment2.endPoint, lineSegment1.endPoint);
                    }

                    mode = LineSegmentOverlapEnum.PartiallyOverlap;
                }
                return(true);
            }
            else
            {
                // if both p1l1 and p2l1 are false, there is probability that the l1 are inside the l2 instead. Only this case needs to be checked since other
                //  cases should be covered by the previous conditional checks
                bool p1l2 = isInSegment(lineSegment2, lineSegment1.startPoint, out p1l2_s);
                bool p2l2 = isInSegment(lineSegment2, lineSegment1.endPoint, out p2l2_s);
                if ((p1l2 && p2l2) &&
                    (p1l2_s == p2l2_s && p1l2_s == LineSegmentOnSegmentEnum.InsideSegment))
                {
                    mode = LineSegmentOverlapEnum.SuperSegment;
                    overlappedSegment = lineSegment1;
                    return(true);
                }
            }
            return(false);
        }
예제 #2
0
        /// <summary>
        /// Calculating intersection beween 2 Faces. The outcome of the intersection should be a LineSegment
        /// </summary>
        /// <param name="F1">First Face</param>
        /// <param name="F2">Second Face</param>
        /// <param name="intersectionLine">The resulting intersection line. Zero if no intersection</param>
        /// <param name="mode">The mode of the intersection: No intersection/parallel, partially intersect, no actual intersection/undefined</param>
        /// <returns></returns>
        public static bool intersect(Face3D F1, Face3D F2, out LineSegment3D intersectionLine, out FaceIntersectEnum mode)
        {
            intersectionLine = new LineSegment3D(new Point3D(0, 0, 0), new Point3D(0, 0, 0));
            mode             = FaceIntersectEnum.Undefined;

            if (F1._basePlane.normalVector == F2._basePlane.normalVector)
            {
                // test points inside another face
                for (int i = 0; i < F2._vertices.Count; i++)
                {
                    if (!Face3D.inside(F1, F2._vertices[i]))
                    {
                        continue;
                    }
                    mode = FaceIntersectEnum.Overlap;
                    return(true);
                }
                mode = FaceIntersectEnum.NoIntersectionParallel;
                return(false);
            }

            LineSegment3D ls1;
            LineSegment3D ls2;
            bool          res1 = Plane3D.PPintersect(F1._basePlane, F2, out ls1);
            bool          res2 = Plane3D.PPintersect(F2._basePlane, F1, out ls2);

            if (!res1 || !res2)
            {
                return(false);       // the faces do not intersect
            }
            // Special case if the intersection occurs only at a single point
            if (ls1.startPoint == ls1.endPoint && ls2.startPoint == ls2.endPoint)
            {
                if (ls1.startPoint.Equals(ls2.startPoint))
                {
                    mode = FaceIntersectEnum.IntersectPartial;
                    return(true);
                }
                return(false);
            }
            else if (ls1.startPoint.Equals(ls1.endPoint))
            {
                // a single point intersection: ls1 is 0 length linesegnment = point
                if (LineSegment3D.isInSegment(ls2, ls1.startPoint))
                {
                    mode = FaceIntersectEnum.IntersectPartial;
                    return(true);
                }
                return(false);
            }
            else if (ls2.startPoint.Equals(ls2.endPoint))
            {
                // a single point intersection: ls1 is 0 length linesegnment = point
                if (LineSegment3D.isInSegment(ls1, ls2.startPoint))
                {
                    mode = FaceIntersectEnum.IntersectPartial;
                    return(true);
                }
                return(false);
            }

            LineSegment3D          ovSegment;
            LineSegmentOverlapEnum ovstat = LineSegmentOverlapEnum.Undefined;
            bool lint = LineSegment3D.overlap(ls1, ls2, out ovSegment, out ovstat);

            if (lint)
            {
                intersectionLine = ovSegment;
                mode             = FaceIntersectEnum.IntersectPartial;
                return(true);
            }
            return(false);
        }