From 553389ce6e83883bfe77f9e6ab19d91ec628b5ae Mon Sep 17 00:00:00 2001 From: Oarcinae Date: Tue, 19 Nov 2024 23:16:52 -0500 Subject: [PATCH 1/2] Saving initial Gleba work. Have a dumb but simple method for placing plants and iron-copper things. Needs refining and testing. --- lib/config.lua | 19 +++++++---- lib/planet_configs/gleba.lua | 58 +++++++++++++++++++++++++++++++++ lib/planet_configs/nauvis.lua | 2 ++ lib/scaled_enemies.lua | 60 ++++++++++++++++++++++++++--------- lib/separate_spawns.lua | 37 +++++++++++++++------ lib/spawn_area_generation.lua | 51 ++++++++++++++++++++++++++++- 6 files changed, 196 insertions(+), 31 deletions(-) create mode 100644 lib/planet_configs/gleba.lua diff --git a/lib/config.lua b/lib/config.lua index 0964210..4b17534 100644 --- a/lib/config.lua +++ b/lib/config.lua @@ -18,6 +18,7 @@ require("lib/planet_configs/nauvis") require("lib/planet_configs/fulgora") require("lib/planet_configs/vulcanus") +require("lib/planet_configs/gleba") ---@alias SpawnShapeChoice "circle" | "octagon" | "square" SPAWN_SHAPE_CHOICE_CIRCLE = "circle" @@ -372,13 +373,13 @@ OCFG = { starting_items = FULGORA_STARTER_ITEMS, spawn_config = FULGORA_SPAWN_CONFIG }, - -- ["gleba"] = { - -- starting_items = NAUVIS_STARTER_ITEMS, - -- spawn_config = NAUVIS_SPAWN_CONFIG - -- }, + ["gleba"] = { + starting_items = GLEBA_STARTER_ITEMS, + spawn_config = GLEBA_SPAWN_CONFIG + }, -- ["aquilo"] = { - -- starting_items = NAUVIS_STARTER_ITEMS, - -- spawn_config = NAUVIS_SPAWN_CONFIG + -- starting_items = AQUILO_STARTER_ITEMS, + -- spawn_config = AQUILO_SPAWN_CONFIG -- } }, @@ -512,6 +513,7 @@ OCFG = { ---@field shared_chest_position OarcOffsetPosition Location of shared chest relative to spawn center (if enabled) ---@field solid_resources table Spawn area config for solid resource tiles ---@field fluid_resources table Spawn area config for fluid resource patches (like oil) +---@field growth_resources table Spawn area config for growth resources (like gleba trees) ---@class OarcConfigSpawnGeneral ---@field spawn_radius_tiles number THIS IS WHAT SETS THE SPAWN CIRCLE SIZE! Create a circle of land area for the spawn If you make this much bigger than a few chunks, good luck. @@ -561,6 +563,11 @@ OCFG = { ---@field x_offset_next integer ---@field y_offset_next integer +---@class OarcConfigGrowthResource +---@field tile string The tile to place +---@field entity string The entity (tree that grows on this specific tile) +---@field size integer + ---@class OarcStoreItem ---@field cost integer ---@field count integer diff --git a/lib/planet_configs/gleba.lua b/lib/planet_configs/gleba.lua new file mode 100644 index 0000000..0cd7b92 --- /dev/null +++ b/lib/planet_configs/gleba.lua @@ -0,0 +1,58 @@ +-- This config is used as the default config for the planet gleba. + +---@type OarcConfigStartingItems +GLEBA_STARTER_ITEMS = table.deepcopy(NO_STARTER_ITEMS) + +---@type OarcConfigSpawn +GLEBA_SPAWN_CONFIG = table.deepcopy(NAUVIS_SPAWN_CONFIG) +GLEBA_SPAWN_CONFIG.fill_tile = "highland-dark-rock-2" +GLEBA_SPAWN_CONFIG.liquid_tile = "gleba-deep-lake" +GLEBA_SPAWN_CONFIG.tree_entity = nil +GLEBA_SPAWN_CONFIG.random_entities = { + {name = "boompuff", count = 10}, + {name = "sunnycomb", count = 10}, + {name = "stingfrond", count = 10}, + {name = "funneltrunk", count = 10}, + {name = "teflilly", count = 10}, + {name = "slipstack", count = 10}, + {name = "cuttlepop", count = 10}, + {name = "water-cane", count = 10}, +} + +GLEBA_SPAWN_CONFIG.solid_resources = +{ + ["stone"] = { + amount = 1000, + size = 20, + + -- These are only used if not using automatic placing. + x_offset = -29, + y_offset = 16 + } +} + +GLEBA_SPAWN_CONFIG.growth_resources = +{ + ["yumako"] = { + tile = "natural-yumako-soil", + entity = "yumako-tree", + size = 20 + }, + ["jellystem"] = { + tile = "natural-jellynut-soil", + entity = "jellystem", + size = 20 + }, + ["iron"] = { + tile = "wetland-dead-skin", + entity = "iron-stromatolite", + size = 20 + }, + ["copper"] = { + tile = "wetland-dead-skin", + entity = "copper-stromatolite", + size = 20 + }, +} + +GLEBA_SPAWN_CONFIG.fluid_resources = { } \ No newline at end of file diff --git a/lib/planet_configs/nauvis.lua b/lib/planet_configs/nauvis.lua index 12effc4..9f18ed4 100644 --- a/lib/planet_configs/nauvis.lua +++ b/lib/planet_configs/nauvis.lua @@ -170,6 +170,8 @@ NAUVIS_SPAWN_CONFIG = y_offset_next = 0 } }, + + growth_resources = {} } ---@type OarcConfigSurface diff --git a/lib/scaled_enemies.lua b/lib/scaled_enemies.lua index c1db06a..5303f63 100644 --- a/lib/scaled_enemies.lua +++ b/lib/scaled_enemies.lua @@ -8,9 +8,14 @@ ENEMY_FORCES_NAMES = { "enemy" } ENEMY_FORCES_NAMES_INCL_NEUTRAL = { "enemy", "neutral" } -ENEMY_BUILT_TYPES = { "biter-spawner", "spitter-spawner", "small-worm-turret", "medium-worm-turret", "big-worm-turret", - "behemoth-worm-turret" } +-- gleba-spawner-small +-- gleba-spawner + +-- yumako-tree +-- copper-stromatolite +-- jellystem +-- yumako-tree ---Downgrades worms based on distance from origin and near/far spawn distances. ---This helps make sure worms aren't too overwhelming even at these further spawn distances. @@ -47,12 +52,15 @@ function DowngradeAndReduceEnemiesOnChunkGenerate(event) y = chunk_area.left_top.y + (CHUNK_SIZE / 2) } + + -- TODO: Change this lookup to be done once during surface init. local nauvis_enemies = surface.map_gen_settings.autoplace_controls["enemy-base"] ~= nil local gleba_enemies = surface.map_gen_settings.autoplace_controls["gleba_enemy_base"] ~= nil -- local vulcanus_enemies = surface.map_gen_settings.territory_settings ~= nil -- Make chunks near a spawn safe by removing enemies + -- TODO: Refactor this to reduce calls to find_entities_filtered maybe? if (util.distance(closest_spawn.position, chunkAreaCenter) < spawn_config.safe_area.safe_radius * CHUNK_SIZE) then if nauvis_enemies or gleba_enemies then RemoveEnemiesInArea(surface, chunk_area) @@ -60,17 +68,21 @@ function DowngradeAndReduceEnemiesOnChunkGenerate(event) -- Create a warning area with heavily reduced enemies elseif (util.distance(closest_spawn.position, chunkAreaCenter) < spawn_config.safe_area.warn_radius * CHUNK_SIZE) then - if nauvis_enemies then - -- TODO: Refactor this to reduce calls to find_entities_filtered! + if nauvis_enemies or gleba_enemies then ReduceEnemiesInArea(surface, chunk_area, spawn_config.safe_area.warn_reduction) + end + + if nauvis_enemies then RemoveWormsInArea(surface, chunk_area, false, true, true, true) -- remove all non-small worms. end -- Create a third area with moderately reduced enemies elseif (util.distance(closest_spawn.position, chunkAreaCenter) < spawn_config.safe_area.danger_radius * CHUNK_SIZE) then - if nauvis_enemies then - -- TODO: Refactor this to reduce calls to find_entities_filtered! + if nauvis_enemies or gleba_enemies then ReduceEnemiesInArea(surface, chunk_area, spawn_config.safe_area.danger_reduction) + end + + if nauvis_enemies then RemoveWormsInArea(surface, chunk_area, false, false, true, true) -- remove all huge/behemoth worms. end end @@ -203,36 +215,54 @@ function ModifyEnemySpawnsNearPlayerStartingAreas(event) -- Warn distance is all SMALL only. elseif (util.distance(enemy_pos, closest_spawn.position) < storage.ocfg.surfaces_config[surface.name].spawn_config.safe_area.warn_radius * CHUNK_SIZE) then - if ((enemy_name == "biter-spawner") or (enemy_name == "spitter-spawner")) then - -- Do nothing. - elseif ((enemy_name == "big-biter") or (enemy_name == "behemoth-biter") or (enemy_name == "medium-biter")) then + + -- Nauvis enemies + if ((enemy_name == "big-biter") or (enemy_name == "behemoth-biter") or (enemy_name == "medium-biter")) then event.entity.destroy() surface.create_entity { name = "small-biter", position = enemy_pos, force = game.forces.enemy } - -- log("Downgraded biter close to spawn.") elseif ((enemy_name == "big-spitter") or (enemy_name == "behemoth-spitter") or (enemy_name == "medium-spitter")) then event.entity.destroy() surface.create_entity { name = "small-spitter", position = enemy_pos, force = game.forces.enemy } - -- log("Downgraded spitter close to spawn.") elseif ((enemy_name == "big-worm-turret") or (enemy_name == "behemoth-worm-turret") or (enemy_name == "medium-worm-turret")) then event.entity.destroy() surface.create_entity { name = "small-worm-turret", position = enemy_pos, force = game.forces.enemy } - -- log("Downgraded worm close to spawn.") + + -- Gleba enemies + elseif ((enemy_name == "big-wriggler-pentapod") or (enemy_name == "medium-wriggler-pentapod")) then + event.entity.destroy() + surface.create_entity { name = "small-wriggler-pentapod", position = enemy_pos, force = game.forces.enemy } + elseif ((enemy_name == "big-stomper-pentapod") or (enemy_name == "medium-stomper-pentapod")) then + event.entity.destroy() + surface.create_entity { name = "small-stomper-pentapod", position = enemy_pos, force = game.forces.enemy } + elseif ((enemy_name == "big-strafer-pentapod") or (enemy_name == "medium-strafer-pentapod")) then + event.entity.destroy() + surface.create_entity { name = "small-strafer-pentapod", position = enemy_pos, force = game.forces.enemy } end -- Danger distance is MEDIUM max. elseif (util.distance(enemy_pos, closest_spawn.position) < storage.ocfg.surfaces_config[surface.name].spawn_config.safe_area.danger_radius * CHUNK_SIZE) then + + -- Nauvis enemies if ((enemy_name == "big-biter") or (enemy_name == "behemoth-biter")) then event.entity.destroy() surface.create_entity { name = "medium-biter", position = enemy_pos, force = game.forces.enemy } - -- log("Downgraded biter further from spawn.") elseif ((enemy_name == "big-spitter") or (enemy_name == "behemoth-spitter")) then event.entity.destroy() surface.create_entity { name = "medium-spitter", position = enemy_pos, force = game.forces.enemy } - -- log("Downgraded spitter further from spawn elseif ((enemy_name == "big-worm-turret") or (enemy_name == "behemoth-worm-turret")) then event.entity.destroy() surface.create_entity { name = "medium-worm-turret", position = enemy_pos, force = game.forces.enemy } - -- log("Downgraded worm further from spawn.") + + -- Gleba enemies + elseif (enemy_name == "big-wriggler-pentapod") then + event.entity.destroy() + surface.create_entity { name = "medium-wriggler-pentapod", position = enemy_pos, force = game.forces.enemy } + elseif (enemy_name == "big-stomper-pentapod") then + event.entity.destroy() + surface.create_entity { name = "medium-stomper-pentapod", position = enemy_pos, force = game.forces.enemy } + elseif (enemy_name == "big-strafer-pentapod") then + event.entity.destroy() + surface.create_entity { name = "medium-strafer-pentapod", position = enemy_pos, force = game.forces.enemy } end end end diff --git a/lib/separate_spawns.lua b/lib/separate_spawns.lua index 7e34d7f..0581cb7 100644 --- a/lib/separate_spawns.lua +++ b/lib/separate_spawns.lua @@ -372,7 +372,7 @@ end ---@param spawn_config OarcConfigSpawn ---@param surface LuaSurface ---@return nil -function GenerateStartingLiquedStrip(delayed_spawn, spawn_config, surface) +function GenerateStartingLiquidStrip(delayed_spawn, spawn_config, surface) local water_data = spawn_config.water -- Reference position is the top of the spawn area. @@ -398,6 +398,7 @@ end ---@return nil function GenerateStartingResources(surface, position) + --TODO: This should come from map gen settings instead: local size_mod = storage.ocfg.resource_placement.size_multiplier local amount_mod = storage.ocfg.resource_placement.amount_multiplier @@ -478,19 +479,26 @@ function PlaceResourcesInSemiCircle(surface, position, size_mod, amount_mod) -- Create list of resource tiles ---@type table local r_list = {} - for r_name, _ in pairs(storage.ocfg.surfaces_config[surface.name].spawn_config.solid_resources --[[@as table]]) do + for r_name, _ in pairs(storage.ocfg.surfaces_config[surface.name].spawn_config.solid_resources) do if (r_name ~= "") then table.insert(r_list, r_name) end end + + for g_name,_ in pairs(storage.ocfg.surfaces_config[surface.name].spawn_config.growth_resources) do + if (g_name ~= "") then + table.insert(r_list, g_name) + end + end + ---@type table local shuffled_list = FYShuffle(r_list) + local num_resources = table_size(shuffled_list) -- This places resources in a semi-circle local surface_config = storage.ocfg.surfaces_config[surface.name] local angle_offset_radians = math.rad(storage.ocfg.resource_placement.angle_offset) local angle_final_radians = math.rad(storage.ocfg.resource_placement.angle_final) - local num_resources = table_size(storage.ocfg.surfaces_config[surface.name].spawn_config.solid_resources) local radius = storage.ocfg.spawn_general.spawn_radius_tiles * surface_config.spawn_config.radius_modifier - storage.ocfg.resource_placement.distance_to_edge -- Special case for only one resource, place it in the middle of the semi-circle. @@ -504,7 +512,13 @@ function PlaceResourcesInSemiCircle(surface, position, size_mod, amount_mod) local pos = { x = math.floor(tx), y = math.floor(ty) } local resourceConfig = surface_config.spawn_config.solid_resources[r_name] - GenerateResourcePatch(surface, r_name, resourceConfig.size * size_mod, pos, resourceConfig.amount * amount_mod) + if (resourceConfig ~= nil) then + GenerateResourcePatch(surface, r_name, resourceConfig.size * size_mod, pos, resourceConfig.amount * amount_mod) + else + local gResourceConfig = surface_config.spawn_config.growth_resources[r_name] + GenerateGrowthResourcePatch(surface, gResourceConfig.tile, gResourceConfig.entity, gResourceConfig.size * size_mod, pos) + end + else local theta = ((angle_final_radians - angle_offset_radians) / (num_resources-1)); local count = 0 @@ -518,8 +532,13 @@ function PlaceResourcesInSemiCircle(surface, position, size_mod, amount_mod) local pos = { x = math.floor(tx), y = math.floor(ty) } - local resourceConfig = storage.ocfg.surfaces_config[surface.name].spawn_config.solid_resources[r_name] - GenerateResourcePatch(surface, r_name, resourceConfig.size * size_mod, pos, resourceConfig.amount * amount_mod) + local resourceConfig = surface_config.spawn_config.solid_resources[r_name] + if (resourceConfig ~= nil) then + GenerateResourcePatch(surface, r_name, resourceConfig.size * size_mod, pos, resourceConfig.amount * amount_mod) + else + local gResourceConfig = surface_config.spawn_config.growth_resources[r_name] + GenerateGrowthResourcePatch(surface, gResourceConfig.tile, gResourceConfig.entity, gResourceConfig.size * size_mod, pos) + end count = count + 1 end end @@ -580,7 +599,7 @@ function GenerateFinalSpawnPieces(delayed_spawn) -- Generate water strip only if we don't have a moat. if (not delayed_spawn.moat or spawn_config.liquid_tile == "lava") then - GenerateStartingLiquedStrip(delayed_spawn, spawn_config, surface) + GenerateStartingLiquidStrip(delayed_spawn, spawn_config, surface) end -- Create the spawn resources here @@ -754,9 +773,9 @@ function SetupAndClearSpawnAreas(surface, chunkArea) -- Remove trees/resources inside the spawn area if (general_spawn_config.shape == SPAWN_SHAPE_CHOICE_CIRCLE) or (general_spawn_config.shape == SPAWN_SHAPE_CHOICE_OCTAGON) then - RemoveInCircle(surface, chunkArea, {"resource", "cliff", "tree", "lightning-attractor", "simple-entity"}, spawn.position, radius + 5) + RemoveInCircle(surface, chunkArea, {"resource", "cliff", "tree", "plant", "lightning-attractor", "simple-entity"}, spawn.position, radius + 5) elseif (general_spawn_config.shape == SPAWN_SHAPE_CHOICE_SQUARE) then - RemoveInSquare(surface, chunkArea, {"resource", "cliff", "tree", "lightning-attractor", "simple-entity"}, spawn.position, radius + 5) + RemoveInSquare(surface, chunkArea, {"resource", "cliff", "tree", "plant", "lightning-attractor", "simple-entity"}, spawn.position, radius + 5) end if (general_spawn_config.shape == SPAWN_SHAPE_CHOICE_CIRCLE) then diff --git a/lib/spawn_area_generation.lua b/lib/spawn_area_generation.lua index 50d720c..e20efcd 100644 --- a/lib/spawn_area_generation.lua +++ b/lib/spawn_area_generation.lua @@ -277,6 +277,7 @@ end ---@param diameter integer ---@param position TilePosition ---@param amount integer +---@return nil function GenerateResourcePatch(surface, resourceName, diameter, position, amount) local midPoint = math.floor(diameter / 2) if (diameter == 0) then @@ -300,7 +301,55 @@ function GenerateResourcePatch(surface, resourceName, diameter, position, amount end end ---- Function to generate a resource patch, of a certain size/amount at a pos. +--- Function to generate a growth resource patch, of a certain size at a pos. +---@param surface LuaSurface +---@param tile_name string +---@param entity_name string +---@param diameter integer +---@param position TilePosition +---@return nil +function GenerateGrowthResourcePatch(surface, tile_name, entity_name, diameter, position) + local midPoint = math.floor(diameter / 2) + if (diameter == 0) then + return + end + + -- Right now only 2 shapes are supported. Circle and Square. + local square_shape = (storage.ocfg.spawn_general.resources_shape == RESOURCES_SHAPE_CHOICE_SQUARE) + + local tiles = {} + for y = -midPoint, midPoint do + for x = -midPoint, midPoint do + -- Either it's a square, or it's a circle so we check if it's inside the circle. + if (square_shape or ((x) ^ 2 + (y) ^ 2 < midPoint ^ 2)) then + table.insert(tiles, { name = tile_name, position = { position.x + x, position.y + y } }) + end + end + end + surface.set_tiles(tiles) + + for y = -midPoint, midPoint do + for x = -midPoint, midPoint do + -- Either it's a square, or it's a circle so we check if it's inside the circle. + if (square_shape or ((x) ^ 2 + (y) ^ 2 < midPoint ^ 2)) then + + -- Reduce chances to spawn to make it more sparse. + if (math.random(1, 20) == 1) then + local pos = surface.find_non_colliding_position(entity_name, { position.x + x, position.y + y }, 2, 0.5) + if (pos ~= nil) then + local entity = surface.create_entity({ name = entity_name, position = pos }) + if (entity.type == "plant") then + entity.tick_grown = game.tick + end + end + end + end + end + end +end + + +---Places random entities around the spawn area. ---@param surface LuaSurface ---@param position MapPosition ---@return nil From 661f36085a92aac07960bf5f624a1c7317e03efc Mon Sep 17 00:00:00 2001 From: Oarcinae Date: Wed, 20 Nov 2024 11:49:02 -0500 Subject: [PATCH 2/2] First pass Gleba secondary spawn seems to be okay. --- lib/config.lua | 9 ++++---- lib/planet_configs/gleba.lua | 38 +++++++++++++++++---------------- lib/planet_configs/nauvis.lua | 2 +- lib/scaled_enemies.lua | 24 ++++++++++++++++++++- lib/separate_spawns.lua | 10 ++++----- lib/spawn_area_generation.lua | 16 ++++++++------ migrations/oarc-mod-v2.1.13.lua | 14 ++++++++++++ 7 files changed, 78 insertions(+), 35 deletions(-) diff --git a/lib/config.lua b/lib/config.lua index 4b17534..5e4634b 100644 --- a/lib/config.lua +++ b/lib/config.lua @@ -513,7 +513,7 @@ OCFG = { ---@field shared_chest_position OarcOffsetPosition Location of shared chest relative to spawn center (if enabled) ---@field solid_resources table Spawn area config for solid resource tiles ---@field fluid_resources table Spawn area config for fluid resource patches (like oil) ----@field growth_resources table Spawn area config for growth resources (like gleba trees) +---@field gleba_resources table Spawn area config for gleba-style resources (like plants and stromatolites) ---@class OarcConfigSpawnGeneral ---@field spawn_radius_tiles number THIS IS WHAT SETS THE SPAWN CIRCLE SIZE! Create a circle of land area for the spawn If you make this much bigger than a few chunks, good luck. @@ -563,10 +563,11 @@ OCFG = { ---@field x_offset_next integer ---@field y_offset_next integer ----@class OarcConfigGrowthResource +---@class OarcConfigGlebaResource ---@field tile string The tile to place ----@field entity string The entity (tree that grows on this specific tile) ----@field size integer +---@field entities string[] The entities that can be placed on the tile +---@field size integer The size of the resource patch +---@field density number How often we attempt to place an entity per tile (so if the entity is bigger, then even a density < 1 might still completely fill the area) ---@class OarcStoreItem ---@field cost integer diff --git a/lib/planet_configs/gleba.lua b/lib/planet_configs/gleba.lua index 0cd7b92..240d3fb 100644 --- a/lib/planet_configs/gleba.lua +++ b/lib/planet_configs/gleba.lua @@ -5,9 +5,9 @@ GLEBA_STARTER_ITEMS = table.deepcopy(NO_STARTER_ITEMS) ---@type OarcConfigSpawn GLEBA_SPAWN_CONFIG = table.deepcopy(NAUVIS_SPAWN_CONFIG) -GLEBA_SPAWN_CONFIG.fill_tile = "highland-dark-rock-2" +GLEBA_SPAWN_CONFIG.fill_tile = "lowland-olive-blubber" GLEBA_SPAWN_CONFIG.liquid_tile = "gleba-deep-lake" -GLEBA_SPAWN_CONFIG.tree_entity = nil +GLEBA_SPAWN_CONFIG.tree_entity = "funneltrunk" GLEBA_SPAWN_CONFIG.random_entities = { {name = "boompuff", count = 10}, {name = "sunnycomb", count = 10}, @@ -19,6 +19,10 @@ GLEBA_SPAWN_CONFIG.random_entities = { {name = "water-cane", count = 10}, } +-- Make the warning and danger areas a bit bigger for this planet. +GLEBA_SPAWN_CONFIG.safe_area.warn_radius = 16 +GLEBA_SPAWN_CONFIG.safe_area.danger_radius = 32 + GLEBA_SPAWN_CONFIG.solid_resources = { ["stone"] = { @@ -31,28 +35,26 @@ GLEBA_SPAWN_CONFIG.solid_resources = } } -GLEBA_SPAWN_CONFIG.growth_resources = +GLEBA_SPAWN_CONFIG.fluid_resources = { } + +GLEBA_SPAWN_CONFIG.gleba_resources = { ["yumako"] = { tile = "natural-yumako-soil", - entity = "yumako-tree", - size = 20 + entities = {"yumako-tree"}, + size = 25, + density = 0.05 }, ["jellystem"] = { tile = "natural-jellynut-soil", - entity = "jellystem", - size = 20 + entities = {"jellystem"}, + size = 25, + density = 0.05 }, ["iron"] = { - tile = "wetland-dead-skin", - entity = "iron-stromatolite", - size = 20 + tile = "wetland-green-slime", + entities = {"iron-stromatolite", "copper-stromatolite"}, + size = 25, + density = 0.10 }, - ["copper"] = { - tile = "wetland-dead-skin", - entity = "copper-stromatolite", - size = 20 - }, -} - -GLEBA_SPAWN_CONFIG.fluid_resources = { } \ No newline at end of file +} \ No newline at end of file diff --git a/lib/planet_configs/nauvis.lua b/lib/planet_configs/nauvis.lua index 9f18ed4..9ec3bb2 100644 --- a/lib/planet_configs/nauvis.lua +++ b/lib/planet_configs/nauvis.lua @@ -171,7 +171,7 @@ NAUVIS_SPAWN_CONFIG = } }, - growth_resources = {} + gleba_resources = {} } ---@type OarcConfigSurface diff --git a/lib/scaled_enemies.lua b/lib/scaled_enemies.lua index 5303f63..5da7184 100644 --- a/lib/scaled_enemies.lua +++ b/lib/scaled_enemies.lua @@ -76,6 +76,10 @@ function DowngradeAndReduceEnemiesOnChunkGenerate(event) RemoveWormsInArea(surface, chunk_area, false, true, true, true) -- remove all non-small worms. end + if gleba_enemies then + DowngradeGlebaSpawnersInArea(surface, chunk_area) + end + -- Create a third area with moderately reduced enemies elseif (util.distance(closest_spawn.position, chunkAreaCenter) < spawn_config.safe_area.danger_radius * CHUNK_SIZE) then if nauvis_enemies or gleba_enemies then @@ -88,6 +92,18 @@ function DowngradeAndReduceEnemiesOnChunkGenerate(event) end end +---Downgrades gleba spawners in the area +---@param surface LuaSurface +---@param area BoundingBox +---@return nil +function DowngradeGlebaSpawnersInArea(surface, area) + for _, entity in pairs(surface.find_entities_filtered { area = area, name = "gleba-spawner", force = "enemy" }) do + local position = entity.position + entity.destroy() + local spawner = surface.create_entity { name = "gleba-spawner-small", position = position, force = game.forces.enemy } + end +end + ---Convenient way to remove aliens, just provide an area ---@param surface LuaSurface ---@param area BoundingBox @@ -237,11 +253,17 @@ function ModifyEnemySpawnsNearPlayerStartingAreas(event) elseif ((enemy_name == "big-strafer-pentapod") or (enemy_name == "medium-strafer-pentapod")) then event.entity.destroy() surface.create_entity { name = "small-strafer-pentapod", position = enemy_pos, force = game.forces.enemy } + + -- Gleba spawners downgrade + elseif (enemy_name == "gleba-spawner") then + event.entity.destroy() + surface.create_entity { name = "gleba-spawner-small", position = enemy_pos, force = game.forces.enemy } + end -- Danger distance is MEDIUM max. elseif (util.distance(enemy_pos, closest_spawn.position) < storage.ocfg.surfaces_config[surface.name].spawn_config.safe_area.danger_radius * CHUNK_SIZE) then - + -- Nauvis enemies if ((enemy_name == "big-biter") or (enemy_name == "behemoth-biter")) then event.entity.destroy() diff --git a/lib/separate_spawns.lua b/lib/separate_spawns.lua index 0581cb7..ef15900 100644 --- a/lib/separate_spawns.lua +++ b/lib/separate_spawns.lua @@ -485,7 +485,7 @@ function PlaceResourcesInSemiCircle(surface, position, size_mod, amount_mod) end end - for g_name,_ in pairs(storage.ocfg.surfaces_config[surface.name].spawn_config.growth_resources) do + for g_name,_ in pairs(storage.ocfg.surfaces_config[surface.name].spawn_config.gleba_resources) do if (g_name ~= "") then table.insert(r_list, g_name) end @@ -515,8 +515,8 @@ function PlaceResourcesInSemiCircle(surface, position, size_mod, amount_mod) if (resourceConfig ~= nil) then GenerateResourcePatch(surface, r_name, resourceConfig.size * size_mod, pos, resourceConfig.amount * amount_mod) else - local gResourceConfig = surface_config.spawn_config.growth_resources[r_name] - GenerateGrowthResourcePatch(surface, gResourceConfig.tile, gResourceConfig.entity, gResourceConfig.size * size_mod, pos) + local gResourceConfig = surface_config.spawn_config.gleba_resources[r_name] + GenerateGlebaStyleResourcePatch(surface, gResourceConfig, gResourceConfig.size * size_mod, pos) end else @@ -536,8 +536,8 @@ function PlaceResourcesInSemiCircle(surface, position, size_mod, amount_mod) if (resourceConfig ~= nil) then GenerateResourcePatch(surface, r_name, resourceConfig.size * size_mod, pos, resourceConfig.amount * amount_mod) else - local gResourceConfig = surface_config.spawn_config.growth_resources[r_name] - GenerateGrowthResourcePatch(surface, gResourceConfig.tile, gResourceConfig.entity, gResourceConfig.size * size_mod, pos) + local gResourceConfig = surface_config.spawn_config.gleba_resources[r_name] + GenerateGlebaStyleResourcePatch(surface, gResourceConfig, gResourceConfig.size * size_mod, pos) end count = count + 1 end diff --git a/lib/spawn_area_generation.lua b/lib/spawn_area_generation.lua index e20efcd..88c876c 100644 --- a/lib/spawn_area_generation.lua +++ b/lib/spawn_area_generation.lua @@ -301,14 +301,17 @@ function GenerateResourcePatch(surface, resourceName, diameter, position, amount end end ---- Function to generate a growth resource patch, of a certain size at a pos. +--- Function to generate a gleba style resource patch (plants or stromatolites), of a certain size at a pos. ---@param surface LuaSurface ----@param tile_name string ----@param entity_name string +---@param gleba_resource OarcConfigGlebaResource ---@param diameter integer ---@param position TilePosition ---@return nil -function GenerateGrowthResourcePatch(surface, tile_name, entity_name, diameter, position) +function GenerateGlebaStyleResourcePatch(surface, gleba_resource, diameter, position) + + local tile_name = gleba_resource.tile + local entity_names = gleba_resource.entities + local midPoint = math.floor(diameter / 2) if (diameter == 0) then return @@ -333,8 +336,9 @@ function GenerateGrowthResourcePatch(surface, tile_name, entity_name, diameter, -- Either it's a square, or it's a circle so we check if it's inside the circle. if (square_shape or ((x) ^ 2 + (y) ^ 2 < midPoint ^ 2)) then - -- Reduce chances to spawn to make it more sparse. - if (math.random(1, 20) == 1) then + -- Density controls how often we try to place an entity per tile. + if (math.random() <= gleba_resource.density) then + local entity_name = entity_names[math.random(1, #entity_names)] local pos = surface.find_non_colliding_position(entity_name, { position.x + x, position.y + y }, 2, 0.5) if (pos ~= nil) then local entity = surface.create_entity({ name = entity_name, position = pos }) diff --git a/migrations/oarc-mod-v2.1.13.lua b/migrations/oarc-mod-v2.1.13.lua index e9469d5..6c2958a 100644 --- a/migrations/oarc-mod-v2.1.13.lua +++ b/migrations/oarc-mod-v2.1.13.lua @@ -27,4 +27,18 @@ if script.active_mods["space-age"] ~= nil then } log("Updating vulcanus config with new spawn_config and starting_items.") end +end + +-- Make sure gleba config is set up if it is missing. +if script.active_mods["space-age"] ~= nil then + if (storage.ocfg.surfaces_config["gleba"] == nil) or + (storage.ocfg.surfaces_config["gleba"].spawn_config.gleba_resources == nil) or + (#storage.ocfg.surfaces_config["gleba"].spawn_config.gleba_resources == 0) then + storage.ocfg.surfaces_config["gleba"] = + { + spawn_config = GLEBA_SPAWN_CONFIG, + starting_items = GLEBA_STARTER_ITEMS + } + log("Updating gleba config with new spawn_config and starting_items.") + end end \ No newline at end of file