117 lines
4.6 KiB
Lua
117 lines
4.6 KiB
Lua
-- Removes a node without calling on on_destruct()
|
||
-- We use this to mess with bed nodes without causing unwanted recursion.
|
||
local function remove_no_destruct(pos)
|
||
minetest.swap_node(pos, {name = "air"})
|
||
minetest.remove_node(pos) -- Now clear the meta
|
||
minetest.check_for_falling(pos)
|
||
end
|
||
|
||
-- Everything is described as if dir=0
|
||
-- z+
|
||
-- /|\ w
|
||
-- | XXX h
|
||
-- +−−−−−−−−−−−> x+
|
||
-- {name,width,height,{cables_left,cables_right,cables_top,cables_bottom}}
|
||
components = {}
|
||
components["and"] = {2,3,{{"in_2",nil,"in_1"},{nil,"out",nil},nil,nil}}
|
||
components["switch"] = {2,1,{{"in"},{"out"},{"activate",nil},nil}}
|
||
components["demux"] = {2,8,{{nil,nil,nil,nil,nil,"in_3","in_2","in_1"},{"out_8","out_7","out_6","out_5","out_4","out_3","out_2","out_1"},nil,nil}}
|
||
|
||
|
||
-- componentsblocks["block"] = {name,x,y}
|
||
componentsblocks = {}
|
||
|
||
for name,cmp in pairs(components)
|
||
do
|
||
local w = cmp[1]
|
||
local h = cmp[2]
|
||
local cables = cmp[3]
|
||
|
||
for x=1,w do
|
||
for y=1,h do
|
||
|
||
local nodename = "logikraft:component_"..name.."_"..tostring(x).."_"..tostring(y)
|
||
minetest.register_node(nodename, {
|
||
drawtype = "block",
|
||
tiles = {
|
||
"component_"..name..".png",
|
||
"component.png",
|
||
((x==w) and (cables[2] and cables[2][y] and "component_port.png" or "component.png") or "component.png"), -- x+
|
||
((x==1) and (cables[1] and cables[1][y] and "component_port.png" or "component.png") or "component.png"), -- x-
|
||
((y==h) and (cables[3] and cables[3][x] and "component_port.png" or "component.png") or "component.png"), -- z+
|
||
((y==1) and (cables[4] and cables[4][x] and "component_port.png" or "component.png") or "component.png"), -- z-
|
||
},
|
||
groups = {circuitry = 1,dig_immediate = 3},
|
||
paramtype2 = "4dir",
|
||
inventory_image = (x == 1 and y == 1 and "component_"..name..".png") or nil,
|
||
drop = "logikraft:component_"..name.."_1_1",
|
||
on_place = (x == 1 and y == 1) and function(itemstack, placer, pointed_thing)
|
||
|
||
local under = pointed_thing.under
|
||
local node = minetest.get_node(under)
|
||
local udef = minetest.registered_nodes[node.name]
|
||
|
||
-- Rightclick is prioritary
|
||
if udef and udef.on_rightclick and
|
||
not (placer and placer:is_player() and
|
||
placer:get_player_control().sneak) then
|
||
return udef.on_rightclick(under, node, placer, itemstack,
|
||
pointed_thing) or itemstack
|
||
end
|
||
|
||
-- Pos will be the head location
|
||
local pos
|
||
if udef and udef.buildable_to then
|
||
pos = under
|
||
else
|
||
pos = pointed_thing.above
|
||
end
|
||
|
||
local dir8 = logikraft.vecTo8dir(placer:get_look_dir())
|
||
|
||
for i = 1,w do
|
||
for j = 1,h do
|
||
local loc = logikraft.addToPos8dir(dir8,pos,i-1,j-1)
|
||
local node_def = minetest.registered_nodes[minetest.get_node(loc).name]
|
||
if not node_def or not node_def.buildable_to then
|
||
-- Then we cannot build here
|
||
return itemstack
|
||
end
|
||
end
|
||
end
|
||
|
||
local dir4 = logikraft.dir8to4(dir8)
|
||
local invw = dir8 % 2 == 0
|
||
|
||
-- If we reached this point, we can build the component
|
||
for i = 1,w do
|
||
for j = 1,h do
|
||
local loc = logikraft.addToPos8dir(dir8,pos,invw and (w-i) or (i-1),j-1)
|
||
minetest.set_node(loc, {name = "logikraft:component_"..name.."_"..tostring(i).."_"..tostring(j), param2 = dir4})
|
||
end
|
||
end
|
||
|
||
if not minetest.is_creative_enabled(placer) then
|
||
itemstack:take_item()
|
||
end
|
||
return itemstack
|
||
end or nil,
|
||
on_destruct = function(pos)
|
||
|
||
local node = minetest.get_node(pos)
|
||
dir4 = node.param2
|
||
|
||
for i = 1,w do
|
||
for j = 1,h do
|
||
local loc = logikraft.addToPos4dir(dir4,pos,i-x,j-y)
|
||
remove_no_destruct(loc)
|
||
end
|
||
end
|
||
end
|
||
})
|
||
componentsblocks["nodename"] = {name,x,y}
|
||
end
|
||
end
|
||
|
||
minetest.register_alias("logikraft:component_"..name, "logikraft:component_"..name .. "_1_1")
|
||
end |