Пример #1
0
        internal void GenerateIslands()
        {
            Noise      islandsNoise    = _instance.islandsNoise;
            GridRandom buildingsRandom = _instance.buildingsRandom;

            TileTierStruct[]    tiers     = _instance.floorBlocksTiers;
            BuildingGenStruct[] buildings = _instance.buildingsGeneration;
            for (int loopX = 0; loopX < CHUNK_SIZE; loopX++)
            {
                for (int loopY = 0; loopY < CHUNK_SIZE; loopY++)
                {
                    Vector2Int gridPosition = new Vector2Int(loopX, loopY) + chunkStartPos;
                    float      distance     = Vector2Int.Distance(gridPosition, Vector2Int.zero);
                    if (distance > _instance.clearZoneRadius)
                    {
                        if (islandsNoise.CheckThreshold(gridPosition, out float noiseValue))
                        {
                            TileAbstSO tile = tiers[tiers.Length - 1].tile;
                            for (int i = 0; i < tiers.Length; i++)
                            {
                                if (distance <= tiers[i].distance)
                                {
                                    float overlap = (distance - tiers[i].overlapStart) / (tiers[i].distance - tiers[i].overlapStart);
                                    if (distance > tiers[i].overlapStart && easeInOutBounce(overlap) > islandsNoise.GetRandomValue(gridPosition))
                                    {
                                        tile = tiers[i].tile;
                                    }
                                    else
                                    {
                                        tile = tiers[i - 1].tile;
                                    }
                                    break;
                                }
                            }
                            SetTile(new TileSlot(tile), ChunkToGridPosition(new Vector2Int(loopX, loopY)), TileMapLayer.Floor, false, true);
                            TileAbstSO building = ChooseBuilding(gridPosition, distance);
                            if (building != null)
                            {
                                SetTile(new TileSlot(building), gridPosition, TileMapLayer.Buildings, false, true);
                            }
                        }
                    }
                    else if (distance <= _instance.startIslandRadius)
                    {
                        SetTile(new TileSlot(_instance.startIslandTile), ChunkToGridPosition(new Vector2Int(loopX, loopY)), TileMapLayer.Floor, false, true);
                    }
                }
            }
            TileAbstSO ChooseBuilding(Vector2Int gridPosition, float distance)
            {
                float sumWeight = 0f;

                float[] chances = new float[buildings.Length];
                for (int i = 0; i < buildings.Length; i++)
                {
                    if (buildings[i].global)
                    {
                        chances[i] = buildings[i].chance;
                    }
                    else
                    {
                        chances[i] = easeInOutSine(1 - Mathf.Clamp(Mathf.Abs(buildings[i].distance - distance) / buildings[i].spread, 0f, 1f)) * buildings[i].chance;
                    }
                    sumWeight += chances[i];
                }
                if (sumWeight > 1)
                {
                    for (int i = 0; i < chances.Length; i++)
                    {
                        chances[i] /= sumWeight;
                    }
                }
                float roll = buildingsRandom.GetRandomValue(gridPosition);

                for (int i = 0; i < chances.Length; i++)
                {
                    roll -= chances[i];
                    if (roll <= 0f)
                    {
                        return(buildings[i].tile);
                    }
                }
                return(null);
            }
        }