SpanningTree() 공개 메소드

public SpanningTree ( KruskalType type = KruskalType.MINIMUM ) : List
type KruskalType
리턴 List
예제 #1
0
    // take all the midpoints of the selected rooms and feed that into the Delaunay procedure
    //  generate a graph, also it's good to have ID for rooms
    // and generate minimum spanning tree
    private void TriangulateMainRoomsMidpointsAndGenerateMST()
    {
        List <Vector2> midpoints = new List <Vector2>();
        List <uint>    colors    = new List <uint>(); // Colors are just necessary part for choosen delaunay library

        Vector2 min = Vector2.positiveInfinity;
        Vector2 max = Vector2.zero;

        for (int i = 0; i < rooms.Count; i++)
        {
            DelaunayMSTRoom room = rooms[i];
            if (room.isMainRoom)
            {
                colors.Add(0);
                midpoints.Add(new Vector2(room.x + room.width / 2, room.y + room.height / 2)); // use division (not multiplication) because we need INT value (or use RoundToInt)
                min.x = Mathf.Min(min.x, room.x);
                min.y = Mathf.Min(min.y, room.y);

                max.x = Mathf.Max(max.x, room.x);
                max.y = Mathf.Max(max.y, room.y);
            }
        }

        Delaunay.Voronoi voronoi = new Delaunay.Voronoi(midpoints, colors, new Rect(min.x, min.y, max.x, max.y));
        delaunayLines = voronoi.DelaunayTriangulation();                   // Triangulate main rooms

        spanningTree = voronoi.SpanningTree(Delaunay.KruskalType.MINIMUM); //Find min. span. tree

        if (settings.isDebugLogEnabled)
        {
            Debug.Log("Main passages count: " + spanningTree.Count);
        }
    }
예제 #2
0
    public Dictionary <Vector2, List <Vector2> > GenDelaunay()
    {
        Dictionary <Vector2, List <Vector2> > points = new Dictionary <Vector2, List <Vector2> >();
        int m_pointCount = 20;

        List <Vector2>     m_points;
        float              m_mapWidth  = 25;
        float              m_mapHeight = 12;
        List <LineSegment> m_edges     = null;
        List <LineSegment> m_spanningTree;
        List <LineSegment> m_delaunayTriangulation;
        List <uint>        colors = new List <uint>();

        m_points = new List <Vector2>();

        for (int i = 0; i < m_pointCount; i++)
        {
            colors.Add(0);
            m_points.Add(new Vector2(
                             Random.Range(2f, m_mapWidth - 2f),
                             Random.Range(2f, m_mapHeight))
                         );
        }
        Delaunay.Voronoi v = new Delaunay.Voronoi(m_points, colors, new Rect(2f, 2f, m_mapWidth, m_mapHeight));
        m_edges                 = v.VoronoiDiagram();
        m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
        m_delaunayTriangulation = v.DelaunayTriangulation();

        foreach (Vector2 coord in m_points)
        {
            points.Add(coord, v.NeighborSitesForSite(coord));
        }

        return(points);
    }
    void CreateDelauneyAndTree()
    {
        mainRoomPoints = new Vector2[mainRooms.Count];
        for (int i = 0; i < mainRooms.Count; i++)
        {
            mainRoomPoints[i] = mainRooms [i].transform.position;
        }

        List <uint> colors = new List <uint> ();

        foreach (Vector2 point in mainRoomPoints)
        {
            colors.Add(0);
        }

        Delaunay.Voronoi v = new Delaunay.Voronoi(mainRoomPoints.ToList(), colors, new Rect(0, 0, 100, 50));
        m_delaunayTriangulation = v.DelaunayTriangulation();
        m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
        corridors = m_spanningTree;
        for (int i = 0; i < m_delaunayTriangulation.Count; i++)
        {
            if (Random.value < level.chanceToAddExtraCorridor)
            {
                corridors.Add(m_delaunayTriangulation[i]);
            }
        }
    }
예제 #4
0
    private void GenerateEdges(List <Vector2> points)
    {
        List <LineSegment> minimumSpanningTree;
        List <LineSegment> delaunayTriangulation;
        List <LineSegment> finalEdges = new List <LineSegment>();

        // Create the Voronoi diagram using the AS3 Delaunay library
        List <uint> colors = new List <uint> ();

        for (int i = 0; i < points.Count; i++)
        {
            colors.Add(0);
        }
        Delaunay.Voronoi voronoi = new Delaunay.Voronoi(points, colors, new Rect(0, 0, _mapWidth, _mapHeight));
        minimumSpanningTree   = voronoi.SpanningTree(KruskalType.MINIMUM);
        delaunayTriangulation = voronoi.DelaunayTriangulation();

        // First add any line segment in the minimum spanning tree to the list _edges
        for (int i = delaunayTriangulation.Count - 1; i >= 0; i--)
        {
            for (int j = 0; j < minimumSpanningTree.Count; j++)
            {
                if (LineSegmentEquals(minimumSpanningTree[j], delaunayTriangulation[i]))
                {
                    finalEdges.Add(delaunayTriangulation[i]);

                    delaunayTriangulation.RemoveAt(i);

                    break;
                }
            }
        }

        // Add a random amount of line segments in the delaunay triangulation but NOT in the minimum spanning tree to the list _edges
        for (int i = 0, count = delaunayTriangulation.Count; i < count; i++)
        {
            float rand = UnityEngine.Random.value;
            if (rand <= 0.35)
            {
                finalEdges.Add(delaunayTriangulation[i]);
            }
        }

        // Create the edges on the map
        // Also update neighbours properties on the nodes
        for (int i = 0, count = finalEdges.Count; i < count; i++)
        {
            LineSegment line = finalEdges[i];

            Vector3 p0 = new Vector3(line.p0.Value.x, line.p0.Value.y, 0);
            Vector3 p1 = new Vector3(line.p1.Value.x, line.p1.Value.y, 0);

            MapEdge mapEdge = CreateMapEdge(p0, p1);
            mapEdge.Initialize(p0, p1);
        }
    }
예제 #5
0
    private void Edges(float[,] map, Color[] pixels)
    {
        m_points = new List <Vector2> ();
        List <uint> colors = new List <uint> ();

        GenerateCity(map, m_points);
        for (int i = 0; i < m_points.Count; i++)
        {
            colors.Add((uint)0);
        }
        Delaunay.Voronoi v = new Delaunay.Voronoi(m_points, colors, new Rect(0, 0, WIDTH, HEIGHT));
        m_edges                 = v.VoronoiDiagram();
        m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
        m_delaunayTriangulation = v.DelaunayTriangulation();
        Color color = Color.red;

        /* Shows Voronoi diagram */

        /*for (int i = 0; i < m_edges.Count; i++) {
         *      LineSegment seg = m_edges [i];
         *      Vector2 left = (Vector2)seg.p0;
         *      Vector2 right = (Vector2)seg.p1;
         *      DrawLine (pixels,left, right,color);
         * }*/
        /* Shows Delaunay triangulation */
        for (int i = 0; i < m_edges.Count; i++)
        {
            LineSegment seg   = m_edges [i];
            Vector2     left  = (Vector2)seg.p0;
            Vector2     right = (Vector2)seg.p1;
            //DrawLine (pixels,left, right,color);

            /*ChunkLOD prefabLOD = mapGen.terrainPrefab.GetComponent<ChunkLOD> ();
             * float chunkSize = prefabLOD.SIZE_W;
             * float terrainSize = mapGen.WIDTH;
             * float SIZE = WIDTH;
             *
             * float length = (right - left).magnitude  * (terrainSize * chunkSize) / (float) SIZE;
             * float angle = Vector2.Angle (right - left, Vector2.right);*/
            float scaleFactor = ChunkLOD.GLOBAL_WIDTH * ChunkLOD.SIZE_W / WIDTH;

            GameObject road = Instantiate(roadPrefab, new Vector3(scaleFactor * left.x, 0.2f, scaleFactor * left.y), Quaternion.identity);
            Road       r    = road.GetComponent <Road> ();
            r.SetMesh(scaleFactor * (right - left));
        }
    }
