public bool IsValidConnection(GameObject thisSystem, GameObject targetSystem)                                       //Returns true if no intersection
    {
        Vector3 lineA = MathsFunctions.ABCLineEquation(thisSystem.transform.position, targetSystem.transform.position); //Line equation from current system to target system

        Vector3 roughCentre = (thisSystem.transform.position + targetSystem.transform.position) / 2f;

        if (roughCentre.x < 65f && roughCentre.x > 55f)        //If the intersection exists in the galactic core, ignore it
        {
            if (roughCentre.y < 65f && roughCentre.y > 55f)
            {
                return(false);
            }
        }

        for (int i = 0; i < coordinateList.Count; ++i)                                                    //For all existing connections
        {
            if (coordinateList[i].systemOne == thisSystem && coordinateList[i].systemTwo == targetSystem) //If a connection already exists between the current system and the target system, continue to the next connection
            {
                continue;
            }
            if (coordinateList[i].systemTwo == thisSystem && coordinateList[i].systemOne == targetSystem)            //Continuation of above
            {
                continue;
            }
            if (coordinateList[i].systemOne == thisSystem || coordinateList[i].systemTwo == thisSystem)            //If the connection contains this system it will not make intersections with the temporary connection
            {
                continue;
            }
            if (coordinateList[i].systemOne == targetSystem || coordinateList[i].systemTwo == targetSystem)            //If the connection contains the target system it will not make intersections with the temporary connection
            {
                continue;
            }

            //if(CheckIfIntersectionCouldOccur(thisSystem, targetSystem, coordinateList[i].systemOne, coordinateList[i].systemTwo) == false)
            //{
            //	continue;
            //

            Vector3 lineB = MathsFunctions.ABCLineEquation(coordinateList[i].systemOne.transform.position, coordinateList[i].systemTwo.transform.position); //Get the line equation between of the connection

            Vector2 intersection = MathsFunctions.IntersectionOfTwoLines(lineA, lineB);                                                                     //Find the intersection of the two lines

            if (intersection == Vector2.zero)                                                                                                               //If the lines are parallel the method returns a zero vector continue to the next connection
            {
                continue;
            }

            if (MathsFunctions.PointLiesOnLine(thisSystem.transform.position, targetSystem.transform.position, intersection))                                     //If the intersection lies on the temporary connection
            {
                if (MathsFunctions.PointLiesOnLine(coordinateList[i].systemOne.transform.position, coordinateList[i].systemTwo.transform.position, intersection)) //And it lies on the current permanent connection
                {
                    return(false);                                                                                                                                //Return true, an intersection does exist
                }
            }
        }

        return(true);
    }
    public void Update()
    {
        if (MasterScript.systemListConstructor.loaded == true && iterator == 0)
        {
            //start = true;
        }

        if (start == true)
        {
            triangles.Clear();
            tempTri.Clear();
            unvisitedStars.Clear();
            externalPoints.Clear();

            CacheNearestStars();                   //First add all the star systems to a list

            Triangle newTri = new Triangle();      //Create a new triangle
            newTri.points.Add(unvisitedStars [0]); //Add the first 3 ordered points from the centre
            newTri.points.Add(unvisitedStars [1]);
            newTri.points.Add(unvisitedStars[2]);

            newTri.lines.Add(MathsFunctions.ABCLineEquation(newTri.points[0].transform.position, newTri.points[1].transform.position));               //Calculate the line equations between the points
            newTri.lines.Add(MathsFunctions.ABCLineEquation(newTri.points[1].transform.position, newTri.points[2].transform.position));
            newTri.lines.Add(MathsFunctions.ABCLineEquation(newTri.points[2].transform.position, newTri.points[0].transform.position));

            externalPoints.Add(unvisitedStars [0]);              //Add the points to the external points list
            externalPoints.Add(unvisitedStars [1]);
            externalPoints.Add(unvisitedStars [2]);

            triangles.Add(newTri);              //Add the triangle to the triangle list

            unvisitedStars.RemoveRange(0, 3);   //Remove the points from the unvisited points list

            start   = false;
            iterate = true;

            timer = Time.time;
        }

        if (start == false && iterate == true)
        {
            if (iterator < unvisitedStars.Count)
            {
                LinkPointToTris(iterator);
                CacheTempTris(iterator);
                DrawDebugTriangles();
                ++iterator;
                timer = Time.time;
            }

            if (iterator == unvisitedStars.Count)
            {
                DrawDebugTriangles();
                iterate = false;
            }
        }
    }
    public bool CheckIsDelaunay(Triangle triOne, Triangle triTwo)
    {
        List <GameObject> sharedSides = MasterScript.triangulation.CheckIfSharesSide(triOne, triTwo);                                                                  //Find if triangles share a side (this actually returns the 2 shared and 2 unshared vertices)

        if (sharedSides.Count == 4)                                                                                                                                    //If 4 vertices are shared
        {
            GameObject sharedPointA = sharedSides[0];                                                                                                                  //Assign the shared points
            GameObject sharedPointB = sharedSides[1];
            GameObject unsharedPointA = sharedSides[2];                                                                                                                //Assign the unshared points
            GameObject unsharedPointB = sharedSides[3];
            float      angleAlpha = 0f, angleBeta = 0f;                                                                                                                //Set some angles to 0

            angleAlpha = MathsFunctions.AngleBetweenLineSegments(unsharedPointA.transform.position, sharedPointA.transform.position, sharedPointB.transform.position); //First angle is at one unshared point

            angleBeta = MathsFunctions.AngleBetweenLineSegments(unsharedPointB.transform.position, sharedPointA.transform.position, sharedPointB.transform.position);  //Second angle is at the other unshared point

            Vector3 sharedPointLine   = MathsFunctions.ABCLineEquation(sharedPointA.transform.position, sharedPointB.transform.position);                              //Get the line between the shared points
            Vector3 unsharedPointLine = MathsFunctions.ABCLineEquation(unsharedPointA.transform.position, unsharedPointB.transform.position);                          //Get the line between the unshared points
            Vector2 intersection      = MathsFunctions.IntersectionOfTwoLines(sharedPointLine, unsharedPointLine);                                                     //Find the intersection of the two lines

            if (MathsFunctions.PointLiesOnLine(sharedPointA.transform.position, sharedPointB.transform.position, intersection) == false)                               //If the intersection does not lie between the shared points then this is a non convex hull
            {
                return(true);                                                                                                                                          //So it cannot be flipped, continue to the next triangle
            }

            if (angleAlpha + angleBeta > 180f)                                        //If the polygon is convex, and the two angles combine to be greater than 180 degrees, the triangles are non delaunay, so we flip them
            {
                int triPosOne = MasterScript.triangulation.triangles.IndexOf(triOne); //Find the position of the two triangles in the triangles list
                int triPosTwo = MasterScript.triangulation.triangles.IndexOf(triTwo);

                triOne.points[0] = unsharedPointA;                 //Reassign the vertices of tri one to make the previously unshared vertices the shared vertices. One of the previously shared vertices is now the unshared vertex.
                triOne.points[1] = unsharedPointB;
                triOne.points[2] = sharedPointA;
                triOne.lines[0]  = MathsFunctions.ABCLineEquation(triOne.points[0].transform.position, triOne.points[1].transform.position);                 //Get the line equations for all the sides
                triOne.lines[1]  = MathsFunctions.ABCLineEquation(triOne.points[1].transform.position, triOne.points[2].transform.position);
                triOne.lines[2]  = MathsFunctions.ABCLineEquation(triOne.points[2].transform.position, triOne.points[0].transform.position);
                MasterScript.triangulation.triangles[triPosOne] = triOne; //Replace the original triangle with this new, flipped triangle

                triTwo.points[0] = unsharedPointA;                        //Do the same for tri two
                triTwo.points[1] = unsharedPointB;
                triTwo.points[2] = sharedPointB;
                triTwo.lines[0]  = MathsFunctions.ABCLineEquation(triTwo.points[0].transform.position, triTwo.points[1].transform.position);
                triTwo.lines[1]  = MathsFunctions.ABCLineEquation(triTwo.points[1].transform.position, triTwo.points[2].transform.position);
                triTwo.lines[2]  = MathsFunctions.ABCLineEquation(triTwo.points[2].transform.position, triTwo.points[0].transform.position);
                MasterScript.triangulation.triangles[triPosTwo] = triTwo;

                ++flips;                 //Increase the number of flips that have been made this pass.

                return(false);           //Return false (a flip has been made)
            }
        }

        return(true);        //Otherwise continue to the next triangle
    }
    private void CheckForNonDelaunayTriangles()
    {
        List <Triangle> numberofnondelaunay = new List <Triangle>();

        for (int i = 0; i < triangles.Count; ++i)
        {
            for (int j = 0; j < triangles.Count; ++j)
            {
                if (i == j)
                {
                    continue;
                }

                List <GameObject> sharedSides = CheckIfSharesSide(triangles[i], triangles[j]);

                if (sharedSides.Count == 4)
                {
                    GameObject sharedPointA = sharedSides[0];
                    GameObject sharedPointB = sharedSides[1];
                    GameObject unsharedPointA = sharedSides[2];
                    GameObject unsharedPointB = sharedSides[3];
                    float      angleAlpha = 0f, angleBeta = 0f;

                    angleAlpha = MathsFunctions.AngleBetweenLineSegments(unsharedPointA.transform.position, sharedPointA.transform.position, sharedPointB.transform.position);

                    angleBeta = MathsFunctions.AngleBetweenLineSegments(unsharedPointB.transform.position, sharedPointA.transform.position, sharedPointB.transform.position);

                    Vector3 sharedPointLine   = MathsFunctions.ABCLineEquation(sharedPointA.transform.position, sharedPointB.transform.position);
                    Vector3 unsharedPointLine = MathsFunctions.ABCLineEquation(unsharedPointA.transform.position, unsharedPointB.transform.position);
                    Vector2 intersection      = MathsFunctions.IntersectionOfTwoLines(sharedPointLine, unsharedPointLine);

                    if (MathsFunctions.PointLiesOnLine(sharedPointA.transform.position, sharedPointB.transform.position, intersection) == false)                    //Is non-convex
                    {
                        continue;
                    }

                    if (angleBeta + angleAlpha > 180)
                    {
                        numberofnondelaunay.Add(triangles[i]);
                    }
                }
            }
        }

        Debug.Log(numberofnondelaunay.Count + " | " + triangles.Count);
    }
    public void SimpleTriangulation()          //This function controls the triangulation and conversion to delaunay of the stars
    {
        CacheNearestStars();                   //First add all the star systems to a list

        Triangle newTri = new Triangle();      //Create a new triangle

        newTri.points.Add(unvisitedStars [0]); //Add the first 3 ordered points from the centre
        newTri.points.Add(unvisitedStars [1]);
        newTri.points.Add(unvisitedStars[2]);

        newTri.lines.Add(MathsFunctions.ABCLineEquation(newTri.points[0].transform.position, newTri.points[1].transform.position));           //Calculate the line equations between the points
        newTri.lines.Add(MathsFunctions.ABCLineEquation(newTri.points[1].transform.position, newTri.points[2].transform.position));
        newTri.lines.Add(MathsFunctions.ABCLineEquation(newTri.points[2].transform.position, newTri.points[0].transform.position));

        externalPoints.Add(unvisitedStars [0]);          //Add the points to the external points list
        externalPoints.Add(unvisitedStars [1]);
        externalPoints.Add(unvisitedStars [2]);

        triangles.Add(newTri);                         //Add the triangle to the triangle list

        unvisitedStars.RemoveRange(0, 3);              //Remove the points from the unvisited points list

        for (int i = 0; i < unvisitedStars.Count; ++i) //For all unchecked points
        {
            LinkPointToTris(i);                        //Link this unvisited point to all possible external points
            CacheTempTris(i);                          //Add all the triangles formed by this linking to the triangle list
        }

        bool isDelaunay = false;                                                  //Say that the list isn't delaunay

        while (isDelaunay == false)                                               //While it isn't delaunay
        {
            isDelaunay = MasterScript.voronoiGenerator.TriangulationToDelaunay(); //Make it delaunay, if the method returns true, the triangulation is delaunay and the while loop will stop
        }

        CheckForNonDelaunayTriangles();          //Debugging method outputs the number of non-delaunay triangles to the log. This has not output any bad values for some time.
    }
    private void LinkPointToTris(int curPoint)         //Send the current unvisited star as the seed point SOMETHING WRONG
    {
        for (int i = 0; i < externalPoints.Count; ++i) //For all the external points
        {
            int nextPoint = i + 1;                     //Assign the next point

            if (nextPoint == externalPoints.Count)     //If the next point is out of range
            {
                nextPoint = 0;                         //Set it to the first point in the list
            }

            Vector3 lineCurToExternal = MathsFunctions.ABCLineEquation(unvisitedStars[curPoint].transform.position, externalPoints[i].transform.position); //Create a line between the external point and the unvisited star

            if (IsIllegalIntersection(i, curPoint, lineCurToExternal))                                                                                     //If there is an illegal intersection between the external point-current point line and the external point-unvisited point line
            {
                continue;                                                                                                                                  //Move onto the next external point
            }

            Vector3 lineCurToNextExternal = MathsFunctions.ABCLineEquation(unvisitedStars[curPoint].transform.position, externalPoints[nextPoint].transform.position);

            if (IsIllegalIntersection(nextPoint, curPoint, lineCurToNextExternal)) //If there is an illegal intersection between the next point-current point line and the external point-unvisited point line
            {
                continue;                                                          //Move onto the next external point
            }

            bool illegal = false;                          //Say that the line is not illegal

            for (int j = 0; j < externalPoints.Count; ++j) //Check through all other external points
            {
                if (j == i || j == nextPoint)
                {
                    continue;
                }

                if (MathsFunctions.IsInTriangle(externalPoints[i].transform.position, externalPoints[nextPoint].transform.position, unvisitedStars[curPoint].transform.position, externalPoints[j].transform.position) == true)                //If the point lies in any of the triangles
                {
                    //if(MathsFunctions.PointsAreColinear(externalPoints[i].transform.position, externalPoints[nextPoint].transform.position, externalPoints[j].transform.position) == false)
                    //{
                    //if(MathsFunctions.PointsAreColinear(externalPoints[i].transform.position, unvisitedStars[curPoint].transform.position, externalPoints[j].transform.position) == false)
                    //{
                    //if(MathsFunctions.PointsAreColinear(externalPoints[nextPoint].transform.position, unvisitedStars[curPoint].transform.position, externalPoints[j].transform.position) == false)
                    //{
                    illegal = true;                                    //It is an illegal triangle
                    break;                                             //
                    //}
                    //}
                    //}
                }
            }

            if (illegal)            //If it's an illegal triangle
            {
                continue;           //Skip to the next point
            }

            GameObject pointA = externalPoints[i];             //Otherwise assign the points of the triangle
            GameObject pointB = externalPoints[nextPoint];
            GameObject pointC = unvisitedStars[curPoint];

            Triangle newTri = new Triangle();       //Create a new triangle object
            newTri.points.Add(pointA);              //Add the points
            newTri.points.Add(pointB);
            newTri.points.Add(pointC);
            newTri.lines.Add(MathsFunctions.ABCLineEquation(pointA.transform.position, pointB.transform.position));               //Calculate the line equations between the points
            newTri.lines.Add(MathsFunctions.ABCLineEquation(pointB.transform.position, pointC.transform.position));
            newTri.lines.Add(MathsFunctions.ABCLineEquation(pointC.transform.position, pointA.transform.position));
            tempTri.Add(newTri);              //Add the triangle to the temptriangle list
        }
    }