Update utils

This commit is contained in:
Starbeamrainbowlabs 2022-09-18 17:32:13 +01:00
parent 58a7629ea1
commit 6f3118036d
No known key found for this signature in database
GPG Key ID: 1BE5172E637709C2
31 changed files with 179 additions and 136 deletions

@ -1,8 +1,11 @@
local wea_c = worldeditadditions_core
--- Prints a 2d array of numbers formatted like a JS TypedArray (e.g. like a manip node list or a convolutional kernel) --- Prints a 2d array of numbers formatted like a JS TypedArray (e.g. like a manip node list or a convolutional kernel)
-- In other words, the numbers should be formatted as a single flat array. -- In other words, the numbers should be formatted as a single flat array.
-- @param tbl number[] The ZERO-indexed list of numbers -- @param tbl number[] The ZERO-indexed list of numbers
-- @param width number The width of 2D array. -- @param width number The width of 2D array.
function worldeditadditions.format.array_2d(tbl, width) local function format_array_2d(tbl, width)
print("==== count: "..(#tbl+1)..", width:"..width.." ====") print("==== count: "..(#tbl+1)..", width:"..width.." ====")
local display_width = 1 local display_width = 1
for _i,value in pairs(tbl) do for _i,value in pairs(tbl) do
@ -11,10 +14,12 @@ function worldeditadditions.format.array_2d(tbl, width)
display_width = display_width + 2 display_width = display_width + 2
local next = {} local next = {}
for i=0, #tbl do for i=0, #tbl do
table.insert(next, worldeditadditions.str_padstart(tostring(tbl[i]), display_width)) table.insert(next, wea_c.str_padstart(tostring(tbl[i]), display_width))
if #next == width then if #next == width then
print(table.concat(next, "")) print(table.concat(next, ""))
next = {} next = {}
end end
end end
end end
return format_array_2d

@ -4,10 +4,12 @@
-- @param n number The number to format. -- @param n number The number to format.
-- @param decimals number The number of decimal places to show. -- @param decimals number The number of decimal places to show.
-- @return string A formatted string that represents the given input number. -- @return string A formatted string that represents the given input number.
function worldeditadditions.format.human_size(n, decimals) local function format_human_size(n, decimals)
local sizes = { "", "K", "M", "G", "T", "P", "E", "Y", "Z" } local sizes = { "", "K", "M", "G", "T", "P", "E", "Y", "Z" }
local factor = math.floor((#tostring(n) - 1) / 3) local factor = math.floor((#tostring(n) - 1) / 3)
local multiplier = 10^(decimals or 0) local multiplier = 10^(decimals or 0)
local result = math.floor(0.5 + (n / (1000 ^ factor)) * multiplier) / multiplier local result = math.floor(0.5 + (n / (1000 ^ factor)) * multiplier) / multiplier
return result .. sizes[factor+1] return result .. sizes[factor+1]
end end
return format_human_size

@ -3,7 +3,7 @@
-- Ported from PHP human_time from Pepperminty Wiki: https://github.com/sbrl/Pepperminty-Wiki/blob/fa81f0d/core/05-functions.php#L82-L104 -- Ported from PHP human_time from Pepperminty Wiki: https://github.com/sbrl/Pepperminty-Wiki/blob/fa81f0d/core/05-functions.php#L82-L104
-- @param ms float The number of milliseconds to convert. -- @param ms float The number of milliseconds to convert.
-- @return string A human-readable string representing the input ms. -- @return string A human-readable string representing the input ms.
function worldeditadditions.format.human_time(ms) local function format_human_time(ms)
if type(ms) ~= "number" then return "unknown" end if type(ms) ~= "number" then return "unknown" end
local tokens = { local tokens = {
{ 31536000 * 1000, 'year' }, { 31536000 * 1000, 'year' },
@ -26,3 +26,6 @@ function worldeditadditions.format.human_time(ms)
end end
end end
end end
return format_human_time

@ -1,8 +1,12 @@
worldeditadditions.format = {} local wea_c = worldeditadditions_core
wea_c.format = {
array_2d = dofile(wea_c.modpath.."/utils/format/array_2d.lua"),
human_size = dofile(wea_c.modpath.."/utils/format/human_size.lua"),
human_time = dofile(wea_c.modpath.."/utils/format/human_time.lua"),
node_distribution = dofile(wea_c.modpath.."/utils/format/node_distribution.lua"),
make_ascii_table = dofile(wea_c.modpath.."/utils/format/make_ascii_table.lua"),
map = dofile(wea_c.modpath.."/utils/format/map.lua"),
}
dofile(worldeditadditions.modpath.."/utils/format/array_2d.lua")
dofile(worldeditadditions.modpath.."/utils/format/node_distribution.lua")
dofile(worldeditadditions.modpath.."/utils/format/make_ascii_table.lua")
dofile(worldeditadditions.modpath.."/utils/format/map.lua")
dofile(worldeditadditions.modpath.."/utils/format/human_time.lua")
dofile(worldeditadditions.modpath.."/utils/format/human_size.lua")

@ -1,3 +1,4 @@
local wea_c = worldeditadditions_core
--- Makes a human-readable table of data. --- Makes a human-readable table of data.
-- Data should be a 2D array - i.e. a table of tables. The nested tables should -- Data should be a 2D array - i.e. a table of tables. The nested tables should
@ -6,7 +7,7 @@
-- useful when you want to print a node list. -- useful when you want to print a node list.
-- @param data table[] A table of tables. Each subtable is a single row of the tabulated output. -- @param data table[] A table of tables. Each subtable is a single row of the tabulated output.
-- @returns string The input table of tables formatted into a nice ASCII table. -- @returns string The input table of tables formatted into a nice ASCII table.
function worldeditadditions.format.make_ascii_table(data) local function format_make_ascii_table(data)
local extra_padding = 2 local extra_padding = 2
local result = {} local result = {}
local max_lengths = {} local max_lengths = {}
@ -22,7 +23,7 @@ function worldeditadditions.format.make_ascii_table(data)
for _key, row in ipairs(data) do for _key, row in ipairs(data) do
local row_result = {} local row_result = {}
for i = 1, #row, 1 do for i = 1, #row, 1 do
row_result[#row_result + 1] = worldeditadditions.str_padend(tostring(row[i]), max_lengths[i], " ") row_result[#row_result + 1] = wea_c.str_padend(tostring(row[i]), max_lengths[i], " ")
end end
result[#result+1] = table.concat(row_result, "") result[#result+1] = table.concat(row_result, "")
end end
@ -30,3 +31,5 @@ function worldeditadditions.format.make_ascii_table(data)
-- TODO: Add multi-column support here -- TODO: Add multi-column support here
return table.concat(result, "\n") return table.concat(result, "\n")
end end
return format_make_ascii_table

@ -1,10 +1,13 @@
--- Formats a key-value table of values as a string. --- Formats a key-value table of values as a string.
-- @param map table The table of key-value pairs to format. -- @param map table The table of key-value pairs to format.
-- @returns string The given table of key-value pairs formatted as a string. -- @returns string The given table of key-value pairs formatted as a string.
function worldeditadditions.format.map(map) local function format_map(map)
local result = {} local result = {}
for key, value in pairs(map) do for key, value in pairs(map) do
table.insert(result, key.."\t"..tostring(value)) table.insert(result, key.."\t"..tostring(value))
end end
return table.concat(result, "\n") return table.concat(result, "\n")
end end
return format_map

@ -1,18 +1,19 @@
local wea_c = worldeditadditions_core
--- Turns an associative node_id → count table into a human-readable list. --- Turns an associative node_id → count table into a human-readable list.
-- @param distribution table A node distribution in the format { node_name = count, .... }. -- @param distribution table A node distribution in the format { node_name = count, .... }.
-- @param nodes_total number The total number of nodes in the distribution. -- @param nodes_total number The total number of nodes in the distribution.
-- @param add_total bool Whether to add a grand total to the bottom or not. Default: no -- @param add_total bool Whether to add a grand total to the bottom or not. Default: no
function worldeditadditions.format.node_distribution(distribution, nodes_total, add_total) local function format_node_distribution(distribution, nodes_total, add_total)
local distribution_data = {} local distribution_data = {}
for node_id, count in pairs(distribution) do for node_id, count in pairs(distribution) do
table.insert(distribution_data, { table.insert(distribution_data, {
count, count,
tostring(worldeditadditions.round((count / nodes_total) * 100, 2)).."%", tostring(wea_c.round((count / nodes_total) * 100, 2)).."%",
minetest.get_name_from_content_id(node_id) minetest.get_name_from_content_id(node_id)
}) })
end end
local result = worldeditadditions.format.make_ascii_table(distribution_data) local result = wea_c.format.make_ascii_table(distribution_data)
if add_total == true then if add_total == true then
result = result.."\n"..string.rep("=", 6 + #tostring(nodes_total) + 6).."\n".. result = result.."\n"..string.rep("=", 6 + #tostring(nodes_total) + 6).."\n"..
@ -21,3 +22,5 @@ function worldeditadditions.format.node_distribution(distribution, nodes_total,
return result return result
end end
return format_node_distribution

@ -1,6 +1,6 @@
local Queue local Queue
if worldeditadditions then if worldeditadditions_core then
Queue = dofile(worldeditadditions.modpath.."/utils/queue.lua") Queue = dofile(worldeditadditions_core.modpath.."/utils/queue.lua")
else else
Queue = require("queue") Queue = require("queue")
end end

@ -1,4 +1,4 @@
local wea = worldeditadditions local wea_c = worldeditadditions_core
-- ███████ █████ ██████ ███████ -- ███████ █████ ██████ ███████
@ -72,7 +72,7 @@ function Mesh.dedupe(self)
for j,face_next in ipairs(self.faces) do for j,face_next in ipairs(self.faces) do
if i ~= j -- If we're not comparing a face to itself... if i ~= j -- If we're not comparing a face to itself...
and face_check == face_next -- ....and the 2 faces are equal.... and face_check == face_next -- ....and the 2 faces are equal....
and not wea.table.contains(toremove, j) then -- ...and we haven't already marked it for removal... and not wea_c.table.contains(toremove, j) then -- ...and we haven't already marked it for removal...
-- Mark it for removal -- Mark it for removal
table.insert(toremove, j) table.insert(toremove, j)
end end

@ -1,3 +1,6 @@
local wea_c = worldeditadditions_core
local node_id_air = minetest.get_content_id("air") local node_id_air = minetest.get_content_id("air")
local node_id_ignore = minetest.get_content_id("ignore") local node_id_ignore = minetest.get_content_id("ignore")
@ -5,7 +8,7 @@ local node_id_ignore = minetest.get_content_id("ignore")
-- It is recommended that the result of this function be cached. -- It is recommended that the result of this function be cached.
-- @param id number The content/node id to check. -- @param id number The content/node id to check.
-- @return bool Whether the given node/content id is an airlike node or not. -- @return bool Whether the given node/content id is an airlike node or not.
function worldeditadditions.is_airlike(id) function wea_c.is_airlike(id)
-- Do a fast check against air and ignore -- Do a fast check against air and ignore
if id == node_id_air then if id == node_id_air then
return true return true
@ -25,7 +28,7 @@ function worldeditadditions.is_airlike(id)
return true return true
end end
-- Just in case -- Just in case
if worldeditadditions.str_starts(name, "wielded_light") then if wea_c.str_starts(name, "wielded_light") then
return true return true
end end
-- Just in case -- Just in case
@ -36,7 +39,7 @@ end
-- It is recommended that the result of this function be cached. -- It is recommended that the result of this function be cached.
-- @param id number The content/node id to check. -- @param id number The content/node id to check.
-- @return bool Whether the given node/content id is a liquid-ish node or not. -- @return bool Whether the given node/content id is a liquid-ish node or not.
function worldeditadditions.is_liquidlike(id) function wea_c.is_liquidlike(id)
-- print("[is_liquidlike]") -- print("[is_liquidlike]")
if id == node_id_ignore then return false end if id == node_id_ignore then return false end
@ -56,7 +59,7 @@ end
-- It is recommended that the result of this function be cached. -- It is recommended that the result of this function be cached.
-- @param id number The content/node id to check. -- @param id number The content/node id to check.
-- @return bool Whether the given node/content id is a sapling or not. -- @return bool Whether the given node/content id is a sapling or not.
function worldeditadditions.is_sapling(id) function wea_c.is_sapling(id)
local node_name = minetest.get_name_from_content_id(id) local node_name = minetest.get_name_from_content_id(id)
return minetest.get_item_group(node_name, "sapling") ~= 0 return minetest.get_item_group(node_name, "sapling") ~= 0
end end
@ -81,7 +84,7 @@ local sapling_aliases = {}
-- @param sapling_node_name string The canonical name of the sapling. -- @param sapling_node_name string The canonical name of the sapling.
-- @param alias string The alias name of the sapling. -- @param alias string The alias name of the sapling.
-- @returns bool[,string] Whether the alias registration was successful or not. If false, then an error message as a string is also returned as the second value. -- @returns bool[,string] Whether the alias registration was successful or not. If false, then an error message as a string is also returned as the second value.
function worldeditadditions.register_sapling_alias(sapling_node_name, alias) function wea_c.register_sapling_alias(sapling_node_name, alias)
if sapling_aliases[sapling_node_name] ~= nil then if sapling_aliases[sapling_node_name] ~= nil then
return false, "Error: An alias against the node name '"..sapling_node_name.."' already exists." return false, "Error: An alias against the node name '"..sapling_node_name.."' already exists."
end end
@ -91,9 +94,9 @@ end
--- Convenience function to register many sapling aliases at once. --- Convenience function to register many sapling aliases at once.
-- @param tbl [string, string][] A list of tables containing exactly 2 strings in the form { sapling_node_name, alias }. -- @param tbl [string, string][] A list of tables containing exactly 2 strings in the form { sapling_node_name, alias }.
-- @returns bool[,string] Whether the alias registrations were successful or not. If false, then an error message as a string is also returned as the second value. -- @returns bool[,string] Whether the alias registrations were successful or not. If false, then an error message as a string is also returned as the second value.
function worldeditadditions.register_sapling_alias_many(tbl) function wea_c.register_sapling_alias_many(tbl)
for i, next in ipairs(tbl) do for i, next in ipairs(tbl) do
local success, msg = worldeditadditions.register_sapling_alias( local success, msg = wea_c.register_sapling_alias(
next[1], next[1],
next[2] next[2]
) )
@ -103,14 +106,14 @@ function worldeditadditions.register_sapling_alias_many(tbl)
end end
--- Returns the current key ⇒ value table of sapling names and aliases. --- Returns the current key ⇒ value table of sapling names and aliases.
-- @return table -- @return table
function worldeditadditions.get_all_sapling_aliases() function wea_c.get_all_sapling_aliases()
return sapling_aliases return sapling_aliases
end end
--- Attempts to normalise a sapling name using the currently registered aliases. --- Attempts to normalise a sapling name using the currently registered aliases.
-- @param in_name string The sapling name to normalise -- @param in_name string The sapling name to normalise
-- @param return_nil_on_failure bool Whether to return nil if we fail to resolve the sapling name with an alias, or return the original node name instead (default: false). -- @param return_nil_on_failure bool Whether to return nil if we fail to resolve the sapling name with an alias, or return the original node name instead (default: false).
function worldeditadditions.normalise_saplingname(in_name, return_nil_on_failure) function wea_c.normalise_saplingname(in_name, return_nil_on_failure)
if sapling_aliases[in_name] then return sapling_aliases[in_name] if sapling_aliases[in_name] then return sapling_aliases[in_name]
elseif return_nil_on_failure then return nil elseif return_nil_on_failure then return nil
else return in_name end else return in_name end

@ -1,6 +1,8 @@
local wea_c = worldeditadditions_core
--- Makes an associative table of node_name => weight into a list of node ids. --- Makes an associative table of node_name => weight into a list of node ids.
-- Node names with a higher weight are repeated more times. -- Node names with a higher weight are repeated more times.
function worldeditadditions.make_weighted(tbl) function wea_c.make_weighted(tbl)
local result = {} local result = {}
for node_name, weight in pairs(tbl) do for node_name, weight in pairs(tbl) do
local next_id = minetest.get_content_id(node_name) local next_id = minetest.get_content_id(node_name)
@ -17,7 +19,7 @@ end
-- (e.g. an entry with a weight of 2 will be repeated twice). -- (e.g. an entry with a weight of 2 will be repeated twice).
-- @param list table[] The list to unwind. -- @param list table[] The list to unwind.
-- @return number[],number The unwound list of node ids, follows by the number of node ids in total. -- @return number[],number The unwound list of node ids, follows by the number of node ids in total.
function worldeditadditions.unwind_node_list(list) function wea_c.unwind_node_list(list)
local result = {} local result = {}
for i,item in ipairs(list) do for i,item in ipairs(list) do
local node_id = minetest.get_content_id(item.node) local node_id = minetest.get_content_id(item.node)
@ -28,7 +30,7 @@ function worldeditadditions.unwind_node_list(list)
return result, #result return result, #result
end end
function worldeditadditions.registered_nodes_by_group(group) function wea_c.registered_nodes_by_group(group)
local result = {} local result = {}
for name, def in pairs(minetest.registered_nodes) do for name, def in pairs(minetest.registered_nodes) do
if def.groups[group] then if def.groups[group] then
@ -39,7 +41,7 @@ function worldeditadditions.registered_nodes_by_group(group)
end end
--- Turns a node_name → weight table into a list of { node_name, weight } tables. --- Turns a node_name → weight table into a list of { node_name, weight } tables.
function worldeditadditions.weighted_to_list(node_weights) function wea_c.weighted_to_list(node_weights)
local result = {} local result = {}
for node_name, weight in pairs(node_weights) do for node_name, weight in pairs(node_weights) do
table.insert(result, { node_name, weight }) table.insert(result, { node_name, weight })
@ -80,7 +82,7 @@ end
-- @param {Vector} pos2 The second position defining the area to emerge. -- @param {Vector} pos2 The second position defining the area to emerge.
-- @param {function} callback The callback to call when the emerging process is complete. -- @param {function} callback The callback to call when the emerging process is complete.
-- @param {any} callback_state A state object to pass to the callback as a 2nd parameter (the 1st parameter is the emerge_area progress tracking state object) -- @param {any} callback_state A state object to pass to the callback as a 2nd parameter (the 1st parameter is the emerge_area progress tracking state object)
function worldeditadditions.emerge_area(pos1, pos2, callback, callback_state) function wea_c.emerge_area(pos1, pos2, callback, callback_state)
local state = { local state = {
stats = { cancelled = 0, error = 0, from_memory = 0, from_disk = 0, generated = 0 }, stats = { cancelled = 0, error = 0, from_memory = 0, from_disk = 0, generated = 0 },
callback = callback, callback = callback,

@ -1,16 +1,18 @@
local wea_c = worldeditadditions_core
-- From http://lua-users.org/wiki/SimpleRound -- From http://lua-users.org/wiki/SimpleRound
function worldeditadditions.round(num, numDecimalPlaces) function wea_c.round(num, numDecimalPlaces)
local mult = 10^(numDecimalPlaces or 0) local mult = 10^(numDecimalPlaces or 0)
return math.floor(num * mult + 0.5) / mult return math.floor(num * mult + 0.5) / mult
end end
function worldeditadditions.hypotenuse(x1, y1, x2, y2) function wea_c.hypotenuse(x1, y1, x2, y2)
local xSquare = (x1 - x2) ^ 2; local xSquare = (x1 - x2) ^ 2;
local ySquare = (y1 - y2) ^ 2; local ySquare = (y1 - y2) ^ 2;
return math.sqrt(xSquare + ySquare); return math.sqrt(xSquare + ySquare);
end end
function worldeditadditions.sum(list) function wea_c.sum(list)
if #list == 0 then return 0 end if #list == 0 then return 0 end
local sum = 0 local sum = 0
for i,value in ipairs(list) do for i,value in ipairs(list) do
@ -22,15 +24,15 @@ end
--- Calculates the mean of all the numbers in the given list. --- Calculates the mean of all the numbers in the given list.
-- @param list number[] The list (table) of numbers to calculate the mean for. -- @param list number[] The list (table) of numbers to calculate the mean for.
-- @returns The mean of the numbers in the given table. -- @returns The mean of the numbers in the given table.
function worldeditadditions.average(list) function wea_c.average(list)
if #list == 0 then return 0 end if #list == 0 then return 0 end
return worldeditadditions.sum(list) / #list return wea_c.sum(list) / #list
end end
--- Finds the minimum value in the given list. --- Finds the minimum value in the given list.
-- @param list number[] The list (table) of numbers to find the minimum value of. -- @param list number[] The list (table) of numbers to find the minimum value of.
-- @returns number The minimum value in the given list. -- @returns number The minimum value in the given list.
function worldeditadditions.min(list) function wea_c.min(list)
if #list == 0 then return nil end if #list == 0 then return nil end
local min = nil local min = nil
for i,value in pairs(list) do for i,value in pairs(list) do
@ -44,7 +46,7 @@ end
--- Finds the maximum value in the given list. --- Finds the maximum value in the given list.
-- @param list number[] The list (table) of numbers to find the maximum value of. -- @param list number[] The list (table) of numbers to find the maximum value of.
-- @returns number The maximum value in the given list. -- @returns number The maximum value in the given list.
function worldeditadditions.max(list) function wea_c.max(list)
if #list == 0 then return nil end if #list == 0 then return nil end
-- We use pairs() instead of ipairs() here, because then we can support -- We use pairs() instead of ipairs() here, because then we can support
-- zero-indexed 1D heightmaps too - and we don't care that the order is -- zero-indexed 1D heightmaps too - and we don't care that the order is
@ -61,7 +63,7 @@ end
--- Returns the minetest.get_us_time() in ms --- Returns the minetest.get_us_time() in ms
-- @return float -- @return float
function worldeditadditions.get_ms_time() function wea_c.get_ms_time()
return minetest.get_us_time() / 1000 return minetest.get_us_time() / 1000
end end
@ -71,10 +73,10 @@ end
-- @param existing_times number[] A list of times - in ms - that the most recent work units have taken. -- @param existing_times number[] A list of times - in ms - that the most recent work units have taken.
-- @param done_count number The number of work units completed so far. -- @param done_count number The number of work units completed so far.
-- @param total_count number The total number of work units to be completed. -- @param total_count number The total number of work units to be completed.
function worldeditadditions.eta(existing_times, done_count, total_count) function wea_c.eta(existing_times, done_count, total_count)
local max = 100 local max = 100
local average = worldeditadditions.average( local average = wea_c.average(
worldeditadditions.table.get_last(existing_times, max) wea_c.table.get_last(existing_times, max)
) )
local times_left = total_count - done_count local times_left = total_count - done_count
if times_left == 0 then return 0 end if times_left == 0 then return 0 end
@ -84,7 +86,7 @@ end
--- Returns the sign (+ or -) at the beginning of a string if present. --- Returns the sign (+ or -) at the beginning of a string if present.
-- @param src string|int Input string. -- @param src string|int Input string.
-- @return string|int Returns the signed multiplier (1|-1). -- @return string|int Returns the signed multiplier (1|-1).
function worldeditadditions.getsign(src) function wea_c.getsign(src)
if type(src) == "number" then if type(src) == "number" then
if src < 0 then return -1 else return 1 end if src < 0 then return -1 else return 1 end
elseif type(src) ~= "string" then return 1 elseif type(src) ~= "string" then return 1
@ -98,12 +100,12 @@ end
-- @param min number The minimum allowed value. -- @param min number The minimum allowed value.
-- @param max number The maximum allowed value. -- @param max number The maximum allowed value.
-- @returns number The clamped number. -- @returns number The clamped number.
function worldeditadditions.clamp(value, min, max) function wea_c.clamp(value, min, max)
if value < min then return min end if value < min then return min end
if value > max then return max end if value > max then return max end
return value return value
end end
-- For Testing: -- For Testing:
-- worldeditadditions = {} -- wea_c = {}
-- print(worldeditadditions.getsign('-y')) -- print(wea_c.getsign('-y'))

@ -1,9 +1,11 @@
---@diagnostic disable: cast-local-type
-- ^--- we're using Vector3 here, so it gets confused
local Vector3 local Vector3
if worldeditadditions then if worldeditadditions_core then
local wea = worldeditadditions local wea_c = worldeditadditions_core
Vector3 = dofile(wea.modpath.."/utils/vector3.lua") Vector3 = dofile(wea_c.modpath.."/utils/vector3.lua")
else else
Vector3 = require("worldeditadditions.utils.vector3") Vector3 = require("worldeditadditions_core.utils.vector3")
end end
--- Parses an absolute axis name to a Vector3 instance. --- Parses an absolute axis name to a Vector3 instance.
@ -64,7 +66,8 @@ end
--- Parses a relative or absolute axis name into a Vector3 instance. --- Parses a relative or absolute axis name into a Vector3 instance.
-- @param axis_name string The axis name to parse. -- @param axis_name string The axis name to parse.
-- @param facing_dir table The direction the player is facing. Obtain this by calling worldeditadditions. -- @param facing_dir table The direction the player is facing. Obtain this by calling worldeditadditions_core.?????
-- TODO: Fix this comment.
local function parse_axis_name(axis_name, facing_dir) local function parse_axis_name(axis_name, facing_dir)
local success, result = parse_relative_axis_name(axis_name, facing_dir) local success, result = parse_relative_axis_name(axis_name, facing_dir)
if not success then if not success then

@ -14,22 +14,18 @@ local function unpack(tbl)
end end
--------------- ---------------
local wea_c = worldeditadditions_core or nil
local Vector3 local Vector3
if worldeditadditions then
local wea = worldeditadditions
Vector3 = dofile(wea.modpath.."/utils/vector3.lua")
else
Vector3 = require("worldeditadditions.utils.vector3")
end
local key_instance local key_instance
if worldeditadditions then if worldeditadditions_core then
local wea = worldeditadditions key_instance = dofile(wea_c.modpath.."/utils/parse/key_instance.lua")
key_instance = dofile(wea.modpath.."/utils/parse/key_instance.lua") Vector3 = dofile(wea_c.modpath.."/utils/vector3.lua")
else else
Vector3 = require("worldeditadditions_core.utils.vector3")
key_instance = require("worldeditadditions.utils.parse.key_instance") key_instance = require("worldeditadditions.utils.parse.key_instance")
end end
--- Unified Axis Keywords banks --- Unified Axis Keywords banks
local keywords = { local keywords = {
-- Compass keywords -- Compass keywords
@ -139,7 +135,7 @@ end
--- Converts Unified Axis Keyword table into Vector3 instances. --- Converts Unified Axis Keyword table into Vector3 instances.
-- @param: tbl: Table: Keyword table to parse -- @param: tbl: Table: Keyword table to parse
-- @param: facing: Table: Output from worldeditadditions.player_dir(name) -- @param: facing: Table: Output from worldeditadditions_core.player_dir(name)
-- @param: sum: Bool | String | nil: Return a single vector by summing the 2 output vectors together -- @param: sum: Bool | String | nil: Return a single vector by summing the 2 output vectors together
-- @returns: Vector3, [Vector3]: returns min, max Vector3s or sum Vector3 (if @param: sum ~= nil) -- @returns: Vector3, [Vector3]: returns min, max Vector3s or sum Vector3 (if @param: sum ~= nil)
-- if error: @returns: false, String: error message -- if error: @returns: false, String: error message

@ -3,7 +3,7 @@
-- @param str string The string to parse. -- @param str string The string to parse.
-- @param invert_percent string The operation mode. Valid modes: "1-in-n" (default), "weight". "1-in-n" refers to a 1-in-N chance of something happening (lower numbers mean greater likelihood). "weight", on the other hand, is instead a weighting that something will happen (higher numbers mean a greater likelihood). -- @param invert_percent string The operation mode. Valid modes: "1-in-n" (default), "weight". "1-in-n" refers to a 1-in-N chance of something happening (lower numbers mean greater likelihood). "weight", on the other hand, is instead a weighting that something will happen (higher numbers mean a greater likelihood).
-- @returns number|nil The 1-in-N chance if parsing was successful, otherwise nil. -- @returns number|nil The 1-in-N chance if parsing was successful, otherwise nil.
function worldeditadditions.parse.chance(str, mode) local function parse_chance(str, mode)
if not mode then mode = "1-in-n" end if not mode then mode = "1-in-n" end
if tonumber(str) ~= nil then return tonumber(str) end if tonumber(str) ~= nil then return tonumber(str) end
if str:sub(#str) == "%" then if str:sub(#str) == "%" then
@ -14,3 +14,6 @@ function worldeditadditions.parse.chance(str, mode)
end end
return nil return nil
end end
return parse_chance

@ -1,3 +1,5 @@
local wea_c = worldeditadditions_core
-- ██████ █████ ██████ ███████ ███████ -- ██████ █████ ██████ ███████ ███████
-- ██ ██ ██ ██ ██ ██ ██ ██ -- ██ ██ ██ ██ ██ ██ ██ ██
-- ██████ ███████ ██████ ███████ █████ -- ██████ ███████ ██████ ███████ █████
@ -5,21 +7,22 @@
-- ██ ██ ██ ██ ██ ███████ ███████ -- ██ ██ ██ ██ ██ ███████ ███████
-- Unified Axes Keyword Parser -- Unified Axes Keyword Parser
local uak_parse = dofile(worldeditadditions.modpath.."/utils/parse/axes_parser.lua") local uak_parse = dofile(wea_c.modpath.."/utils/parse/axes_parser.lua")
-- Old axis parsing functions -- Old axis parsing functions
local axes = dofile(worldeditadditions.modpath.."/utils/parse/axes.lua") local axes = dofile(wea_c.modpath.."/utils/parse/axes.lua")
worldeditadditions.parse = { wea_c.parse = {
direction_keyword = uak_parse.keyword, direction_keyword = uak_parse.keyword,
directions = uak_parse.keytable, directions = uak_parse.keytable,
-- Old parse functions (marked for deprecation). -- Old parse functions (marked for deprecation).
-- Use parse.keytable or parse.keyword instead -- Use parse.keytable or parse.keyword instead
axes = axes.parse_axes, axes = axes.parse_axes,
axis_name = axes.parse_axis_name, axis_name = axes.parse_axis_name,
seed = dofile(wea_c.modpath.."/utils/parse/seed.lua"),
chance = dofile(wea_c.modpath.."/utils/parse/chance.lua"),
map = dofile(wea_c.modpath.."/utils/parse/map.lua"),
weighted_nodes = dofile(wea_c.modpath.."/utils/parse/weighted_nodes.lua")
} }
dofile(worldeditadditions.modpath.."/utils/parse/chance.lua") dofile(wea_c.modpath.."/utils/parse/tokenise_commands.lua")
dofile(worldeditadditions.modpath.."/utils/parse/map.lua")
dofile(worldeditadditions.modpath.."/utils/parse/seed.lua")
dofile(worldeditadditions.modpath.."/utils/parse/weighted_nodes.lua")
dofile(worldeditadditions.modpath.."/utils/parse/tokenise_commands.lua")

@ -1,4 +1,5 @@
local wea = worldeditadditions ---@diagnostic disable: cast-local-type
local wea_c = worldeditadditions_core
--- Parses a map of key-value pairs into a table. --- Parses a map of key-value pairs into a table.
-- For example, "count 25000 speed 0.8 rate_erosion 0.006 doawesome true" would be parsed into -- For example, "count 25000 speed 0.8 rate_erosion 0.006 doawesome true" would be parsed into
@ -6,10 +7,10 @@ local wea = worldeditadditions
-- @param params_text string The string to parse. -- @param params_text string The string to parse.
-- @param keywords string[]? Optional. A list of keywords. Keywords can be present on their own without a value. If found, their value will be automatically set to bool true. -- @param keywords string[]? Optional. A list of keywords. Keywords can be present on their own without a value. If found, their value will be automatically set to bool true.
-- @returns table A table of key-value pairs parsed out from the given string. -- @returns table A table of key-value pairs parsed out from the given string.
function worldeditadditions.parse.map(params_text, keywords) local function parse_map(params_text, keywords)
if not keywords then keywords = {} end if not keywords then keywords = {} end
local result = {} local result = {}
local parts = wea.split(params_text, "%s+", false) local parts = wea_c.split(params_text, "%s+", false)
local last_key = nil local last_key = nil
local mode = "KEY" local mode = "KEY"
@ -26,7 +27,7 @@ function worldeditadditions.parse.map(params_text, keywords)
else else
last_key = part last_key = part
-- Keyword support -- Keyword support
if wea.table.contains(keywords, last_key) then if wea_c.table.contains(keywords, last_key) then
result[last_key] = true result[last_key] = true
else else
mode = "VALUE" mode = "VALUE"
@ -35,3 +36,5 @@ function worldeditadditions.parse.map(params_text, keywords)
end end
return true, result return true, result
end end
return parse_map

@ -6,7 +6,7 @@
-- (caution: certainlly NOT crypto-secure!). -- (caution: certainlly NOT crypto-secure!).
-- @param {string} str The string to convert. -- @param {string} str The string to convert.
-- @source https://stackoverflow.com/a/2624210/1460422 The idea came from here -- @source https://stackoverflow.com/a/2624210/1460422 The idea came from here
function worldeditadditions.parse.seed(str) local function parse_seed(str)
if type(str) == "number" then return str end if type(str) == "number" then return str end
if tonumber(str) ~= nil then return tonumber(str) end if tonumber(str) ~= nil then return tonumber(str) end
local result = 0 local result = 0
@ -15,3 +15,6 @@ function worldeditadditions.parse.seed(str)
end end
return result return result
end end
return parse_seed

@ -1,11 +1,11 @@
--- Parses a list of strings as a list of weighted nodes - e.g. like in --- Parses a list of strings as a list of weighted nodes - e.g. like in
-- the //mix command. Example: "dirt 5 stone sand 2". -- the //mix command. Example: "dirt 5 stone sand 2".
-- @param parts string[] The list of strings to parse (try worldeditadditions.split) -- @param parts string[] The list of strings to parse (try worldeditadditions_core.split)
-- @param as_list bool If true, then table.insert() successive { node = string, weight = number } subtables when parsing instead of populating as an associative array. -- @param as_list bool If true, then table.insert() successive { node = string, weight = number } subtables when parsing instead of populating as an associative array.
-- @param func_normalise callable If specified, the given function will be used to normalise node names instead of worldedit.normalize_nodename. A single argument is passed containing the un-normalised node name, and the return value is assumed to be the normalised node name. -- @param func_normalise callable If specified, the given function will be used to normalise node names instead of worldedit.normalize_nodename. A single argument is passed containing the un-normalised node name, and the return value is assumed to be the normalised node name.
-- @returns table A table in the form node_name => weight. -- @returns table A table in the form node_name => weight.
function worldeditadditions.parse.weighted_nodes(parts, as_list, func_normalise) local function parse_weighted_nodes(parts, as_list, func_normalise)
if as_list == nil then as_list = false end if as_list == nil then as_list = false end
local MODE_EITHER = 1 local MODE_EITHER = 1
local MODE_NODE = 2 local MODE_NODE = 2
@ -61,3 +61,6 @@ function worldeditadditions.parse.weighted_nodes(parts, as_list, func_normalise)
return true, result return true, result
end end
return parse_weighted_nodes

@ -1,7 +1,7 @@
local wea = worldeditadditions local wea_c = worldeditadditions_core
dofile(wea.modpath.."/utils/strings/split.lua") dofile(wea_c.modpath.."/utils/strings/split.lua")
dofile(wea.modpath.."/utils/strings/polyfill.lua") dofile(wea_c.modpath.."/utils/strings/polyfill.lua")
dofile(wea.modpath.."/utils/strings/tochars.lua") dofile(wea_c.modpath.."/utils/strings/tochars.lua")
wea.split_shell = dofile(wea.modpath.."/utils/strings/split_shell.lua") wea_c.split_shell = dofile(wea_c.modpath.."/utils/strings/split_shell.lua")
wea.to_boolean = dofile(wea.modpath.."/utils/strings/to_boolean.lua") wea_c.to_boolean = dofile(wea_c.modpath.."/utils/strings/to_boolean.lua")

@ -43,12 +43,12 @@ local function trim(str)
end end
if worldeditadditions then if worldeditadditions_core then
worldeditadditions.str_padend = str_padend worldeditadditions_core.str_padend = str_padend
worldeditadditions.str_padstart = str_padstart worldeditadditions_core.str_padstart = str_padstart
worldeditadditions.str_starts = str_starts worldeditadditions_core.str_starts = str_starts
worldeditadditions.str_ends = str_ends worldeditadditions_core.str_ends = str_ends
worldeditadditions.trim = trim worldeditadditions_core.trim = trim
else else
return { return {
str_padend = str_padend, str_padend = str_padend,

@ -15,7 +15,7 @@
-- for substr in gsplit(text, pattern, plain) do -- for substr in gsplit(text, pattern, plain) do
-- doSomething(substr) -- doSomething(substr)
-- end -- end
function worldeditadditions.gsplit(text, pattern, plain) function worldeditadditions_core.gsplit(text, pattern, plain)
local splitStart, length = 1, #text local splitStart, length = 1, #text
return function () return function ()
if splitStart then if splitStart then
@ -48,9 +48,9 @@ end
-- @param plain boolean If true (or truthy), pattern is interpreted as a -- @param plain boolean If true (or truthy), pattern is interpreted as a
-- plain string, not a Lua pattern -- plain string, not a Lua pattern
-- @returns table A sequence table containing the substrings -- @returns table A sequence table containing the substrings
function worldeditadditions.dsplit(text, pattern, plain) function worldeditadditions_core.dsplit(text, pattern, plain)
local ret = {} local ret = {}
for match in worldeditadditions.gsplit(text, pattern, plain) do for match in worldeditadditions_core.gsplit(text, pattern, plain) do
table.insert(ret, match) table.insert(ret, match)
end end
return ret return ret
@ -62,7 +62,7 @@ end
-- @param plain boolean If true (or truthy), pattern is interpreted as a -- @param plain boolean If true (or truthy), pattern is interpreted as a
-- plain string, not a Lua pattern -- plain string, not a Lua pattern
-- @returns table A sequence table containing the substrings -- @returns table A sequence table containing the substrings
function worldeditadditions.split(str,dlm,plain) function worldeditadditions_core.split(str,dlm,plain)
local pos, ret = 0, {} local pos, ret = 0, {}
local ins, i = str:find(dlm,pos,plain) local ins, i = str:find(dlm,pos,plain)
-- "if plain" shaves off some time in the while statement -- "if plain" shaves off some time in the while statement

@ -1,5 +1,6 @@
-- worldeditadditions = { modpath="/home/sbrl/.minetest/worlds/Mod-Sandbox/worldmods/WorldEditAdditions/worldeditadditions/" } -- worldeditadditions_core = { modpath="/home/sbrl/.minetest/worlds/Mod-Sandbox/worldmods/WorldEditAdditions/worldeditadditions_core/" }
local table_map = dofile(worldeditadditions.modpath.."/utils/tables/table_map.lua") local wea_c = worldeditadditions_core
local table_map = dofile(wea_c.modpath.."/utils/tables/table_map.lua")
local function is_whitespace(char) local function is_whitespace(char)
return char:match("%s") return char:match("%s")
@ -26,7 +27,7 @@ local function split_shell(text, autotrim)
if mode == "NORMAL" then if mode == "NORMAL" then
if is_whitespace(curchar) and #acc > 0 then if is_whitespace(curchar) and #acc > 0 then
local nextval = worldeditadditions.trim(table.concat(acc, "")) local nextval = wea_c.trim(table.concat(acc, ""))
if #nextval > 0 then if #nextval > 0 then
table.insert(result, table.concat(acc, "")) table.insert(result, table.concat(acc, ""))
end end

@ -3,7 +3,7 @@
-- @param sort bool Sort characters -- @param sort bool Sort characters
-- @param rem_dups bool Remove duplicate characters -- @param rem_dups bool Remove duplicate characters
-- @returns table A sequence table containing the substrings -- @returns table A sequence table containing the substrings
function worldeditadditions.tochars(text,sort,rem_dups) function worldeditadditions_core.tochars(text,sort,rem_dups)
local t, set = {}, {} local t, set = {}, {}
if rem_dups then if rem_dups then
text:gsub(".",function(c) set[c] = true end) text:gsub(".",function(c) set[c] = true end)
@ -20,7 +20,7 @@ end
--- Split into a set of characters. --- Split into a set of characters.
-- @param text string The string to iterate over -- @param text string The string to iterate over
-- @returns table A sequence set table containing the substrings -- @returns table A sequence set table containing the substrings
function worldeditadditions.tocharset(text) function worldeditadditions_core.tocharset(text)
local t = {} local t = {}
text:gsub(".",function(c) t[c] = true end) text:gsub(".",function(c) t[c] = true end)
return t return t

@ -8,18 +8,18 @@
-- Lua doesn't exactly come with batteries included, so this is quite an -- Lua doesn't exactly come with batteries included, so this is quite an
-- extensive collection of functions :P -- extensive collection of functions :P
local wea = worldeditadditions local wea_c = worldeditadditions_core
wea.table = { wea_c.table = {
apply = dofile(wea.modpath.."/utils/tables/table_apply.lua"), apply = dofile(wea_c.modpath.."/utils/tables/table_apply.lua"),
contains = dofile(wea.modpath.."/utils/tables/table_contains.lua"), contains = dofile(wea_c.modpath.."/utils/tables/table_contains.lua"),
deepcopy = dofile(wea.modpath.."/utils/tables/deepcopy.lua"), deepcopy = dofile(wea_c.modpath.."/utils/tables/deepcopy.lua"),
filter = dofile(wea.modpath.."/utils/tables/table_filter.lua"), filter = dofile(wea_c.modpath.."/utils/tables/table_filter.lua"),
get_last = dofile(wea.modpath.."/utils/tables/table_get_last.lua"), get_last = dofile(wea_c.modpath.."/utils/tables/table_get_last.lua"),
makeset = dofile(wea.modpath.."/utils/tables/makeset.lua"), makeset = dofile(wea_c.modpath.."/utils/tables/makeset.lua"),
map = dofile(wea.modpath.."/utils/tables/table_map.lua"), map = dofile(wea_c.modpath.."/utils/tables/table_map.lua"),
shallowcopy = dofile(wea.modpath.."/utils/tables/shallowcopy.lua"), shallowcopy = dofile(wea_c.modpath.."/utils/tables/shallowcopy.lua"),
tostring = dofile(wea.modpath.."/utils/tables/table_tostring.lua"), tostring = dofile(wea_c.modpath.."/utils/tables/table_tostring.lua"),
unique = dofile(wea.modpath.."/utils/tables/table_unique.lua"), unique = dofile(wea_c.modpath.."/utils/tables/table_unique.lua"),
unpack = dofile(wea.modpath.."/utils/tables/table_unpack.lua"), unpack = dofile(wea_c.modpath.."/utils/tables/table_unpack.lua"),
} }

@ -1,6 +1,6 @@
local wea = worldeditadditions local wea_c = worldeditadditions_core
local table_unpack = dofile(wea.modpath.."/utils/tables/table_unpack.lua") local table_unpack = dofile(wea_c.modpath.."/utils/tables/table_unpack.lua")
--- Returns only the last count items in a given numerical table-based list. --- Returns only the last count items in a given numerical table-based list.

@ -1,5 +1,5 @@
local wea = worldeditadditions local wea_c = worldeditadditions_core
local Vector3 = wea.Vector3 local Vector3 = wea_c.Vector3
--- Applies changes to a heightmap to a Voxel Manipulator data block. --- Applies changes to a heightmap to a Voxel Manipulator data block.
-- @param pos1 vector Position 1 of the defined region -- @param pos1 vector Position 1 of the defined region

@ -1,5 +1,5 @@
local wea = worldeditadditions local wea_c = worldeditadditions_core
local Vector3 = wea.Vector3 local Vector3 = wea_c.Vector3
--- Calculates a normal map for the given heightmap. --- Calculates a normal map for the given heightmap.

@ -1,5 +1,5 @@
local wea = worldeditadditions local wea_c = worldeditadditions_core
local Vector3 = wea.Vector3 local Vector3 = wea_c.Vector3
--- Converts a 2d heightmap into slope values in radians. --- Converts a 2d heightmap into slope values in radians.
@ -9,10 +9,10 @@ local Vector3 = wea.Vector3
-- @param heightmap_size int[] The size of the heightmap in the form [ z, x ] -- @param heightmap_size int[] The size of the heightmap in the form [ z, x ]
-- @return Vector[] The calculated slope map, in the same form as the input heightmap. Each element of the array is a (floating-point) number representing the slope in that cell in radians. -- @return Vector[] The calculated slope map, in the same form as the input heightmap. Each element of the array is a (floating-point) number representing the slope in that cell in radians.
local function calculate_slopes(heightmap, heightmap_size) local function calculate_slopes(heightmap, heightmap_size)
local normals = wea.terrain.calculate_normals(heightmap, heightmap_size) local normals = wea_c.terrain.calculate_normals(heightmap, heightmap_size)
local slopes = { } local slopes = { }
local up = wea.Vector3.new(0, 1, 0) -- Z & Y are flipped local up = Vector3.new(0, 1, 0) -- Z & Y are flipped
for z = heightmap_size.z-1, 0, -1 do for z = heightmap_size.z-1, 0, -1 do
for x = heightmap_size.x-1, 0, -1 do for x = heightmap_size.x-1, 0, -1 do

@ -1,12 +1,10 @@
local wea = worldeditadditions local wea_c = worldeditadditions_core
local Vector3 = wea.Vector3
local terrain = { local terrain = {
make_heightmap = dofile(wea.modpath.."/utils/terrain/make_heightmap.lua"), make_heightmap = dofile(wea_c.modpath.."/utils/terrain/make_heightmap.lua"),
calculate_normals = dofile(wea.modpath.."/utils/terrain/calculate_normals.lua"), calculate_normals = dofile(wea_c.modpath.."/utils/terrain/calculate_normals.lua"),
calculate_slopes = dofile(wea.modpath.."/utils/terrain/calculate_slopes.lua"), calculate_slopes = dofile(wea_c.modpath.."/utils/terrain/calculate_slopes.lua"),
apply_heightmap_changes = dofile(wea.modpath.."/utils/terrain/apply_heightmap_changes.lua") apply_heightmap_changes = dofile(wea_c.modpath.."/utils/terrain/apply_heightmap_changes.lua")
} }
return terrain return terrain

@ -1,5 +1,5 @@
local wea = worldeditadditions local wea_c = worldeditadditions_core
local Vector3 = wea.Vector3 local Vector3 = wea_c.Vector3
--- Given a manip object and associates, generates a 2D x/z heightmap. --- Given a manip object and associates, generates a 2D x/z heightmap.
@ -23,7 +23,7 @@ local function make_heightmap(pos1, pos2, manip, area, data)
-- Scan each column top to bottom -- Scan each column top to bottom
for y = pos2.y+1, pos1.y, -1 do for y = pos2.y+1, pos1.y, -1 do
local i = area:index(x, y, z) local i = area:index(x, y, z)
if not (wea.is_airlike(data[i]) and not wea.is_liquidlike(data[i])) then if not (wea_c.is_airlike(data[i]) and not wea_c.is_liquidlike(data[i])) then
-- It's the first non-airlike node in this column -- It's the first non-airlike node in this column
-- Start heightmap values from 1 (i.e. there's at least 1 node in the column) -- Start heightmap values from 1 (i.e. there's at least 1 node in the column)
heightmap[hi] = (y - pos1.y) + 1 heightmap[hi] = (y - pos1.y) + 1