require 'modules.sticky_landfill' require 'modules.dynamic_player_spawn' require 'modules.biters_yield_ore' local math_random = math.random local math_floor = math.floor local table_insert = table.insert local math_abs = math.abs local map_height = 96 local infini_ores = {'iron-ore', 'iron-ore', 'copper-ore', 'coal', 'stone'} local function on_player_joined_game(event) local surface = game.surfaces['railway_troopers'] local player = game.players[event.player_index] if player.online_time == 0 then player.teleport(surface.find_non_colliding_position('character', game.forces.player.get_spawn_position(surface), 32, 0.5), surface) end end local function set_commands(unit_group) local surface = unit_group.surface local position = unit_group.position local commands = {} for x = position.x, -8196, -32 do if surface.is_chunk_generated({math_floor(x / 32), math_floor(position.y / 32)}) then if math_random(1, 16) == 1 then commands[#commands + 1] = { type = defines.command.build_base, destination = {x = x, y = position.y}, distraction = defines.distraction.by_anything, ignore_planner = true } else commands[#commands + 1] = { type = defines.command.attack_area, destination = {x = x, y = position.y}, radius = 16, distraction = defines.distraction.by_anything } end else break end end if #commands == 0 then return end unit_group.set_command( { type = defines.command.compound, structure_type = defines.compound_command.return_last, commands = commands } ) end local function send_wave(spawner, search_radius) local biters = spawner.surface.find_enemy_units(spawner.position, search_radius, 'player') if biters[1] then local unit_group = spawner.surface.create_unit_group({position = {x = spawner.position.x, y = -42 + math_random(0, 84)}, force = 'enemy'}) for _, unit in pairs(biters) do unit_group.add_member(unit) end set_commands(unit_group) end end local function on_entity_spawned(event) global.on_entity_spawned_counter = global.on_entity_spawned_counter + 1 local c = global.on_entity_spawned_counter * 0.5 if c % 2 ~= 0 then return end for a = 14, 6, -2 do local b = 2 ^ a if c % b == 0 then send_wave(event.spawner, a ^ 2 - 28) return end end end local function on_entity_died(event) local entity = event.entity if not entity.valid then return end if entity.type == 'unit' and entity.spawner then entity.spawner.damage(20, game.forces[1]) end end local function is_out_of_map(p) local a = p.x + 1960 local b = math_abs(p.y) if a * 0.025 >= b then return end if a * -0.025 > b then return end return true end local function draw_west_side(surface, left_top) local entities = {} for x = 0, 31, 1 do for y = 0, 31, 1 do local position = {x = left_top.x + x, y = left_top.y + y} if math_abs(position.y) > map_height * 0.5 then surface.set_tiles({{name = 'out-of-map', position = position}}, true) else surface.set_tiles({{name = 'deepwater-green', position = position}}, true) if math_random(1, 64) == 1 then table_insert(entities, {name = 'fish', position = position}) end if math_random(1, 8196) == 1 and position.x < -64 then table_insert(entities, {name = 'crude-oil', position = position, amount = 200000 + math_abs(left_top.x * 500)}) end end end end for _, entity in pairs(entities) do surface.create_entity(entity) end end local function draw_east_side(surface, left_top) local entities = {} if left_top.y == 0 and left_top.x < 64 then for x = 0, 30, 2 do surface.create_entity({name = 'straight-rail', position = {left_top.x + x, 0}, direction = 2, force = 'player'}) end if left_top.x == -32 then local entity = surface.create_entity({name = 'cargo-wagon', position = {-24, 0}, force = 'player', direction = 2}) entity.get_inventory(defines.inventory.cargo_wagon).insert({name = 'firearm-magazine', count = 600}) entity.get_inventory(defines.inventory.cargo_wagon).insert({name = 'shotgun', count = 2}) entity.get_inventory(defines.inventory.cargo_wagon).insert({name = 'shotgun-shell', count = 64}) entity.get_inventory(defines.inventory.cargo_wagon).insert({name = 'light-armor', count = 5}) entity.get_inventory(defines.inventory.cargo_wagon).insert({name = 'grenade', count = 32}) entity.get_inventory(defines.inventory.cargo_wagon).insert({name = 'pistol', count = 10}) entity.get_inventory(defines.inventory.cargo_wagon).insert({name = 'rail', count = 100}) entity = surface.create_entity({name = 'locomotive', position = {-18, 0}, force = 'player', direction = 2}) entity.get_inventory(defines.inventory.fuel).insert({name = 'wood', count = 25}) end end for x = 0, 31, 1 do for y = 0, 31, 1 do local position = {x = left_top.x + x, y = left_top.y + y} if is_out_of_map(position) then surface.set_tiles({{name = 'out-of-map', position = position}}, true) else if math_random(1, 4096) == 1 and left_top.x > -32 and math_abs(left_top.y) > 2 then table_insert(entities, {name = infini_ores[math_random(1, #infini_ores)], position = position, amount = 99999999}) table_insert(entities, {name = 'electric-mining-drill', position = position, force = 'enemy'}) end end end end for _, entity in pairs(entities) do local e = surface.create_entity(entity) if e.name == 'electric-mining-drill' then if e.position.y < 0 then e.direction = 4 else e.direction = 0 end e.minable = false e.destructible = false --e.insert({name = "coal", count = math_random(8, 36)}) end end end local function on_chunk_generated(event) local surface = event.surface local left_top = event.area.left_top if left_top.x < -32 then draw_west_side(surface, left_top) else draw_east_side(surface, left_top) end end local type_whitelist = { ['artillery-wagon'] = true, ['car'] = true, ['cargo-wagon'] = true, ['construction-robot'] = true, ['container'] = true, ['curved-rail'] = true, ['electric-pole'] = true, ['entity-ghost'] = true, ['fluid-wagon'] = true, ['heat-pipe'] = true, ['inserter'] = true, ['lamp'] = true, ['locomotive'] = true, ['logistic-robot'] = true, ['rail-chain-signal'] = true, ['rail-signal'] = true, ['splitter'] = true, ['straight-rail'] = true, ['tile-ghost'] = true, ['train-stop'] = true, ['transport-belt'] = true, ['underground-belt'] = true, ['wall'] = true, ['gate'] = true, ['beacon'] = true } local function deny_building(event) local entity = event.created_entity if not entity.valid then return end if type_whitelist[event.created_entity.type] then return end if entity.position.x < -32 then return end if event.player_index then game.players[event.player_index].insert({name = entity.name, count = 1}) else local inventory = event.robot.get_inventory(defines.inventory.robot_cargo) inventory.insert({name = entity.name, count = 1}) end event.created_entity.surface.create_entity( { name = 'flying-text', position = entity.position, text = 'Can only be built west!', color = {r = 0.98, g = 0.66, b = 0.22} } ) entity.destroy() end local function on_built_entity(event) deny_building(event) end local function on_robot_built_entity(event) deny_building(event) end local function on_research_finished(event) event.research.force.character_inventory_slots_bonus = game.forces.player.mining_drill_productivity_bonus * 200 event.research.force.character_item_pickup_distance_bonus = game.forces.player.mining_drill_productivity_bonus * 10 end local function send_tick_wave() if game.tick % 54000 ~= 3600 then return end local surface = game.surfaces['railway_troopers'] local spawners = surface.find_entities_filtered({type = 'unit-spawner'}) if not spawners[1] then return end local search_radius = 16 for _, player in pairs(game.connected_players) do if player.position.x * 0.5 > search_radius then search_radius = math_floor(player.position.x * 0.5) end end if search_radius > 256 then search_radius = 256 end send_wave(spawners[math_random(1, #spawners)], search_radius) end local function on_tick() send_tick_wave() end local function on_init() global.drop_schedule = {} global.on_entity_spawned_counter = 0 game.map_settings.enemy_evolution.destroy_factor = 0.001 --game.map_settings.enemy_evolution.pollution_factor = 0 --game.map_settings.enemy_evolution.time_factor = 0 game.map_settings.enemy_expansion.enabled = true game.map_settings.enemy_expansion.max_expansion_cooldown = 900 game.map_settings.enemy_expansion.min_expansion_cooldown = 900 game.map_settings.enemy_expansion.settler_group_max_size = 128 game.map_settings.enemy_expansion.settler_group_min_size = 32 game.map_settings.enemy_expansion.max_expansion_distance = 16 game.map_settings.pollution.enemy_attack_pollution_consumption_modifier = 0.25 local map_gen_settings = { ['water'] = 0, ['starting_area'] = 0.60, ['cliff_settings'] = {cliff_elevation_interval = 0, cliff_elevation_0 = 0}, ['autoplace_controls'] = { ['coal'] = {frequency = 0, size = 0.65, richness = 0.5}, ['stone'] = {frequency = 0, size = 0.65, richness = 0.5}, ['copper-ore'] = {frequency = 0, size = 0.65, richness = 0.5}, ['iron-ore'] = {frequency = 0, size = 0.65, richness = 0.5}, ['uranium-ore'] = {frequency = 0, size = 1, richness = 1}, ['crude-oil'] = {frequency = 0, size = 1, richness = 0.75}, ['trees'] = {frequency = 2, size = 0.15, richness = 1}, ['enemy-base'] = {frequency = 256, size = 2, richness = 1} } } local surface = game.create_surface('railway_troopers', map_gen_settings) surface.request_to_generate_chunks({0, 0}, 4) surface.force_generate_chunk_requests() local force = game.forces.player force.set_spawn_position({-30, 0}, surface) force.technologies['landfill'].researched = true force.technologies['railway'].researched = true force.technologies['engine'].researched = true local types_to_disable = { ['ammo'] = true, ['armor'] = true, ['car'] = true, ['gun'] = true, ['capsule'] = true } for _, recipe in pairs(game.recipe_prototypes) do if types_to_disable[recipe.subgroup.name] then force.set_hand_crafting_disabled_for_recipe(recipe.name, true) end end end local Event = require 'utils.event' Event.on_init(on_init) Event.add(defines.events.on_research_finished, on_research_finished) Event.add(defines.events.on_tick, on_tick) Event.add(defines.events.on_built_entity, on_built_entity) Event.add(defines.events.on_robot_built_entity, on_robot_built_entity) Event.add(defines.events.on_entity_died, on_entity_died) Event.add(defines.events.on_entity_spawned, on_entity_spawned) Event.add(defines.events.on_player_joined_game, on_player_joined_game) Event.add(defines.events.on_chunk_generated, on_chunk_generated)