258 lines
7.3 KiB
Lua
258 lines
7.3 KiB
Lua
realdoors.electronic_defs = {}
|
|
|
|
realdoors.electronic_formspec = "size[16,4]" ..
|
|
"list[context;cardslot;1,1;1,1]" ..
|
|
"button[3,1;3,1;cardcheck;Use keycard]" ..
|
|
"list[context;cardslot;7,1;1,1;1]" ..
|
|
"button[9,1;3,1;carddup;Copy card]" ..
|
|
"button[13,1;3,1;cardadd;Add card]" ..
|
|
"button[13,2;3,1;cardrm;Remove card]" ..
|
|
"button[13,3;3,1;cardrst;Remove all cards]" ..
|
|
"button[1,3;3,1;close;Close door]" ..
|
|
"list[current_player;main;1,2;9,1]"
|
|
|
|
function table_contains(t, e)
|
|
for _, v in ipairs(t) do
|
|
if v == e then
|
|
return true
|
|
end
|
|
end
|
|
return false
|
|
end
|
|
|
|
function table_remove(t, e)
|
|
for k, v in ipairs(t) do
|
|
if v == e then
|
|
t[k] = nil
|
|
end
|
|
end
|
|
return t
|
|
end
|
|
|
|
realdoors.electronic_formspec_handler = function(pos, fields, sender)
|
|
local meta = minetest.get_meta(pos)
|
|
if fields.close then
|
|
if meta:get_string("state") == "open" then
|
|
realdoors.toggle(pos)
|
|
end
|
|
end
|
|
local inv = minetest.get_inventory({type = "node", pos = pos})
|
|
local cardstack = inv:get_stack("cardslot", 1)
|
|
if cardstack:get_name() ~= "realdoors:card" then return end
|
|
local key = cardstack:get_meta():get_string("id")
|
|
|
|
local reqkeys = minetest.deserialize(meta:get_string("keys")) or {}
|
|
|
|
if fields.carddup then
|
|
local dupstack = inv:get_stack("cardslot", 2)
|
|
if dupstack:get_name() ~= "realdoors:card_blank" then return end
|
|
dupstack:set_name("realdoors:card")
|
|
dupstack:get_meta():set_string("id", key)
|
|
inv:set_stack("cardslot", 2, dupstack)
|
|
return
|
|
end
|
|
if fields.cardadd then
|
|
local newstack = inv:get_stack("cardslot", 2)
|
|
if newstack:get_name() ~= "realdoors:card" then return end
|
|
if key == meta:get_string("key") then
|
|
table.insert(reqkeys, newstack:get_meta():get_string("id"))
|
|
meta:set_string("keys", minetest.serialize(reqkeys))
|
|
minetest.chat_send_player(sender:get_player_name(), "The following card has been added: " .. newstack:get_meta():get_string("id"))
|
|
minetest.sound_play("lockbeep_ok", {
|
|
pos = pos,
|
|
max_hear_distance = 8,
|
|
gain = 4.0,
|
|
})
|
|
else
|
|
minetest.chat_send_player(sender:get_player_name(), "Your keycard is not the correct master card")
|
|
minetest.sound_play("lockbeep_error", {
|
|
pos = pos,
|
|
max_hear_distance = 8,
|
|
gain = 4.0,
|
|
})
|
|
end
|
|
return
|
|
end
|
|
if fields.cardrm then
|
|
local newstack = inv:get_stack("cardslot", 2)
|
|
if newstack:get_name() ~= "realdoors:card" then return end
|
|
if key == meta:get_string("key") then
|
|
reqkeys = table_remove(reqkeys, newstack:get_meta():get_string("id"))
|
|
meta:set_string("keys", minetest.serialize(reqkeys))
|
|
minetest.chat_send_player(sender:get_player_name(), "The following card has been removed: " .. newstack:get_meta():get_string("id"))
|
|
minetest.sound_play("lockbeep_ok", {
|
|
pos = pos,
|
|
max_hear_distance = 8,
|
|
gain = 4.0,
|
|
})
|
|
else
|
|
minetest.chat_send_player(sender:get_player_name(), "Your keycard is not the correct master card")
|
|
minetest.sound_play("lockbeep_error", {
|
|
pos = pos,
|
|
max_hear_distance = 8,
|
|
gain = 4.0,
|
|
})
|
|
end
|
|
return
|
|
end
|
|
if fields.cardrst then
|
|
if key == meta:get_string("key") then
|
|
reqkeys = {}
|
|
meta:set_string("keys", minetest.serialize(reqkeys))
|
|
minetest.chat_send_player(sender:get_player_name(), "All cards except for the master card have been removed")
|
|
minetest.sound_play("lockbeep_ok", {
|
|
pos = pos,
|
|
max_hear_distance = 8,
|
|
gain = 4.0,
|
|
})
|
|
else
|
|
minetest.chat_send_player(sender:get_player_name(), "Your keycard is not the correct master card")
|
|
minetest.sound_play("lockbeep_error", {
|
|
pos = pos,
|
|
max_hear_distance = 8,
|
|
gain = 4.0,
|
|
})
|
|
end
|
|
return
|
|
end
|
|
if not fields.cardcheck then return end
|
|
if meta:get_string("key") == "" then
|
|
meta:set_string("key", key)
|
|
minetest.chat_send_player(sender:get_player_name(), "The following card is now the master card: " .. key)
|
|
minetest.sound_play("lockbeep_ok", {
|
|
pos = pos,
|
|
max_hear_distance = 8,
|
|
gain = 4.0,
|
|
})
|
|
return
|
|
end
|
|
if table_contains(reqkeys, key) then
|
|
realdoors.toggle(pos)
|
|
minetest.sound_play("lockbeep_ok", {
|
|
pos = pos,
|
|
max_hear_distance = 8,
|
|
gain = 4.0,
|
|
})
|
|
else
|
|
minetest.chat_send_player(sender:get_player_name(), "Your keycard is not valid")
|
|
minetest.sound_play("lockbeep_error", {
|
|
pos = pos,
|
|
max_hear_distance = 8,
|
|
gain = 4.0,
|
|
})
|
|
end
|
|
end
|
|
|
|
realdoors.register_electronic = function(def)
|
|
minetest.register_node("realdoors:edoor_" .. def.name .. "_a", {
|
|
description = def.desc .. " (left)",
|
|
drawtype = "mesh",
|
|
tiles = {def.tex},
|
|
inventory_image = def.tex_inv,
|
|
paramtype = "light",
|
|
paramtype2 = "facedir",
|
|
is_ground_content = false,
|
|
sunlight_propagates = false,
|
|
selection_box = {
|
|
type = "fixed",
|
|
fixed = {
|
|
{-0.5, -0.5, -0.5, 0.5, 1.5, -0.375},
|
|
},
|
|
},
|
|
collision_box = {
|
|
type = "fixed",
|
|
fixed = {
|
|
{-0.5, -0.5, -0.5, 0.5, 1.5, -0.375},
|
|
},
|
|
},
|
|
mesh = "realdoor_a.obj",
|
|
sounds = default.node_sound_wood_defaults(),
|
|
groups = {snappy = 3},
|
|
on_construct = function(pos)
|
|
minetest.get_meta(pos):set_string("state", "closed")
|
|
local inv = minetest.get_inventory({type = "node", pos = pos})
|
|
inv:set_size("cardslot", 2)
|
|
minetest.get_meta(pos):set_string("formspec", realdoors.electronic_formspec)
|
|
end,
|
|
on_receive_fields = function(pos, formname, fields, sender)
|
|
realdoors.electronic_formspec_handler(pos, fields, sender)
|
|
end,
|
|
})
|
|
minetest.register_node("realdoors:edoor_" .. def.name .. "_b", {
|
|
description = def.desc .. " (right)",
|
|
drawtype = "mesh",
|
|
tiles = {def.tex},
|
|
inventory_image = def.tex_inv,
|
|
paramtype = "light",
|
|
paramtype2 = "facedir",
|
|
is_ground_content = false,
|
|
sunlight_propagates = false,
|
|
selection_box = {
|
|
type = "fixed",
|
|
fixed = {
|
|
{-0.5, -0.5, -0.5, 0.5, 1.5, -0.375},
|
|
},
|
|
},
|
|
collision_box = {
|
|
type = "fixed",
|
|
fixed = {
|
|
{-0.5, -0.5, -0.5, 0.5, 1.5, -0.375},
|
|
},
|
|
},
|
|
mesh = "realdoor_b.obj",
|
|
sounds = default.node_sound_wood_defaults(),
|
|
groups = {snappy = 3},
|
|
on_construct = function(pos)
|
|
minetest.get_meta(pos):set_string("state", "closed")
|
|
local inv = minetest.get_inventory({type = "node", pos = pos})
|
|
inv:set_size("cardslot", 2)
|
|
minetest.get_meta(pos):set_string("formspec", realdoors.electronic_formspec)
|
|
end,
|
|
on_receive_fields = function(pos, formname, fields, sender)
|
|
realdoors.electronic_formspec_handler(pos, fields, sender)
|
|
end,
|
|
})
|
|
realdoors.electronic_defs[def.name] = def
|
|
end
|
|
|
|
realdoors.init_card = function(itemstack, id)
|
|
if not id then
|
|
math.randomseed(os.clock())
|
|
id = math.random(111111111, 999999999)
|
|
end
|
|
local meta = itemstack:get_meta()
|
|
meta:set_string("id", tostring(id))
|
|
return itemstack
|
|
end
|
|
|
|
minetest.register_craftitem("realdoors:card_blank", {
|
|
description = "Blank keycard",
|
|
inventory_image = "card_blank.png",
|
|
})
|
|
minetest.register_craftitem("realdoors:card", {
|
|
description = "Keycard",
|
|
inventory_image = "realdoors_card.png",
|
|
})
|
|
|
|
minetest.register_craft({
|
|
type = "shaped",
|
|
output = "realdoors:card_blank",
|
|
recipe = {
|
|
{"default:paper"},
|
|
{"default:mese_crystal"},
|
|
{"default:paper"},
|
|
},
|
|
})
|
|
minetest.register_craft({
|
|
type = "shapeless",
|
|
output = "realdoors:card",
|
|
recipe = {"realdoors:card_blank", "default:mese_crystal"},
|
|
})
|
|
|
|
minetest.register_on_craft(function(itemstack, player, old_craft_grid, craft_inv)
|
|
if itemstack:get_name() ~= "realdoors:card" then return end
|
|
return realdoors.init_card(itemstack)
|
|
end)
|
|
|
|
minetest.log("verbose", "[realdoors] Loaded electronic.lua v" .. realdoors.v)
|