From e67151d3509b99c5d4158946c988d197da0b3037 Mon Sep 17 00:00:00 2001 From: BuckarooBanzay Date: Thu, 18 Feb 2021 14:00:58 +0100 Subject: [PATCH] create a fake user for "after_place_node" / various fixes --- create_fake_player.lua | 134 +++++++++++++++++++++++++++++++++++++++++ digiline.lua | 40 +++++++----- init.lua | 2 +- node.lua | 9 --- readme.md | 11 +--- recipe.lua | 4 +- 6 files changed, 165 insertions(+), 35 deletions(-) create mode 100644 create_fake_player.lua diff --git a/create_fake_player.lua b/create_fake_player.lua new file mode 100644 index 0000000..221767b --- /dev/null +++ b/create_fake_player.lua @@ -0,0 +1,134 @@ +-- borrowed from https://gitlab.com/VanessaE/pipeworks/-/blob/master/common.lua + +local function delay(...) + local args = {...} + return (function() return unpack(args) end) +end + +local function get_set_wrap(name, is_dynamic) + return (function(self) + return self["_" .. name] + end), (function(self, value) + if is_dynamic then + self["_" .. name] = type(value) == "table" + and table.copy(value) or value + end + end) +end + + +function digibuilder.create_fake_player(def, is_dynamic) + local wielded_item = ItemStack("") + if def.inventory and def.wield_list then + wielded_item = def.inventory:get_stack(def.wield_list, def.wield_index or 1) + end + local p = { + get_player_name = delay(def.name), + is_player = delay(true), + is_fake_player = true, + + _formspec = def.formspec or default.gui_survival_form, + _hp = def.hp or 20, + _breath = 11, + _pos = def.position and table.copy(def.position) or vector.new(), + _properties = def.properties or { eye_height = def.eye_height or 1.47 }, + _inventory = def.inventory, + _wield_index = def.wield_index or 1, + _wielded_item = wielded_item, + + -- Model and view + _eye_offset1 = vector.new(), + _eye_offset3 = vector.new(), + set_eye_offset = function(self, first, third) + self._eye_offset1 = table.copy(first) + self._eye_offset3 = table.copy(third) + end, + get_eye_offset = function(self) + return self._eye_offset1, self._eye_offset3 + end, + get_look_dir = delay(def.look_dir or {x=0, y=0, z=1}), + get_look_pitch = delay(def.look_pitch or 0), + get_look_yaw = delay(def.look_yaw or 0), + get_look_horizontal = delay(def.look_yaw or 0), + get_look_vertical = delay(-(def.look_pitch or 0)), + set_animation = delay(), + + -- Controls + get_player_control = delay({ + jump=false, right=false, left=false, LMB=false, RMB=false, + sneak=def.sneak, aux1=false, down=false, up=false + }), + get_player_control_bits = delay(def.sneak and 64 or 0), + + -- Inventory and ItemStacks + get_inventory = delay(def.inventory), + set_wielded_item = function(self, item) + if self._inventory and def.wield_list then + return self._inventory:set_stack(def.wield_list, + self._wield_index, item) + end + self._wielded_item = ItemStack(item) + end, + get_wielded_item = function(self) + if self._inventory and def.wield_list then + return self._inventory:get_stack(def.wield_list, + self._wield_index) + end + return ItemStack(self._wielded_item) + end, + get_wield_list = delay(def.wield_list), + + punch = delay(), + remove = delay(), + right_click = delay(), + set_attach = delay(), + set_detach = delay(), + set_bone_position = delay(), + hud_change = delay(), + } + -- Getter & setter functions + p.get_inventory_formspec, p.set_inventory_formspec + = get_set_wrap("formspec", is_dynamic) + p.get_breath, p.set_breath = get_set_wrap("breath", is_dynamic) + p.get_hp, p.set_hp = get_set_wrap("hp", is_dynamic) + p.get_pos, p.set_pos = get_set_wrap("pos", is_dynamic) + p.get_wield_index, p.set_wield_index = get_set_wrap("wield_index", true) + p.get_properties, p.set_properties = get_set_wrap("properties", false) + + -- For players, move_to and get_pos do the same + p.move_to = p.get_pos + + -- Backwards compatibilty + p.getpos = p.get_pos + p.setpos = p.set_pos + p.moveto = p.move_to + + -- TODO "implement" all these + -- set_armor_groups + -- get_armor_groups + -- get_animation + -- get_bone_position + -- get_player_velocity + -- set_look_pitch + -- set_look_yaw + -- set_physics_override + -- get_physics_override + -- hud_add + -- hud_remove + -- hud_get + -- hud_set_flags + -- hud_get_flags + -- hud_set_hotbar_itemcount + -- hud_get_hotbar_itemcount + -- hud_set_hotbar_image + -- hud_get_hotbar_image + -- hud_set_hotbar_selected_image + -- hud_get_hotbar_selected_image + -- hud_replace_builtin + -- set_sky + -- get_sky + -- override_day_night_ratio + -- get_day_night_ratio + -- set_local_animation + return p +end diff --git a/digiline.lua b/digiline.lua index b920e92..82b1488 100644 --- a/digiline.lua +++ b/digiline.lua @@ -35,7 +35,7 @@ function digibuilder.digiline_effector(pos, _, channel, msg) local node = digibuilder.get_node(absolute_pos) -- get and validate node definition - local node_def = minetest.registered_items[node.name] + local node_def = minetest.registered_nodes[node.name] if not node_def then digilines.receptor_send(pos, digibuilder.digiline_rules, set_channel, { pos = msg.pos, @@ -81,7 +81,7 @@ function digibuilder.digiline_effector(pos, _, channel, msg) local node = digibuilder.get_node(absolute_pos) -- get and validate node definition - local node_def = minetest.registered_items[node.name] + local node_def = minetest.registered_nodes[node.name] if not node_def then digilines.receptor_send(pos, digibuilder.digiline_rules, set_channel, { pos = msg.pos, @@ -91,7 +91,7 @@ function digibuilder.digiline_effector(pos, _, channel, msg) return end - local is_creative = meta:get_int("creative") == 1 + local is_creative = minetest.check_player_privs(owner, "creative") local inv = meta:get_inventory() @@ -118,7 +118,7 @@ function digibuilder.digiline_effector(pos, _, channel, msg) end -- get and validate place node definition - local place_node_def = minetest.registered_items[msg.name] + local place_node_def = minetest.registered_nodes[msg.name] if not place_node_def then digilines.receptor_send(pos, digibuilder.digiline_rules, set_channel, { pos = msg.pos, @@ -128,21 +128,12 @@ function digibuilder.digiline_effector(pos, _, channel, msg) return end - -- check if "after_place_node" is defined - if place_node_def.after_place_node then - digilines.receptor_send(pos, digibuilder.digiline_rules, set_channel, { - pos = msg.pos, - error = true, - message = "can't place complex node: '" .. msg.name .. "'" - }) - return - end - if not is_creative then -- remove item inv:remove_item("main", msg.name) end + -- only allow param2 setting for "facedir" types local param2 = tonumber(msg.param2) local enable_param2 = place_node_def.paramtype2 == "facedir" and param2 and param2 > 0 and param2 <= 255 @@ -163,6 +154,27 @@ function digibuilder.digiline_effector(pos, _, channel, msg) minetest.set_node(absolute_pos, place_node) + -- check if "after_place_node" is defined + if place_node_def.after_place_node then + local player = digibuilder.create_fake_player({ + name = owner + }) + + local pointed_thing = {} + pointed_thing.type = "node" + pointed_thing.above = {x=absolute_pos.x, y=absolute_pos.y, z=absolute_pos.z} + pointed_thing.under = {x=absolute_pos.x, y=absolute_pos.y - 1, z=absolute_pos.z} + + local itemstack = ItemStack() + + place_node_def.after_place_node(absolute_pos, player, itemstack, pointed_thing) + end + + -- check if the node is falling + if place_node_def.groups.falling_node then + minetest.check_for_falling(absolute_pos) + end + digilines.receptor_send(pos, digibuilder.digiline_rules, set_channel, { pos = msg.pos, name = place_node.name, diff --git a/init.lua b/init.lua index 8cbc8cf..a41bc17 100644 --- a/init.lua +++ b/init.lua @@ -6,8 +6,8 @@ digibuilder = { local MP = minetest.get_modpath("digibuilder") --- common functions dofile(MP.."/marker.lua") +dofile(MP.."/create_fake_player.lua") dofile(MP.."/formspec.lua") dofile(MP.."/digiline_rules.lua") dofile(MP.."/digiline_validate_pos.lua") diff --git a/node.lua b/node.lua index 37ccbdc..4e6f66b 100644 --- a/node.lua +++ b/node.lua @@ -49,15 +49,6 @@ minetest.register_node("digibuilder:digibuilder", { -- set owner local owner = placer:get_player_name() or "" meta:set_string("owner", owner) - - -- creative flag - local has_give = minetest.check_player_privs(owner, "give") - local has_creative = minetest.check_player_privs(owner, "creative") - if has_give or has_creative then - meta:set_int("creative", 1) - else - meta:set_int("creative", 0) - end end, on_construct = function(pos) diff --git a/readme.md b/readme.md index 84d21d0..dfe3868 100644 --- a/readme.md +++ b/readme.md @@ -5,12 +5,10 @@ Build nodes with digiline commands ![](https://github.com/BuckarooBanzay/digibuilder/workflows/luacheck/badge.svg) -State: **WIP** - # Settings -* **digibuilder.max_radius** max radius -* **digibuilder.setnode_delay** delay between setnode calls in seconds +* **digibuilder.max_radius** max radius, default: 15 nodes +* **digibuilder.setnode_delay** delay between setnode calls in seconds, default: 0.5 # Commands @@ -50,11 +48,6 @@ end For code examples for the `luacontroller` see the "examples" directory -# Open issues - -* [ ] `after_place_node(pos, placer, itemstack, pointed_thing)` compat (digtron mod?) -* [ ] Storage of read schematics/buildings - # License diff --git a/recipe.lua b/recipe.lua index 8cec74d..7733855 100644 --- a/recipe.lua +++ b/recipe.lua @@ -1,5 +1,5 @@ -if minetest.get_modpath("mesecons_luacontroller") then +if minetest.get_modpath("mesecons_luacontroller") and minetest.get_modpath("default") then local c = "mesecons_luacontroller:luacontroller0000" @@ -7,7 +7,7 @@ if minetest.get_modpath("mesecons_luacontroller") then output = "digibuilder:digibuilder", recipe = { {c,c,c}, - {c,c,c}, + {c,"default:diamondblock",c}, {c,c,c} } })