Compare commits
5 Commits
15e5a72a9a
...
ec41aa93f6
Author | SHA1 | Date |
---|---|---|
Sapier | ec41aa93f6 | |
Sapier | 9d7e4279f4 | |
Sapier | b9608c029f | |
Sapier | cd6e0bcb35 | |
Sapier | ba0b80282e |
2
init.lua
2
init.lua
|
@ -8,7 +8,7 @@
|
|||
--
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
local version = "0.0.9"
|
||||
local version = "0.0.13"
|
||||
|
||||
if adv_spawning ~= nil then
|
||||
core.log("error", "MOD: adv_spawning requires adv_spawning variable to be available")
|
||||
|
|
175
internal.lua
175
internal.lua
|
@ -105,6 +105,7 @@ function adv_spawning.initialize()
|
|||
adv_spawning.gettime = function() return os.clock() * 1000 end
|
||||
|
||||
if type(minetest.get_us_time) == "function" then
|
||||
adv_spawning.log("action", "Using minetest.get_us_time() for quota calc")
|
||||
adv_spawning.gettime = function()
|
||||
return minetest.get_us_time() / 1000
|
||||
end
|
||||
|
@ -113,6 +114,7 @@ function adv_spawning.initialize()
|
|||
local status, module = pcall(require, 'socket')
|
||||
|
||||
if status and type(module.gettime) == "function" then
|
||||
adv_spawning.log("action", "Using socket.gettime() for quota calc")
|
||||
adv_spawning.gettime = function()
|
||||
return socket.gettime()*1000
|
||||
end
|
||||
|
@ -373,7 +375,7 @@ end
|
|||
-- @param minp (OPTIONAL) override spawner defaults
|
||||
-- @param maxp (OPTIONAL) override spawner defaults
|
||||
-- @param ignore_active_area set to true for mapgen spawning
|
||||
-- @return successfull true/false, permanent_error true,false
|
||||
-- @return successfull true/false, permanent_error true,false, reason_string
|
||||
--------------------------------------------------------------------------------
|
||||
function adv_spawning.handlespawner(spawnername,spawnerpos,minp,maxp,ignore_active_area)
|
||||
|
||||
|
@ -382,7 +384,7 @@ function adv_spawning.handlespawner(spawnername,spawnerpos,minp,maxp,ignore_acti
|
|||
|
||||
if not adv_spawning.check_daytime(spawndef.daytimes) then
|
||||
adv_spawning.log("info","didn't meet daytime check")
|
||||
return false,nil
|
||||
return false,nil, "daytimecheck failed"
|
||||
end
|
||||
|
||||
local max_x = spawnerpos.x + adv_spawning.spawner_distance/2
|
||||
|
@ -412,15 +414,20 @@ function adv_spawning.handlespawner(spawnername,spawnerpos,minp,maxp,ignore_acti
|
|||
new_pos.x = math.random(min_x,max_x)
|
||||
new_pos.z = math.random(min_z,max_z)
|
||||
|
||||
local yreason = "ukn"
|
||||
|
||||
--check if entity is configured to spawn at surface
|
||||
if spawndef.relative_height == nil or
|
||||
(spawndef.relative_height.max ~= nil and
|
||||
spawndef.relative_height.max <= 1) then
|
||||
new_pos.y = adv_spawning.get_surface(lower_y,upper_y,new_pos,
|
||||
new_pos.y, yreason = adv_spawning.get_surface(lower_y,upper_y,new_pos,
|
||||
spawndef.spawn_inside)
|
||||
else
|
||||
new_pos.y = adv_spawning.get_relative_pos(lower_y,upper_y,new_pos,
|
||||
if spawndef.spawn_inside == nil then
|
||||
print("ERROR: " .. spawnername .. " tries to spawn within nil")
|
||||
assert(false)
|
||||
end
|
||||
new_pos.y, yreason = adv_spawning.get_relative_pos(lower_y,upper_y,new_pos,
|
||||
spawndef.spawn_inside,
|
||||
spawndef.relative_height,
|
||||
spawndef.absolute_height)
|
||||
|
@ -432,21 +439,23 @@ function adv_spawning.handlespawner(spawnername,spawnerpos,minp,maxp,ignore_acti
|
|||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't find a suitable y pos "
|
||||
.. lower_y .. "<-->" .. upper_y )
|
||||
return false,nil
|
||||
return false, nil, "didn't find a valid ypos at " .. minetest.pos_to_string(new_pos)
|
||||
.. " " .. lower_y .. "<-->" .. upper_y .. " rsn: " .. yreason
|
||||
end
|
||||
|
||||
--check absolute height
|
||||
if not adv_spawning.check_absolute_height(new_pos,spawndef.absolute_height) then
|
||||
local abs_height_retval, abs_height_rsn = adv_spawning.check_absolute_height(new_pos,spawndef.absolute_height)
|
||||
if not abs_height_retval then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet absolute height check")
|
||||
return false,true
|
||||
return false, true, "absolute height check failed rsn: " .. abs_height_rsn
|
||||
end
|
||||
|
||||
--check active area
|
||||
if not ignore_active_area and not adv_spawning.check_active_block(new_pos) then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet active area check")
|
||||
return false,nil
|
||||
return false, nil , "area check failed"
|
||||
end
|
||||
|
||||
--check surface
|
||||
|
@ -459,7 +468,7 @@ function adv_spawning.handlespawner(spawnername,spawnerpos,minp,maxp,ignore_acti
|
|||
minetest.pos_to_string(new_pos) ..
|
||||
" didn't meet surface check, is: " ..
|
||||
minetest.get_node({x=new_pos.x,z=new_pos.z,y=new_pos.y-1}).name)
|
||||
return false,nil
|
||||
return false, nil, "surface check failed"
|
||||
end
|
||||
|
||||
--flat area check
|
||||
|
@ -470,7 +479,7 @@ function adv_spawning.handlespawner(spawnername,spawnerpos,minp,maxp,ignore_acti
|
|||
spawndef.surfaces) then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet flat area check")
|
||||
return false,nil
|
||||
return false, nil, "flat area check failed"
|
||||
end
|
||||
|
||||
--check collisionbox
|
||||
|
@ -485,28 +494,28 @@ function adv_spawning.handlespawner(spawnername,spawnerpos,minp,maxp,ignore_acti
|
|||
if not checkresult then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet collisionbox check")
|
||||
return false,nil
|
||||
return false, nil, "collision box check failed"
|
||||
end
|
||||
|
||||
--check entities around
|
||||
if not adv_spawning.check_entities_around(new_pos,spawndef.entities_around) then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet entities check")
|
||||
return false,nil
|
||||
return false, nil, "entitie around check failed"
|
||||
end
|
||||
|
||||
--check nodes around
|
||||
if not adv_spawning.check_nodes_around(new_pos,spawndef.nodes_around) then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet nodes check")
|
||||
return false,nil
|
||||
return false, nil, "nodes around check failed"
|
||||
end
|
||||
|
||||
--check light around
|
||||
if not adv_spawning.check_light_around(new_pos,spawndef.light_around) then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet light check")
|
||||
return false,nil
|
||||
return false, nil, "light check failed"
|
||||
end
|
||||
|
||||
-- ONLY use this if you have luajit
|
||||
|
@ -514,31 +523,37 @@ function adv_spawning.handlespawner(spawnername,spawnerpos,minp,maxp,ignore_acti
|
|||
-- if not adv_spawning.check_light_around_voxel(new_pos,spawndef.light_around) then
|
||||
-- adv_spawning.log("info",
|
||||
-- minetest.pos_to_string(new_pos) .. " didn't meet light check")
|
||||
-- return false,nil
|
||||
-- return false, nil, "luajit light check failed"
|
||||
-- end
|
||||
|
||||
--check humidity
|
||||
if not adv_spawning.check_humidity_around(new_pos,spawndef.humidity_around) then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet humidity check")
|
||||
return false,nil
|
||||
return false, nil, "humidity check failed"
|
||||
end
|
||||
|
||||
--check temperature
|
||||
if not adv_spawning.check_temperature_around(new_pos,spawndef.temperature_around) then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet temperature check")
|
||||
return false,nil
|
||||
return false, nil, "temperature check failed"
|
||||
end
|
||||
|
||||
--custom check
|
||||
if (spawndef.custom_check ~= nil and
|
||||
type(spawndef.custom_check) == "function") then
|
||||
|
||||
if not spawndef.custom_check(new_pos,spawndef) then
|
||||
local retval, reason = spawndef.custom_check(new_pos,spawndef)
|
||||
|
||||
if not reason then
|
||||
reason = "custom check failed"
|
||||
end
|
||||
|
||||
if not retval then
|
||||
adv_spawning.log("info",
|
||||
minetest.pos_to_string(new_pos) .. " didn't meet custom check")
|
||||
return false,nil
|
||||
return false, nil, reason
|
||||
end
|
||||
end
|
||||
|
||||
|
@ -570,30 +585,47 @@ function adv_spawning.get_surface(y_min,y_max,new_pos,spawn_inside)
|
|||
local top_pos = { x=new_pos.x, z=new_pos.z, y=y_max}
|
||||
local bottom_pos = { x=new_pos.x, z=new_pos.z, y=y_min}
|
||||
|
||||
-- get list of all nodes within our y-range we could spawn within
|
||||
local spawnable_nodes =
|
||||
minetest.find_nodes_in_area(bottom_pos, top_pos, spawn_inside)
|
||||
|
||||
-- if there ain't a single node to spawn within get out of here
|
||||
if #spawnable_nodes == 0 then
|
||||
return nil
|
||||
return nil, "no spawnable nodes at all"
|
||||
end
|
||||
|
||||
local spawnable_node_passed = false
|
||||
|
||||
-- loop from topmost position to bottom
|
||||
for i=y_max, y_min, -1 do
|
||||
-- get current position
|
||||
local pos = { x=new_pos.x,z=new_pos.z,y=i}
|
||||
|
||||
-- if the node at current position ain't one of those we can spawn within
|
||||
if not adv_spawning.contains_pos(spawnable_nodes,pos) then
|
||||
|
||||
-- get more information about this node
|
||||
local node = minetest.get_node(pos)
|
||||
|
||||
local text = "false"
|
||||
|
||||
if spawnable_node_passed then
|
||||
text = "true"
|
||||
end
|
||||
|
||||
-- if node ain't unloaded and we did already see a spawnable node above
|
||||
-- return position above as pos to spawn
|
||||
if node.name ~= "ignore" and
|
||||
spawnable_node_passed then
|
||||
return i+1
|
||||
return i+1, "pos found"
|
||||
end
|
||||
else
|
||||
-- set marker about having seen a spawnable node above
|
||||
spawnable_node_passed = true
|
||||
end
|
||||
end
|
||||
|
||||
return nil
|
||||
return nil, "no matching node, nodecnt: " .. #spawnable_nodes
|
||||
end
|
||||
|
||||
--------------------------------------------------------------------------------
|
||||
|
@ -612,7 +644,8 @@ function adv_spawning.get_relative_pos(y_min,y_max,new_pos,spawn_inside,relative
|
|||
if y_val == nil then
|
||||
if (relative_height.min ~= nil or
|
||||
relative_height.max ~= nil) then
|
||||
return nil
|
||||
return nil, "y_pos not witing range of "
|
||||
.. relative_height.min .. "<-->" .. relative_height.max
|
||||
else
|
||||
y_val = y_min
|
||||
end
|
||||
|
@ -636,17 +669,17 @@ function adv_spawning.get_relative_pos(y_min,y_max,new_pos,spawn_inside,relative
|
|||
|
||||
if top_pos.y < bottom_pos.y then
|
||||
--print("Invalid interval: " .. bottom_pos.y .. "<-->" .. top_pos.y)
|
||||
return nil
|
||||
return nil, "invalid interval: " .. bottom_pos.y .. "<-->" .. top_pos.y
|
||||
end
|
||||
|
||||
local spawnable_nodes =
|
||||
minetest.find_nodes_in_area(bottom_pos, top_pos, spawn_inside)
|
||||
|
||||
if #spawnable_nodes > 0 then
|
||||
return spawnable_nodes[math.random(1,#spawnable_nodes)].y
|
||||
return spawnable_nodes[math.random(1,#spawnable_nodes)].y, "rpos found"
|
||||
else
|
||||
--print("no suitable nodes" .. bottom_pos.y .. "<-->" .. top_pos.y)
|
||||
return nil
|
||||
return nil, "no spawnable nodes found around"
|
||||
end
|
||||
end
|
||||
|
||||
|
@ -681,20 +714,20 @@ end
|
|||
--------------------------------------------------------------------------------
|
||||
function adv_spawning.check_absolute_height(pos,absolute_height)
|
||||
if absolute_height == nil then
|
||||
return true
|
||||
return true, "no height limit"
|
||||
end
|
||||
|
||||
if absolute_height.min ~= nil and
|
||||
pos.y < absolute_height.min then
|
||||
return false
|
||||
return false, pos.y .. " < " .. absolute_height.min
|
||||
end
|
||||
|
||||
if absolute_height.max ~= nil and
|
||||
pos.y > absolute_height.max then
|
||||
return false
|
||||
return false, pos.y .. " > " .. absolute_height.max
|
||||
end
|
||||
|
||||
return true
|
||||
return true, "height ok"
|
||||
end
|
||||
|
||||
--------------------------------------------------------------------------------
|
||||
|
@ -1225,7 +1258,7 @@ function adv_spawning.check_flat_area(new_pos,flat_area,spawn_inside,surfaces)
|
|||
|
||||
local required_nodes = (range*2+1)*(range*2+1) - current_deviation
|
||||
|
||||
if surface == nil then
|
||||
if surfaces == nil then
|
||||
local ground_nodes =
|
||||
minetest.find_nodes_in_area(back_left, front_right, spawn_inside)
|
||||
|
||||
|
@ -1576,3 +1609,83 @@ function adv_spawning.table_count(tocount)
|
|||
|
||||
return retval
|
||||
end
|
||||
|
||||
function adv_spawning.build_shell(pos, d)
|
||||
local retval = {}
|
||||
|
||||
-- build top face
|
||||
for x = -d , d , 1 do
|
||||
for z = -d, d, 1 do
|
||||
retval[#retval+1] = { x = pos.x + x, y = pos.y + d, z = pos.z + z}
|
||||
end
|
||||
end
|
||||
|
||||
-- build bottom face
|
||||
for x = -d , d , 1 do
|
||||
for z = -d, d, 1 do
|
||||
retval[#retval+1] = { x = pos.x + x, y = pos.y -d, z = pos.z + z}
|
||||
end
|
||||
end
|
||||
|
||||
-- build x- face
|
||||
for z = -d , d , 1 do
|
||||
for y = - (d -1) , (d -1), 1 do
|
||||
retval[#retval+1] = { x = pos.x -d, y = pos.y + y, z = pos.z + z}
|
||||
end
|
||||
end
|
||||
|
||||
-- build x+ face
|
||||
for z = -d , d , 1 do
|
||||
for y = - (d -1) , (d -1), 1 do
|
||||
retval[#retval+1] = { x = pos.x + d, y = pos.y + y, z = pos.z + z}
|
||||
end
|
||||
end
|
||||
|
||||
-- build z- face
|
||||
for x = - (d -1) , (d -1) , 1 do
|
||||
for y = - (d -1) , (d -1), 1 do
|
||||
retval[#retval+1] = { x = pos.x + x, y = pos.y + y, z = pos.z - d}
|
||||
end
|
||||
end
|
||||
|
||||
-- build z+ face
|
||||
for x = -(d -1) , (d -1) , 1 do
|
||||
for y = - (d -1) , (d -1), 1 do
|
||||
retval[#retval+1] = { x = pos.x + x, y = pos.y + y, z = pos.z + d}
|
||||
end
|
||||
end
|
||||
|
||||
return retval;
|
||||
end
|
||||
|
||||
--------------------------------------------------------------------------------
|
||||
-- @function [parent=#adv_spawning] table_count
|
||||
-- @param tocount table to get number of elements from
|
||||
--------------------------------------------------------------------------------
|
||||
function adv_spawning.find_nodes_in(pos, min_range, max_range, nodetypes)
|
||||
|
||||
local nodetypes_to_use = nodetypes
|
||||
|
||||
if type(nodetypes) == "string" then
|
||||
nodetypes_to_use = { }
|
||||
table.insert(nodetypes_to_use, nodetypes)
|
||||
end
|
||||
|
||||
for i = min_range, max_range, 1 do
|
||||
local positions = adv_spawning.build_shell(pos, i)
|
||||
|
||||
for i = 1, #positions, 1 do
|
||||
local node = minetest.get_node_or_nil(positions[i])
|
||||
|
||||
if node ~= nil then
|
||||
for i = 1, #nodetypes_to_use, 1 do
|
||||
if node.name == nodetypes_to_use[i] then
|
||||
return positions[i]
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
return nil
|
||||
end
|
||||
|
|
176
spawn_seed.lua
176
spawn_seed.lua
|
@ -16,7 +16,9 @@
|
|||
--------------------------------------------------------------------------------
|
||||
function adv_spawning.seed_step(self,dtime)
|
||||
if not self.activated then
|
||||
local starttime = adv_spawning.gettime()
|
||||
adv_spawning.seed_activate(self)
|
||||
adv_spawning.check_time(starttime, "Initializing spawner on_step took way too much time")
|
||||
return
|
||||
end
|
||||
|
||||
|
@ -47,10 +49,13 @@ function adv_spawning.seed_step(self,dtime)
|
|||
local per_step_count = 0
|
||||
local key = nil
|
||||
|
||||
local starttime = adv_spawning.gettime()
|
||||
|
||||
while #self.pending_spawners > 0 and
|
||||
per_step_count < adv_spawning.max_spawns_per_spawner and
|
||||
(not adv_spawning.time_over(10)) do
|
||||
|
||||
|
||||
local rand_spawner = math.random(1,#self.pending_spawners)
|
||||
key = self.pending_spawners[rand_spawner]
|
||||
|
||||
|
@ -61,13 +66,17 @@ function adv_spawning.seed_step(self,dtime)
|
|||
end
|
||||
|
||||
while tries > 0 do
|
||||
local successfull, permanent_error, reason =
|
||||
adv_spawning.handlespawner(key,self.object:getpos())
|
||||
|
||||
if adv_spawning.handlespawner(key,self.object:getpos()) then
|
||||
if successfull then
|
||||
self.spawning_data[key] =
|
||||
adv_spawning.spawner_definitions[key].spawn_interval
|
||||
self.spawn_fail_reasons[key] = "successfull spawned"
|
||||
else
|
||||
self.spawning_data[key] =
|
||||
adv_spawning.spawner_definitions[key].spawn_interval/4
|
||||
self.spawn_fail_reasons[key] = reason
|
||||
end
|
||||
|
||||
--check quota again
|
||||
|
@ -81,6 +90,10 @@ function adv_spawning.seed_step(self,dtime)
|
|||
tries = tries -1
|
||||
end
|
||||
|
||||
|
||||
starttime = adv_spawning.check_time(starttime, key .. " for " ..
|
||||
adv_spawning.spawner_definitions[key].spawnee .. " did use way too much time")
|
||||
|
||||
table.remove(self.pending_spawners,rand_spawner)
|
||||
per_step_count = per_step_count +1
|
||||
end
|
||||
|
@ -117,9 +130,19 @@ function adv_spawning.seed_activate(self)
|
|||
adv_spawning.seed_validate_spawndata(self)
|
||||
|
||||
self.pending_spawners = {}
|
||||
self.spawn_fail_reasons = {}
|
||||
self.initialized_spawners = 0
|
||||
self.activated = true
|
||||
|
||||
-- fix unaligned own pos
|
||||
local pos = self.object:getpos()
|
||||
|
||||
pos.x = math.floor(pos.x + 0.5)
|
||||
pos.y = math.floor(pos.y + 0.5)
|
||||
pos.z = math.floor(pos.z + 0.5)
|
||||
|
||||
self.object:setpos(pos)
|
||||
|
||||
if not adv_spawning.quota_leave() then
|
||||
adv_spawning.dbg_log(2, "on activate " .. self.name .. " did use way too much time")
|
||||
end
|
||||
|
@ -138,7 +161,13 @@ function adv_spawning.on_rightclick(self, clicker)
|
|||
print("ADV_SPAWNING: Spawner may spawn " .. adv_spawning.table_count(self.spawning_data) .. " mobs:")
|
||||
local index = 1
|
||||
for key,value in pairs(self.spawning_data) do
|
||||
print(string.format("%3d:",index) .. string.format("%30s ",key) .. string.format("%3d s", value))
|
||||
local reason = "unknown"
|
||||
|
||||
if self.spawn_fail_reasons[key] then
|
||||
reason = self.spawn_fail_reasons[key]
|
||||
end
|
||||
|
||||
print(string.format("%3d:",index) .. string.format("%30s ",key) .. string.format("%3d s (", value) .. reason .. ")")
|
||||
index = index +1
|
||||
end
|
||||
end
|
||||
|
@ -238,6 +267,95 @@ function adv_spawning.seed_check_for_collision(self)
|
|||
return false
|
||||
end
|
||||
|
||||
|
||||
function adv_spawning.init_spawner(self, pos, name, spawnerdef)
|
||||
local starttime = adv_spawning.gettime()
|
||||
|
||||
if self.spawner_init_state ~= nil then
|
||||
self.spawner_init_state = "initial"
|
||||
end
|
||||
|
||||
local starttime = adv_spawning.gettime()
|
||||
if self.spawner_init_state == "initial" then
|
||||
|
||||
--check if cyclic spawning is enabled
|
||||
if spawnerdef.cyclic_spawning ~= nil and
|
||||
spawnerdef.cyclic_spawning == false then
|
||||
self.spawning_data[name] = nil
|
||||
return true
|
||||
end
|
||||
self.spawner_init_state = "abs_height"
|
||||
end
|
||||
|
||||
starttime = adv_spawning.check_time(starttime, name .. "cyclic check")
|
||||
if self.spawner_init_state == "abs_height" then
|
||||
--if spawner is far away from spawn area don't even try to spawn
|
||||
if spawnerdef.absolute_height ~= nil then
|
||||
if spawnerdef.absolute_height.min ~= nil and
|
||||
spawnerdef.absolute_height.min
|
||||
> pos.y + (adv_spawning.spawner_distance/2) then
|
||||
self.spawning_data[name] = nil
|
||||
return true
|
||||
end
|
||||
|
||||
if spawnerdef.absolute_height.max ~= nil
|
||||
and spawnerdef.absolute_height.max
|
||||
< pos.y - (adv_spawning.spawner_distance/2) then
|
||||
self.spawning_data[name] = nil
|
||||
return true
|
||||
end
|
||||
end
|
||||
self.spawner_init_state = "environment"
|
||||
end
|
||||
|
||||
starttime = adv_spawning.check_time(starttime, name .. "height check")
|
||||
if self.spawner_init_state == "environment" then
|
||||
|
||||
local runidx = 1
|
||||
local radius = adv_spawning.spawner_distance / 2
|
||||
|
||||
if self.spawnerinit_env_radius ~= nil then
|
||||
runidx = self.spawnerinit_env_radius
|
||||
end
|
||||
|
||||
local found = false
|
||||
|
||||
for i = runidx , radius, 1 do
|
||||
adv_spawning.quota_leave()
|
||||
|
||||
if not adv_spawning.quota_enter() then
|
||||
self.spawnerinit_env_radius = runidx
|
||||
return false
|
||||
end
|
||||
|
||||
if spawnerdef.spawn_inside == nil then
|
||||
print(name .. " tries to spawn within nil")
|
||||
assert(false)
|
||||
end
|
||||
|
||||
local resultpos = adv_spawning.find_nodes_in(pos, runidx, runidx, spawnerdef.spawn_inside)
|
||||
|
||||
if (resultpos ~= nil) then
|
||||
local node = minetest.get_node_or_nil(resultpos)
|
||||
found = true
|
||||
break
|
||||
end
|
||||
end
|
||||
|
||||
starttime = adv_spawning.check_time(starttime, name ..
|
||||
" at environment check radius was: " .. radius ..
|
||||
" env: " .. dump(spawnerdef.spawn_inside))
|
||||
|
||||
if not found then
|
||||
self.spawning_data[name] = nil
|
||||
end
|
||||
end
|
||||
|
||||
self.spawner_init_state = "initial"
|
||||
self.spawning_data[name] = spawnerdef.spawn_interval * math.random()
|
||||
return true
|
||||
end
|
||||
|
||||
--------------------------------------------------------------------------------
|
||||
-- @function [parent=#adv_spawning] seed_scan_for_applyable_spawners
|
||||
-- @param self spawner entity
|
||||
|
@ -251,12 +369,17 @@ function adv_spawning.seed_scan_for_applyable_spawners(self)
|
|||
end
|
||||
|
||||
local runindex = 0
|
||||
|
||||
if self.spawner_init_idx ~= nil then
|
||||
runindex = self.spawner_init_idx
|
||||
end
|
||||
|
||||
local pos = self.object:getpos()
|
||||
for key,value in pairs(adv_spawning.spawner_definitions) do
|
||||
if not adv_spawning.quota_enter() then
|
||||
return false
|
||||
end
|
||||
local starttime = adv_spawning.gettime()
|
||||
|
||||
local continue = false
|
||||
|
||||
if runindex >= self.initialized_spawners then
|
||||
|
@ -265,50 +388,15 @@ function adv_spawning.seed_scan_for_applyable_spawners(self)
|
|||
continue = true
|
||||
end
|
||||
|
||||
|
||||
if not continue then
|
||||
runindex = runindex + 1
|
||||
|
||||
--check if cyclic spawning is enabled
|
||||
if not continue and
|
||||
value.cyclic_spawning ~= nil and
|
||||
value.cyclic_spawning == false then
|
||||
continue = true
|
||||
if not adv_spawning.init_spawner(self, pos, key, value) then
|
||||
return false
|
||||
end
|
||||
end
|
||||
|
||||
--if spawner is far away from spawn area don't even try to spawn
|
||||
if not continue and
|
||||
value.absolute_height ~= nil then
|
||||
if value.absolute_height.min ~= nil and
|
||||
value.absolute_height.min
|
||||
> pos.y + (adv_spawning.spawner_distance/2) then
|
||||
continue = true
|
||||
end
|
||||
|
||||
if value.absolute_height.max ~= nil
|
||||
and value.absolute_height.max
|
||||
< pos.y - (adv_spawning.spawner_distance/2) then
|
||||
continue = true
|
||||
end
|
||||
end
|
||||
starttime = adv_spawning.check_time(starttime, key .. " at spawn range check")
|
||||
|
||||
--check for presence of environment
|
||||
if not continue then
|
||||
local radius =
|
||||
math.sqrt(adv_spawning.spawner_distance*
|
||||
adv_spawning.spawner_distance*2)/2
|
||||
|
||||
if minetest.find_node_near(pos,radius,
|
||||
value.spawn_inside) == nil then
|
||||
continue = false
|
||||
end
|
||||
end
|
||||
starttime = adv_spawning.check_time(starttime, key .. " at environment check")
|
||||
|
||||
if not continue then
|
||||
self.spawning_data[key] = value.spawn_interval * math.random()
|
||||
else
|
||||
self.spawning_data[key] = nil
|
||||
end
|
||||
adv_spawning.quota_leave()
|
||||
end
|
||||
|
||||
return self.initialized_spawners == #adv_spawning.spawner_definitions
|
||||
|
|
Loading…
Reference in New Issue