prepared to add depot bypass

This commit is contained in:
Monica Moniot
2022-11-30 23:29:46 -05:00
parent 24b00b9f3e
commit ac09811324
8 changed files with 101 additions and 66 deletions

View File

@@ -88,3 +88,8 @@ Version: 1.0.5
Date: 2022-11-30
Features:
- Fixed a crash related to the central planner
---------------------------------------------------------------------------------------------------
Version: 1.0.6
Date: 2022-11-30
Features:
- Added depot bypass

View File

@@ -1,6 +1,6 @@
{
"name": "cybersyn",
"version": "1.0.5",
"version": "1.0.6",
"title": "Project Cybersyn",
"author": "Mami",
"factorio_version": "1.1",

View File

@@ -7,7 +7,6 @@ local INF = math.huge
local btest = bit32.btest
local band = bit32.band
local table_remove = table.remove
local table_sort = table.sort
local random = math.random
@@ -48,8 +47,8 @@ local function get_valid_train(map_data, r_station_id, p_station_id, item_type,
return nil, INF
end
---@type Depot|nil
local best_depot = nil
---@type uint?
local best_train = nil
local best_capacity = 0
local best_dist = INF
local valid_train_exists = false
@@ -57,8 +56,7 @@ local function get_valid_train(map_data, r_station_id, p_station_id, item_type,
local is_fluid = item_type == "fluid"
local trains = map_data.available_trains[network_name]
if trains then
for train_id, depot_id in pairs(trains) do
local depot = map_data.depots[depot_id]
for train_id, _ in pairs(trains) do
local train = map_data.trains[train_id]
local layout_id = train.layout_id
--check cargo capabilities
@@ -73,20 +71,20 @@ local function get_valid_train(map_data, r_station_id, p_station_id, item_type,
valid_train_exists = true
--check if exists valid path
--check if path is shortest so we prioritize locality
local d_to_p_dist = get_stop_dist(depot.entity_stop, p_station.entity_stop) - DEPOT_PRIORITY_MULT*train.priority
local d_to_p_dist = get_stop_dist(train.entity.front_stock, p_station.entity_stop) - DEPOT_PRIORITY_MULT*train.priority
local dist = d_to_p_dist
if capacity > best_capacity or (capacity == best_capacity and dist < best_dist) then
best_capacity = capacity
best_dist = dist
best_depot = depot
best_train = train_id
end
end
end
end
if valid_train_exists then
return best_depot, best_dist + p_to_r_dist
return best_train, best_dist + p_to_r_dist
else
return nil, p_to_r_dist
end
@@ -96,14 +94,14 @@ end
---@param map_data MapData
---@param r_station_id uint
---@param p_station_id uint
---@param depot Depot
---@param train_id uint
---@param primary_item_name string
local function send_train_between(map_data, r_station_id, p_station_id, depot, primary_item_name)
local function send_train_between(map_data, r_station_id, p_station_id, train_id, primary_item_name)
--trains and stations expected to be of the same network
local economy = map_data.economy
local r_station = map_data.stations[r_station_id]
local p_station = map_data.stations[p_station_id]
local train = map_data.trains[depot.available_train_id]
local train = map_data.trains[train_id]
---@type string
local network_name = r_station.network_name
@@ -192,14 +190,14 @@ local function send_train_between(map_data, r_station_id, p_station_id, depot, p
end
end
remove_available_train(map_data, train, depot)
remove_available_train(map_data, train_id, train)
train.status = STATUS_D_TO_P
train.p_station_id = p_station_id
train.r_station_id = r_station_id
train.manifest = manifest
train.last_manifest_tick = map_data.total_ticks
set_manifest_schedule(train.entity, depot.entity_stop, p_station.entity_stop, r_station.entity_stop, manifest)
set_manifest_schedule(train.entity, train.depot_name, p_station.entity_stop, r_station.entity_stop, manifest)
set_comb2(map_data, p_station)
set_comb2(map_data, r_station)
if p_station.entity_comb1.valid then
@@ -421,7 +419,7 @@ local function tick_dispatch(map_data, mod_settings)
max_threshold = 0
local best_i = 0
local best_depot = nil
local best_train = nil
local best_dist = INF
local best_prior = -INF
local can_be_serviced = false
@@ -432,12 +430,12 @@ local function tick_dispatch(map_data, mod_settings)
if effective_count >= r_threshold then
local prior = p_station.priority
local slot_threshold = item_type == "fluid" and r_threshold or ceil(r_threshold/get_stack_size(map_data, item_name))
local depot, d = get_valid_train(map_data, r_station_id, p_station_id, item_type, slot_threshold)
local train, d = get_valid_train(map_data, r_station_id, p_station_id, item_type, slot_threshold)
if prior > best_prior or (prior == best_prior and d < best_dist) then
if depot then
if train then
best_i = j
best_dist = d
best_depot = depot
best_train = train
best_prior = prior
can_be_serviced = true
elseif d < INF then
@@ -451,12 +449,8 @@ local function tick_dispatch(map_data, mod_settings)
end
end
end
if
best_depot and (
best_depot.entity_comb.status == defines.entity_status.working or
best_depot.entity_comb.status == defines.entity_status.low_power)
then
send_train_between(map_data, r_station_id, table_remove(p_stations, best_i), best_depot, item_name)
if best_train then
send_train_between(map_data, r_station_id, table_remove(p_stations, best_i), best_train, item_name)
return false
else
if can_be_serviced then

View File

@@ -11,12 +11,12 @@ function get_stack_size(map_data, item_name)
end
---@param stop0 LuaEntity
---@param stop1 LuaEntity
function get_stop_dist(stop0, stop1)
local surface0 = stop0.surface.index
local surface1 = stop1.surface.index
return (surface0 == surface1 and get_distance(stop0.position, stop1.position) or DIFFERENT_SURFACE_DISTANCE)
---@param entity0 LuaEntity
---@param entity1 LuaEntity
function get_stop_dist(entity0, entity1)
local surface0 = entity0.surface.index
local surface1 = entity1.surface.index
return (surface0 == surface1 and get_distance(entity0.position, entity1.position) or DIFFERENT_SURFACE_DISTANCE)
end
@@ -107,13 +107,13 @@ function rename_manifest_schedule(train, stop, old_name)
end
---@param train LuaTrain
---@param depot_stop LuaEntity
---@param depot_name string
---@param p_stop LuaEntity
---@param r_stop LuaEntity
---@param manifest Manifest
function set_manifest_schedule(train, depot_stop, p_stop, r_stop, manifest)
function set_manifest_schedule(train, depot_name, p_stop, r_stop, manifest)
--NOTE: train must be on same surface as depot_stop
local d_surface = depot_stop.surface
local d_surface = train.front_stock.surface
local p_surface = p_stop.surface
local r_surface = r_stop.surface
local d_surface_i = d_surface.index
@@ -121,7 +121,7 @@ function set_manifest_schedule(train, depot_stop, p_stop, r_stop, manifest)
local r_surface_i = r_surface.index
if d_surface_i == p_surface_i and p_surface_i == r_surface_i then
train.schedule = {current = 1, records = {
create_inactivity_order(depot_stop.backer_name),
create_inactivity_order(depot_name),
create_direct_to_station_order(p_stop),
create_loading_order(p_stop, manifest),
create_direct_to_station_order(r_stop),
@@ -135,7 +135,7 @@ function set_manifest_schedule(train, depot_stop, p_stop, r_stop, manifest)
if is_train_in_orbit or d_zone.orbit_index == other_zone.index then
local elevator_name = se_get_space_elevator_name(d_surface)
if elevator_name then
local records = {create_inactivity_order(depot_stop.backer_name)}
local records = {create_inactivity_order(depot_name)}
if d_surface_i == p_surface_i then
records[#records + 1] = create_direct_to_station_order(p_stop)
else
@@ -160,12 +160,12 @@ function set_manifest_schedule(train, depot_stop, p_stop, r_stop, manifest)
end
--NOTE: create a schedule that cannot be fulfilled, the train will be stuck but it will give the player information what went wrong
train.schedule = {current = 1, records = {
create_inactivity_order(depot_stop.backer_name),
create_inactivity_order(depot_name),
create_loading_order(p_stop, manifest),
create_unloading_order(r_stop),
}}
lock_train(train)
send_lost_train_alert(train, depot_stop.backer_name)
send_lost_train_alert(train, depot_name)
end

View File

@@ -11,7 +11,7 @@
---@field public warmup_station_ids uint[]
---@field public depots {[uint]: Depot}
---@field public trains {[uint]: Train}
---@field public available_trains {[string]: {[uint]: uint}} --{[network_name]: {[train_id]: depot_id}}
---@field public available_trains {[string]: {[uint]: true?}} --{[network_name]: {[train_id]: depot_id}}
---@field public layouts {[uint]: int[]}
---@field public layout_train_count {[uint]: int}
---@field public tick_state uint
@@ -58,6 +58,7 @@
---@field public manifest Manifest
---@field public last_manifest_tick int
---@field public has_filtered_wagon boolean
---@field public is_available true?
---@field public depot_id uint?
---@field public depot_name string
---@field public network_name string?

View File

@@ -55,9 +55,11 @@ end
---@param train Train
---@param train_id uint
function remove_train(map_data, train, train_id)
if train.status == STATUS_D then
local depot = map_data.depots[train.depot_id]
remove_available_train(map_data, train, depot)
local parked_at_depot_id = train.depot_id
if parked_at_depot_id then
local depot = map_data.depots[parked_at_depot_id]
remove_available_train(map_data, parked_at_depot_id, train)
depot.available_train_id = nil
end
local layout_id = train.layout_id
local count = map_data.layout_train_count[layout_id]

View File

@@ -52,12 +52,28 @@ local function on_failed_delivery(map_data, train)
end
---@param map_data MapData
---@param train_id uint
---@param train Train
local function add_available_train(map_data, train_id, train)
local network_name = train.network_name
if network_name then
local network = map_data.available_trains[network_name]
if not network then
network = {}
map_data.available_trains[network_name] = network
end
network[train_id] = true
train.is_available = true
end
end
---@param map_data MapData
---@param depot_id uint
---@param depot Depot
---@param train_id uint
local function add_available_train(map_data, depot_id, train_id)
local depot = map_data.depots[depot_id]
local train = map_data.trains[train_id]
---@param train Train
local function add_available_train_to_depot(map_data, train_id, train, depot_id, depot)
local comb = depot.entity_comb
local network_name = get_comb_network_name(comb)
if network_name then
@@ -66,7 +82,8 @@ local function add_available_train(map_data, depot_id, train_id)
network = {}
map_data.available_trains[network_name] = network
end
network[train_id] = depot_id
network[train_id] = true
train.is_available = true
end
depot.available_train_id = train_id
train.status = STATUS_D
@@ -94,13 +111,12 @@ local function add_available_train(map_data, depot_id, train_id)
end
end
---@param map_data MapData
---@param train_id uint
---@param train Train
---@param depot Depot
function remove_available_train(map_data, train, depot)
function remove_available_train(map_data, train_id, train)
---@type uint
local train_id = depot.available_train_id
if train.network_name then
local network = map_data.available_trains[train.network_name]
if train.is_available then
local network = map_data.available_trains[train.network_name--[[@as string]]]
if network then
network[train_id] = nil
if next(network) == nil then
@@ -108,7 +124,6 @@ function remove_available_train(map_data, train, depot)
end
end
end
depot.available_train_id = nil
end
@@ -132,8 +147,9 @@ local function on_depot_broken(map_data, depot)
local train = map_data.trains[train_id]
lock_train(train.entity)
send_lost_train_alert(train.entity, depot.entity_stop.backer_name)
remove_available_train(map_data, train, depot)
remove_available_train(map_data, train_id, train)
map_data.trains[train_id] = nil
depot.available_train_id = nil
end
map_data.depots[depot.entity_stop.unit_number] = nil
end
@@ -350,8 +366,9 @@ function on_combinator_network_updated(map_data, comb, network_name)
local train_id = depot.available_train_id
if train_id then
local train = map_data.trains[train_id]
remove_available_train(map_data, train, depot)
add_available_train(map_data, depot_id, train_id)
remove_available_train(map_data, train_id, train)
depot.available_train_id = nil
add_available_train_to_depot(map_data, train_id, train, depot_id, depot)
end
end
end
@@ -522,7 +539,7 @@ end
---@param old_name string
local function on_station_rename(map_data, stop, old_name)
--search for trains coming to the renamed station
local station_id = stop.unit_number
local station_id = stop.unit_number--[[@as uint]]
local station = map_data.stations[station_id]
if station and station.deliveries_total > 0 then
for train_id, train in pairs(map_data.trains) do
@@ -552,7 +569,7 @@ local function on_station_rename(map_data, stop, old_name)
else
local depot = map_data.depots[station_id]
if depot and depot.available_train_id then
local train = map_data.trains[depot.available_train_id]
local train = map_data.trains[depot.available_train_id--[[@as uint]]]
train.depot_name = stop.backer_name
end
end
@@ -581,18 +598,19 @@ local function on_train_arrives_depot(map_data, depot_id, train_entity)
local train_id = train_entity.id
local train = map_data.trains[train_id]
if train then
remove_available_train(map_data, train_id, train)
if train.manifest and train.status == STATUS_R_TO_D then
--succeeded delivery
train.p_station_id = 0
train.r_station_id = 0
train.manifest = nil
add_available_train(map_data, depot_id, train_id)
add_available_train_to_depot(map_data, train_id, train, depot_id, map_data.depots[depot_id])
else
if train.manifest then
on_failed_delivery(map_data, train)
send_unexpected_train_alert(train.entity)
end
add_available_train(map_data, depot_id, train_id)
add_available_train_to_depot(map_data, train_id, train, depot_id, map_data.depots[depot_id])
end
if is_train_empty then
set_depot_schedule(train_entity, train.depot_name)
@@ -616,7 +634,7 @@ local function on_train_arrives_depot(map_data, depot_id, train_entity)
}
update_train_layout(map_data, train)
map_data.trains[train_id] = train
add_available_train(map_data, depot_id, train_id)
add_available_train_to_depot(map_data, train_id, train, depot_id, map_data.depots[depot_id])
set_depot_schedule(train_entity, train.depot_name)
else
@@ -661,8 +679,9 @@ local function on_train_arrives_buffer(map_data, stop, train)
end
end
---@param map_data MapData
---@param train_id uint
---@param train Train
local function on_train_leaves_station(map_data, train)
local function on_train_leaves_station(map_data, train_id, train)
if train.manifest then
if train.status == STATUS_P then
train.status = STATUS_P_TO_R
@@ -692,8 +711,9 @@ local function on_train_leaves_station(map_data, train)
unset_wagon_combs(map_data, station)
end
elseif train.status == STATUS_D then
local depot = map_data.depots[train.depot_id]
remove_available_train(map_data, train, depot)
local depot = map_data.depots[train.depot_id--[[@as uint]]]
remove_available_train(map_data, train_id, train)
depot.available_train_id = nil
end
end
@@ -789,9 +809,10 @@ local function on_train_built(event)
end
end
local function on_train_changed(event)
local train_e = event.train
local train_e = event.train--[[@as LuaTrain]]
if not train_e.valid then return end
local train = global.trains[train_e.id]
local train_id = train_e.id
local train = global.trains[train_id]
if train_e.state == defines.train_state.wait_station then
local stop = train_e.station
if stop and stop.valid and stop.name == "train-stop" then
@@ -800,7 +821,7 @@ local function on_train_changed(event)
on_train_arrives_buffer(global, stop, train)
end
else
local depot_id = stop.unit_number
local depot_id = stop.unit_number--[[@as uint]]
if global.depots[depot_id] then
on_train_arrives_depot(global, depot_id, train_e)
end
@@ -808,7 +829,7 @@ local function on_train_changed(event)
end
elseif event.old_state == defines.train_state.wait_station then
if train then
on_train_leaves_station(global, train)
on_train_leaves_station(global, train_id, train)
end
end
end

View File

@@ -124,6 +124,18 @@ local migrations_table = {
map_data.tick_state = STATE_INIT
map_data.tick_data = {}
end,
["1.0.6"] = function()
---@type MapData
local map_data = global
map_data.tick_state = STATE_INIT
map_data.tick_data = {}
for k, v in pairs(map_data.available_trains) do
for id, _ in pairs(v) do
local train = map_data.trains[id]
train.is_available = true
end
end
end,
}
---@param data ConfigurationChangedData