Skip to content

Commit

Permalink
Spread processing out over 600 ticks (to avoid lag spikes every 10 se…
Browse files Browse the repository at this point in the history
…conds)
  • Loading branch information
Quezler committed Dec 10, 2023
1 parent 31c218c commit c14f725
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 15 deletions.
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
local Handler = require('scripts.handler')

script.on_init(Handler.on_init)
script.on_configuration_changed(Handler.on_configuration_changed)

for _, event in ipairs({
defines.events.on_built_entity,
Expand All @@ -27,19 +28,28 @@ script.on_nth_tick(600, function(event) -- no_material_for_construction expires

for surface_index, surface_alerts in pairs(alerts) do
for _, surface_alert in ipairs(surface_alerts[defines.alert_type.no_material_for_construction]) do
Handler.handle_construction_alert(surface_alert)
if surface_alert.target and surface_alert.target.valid then
assert(surface_alert.target.unit_number > 0)
global.alert_targets[surface_alert.target.unit_number] = surface_alert.target
end
end
end
end
end

global.alert_targets_per_tick = math.ceil(table_size(global.alert_targets) / 600)
-- log('global.alert_targets_per_tick = ' .. global.alert_targets_per_tick)
end)

script.on_event(defines.events.on_tick, Handler.on_tick)
script.on_nth_tick(60 * 60 * 10, Handler.gc) -- every 10 minutes

commands.add_command('se-interstellar-construction-requests-fulfillment', nil, function(command)
game.print(serpent.block({
table_size(global.structs),
#global.deck,
#global.pile,
'global.alert_targets = ' .. table_size(global.alert_targets),
'global.alert_targets_per_tick = ' .. global.alert_targets_per_tick,
}))
end)
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
"name": "se-interstellar-construction-requests-fulfillment",
"title": "Space Exploration - interstellar construction requests fulfillment",
"description": "Keeping building equipment stocked at every planet is tedious, just shoot it there from nauvis.",
"version": "1.0.3",
"version": "1.0.4",
"author": "Quezler",
"factorio_version": "1.1",
"dependencies": [
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ function Handler.on_init(event)

global.deathrattles = {}

global.alert_targets = {}
global.alert_targets_per_tick = 1

-- log('items_to_place_this')
-- for _, entity_prototype in pairs(game.entity_prototypes) do
-- for _, item_to_place_this in pairs(entity_prototype.items_to_place_this or {}) do
Expand All @@ -26,6 +29,11 @@ function Handler.on_init(event)
-- {curved-rail, se-space-curved-rail, concrete-wall-ruin, steel-wall-ruin, stone-wall-ruin}
end

function Handler.on_configuration_changed(event)
global.alert_targets = global.alert_targets or {}
global.alert_targets_per_tick = global.alert_targets_per_tick or 1
end

function Handler.on_created_entity(event)
local entity = event.created_entity or event.entity or event.destination

Expand Down Expand Up @@ -97,18 +105,16 @@ function Handler.shoot(struct)
}
end

function Handler.handle_construction_alert(alert)
if not alert.target then return end -- attempt to index field 'target' (a nil value)
if not alert.target.valid then return end -- ghost might have been removed or revived already
if alert.target.name ~= "entity-ghost" then return end -- can be "item-request-proxy" or "tile-ghost"
function Handler.handle_construction_alert(alert_target)
if alert_target.name ~= "entity-ghost" then return end -- can be "item-request-proxy" or "tile-ghost"

local handled_alert = global.handled_alerts[alert.target.unit_number]
local handled_alert = global.handled_alerts[alert_target.unit_number]
if handled_alert and handled_alert.entity.valid and handled_alert.proxy.valid then return end

local zone = remote.call("space-exploration", "get_zone_from_surface_index", {surface_index = alert.target.surface.index})
local zone = remote.call("space-exploration", "get_zone_from_surface_index", {surface_index = alert_target.surface.index})
if not zone then return end

for _, item_to_place_this in ipairs(alert.target.ghost_prototype.items_to_place_this) do
for _, item_to_place_this in ipairs(alert_target.ghost_prototype.items_to_place_this) do
if item_to_place_this.count == 1 then -- no support for e.g. curved rails (which need 4) yet

local anti_infinite_loop = 0
Expand All @@ -120,7 +126,7 @@ function Handler.handle_construction_alert(alert)
if anti_infinite_loop > anti_infinite_loop_max then return end
anti_infinite_loop = anti_infinite_loop + 1

if alert.target.force == struct.entity.force then
if alert_target.force == struct.entity.force then
-- we're gonna check for orange coverage for now, instead of green venn diagrams and filtering out personal roboports
local network = struct.entity.surface.find_logistic_network_by_position(struct.entity.position, struct.entity.force)
if network and network.can_satisfy_request(item_to_place_this.name, item_to_place_this.count, true) then
Expand All @@ -143,19 +149,19 @@ function Handler.handle_construction_alert(alert)
use_rich_text = true,
}

global.handled_alerts[alert.target.unit_number] = {
global.handled_alerts[alert_target.unit_number] = {
struct_unit_number = struct.unit_number,
unit_number = alert.target.unit_number,
entity = alert.target,
unit_number = alert_target.unit_number,
entity = alert_target,
proxy = proxy,
itemstack = item_to_place_this,
}

struct.proxy = proxy -- the struct doesn't need a reference to the handled alert right?
struct.updated_at = game.tick

global.deathrattles[script.register_on_entity_destroyed(proxy)] = alert.target.unit_number
global.deathrattles[script.register_on_entity_destroyed(alert.target)] = alert.target.unit_number
global.deathrattles[script.register_on_entity_destroyed(proxy)] = alert_target.unit_number
global.deathrattles[script.register_on_entity_destroyed(alert_target)] = alert_target.unit_number
return
end
end
Expand Down Expand Up @@ -209,6 +215,19 @@ function Handler.on_entity_destroyed(event)
end
end

function Handler.on_tick(event)
-- log('#alert_targets = ' .. table_size(global.alert_targets))
local i = 1
for unit_number, alert_target in pairs(global.alert_targets) do
global.alert_targets[unit_number] = nil
if alert_target.valid then
Handler.handle_construction_alert(alert_target)
i = i + 1
if i > global.alert_targets_per_tick then return end
end
end
end

function Handler.gc(event)
for unit_number, struct in pairs(global.structs) do
if not struct.entity.valid then
Expand Down

0 comments on commit c14f725

Please sign in to comment.