예제 #6
0
        private void VoronoiGeneration()
        {
            List <Vector2> points = new List <Vector2>();
            List <uint>    colors = new List <uint>();

            for (int i = 0; i < primaryRooms.Count; i++)
            {
                points.Add(primaryRooms[i].center);
                colors.Add(0);
            }

            Delaunay.Voronoi v = new Delaunay.Voronoi(points, colors, new Rect(center, size));

            edges                 = v.VoronoiDiagram();
            spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
            delaunayTriangulation = v.DelaunayTriangulation();
        }
예제 #7
0
    private void Demo()
    {
        List <uint> colors = new List <uint>();

        m_points = new List <Vector2>();

        for (int i = 0; i < m_pointCount; i++)
        {
            colors.Add(0);
            m_points.Add(new Vector2(
                             UnityEngine.Random.Range(0, m_mapWidth),
                             UnityEngine.Random.Range(0, m_mapHeight)));
        }

        Delaunay.Voronoi v = new Delaunay.Voronoi(m_points, colors, new Rect(0, 0, m_mapWidth, m_mapHeight));
        m_edges                 = v.VoronoiDiagram();
        m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
        m_delaunayTriangulation = v.DelaunayTriangulation();
    }
	private void Demo ()
	{
				
		List<uint> colors = new List<uint> ();
		m_points = new List<Vector2> ();
			
		for (int i = 0; i < m_pointCount; i++) {
			colors.Add (0);
			m_points.Add (new Vector2 (
					UnityEngine.Random.Range (0, m_mapWidth),
					UnityEngine.Random.Range (0, m_mapHeight))
			);
		}
		Delaunay.Voronoi v = new Delaunay.Voronoi (m_points, colors, new Rect (0, 0, m_mapWidth, m_mapHeight));
		m_edges = v.VoronoiDiagram ();
			
		m_spanningTree = v.SpanningTree (KruskalType.MINIMUM);
		m_delaunayTriangulation = v.DelaunayTriangulation ();
	}
		public void Demo () /** Public so that the custom Inspector class can call it */
		{
		
				List<uint> colors = new List<uint> ();
				m_points = new List<Vector2> ();
		
				for (int i = 0; i < numSitesToGenerate; i++) {
						colors.Add (0);
						m_points.Add (new Vector2 (
				UnityEngine.Random.Range (0, m_mapWidth),
				UnityEngine.Random.Range (0, m_mapHeight))
						);
				}
				v = new Delaunay.Voronoi (m_points, colors, new Rect (0, 0, m_mapWidth, m_mapHeight));
				m_edges = v.VoronoiDiagram ();
		
				m_spanningTree = v.SpanningTree (KruskalType.MINIMUM);
				m_delaunayTriangulation = v.DelaunayTriangulation ();
				
				Debug.Log ("Created a Voronoi object. But for Unity, it's recommend you convert it to a VoronoiMap (data structure using Unity GameObjects and MonoBehaviours)");
				//Example:
                VoronoiDiagram map = VoronoiDiagram.CreateDiagramFromVoronoiOutput( v, true );
		}
예제 #10
0
    public void Demo()              /** Public so that the custom Inspector class can call it */
    {
        List <uint> colors = new List <uint> ();

        m_points = new List <Vector2> ();

        for (int i = 0; i < numSitesToGenerate; i++)
        {
            colors.Add(0);
            m_points.Add(new Vector2(
                             UnityEngine.Random.Range(0, m_mapWidth),
                             UnityEngine.Random.Range(0, m_mapHeight))
                         );
        }
        v       = new Delaunay.Voronoi(m_points, colors, new Rect(0, 0, m_mapWidth, m_mapHeight));
        m_edges = v.VoronoiDiagram();

        m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
        m_delaunayTriangulation = v.DelaunayTriangulation();

        Debug.Log("Created a Voronoi object. But for Unity, it's recommend you convert it to a VoronoiMap (data structure using Unity GameObjects and MonoBehaviours)");
        //Example:
        VoronoiDiagram map = VoronoiDiagram.CreateDiagramFromVoronoiOutput(v, true);
    }
예제 #11
0
    void Start()
    {
        map = createMap();
        List <float[]> weighten_map = weightenMap(map);

        Color[] pixels = createPixelMap(map);

        /* Change position of plane according to desired borders */
        this.gameObject.transform.position = new Vector3((PLANE_MIN_BORDER + PLANE_MAX_BORDER) / 2, 0, (PLANE_MIN_BORDER + PLANE_MAX_BORDER) / 2);
        /* Rescale plane with desired size */
        this.gameObject.transform.localScale = new Vector3(PLANE_SIZE / 10, 1, PLANE_SIZE / 10);

        m_points = new List <Vector2> ();
        List <uint> colors = new List <uint> ();

        /* Create circle points */

        /* center */
        colors.Add((uint)0);
        m_points.Add(new Vector2(SIZE / 2, SIZE / 2));

        /* Add the points on the cercle */
        for (int i = 0; i < SIZE; i++)
        {
            for (int j = 0; j < SIZE; j++)
            {
                int x = i - SIZE / 2;
                int y = j - SIZE / 2;

                if (x * x + y * y == CENTER_RADIUS * CENTER_RADIUS)
                {
                    colors.Add((uint)0);
                    Vector2 vec = new Vector2(i, j);
                    m_points.Add(vec);
                }
            }
        }

        /* Add N random points */
        for (int i = 0; i < NPOINTS; i++)
        {
            colors.Add((uint)0);
            /* Higher density points have ore chance to be selected */
            float[] rnd_coord = weighten_map[(int)UnityEngine.Random.Range(0, weighten_map.Count)];
            Vector2 vec       = new Vector2(rnd_coord[0], rnd_coord[1]);
            m_points.Add(vec);
        }

        /* Generate Graphs */
        Delaunay.Voronoi v = new Delaunay.Voronoi(m_points, colors, new Rect(0, 0, SIZE, SIZE));
        m_edges                 = v.VoronoiDiagram();
        m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
        m_delaunayTriangulation = v.DelaunayTriangulation();

        /* Instatiates buildings and roads */
        createStructures();

        /* build navmesh */
        surface.BuildNavMesh();

        /* Instatiate agents and affect them homes */
        createPopulation();

        /* Build lists of workplaces and habitations */
        splitHabitationWorkplace();

        /* Give a workplace to each agent */
        affectWorkplaces();
    }
