private void checkIntersection(Event upper,Event lower, OrderedSet<Event> Q,List<Point> outPoints)
        {
            Line a = new Line(upper.point,segments[upper.segIdx].End);
            Line b = new Line(lower.point,segments[lower.segIdx].End);

            if (HelperMethods.CheckTurn(new Line(a.Start, a.End), b.Start) == HelperMethods.CheckTurn(new Line(a.Start, a.End), b.End)
             || (HelperMethods.CheckTurn(new Line(b.Start, b.End), a.Start) == HelperMethods.CheckTurn(new Line(b.Start, b.End), a.End)))
                return;
            double aa, bb, cc, dd;
            Point interPoint;
            if (Math.Abs(a.Start.X - a.End.X) < Constants.Epsilon)
            {
                bb = (b.Start.Y - b.End.Y) / (b.Start.X - b.End.X);
                dd = b.Start.Y - b.Start.X * bb;
                interPoint = new Point(a.Start.X, (bb * a.Start.X + dd));
            }
            else if (Math.Abs(b.Start.X - b.End.X) < Constants.Epsilon)
            {
                aa = (a.Start.Y - a.End.Y) / (a.Start.X - a.End.X);
                cc = a.Start.Y - a.Start.X * aa;
                interPoint = new Point(b.Start.X, (aa * a.Start.X + cc));
            }
            else
            {
                aa = (a.Start.Y - a.End.Y) / (a.Start.X - a.End.X);
                bb = (b.Start.Y - b.End.Y) / (b.Start.X - b.End.X);
                cc = a.Start.Y - a.Start.X * aa;
                dd = b.Start.Y - b.Start.X * bb;
                double interX = (dd - cc) / (aa - bb);
                interPoint = new Point(interX, (aa * interX + cc));
            }
            Q.Add(new Event(interPoint, PointType.Intersection,-1 ,upper,lower));
            outPoints.Add(interPoint);
        }
 public Event(Point p, PointType type, int sIdx,Event _upper,Event _lower)
 {
     point = p; pType = type; segIdx = sIdx; upper = _upper; lower = _lower;
 }
 private double lineVal(Event line, double x)
 {
     Line a= segments[line.segIdx];
     if(Math.Abs(a.Start.X-a.End.X)<Constants.Epsilon)
         return double.MaxValue;
     double m = (a.End.Y - a.Start.Y)/ (a.End.X - a.Start.X);
     double c = a.Start.Y - (a.Start.X * m);
     return x * m + c;
 }
 private void handleEvent(Event curEvent, OrderedSet<Event> L, OrderedSet<Event> Q, List<Point> outPoints)
 {
     switch (curEvent.pType)
     {
         case PointType.Start:
             {
                 KeyValuePair<Event, Event> upLow = L.DirectUpperAndLower(curEvent);
                 if (upLow.Key != null)
                     checkIntersection(upLow.Key, curEvent, Q, outPoints);
                 if (upLow.Value != null)
                     checkIntersection(curEvent, upLow.Value, Q, outPoints);
                 L.Add(curEvent);
                 break;
             }
         case PointType.End:
             {
                 KeyValuePair<Event, Event> upLow = L.DirectUpperAndLower(curEvent);
                 if (upLow.Key != null && upLow.Value != null)
                     checkIntersection(upLow.Key, upLow.Value, Q, outPoints);
                 L.Remove(new Event(segments[curEvent.segIdx].Start, PointType.Start, curEvent.segIdx, null, null));
                 break;
             }
         case PointType.Intersection:
             {
                 Event upup = L.DirectUpperAndLower(curEvent.upper).Key;
                 Event lowlow = L.DirectUpperAndLower(curEvent.lower).Value;
                 if (upup !=null)
                     checkIntersection(upup, curEvent.lower, Q, outPoints);
                 if (lowlow != null)
                     checkIntersection(curEvent.upper,lowlow, Q, outPoints);
                 L.Remove(curEvent.upper); L.Remove(curEvent.lower);
                 curEvent.lower.point.X = curEvent.point.X;curEvent.lower.point.Y = curEvent.point.Y;
                 curEvent.upper.point.X = curEvent.point.X; curEvent.upper.point.Y = curEvent.point.Y;
                 L.Add(curEvent.upper); L.Add(curEvent.lower);
                 break;
             }
         default:
             break;
     }
 }
        private int comparerEventY(Event x, Event y)
        {
            if (x.pType == PointType.Start && y.pType == PointType.Start
                && x.segIdx == y.segIdx)
                return 0;
            if (x.point.Equals(y.point))
            {
                if(segments[x.segIdx].End.Equals(segments[y.segIdx].End))
                    return 0;
                double maxEX = Math.Max(segments[x.segIdx].End.X, segments[y.segIdx].End.X);

                return lineVal(x, maxEX) < lineVal(y, maxEX) ? -1 : 1;
            }
            double maxSX = Math.Max(x.point.X, y.point.X);
            return lineVal(x, maxSX) < lineVal(y, maxSX) ? -1 : 1;
        }
 private int comparerEventX(Event x, Event y)
 {
     if (x.pType == PointType.Start && y.pType == PointType.Start
         && x.segIdx == y.segIdx)
         return 0;
     if (x.point.Equals(y.point))
         return 0;
     if (Math.Abs(x.point.X - y.point.X) < Constants.Epsilon)
         return x.point.Y < y.point.Y ? -1 : 1;
     return x.point.X < y.point.X ? -1 : 1;
 }