// ================================== Setters private static List <Vector2> SavedCoordinates(MapModel model, bool getNew = false) { List <Vector2> tileCoordinates; if (getNew) { tileCoordinates = PossionDiscSampling.CreateRandomList(model.bounds, model.minDistanceTiles); int length = tileCoordinates.Count; PlayerPrefs.SetInt("length", length); for (int index = 0; index < length; index++) { PlayerPrefs.SetFloat(index + "x", tileCoordinates[index].x); PlayerPrefs.SetFloat(index + "y", tileCoordinates[index].y); } } else { tileCoordinates = new List <Vector2>(); int length = PlayerPrefs.GetInt("length"); for (int index = 0; index < length; index++) { float x = PlayerPrefs.GetFloat(index + "x"); float y = PlayerPrefs.GetFloat(index + "y"); tileCoordinates.Add(new Vector2(x, y)); } } return(tileCoordinates); }
// uses http://www.cs.ubc.ca/~rbridson/docs/bridson-siggraph07-poissondisk.pdf & https://www.youtube.com/watch?v=7WcmyxyFO7o public static List <Vector2> CreateRandomList(Rect bounds, float minDistance, int amount = int.MaxValue, int k = 30) { float cellSize = minDistance / (float)Math.Sqrt(2); int width = Mathf.CeilToInt(bounds.width / cellSize); int height = Mathf.CeilToInt(bounds.height / cellSize); int[,] map = new int[width, height]; List <Vector2> outputList = new List <Vector2>(); List <Vector2> activeList = new List <Vector2>(); activeList.Add(PossionDiscSampling.CreateRandom(bounds)); while (outputList.Count < amount) { if (activeList.Count == 0) { if (amount == int.MaxValue) { break; } else { throw new Exception("Active list got too small too soon! Choose a smaller min distance!"); } } bool candidateAccepted = false; int index = UnityEngine.Random.Range(0, activeList.Count); Vector2 center = activeList[index]; for (int i = 0; i < k; i++) { float angle = UnityEngine.Random.value * Mathf.PI * 2; Vector2 dir = new Vector2(Mathf.Sin(angle), Mathf.Cos(angle)); Vector2 candidate = center + dir * UnityEngine.Random.Range(minDistance, 2 * minDistance); if (bounds.Contains(candidate)) { if (IsValid(candidate, outputList, cellSize, minDistance, map)) { candidateAccepted = true; outputList.Add(candidate); activeList.Add(candidate); map[(int)(candidate.x / cellSize), (int)(candidate.y / cellSize)] = outputList.Count; break; } } } if (!candidateAccepted) { activeList.RemoveAt(index); } } return(outputList); }
private void StartFortunesAlgorithm(MapModel model) { List <Vector2> tileCoordinates = PossionDiscSampling.CreateRandomList(model.bounds, model.minDistanceTiles); FortunesAlgorithm algorithm = new FortunesAlgorithm(tileCoordinates); algorithm.RemoveShortBoundaries(model.minBoundaryLength); algorithm.MakeBoundariesWiggely(); algorithm.CutCorners(model.bounds); (model.borderInits, model.tileInits) = algorithm.GetBordersAndTiles(); }