예제 #12
0
  void Start()
  {
      map = createMap();
      Color[] pixels = createPixelMap(map);

      /* Create random points points */
      m_points = new List <Vector2> ();
      List <uint> colors = new List <uint> ();

      for (int i = 0; i < NPOINTS; i++)
      {
          int x    = Random.Range(0, WIDTH - 1);
          int y    = Random.Range(0, HEIGHT - 1);
          int iter = 0;
          while (iter < 3 && map[x, y] < 0.7)
          {
              x = Random.Range(0, WIDTH - 1);
              y = Random.Range(0, HEIGHT - 1);
              iter++;
          }
          colors.Add((uint)0);
          Vector2 vec = new Vector2(x, y);
          m_points.Add(vec);
      }

      /* Generate Graphs */
      Delaunay.Voronoi v = new Delaunay.Voronoi(m_points, colors, new Rect(0, 0, WIDTH, HEIGHT));
      m_edges                 = v.VoronoiDiagram();
      m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
      m_delaunayTriangulation = v.DelaunayTriangulation();

      /* Shows Voronoi diagram */
      Color color = Color.blue;

      for (int i = 0; i < m_edges.Count; i++)
      {
          LineSegment seg   = m_edges[i];
          Vector2     left  = (Vector2)seg.p0;
          Vector2     right = (Vector2)seg.p1;
          //DrawLine (pixels,left, right,color);
          Vector2    dir = (right - left) / WIDTH * 100;
          float      a   = Vector2.SignedAngle(Vector2.right, right - left);
          GameObject go  = Instantiate(road, new Vector3(left.y / WIDTH * 100 - 100 / 2, 0, left.x / HEIGHT * 100 - 100 / 2), Quaternion.Euler(0, a + 90, 0));
          go.transform.localScale = new Vector3(dir.magnitude, 1, 1);
          go.transform.parent     = roadsParent.transform;
          // set the zone type : 1 - work / 0 - home / 2 - nothing
          if (Mathf.RoundToInt(seg.p0.Value.x) >= 0 && Mathf.RoundToInt(seg.p0.Value.x) < WIDTH &&
              Mathf.RoundToInt(seg.p0.Value.y) >= 0 && Mathf.RoundToInt(seg.p0.Value.y) < HEIGHT &&
              Mathf.RoundToInt(seg.p1.Value.x) >= 0 && Mathf.RoundToInt(seg.p1.Value.x) < WIDTH &&
              Mathf.RoundToInt(seg.p1.Value.y) >= 0 && Mathf.RoundToInt(seg.p1.Value.y) < HEIGHT &&
              map[Mathf.RoundToInt(seg.p0.Value.x), Mathf.RoundToInt(seg.p0.Value.y)] > 0.7 &&
              map[Mathf.RoundToInt(seg.p1.Value.x), Mathf.RoundToInt(seg.p1.Value.y)] > 0.7)
          {
              changeMaterial(go, test_road);
              Road go_data = go.GetComponent("Road") as Road;
              go_data.zoneType = 1;
              go.GetComponent <NavMeshModifier>().area = 3;
          }
          else if (Mathf.RoundToInt(seg.p0.Value.x) >= 0 && Mathf.RoundToInt(seg.p0.Value.x) < WIDTH &&
                   Mathf.RoundToInt(seg.p0.Value.y) >= 0 && Mathf.RoundToInt(seg.p0.Value.y) < HEIGHT &&
                   Mathf.RoundToInt(seg.p1.Value.x) >= 0 && Mathf.RoundToInt(seg.p1.Value.x) < WIDTH &&
                   Mathf.RoundToInt(seg.p1.Value.y) >= 0 && Mathf.RoundToInt(seg.p1.Value.y) < HEIGHT &&
                   map[Mathf.RoundToInt(seg.p0.Value.x), Mathf.RoundToInt(seg.p0.Value.y)] > 0.5 &&
                   map[Mathf.RoundToInt(seg.p1.Value.x), Mathf.RoundToInt(seg.p1.Value.y)] > 0.5)
          {
              Road go_data = go.GetComponent("Road") as Road;
              go_data.zoneType = 2;
          }
      }

      /* Shows Delaunay triangulation */

      /*
       * color = Color.red;
       * if (m_delaunayTriangulation != null) {
       *      for (int i = 0; i < m_delaunayTriangulation.Count; i++) {
       *                      LineSegment seg = m_delaunayTriangulation [i];
       *                      Vector2 left = (Vector2)seg.p0;
       *                      Vector2 right = (Vector2)seg.p1;
       *                      DrawLine (pixels,left, right,color);
       *      }
       * }*/

      /* Shows spanning tree */

      /*
       * color = Color.black;
       * if (m_spanningTree != null) {
       *      for (int i = 0; i< m_spanningTree.Count; i++) {
       *              LineSegment seg = m_spanningTree [i];
       *              Vector2 left = (Vector2)seg.p0;
       *              Vector2 right = (Vector2)seg.p1;
       *              DrawLine (pixels,left, right,color);
       *      }
       * }*/

      /* Apply pixels to texture */
      //tx = new Texture2D(WIDTH, HEIGHT);
      //land.SetTexture ("_MainTex", tx);
      //tx.SetPixels (pixels);
      //tx.Apply ();

      /* Generate Buildings */
      generateHouses();
      /* build the NavMesh */
      roadsParent.GetComponent <NavMeshSurface>().BuildNavMesh();
      /* Start Game Logic */
      HumansManager.gameState = 0;           // Ready to start game logic
  }
