From 641780dd26378369d721af9c94729a5406f48afe Mon Sep 17 00:00:00 2001 From: crabman77 Date: Wed, 3 Feb 2016 04:22:41 +0100 Subject: [PATCH] update mobs mod --- mods/mobs/README.txt | 1 + mods/mobs/api.lua | 65 +++++++++++++++++++++++--------------- mods/mobs/mese_monster.lua | 2 +- mods/mobs/spawner.lua | 54 ++++++++++++++++++++++++------- 4 files changed, 83 insertions(+), 39 deletions(-) diff --git a/mods/mobs/README.txt b/mods/mobs/README.txt index 346f3a57..0082e4bb 100755 --- a/mods/mobs/README.txt +++ b/mods/mobs/README.txt @@ -28,6 +28,7 @@ This mod contains the following additions: Changelog: +1.25- Mobs no longer spawn within 12 blocks of player or despawn within same range, spawners now have player detection, Code tidy and tweak. 1.24- Added feature where certain animals run away when punched (runaway = true in mob definition) 1.23- Added mob spawner block for admin to setup spawners in-game (place and right click to enter settings) 1.22- Added ability to name tamed animals and npc using nametags, also npc will attack anyone who punches them apart from owner diff --git a/mods/mobs/api.lua b/mods/mobs/api.lua index 69712d14..2520165c 100755 --- a/mods/mobs/api.lua +++ b/mods/mobs/api.lua @@ -1,4 +1,4 @@ --- Mobs Api (29th January 2016) +-- Mobs Api (2nd February 2016) mobs = {} mobs.mod = "redo" @@ -35,21 +35,12 @@ end set_velocity = function(self, v) - local x = 0 - local z = 0 - - if v and v ~= 0 then - - local yaw = (self.object:getyaw() + self.rotate) or 0 - - x = math.sin(yaw) * -v - z = math.cos(yaw) * v - end + local yaw = (self.object:getyaw() + self.rotate) or 0 self.object:setvelocity({ - x = x, + x = math.sin(yaw) * -v, y = self.object:getvelocity().y, - z = z + z = math.cos(yaw) * v }) end @@ -775,6 +766,19 @@ minetest.register_entity(name, { if self.lifetimer <= 0 then + -- only despawn away from player + local objs = minetest.get_objects_inside_radius(pos, 10) + + for _,oir in pairs(objs) do + + if oir:is_player() then + + self.lifetimer = 20 + + return + end + end + minetest.log("action", "lifetimer expired, removed " .. self.name) @@ -1073,7 +1077,7 @@ minetest.register_entity(name, { } if vec.x ~= 0 - or vec.z ~= 0 then + and vec.z ~= 0 then yaw = (math.atan(vec.z / vec.x) + pi / 2) - self.rotate @@ -1142,7 +1146,7 @@ minetest.register_entity(name, { } if vec.x ~= 0 - or vec.z ~= 0 then + and vec.z ~= 0 then yaw = (math.atan(vec.z / vec.x) + pi / 2) - self.rotate @@ -1151,7 +1155,7 @@ minetest.register_entity(name, { end end else - yaw = self.object:getyaw() + ((math.random(0, 360) - 180) / 180 * pi) + yaw = (math.random(0, 360) - 180) / 180 * pi end self.object:setyaw(yaw) @@ -1205,7 +1209,7 @@ minetest.register_entity(name, { } if vec.x ~= 0 - or vec.z ~= 0 then + and vec.z ~= 0 then yaw = math.atan(vec.z / vec.x) + 3 * pi / 2 - self.rotate @@ -1219,7 +1223,7 @@ minetest.register_entity(name, { -- otherwise randomly turn elseif math.random(1, 100) <= 30 then - yaw = self.object:getyaw() + ((math.random(0, 360) - 180) / 180 * pi) + yaw = (math.random(0, 360) - 180) / 180 * pi self.object:setyaw(yaw) end @@ -1307,7 +1311,7 @@ minetest.register_entity(name, { } if vec.x ~= 0 - or vec.z ~= 0 then + and vec.z ~= 0 then yaw = math.atan(vec.z / vec.x) + pi / 2 - self.rotate @@ -1456,7 +1460,7 @@ minetest.register_entity(name, { } if vec.x ~= 0 - or vec.z ~= 0 then + and vec.z ~= 0 then yaw = (math.atan(vec.z / vec.x) + pi / 2) - self.rotate @@ -1538,7 +1542,7 @@ minetest.register_entity(name, { } if vec.x ~= 0 - or vec.z ~= 0 then + and vec.z ~= 0 then yaw = (math.atan(vec.z / vec.x) + pi / 2) - self.rotate @@ -1573,8 +1577,7 @@ minetest.register_entity(name, { local obj = minetest.add_entity(p, self.arrow) local ent = obj:get_luaentity() - - local amount = (vec.x ^ 2 + vec.y ^ 2 + vec.z ^ 2) ^ 0.5 + local amount = (vec.x * vec.x + vec.y * vec.y + vec.z * vec.z) ^ 0.5 local v = ent.velocity ent.switch = 1 @@ -1670,7 +1673,7 @@ minetest.register_entity(name, { } if vec.x ~= 0 - or vec.z ~= 0 then + and vec.z ~= 0 then local yaw = math.atan(vec.z / vec.x) + 3 * pi / 2 - self.rotate @@ -1791,8 +1794,8 @@ minetest.register_entity(name, { self.object:set_hp(self.health) self.object:set_armor_groups({fleshy = self.armor}) self.old_y = self.object:getpos().y - self.object:setyaw(math.random(1, 360) / 180 * pi) - self.sounds.distance = (self.sounds.distance or 10) + self.object:setyaw((math.random(0, 360) - 180) / 180 * pi) + self.sounds.distance = self.sounds.distance or 10 self.textures = textures self.mesh = mesh self.collisionbox = colbox @@ -1893,6 +1896,16 @@ function mobs:spawn_specific(name, nodes, neighbors, min_light, max_light, -- spawn above node pos.y = pos.y + 1 + -- only spawn away from player + local objs = minetest.get_objects_inside_radius(pos, 10) + + for _,oir in pairs(objs) do + + if oir:is_player() then + return + end + end + -- mobs cannot spawn in protected areas when enabled if spawn_protected == 1 and minetest.is_protected(pos, "") diff --git a/mods/mobs/mese_monster.lua b/mods/mobs/mese_monster.lua index 7fde97de..92ac8a20 100755 --- a/mods/mobs/mese_monster.lua +++ b/mods/mobs/mese_monster.lua @@ -37,7 +37,7 @@ mobs:register_mob("mobs:mese_monster", { jump_height = 8, fall_damage = 0, fall_speed = -6, - stepheight = 3, + stepheight = 2.1, -- drops mese when dead drops = { {name = "default:mese_crystal", diff --git a/mods/mobs/spawner.lua b/mods/mobs/spawner.lua index 47d45eb2..3466d201 100755 --- a/mods/mobs/spawner.lua +++ b/mods/mobs/spawner.lua @@ -1,6 +1,6 @@ -- mob spawner -local spawner_default = "mobs:pig 10 15 0" +local spawner_default = "mobs:pig 10 15 0 0" minetest.register_node("mobs:spawner", { tiles = {"mob_spawner.png"}, @@ -15,13 +15,18 @@ minetest.register_node("mobs:spawner", { local meta = minetest.get_meta(pos) -- text entry formspec - meta:set_string("formspec", "field[text;mob_name min_light max_light amount;${command}]") + meta:set_string("formspec", "field[text;Mob MinLight MaxLight Amount PlayerDist;${command}]") meta:set_string("infotext", "Spawner Not Active (enter settings)") meta:set_string("command", spawner_default) end, on_right_click = function(pos, placer) - local meta = minetest.get_meta(pos) + + if minetest.is_protected(pos, placer:get_player_name()) then + return + end + +-- local meta = minetest.get_meta(pos) end, on_receive_fields = function(pos, formname, fields, sender) @@ -39,15 +44,17 @@ minetest.register_node("mobs:spawner", { return end - local mob = comm[1] - local mlig = tonumber(comm[2]) - local xlig = tonumber(comm[3]) - local num = tonumber(comm[4]) + local mob = comm[1] -- mob to spawn + local mlig = tonumber(comm[2]) -- min light + local xlig = tonumber(comm[3]) -- max light + local num = tonumber(comm[4]) -- total mobs in area + local pla = tonumber(comm[5])-- player distance (0 to disable) - if mob and mob ~= "" + if mob and mob ~= "" and mobs.spawning_mobs[mob] == true and num and num >= 0 and num <= 10 and mlig and mlig >= 0 and mlig <= 15 - and xlig and xlig >= 0 and xlig <= 15 then + and xlig and xlig >= 0 and xlig <= 15 + and pla and pla >=0 and pla <= 20 then meta:set_string("command", fields.text) meta:set_string("infotext", "Spawner Active (" .. mob .. ")") @@ -79,6 +86,7 @@ minetest.register_abm({ local mlig = tonumber(comm[2]) local xlig = tonumber(comm[3]) local num = tonumber(comm[4]) + local pla = tonumber(comm[5]) or 0 -- if amount is 0 then do nothing if num == 0 then @@ -88,7 +96,7 @@ minetest.register_abm({ local count = 0 local ent = nil - -- count objects of same type in area + -- count mob objects of same type in area for k, obj in pairs(objs) do ent = obj:get_luaentity() @@ -103,6 +111,28 @@ minetest.register_abm({ return end + -- spawn mob if player detected and in range + if pla > 0 then + + local in_range = 0 + local objs = minetest.get_objects_inside_radius(pos, pla) + + for _,oir in pairs(objs) do + + if oir:is_player() then + + in_range = 1 + + break + end + end + + -- player not found + if in_range == 0 then + return + end + end + -- find air blocks within 5 nodes of spawner local air = minetest.find_nodes_in_area( {x = pos.x - 5, y = pos.y, z = pos.z - 5}, @@ -113,12 +143,12 @@ minetest.register_abm({ if air and #air > 0 then local pos2 = air[math.random(#air)] - local lig = minetest.get_node_light(pos2) + local lig = minetest.get_node_light(pos2) or 0 pos2.y = pos2.y + 0.5 -- only if light levels are within range - if lig and lig >= mlig and lig <= xlig then + if lig >= mlig and lig <= xlig then minetest.add_entity(pos2, mob) end end