| | |
| | | -- A simple special-purpose class, this is used for building up sets of three-dimensional points for fast reference |
| | | |
| | | Pointset = {} |
| | | Pointset.__index = Pointset |
| | | |
| | | function Pointset.create() |
| | | local set = {} |
| | | setmetatable(set,Pointset) |
| | | set.points = {} |
| | | return set |
| | | end |
| | | |
| | | function Pointset:set(x, y, z, value) |
| | | -- sets a value in the 3D array "points". |
| | | if self.points[x] == nil then |
| | | self.points[x] = {} |
| | | end |
| | | if self.points[x][y] == nil then |
| | | self.points[x][y] = {} |
| | | end |
| | | self.points[x][y][z] = value |
| | | end |
| | | |
| | | function Pointset:set_if_not_in(excluded, x, y, z, value) |
| | | -- If a value is not already set for this point in the 3D array "excluded", set it in "points" |
| | | if excluded:get(x, y, z) ~= nil then |
| | | return |
| | | end |
| | | self:set(x, y, z, value) |
| | | end |
| | | |
| | | function Pointset:get(x, y, z) |
| | | -- return a value from the 3D array "points" |
| | | if self.points[x] == nil or self.points[x][y] == nil then |
| | | return nil |
| | | end |
| | | return self.points[x][y][z] |
| | | end |
| | | |
| | | function Pointset:set_pos(pos, value) |
| | | self:set(pos.x, pos.y, pos.z, value) |
| | | end |
| | | |
| | | function Pointset:set_pos_if_not_in(excluded, pos, value) |
| | | self:set_if_not_in(excluded, pos.x, pos.y, pos.z, value) |
| | | end |
| | | |
| | | function Pointset:get_pos(pos) |
| | | return self:get(pos.x, pos.y, pos.z) |
| | | end |
| | | |
| | | function Pointset:pop() |
| | | -- returns a point that's in the 3D array, and then removes it. |
| | | local pos = {} |
| | | local ytable |
| | | local ztable |
| | | local val |
| | | |
| | | local count = 0 |
| | | for _ in pairs(self.points) do count = count + 1 end |
| | | if count == 0 then |
| | | return nil |
| | | end |
| | | |
| | | pos.x, ytable = next(self.points) |
| | | pos.y, ztable = next(ytable) |
| | | pos.z, val = next(ztable) |
| | | |
| | | self.points[pos.x][pos.y][pos.z] = nil |
| | | |
| | | count = 0 |
| | | for _ in pairs(self.points[pos.x][pos.y]) do count = count + 1 end |
| | | if count == 0 then |
| | | self.points[pos.x][pos.y] = nil |
| | | end |
| | | |
| | | count = 0 |
| | | for _ in pairs(self.points[pos.x]) do count = count + 1 end |
| | | if count == 0 then |
| | | self.points[pos.x] = nil |
| | | end |
| | | |
| | | return pos, val |
| | | end |
| | | |
| | | function Pointset:get_pos_list(value) |
| | | -- Returns a list of all points with the given value in standard Minetest vector format. If no value is provided, returns all points |
| | | local outlist = {} |
| | | for x, ytable in ipairs(self.points) do |
| | | for y, ztable in ipairs(ytable) do |
| | | for z, val in ipairs(ztable) do |
| | | if (value == nil and val ~= nil ) or val == value then |
| | | table.insert(outlist, {x=x, y=y, z=z}) |
| | | end |
| | | end |
| | | end |
| | | end |
| | | return outlist |
| | | end |
| | | |
| | | |
| | | |
| | | -- Configuration |
| | | |
| | | local xnotreetrap_max_charge = 30000 -- Maximum charge of the saw |
| | | local xnotreetap_max_charge = 30000 -- Maximum charge of the saw |
| | | -- Gives 2500 nodes on a single charge (about 50 complete normal trees) |
| | | local xnotreetrap_charge_per_node = 12 |
| | | local xnotreetap_charge_per_node = 12 |
| | | -- Cut down tree leaves. Leaf decay may cause slowness on large trees |
| | | -- if this is disabled. |
| | | local xnotreetrap_leaves = true |
| | | local xnotreetap_leaves = true |
| | | |
| | | -- First value is node name; second is whether the node is considered even if chainsaw_leaves is false. |
| | | -- First value is node name; second is whether the node is considered even if xnotreetap_leaves is false. |
| | | local nodes = { |
| | | -- Rubber trees from moretrees or technic_worldgen if moretrees isn't installed |
| | | {"moretrees:rubber_tree_trunk_empty", true}, |
| | |
| | | {"moretrees:rubber_tree_leaves", false}, |
| | | } |
| | | |
| | | -- Remember node visited recursive and not dig twice |
| | | local nodeVisited = Pointset.create() |
| | | |
| | | local timber_nodenames = {} |
| | | for _, node in pairs(nodes) do |
| | | if chainsaw_leaves or node[2] then |
| | | if xnotreetap_leaves or node[2] then |
| | | timber_nodenames[node[1]] = true |
| | | end |
| | | end |
| | | |
| | | |
| | | local S = technic.getter |
| | | local mesecons_materials = minetest.get_modpath("mesecons_materials") |
| | | |
| | | technic.register_power_tool("technic:xnotreetap", xnotreetap_max_charge) |
| | | |
| | | local mesecons_materials = minetest.get_modpath("mesecons_materials") |
| | | |
| | | |
| | | -- This function checks if the specified node should be sawed |
| | | local function check_if_node_sawed(pos) |
| | | local node_name = minetest.get_node(pos).name |
| | | local node = minetest.get_node(pos) |
| | | local node_name = node.name |
| | | |
| | | if timber_nodenames[node_name] |
| | | or (xnotreetap_leaves and minetest.get_item_group(node_name, "leaves") ~= 0) |
| | | or minetest.get_item_group(node_name, "tree") ~= 0 then |
| | | minetest.log("action", "[Xno Tree Tap] "..node_name.." good node to collect.") --print to log |
| | | return true |
| | | end |
| | | |
| | |
| | | |
| | | -- Table for saving what was sawed down |
| | | local produced = {} |
| | | |
| | | local function myString (v) |
| | | return v.x.." "..v.y.." "..v.z.." " |
| | | end |
| | | |
| | | -- Save the items sawed down so that we can drop them in a nice single stack |
| | | local function handle_drops(drops) |
| | |
| | | end |
| | | end |
| | | |
| | | -- inserisco un valore in tabella |
| | | local function add_table(table, toadd) |
| | | table:set(toadd.x, toadd.y, toadd.z, true) |
| | | end |
| | | |
| | | -- bool controllo se un valore è presente in tabella |
| | | local function in_table(table, pos) |
| | | local val = table:get(pos.x, pos.y, pos.z) |
| | | local visited = 'NO' |
| | | |
| | | if val ~= nil then |
| | | if val then |
| | | visited = 'SI' |
| | | end |
| | | minetest.log("action", "[Xno Tree Tap] "..myString(pos).." visited? " .. visited) --print to log |
| | | return val |
| | | end |
| | | return false |
| | | end |
| | | |
| | | -- verifico se un nodo è nella tabella visitato |
| | | local function check_if_node_visited (pos) |
| | | return in_table(nodeVisited, pos) |
| | | end |
| | | |
| | | local function set_node_visited (pos) |
| | | minetest.log("action", "[Xno Tree Tap] "..myString(pos).." set node visited.") --print to log |
| | | add_table(nodeVisited, pos) |
| | | end |
| | | |
| | | -- This function does all the hard work. Recursively we dig the node at hand |
| | | -- if it is in the table and then search the surroundings for more stuff to dig. |
| | |
| | | if remaining_charge < xnotreetap_charge_per_node then |
| | | return remaining_charge |
| | | end |
| | | local node = minetest.get_node(pos) |
| | | |
| | | if check_if_node_visited(pos) then |
| | | return remaining_charge |
| | | end |
| | | |
| | | if not check_if_node_sawed(pos) then |
| | | return remaining_charge |
| | | end |
| | | |
| | | local node = minetest.get_node(pos) |
| | | |
| | | if node.name == "moretrees:rubber_tree_trunk" then |
| | | --raccolta gomma |
| | | node.name = "moretrees:rubber_tree_trunk_empty" |
| | | minetest.swap_node(pos, node) |
| | | minetest.handle_node_drops(pointed_thing.above, {"technic:raw_latex"}, user) |
| | | handle_drops(minetest.get_node_drops("technic:raw_latex", "")) |
| | | remaining_charge = remaining_charge - xnotreetap_charge_per_node |
| | | |
| | | -- Wood found - cut it |
| | | -- handle_drops(minetest.get_node_drops(node.name, "")) |
| | | -- minetest.remove_node(pos) |
| | | -- remaining_charge = remaining_charge - xnotreetap_charge_per_node |
| | | end |
| | | |
| | | if node.name == "moretrees:rubber_tree_leaves" then |
| | | -- Leaves found - cut it |
| | | handle_drops(minetest.get_node_drops(node.name, "")) |
| | | minetest.remove_node(pos) |
| | | remaining_charge = remaining_charge - xnotreetap_charge_per_node |
| | | |
| | | if not technic.creative_mode then |
| | | local item_wear = tonumber(itemstack:get_wear()) |
| | | item_wear = item_wear + 819 |
| | | if item_wear > 65535 then |
| | | itemstack:clear() |
| | | return itemstack |
| | | end |
| | | itemstack:set_wear(item_wear) |
| | | end |
| | | end |
| | | |
| | | set_node_visited(pos) |
| | | |
| | | -- Check surroundings and run recursively if any charge left |
| | | for npos in iterSawTries(pos) do |
| | |
| | | minetest.register_tool("technic:xnotreetap", { |
| | | description = S("Xno Tree Tap"), |
| | | inventory_image = "technic_tree_tap.png", |
| | | |
| | | stack_max = 1, |
| | | |
| | | wear_represents = "technic_RE_charge", |
| | | on_refill = technic.refill_RE_charge, |
| | | |
| | | on_use = function(itemstack, user, pointed_thing) |
| | | if pointed_thing.type ~= "node" then |
| | | return itemstack |
| | |
| | | return |
| | | end |
| | | |
| | | --raccolta gomma |
| | | -- node.name = "moretrees:rubber_tree_trunk_empty" |
| | | -- minetest.swap_node(pos, node) |
| | | -- minetest.handle_node_drops(pointed_thing.above, {"technic:raw_latex"}, user) |
| | | -- |
| | | -- if not technic.creative_mode then |
| | | -- local item_wear = tonumber(itemstack:get_wear()) |
| | | -- item_wear = item_wear + 819 |
| | | -- if item_wear > 65535 then |
| | | -- itemstack:clear() |
| | | -- return itemstack |
| | | -- end |
| | | -- itemstack:set_wear(item_wear) |
| | | -- end |
| | | -- return itemstack |
| | | |
| | | -- Send current charge to digging function so that the |
| | | -- chainsaw will stop after digging a number of nodes |
| | | meta.charge = xnotreetap_dig(pointed_thing.under, meta.charge) |
| | |
| | | }, |
| | | }) |
| | | |
| | | minetest.register_abm({ |
| | | label = "Tools: xno tree tap", |
| | | nodenames = {"moretrees:rubber_tree_trunk_empty"}, |
| | | interval = 60, |
| | | chance = 15, |
| | | action = function(pos, node) |
| | | if minetest.find_node_near(pos, (moretrees and moretrees.leafdecay_radius) or 5, {"moretrees:rubber_tree_leaves"}) then |
| | | node.name = "moretrees:rubber_tree_trunk" |
| | | minetest.swap_node(pos, node) |
| | | end |
| | | end |
| | | }) |
| | | |
| | | |
| | | |
| | | --minetest.register_abm({ |
| | | -- label = "Tools: xno tree tap", |
| | | -- nodenames = {"moretrees:rubber_tree_trunk_empty"}, |
| | | -- interval = 60, |
| | | -- chance = 15, |
| | | -- action = function(pos, node) |
| | | -- if minetest.find_node_near(pos, (moretrees and moretrees.leafdecay_radius) or 5, {"moretrees:rubber_tree_leaves"}) then |
| | | -- node.name = "moretrees:rubber_tree_trunk" |
| | | -- minetest.swap_node(pos, node) |
| | | -- end |
| | | -- end |
| | | --}) |
| | | |
| | | |
| | | |