2021-04-11 17:51:01 -07:00
|
|
|
-- Custom door implementation because I don't want to depend on other mods for content.
|
|
|
|
-- Registers only 2 nodes per door. Relies on front and back faces being identical. Locked doors implemented via param2.
|
|
|
|
|
|
|
|
local function can_interact(pos, player)
|
|
|
|
local meta = minetest.get_meta(pos)
|
|
|
|
local owner = meta:get_string("owner")
|
|
|
|
-- Not locked, is owner, or has valid key
|
|
|
|
return owner == "" or player:get_player_name() == owner or meta:get_string("secret") == player:get_wielded_item():get_meta():get_string("secret")
|
|
|
|
end
|
|
|
|
|
|
|
|
local function toggle_door(pos)
|
|
|
|
local node = minetest.get_node(pos)
|
|
|
|
local meta = minetest.get_meta(pos)
|
|
|
|
|
|
|
|
local door, flip = node.name:match("^(.+_)(%w)$")
|
|
|
|
local yaw = minetest.dir_to_yaw(minetest.facedir_to_dir(node.param2))
|
|
|
|
local rot = minetest.dir_to_facedir(minetest.yaw_to_dir(yaw + math.rad(flip == "a" and -90 or 90)))
|
|
|
|
|
|
|
|
minetest.set_node({x = pos.x, y = pos.y + 1, z = pos.z}, {name = "greek:door_blank", param2 = rot})
|
|
|
|
minetest.swap_node(pos, {name = door .. (flip == "a" and "b" or "a"), param2 = rot + (meta:get_string("owner") ~= "" and 128 or 0)})
|
|
|
|
|
|
|
|
local state = (meta:get_int("state") + 1) % 2
|
|
|
|
meta:set_int("state", state)
|
2022-03-25 20:39:00 -07:00
|
|
|
if minetest.get_modpath("doors") then minetest.sound_play("doors_door_" .. ({"close", "open"})[state + 1], {pos = pos}, true) end
|
2021-04-11 17:51:01 -07:00
|
|
|
end
|
|
|
|
|
|
|
|
minetest.register_node("greek:door_blank", {
|
|
|
|
drawtype = "airlike",
|
2021-08-27 13:51:44 -07:00
|
|
|
paramtype = "light",
|
|
|
|
sunlight_propagates = true,
|
2021-04-11 17:51:01 -07:00
|
|
|
paramtype2 = "facedir",
|
2021-08-27 13:51:44 -07:00
|
|
|
walkable = true,
|
|
|
|
pointable = false,
|
|
|
|
diggable = false,
|
|
|
|
buildable_to = false,
|
|
|
|
floodable = false,
|
|
|
|
drop = "",
|
|
|
|
groups = {not_in_creative_inventory = 1},
|
2021-04-11 17:51:01 -07:00
|
|
|
collision_box = {
|
|
|
|
type = "fixed",
|
|
|
|
fixed = {-0.5, -0.5, -0.5, 0.5, 0.5, -6 / 16},
|
|
|
|
},
|
|
|
|
})
|
|
|
|
|
|
|
|
local door_count = 4
|
|
|
|
|
|
|
|
for i = 1, door_count do
|
|
|
|
local def = {
|
|
|
|
description = "Blue Door " .. i,
|
|
|
|
drawtype = "mesh",
|
|
|
|
mesh = "greek_door.obj",
|
|
|
|
tiles = {{name = "greek_door_" .. i .. ".png", backface_culling = true, color = "white"}},
|
|
|
|
overlay_tiles = {"greek_door_handle.png"},
|
|
|
|
paramtype = "light",
|
|
|
|
sunlight_propagates = true,
|
|
|
|
paramtype2 = "colorfacedir",
|
|
|
|
palette = "greek_door_palette.png",
|
|
|
|
selection_box = {
|
|
|
|
type = "fixed",
|
|
|
|
fixed = {-0.5, -0.5, -0.5, 0.5, 1.5, -6 / 16},
|
|
|
|
},
|
|
|
|
collision_box = {
|
|
|
|
type = "fixed",
|
|
|
|
fixed = {-0.5, -0.5, -0.5, 0.5, 1.5, -6 / 16},
|
|
|
|
},
|
|
|
|
groups = {choppy = 2, oddly_breakable_by_hand = 2, flammable = 2, door = 1},
|
|
|
|
on_rightclick = function(pos, _, clicker) if can_interact(pos, clicker) then toggle_door(pos) end end,
|
|
|
|
on_key_use = function(pos, player) if can_interact(pos, player) then toggle_door(pos) end end,
|
|
|
|
on_skeleton_key_use = function(pos, player, newsecret)
|
|
|
|
local meta = minetest.get_meta(pos)
|
|
|
|
local name = player:get_player_name()
|
|
|
|
local owner = meta:get_string("owner")
|
|
|
|
|
|
|
|
if owner ~= name then
|
|
|
|
if owner ~= "" then minetest.chat_send_player(name, "You do not own this door.") end
|
|
|
|
return
|
|
|
|
end
|
|
|
|
|
|
|
|
local secret = meta:get_string("secret")
|
|
|
|
secret = secret ~= "" and secret or newsecret
|
|
|
|
meta:set_string("secret", secret)
|
|
|
|
|
|
|
|
return secret
|
|
|
|
end,
|
|
|
|
on_punch = function(pos, node, puncher, pointed)
|
|
|
|
-- Allow binding a key to multiple doors
|
|
|
|
local stack = puncher:get_wielded_item()
|
|
|
|
print(stack:get_name())
|
|
|
|
if minetest.get_item_group(stack:get_name(), "key") == 1 then
|
|
|
|
local meta = minetest.get_meta(pos)
|
|
|
|
local name = puncher:get_player_name()
|
|
|
|
|
|
|
|
if meta:get_string("owner") == name then
|
|
|
|
local current = meta:get_string("secret")
|
|
|
|
local new = stack:get_meta():get_string("secret")
|
|
|
|
|
|
|
|
if current == "" then
|
|
|
|
meta:set_string("secret", new)
|
|
|
|
elseif current ~= new then
|
|
|
|
minetest.chat_send_player(name, "This door has already been bound to a key.")
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
minetest.node_punch(pos, node, puncher, pointed)
|
|
|
|
end,
|
|
|
|
on_rotate = function() return false end,
|
|
|
|
on_dig = function(pos, node, digger)
|
|
|
|
minetest.remove_node({x = pos.x, y = pos.y + 1, z = pos.z})
|
|
|
|
minetest.set_node({x = pos.x, y = pos.y + 1, z = pos.z}, {name = "air"})
|
|
|
|
return minetest.node_dig(pos, node, digger)
|
|
|
|
end,
|
|
|
|
on_blast = function(pos)
|
|
|
|
if minetest.get_meta(pos):get_string("owner") ~= "" then return end
|
|
|
|
local name = minetest.get_node(pos).name
|
2021-08-27 13:51:44 -07:00
|
|
|
minetest.remove_node(pos)
|
|
|
|
minetest.remove_node({x = pos.x, y = pos.y + 1, z = pos.z})
|
|
|
|
return {name}
|
|
|
|
end,
|
2021-04-11 17:51:01 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
do -- Register normal version
|
|
|
|
local defcopy = table.copy(def)
|
|
|
|
|
|
|
|
-- Check for obstructions and place invisible node
|
|
|
|
defcopy.on_place = function(itemstack, placer, pointed)
|
2021-08-27 13:51:44 -07:00
|
|
|
local pos
|
2021-04-11 17:51:01 -07:00
|
|
|
|
2021-08-27 13:51:44 -07:00
|
|
|
if pointed.type ~= "node" then return itemstack end
|
2021-04-11 17:51:01 -07:00
|
|
|
|
2021-08-27 13:51:44 -07:00
|
|
|
local node = minetest.get_node(pointed.under)
|
|
|
|
local pdef = minetest.registered_nodes[node.name]
|
2021-04-11 17:51:01 -07:00
|
|
|
|
|
|
|
if pdef and pdef.on_rightclick and not placer:get_player_control().sneak then
|
|
|
|
return pdef.on_rightclick(pointed.under, node, placer, itemstack, pointed)
|
|
|
|
end
|
|
|
|
|
2021-08-27 13:51:44 -07:00
|
|
|
if pdef and pdef.buildable_to then
|
|
|
|
pos = pointed.under
|
|
|
|
else
|
|
|
|
pos = pointed.above
|
|
|
|
node = minetest.get_node(pos)
|
|
|
|
pdef = minetest.registered_nodes[node.name]
|
|
|
|
if not pdef or not pdef.buildable_to then return itemstack end
|
|
|
|
end
|
2021-04-11 17:51:01 -07:00
|
|
|
|
2021-08-27 13:51:44 -07:00
|
|
|
local above = {x = pos.x, y = pos.y + 1, z = pos.z}
|
|
|
|
local top_node = minetest.get_node_or_nil(above)
|
|
|
|
local topdef = top_node and minetest.registered_nodes[top_node.name]
|
2021-04-11 17:51:01 -07:00
|
|
|
|
2021-08-27 13:51:44 -07:00
|
|
|
if not topdef or not topdef.buildable_to then return itemstack end
|
2021-04-11 17:51:01 -07:00
|
|
|
|
2021-08-27 13:51:44 -07:00
|
|
|
local pn = placer and placer:get_player_name() or ""
|
|
|
|
if minetest.is_protected(pos, pn) or minetest.is_protected(above, pn) then return itemstack end
|
2021-04-11 17:51:01 -07:00
|
|
|
|
2021-08-27 13:51:44 -07:00
|
|
|
return minetest.item_place_node(itemstack, placer, pointed)
|
|
|
|
end
|
2021-04-11 17:51:01 -07:00
|
|
|
|
|
|
|
-- Set metadata and rotate door
|
|
|
|
defcopy.after_place_node = function(pos, placer)
|
|
|
|
local node = minetest.get_node(pos)
|
|
|
|
local meta = minetest.get_meta(pos)
|
|
|
|
|
|
|
|
-- Check if door is locked
|
|
|
|
if math.floor(node.param2 / 32) >= 4 then
|
|
|
|
local name = placer:get_player_name()
|
|
|
|
meta:set_string("owner", name)
|
|
|
|
meta:set_string("infotext", "Blue Door\nOwned by " .. name)
|
|
|
|
end
|
|
|
|
|
|
|
|
meta:set_int("state", 0)
|
|
|
|
|
|
|
|
local dir = node.param2 % 32
|
|
|
|
local ref = {
|
|
|
|
{x = -1, y = 0, z = 0},
|
|
|
|
{x = 0, y = 0, z = 1},
|
|
|
|
{x = 1, y = 0, z = 0},
|
|
|
|
{x = 0, y = 0, z = -1},
|
|
|
|
}
|
|
|
|
|
|
|
|
local aside = {
|
|
|
|
x = pos.x + ref[dir + 1].x,
|
|
|
|
y = pos.y + ref[dir + 1].y,
|
|
|
|
z = pos.z + ref[dir + 1].z,
|
|
|
|
}
|
|
|
|
|
|
|
|
if minetest.get_item_group(minetest.get_node(aside).name, "door") == 1 then
|
|
|
|
minetest.swap_node(pos, {name = node.name:match("^(.+_)%w$") .. "b", param2 = node.param2})
|
|
|
|
end
|
|
|
|
|
|
|
|
minetest.set_node({x = pos.x, y = pos.y + 1, z = pos.z}, {name = "greek:door_blank", param2 = node.param2})
|
|
|
|
end
|
|
|
|
|
|
|
|
defcopy.color = "#242424"
|
|
|
|
|
|
|
|
-- Use overlay for door because it wont be colored
|
|
|
|
defcopy.inventory_overlay = "greek_door_" .. i .. "_inv.png"
|
|
|
|
defcopy.inventory_image = "greek_door_inv_handle.png"
|
|
|
|
|
|
|
|
defcopy.wield_overlay = "greek_door_" .. i .. "_inv.png"
|
|
|
|
defcopy.wield_image = "greek_door_inv_handle.png"
|
|
|
|
|
|
|
|
minetest.register_node("greek:door_" .. i .. "_a", defcopy)
|
|
|
|
end
|
|
|
|
|
|
|
|
do -- Register mirrored version (should not be obtainable normally)
|
|
|
|
local defcopy = table.copy(def)
|
|
|
|
-- Fancy flipping
|
|
|
|
local front = "([combine\\:16x32\\:0,0=%s\\^[transformFX)"
|
|
|
|
local back = "([combine\\:16x32\\:-16,0=%s\\^[transformFX)"
|
|
|
|
local sides = "([combine\\:4x32\\:-32,0=%s\\^[transformFX)"
|
|
|
|
local tops = "([combine\\:2x32\\:-36,0=%s\\^[transformFX)"
|
|
|
|
|
|
|
|
defcopy.tiles[1].name = (("[combine:38x32:0,0=%s:16,0=%s:32,0=%s:36,0=%s"):format(front, back, sides, tops):gsub("%%s", def.tiles[1].name))
|
|
|
|
defcopy.overlay_tiles = {(("[combine:38x32:0,0=([combine\\:16x32\\:0,0=%s\\^[transformFX):16,0=([combine\\:16x32\\:-16,0=%s\\^[transformFX)"):gsub("%%s", def.overlay_tiles[1]))}
|
|
|
|
|
|
|
|
defcopy.groups.not_in_creative_inventory = 1
|
|
|
|
|
|
|
|
defcopy.drop = "greek:door_" .. i .. "_a"
|
|
|
|
defcopy.preserve_metadata = function(_, node, oldmeta, drops)
|
|
|
|
-- Preserve locked state
|
|
|
|
if oldmeta.owner then
|
|
|
|
local meta = drops[1]:get_meta()
|
|
|
|
meta:set_int("palette_index", 128)
|
|
|
|
meta:set_string("description", "Locked " .. minetest.registered_items[node.name].description)
|
|
|
|
meta:set_string("color", "#dcdcdc")
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
minetest.register_node("greek:door_" .. i .. "_b", defcopy)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
greek.register_craftring("greek:door_%s_a", door_count)
|
|
|
|
|
|
|
|
for _, item in pairs(greek.settings_list("blue_wood")) do
|
|
|
|
-- Only bother registering our own if it is used
|
|
|
|
if item == "greek:blue_wood" then
|
|
|
|
greek.register_node_and_stairs("greek:blue_wood", {
|
|
|
|
description = "Blue Wood",
|
|
|
|
tiles = {"greek_blue_wood.png"},
|
|
|
|
groups = {choppy = 2, oddly_breakable_by_hand = 2, flammable = 2, wood = 2},
|
|
|
|
sounds = greek.default_sounds("node_sound_wood_defaults"),
|
|
|
|
})
|
|
|
|
|
|
|
|
minetest.register_craft({
|
|
|
|
output = "greek:blue_wood",
|
|
|
|
recipe = {"group:wood", "dye:blue"},
|
|
|
|
type = "shapeless",
|
|
|
|
})
|
|
|
|
end
|
|
|
|
|
|
|
|
greek.add_group(item, "blue_wood")
|
|
|
|
end
|
|
|
|
|
|
|
|
minetest.register_craft({
|
|
|
|
output = "greek:door_1_a 2",
|
|
|
|
recipe = {
|
|
|
|
{"group:greek:blue_wood", "group:greek:blue_wood"},
|
|
|
|
{"group:greek:blue_wood", "group:greek:blue_wood"},
|
|
|
|
{"group:greek:blue_wood", "group:greek:blue_wood"},
|
|
|
|
},
|
|
|
|
})
|
|
|
|
|
|
|
|
for _, item in pairs(greek.settings_list("door_lock")) do
|
|
|
|
greek.add_group(item, "door_lock")
|
|
|
|
end
|
|
|
|
|
|
|
|
minetest.register_craft({
|
|
|
|
output = ItemStack({
|
|
|
|
name = "greek:door_1_a",
|
|
|
|
meta = {
|
|
|
|
description = "Locked " .. minetest.registered_items["greek:door_1_a"].description,
|
|
|
|
color = "#dcdcdc",
|
|
|
|
palette_index = 128,
|
|
|
|
},
|
|
|
|
}):to_string(),
|
|
|
|
recipe = {"greek:door_1_a", "group:greek:door_lock"},
|
|
|
|
type = "shapeless",
|
|
|
|
})
|
|
|
|
|
|
|
|
local shutter_count = 3
|
|
|
|
|
|
|
|
for i = 1, shutter_count do
|
|
|
|
local def = {
|
|
|
|
description = "Blue Shutters " .. i,
|
|
|
|
drawtype = "mesh",
|
|
|
|
mesh = "greek_shutters.obj",
|
|
|
|
tiles = {{name = "greek_shutters_" .. i .. ".png", backface_culling = true}, "blank.png"},
|
|
|
|
paramtype = "light",
|
|
|
|
sunlight_propagates = true,
|
|
|
|
paramtype2 = "facedir",
|
|
|
|
selection_box = {
|
|
|
|
type = "fixed",
|
|
|
|
fixed = {-0.5, -0.5, 6 / 16, 0.5, 0.5, 0.5},
|
|
|
|
},
|
|
|
|
collision_box = {
|
|
|
|
type = "fixed",
|
|
|
|
fixed = {-0.5, -0.5, 6 / 16, 0.5, 0.5, 0.5},
|
|
|
|
},
|
|
|
|
groups = {choppy = 2, oddly_breakable_by_hand = 2, flammable = 2},
|
|
|
|
on_rightclick = function(pos, node)
|
|
|
|
minetest.swap_node(pos, {name = "greek:shutters_" .. i .. "_open", param2 = node.param2})
|
2022-03-25 20:39:00 -07:00
|
|
|
if minetest.get_modpath("doors") then minetest.sound_play("doors_door_open", {pos = pos}, true) end
|
2021-04-11 17:51:01 -07:00
|
|
|
end,
|
|
|
|
}
|
|
|
|
|
|
|
|
minetest.register_node("greek:shutters_" .. i, def)
|
|
|
|
|
|
|
|
def = table.copy(def)
|
|
|
|
def.tiles = {"blank.png", def.tiles[1]}
|
|
|
|
def.groups.not_in_creative_inventory = 1
|
|
|
|
def.drop = "greek:shutters_" .. i
|
|
|
|
def.on_rightclick = function(pos, node)
|
|
|
|
minetest.swap_node(pos, {name = "greek:shutters_" .. i, param2 = node.param2})
|
2022-03-25 20:39:00 -07:00
|
|
|
if minetest.get_modpath("doors") then minetest.sound_play("doors_door_close", {pos = pos}, true) end
|
2021-04-11 17:51:01 -07:00
|
|
|
end
|
|
|
|
|
|
|
|
minetest.register_node("greek:shutters_" .. i .. "_open", def)
|
|
|
|
end
|
|
|
|
|
|
|
|
greek.register_craftring("greek:shutters_%s", shutter_count)
|
|
|
|
|
|
|
|
minetest.register_craft({
|
|
|
|
output = "greek:shutters_1 2",
|
|
|
|
recipe = {
|
|
|
|
{"group:greek:blue_wood", "", "group:greek:blue_wood"},
|
|
|
|
{"group:greek:blue_wood", "", "group:greek:blue_wood"},
|
|
|
|
},
|
|
|
|
})
|