From 8df8e44a0c953026b61a4fe1e393435d127cd6be Mon Sep 17 00:00:00 2001 From: Vanessa Ezekowitz Date: Tue, 29 Jan 2013 16:22:33 -0500 Subject: [PATCH] add experimental support for calling an arbitrary function in the spawning ABM after all other biome tests and general checks (aside from spawning at the sides/bottom/top of a node) are done. --- API.txt | 20 +++++++++++++------- plants_lib/init.lua | 11 +++++++++-- 2 files changed, 22 insertions(+), 9 deletions(-) diff --git a/API.txt b/API.txt index 8d5a333..f786348 100644 --- a/API.txt +++ b/API.txt @@ -68,13 +68,7 @@ you must pass at least four arguments as regular keyed entries in the table, in any order: plants_lib: spawn_on_surfaces({ - spawn_plants = {table}, -- List of plants to spawn with this ABM call. - -- The program will choose one of these at - -- random each time the ABM executes. The - -- more nodes you can pack into this parameter - -- to avoid making too many calls to this - -- function, the lower the CPU load will - -- likely be. + spawn_plants = something, -- [*] String or table; see below. spawn_delay = number, -- same as sdelay spawn_chance = number, -- same as schance spawn_surfaces = {table} -- List of node names on which the plants @@ -234,6 +228,18 @@ plants_lib: spawn_on_surfaces({ -- settings. }) +[*] spawn_plants must be either a table or a string. If it's a table, the +values therein are treated as a list of nodenames to pick from randomly on +each application of the ABM code. The more nodes you can pack into this +parameter to avoid making too many calls to this function, the lower the CPU +load will likely be. + +You can also specify a string containing the name of a function to execute. +In this case, the function will be passed a single position parameter +indicating where the function should place the desired object, and the checks +for spawning on top vs. sides vs. bottom vs. replacing the target node will be +skipped. + By default, if a biome node, size, and count are not defined, the biome checking is disabled. Same holds true for the nneighbors bit above that. diff --git a/plants_lib/init.lua b/plants_lib/init.lua index ac17249..183f609 100644 --- a/plants_lib/init.lua +++ b/plants_lib/init.lua @@ -11,7 +11,7 @@ plantslib = {} -local DEBUG = true --... except if you want to spam the console with debugging info :-) +local DEBUG = false --... except if you want to spam the console with debugging info :-) plantslib.plantlife_seed_diff = 329 -- needs to be global so other mods can see it @@ -240,7 +240,11 @@ function plantslib:spawn_on_surfaces(sd,sp,sr,sc,ss,sa) local plant_to_spawn = biome.spawn_plants[rnd] plantslib:dbg("Chose entry number "..rnd.." of "..biome.spawn_plants_count) - if not biome.spawn_on_side and not biome.spawn_on_bottom and not biome.spawn_replace_node then + if type(spawn_plants) == "string" then + plantslib:dbg("Call function: "..spawn_plants.."("..dump(pos)..")") + assert(loadstring(spawn_plants.."("..dump(pos)..")"))() + + elseif not biome.spawn_on_side and not biome.spawn_on_bottom and not biome.spawn_replace_node then local fdir = biome.facedir if biome.random_facedir then fdir = math.random(biome.random_facedir[1],biome.random_facedir[2]) @@ -250,6 +254,7 @@ function plantslib:spawn_on_surfaces(sd,sp,sr,sc,ss,sa) plantslib:dbg("Spawn: "..plant_to_spawn.." on top of ("..dump(pos)..")") minetest.env:add_node(p_top, { name = plant_to_spawn, param2 = fdir }) end + elseif biome.spawn_replace_node then local fdir = biome.facedir if biome.random_facedir then @@ -258,12 +263,14 @@ function plantslib:spawn_on_surfaces(sd,sp,sr,sc,ss,sa) end plantslib:dbg("Spawn: "..plant_to_spawn.." to replace "..minetest.env:get_node(pos).name.." at ("..dump(pos)..")") minetest.env:add_node(pos, { name = plant_to_spawn, param2 = fdir }) + elseif biome.spawn_on_side then local onside = plantslib:find_open_side(pos) if onside then plantslib:dbg("Spawn: "..plant_to_spawn.." at side of ("..dump(pos).."), facedir "..onside.facedir.."") minetest.env:add_node(onside.newpos, { name = plant_to_spawn, param2 = onside.facedir }) end + elseif biome.spawn_on_bottom then if minetest.env:get_node({x=pos.x, y=pos.y-1, z=pos.z}).name == "air" then local fdir = biome.facedir