//distance field public void generateDistanceField(MCell cell0) { foreach (MCell c in cells) { c.cost = -1.0; // set all cells to -1 } List <MCell> front = new List <MCell>(); front.Add(cell0); // add first cell to front cell list cell0.cost = 0.0; // set its cost to 0.0 for (int i = 0; i < 100000; ++i) { if (front.Count == 0) { break; // if there are no cells in front break } MCell c = front[front.Count - 1]; // set current cell to first cell of front front.RemoveAt(front.Count - 1); // remove the cell for (int j = 0; j < c.others.Length; ++j) { if (!c.isOpen(j)) { continue; // if cell is not open in direction of j continue } MCell nc = c.others[j]; // new cell double transitionCost = (c.p - nc.p).magnitude; // calculate transition cost which is the distance between the two cell points double newOtherCost = c.cost + transitionCost; // cost is equal to current cell cost and transition cost if (nc.cost < 0.0 || newOtherCost < nc.cost) { nc.cost = newOtherCost; front.Add(nc); // add new cell to front } } } }
// Use this for initialization void Start() { lines = GetComponent <LineRenderer>(); maze = new Maze(); // instantiate new maze object maze.create(resolutionX, resolutionY, protos, protoBlock); // create it System.Random rnd = new System.Random(); MCell firstCell = maze.cells[rnd.Next() % maze.resx, rnd.Next() % maze.resy]; // pick the starting cell maze.generateDistanceField(firstCell); // generate solution path from the first cell to the one with the highest cost MCell currentCell = firstCell; MCell maxC = firstCell; foreach (MCell c in maze.cells) { if (c.cost > maxC.cost) { maxC = c; // if the cell cost is greater than the max cost, update max cost to cell cost } } double maxcost = maxC.cost; foreach (MCell c in maze.cells) { if (c.cost < 0.0) { c.setFloorColor(mooTwo); // if the cell is not accessible set it to a custom color } else { float ncost = (float)(c.cost / maxcost); c.setFloorColor(new Color(ncost, ncost, ncost, 1.0f)); // otherwise, set a gradient of grey } } MCell targetMoo = maxC; List <MCell> path = new List <MCell>(); for (int s = 0; s < 200; ++s) { path.Add(targetMoo); if (targetMoo == firstCell) { break; // if the first and last cell are the same then break } MCell nextCell = new MCell(); for (int b = 0; b < 4; ++b) { if (targetMoo.isOpen(b) && targetMoo.others[b].cost == targetMoo.cost - 1.0 ) // if the last cell is open in the direction of the neighboring cell and the cost of the neighboring cell is 1 less, then make it the next cell { nextCell = targetMoo.others[b]; } } if (nextCell.others.Length > 0.0) { for (int d = 0; d < nextCell.others.Length; ++d) { if (nextCell.isOpen(d) && nextCell.others[d].cost == targetMoo.cost - 2.0 ) // if the neighbors of the next cell have a cost of two less than the target cell, make it the next cell { targetMoo = nextCell; } else if (nextCell.cost == 0.0) { targetMoo = firstCell; // end of solution path } } } } lines.positionCount = path.Count; // draw the path for (int i = 0; i < path.Count; ++i) { Vector3 lp = path[i].p; lp.y += 1.0f; lines.SetPosition(i, lp); Material lineMaterial = new Material(Shader.Find("Sprites/Default")); lines.material = lineMaterial; } }