mirror of
https://github.com/minetest-mods/digtron.git
synced 2024-07-07 08:15:22 +02:00
indicator entities for when Digtron can't be built
This commit is contained in:
parent
f14b0a9a42
commit
292889651c
201
entities.lua
Normal file
201
entities.lua
Normal file
@ -0,0 +1,201 @@
|
||||
-- The default minetest.add_entity crashes with an exception if you try adding an entity in an unloaded area
|
||||
-- this wrapper catches that exception and just ignores it.
|
||||
digtron.safe_add_entity = function(pos, name)
|
||||
success, ret = pcall(minetest.add_entity, pos, name)
|
||||
if success then return ret else return nil end
|
||||
end
|
||||
|
||||
local safe_add_entity = digtron.safe_add_entity
|
||||
|
||||
-------------------------------------------------------------------------------------------------
|
||||
-- For displaying where things get built under which periodicities
|
||||
|
||||
minetest.register_entity("digtron:marker", {
|
||||
initial_properties = {
|
||||
visual = "cube",
|
||||
visual_size = {x=1.05, y=1.05},
|
||||
textures = {"digtron_marker_side.png","digtron_marker_side.png","digtron_marker.png","digtron_marker.png","digtron_marker_side.png","digtron_marker_side.png"},
|
||||
collisionbox = {-0.525, -0.525, -0.525, 0.525, 0.525, 0.525},
|
||||
physical = false,
|
||||
},
|
||||
|
||||
on_activate = function(self, staticdata)
|
||||
minetest.after(5.0,
|
||||
function(self)
|
||||
self.object:remove()
|
||||
end,
|
||||
self)
|
||||
end,
|
||||
|
||||
on_rightclick=function(self, clicker)
|
||||
self.object:remove()
|
||||
end,
|
||||
|
||||
on_punch = function(self, hitter)
|
||||
self.object:remove()
|
||||
end,
|
||||
})
|
||||
|
||||
local vertical = {x=1.5708, y=0, z=0}
|
||||
-- TODO: update to new method of finding buildpos?
|
||||
-- TODO: add item indicator entity as well
|
||||
digtron.show_offset_markers = function(pos, offset, period)
|
||||
local buildpos = digtron.find_new_pos(pos, minetest.get_node(pos).param2)
|
||||
local x_pos = math.floor((buildpos.x+offset)/period)*period - offset
|
||||
safe_add_entity({x=x_pos, y=buildpos.y, z=buildpos.z}, "digtron:marker")
|
||||
if x_pos >= buildpos.x then
|
||||
safe_add_entity({x=x_pos - period, y=buildpos.y, z=buildpos.z}, "digtron:marker")
|
||||
end
|
||||
if x_pos <= buildpos.x then
|
||||
safe_add_entity({x=x_pos + period, y=buildpos.y, z=buildpos.z}, "digtron:marker")
|
||||
end
|
||||
|
||||
local y_pos = math.floor((buildpos.y+offset)/period)*period - offset
|
||||
local entity = safe_add_entity({x=buildpos.x, y=y_pos, z=buildpos.z}, "digtron:marker")
|
||||
if entity ~= nil then entity:set_rotation(vertical) end
|
||||
if y_pos >= buildpos.y then
|
||||
local entity = safe_add_entity({x=buildpos.x, y=y_pos - period, z=buildpos.z}, "digtron:marker")
|
||||
if entity ~= nil then entity:set_rotation(vertical) end
|
||||
end
|
||||
if y_pos <= buildpos.y then
|
||||
local entity = safe_add_entity({x=buildpos.x, y=y_pos + period, z=buildpos.z}, "digtron:marker")
|
||||
if entity ~= nil then entity:set_rotation(vertical) end
|
||||
end
|
||||
|
||||
local z_pos = math.floor((buildpos.z+offset)/period)*period - offset
|
||||
local entity = safe_add_entity({x=buildpos.x, y=buildpos.y, z=z_pos}, "digtron:marker")
|
||||
if entity ~= nil then entity:setyaw(1.5708) end
|
||||
if z_pos >= buildpos.z then
|
||||
local entity = safe_add_entity({x=buildpos.x, y=buildpos.y, z=z_pos - period}, "digtron:marker")
|
||||
if entity ~= nil then entity:setyaw(1.5708) end
|
||||
end
|
||||
if z_pos <= buildpos.z then
|
||||
local entity = safe_add_entity({x=buildpos.x, y=buildpos.y, z=z_pos + period}, "digtron:marker")
|
||||
if entity ~= nil then entity:setyaw(1.5708) end
|
||||
end
|
||||
end
|
||||
|
||||
-----------------------------------------------------------------------------------------------
|
||||
-- For displaying whether nodes are part of a digtron or are obstructed
|
||||
|
||||
minetest.register_entity("digtron:marker_crate_good", {
|
||||
initial_properties = {
|
||||
visual = "cube",
|
||||
visual_size = {x=1.05, y=1.05},
|
||||
textures = {"digtron_crate.png", "digtron_crate.png", "digtron_crate.png", "digtron_crate.png", "digtron_crate.png", "digtron_crate.png"},
|
||||
collisionbox = {-0.525, -0.525, -0.525, 0.525, 0.525, 0.525},
|
||||
physical = false,
|
||||
glow = minetest.LIGHT_MAX,
|
||||
},
|
||||
|
||||
on_activate = function(self, staticdata)
|
||||
minetest.after(digtron.config.marker_crate_good_duration,
|
||||
function(self)
|
||||
self.object:remove()
|
||||
end,
|
||||
self)
|
||||
end,
|
||||
|
||||
on_rightclick=function(self, clicker)
|
||||
self.object:remove()
|
||||
end,
|
||||
|
||||
on_punch = function(self, hitter)
|
||||
self.object:remove()
|
||||
end,
|
||||
})
|
||||
|
||||
minetest.register_entity("digtron:marker_crate_bad", {
|
||||
initial_properties = {
|
||||
visual = "cube",
|
||||
visual_size = {x=1.05, y=1.05},
|
||||
textures = {"digtron_no_entry.png", "digtron_no_entry.png", "digtron_no_entry.png", "digtron_no_entry.png", "digtron_no_entry.png", "digtron_no_entry.png"},
|
||||
collisionbox = {-0.525, -0.525, -0.525, 0.525, 0.525, 0.525},
|
||||
physical = false,
|
||||
glow = minetest.LIGHT_MAX,
|
||||
},
|
||||
|
||||
on_activate = function(self, staticdata)
|
||||
minetest.after(digtron.config.marker_crate_bad_duration,
|
||||
function(self)
|
||||
self.object:remove()
|
||||
end,
|
||||
self)
|
||||
end,
|
||||
|
||||
on_rightclick=function(self, clicker)
|
||||
self.object:remove()
|
||||
end,
|
||||
|
||||
on_punch = function(self, hitter)
|
||||
self.object:remove()
|
||||
end,
|
||||
})
|
||||
|
||||
-----------------------------------------------------------------------------------------------------------------
|
||||
-- Builder items
|
||||
|
||||
digtron.remove_builder_item = function(pos)
|
||||
local objects = minetest.env:get_objects_inside_radius(pos, 0.5)
|
||||
if objects ~= nil then
|
||||
for _, obj in ipairs(objects) do
|
||||
if obj and obj:get_luaentity() and obj:get_luaentity().name == "digtron:builder_item" then
|
||||
obj:remove()
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
digtron.update_builder_item = function(pos)
|
||||
digtron.remove_builder_item(pos)
|
||||
node_inventory_table.pos = pos
|
||||
local inv = minetest.get_inventory(node_inventory_table)
|
||||
local item_stack = inv:get_stack("main", 1)
|
||||
if not item_stack:is_empty() then
|
||||
digtron.create_builder_item = item_stack:get_name()
|
||||
minetest.add_entity(pos,"digtron:builder_item")
|
||||
end
|
||||
end
|
||||
|
||||
minetest.register_entity("digtron:builder_item", {
|
||||
|
||||
initial_properties = {
|
||||
hp_max = 1,
|
||||
is_visible = true,
|
||||
visual = "wielditem",
|
||||
visual_size = {x=0.25, y=0.25},
|
||||
collisionbox = {0,0,0,0,0,0},
|
||||
physical = false,
|
||||
textures = {""},
|
||||
automatic_rotate = math.pi * 0.25,
|
||||
},
|
||||
|
||||
on_activate = function(self, staticdata)
|
||||
local props = self.object:get_properties()
|
||||
if staticdata ~= nil and staticdata ~= "" then
|
||||
local pos = self.object:getpos()
|
||||
local node = minetest.get_node(pos)
|
||||
if minetest.get_node_group(node.name, "digtron") ~= 4 then
|
||||
-- We were reactivated without a builder node on our location, self-destruct
|
||||
self.object:remove()
|
||||
return
|
||||
end
|
||||
props.textures = {staticdata}
|
||||
self.object:set_properties(props)
|
||||
elseif digtron.create_builder_item ~= nil then
|
||||
props.textures = {digtron.create_builder_item}
|
||||
self.object:set_properties(props)
|
||||
digtron.create_builder_item = nil
|
||||
else
|
||||
self.object:remove()
|
||||
end
|
||||
end,
|
||||
|
||||
get_staticdata = function(self)
|
||||
local props = self.object:get_properties()
|
||||
if props ~= nil and props.textures ~= nil and props.textures[1] ~= nil then
|
||||
return props.textures[1]
|
||||
end
|
||||
return ""
|
||||
end,
|
||||
})
|
@ -469,10 +469,10 @@ digtron.remove_from_world = function(digtron_id, root_pos, player_name)
|
||||
minetest.bulk_set_node(nodes_to_destroy, {name="air"})
|
||||
end
|
||||
|
||||
digtron.build_to_world = function(digtron_id, root_pos, player_name)
|
||||
-- Tests if a Digtron can be built at the designated location
|
||||
digtron.is_buildable_to = function(digtron_id, root_pos, player_name, show_visualization)
|
||||
local layout = retrieve_layout(digtron_id)
|
||||
local root_hash = minetest.hash_node_position(root_pos)
|
||||
local nodes_to_create = {}
|
||||
|
||||
local permitted = true
|
||||
for hash, data in pairs(layout) do
|
||||
@ -482,34 +482,49 @@ digtron.build_to_world = function(digtron_id, root_pos, player_name)
|
||||
-- TODO: lots of testing needed here
|
||||
if not (node_def and node_def.buildable_to) then
|
||||
minetest.chat_send_all("not permitted due to " .. node.name .. " at " .. minetest.pos_to_string(node_pos))
|
||||
permitted = false
|
||||
break
|
||||
end
|
||||
end
|
||||
|
||||
if permitted then
|
||||
-- TODO: voxelmanip might be better here, less likely than with destroy though since metadata needs to be written
|
||||
for hash, data in pairs(layout) do
|
||||
local node_pos = minetest.get_position_from_hash(hash + root_hash - origin_hash)
|
||||
minetest.set_node(node_pos, data.node)
|
||||
local meta = minetest.get_meta(node_pos)
|
||||
for field, value in pairs(data.meta.fields) do
|
||||
meta:set_string(field, value)
|
||||
if not show_visualization then
|
||||
return false
|
||||
else
|
||||
permitted = false
|
||||
digtron.safe_add_entity(node_pos, "digtron:marker_crate_bad")
|
||||
end
|
||||
meta:set_string("digtron_id", digtron_id)
|
||||
meta:mark_as_private("digtron_id")
|
||||
-- Not needed - local inventories not used by active digtron, will be restored if disassembled
|
||||
-- local inv = meta:get_inventory()
|
||||
-- for listname, size in pairs(data.meta.inventory) do
|
||||
-- inv:set_size(listname, size)
|
||||
-- end
|
||||
elseif show_visualization then
|
||||
digtron.safe_add_entity(node_pos, "digtron:marker_crate_good")
|
||||
end
|
||||
local bbox = retrieve_bounding_box(digtron_id)
|
||||
persist_bounding_box(digtron_id, bbox)
|
||||
persist_pos(digtron_id, root_pos)
|
||||
end
|
||||
return permitted
|
||||
end
|
||||
|
||||
-- Places the Digtron into the world.
|
||||
digtron.build_to_world = function(digtron_id, root_pos, player_name)
|
||||
local layout = retrieve_layout(digtron_id)
|
||||
local root_hash = minetest.hash_node_position(root_pos)
|
||||
|
||||
if not digtron.is_buildable_to(digtron_id, root_pos, player_name, true) then
|
||||
return false
|
||||
end
|
||||
|
||||
return permitted
|
||||
-- TODO: voxelmanip might be better here, less likely than with destroy though since metadata needs to be written
|
||||
for hash, data in pairs(layout) do
|
||||
local node_pos = minetest.get_position_from_hash(hash + root_hash - origin_hash)
|
||||
minetest.set_node(node_pos, data.node)
|
||||
local meta = minetest.get_meta(node_pos)
|
||||
for field, value in pairs(data.meta.fields) do
|
||||
meta:set_string(field, value)
|
||||
end
|
||||
meta:set_string("digtron_id", digtron_id)
|
||||
meta:mark_as_private("digtron_id")
|
||||
-- Not needed - local inventories not used by active digtron, will be restored if disassembled
|
||||
-- local inv = meta:get_inventory()
|
||||
-- for listname, size in pairs(data.meta.inventory) do
|
||||
-- inv:set_size(listname, size)
|
||||
-- end
|
||||
end
|
||||
local bbox = retrieve_bounding_box(digtron_id)
|
||||
persist_bounding_box(digtron_id, bbox)
|
||||
persist_pos(digtron_id, root_pos)
|
||||
|
||||
return true
|
||||
end
|
||||
|
||||
---------------------------------------------------------------------------------
|
||||
|
6
init.lua
6
init.lua
@ -1,8 +1,14 @@
|
||||
digtron = {}
|
||||
digtron.doc = {}
|
||||
|
||||
digtron.config = {}
|
||||
|
||||
digtron.config.marker_crate_bad_duration = 5
|
||||
digtron.config.marker_crate_good_duration = 5
|
||||
|
||||
local modpath = minetest.get_modpath(minetest.get_current_modname())
|
||||
|
||||
dofile(modpath.."/entities.lua")
|
||||
dofile(modpath.."/functions.lua")
|
||||
dofile(modpath.."/controller.lua")
|
||||
dofile(modpath.."/nodes/node_misc.lua")
|
||||
|
Loading…
Reference in New Issue
Block a user