예제 #13
0
    void Start()
    {
        ag            = GetComponent <AgentControlerInitial>();
        float [,] map = createMap();
        float[,] map2 = new float[WIDTH, HEIGHT];
        Color[] pixels = createPixelMap(map);
        float   sum    = 0;

        for (int i = 0; i <= map.GetUpperBound(0); i++)
        {
            for (int j = 0; j <= map.GetUpperBound(1); j++)
            {
                sum = sum + map[i, j];
            }
        }
        for (int i = 0; i <= map.GetUpperBound(0); i++)
        {
            for (int j = 0; j <= map.GetUpperBound(1); j++)
            {
                map2[i, j] = map[i, j] / sum;
            }
        }

        /* Create random points points */

        m_points = new List <Vector2> ();
        List <uint> colors = new List <uint> ();

        for (int i = 0; i < NPOINTS; i++)
        {
            colors.Add((uint)0);
            int[] col = { 0, 0 };
            col = getRandomValue(map2);
            //Vector2 vec = new Vector2(Random.Range(0, WIDTH - 1), Random.Range(0, HEIGHT - 1));
            //Debug.Log(vec);
            Vector2 vec = new Vector2(col[0], col[1]);
            //Debug.Log(vec);
            m_points.Add(vec);
        }

        /* Generate Graphs */
        Delaunay.Voronoi v = new Delaunay.Voronoi(m_points, colors, new Rect(0, 0, WIDTH, HEIGHT));
        m_edges                 = v.VoronoiDiagram();
        m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
        m_delaunayTriangulation = v.DelaunayTriangulation();


        /* Shows Voronoi diagram */
        Color color = Color.blue;

        update_table();
        update_table_city();
        for (int i = 0; i < m_edges.Count; i++)
        {
            LineSegment seg     = m_edges [i];
            Vector2     left    = (Vector2)seg.p0;
            Vector2     right   = (Vector2)seg.p1;
            Vector2     segment = (right - left) / WIDTH * 10;
            float       angle   = Vector2.SignedAngle(Vector2.right, right - left);
            // 10 taille du plan et 5 c'est le décalage du plan
            // Changer emission tiling -1 et -1
            GameObject go;
            if (isCity[edge_table[i][0]] == 0)
            {
                go = Instantiate(road, new Vector3(5 - left.y / WIDTH * plane_factor, 0, 5 - left.x / HEIGHT * plane_factor), Quaternion.Euler(0, angle + 90, 0));
            }
            else
            {
                go = Instantiate(highway, new Vector3(5 - left.y / WIDTH * plane_factor, 0, 5 - left.x / HEIGHT * plane_factor), Quaternion.Euler(0, angle + 90, 0));
            }
            go.transform.localScale = new Vector3(segment.magnitude, 1, 1);
            Vector3 tmpPosition   = go.transform.localPosition;
            Vector3 tmpPositionlb = go.transform.localPosition + new Vector3(-0.45f, 0f, -0.025f);
            Vector3 tmpPositionrb = go.transform.localPosition + new Vector3(-0.45f, 0f, 0.025f);
            //Vector3 tmpPositionle = go.transform.localPosition + new Vector3(0.45f, 0f, -0.025f);
            //Vector3 tmpPositionre = go.transform.localPosition + new Vector3(0.45f, 0f, 0.025f);
            Vector3 center_road = new Vector3(5 - (left.y + right.y) / (2 * WIDTH) * plane_factor, 0f, 5 - (left.x + right.x) / (2 * HEIGHT) * plane_factor);
            Vector3 perp        = Quaternion.Euler(0, angle + 80, 0) * new Vector3(0f, 0f, 0.1f);
            //perp = perp.normalized*0.06f;
            Vector3 tmp_building_posr = center_road;
            Vector3 tmp_building_posl = center_road;
            Vector3 building_posr     = new Vector3(tmp_building_posr.x, 0f, tmp_building_posr.z) - perp;
            Vector3 building_posl     = new Vector3(tmp_building_posl.x, 0f, tmp_building_posl.z) + perp;
            //building_posr =  go.transform.TransformPoint(building_posr);
            //building_posl = go.transform.TransformPoint(building_posl);
            //Instantiate(road, new Vector3(5 - left.y / WIDTH * plane_factor, 0, 5 - left.x / HEIGHT * plane_factor), Quaternion.Euler(0, angle + 90, 0));
            //Instantiate(road, new Vector3(5 - left.y / WIDTH * plane_factor, 0, 5 - left.x / HEIGHT * plane_factor), Quaternion.Euler(0, angle + 90, 0));

            if (isCity[edge_table[i][0]] == 0)
            {
                if (nb_rest <= 2 && Random.Range(0, 100) < 3)
                {
                    nb_rest += 1;
                    GameObject resta = Instantiate(restau, building_posl, Quaternion.Euler(0, angle + 90, 0));
                    list_restau.Add(go);
                    list_restau2.Add(resta);
                }
                else if (segment.magnitude > 0.15)
                {
                    GameObject skyscrapl = Instantiate(skyscraper, building_posl, Quaternion.Euler(0, angle + 90, 0));
                    GameObject skyscrapr = Instantiate(skyscraper, building_posr, Quaternion.Euler(0, angle + 90, 0));
                    list_skys.Add(go);
                    list_skys.Add(go);
                    list_skys2.Add(skyscrapl);
                    list_skys2.Add(skyscrapr);
                    //Destroy(go);
                    if (segment.magnitude < 1.1f * skyscr_size)
                    {
                        float rapp = (segment.magnitude) / (1.1f * skyscr_size);
                        //Debug.Log(rapp);
                        skyscrapl.transform.localScale = skyscrapl.transform.localScale * Mathf.Max(0.2f, rapp);
                        skyscrapr.transform.localScale = skyscrapr.transform.localScale * Mathf.Max(0.2f, rapp);
                    }
                }
            }
            else if (isCity[edge_table[i][0]] == 1)
            {
                /*int nb_house = Mathf.FloorToInt(segment.magnitude / 1.5f * home_size);
                 * Vector2 single_length = segment / (nb_house*2);
                 * Vector3 add_length = new Vector3(single_length.x, 0f, single_length.y);*/
                if (segment.magnitude > 0.2)
                {
                    GameObject house1 = Instantiate(house, building_posl + new Vector3(0f, 0.04f, 0f), Quaternion.Euler(0, angle + 90, 0));
                    GameObject house2 = Instantiate(house, building_posr + new Vector3(0f, 0.04f, 0f), Quaternion.Euler(0, angle + 90, 0));
                    list_house.Add(go);
                    list_house.Add(go);
                    list_house2.Add(house1);
                    list_house2.Add(house2);
                }
            }
            else if (isCity[edge_table[i][0]] == 2)
            {
                park_list.Add(go);
                isCity[edge_table[i][0]]++;
            }
            DrawLine(pixels, left, right, color);
        }

        /* Shows Delaunay triangulation */

        /*
         * color = Color.red;
         * if (m_delaunayTriangulation != null) {
         *      for (int i = 0; i < m_delaunayTriangulation.Count; i++) {
         *                      LineSegment seg = m_delaunayTriangulation [i];
         *                      Vector2 left = (Vector2)seg.p0;
         *                      Vector2 right = (Vector2)seg.p1;
         *                      DrawLine (pixels,left, right,color);
         *      }
         * }*/

        /* Shows spanning tree */

        /*
         * color = Color.black;
         * if (m_spanningTree != null) {
         *      for (int i = 0; i< m_spanningTree.Count; i++) {
         *              LineSegment seg = m_spanningTree [i];
         *              Vector2 left = (Vector2)seg.p0;
         *              Vector2 right = (Vector2)seg.p1;
         *              DrawLine (pixels,left, right,color);
         *      }
         * }*/

        /* Apply pixels to texture */
        tx = new Texture2D(WIDTH, HEIGHT);
        land.SetTexture("_MainTex", tx);
        tx.SetPixels(pixels);
        tx.Apply();



        plane.GetComponent <NavMeshSurface>().BuildNavMesh();
        ag.initializeAgent();
    }
        public void StartTriangulation()
        {
            List <Vector2> m_points = rooms.Select(o => o.rect.center).ToList();
            List <uint>    colors   = new List <uint>();

            foreach (Vector2 v in m_points)
            {
                colors.Add(0);
            }

            v = new Voronoi(m_points, colors, new Rect(0, 0, -999999, 999999));

            m_delaunayTriangulation = v.DelaunayTriangulation();
            m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);

            List <LineSegment> trisLeft = new List <LineSegment>();

            foreach (LineSegment d in m_delaunayTriangulation)
            {
                bool safeToAdd = true;
                foreach (LineSegment s in m_spanningTree)
                {
                    if ((d.p0 == s.p0 && d.p1 == s.p1) || (d.p0 == s.p1 && d.p1 == s.p0))
                    {
                        safeToAdd = false;
                        break;
                    }
                }
                if (safeToAdd)
                {
                    trisLeft.Add(d);
                }
            }

            trisLeft = trisLeft.OrderBy(o => (Vector2.SqrMagnitude((Vector2)(o.p0 - o.p1)))).ToList();
            for (int i = 0; i < (int)(trisLeft.Count * keepConnection); i++)
            {
                m_spanningTree.Add(trisLeft[i]);
            }

            roomConnection.Clear();
            foreach (LineSegment l in m_spanningTree)
            {
                if (roomConnection.ContainsKey(l))
                {
                    continue;
                }

                Room r1 = null, r2 = null;
                foreach (Room r in rooms)
                {
                    if (r.rect.center == l.p0)
                    {
                        r1 = r;
                    }
                    else if (r.rect.center == l.p1)
                    {
                        r2 = r;
                    }
                }

                if (r1 == null || r2 == null)
                {
                    Debug.Log("Dude, something doesn't right! Room is not detected in triangulation! Check here");
                }
                else
                {
                    roomConnection.Add(l, new List <Room>(2)
                    {
                        r1, r2
                    });
                }
            }
        }
		public void StartTriangulation()
		{
			if (dg == null)
				return;
			mainRooms.Clear();
			float mean = dg.rooms.Average(o => o.rect.size.sqrMagnitude);
			var roomFromTheBiggest = dg.rooms.OrderBy(o => o.rect.size.sqrMagnitude).ToList();
			roomFromTheBiggest.Reverse();
			foreach(Room r in roomFromTheBiggest)
			{
				if(r.rect.size.sqrMagnitude >= mean)
				{
					mainRooms.Add(r);
				}
				if (mainRooms.Count >= dg.rooms.Count * mainRoomSize)
					break;
			}

			List<Vector2> m_points = mainRooms.Select(o => o.rect.center).ToList();
			List<uint> colors = new List<uint>();
			foreach (Vector2 v in m_points)
				colors.Add(0);

			v = new Voronoi(m_points, colors, new Rect(0, 0, -999999, 999999));

			m_delaunayTriangulation = v.DelaunayTriangulation();
			m_spanningTree = v.SpanningTree(KruskalType.MINIMUM);

			List<LineSegment> trisLeft = new List<LineSegment>();
			foreach(LineSegment d in m_delaunayTriangulation)
			{
				bool safeToAdd = true;
				foreach(LineSegment s in m_spanningTree)
				{
					if ((d.p0 == s.p0 && d.p1 == s.p1) || (d.p0 == s.p1 && d.p1 == s.p0)) 
					{
						safeToAdd = false;
						break;
					}
				}
				if(safeToAdd)
					trisLeft.Add(d);
			}

			trisLeft = trisLeft.OrderBy(o => (Vector2.SqrMagnitude((Vector2)(o.p0 - o.p1)))).ToList();
			for(int i = 0; i < (int)(trisLeft.Count * keepConnection); i++)
			{
				m_spanningTree.Add(trisLeft[i]);
			}
			
			dg.roomConnection.Clear();
			foreach(LineSegment l in m_spanningTree)
			{
				if (dg.roomConnection.ContainsKey(l))
					continue;

				Room r1 = null, r2 = null;
				foreach(Room r in mainRooms)
				{
					if (r.rect.center == l.p0)
						r1 = r;
					else if (r.rect.center == l.p1)
						r2 = r;
				}

				if(r1 == null || r2 == null)
				{
#if DEBUG_MODE
					Debug.Log("Dude, something doesn't right! Room is not detected in triangulation! Check here");
#endif
				}
				else 
				{
					dg.roomConnection.Add(l, new List<Room>(2) { r1, r2 });
				}
			}
		}
