2020-06-07 21:46:46 +02:00
--- Makes an associative table of node_name => weight into a list of node ids.
2021-02-10 01:53:30 +01:00
-- Node names with a higher weight are repeated more times.
2020-06-07 21:46:46 +02:00
function worldeditadditions . make_weighted ( tbl )
local result = { }
for node_name , weight in pairs ( tbl ) do
local next_id = minetest.get_content_id ( node_name )
2020-09-14 02:19:15 +02:00
-- print("[make_weighted] seen "..node_name.." @ weight "..weight.." → id "..next_id)
2020-06-07 21:46:46 +02:00
for i = 1 , weight do
2020-06-11 01:38:16 +02:00
table.insert ( result , next_id )
end
end
return result , # result
end
--- Unwinds a list of { node = string, weight = number } tables into a list of node ids.
-- The node ids will be repeated multiple times according to their weights
-- (e.g. an entry with a weight of 2 will be repeated twice).
-- @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.
function worldeditadditions . unwind_node_list ( list )
local result = { }
for i , item in ipairs ( list ) do
local node_id = minetest.get_content_id ( item.node )
for i = 1 , item.weight do
table.insert ( result , node_id )
2020-06-07 21:46:46 +02:00
end
end
return result , # result
end
2020-06-09 21:43:29 +02:00
2020-09-13 21:32:55 +02:00
function worldeditadditions . registered_nodes_by_group ( group )
local result = { }
for name , def in pairs ( minetest.registered_nodes ) do
if def.groups [ group ] then
result [ # result + 1 ] = name
end
2020-06-11 01:38:16 +02:00
end
2020-09-13 21:32:55 +02:00
return result
2020-09-13 16:43:49 +02:00
end
2020-09-14 02:19:15 +02:00
--- Turns a node_name → weight table into a list of { node_name, weight } tables.
function worldeditadditions . weighted_to_list ( node_weights )
local result = { }
for node_name , weight in pairs ( node_weights ) do
table.insert ( result , { node_name , weight } )
end
return result
end
2020-10-10 22:43:22 +02:00
local function emerge_callback ( pos , action , num_calls_remaining , state )
if not state.total then
state.total = num_calls_remaining + 1
state.loaded_blocks = 0
end
state.loaded_blocks = state.loaded_blocks + 1
if state.loaded_blocks == state.total then
2020-10-10 22:57:19 +02:00
state.callback ( state , state.callback_state )
2020-10-10 22:43:22 +02:00
else
if action == minetest.EMERGE_CANCELLED then
state.stats . cancelled = state.stats . cancelled + 1
elseif action == minetest.EMERGE_ERRORED then
state.stats . error = state.stats . error + 1
elseif action == minetest.EMERGE_FROM_MEMORY then
state.stats . from_memory = state.stats . from_memory + 1
elseif action == minetest.EMERGE_FROM_DISK then
state.stats . from_disk = state.stats . from_disk + 1
elseif action == minetest.EMERGE_GENERATED then
state.stats . generated = state.stats . generated + 1
end
end
end
--- Loads the area defined by the specified region using minetest.emerge_area.
-- Unlike minetest.emerge_area, this command calls the specified callback only
-- once upon completion.
-- @param {Vector} pos1 The first 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 {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 )
local state = {
stats = { cancelled = 0 , error = 0 , from_memory = 0 , from_disk = 0 , generated = 0 } ,
callback = callback ,
callback_state = callback_state
}
2020-10-10 22:50:03 +02:00
minetest.emerge_area ( pos1 , pos2 , emerge_callback , state )
2020-10-10 22:43:22 +02:00
end