From 69e4b8f99aac08c404a733c2338f9de9cddab829 Mon Sep 17 00:00:00 2001 From: orwell Date: Sat, 20 Jul 2024 21:04:17 +0200 Subject: Support signal aspect selection for routes again --- advtrains_interlocking/database.lua | 7 ++++ advtrains_interlocking/route_ui.lua | 58 ++++++++++++++++++++++++++------- advtrains_interlocking/routesetting.lua | 16 ++++++--- advtrains_interlocking/signal_api.lua | 3 +- 4 files changed, 68 insertions(+), 16 deletions(-) diff --git a/advtrains_interlocking/database.lua b/advtrains_interlocking/database.lua index 49ca13d..a8d9584 100644 --- a/advtrains_interlocking/database.lua +++ b/advtrains_interlocking/database.lua @@ -254,6 +254,13 @@ routes = { ars = { } use_rscache = false -- if true, the track section's rs_cache will be used to set locks in addition to the locks table -- this is disabled for legacy routes, but enabled for all new routes by default + -- Fields to specify the signal aspect of the signal + main_aspect = "_free" -- The main aspect that the route start signal is to show + assign_dst = false -- Whether to assign distant signal (affects only the signal at the start of the route) + -- false: start signal does not set distant signal (the default), for long blocks + -- it is assumed that the next main signal will have its own distant sig + -- true: start signal sets distant signal to the next signal on the route with route_role "main" (typically the end signal) + -- for short blocks where end signal doesn't have its own distant sig -- Fields used by the autorouter: ar_end_sigd = -- the sigd describing the end of the route. Used for merging route options on recalculation } diff --git a/advtrains_interlocking/route_ui.lua b/advtrains_interlocking/route_ui.lua index 863fe11..b01d449 100644 --- a/advtrains_interlocking/route_ui.lua +++ b/advtrains_interlocking/route_ui.lua @@ -3,6 +3,7 @@ local atil = advtrains.interlocking local ildb = atil.db +local F = advtrains.formspec -- TODO duplicate local lntrans = { "A", "B" } @@ -83,9 +84,32 @@ function atil.show_route_edit_form(pname, sigd, routeid) itab("E (none)") end - form = form.."textlist[0.5,2;3,3.9;rtelog;"..table.concat(tab, ",").."]" + form = form.."textlist[0.5,2;3.5,3.9;rtelog;"..table.concat(tab, ",").."]" + + -- to the right of rtelog a signal aspect selection for the start signal + form = form..F.label(4.5, 2, "Signal Aspect:") + -- main aspect list + local signalpos = tcbs.signal + local ndef = signalpos and advtrains.ndb.get_ndef(signalpos) + if ndef and ndef.advtrains and ndef.advtrains.main_aspects then + local entries = { "" } + local sel = 1 + for i, mae in ipairs(ndef.advtrains.main_aspects) do + entries[i+1] = mae.description + if mae.name == route.main_aspect then + sel = i+1 + end + end + form = form..F.dropdown(4.5, 3.0, 4, "sa_main_aspect", entries, sel, true) + -- checkbox for assign distant signal + form = form..string.format("checkbox[4.5,4.0;sa_distant;Announce distant signal;%s]", route.assign_dst) + end + + form = form.."button[0.5,6;1,1;prev;<<<]" + form = form.."button[1.5,6;1,1;back;Back]" + form = form.."button[2.5,6;1,1;next;>>>]" + - form = form.."button[0.5,6;3,1;back;<<< Back to signal]" if route.smartroute_generated then form = form.."button[3.5,6;2,1;noautogen;Clr Autogen]" end @@ -123,20 +147,32 @@ minetest.register_on_player_receive_fields(function(player, formname, fields) local route = tcbs.routes[routeid] if not route then return end + if fields.prev then + atil.show_route_edit_form(pname, sigd, routeid - 1) + return + end + if fields.next then + atil.show_route_edit_form(pname, sigd, routeid + 1) + return + end + if fields.setname and fields.name then route.name = fields.name end - if fields.aspect then - local suppasp = advtrains.interlocking.signal_get_supported_aspects(tcbs.signal) - - local callback = function(pname, asp) - route.aspect = asp - advtrains.interlocking.show_route_edit_form(pname, sigd, routeid) + if fields.sa_main_aspect then + local idx = tonumber(fields.sa_main_aspect) + route.main_aspect = nil + if idx > 1 then + local signalpos = tcbs.signal + local ndef = signalpos and advtrains.ndb.get_ndef(signalpos) + if ndef and ndef.advtrains and ndef.advtrains.main_aspects then + route.main_aspect = ndef.advtrains.main_aspects[idx - 1].name + end end - - advtrains.interlocking.show_signal_aspect_selector(pname, suppasp, route.name, callback, route.aspect or advtrains.interlocking.GENERIC_FREE) - return + end + if fields.sa_distant then + route.assign_dst = minetest.is_yes(fields.sa_distant) end if fields.noautogen then diff --git a/advtrains_interlocking/routesetting.lua b/advtrains_interlocking/routesetting.lua index 34a273a..0207519 100644 --- a/advtrains_interlocking/routesetting.lua +++ b/advtrains_interlocking/routesetting.lua @@ -147,7 +147,7 @@ function ilrs.set_route(signal, route, try) tcbs_ref = c_tcbs, role = ndef and ndef.advtrains and ndef.advtrains.route_role, masp_override = c_rseg.masp_override, --TODO implement masp_override on UI side - dst_type = "next_main", --TODO allow user differentiate + assign_dst = (i~=1) or route.assign_dst -- Behavior: for first signal assign depending on route.assign_dst, all others always assign } signals[#signals+1] = sig_table end @@ -171,10 +171,18 @@ function ilrs.set_route(signal, route, try) -- note the signals are iterated backwards. Switch depending on the role local sig = signals[i] -- apply mainaspect - sig.tcbs_ref.route_aspect = sig.masp_override or "_default" + sig.tcbs_ref.route_aspect = sig.masp_override or route.main_aspect or "_default" if sig.role == "distant" or sig.role == "distant_repeater" or sig.role == "main_distant" then - -- assign the remote as the last mainsig - sig.tcbs_ref.route_remote = last_mainsig + if last_mainsig then + -- assign the remote as the last mainsig if desired + if sig.assign_dst then + sig.tcbs_ref.route_remote = last_mainsig + end + -- if it wasn't a distant_repeater clear the mainsig + if sig.role ~= "distant_repeater" then + last_mainsig = false + end + end end if sig.role == "main" or sig.role == "main_distant" or sig.role == "end" then -- record this as the new last mainsig diff --git a/advtrains_interlocking/signal_api.lua b/advtrains_interlocking/signal_api.lua index cede405..bf14247 100644 --- a/advtrains_interlocking/signal_api.lua +++ b/advtrains_interlocking/signal_api.lua @@ -100,7 +100,8 @@ ndef.advtrains = { -- Determines how the signal behaves when routes are set. Only in effect when signal is assigned to a TCB. -- main: The signal is a possible endpoint for a train move route. Distant signals before it refer to it. -- shunt: The signal is a possible endpoint for a shunt move route. Ignored for distant signals. - -- distant, distant_repeater: When route is set, signal is always assigned its first main aspect. The next signal with role="main" is set as the remote signal. (currently no further distinction) + -- distant, distant_repeater: The next signal with role="main" is set as the remote signal. main_aspects may be undefined, the main aspect passed to apply_aspect is a dummy one in this case. + -- distant: if more than one distant signal is before a main signal, only the last one is assigned (but any number of distant_repeater signals are allowed) -- main_distant: Combination of main and distant - like "main", but additionally gets assigned to the next main like a "distant" -- end: like main, but signifies that it marks an end of track and trains cannot continue further. (currently no practical implications above main) } -- cgit v1.2.3