예제 #16
0
    void Start()
    {
        map        = createmap();
        _cities    = new Dictionary <Vector2, City>();
        realPoints = new List <Vector2>();
        tx         = new Texture2D((int)m_mapWidth, (int)m_mapHeight);
        pixels     = new Color[(int)m_mapWidth * (int)m_mapHeight];
        for (int i = 0; i < m_mapWidth; i++)
        {
            for (int j = 0; j < m_mapHeight; j++)
            {
                //pixels[i * m_mapHeight + j] =
                //  Color.Lerp(Color.green, Color.HSVToRGB(63 / 255f, 45 / 255f, 41 / 255f), map[i, j]);
                /* A remplacer pour le shader:*/
                pixels[i * m_mapHeight + j] = Color.green;
            }
        }
        m_points = new List <Vector2>();
        List <uint> colors = new List <uint>();

        /* Randomly pick vertices */
        for (int i = 0; i < m_pointCount; i++)
        {
            colors.Add((uint)0);
            Vector2 vec = findpoint(map);
            m_points.Add(vec);
            realPoints.Add(vec);

            new List <Vector2>
            {
                new Vector2(vec.x - m_mapWidth, vec.y),
                new Vector2(vec.x + m_mapWidth, vec.y),
                new Vector2(vec.x - m_mapWidth, vec.y - m_mapHeight),
                new Vector2(vec.x + m_mapWidth, vec.y - m_mapHeight),
                new Vector2(vec.x, vec.y - m_mapHeight),
                new Vector2(vec.x, vec.y + m_mapHeight),
                new Vector2(vec.x + m_mapWidth, vec.y + m_mapHeight),
                new Vector2(vec.x - m_mapWidth, vec.y + m_mapHeight)
            }
            .ForEach(p =>
            {
                colors.Add(0);
                m_points.Add(p);
            });
        }
        /* Generate Graphs */
        Delaunay.Voronoi v = new Delaunay.Voronoi(m_points, colors,
                                                  new Rect(-m_mapWidth, -m_mapHeight, m_mapWidth * 2, m_mapHeight * 2));
        m_edges                 = v.VoronoiDiagram();
        m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
        m_delaunayTriangulation = v.DelaunayTriangulation();

        Dictionary <Vector2, List <LineSegment> > intersections = new Dictionary <Vector2, List <LineSegment> >();

        realPoints.ForEach(p =>
        {
            if (!intersections.ContainsKey(p))
            {
                intersections.Add(p, new List <LineSegment>());
            }
        });

        m_spanningTree.ForEach(e =>
                               new List <Vector2?> {
            e.p0, e.p1
        }
                               .Where(p => p != null)
                               .ToList()
                               .ForEach(p =>
        {
            List <LineSegment> result;
            if (intersections.TryGetValue((Vector2)p, out result))
            {
                if (!result.Contains(e))
                {
                    result.Add(e);
                }
            }
        }));

        intersections.Keys.ToList().ForEach(p =>
        {
            List <LineSegment> result;
            if (intersections.TryGetValue(p, out result))
            {
                if (result.Count == 1)
                {
                    _cities.Add(p, new City(p));
                    World.AddVillage(ToWorldPosition(p), false);
                }
                else if (result.Count > 3)
                {
                    _cities.Add(p, new City(p).SetSizeBetween(5, 10));
                    World.AddVillage(ToWorldPosition(p), true);
                }
            }
        });

        Color color = Color.blue;

        /* Shows Voronoi diagram */

        /*for (int i = 0; i < m_edges.Count; i++)
         * {
         *  LineSegment seg = m_edges[i];
         *  Vector2 left = (Vector2) seg.p0;
         *  Vector2 right = (Vector2) seg.p1;
         *  DrawLine(left, right, color);
         * }*/

        color = Color.red;

        /* Shows Delaunay triangulation */ /*
         *      if (m_delaunayTriangulation != null) {
         *              for (int i = 0; i < m_delaunayTriangulation.Count; i++) {
         *                              LineSegment seg = m_delaunayTriangulation [i];
         *                              Vector2 left = (Vector2)seg.p0;
         *                              Vector2 right = (Vector2)seg.p1;
         *                              DrawLine (left, right,color);
         *              }
         *      }*/

        /* Shows spanning tree */

        color = Color.red;
        if (m_spanningTree != null)
        {
            for (int i = 0; i < m_spanningTree.Count; i++)
            {
                LineSegment seg   = m_spanningTree[i];
                Vector2     left  = (Vector2)seg.p0;
                Vector2     right = (Vector2)seg.p1;
                DrawLine(left, right, color);
            }
        }

        _cities.Add(new Vector2(0, 0), new City(new Vector2(10, 10)));
        _cities.Keys.ToList().ForEach(k => DrawPoint(_cities[k].position, Color.blue));

        land.SetTexture("_SplatTex", tx);
        tx.SetPixels(pixels);
        tx.Apply();
    }
