/// <summary> /// Scans segment's occupancy matrix and fills the areas list according to placer values. /// </summary> private void MapAreas() { PlacerSpot spot = new PlacerSpot(); //be gentle with the stack, allocate only once for (int i = 0; i <= TrackSegment.WIDTH - size; i++) { for (int j = 0; j <= TrackSegment.LENGTH - size; j++) { spot.x = i; spot.y = j; float fill = PlacerArea.GetSpotRatio(PlacerSpot.Type.Empty, spots, spot, size); if (!allowIntertwined && !Mathf.Approximately(fill, 1f)) { continue; } if (fill >= targetFillRatio) { areas.Add(new PlacerArea(spots, spot, size)); } } } }
/// <summary> /// Check to see if it intersects another area. /// </summary> /// <param name="area">Other area.</param> /// <returns>True, if areas intersect, else false</returns> public bool Overlaps(PlacerArea area) { return(pivot.x >= area.pivot.x - (size - 1) && pivot.x <= area.pivot.x + area.size - 1 && pivot.y >= area.pivot.y - (size - 1) && pivot.y <= area.pivot.y + area.size - 1); }
public override void Place(TrackSegment segment, int[,] spots) { base.Place(segment, spots); MapAreas(); //build list if (areas.Count == 0) //nothing to do, exit { return; } //determine actual possible pathes count - not all may fit int count = (areas.Count < targetCount)? areas.Count : targetCount; //place patches towards the target count for (int i = 0; i < count && areas.Count > 0; i++) { //choose area PlacerArea area = areas[Random.Range(0, areas.Count)]; //builds free spots list area.GetSpots(PlacerSpot.Type.Empty, free); //choose from free spots and place assets for (int j = 0; j < assetsPerPatch; j++) { int index = Random.Range(0, free.Count); PlacerSpot spot = free[index]; Mark(spot); AddAsset(spot); free.RemoveAt(index); } //prepare for next patch free.Clear(); areas.RemoveAll(item => area.Overlaps(item) && (!allowIntertwined || allowIntertwined && item.GetSpotRatio(PlacerSpot.Type.Empty) < targetFillRatio)); } //cleanup areas.Clear(); }