mirror of
				https://codeberg.org/tenplus1/mobs_redo.git
				synced 2025-10-31 15:45:22 +01:00 
			
		
		
		
	tweak/tidy, check env damage when riding mob
This commit is contained in:
		
							
								
								
									
										177
									
								
								api.lua
									
									
									
									
									
								
							
							
						
						
									
										177
									
								
								api.lua
									
									
									
									
									
								
							| @@ -19,7 +19,7 @@ end | |||||||
|  |  | ||||||
| mobs = { | mobs = { | ||||||
| 	mod = "redo", | 	mod = "redo", | ||||||
| 	version = "20241130", | 	version = "20241201", | ||||||
| 	spawning_mobs = {}, | 	spawning_mobs = {}, | ||||||
| 	translate = S, | 	translate = S, | ||||||
| 	node_snow = has(minetest.registered_aliases["mapgen_snow"]) | 	node_snow = has(minetest.registered_aliases["mapgen_snow"]) | ||||||
| @@ -263,27 +263,26 @@ end | |||||||
|  |  | ||||||
| function mob_class:collision() | function mob_class:collision() | ||||||
|  |  | ||||||
| 	local pos = self.object:get_pos() ; if not pos then return {0, 0} end | 	local pos = self.object:get_pos() ; if not pos then return 0, 0 end | ||||||
| 	local x, z = 0, 0 | 	local x, z = 0, 0 | ||||||
| 	local prop = self.object:get_properties() | 	local prop = self.object:get_properties() | ||||||
| 	local width = -prop.collisionbox[1] + prop.collisionbox[4] + 0.5 | 	local width = -prop.collisionbox[1] + prop.collisionbox[4] + 0.5 | ||||||
| 	local pos2, vec, force |  | ||||||
|  |  | ||||||
| 	for _,object in pairs(minetest.get_objects_inside_radius(pos, width)) do | 	for _,object in pairs(minetest.get_objects_inside_radius(pos, width)) do | ||||||
|  |  | ||||||
| 		if object:is_player() then | 		if object:is_player() then | ||||||
|  |  | ||||||
| 			pos2 = object:get_pos() | 			local pos2 = object:get_pos() | ||||||
| 			vec  = {x = pos.x - pos2.x, z = pos.z - pos2.z} | 			local vx, vz  = pos.x - pos2.x, pos.z - pos2.z | ||||||
| 			force = width - vector.distance( | 			local force = width - (vx * vx + vz * vz) ^ 0.5 | ||||||
| 					{x = pos.x, y = 0, z = pos.z}, {x = pos2.x, y = 0, z = pos2.z}) |  | ||||||
|  |  | ||||||
| 			x = x + (vec.x * force) | 			if force > 0 then | ||||||
| 			z = z + (vec.z * force) | 				force = force * 2 ; x = x + vx * force ; z = z + vz * force | ||||||
|  | 			end | ||||||
| 		end | 		end | ||||||
| 	end | 	end | ||||||
|  |  | ||||||
| 	return({x, z}) | 	return x, z | ||||||
| end | end | ||||||
|  |  | ||||||
| -- check if string exists in another string or table | -- check if string exists in another string or table | ||||||
| @@ -325,7 +324,7 @@ function mob_class:set_velocity(v) | |||||||
| 	local c_x, c_y = 0, 0 | 	local c_x, c_y = 0, 0 | ||||||
|  |  | ||||||
| 	-- can mob be pushed, if so calculate direction | 	-- can mob be pushed, if so calculate direction | ||||||
| 	if self.pushable then c_x, c_y = unpack(self:collision()) end | 	if self.pushable then c_x, c_y = self:collision() end | ||||||
|  |  | ||||||
| 	local yaw = (self.object:get_yaw() or 0) + (self.rotate or 0) | 	local yaw = (self.object:get_yaw() or 0) + (self.rotate or 0) | ||||||
|  |  | ||||||
| @@ -634,9 +633,9 @@ function mob_class:update_tag(newname) | |||||||
|  |  | ||||||
| 	local text = "" | 	local text = "" | ||||||
|  |  | ||||||
| 	if self.horny == true then | 	if self.horny then | ||||||
| 		text = "\nLoving: " .. (self.hornytimer - (HORNY_TIME + HORNY_AGAIN_TIME)) | 		text = "\nLoving: " .. (self.hornytimer - (HORNY_TIME + HORNY_AGAIN_TIME)) | ||||||
| 	elseif self.child == true then | 	elseif self.child then | ||||||
| 		text = "\nGrowing: " .. (self.hornytimer - CHILD_GROW_TIME) | 		text = "\nGrowing: " .. (self.hornytimer - CHILD_GROW_TIME) | ||||||
| 	elseif self._tame_countdown then | 	elseif self._tame_countdown then | ||||||
| 		text = "\nTaming: " .. self._tame_countdown | 		text = "\nTaming: " .. self._tame_countdown | ||||||
| @@ -888,28 +887,23 @@ end | |||||||
|  |  | ||||||
| -- Returns true if node can deal damage to self | -- Returns true if node can deal damage to self | ||||||
|  |  | ||||||
| local function is_node_dangerous(mob_object, nodename) | local function is_node_dangerous(self, nodename) | ||||||
|  |  | ||||||
| 	if mob_object.water_damage > 0 |  | ||||||
| 	and minetest.get_item_group(nodename, "water") ~= 0 then return true end |  | ||||||
|  |  | ||||||
| 	if mob_object.lava_damage > 0 |  | ||||||
| 	and minetest.get_item_group(nodename, "lava") ~= 0 then return true end |  | ||||||
|  |  | ||||||
| 	if mob_object.fire_damage > 0 |  | ||||||
| 	and minetest.get_item_group(nodename, "fire") ~= 0 then return true end |  | ||||||
|  |  | ||||||
| 	local def = minetest.registered_nodes[nodename] | 	local def = minetest.registered_nodes[nodename] | ||||||
|  |  | ||||||
| 	if mob_object.node_damage and def.damage_per_second > 0 then | 	if (self.water_damage and def.groups.water) | ||||||
|  | 	or (self.lava_damage and def.groups.lava) | ||||||
|  | 	or (self.fire_damage and def.groups.fire) then return true end | ||||||
|  |  | ||||||
|  | 	if self.node_damage and def.damage_per_second > 0 then | ||||||
|  |  | ||||||
| 		-- check for node immunity or special damage | 		-- check for node immunity or special damage | ||||||
| 		local damage = def.damage_per_second | 		local damage = def.damage_per_second | ||||||
|  |  | ||||||
| 		for n = 1, #mob_object.immune_to do | 		for n = 1, #mob_object.immune_to do | ||||||
|  |  | ||||||
| 			if mob_object.immune_to[n][1] == nodename then | 			if self.immune_to[n][1] == nodename then | ||||||
| 				damage = mob_object.immune_to[n][2] or 0 ; break | 				damage = self.immune_to[n][2] or 0 ; break | ||||||
| 			end | 			end | ||||||
| 		end | 		end | ||||||
|  |  | ||||||
| @@ -1080,14 +1074,14 @@ function mob_class:do_env_damage() | |||||||
|  |  | ||||||
| 	--- suffocation inside solid node | 	--- suffocation inside solid node | ||||||
| 	if (self.suffocation and self.suffocation ~= 0) | 	if (self.suffocation and self.suffocation ~= 0) | ||||||
| 	and (nodef.walkable == nil or nodef.walkable == true) | 	and (nodef.walkable == nil or nodef.walkable) | ||||||
| 	and (nodef.collision_box == nil or nodef.collision_box.type == "regular") | 	and (nodef.collision_box == nil or nodef.collision_box.type == "regular") | ||||||
| 	and (nodef.node_box == nil or nodef.node_box.type == "regular") | 	and (nodef.node_box == nil or nodef.node_box.type == "regular") | ||||||
| 	and (nodef.groups.disable_suffocation ~= 1) then | 	and (nodef.groups.disable_suffocation ~= 1) then | ||||||
|  |  | ||||||
| 		local damage | 		local damage | ||||||
|  |  | ||||||
| 		if type(self.suffocation) == "boolean" and self.suffocation == true then | 		if type(self.suffocation) == "boolean" and self.suffocation then | ||||||
| 			damage = 2 | 			damage = 2 | ||||||
| 		else | 		else | ||||||
| 			damage = self.suffocation | 			damage = self.suffocation | ||||||
| @@ -1123,10 +1117,7 @@ function mob_class:do_jump() | |||||||
| 	local blocked = minetest.registered_nodes[self.looking_above].walkable | 	local blocked = minetest.registered_nodes[self.looking_above].walkable | ||||||
|  |  | ||||||
| 	-- if mob can leap then remove blockages and let them try | 	-- if mob can leap then remove blockages and let them try | ||||||
| 	if self.can_leap == true then | 	if self.can_leap then blocked = false ; self.facing_fence = false end | ||||||
| 		blocked = false |  | ||||||
| 		self.facing_fence = false |  | ||||||
| 	end |  | ||||||
|  |  | ||||||
| 	-- jump if possible | 	-- jump if possible | ||||||
| 	if self.jump and self.jump_height > 0 and not self.fly and not self.child | 	if self.jump and self.jump_height > 0 and not self.fly and not self.child | ||||||
| @@ -1231,7 +1222,7 @@ end | |||||||
| function mob_class:breed() | function mob_class:breed() | ||||||
|  |  | ||||||
| 	-- child takes a long time before growing into adult | 	-- child takes a long time before growing into adult | ||||||
| 	if self.child == true then | 	if self.child then | ||||||
|  |  | ||||||
| 		self.hornytimer = self.hornytimer + 1 | 		self.hornytimer = self.hornytimer + 1 | ||||||
|  |  | ||||||
| @@ -1274,7 +1265,7 @@ function mob_class:breed() | |||||||
|  |  | ||||||
| 	-- horny animal can mate for HORNY_TIME seconds, | 	-- horny animal can mate for HORNY_TIME seconds, | ||||||
| 	-- afterwards horny animal cannot mate again for HORNY_AGAIN_TIME seconds | 	-- afterwards horny animal cannot mate again for HORNY_AGAIN_TIME seconds | ||||||
| 	if self.horny == true and self.hornytimer < HORNY_TIME + HORNY_AGAIN_TIME then | 	if self.horny and self.hornytimer < HORNY_TIME + HORNY_AGAIN_TIME then | ||||||
|  |  | ||||||
| 		self.hornytimer = self.hornytimer + 1 | 		self.hornytimer = self.hornytimer + 1 | ||||||
|  |  | ||||||
| @@ -1287,7 +1278,7 @@ function mob_class:breed() | |||||||
| 	end | 	end | ||||||
|  |  | ||||||
| 	-- find another same animal who is also horny and mate if nearby | 	-- find another same animal who is also horny and mate if nearby | ||||||
| 	if self.horny == true and self.hornytimer <= HORNY_TIME then | 	if self.horny and self.hornytimer <= HORNY_TIME then | ||||||
|  |  | ||||||
| 		local pos = self.object:get_pos() | 		local pos = self.object:get_pos() | ||||||
| 		local prop = self.object:get_properties().collisionbox | 		local prop = self.object:get_properties().collisionbox | ||||||
| @@ -1323,8 +1314,8 @@ function mob_class:breed() | |||||||
| 			end | 			end | ||||||
|  |  | ||||||
| 			-- found another similar horny animal that isn't self? | 			-- found another similar horny animal that isn't self? | ||||||
| 			if ent and ent.object ~= self.object and canmate == true | 			if ent and ent.object ~= self.object and canmate | ||||||
| 			and ent.horny == true and ent.hornytimer <= HORNY_TIME then | 			and ent.horny and ent.hornytimer <= HORNY_TIME then | ||||||
|  |  | ||||||
| 				local pos2 = ent.object:get_pos() | 				local pos2 = ent.object:get_pos() | ||||||
|  |  | ||||||
| @@ -1394,7 +1385,7 @@ function mob_class:replace(pos) | |||||||
| 	local vel = self.object:get_velocity() ; if not vel then return end | 	local vel = self.object:get_velocity() ; if not vel then return end | ||||||
|  |  | ||||||
| 	if not mobs_griefing or not self.replace_rate or not self.replace_what | 	if not mobs_griefing or not self.replace_rate or not self.replace_what | ||||||
| 	or self.child == true or vel.y ~= 0 or random(self.replace_rate) > 1 then | 	or self.child or vel.y ~= 0 or random(self.replace_rate) > 1 then | ||||||
| 		return | 		return | ||||||
| 	end | 	end | ||||||
|  |  | ||||||
| @@ -1450,7 +1441,7 @@ end | |||||||
|  |  | ||||||
| function mob_class:day_docile() | function mob_class:day_docile() | ||||||
|  |  | ||||||
| 	if self.docile_by_day == true | 	if self.docile_by_day | ||||||
| 	and self.time_of_day > 0.2 and self.time_of_day < 0.8 then return true end | 	and self.time_of_day > 0.2 and self.time_of_day < 0.8 then return true end | ||||||
| end | end | ||||||
|  |  | ||||||
| @@ -1514,22 +1505,21 @@ function mob_class:smart_mobs(s, p, dist, dtime) | |||||||
| 	-- im stuck, search for path | 	-- im stuck, search for path | ||||||
| 	if not has_lineofsight then | 	if not has_lineofsight then | ||||||
|  |  | ||||||
| 		if los_switcher == true then | 		if los_switcher then | ||||||
| 			use_pathfind = true | 			use_pathfind = true | ||||||
| 			los_switcher = false | 			los_switcher = false | ||||||
| 		end -- cannot see target! | 		end -- cannot see target! | ||||||
| 	else | 	else | ||||||
| 		if los_switcher == false then | 		if not los_switcher then | ||||||
|  |  | ||||||
| 			los_switcher = true | 			los_switcher = true | ||||||
| 			use_pathfind = false | 			use_pathfind = false | ||||||
|  |  | ||||||
| 			minetest.after(1, function(self) | 			minetest.after(1, function(self) | ||||||
|  |  | ||||||
| 				if self.object:get_luaentity() then | 				if not self.object:get_luaentity() then return end | ||||||
|  |  | ||||||
| 					if has_lineofsight then self.path.following = false end | 				if has_lineofsight then self.path.following = false end | ||||||
| 				end |  | ||||||
| 			end, self) | 			end, self) | ||||||
| 		end -- can see target! | 		end -- can see target! | ||||||
| 	end | 	end | ||||||
| @@ -1541,10 +1531,9 @@ function mob_class:smart_mobs(s, p, dist, dtime) | |||||||
|  |  | ||||||
| 		minetest.after(1, function(self) | 		minetest.after(1, function(self) | ||||||
|  |  | ||||||
| 			if self.object:get_luaentity() then | 			if not self.object:get_luaentity() then return end | ||||||
|  |  | ||||||
| 				if has_lineofsight then self.path.following = false end | 			if has_lineofsight then self.path.following = false end | ||||||
| 			end |  | ||||||
| 		end, self) | 		end, self) | ||||||
| 	end | 	end | ||||||
|  |  | ||||||
| @@ -1555,16 +1544,15 @@ function mob_class:smart_mobs(s, p, dist, dtime) | |||||||
|  |  | ||||||
| 		minetest.after(1, function(self) | 		minetest.after(1, function(self) | ||||||
|  |  | ||||||
| 			if self.object:get_luaentity() then | 			if not self.object:get_luaentity() then return end | ||||||
|  |  | ||||||
| 				if has_lineofsight then self.path.following = false end | 			if has_lineofsight then self.path.following = false end | ||||||
| 			end |  | ||||||
| 		end, self) | 		end, self) | ||||||
| 	end | 	end | ||||||
|  |  | ||||||
| 	local prop = self.object:get_properties() | 	local prop = self.object:get_properties() | ||||||
|  |  | ||||||
| 	if abs(vsubtract(s, target_pos).y) > prop.stepheight then | 	if abs(s.y - target_pos.y) > prop.stepheight then | ||||||
|  |  | ||||||
| 		if height_switcher then use_pathfind = true ; height_switcher = false end | 		if height_switcher then use_pathfind = true ; height_switcher = false end | ||||||
| 	else | 	else | ||||||
| @@ -1583,9 +1571,7 @@ function mob_class:smart_mobs(s, p, dist, dtime) | |||||||
| 				{x = s.x, y = s.y - 4, z = s.z}, 1) | 				{x = s.x, y = s.y - 4, z = s.z}, 1) | ||||||
|  |  | ||||||
| 		-- determine node above ground (adjust height for player models) | 		-- determine node above ground (adjust height for player models) | ||||||
| 		if not ssight then | 		if not ssight then s.y = sground.y + 1 end | ||||||
| 			s.y = sground.y + 1 |  | ||||||
| 		end |  | ||||||
|  |  | ||||||
| 		local p1 = self.attack and self.attack:get_pos() | 		local p1 = self.attack and self.attack:get_pos() | ||||||
|  |  | ||||||
| @@ -1837,7 +1823,7 @@ function mob_class:general_attack() | |||||||
|  |  | ||||||
| 		-- choose closest player to attack that isnt self | 		-- choose closest player to attack that isnt self | ||||||
| 		if dist ~= 0 and dist < min_dist | 		if dist ~= 0 and dist < min_dist | ||||||
| 		and self:line_of_sight(sp, p) == true and not is_peaceful_player(player) then | 		and self:line_of_sight(sp, p) and not is_peaceful_player(player) then | ||||||
| 			min_dist = dist | 			min_dist = dist | ||||||
| 			min_player = player | 			min_player = player | ||||||
| 		end | 		end | ||||||
| @@ -1897,7 +1883,7 @@ function mob_class:do_runaway_from() | |||||||
| 			dist = get_distance(p, s) | 			dist = get_distance(p, s) | ||||||
|  |  | ||||||
| 			-- choose closest player/mob to runaway from | 			-- choose closest player/mob to runaway from | ||||||
| 			if dist < min_dist and self:line_of_sight(sp, p) == true then | 			if dist < min_dist and self:line_of_sight(sp, p) then | ||||||
| 				min_dist = dist | 				min_dist = dist | ||||||
| 				min_player = player | 				min_player = player | ||||||
| 			end | 			end | ||||||
| @@ -2065,39 +2051,26 @@ function mob_class:do_states(dtime) | |||||||
| 	local yaw = self.object:get_yaw() ; if not yaw then return end | 	local yaw = self.object:get_yaw() ; if not yaw then return end | ||||||
|  |  | ||||||
| 	-- are we standing in something that hurts ?  Try to get out | 	-- are we standing in something that hurts ?  Try to get out | ||||||
| 	if is_node_dangerous(self, self.standing_in) then | 	if is_node_dangerous(self, self.standing_in) then -- and self.pause_timer <= 0 then | ||||||
|  |  | ||||||
| 		local s = self.object:get_pos() | 		local s = self.object:get_pos() | ||||||
| 		local grps = {} |  | ||||||
|  |  | ||||||
| 		if self.water_damage > 0 then table.insert(grps, "group:water") end | 		local lp = minetest.find_nodes_in_area_under_air( | ||||||
| 		if self.fire_damage > 0 then table.insert(grps, "group:fire") end | 				{x = s.x - 7, y = s.y - 1.0, z = s.z - 7}, | ||||||
| 		if self.lava_damage > 0 then table.insert(grps, "group:lava") end | 				{x = s.x + 7, y = s.y + 1.0, z = s.z + 7}, | ||||||
|  | 				{"group:cracky", "group:crumbly", "group:choppy", "group:solid"}) | ||||||
|  |  | ||||||
| 		local lp = minetest.find_node_near(s, 1, grps) | 		-- did we find land ? if so face random block to climb onto | ||||||
|  | 		if #lp > 0 then | ||||||
|  |  | ||||||
| 		if lp then | 			yaw = self:yaw_to_pos( lp[random(#lp)] ) | ||||||
|  | 		 | ||||||
|  | 			self.pause_timer = 3 | ||||||
|  | 			self.following = nil | ||||||
|  | 			self:set_velocity(self.run_velocity) | ||||||
|  | 			self:set_animation("walk") | ||||||
|  |  | ||||||
| 			if self.pause_timer <= 0 then | 			return | ||||||
|  |  | ||||||
| 				lp = minetest.find_nodes_in_area_under_air( |  | ||||||
| 						{x = s.x - 5, y = s.y , z = s.z - 5}, |  | ||||||
| 						{x = s.x + 5, y = s.y + 2, z = s.z + 5}, |  | ||||||
| 						{"group:cracky", "group:crumbly", "group:choppy", "group:solid"}) |  | ||||||
|  |  | ||||||
| 				-- did we find land ? if so face random block to climb onto |  | ||||||
| 				if lp and #lp > 0 then |  | ||||||
| 					yaw = self:yaw_to_pos( lp[random(#lp)] ) |  | ||||||
| 				end |  | ||||||
|  |  | ||||||
| 				self.pause_timer = 3 |  | ||||||
| 				self.following = nil |  | ||||||
|  |  | ||||||
| 				self:set_velocity(self.run_velocity) |  | ||||||
| 				self:set_animation("walk") |  | ||||||
|  |  | ||||||
| 				return |  | ||||||
| 			end |  | ||||||
| 		end | 		end | ||||||
| 	end | 	end | ||||||
|  |  | ||||||
| @@ -2156,8 +2129,7 @@ function mob_class:do_states(dtime) | |||||||
| 		end | 		end | ||||||
|  |  | ||||||
| 		-- stand for great fall in front | 		-- stand for great fall in front | ||||||
| 		if self.facing_fence == true or self.at_cliff | 		if self.facing_fence or self.at_cliff or random(100) <= self.stand_chance then | ||||||
| 		or random(100) <= self.stand_chance then |  | ||||||
|  |  | ||||||
| 			-- don't stand if mob flies and keep_flying set | 			-- don't stand if mob flies and keep_flying set | ||||||
| 			if (self.fly and not self.keep_flying) or not self.fly then | 			if (self.fly and not self.keep_flying) or not self.fly then | ||||||
| @@ -2443,8 +2415,7 @@ function mob_class:do_states(dtime) | |||||||
| 					self.timer = 0 | 					self.timer = 0 | ||||||
|  |  | ||||||
| 					-- no custom attack or custom attack returns true to continue | 					-- no custom attack or custom attack returns true to continue | ||||||
| 					if not self.custom_attack | 					if not self.custom_attack or self:custom_attack(self, p) then | ||||||
| 					or self:custom_attack(self, p) == true then |  | ||||||
|  |  | ||||||
| 						self:set_animation("punch") | 						self:set_animation("punch") | ||||||
|  |  | ||||||
| @@ -2453,7 +2424,7 @@ function mob_class:do_states(dtime) | |||||||
| 						p2.y = p2.y + .5 | 						p2.y = p2.y + .5 | ||||||
| 						s2.y = s2.y + .5 | 						s2.y = s2.y + .5 | ||||||
|  |  | ||||||
| 						if self:line_of_sight(p2, s2) == true then | 						if self:line_of_sight(p2, s2) then | ||||||
|  |  | ||||||
| 							-- play attack sound | 							-- play attack sound | ||||||
| 							self:mob_sound(self.sounds.attack) | 							self:mob_sound(self.sounds.attack) | ||||||
| @@ -2846,7 +2817,7 @@ function mob_class:on_punch(hitter, tflp, tool_capabilities, dir, damage) | |||||||
| 	end | 	end | ||||||
|  |  | ||||||
| 	-- if skittish then run away | 	-- if skittish then run away | ||||||
| 	if self.runaway == true and self.order ~= "stand" then | 	if self.runaway and self.order ~= "stand" then | ||||||
|  |  | ||||||
| 		local lp = hitter:get_pos() | 		local lp = hitter:get_pos() | ||||||
|  |  | ||||||
| @@ -2861,7 +2832,7 @@ function mob_class:on_punch(hitter, tflp, tool_capabilities, dir, damage) | |||||||
|  |  | ||||||
| 	-- attack puncher and call other mobs for help | 	-- attack puncher and call other mobs for help | ||||||
| 	if self.passive == false and self.state ~= "flop" | 	if self.passive == false and self.state ~= "flop" | ||||||
| 	and self.child == false and self.attack_players == true | 	and not self.child and self.attack_players | ||||||
| 	and not (is_player(hitter) and hitter_name == self.owner) | 	and not (is_player(hitter) and hitter_name == self.owner) | ||||||
| 	and not is_invisible(self, hitter_name) | 	and not is_invisible(self, hitter_name) | ||||||
| 	and self.object ~= hitter then | 	and self.object ~= hitter then | ||||||
| @@ -2881,7 +2852,7 @@ function mob_class:on_punch(hitter, tflp, tool_capabilities, dir, damage) | |||||||
| 			if ent and ent._cmi_is_mob then | 			if ent and ent._cmi_is_mob then | ||||||
|  |  | ||||||
| 				-- only alert members of same mob and assigned helper | 				-- only alert members of same mob and assigned helper | ||||||
| 				if ent.group_attack == true and ent.state ~= "attack" | 				if ent.group_attack and ent.state ~= "attack" | ||||||
| 				and not (is_player(hitter) and ent.owner == hitter_name) | 				and not (is_player(hitter) and ent.owner == hitter_name) | ||||||
| 				and (ent.name == self.name or ent.name == self.group_helper) then | 				and (ent.name == self.name or ent.name == self.group_helper) then | ||||||
| 					ent:do_attack(hitter) | 					ent:do_attack(hitter) | ||||||
| @@ -3051,13 +3022,13 @@ function mob_class:mob_activate(staticdata, def, dtime) | |||||||
| 	local selbox = self.base_selbox | 	local selbox = self.base_selbox | ||||||
|  |  | ||||||
| 	-- is there a specific texture if gotten | 	-- is there a specific texture if gotten | ||||||
| 	if self.gotten == true and def.gotten_texture then textures = def.gotten_texture end | 	if self.gotten and def.gotten_texture then textures = def.gotten_texture end | ||||||
|  |  | ||||||
| 	-- specific mesh if gotten | 	-- specific mesh if gotten | ||||||
| 	if self.gotten == true and def.gotten_mesh then mesh = def.gotten_mesh end | 	if self.gotten and def.gotten_mesh then mesh = def.gotten_mesh end | ||||||
|  |  | ||||||
| 	-- set child objects to half size | 	-- set child objects to half size | ||||||
| 	if self.child == true then | 	if self.child then | ||||||
|  |  | ||||||
| 		vis_size = {x = self.base_size.x * .5, y = self.base_size.y * .5} | 		vis_size = {x = self.base_size.x * .5, y = self.base_size.y * .5} | ||||||
|  |  | ||||||
| @@ -3573,7 +3544,7 @@ local function can_spawn(pos, name) | |||||||
|  |  | ||||||
| 		pos2 = {x = pos.x + x, y = pos.y + y, z = pos.z + z} | 		pos2 = {x = pos.x + x, y = pos.y + y, z = pos.z + z} | ||||||
|  |  | ||||||
| 		if minetest.registered_nodes[node_ok(pos2).name].walkable == true then | 		if minetest.registered_nodes[node_ok(pos2).name].walkable then | ||||||
| 			return nil | 			return nil | ||||||
| 		end | 		end | ||||||
| 	end | 	end | ||||||
| @@ -3768,7 +3739,7 @@ function mobs:spawn_specific(name, nodes, neighbors, min_light, max_light, inter | |||||||
| 		end | 		end | ||||||
|  |  | ||||||
| 		-- additional custom checks for spawning mob | 		-- additional custom checks for spawning mob | ||||||
| 		if mobs:spawn_abm_check(pos, node, name) == true then | 		if mobs:spawn_abm_check(pos, node, name) then | ||||||
| 			return | 			return | ||||||
| 		end | 		end | ||||||
|  |  | ||||||
| @@ -3803,7 +3774,7 @@ function mobs:spawn_specific(name, nodes, neighbors, min_light, max_light, inter | |||||||
| 					return | 					return | ||||||
| 				end | 				end | ||||||
| 			else | 			else | ||||||
| 				if day_toggle == true then -- night time but mob wants day | 				if day_toggle then -- night time but mob wants day | ||||||
| --print("--- mob needs day", name) | --print("--- mob needs day", name) | ||||||
| 					return | 					return | ||||||
| 				end | 				end | ||||||
| @@ -3860,7 +3831,7 @@ function mobs:spawn_specific(name, nodes, neighbors, min_light, max_light, inter | |||||||
|  |  | ||||||
| 				local pos2 = {x = pos.x, y = pos.y + n, z = pos.z} | 				local pos2 = {x = pos.x, y = pos.y + n, z = pos.z} | ||||||
|  |  | ||||||
| 				if minetest.registered_nodes[node_ok(pos2).name].walkable == true then | 				if minetest.registered_nodes[node_ok(pos2).name].walkable then | ||||||
| --print ("--- inside block", name, node_ok(pos2).name) | --print ("--- inside block", name, node_ok(pos2).name) | ||||||
| 					return | 					return | ||||||
| 				end | 				end | ||||||
| @@ -3894,7 +3865,7 @@ function mobs:spawn_specific(name, nodes, neighbors, min_light, max_light, inter | |||||||
| 	end | 	end | ||||||
|  |  | ||||||
| 	-- are we registering an abm or lbm? | 	-- are we registering an abm or lbm? | ||||||
| 	if map_load == true then | 	if map_load then | ||||||
|  |  | ||||||
| 		minetest.register_lbm({ | 		minetest.register_lbm({ | ||||||
| 			name = name .. "_spawning", | 			name = name .. "_spawning", | ||||||
| @@ -4062,7 +4033,7 @@ function mobs:register_arrow(name, def) | |||||||
|  |  | ||||||
| 					local entity = thing.ref:get_luaentity() | 					local entity = thing.ref:get_luaentity() | ||||||
|  |  | ||||||
| 					if entity and self.hit_mob and entity._cmi_is_mob == true then | 					if entity and self.hit_mob and entity._cmi_is_mob then | ||||||
|  |  | ||||||
| 						self:hit_mob(thing.ref) | 						self:hit_mob(thing.ref) | ||||||
|  |  | ||||||
| @@ -4096,7 +4067,7 @@ function mobs:register_arrow(name, def) | |||||||
|  |  | ||||||
| 						self:hit_node(pos, node) | 						self:hit_node(pos, node) | ||||||
|  |  | ||||||
| 						if (type(self.drop) == "boolean" and self.drop == true) | 						if (type(self.drop) == "boolean" and self.drop) | ||||||
| 						or (type(self.drop) == "number" and random(self.drop) == 1) then | 						or (type(self.drop) == "number" and random(self.drop) == 1) then | ||||||
|  |  | ||||||
| 							pos.y = pos.y + 1 | 							pos.y = pos.y + 1 | ||||||
| @@ -4171,7 +4142,7 @@ function mobs:register_egg(mob, desc, background, addegg, no_creative) | |||||||
| 	local grp = {spawn_egg = 1} | 	local grp = {spawn_egg = 1} | ||||||
|  |  | ||||||
| 	-- do NOT add this egg to creative inventory (e.g. dungeon master) | 	-- do NOT add this egg to creative inventory (e.g. dungeon master) | ||||||
| 	if no_creative == true then grp.not_in_creative_inventory = 1 end | 	if no_creative then grp.not_in_creative_inventory = 1 end | ||||||
|  |  | ||||||
| 	local invimg = background | 	local invimg = background | ||||||
|  |  | ||||||
| @@ -4518,7 +4489,7 @@ function mobs:feed_tame(self, clicker, feed_count, breed, tame) | |||||||
| 		self.object:set_hp(self.health) | 		self.object:set_hp(self.health) | ||||||
|  |  | ||||||
| 		-- make children grow quicker | 		-- make children grow quicker | ||||||
| 		if self.child == true then | 		if self.child then | ||||||
|  |  | ||||||
| 			-- deduct 10% of the time to adulthood | 			-- deduct 10% of the time to adulthood | ||||||
| 			self.hornytimer = floor(self.hornytimer + ( | 			self.hornytimer = floor(self.hornytimer + ( | ||||||
|   | |||||||
							
								
								
									
										65
									
								
								mount.lua
									
									
									
									
									
								
							
							
						
						
									
										65
									
								
								mount.lua
									
									
									
									
									
								
							| @@ -22,35 +22,17 @@ local abs, cos, floor, sin, sqrt, pi = | |||||||
|  |  | ||||||
| -- helper functions | -- helper functions | ||||||
|  |  | ||||||
| local function node_ok(pos, fallback) |  | ||||||
|  |  | ||||||
| 	fallback = fallback or mobs.fallback_node |  | ||||||
|  |  | ||||||
| 	local node = minetest.get_node_or_nil(pos) |  | ||||||
|  |  | ||||||
| 	if node and minetest.registered_nodes[node.name] then return node end |  | ||||||
|  |  | ||||||
| 	return {name = fallback} |  | ||||||
| end |  | ||||||
|  |  | ||||||
|  |  | ||||||
| local function node_is(entity) | local function node_is(entity) | ||||||
|  |  | ||||||
| 	if not entity.standing_on then return "other" end | 	if not entity.standing_on then return "other" end | ||||||
|  |  | ||||||
| 	if entity.standing_on == "air" then return "air" end | 	if entity.standing_on == "air" then return "air" end | ||||||
|  |  | ||||||
| 	if minetest.get_item_group(entity.standing_on, "lava") ~= 0 then | 	local def = minetest.registered_nodes[entity.standing_on] | ||||||
| 		return "lava" |  | ||||||
| 	end |  | ||||||
|  |  | ||||||
| 	if minetest.get_item_group(entity.standing_on, "liquid") ~= 0 then | 	if def.groups.lava then return "lava" end | ||||||
| 		return "liquid" | 	if def.groups.liquid then return "liquid" end | ||||||
| 	end | 	if def.groups.walkable then return "walkable" end | ||||||
|  |  | ||||||
| 	if minetest.registered_nodes[entity.standing_on].walkable == true then |  | ||||||
| 		return "walkable" |  | ||||||
| 	end |  | ||||||
|  |  | ||||||
| 	return "other" | 	return "other" | ||||||
| end | end | ||||||
| @@ -236,6 +218,11 @@ function mobs.detach(player) | |||||||
| 	end) | 	end) | ||||||
| end | end | ||||||
|  |  | ||||||
|  | -- vars | ||||||
|  |  | ||||||
|  | local GRAVITY = -9.8 | ||||||
|  | local damage_counter = 0 | ||||||
|  |  | ||||||
| -- ride mob like car or horse | -- ride mob like car or horse | ||||||
|  |  | ||||||
| function mobs.drive(entity, moving_anim, stand_anim, can_fly, dtime) | function mobs.drive(entity, moving_anim, stand_anim, can_fly, dtime) | ||||||
| @@ -245,7 +232,7 @@ function mobs.drive(entity, moving_anim, stand_anim, can_fly, dtime) | |||||||
|  |  | ||||||
| 	if entity.player_rotation.y == 90 then rot_view = pi / 2 end | 	if entity.player_rotation.y == 90 then rot_view = pi / 2 end | ||||||
|  |  | ||||||
| 	local acce_y = 0 | 	local acce_y = GRAVITY | ||||||
| 	local velo = entity.object:get_velocity() ; if not velo then return end | 	local velo = entity.object:get_velocity() ; if not velo then return end | ||||||
|  |  | ||||||
| 	entity.v = get_v(velo) * get_sign(entity.v) | 	entity.v = get_v(velo) * get_sign(entity.v) | ||||||
| @@ -321,6 +308,35 @@ function mobs.drive(entity, moving_anim, stand_anim, can_fly, dtime) | |||||||
| 		end | 		end | ||||||
| 	end | 	end | ||||||
|  |  | ||||||
|  | 	local ni = node_is(entity) | ||||||
|  |  | ||||||
|  | 	-- env damage | ||||||
|  | 	if ni == "liquid" or ni == "lava" then | ||||||
|  |  | ||||||
|  | 		damage_counter = damage_counter + dtime | ||||||
|  |  | ||||||
|  | 		if damage_counter > 1 then | ||||||
|  |  | ||||||
|  | 			local damage = 0 | ||||||
|  |  | ||||||
|  | 			if entity.lava_damage > 0 and ni == "lava" then | ||||||
|  | 				damage = entity.lava_damage | ||||||
|  | 			elseif entity.water_damage > 0 and ni == "liquid" then | ||||||
|  | 				damage = entity.water_damage | ||||||
|  | 			end | ||||||
|  |  | ||||||
|  | 			if damage >= 1 then | ||||||
|  |  | ||||||
|  | 				entity.object:punch(entity.object, 1.0, { | ||||||
|  | 					full_punch_interval = 1.0, | ||||||
|  | 					damage_groups = {fleshy = damage} | ||||||
|  | 				}, nil) | ||||||
|  | 			end | ||||||
|  |  | ||||||
|  | 			damage_counter = 0 | ||||||
|  | 		end | ||||||
|  | 	end | ||||||
|  |  | ||||||
| 	-- if not moving then set animation and return | 	-- if not moving then set animation and return | ||||||
| 	if entity.v == 0 and velo.x == 0 and velo.y == 0 and velo.z == 0 then | 	if entity.v == 0 and velo.x == 0 and velo.y == 0 and velo.z == 0 then | ||||||
|  |  | ||||||
| @@ -361,12 +377,11 @@ function mobs.drive(entity, moving_anim, stand_anim, can_fly, dtime) | |||||||
|  |  | ||||||
| 	p.y = p.y - 0.5 | 	p.y = p.y - 0.5 | ||||||
|  |  | ||||||
| 	local ni = node_is(entity) |  | ||||||
| 	local v = entity.v | 	local v = entity.v | ||||||
|  |  | ||||||
| 	if ni == "air" then | 	if ni == "air" then | ||||||
|  |  | ||||||
| 		if can_fly == true then new_acce.y = 0 end | 		if can_fly then new_acce.y = 0 ; acce_y = 0 end | ||||||
|  |  | ||||||
| 	elseif ni == "liquid" or ni == "lava" then | 	elseif ni == "liquid" or ni == "lava" then | ||||||
|  |  | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user