예제 #17
0
    IEnumerator Create()
    {
        #region Create Random Size & Pos Rooms
        int counter = 0;
        int roomAmount = 25;
        int widthSum = 0;
        int heightSum = 0;
        while (counter < roomAmount) {
            Room room = CreateRandRoom ();
            room.name = counter.ToString ();
            rooms.Add (room);
            counter++;

            // sum width/height
            widthSum += room.Width;
            heightSum += room.Height;

            yield return new WaitForSeconds (0.05f);
        }
        #endregion

        #region Remove Small Rooms
        float widthMean = widthSum / roomAmount;
        float heightMean = heightSum / roomAmount;

        yield return new WaitForSeconds (4);
        for (int i = 0; i < rooms.Count; i++) {
            //rooms[i].RemovePhysics();
            rooms [i].ResetRect ();

            if (rooms [i].Width < widthMean || rooms [i].Height < heightMean) {
                Destroy (rooms [i].gameObject);
                rooms.Remove (rooms [i]);
                i--;
            }
        }
        yield return new WaitForSeconds (0.5f);
        #endregion

        #region  Create room connection using DelaunayTriangles
        _points = new List<Vector2> ();
        for (int i = 0; i < rooms.Count; i++)
            _points.Add (rooms [i].Position);
        Rect rect = GetMinRect (rooms);

        Voronoi v = new Voronoi (_points, null, rect);
        _edges = v.VoronoiDiagram ();
        _spanningTree = v.SpanningTree (KruskalType.MINIMUM);
        _delaunayTriangulation = v.DelaunayTriangulation ();
        #endregion

        #region Extra Loop Connection
        int maxExtraPathAmt = (int)(_delaunayTriangulation.Count * 0.1f);
        int rand = Random.Range (1, maxExtraPathAmt);
        Debug.Log (rand);

        while (rand > 0) {
            int randIndex = Random.Range (0, _delaunayTriangulation.Count);

            if (_spanningTree.Contains (_delaunayTriangulation [randIndex]))
                continue;
            else {
                _spanningTree.Add (_delaunayTriangulation [randIndex]);
                rand--;
            }
        }
        yield return new WaitForSeconds (0.5f);
        #endregion

        #region Create HallWays
        for (int i = 0; i < _spanningTree.Count; i++) {
            yield return new WaitForSeconds (0.2f);
            Room room0 = GetRoomFromPos (_spanningTree [i].p0);
            Room room1 = GetRoomFromPos (_spanningTree [i].p1);

            Debug.Log ("Creating Hallway Between " + room0.name + "  " + room1.name);

            float xDistance = Mathf.Abs (room0.Position.x - room1.Position.x);
            float yDistance = Mathf.Abs (room0.Position.y - room1.Position.y);

            float xMidPointDistance = xDistance / 2;
            float yMidPointDistance = yDistance / 2;

            #region Close in X-Axis
            // mid x point is inside of both rects
            if (room0.Position.x + xMidPointDistance < room0.rectMaxX// removed equal sign ==> 避免房间刚好快要重叠,防止做路径时麻烦,因为路径瓦片可能会刚好在网格线上
                         && room1.Position.x + xMidPointDistance < room1.rectMaxX) {
                Vector2 startPoint = Vector2.zero;
                Vector2 endPoint = Vector2.zero;

                // room0 above room1
                if (room0.Position.y >= room1.Position.y) {
                    // room0 left to room1
                    if (room0.Position.x <= room1.Position.x) {
                        startPoint.Set (room0.Position.x + xMidPointDistance, room0.rectMinY);
                        endPoint.Set (room1.Position.x - xMidPointDistance, room1.rectMaxY);
                    }
                    // room1 left to room0
                    else if (room0.Position.x > room1.Position.x) {
                        startPoint.Set (room0.Position.x - xMidPointDistance, room0.rectMinY);
                        endPoint.Set (room1.Position.x + xMidPointDistance, room1.rectMaxY);
                    }
                }

                // room1 above room0
                else if (room0.Position.y < room1.Position.y) {
                    // room0 left to room1
                    if (room0.Position.x <= room1.Position.x) {
                        startPoint.Set (room0.Position.x + xMidPointDistance, room0.rectMaxY);
                        endPoint.Set (room1.Position.x - xMidPointDistance, room1.rectMinY);
                    }
                    // room1 left to room0
                    else if (room0.Position.x > room1.Position.x) {
                        startPoint.Set (room0.Position.x - xMidPointDistance, room0.rectMaxY);
                        endPoint.Set (room1.Position.x + xMidPointDistance, room1.rectMinY);
                    }
                }

                #endregion

                // create vertical line
                HallWay hallway = new HallWay (startPoint, endPoint, room0, room1);
                _hallways.Add (hallway);
                room0.AddHallWay (hallway);
                Debug.Log ("##CloseXAxis created hallway from " + startPoint + " to " + endPoint + " between " + room0.name + "  " + room1.name);
            }

            #region Close In Y-Axis
            // mid y point is inside of both rects
            else if (room0.Position.y + yMidPointDistance < room0.rectMaxY
                              && room1.Position.y + yMidPointDistance < room1.rectMaxY) {
                Vector2 startPoint = Vector2.zero;
                Vector2 endPoint = Vector2.zero;

                // room0 above room1
                if (room0.Position.y >= room1.Position.y) {
                    // room0 left to room1
                    if (room0.Position.x <= room1.Position.x) {
                        startPoint.Set (room0.rectMaxX, room0.Position.y - yMidPointDistance);
                        endPoint.Set (room1.rectMinX, room1.Position.y + yMidPointDistance);
                    }
                    // room1 left to room0
                    else if (room0.Position.x > room1.Position.x) {
                        startPoint.Set (room0.rectMinX, room0.Position.y - yMidPointDistance);
                        endPoint.Set (room1.rectMaxX, room1.Position.y + yMidPointDistance);
                    }
                }

                // room1 above room0
                else if (room0.Position.y < room1.Position.y) {
                    // room0 left to room1
                    if (room0.Position.x <= room1.Position.x) {
                        startPoint.Set (room0.rectMaxX, room0.Position.y + yMidPointDistance);
                        endPoint.Set (room1.rectMinX, room1.Position.y - yMidPointDistance);
                    }
                    // room1 left to room0
                else if (room0.Position.x > room1.Position.x) {
                        startPoint.Set (room0.rectMinX, room0.Position.y + yMidPointDistance);
                        endPoint.Set (room1.rectMaxX, room1.Position.y - yMidPointDistance);
                    }
                }

                // create vertical line
                HallWay hallway = new HallWay (startPoint, endPoint, room0, room1);
                _hallways.Add (hallway);
                room0.AddHallWay (hallway);

                Debug.Log ("##CloseYAxis created hallway from " + startPoint + " to " + endPoint + " between " + room0.name + "  " + room1.name);
            }
            #endregion

            #region Far In Both Axis
            // create L shape hall way
            else {
                Vector2 startPoint = Vector2.zero;
                Vector2 turnPoint = Vector2.zero;
                Vector2 endPoint = Vector2.zero;

                // room0 above room1
                if (room0.Position.y >= room1.Position.y) {
                    // room0 left to room1
                    if (room0.Position.x <= room1.Position.x) {
                        startPoint.Set (room0.rectMaxX, room0.Position.y);
                        turnPoint.Set (room0.Position.x + xDistance, room0.Position.y);
                        endPoint.Set (room1.Position.x, room1.rectMaxY);

                        #region Check If Line Collider With Other Room
                        if (LineHasCollision (startPoint, turnPoint, room0.Collider)
                                              ||
                                              LineHasCollision (turnPoint, endPoint, room1.Collider)) {
                            // go other way
                            startPoint.Set (room0.Position.x, room0.rectMinY);
                            turnPoint.Set (room0.Position.x, room0.Position.y - yDistance);
                            endPoint.Set (room1.rectMinX, room1.Position.y);
                            Debug.Log ("go other way");
                        }

                        // still has collision, delete this segment from spanning tree
                        if (LineHasCollision (startPoint, turnPoint, room0.Collider)
                                              ||
                                              LineHasCollision (turnPoint, endPoint, room1.Collider)) {
                            Debug.Log ("still collision, remove path");

                            _spanningTree.RemoveAt (i);
                            i--;
                            continue;
                        }
                        #endregion
                    }

                    // room1 left to room0
                    else if (room0.Position.x > room1.Position.x) {
                        startPoint.Set (room0.rectMinX, room0.Position.y);
                        turnPoint.Set (room0.Position.x - xDistance, room0.Position.y);
                        endPoint.Set (room1.Position.x, room1.rectMaxY);

                        #region Check If Line Collider With Other Room
                        if (LineHasCollision (startPoint, turnPoint, room0.Collider)
                                              ||
                                              LineHasCollision (turnPoint, endPoint, room1.Collider)) {
                            // go other way
                            startPoint.Set (room0.Position.x, room0.rectMinY);
                            turnPoint.Set (room0.Position.x, room0.Position.y - yDistance);
                            endPoint.Set (room1.rectMaxX, room1.Position.y);

                            Debug.Log ("go other way");
                        }

                        // still has collision, delete this segment from spanning tree
                        if (LineHasCollision (startPoint, turnPoint, room0.Collider)
                                              ||
                                              LineHasCollision (turnPoint, endPoint, room1.Collider)) {
                            Debug.Log ("still collison, delete path");

                            _spanningTree.RemoveAt (i);
                            i--;
                            continue;
                        }
                        #endregion
                    }
                }

                // room1 above room0
                else if (room0.Position.y < room1.Position.y) {
                    // room0 left to room1
                    if (room0.Position.x <= room1.Position.x) {
                        startPoint.Set (room0.Position.x, room0.rectMaxY);
                        turnPoint.Set (room0.Position.x, room0.Position.y + yDistance);
                        endPoint.Set (room1.rectMinX, room1.Position.y);

                        #region Check If Line Collider With Other Room
                        if (LineHasCollision (startPoint, turnPoint, room0.Collider)
                                              ||
                                              LineHasCollision (turnPoint, endPoint, room1.Collider)) {
                            // go other way
                            startPoint.Set (room0.rectMaxX, room0.Position.y);
                            turnPoint.Set (room0.Position.x + xDistance, room0.Position.y);
                            endPoint.Set (room1.Position.x, room1.rectMinY);

                            Debug.Log ("go other way");
                        }

                        // still has collision, delete this segment from spanning tree
                        if (LineHasCollision (startPoint, turnPoint, room0.Collider)
                                              ||
                                              LineHasCollision (turnPoint, endPoint, room1.Collider)) {
                            Debug.Log ("still collision, delete path");
                            _spanningTree.RemoveAt (i);
                            i--;
                            continue;
                        }
                        #endregion
                    }
                    // room1 left to room0
                    else if (room0.Position.x > room1.Position.x) {
                        startPoint.Set (room1.rectMaxX, room1.Position.y);
                        turnPoint.Set (room1.Position.x + xDistance, room1.Position.y);
                        endPoint.Set (room0.Position.x, room0.rectMaxY);

                        #region Check If Line Collider With Other Room
                        if (LineHasCollision (startPoint, turnPoint, room1.Collider)
                            ||
                            LineHasCollision (turnPoint, endPoint, room0.Collider)) {
                            // go other way
                            startPoint.Set (room1.Position.x, room1.rectMinY);
                            turnPoint.Set (room1.Position.x, room1.Position.y - yDistance);
                            endPoint.Set (room0.rectMinX, room0.Position.y);

                            Debug.Log ("go other way");
                        }

                        // still has collision, delete this segment from spanning tree
                        if (LineHasCollision (startPoint, turnPoint, room1.Collider)
                            ||
                            LineHasCollision (turnPoint, endPoint, room0.Collider)) {
                            Debug.Log ("still collision, delete path");
                            _spanningTree.RemoveAt (i);
                            i--;
                            continue;
                        }
                        #endregion
                    }
                }

                // create vertical line
                LHallWay hallway = new LHallWay (startPoint, turnPoint, endPoint, room0, room1);
                _hallways.Add (hallway);
                room0.AddHallWay (hallway);

                Debug.Log ("##Lshape created hallway from " + startPoint + " to " + turnPoint + " to " + endPoint + " between " + room0.name + "  " + room1.name);
            }
            #endregion
        }

        #endregion

        #region Remove Physics
        for (int i = 0; i < rooms.Count; i++)
            rooms [i].RemovePhysics ();
        #endregion

        #region Create Tiles
        for (int i = 0; i < rooms.Count; i++) {
            rooms [i].Fill ();
            yield return new WaitForSeconds (0.2f);
        }
        //for (int i = 0; i < _hallways.Count; i++) {
        //	_hallways [i].Fill ();
        //	yield return new WaitForSeconds (0.2f);
        //}
        #endregion
    }
