mirror of
https://github.com/minetest-mods/mesecons.git
synced 2025-02-05 12:30:20 +01:00
fix: the effector action can not be triggered when effector with conductor
This commit is contained in:
parent
fef402e88a
commit
a6a769aff6
@ -127,6 +127,67 @@ do
|
||||
end
|
||||
end
|
||||
|
||||
-- Utility node: this effector with conductor is used to test outputs.
|
||||
do
|
||||
local _rules = {
|
||||
{x = 1, y = 0, z = 0, name = "000001"},
|
||||
{x = -1, y = 0, z = 0, name = "000010"},
|
||||
{x = 0, y = 1, z = 0, name = "000100"},
|
||||
{x = 0, y = -1, z = 0, name = "001000"},
|
||||
{x = 0, y = 0, z = 1, name = "010000"},
|
||||
{x = 0, y = 0, z = -1, name = "100000"},
|
||||
}
|
||||
-- This is a list of actions in the form {<kind>, <pos>},
|
||||
-- where <kind> is "on", "off", or "overheat".
|
||||
mesecon._test_eff_conductor_events = {}
|
||||
local function action_on(pos, node)
|
||||
table.insert(mesecon._test_eff_conductor_events, {"on", pos})
|
||||
minetest.swap_node(pos, {name = "mesecons:test_effect_conductor_on", param2 = node.param2})
|
||||
end
|
||||
local function action_off(pos, node)
|
||||
table.insert(mesecon._test_eff_conductor_events, {"off", pos})
|
||||
minetest.swap_node(pos, {name = "mesecons:test_effect_conductor_off", param2 = node.param2})
|
||||
end
|
||||
local function action_change(pos, node, rule_name, new_state)
|
||||
if mesecon.do_overheat(pos) then
|
||||
table.insert(mesecon._test_eff_conductor_events, {"overheat", pos})
|
||||
minetest.remove_node(pos)
|
||||
return
|
||||
end
|
||||
-- minetest.swap_node(pos, node)
|
||||
end
|
||||
local off_spec = {
|
||||
effector = {
|
||||
rules = _rules,
|
||||
action_on = action_on,
|
||||
action_off = action_off,
|
||||
action_change = action_change,
|
||||
},
|
||||
conductor = {
|
||||
state = mesecon.state.off,
|
||||
rules = _rules,
|
||||
onstate = "mesecons:test_effect_conductor_on",
|
||||
}
|
||||
}
|
||||
local on_spec = {
|
||||
effector = {
|
||||
rules = _rules,
|
||||
action_on = action_on,
|
||||
action_off = action_off,
|
||||
action_change = action_change,
|
||||
},
|
||||
conductor = {
|
||||
state = mesecon.state.on,
|
||||
rules = _rules,
|
||||
offstate = "mesecons:test_effect_conductor_off",
|
||||
}
|
||||
}
|
||||
mesecon.register_node("mesecons:test_effect_conductor", {
|
||||
description = "Test Effector With Conductor",
|
||||
}, {mesecons = off_spec}, {mesecons = on_spec})
|
||||
end
|
||||
|
||||
|
||||
mesecon._test_autoconnects = {}
|
||||
mesecon.register_autoconnect_hook("test", function(pos, node)
|
||||
table.insert(mesecon._test_autoconnects, {pos, node})
|
||||
|
@ -84,6 +84,7 @@ function mesecon.get_any_outputrules(node)
|
||||
end
|
||||
end
|
||||
|
||||
-- TODO: howto get the rules when conductor has rules and effector has rules
|
||||
function mesecon.get_any_inputrules(node)
|
||||
if not node then return nil end
|
||||
|
||||
@ -433,10 +434,14 @@ function mesecon.turnon(pos, link)
|
||||
if not node then
|
||||
-- Area does not exist; do nothing
|
||||
pos_can_be_skipped[minetest.hash_node_position(f.pos)] = true
|
||||
elseif mesecon.is_conductor(node.name) then
|
||||
else
|
||||
local processed = false
|
||||
local isEffector = mesecon.is_effector(node.name)
|
||||
local isOff = true
|
||||
if mesecon.is_conductor(node.name) then
|
||||
local rules = mesecon.conductor_get_rules(node)
|
||||
|
||||
if mesecon.is_conductor_off(node, f.link) then
|
||||
isOff = mesecon.is_conductor_off(node, f.link)
|
||||
if isOff then
|
||||
-- Call turnon on neighbors
|
||||
for _, r in ipairs(mesecon.rule2meta(f.link, rules)) do
|
||||
local np = vector.add(f.pos, r)
|
||||
@ -451,16 +456,16 @@ function mesecon.turnon(pos, link)
|
||||
end
|
||||
|
||||
-- Only conductors with flat rules can be reliably skipped later
|
||||
if not rules[1] or rules[1].x then
|
||||
pos_can_be_skipped[minetest.hash_node_position(f.pos)] = true
|
||||
processed = rules[1] and not rules[1].x
|
||||
end
|
||||
elseif mesecon.is_effector(node.name) then
|
||||
if isEffector and isOff then
|
||||
processed = true
|
||||
mesecon.changesignal(f.pos, node, f.link, mesecon.state.on, depth)
|
||||
if mesecon.is_effector_off(node.name) then
|
||||
mesecon.activate(f.pos, node, f.link, depth)
|
||||
end
|
||||
else
|
||||
pos_can_be_skipped[minetest.hash_node_position(f.pos)] = true
|
||||
end
|
||||
if not processed then pos_can_be_skipped[minetest.hash_node_position(f.pos)] = true end
|
||||
end
|
||||
depth = depth + 1
|
||||
end
|
||||
@ -497,10 +502,14 @@ function mesecon.turnoff(pos, link)
|
||||
if not node then
|
||||
-- Area does not exist; do nothing
|
||||
pos_can_be_skipped[minetest.hash_node_position(f.pos)] = true
|
||||
elseif mesecon.is_conductor(node.name) then
|
||||
else
|
||||
local processed = false
|
||||
local isEffector = mesecon.is_effector(node.name)
|
||||
local isOn = true
|
||||
if mesecon.is_conductor(node.name) then
|
||||
local rules = mesecon.conductor_get_rules(node)
|
||||
|
||||
if mesecon.is_conductor_on(node, f.link) then
|
||||
isOn = mesecon.is_conductor_on(node, f.link)
|
||||
if isOn then
|
||||
for _, r in ipairs(mesecon.rule2meta(f.link, rules)) do
|
||||
local np = vector.add(f.pos, r)
|
||||
|
||||
@ -525,18 +534,19 @@ function mesecon.turnoff(pos, link)
|
||||
end
|
||||
|
||||
-- Only conductors with flat rules can be reliably skipped later
|
||||
if not rules[1] or rules[1].x then
|
||||
pos_can_be_skipped[minetest.hash_node_position(f.pos)] = true
|
||||
processed = rules[1] and not rules[1].x
|
||||
end
|
||||
elseif mesecon.is_effector(node.name) then
|
||||
|
||||
if isEffector and isOn then
|
||||
processed = true
|
||||
table.insert(signals, {
|
||||
pos = f.pos,
|
||||
node = node,
|
||||
link = f.link,
|
||||
depth = depth
|
||||
})
|
||||
else
|
||||
pos_can_be_skipped[minetest.hash_node_position(f.pos)] = true
|
||||
end
|
||||
if not processed then pos_can_be_skipped[minetest.hash_node_position(f.pos)] = true end
|
||||
end
|
||||
depth = depth + 1
|
||||
end
|
||||
|
42
mesecons/spec/effector_conductor_spec.lua
Normal file
42
mesecons/spec/effector_conductor_spec.lua
Normal file
@ -0,0 +1,42 @@
|
||||
require("mineunit")
|
||||
|
||||
fixture("mesecons")
|
||||
|
||||
|
||||
describe("action effector with conductor", function()
|
||||
local layout = {
|
||||
{{x = 1, y = 0, z = 0}, "mesecons:test_receptor_off"},
|
||||
{{x = 0, y = 0, z = 0}, "mesecons:test_conductor_off"},
|
||||
{{x = 0, y = 1, z = 0}, "mesecons:test_effect_conductor_off"},
|
||||
{{x = 0, y = 2, z = 0}, "mesecons:test_effect_conductor_off"},
|
||||
}
|
||||
|
||||
before_each(function()
|
||||
world.layout(layout)
|
||||
end)
|
||||
|
||||
after_each(function()
|
||||
mesecon._test_reset()
|
||||
world.clear()
|
||||
end)
|
||||
|
||||
it("executes in order", function()
|
||||
world.set_node(layout[1][1], "mesecons:test_receptor_on")
|
||||
mesecon.receptor_on(layout[1][1], mesecon.rules.alldirs)
|
||||
mineunit:execute_globalstep() -- Execute receptor_on action
|
||||
mineunit:execute_globalstep() -- Execute activate/change actions
|
||||
assert.equal(2, #mesecon._test_eff_conductor_events)
|
||||
assert.same({"on", layout[3][1]}, mesecon._test_eff_conductor_events[1])
|
||||
assert.same({"on", layout[4][1]}, mesecon._test_eff_conductor_events[2])
|
||||
world.set_node(layout[1][1], "mesecons:test_receptor_off")
|
||||
mesecon.receptor_off(layout[1][1], mesecon.rules.alldirs)
|
||||
mineunit:execute_globalstep() -- Execute receptor_off action
|
||||
mineunit:execute_globalstep() -- Execute deactivate/change actions
|
||||
assert.equal(4, #mesecon._test_eff_conductor_events)
|
||||
assert.same({"off", layout[3][1]}, mesecon._test_eff_conductor_events[3])
|
||||
assert.same({"off", layout[4][1]}, mesecon._test_eff_conductor_events[4])
|
||||
|
||||
end)
|
||||
|
||||
|
||||
end)
|
Loading…
Reference in New Issue
Block a user