From 1f3a4c3bfc2a462ff51bd6b391be0d39a6a6c944 Mon Sep 17 00:00:00 2001 From: orwell96 Date: Wed, 7 Jul 2021 22:14:20 +0200 Subject: Rework train same-track collision system and deterministic coupling - Adds a separate collision system for trains sharing a path - Moved some coupling-related code to couple.lua and refactor it - Handle coupling in a way that the initiating train always keeps its ID - As a side effect, engine has its direction reversed after coupling --- advtrains/path.lua | 39 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) (limited to 'advtrains/path.lua') diff --git a/advtrains/path.lua b/advtrains/path.lua index 714781a..f2b8a13 100644 --- a/advtrains/path.lua +++ b/advtrains/path.lua @@ -417,3 +417,42 @@ function advtrains.path_lookup(train, pos) end return nil end + +-- Projects the path of "train" onto the path of "onto_train_id", and returns the index on onto_train's path +-- that corresponds to "index" on "train"'s path, as well as whether both trains face each other +-- index may be fractional +-- returns: res_index, trains_facing +-- returns nil when path can not be projected, either because trains are on different tracks or +-- node at "index" happens to be on a turnout and it's the wrong direction +-- Note - duplicate with similar functionality is in train_step_b() - that code combines train detection with projecting +function advtrains.path_project(train, index, onto_train_id) + local base_idx = atfloor(index) + local frac_part = index - base_idx + local base_pos = advtrains.path_get(train, base_idx) + local base_cn = train.path_cn[base_idx] + local otrn = advtrains.trains[onto_train_id] + -- query occupation + local occ = advtrains.occ.get_trains_over(base_pos) + -- is wanted train id contained? + local ob_idx = occ[onto_train_id] + if not ob_idx then + return nil + end + + -- retrieve other train's cn and cp + local ocn = otrn.path_cn[ob_idx] + local ocp = otrn.path_cp[ob_idx] + + if base_cn == ocn then + -- same direction + return ob_idx + frac_part, false + elseif base_cn == ocp then + -- facing trains - subtract index frac + return ob_idx - frac_part, true + else + -- same path item but no common connections - deny + return nil + end +end + + -- cgit v1.2.3