예제 #18
0
    // Start is called before the first frame update
    void Start()
    {
        float [,] map = createMap();
        Color[] pixels = createPixelMap(map);

        /* Create random points points */
        m_points = new List <Vector2> ();
        List <uint> colors = new List <uint> ();

        for (int i = 0; i < NPOINTS; i++)
        {
            int iter = 0;
            colors.Add((uint)0);
            Vector2 vec;
            do
            {
                vec = new Vector2(Random.Range(0, WIDTH - 1), Random.Range(0, HEIGHT - 1));
            } while (map[(int)vec.x, (int)vec.y] < 0.73 && iter++ < 40);

            m_points.Add(vec);
        }

        /* Generate Graphs */
        Delaunay.Voronoi v = new Delaunay.Voronoi(m_points, colors, new Rect(0, 0, WIDTH, HEIGHT));
        m_edges        = v.VoronoiDiagram();
        m_spanningTree = v.SpanningTree(KruskalType.MINIMUM);
        //m_delaunayTriangulation = v.DelaunayTriangulation();

        Vector2 randomOne = new Vector2(0, 0);
        Vector3 rndDir    = new Vector3(0, 0, 0);
        Vector2 randomL   = new Vector2(0, 0);

        //DrawRiver(pixels, map);

        /* Shows Voronoi diagram */
        Color color = Color.blue;

        for (int i = 0; i < m_edges.Count; i++)
        {
            LineSegment seg = m_edges[i];

            Vector2 left  = (Vector2)seg.p0;
            Vector2 right = (Vector2)seg.p1;

            Vector2 mid    = (left + right) / 2;
            float   length = Vector3.Distance(left, right);

            Vector3 l   = new Vector3(left.x * (-10) + 1000, 1, left.y * (-10) + 1000);
            Vector3 r   = new Vector3(right.x * (-10) + 1000, 1, right.y * (-10) + 1000);
            Vector3 dir = l - r;

            GameObject prefab;
            GameObject habitation;

            if (map[(int)mid.x, (int)mid.y] < 0.7)
            {
                prefab     = prefab_highway;
                habitation = prefab_house;
            }
            else
            {
                prefab     = prefab_road;
                habitation = prefab_building;
                randomOne  = mid;
                rndDir     = dir;
                randomL    = l;
            }

            if (works <= population)
            {
                // Pas assez de travail, on met des bureaux
                GameObject obj = Instantiate(prefab_office, new Vector3((mid.x) * (-10) + 1000, 0.9f, mid.y * (-10) + 1000), Quaternion.LookRotation(dir));
                works += obj.GetComponent <Office>().nbWorkers;
                offices.Add(obj);
            }
            else
            {
                // On met des habitations
                GameObject obj = Instantiate(habitation, new Vector3((mid.x) * (-10) + 1000, 0.9f, mid.y * (-10) + 1000), Quaternion.LookRotation(dir));
                habitations.Add(obj);

                population += obj.GetComponent <Home>().nInhabitants;
                houses.Add(obj);
            }
            prefab.transform.localScale = new Vector3(1, 1, length);
            Instantiate(prefab, new Vector3(mid.x * (-10) + 1000, 1, mid.y * (-10) + 1000), Quaternion.LookRotation(dir));
            Instantiate(prefab_pedestrian_cross, l, Quaternion.LookRotation(dir));
            Instantiate(prefab_pedestrian_cross, r, Quaternion.LookRotation(dir));
        }

        roadSurface.BuildNavMesh();
        walkwaySurface.BuildNavMesh();

        // Instantiate a car
        //Instantiate(prefab_car, new Vector3(randomOne.x*(-10)+1000, 1, randomOne.y*(-10)+1000), Quaternion.LookRotation(rndDir));

        //Vector2 p = new Vector2(-10, -10);
        Vector2 p             = new Vector2(1000, 1000);
        Vector2 a             = (randomOne * (-10.0f) + p) - (randomL * (-10) + p).normalized * 0.3f;
        Vector2 perpendicular = (new Vector2(a.y, -a.x)).normalized;

        //Instantiate(prefab_walker, new Vector3(randomOne.x*(-10)+1000, 1, randomOne.y*(-10)+1000), Quaternion.LookRotation(rndDir));

        //mainCam.transform.position = new Vector3(randomOne.x * (-10) + 1000, 50, randomOne.y * (-10) + 1000);
        //mainCam.transform.LookAt(new Vector3(randomOne.x*(-10)+1000, 1, randomOne.y*(-10)+1000));

        /* Apply pixels to texture */
        tx = new Texture2D(WIDTH, HEIGHT);
        land.SetTexture("_MainTex", tx);
        tx.SetPixels(pixels);
        tx.Apply();
    }
