Compare commits
5 Commits
c6eed37729
...
cfc84dee9e
Author | SHA1 | Date |
---|---|---|
VanessaE | cfc84dee9e | |
Vanessa Ezekowitz | accc09e983 | |
Vanessa Ezekowitz | fa57a07e29 | |
Vanessa Ezekowitz | e352d7870c | |
Vanessa Ezekowitz | 55e8eb95d8 |
|
@ -1 +1,2 @@
|
|||
default
|
||||
intllib?
|
||||
|
|
184
init.lua
184
init.lua
|
@ -5,12 +5,12 @@ autoclose_doors = {}
|
|||
|
||||
-- Boilerplate to support localized strings if intllib mod is installed.
|
||||
local S
|
||||
if autoclose_doors.intllib_modpath then
|
||||
dofile(autoclose_doors.intllib_modpath.."/intllib.lua")
|
||||
S = intllib.Getter(minetest.get_current_modname())
|
||||
if minetest.get_modpath("intllib") then
|
||||
S = intllib.Getter()
|
||||
else
|
||||
S = function ( s ) return s end
|
||||
S = function(s) return s end
|
||||
end
|
||||
|
||||
autoclose_doors.gettext = S
|
||||
|
||||
--
|
||||
|
@ -27,145 +27,18 @@ end
|
|||
local modpath = minetest.get_modpath("autoclose_doors")
|
||||
dofile(modpath.."/door_models.lua")
|
||||
|
||||
-- the good stuff!
|
||||
-- check if a door is marked as closed
|
||||
|
||||
local function isSolid(pos,adj)
|
||||
local adj = {x=adj[1],y=adj[2],z=adj[3]}
|
||||
local node = minetest.get_node(vector.add(pos,adj))
|
||||
if node then
|
||||
local idef = minetest.registered_nodes[minetest.get_node(vector.add(pos,adj)).name]
|
||||
if idef then
|
||||
return idef.walkable
|
||||
end
|
||||
end
|
||||
return false
|
||||
end
|
||||
|
||||
local function countSolids(pos,node,level)
|
||||
local solids = 0
|
||||
for x = -1, 1 do
|
||||
for z = -1, 1 do
|
||||
local y = 0
|
||||
if node.param2 == 5 then
|
||||
y = -level
|
||||
else
|
||||
y = level
|
||||
end
|
||||
-- special cases when x == z == 0
|
||||
if x == 0 and z == 0 then
|
||||
if level == 1 then
|
||||
-- when looking past the trap door, cannot be solid in center
|
||||
if isSolid(pos,{x,y,z}) then
|
||||
return false
|
||||
end
|
||||
-- no else. it doesn't matter if x == y == z is solid, that's us.
|
||||
end
|
||||
elseif isSolid(pos,{x,y,z}) then
|
||||
solids = solids + 1
|
||||
end
|
||||
end
|
||||
end
|
||||
return solids
|
||||
end
|
||||
|
||||
local function calculateClosed(pos)
|
||||
local node = minetest.get_node(pos)
|
||||
-- the door is considered closed if it is closing off something.
|
||||
|
||||
local solids = 0
|
||||
local direction = node.param2 % 6
|
||||
local isTrap = direction == 0 or direction == 5
|
||||
if isTrap then
|
||||
-- the trap door is considered closed when all nodes on its sides are solid
|
||||
-- or all nodes in the 3x3 above/below it are solid except the center
|
||||
for level = 0, 1 do
|
||||
local fail = false
|
||||
local solids = countSolids(pos,node,level)
|
||||
if solids == 8 then
|
||||
return true
|
||||
end
|
||||
end
|
||||
return false
|
||||
else
|
||||
-- the door is considered closed when the nodes on its sides are solid
|
||||
-- or the 3 nodes in its facing direction are solid nonsolid solid
|
||||
|
||||
-- sorry I dunno the math to figure whether to x or z
|
||||
if direction == 1 or direction == 2 then
|
||||
if isSolid(pos,{0,0,-1}) and isSolid(pos,{0,0,1}) then
|
||||
if string.find(node.name,'_bottom_') then
|
||||
return calculateClosed({x=pos.x,y=pos.y+1,z=pos.z})
|
||||
else
|
||||
return true
|
||||
end
|
||||
end
|
||||
local x
|
||||
if direction == 1 then
|
||||
x = 1
|
||||
else
|
||||
x = -1
|
||||
end
|
||||
if isSolid(pos,{x,0,-1}) and not isSolid(pos,{x,0,0}) and isSolid(pos,{x,0,1}) then
|
||||
if string.find(node.name,'_bottom_') then
|
||||
return calculateClosed({x=pos.x,y=pos.y+1,z=pos.z})
|
||||
else
|
||||
return true
|
||||
end
|
||||
end
|
||||
return false
|
||||
else
|
||||
-- direction == 3 or 4
|
||||
if isSolid(pos,{-1,0,0}) and isSolid(pos,{1,0,0}) then
|
||||
if string.find(node.name,'_bottom_') then
|
||||
return calculateClosed({x=pos.x,y=pos.y+1,z=pos.z})
|
||||
else
|
||||
return true
|
||||
end
|
||||
end
|
||||
local z
|
||||
if direction == 3 then
|
||||
z = 1
|
||||
else
|
||||
z = -1
|
||||
end
|
||||
if isSolid(pos,{-1,0,z}) and not isSolid(pos,{0,0,z}) and isSolid(pos,{1,0,z}) then
|
||||
if string.find(node.name,'_bottom_') then
|
||||
return calculateClosed({x=pos.x,y=pos.y+1,z=pos.z})
|
||||
else
|
||||
return true
|
||||
end
|
||||
end
|
||||
return false
|
||||
end
|
||||
error("What direction is this???",direction)
|
||||
end
|
||||
end
|
||||
|
||||
-- isClosed flag, is 0 or 1 0 = open, 1 = closed
|
||||
local function getClosed(pos)
|
||||
local isClosed = minetest.get_meta(pos):get_string('closed')
|
||||
if isClosed=='' then
|
||||
if calculateClosed(pos) then
|
||||
return true
|
||||
else
|
||||
return false
|
||||
end
|
||||
else
|
||||
isClosed = tonumber(isClosed)
|
||||
-- may be closed or open (1 or 0)
|
||||
return isClosed == 1
|
||||
end
|
||||
local c = minetest.get_meta(pos):get_string("closed")
|
||||
if c == "true" then
|
||||
return true
|
||||
else
|
||||
return false
|
||||
end
|
||||
end
|
||||
|
||||
local function addDoorNode(pos,def,isClosed)
|
||||
if isClosed then
|
||||
isClosed = 1
|
||||
else
|
||||
isClosed = 0
|
||||
end
|
||||
minetest.add_node(pos, def)
|
||||
minetest.get_meta(pos):set_int('closed',isClosed)
|
||||
end
|
||||
-- register the nodes
|
||||
|
||||
local sides = {"left", "right"}
|
||||
local rsides = {"right", "left"}
|
||||
|
@ -284,24 +157,17 @@ for i in ipairs(sides) do
|
|||
on_rightclick = function(pos, node, clicker)
|
||||
autoclose_doors.flip_door(pos, node, clicker, doorname, side)
|
||||
end,
|
||||
-- both left and right doors may be used for open or closed doors
|
||||
-- so they have to have both action_on and action_off and just
|
||||
-- check when that action is invoked if to continue
|
||||
|
||||
on_punch = function(pos, node, puncher)
|
||||
minetest.get_meta(pos):set_string('closed',nil)
|
||||
end,
|
||||
drop = "autoclose_doors:"..doorname.."_bottom_left",
|
||||
mesecons = {
|
||||
effector = {
|
||||
action_on = function(pos,node)
|
||||
local isClosed = getClosed(pos)
|
||||
local isClosed = getClosed(pos)
|
||||
if isClosed then
|
||||
autoclose_doors.flip_door(pos,node,nil,doorname,side,isClosed)
|
||||
end
|
||||
end,
|
||||
action_off = function(pos,node)
|
||||
local isClosed = getClosed(pos)
|
||||
local isClosed = getClosed(pos)
|
||||
if not isClosed then
|
||||
autoclose_doors.flip_door(pos,node,nil,doorname,side,isClosed)
|
||||
end
|
||||
|
@ -374,8 +240,9 @@ function autoclose_doors.place_door(itemstack, placer, pointed_thing, name, forc
|
|||
end
|
||||
|
||||
local def = { name = "autoclose_doors:"..name.."_bottom_"..side, param2=fdir}
|
||||
addDoorNode(pos1, def, true)
|
||||
minetest.add_node(pos1, { name = "autoclose_doors:"..name.."_bottom_"..side, param2=fdir })
|
||||
minetest.add_node(pos2, { name = "autoclose_doors:"..name.."_top_"..side, param2=fdir})
|
||||
minetest.get_meta(pos1):set_string("closed", "true")
|
||||
if not autoclose_doors.expect_infinite_stacks then
|
||||
itemstack:take_item()
|
||||
return itemstack
|
||||
|
@ -389,9 +256,11 @@ end
|
|||
-- also adjusting param2 so the node is at 90 degrees.
|
||||
|
||||
function autoclose_doors.flip_door(pos, node, player, name, side, isClosed)
|
||||
if isClosed == nil then
|
||||
isClosed = getClosed(pos)
|
||||
end
|
||||
|
||||
if isClosed == nil then
|
||||
isClosed = getClosed(pos)
|
||||
end
|
||||
|
||||
-- this is where we swap the isClosed status!
|
||||
-- i.e. if isClosed, we're adding an open door
|
||||
-- and if not isClosed, a closed door
|
||||
|
@ -422,12 +291,13 @@ function autoclose_doors.flip_door(pos, node, player, name, side, isClosed)
|
|||
})
|
||||
-- XXX: does the top half have to remember open/closed too?
|
||||
minetest.add_node({x=pos.x, y=pos.y+1, z=pos.z}, { name = "autoclose_doors:"..name.."_top_"..rside, param2=nfdir})
|
||||
minetest.add_node(pos, { name = "autoclose_doors:"..name.."_bottom_"..rside, param2=nfdir })
|
||||
|
||||
addDoorNode(pos,{ name = "autoclose_doors:"..name.."_bottom_"..rside, param2=nfdir },isClosed)
|
||||
|
||||
local timer = minetest.get_node_timer(pos)
|
||||
if not isClosed then
|
||||
timer:start(10)
|
||||
if isClosed then
|
||||
minetest.get_meta(pos):set_string("closed", "true")
|
||||
else
|
||||
minetest.get_node_timer(pos):start(10)
|
||||
minetest.get_meta(pos):set_string("closed", "false")
|
||||
end
|
||||
end
|
||||
|
||||
|
|
Loading…
Reference in New Issue