예제 #19
0
    void Awake()
    {
        ListImmeubles = new List <GameObject>();
        ListHouses    = new List <GameObject>();

        PLANE_CELL_NB = 10 * PLANE_SIZE;
        map           = createMap();
        Color[] pixels = createPixelMap(map);

        /* Create random points points */

        m_points = new List <Vector2> ();
        List <uint> colors = new List <uint> ();

        for (int i = 0; i < NPOINTS; i++)
        {
            colors.Add((uint)0);

            int x_coord = Random.Range(0, WIDTH_VORONOI - 1);
            int y_coord = Random.Range(0, HEIGHT_VORONOI - 1);
            int nb_try  = 0;
            while (map[x_coord, y_coord] < 0.7 && nb_try < 50)
            {
                x_coord = Random.Range(0, WIDTH_VORONOI - 1);
                y_coord = Random.Range(0, HEIGHT_VORONOI - 1);
                nb_try++;
            }
            Vector2 vec = new Vector2(x_coord, y_coord);
            m_points.Add(vec);
        }


        /* Generate immeubles where points are */
        foreach (Vector2 point in m_points)
        {
            GameObject immeuble_go = Instantiate(immeuble, new Vector3(
                                                     (point.x / WIDTH_VORONOI - 0.5f) * PLANE_CELL_NB + immeuble.transform.position.x,
                                                     immeuble.transform.position.y,
                                                     (point.y / HEIGHT_VORONOI - 0.5f) * PLANE_CELL_NB + immeuble.transform.position.z
                                                     ),
                                                 immeuble.transform.rotation);
            ListImmeubles.Add(immeuble_go);
        }

        /* Generate Graphs */
        Delaunay.Voronoi v = new Delaunay.Voronoi(m_points, colors, new Rect(0, 0, WIDTH_VORONOI, HEIGHT_VORONOI));
        m_edges                 = v.VoronoiDiagram();
        m_spanningTree          = v.SpanningTree(KruskalType.MINIMUM);
        m_delaunayTriangulation = v.DelaunayTriangulation();

        Debug.Log("Centroides " + m_points.Count + " Edges " + m_edges.Count);

        /* Shows Voronoi diagram */
        Color color = Color.blue;
        float left_real_x;
        float left_real_y;
        float right_real_x;
        float right_real_y;

        for (int i = 0; i < m_edges.Count; i++)
        {
            LineSegment seg   = m_edges [i];
            Vector2     left  = (Vector2)seg.p0;
            Vector2     right = (Vector2)seg.p1;

            left_real_x  = (left.x / HEIGHT_VORONOI - 0.5F) * PLANE_CELL_NB;
            left_real_y  = (left.y / WIDTH_VORONOI - 0.5F) * PLANE_CELL_NB;
            right_real_x = (right.x / HEIGHT_VORONOI - 0.5F) * PLANE_CELL_NB;
            right_real_y = (right.y / WIDTH_VORONOI - 0.5F) * PLANE_CELL_NB;
            Vector2 segment = (right - left) / WIDTH_VORONOI * PLANE_SIZE;
            Debug.Log("Magnitude segment : " + segment.magnitude);
            float angle = Vector2.SignedAngle(Vector2.right, right - left);



            if (segment.magnitude > 1.5f)          //Spawn houses around road if and only if road is long enough
            {
                for (float j = 1; j < NBHOUSE_ROAD; j++)
                {
                    //Debug.Log("x" + left_real_y + "z" + left_real_x);
                    //Debug.Log("End x" + right_real_y + "End z" + right_real_x);
                    //Debug.Log("house pos " + left_real_y + (j / NBHOUSE_ROAD) * right_real_y);

                    /*
                     *      (1 - (j / NBHOUSE_ROAD)) * left_real_y + (j / NBHOUSE_ROAD) * ((right - left).y / HEIGHT_VORONOI - 0.5F) * PLANE_CELL_NB,
                     *      immeuble.transform.position.y,
                     *      (1 - (j / NBHOUSE_ROAD)) * left_real_x + (j / NBHOUSE_ROAD) * ((right - left).x / HEIGHT_VORONOI - 0.5F) * PLANE_CELL_NB
                     */

                    GameObject mush_house = Instantiate(house, new Vector3(
                                                            left_real_y + (j / NBHOUSE_ROAD) * (right_real_y - left_real_y) + house.transform.position.x,
                                                            house.transform.position.y,
                                                            left_real_x + (j / NBHOUSE_ROAD) * (right_real_x - left_real_x) + house.transform.position.z
                                                            ),
                                                        house.transform.rotation);

                    ListHouses.Add(mush_house);

                    // Add house light to light controller
                    LightController.house_light.Add(mush_house.GetComponentInChildren <Light>());
                }
            }

            GameObject go = Instantiate(road, new Vector3(left_real_y, 0, left_real_x), Quaternion.Euler(new Vector3(0, angle + 90, 0)));         //plane 10x10 starts at -5
            go.transform.localScale = new Vector3(segment.magnitude, 1, 1);
            go.transform.parent     = environment.transform;


            DrawLine(pixels, left, right, color);
        }

        //List<Vector2> sitecoords = v.SiteCoords();
        for (int i = 0; i < m_points.Count; i++)         //m_points
        {
            //Vector2 pos = (sitecoords[i]/WIDTH_VORONOI*10-new Vector2(5,5))* PLANE_SIZE;
            //Instantiate(immeuble, new Vector3(pos.x, 0.1f,pos.y), Quaternion.identity);

            //GameObject go = Instantiate(immeuble, new Vector3((m_points[i].y / WIDTH_VORONOI - 0.5F)*PLANE_CELL_NB, immeuble.transform.position.y, (m_points[i].x / HEIGHT_VORONOI -0.5F)*PLANE_CELL_NB), immeuble.transform.rotation);
        }



        /* Shows Delaunay triangulation */

        /*
         * color = Color.red;
         * if (m_delaunayTriangulation != null) {
         *      for (int i = 0; i < m_delaunayTriangulation.Count; i++) {
         *                      LineSegment seg = m_delaunayTriangulation [i];
         *                      Vector2 left = (Vector2)seg.p0;
         *                      Vector2 right = (Vector2)seg.p1;
         *                      DrawLine (pixels,left, right,color);
         *      }
         * }*/

        /* Shows spanning tree */

        /*
         * color = Color.black;
         * if (m_spanningTree != null) {
         *      for (int i = 0; i< m_spanningTree.Count; i++) {
         *              LineSegment seg = m_spanningTree [i];
         *              Vector2 left = (Vector2)seg.p0;
         *              Vector2 right = (Vector2)seg.p1;
         *              DrawLine (pixels,left, right,color);
         *      }
         * }*/

        /* Apply pixels to texture */
        tx = new Texture2D(WIDTH_VORONOI, HEIGHT_VORONOI);
        land.SetTexture("_MainTex", tx);
        tx.SetPixels(pixels);
        tx.Apply();          //texture envoyée vers la carte graphique pour devenir visible

        environment.GetComponent <NavMeshSurface>().BuildNavMesh();

        // Spawn agent with a house and an immeuble to work
        for (int i = 0; i < ListHouses.Count; i++)
        {
            GameObject mush_house = ListHouses[i];
            for (int k = 0; k < NB_AGENT_PER_HOUSE; k++)
            {
                GameObject agent_go = Instantiate(agent, new Vector3(
                                                      1 + Random.Range(0, 5f) + mush_house.transform.position.x,
                                                      0.08f,
                                                      1 + Random.Range(0, 5f) + mush_house.transform.position.z)
                                                  , mush_house.transform.rotation);
                agent_go.GetComponent <move>().home     = mush_house;
                agent_go.GetComponent <move>().immeuble = ListImmeubles[Random.Range(0, ListImmeubles.Count - 1)];
                LightController.agents.Add(agent_go);
            }
        }
        LightController.nb_agent_total = LightController.agents.Count;
    }