From 7cbba73d50b63954c401c53f8a041e1f4f6c8e08 Mon Sep 17 00:00:00 2001 From: Eliy21 Date: Thu, 23 Nov 2023 00:32:23 +0000 Subject: [PATCH] Combat (mostly PvE) rebalancing (#4005) -Added short mob invulnerability time after being hit -Added separate shorter range for hitting mobs (as opposed to node interaction) -Reworked mob knockback -Slowed down natural health regeneration from saturation -Added a setting for the saturation health regen speed Reviewed-on: https://git.minetest.land/MineClone2/MineClone2/pulls/4005 Reviewed-by: the-real-herowl Co-authored-by: Eliy21 Co-committed-by: Eliy21 --- mods/ENTITIES/mcl_mobs/combat.lua | 44 ++++++++++++++++++++++++++----- mods/ENTITIES/mcl_mobs/init.lua | 1 + mods/ITEMS/mcl_bows/bow.lua | 2 +- mods/PLAYER/mcl_hunger/init.lua | 5 ++-- settingtypes.txt | 4 +++ 5 files changed, 46 insertions(+), 10 deletions(-) diff --git a/mods/ENTITIES/mcl_mobs/combat.lua b/mods/ENTITIES/mcl_mobs/combat.lua index 7775c1b8e..6952f6581 100644 --- a/mods/ENTITIES/mcl_mobs/combat.lua +++ b/mods/ENTITIES/mcl_mobs/combat.lua @@ -532,11 +532,28 @@ function mob_class:on_punch(hitter, tflp, tool_capabilities, dir) return end + local time_now = minetest.get_us_time() + local is_player = hitter:is_player() if is_player then + local time_diff = time_now - self.invul_timestamp + + -- check for invulnerability time in microseconds (0.5 second) + if time_diff <= 500000 and time_diff >= 0 then + return + end + + local mob_pos = self.object:get_pos() + local player_pos = hitter:get_pos() + + -- is mob out of reach? + if vector.distance(mob_pos, player_pos) > 3 then + return + end + -- is mob protected? - if self.protected and minetest.is_protected(self.object:get_pos(), hitter:get_player_name()) then + if self.protected and minetest.is_protected(mob_pos, hitter:get_player_name()) then return end @@ -545,7 +562,7 @@ function mob_class:on_punch(hitter, tflp, tool_capabilities, dir) end -- set/update 'drop xp' timestamp if hitted by player - self.xp_timestamp = minetest.get_us_time() + self.xp_timestamp = time_now end @@ -657,6 +674,9 @@ function mob_class:on_punch(hitter, tflp, tool_capabilities, dir) -- do damage self.health = self.health - damage + -- give invulnerability + self.invul_timestamp = time_now + -- skip future functions if dead, except alerting others if self:check_for_death( "hit", {type = "punch", puncher = hitter}) then die = true @@ -672,10 +692,10 @@ function mob_class:on_punch(hitter, tflp, tool_capabilities, dir) if not v then return end local r = 1.4 - math.min(punch_interval, 1.4) local kb = r * (math.abs(v.x)+math.abs(v.z)) - local up = 2 + local up = 2.625 if die==true then - kb=kb*2 + kb=kb*1.25 end -- if already in air then dont go up anymore when hit @@ -689,7 +709,7 @@ function mob_class:on_punch(hitter, tflp, tool_capabilities, dir) if tool_capabilities.damage_groups["knockback"] then kb = tool_capabilities.damage_groups["knockback"] else - kb = kb * 1.5 + kb = kb * 1.25 end @@ -699,9 +719,19 @@ function mob_class:on_punch(hitter, tflp, tool_capabilities, dir) end if hitter and is_player then local wielditem = hitter:get_wielded_item() - kb = kb + 3 * mcl_enchanting.get_enchantment(wielditem, "knockback") - elseif luaentity and luaentity._knockback then + local hv = hitter:get_velocity() + local dir_dot = (hv.x * dir.x) + (hv.z * dir.z) + local player_mag = math.sqrt((hv.x * hv.x) + (hv.z * hv.z)) + local mob_mag = math.sqrt((v.x * v.x) + (v.z * v.z)) + kb = kb + 9 * mcl_enchanting.get_enchantment(wielditem, "knockback") + -- add player velocity to mob knockback + if dir_dot > 0 and mob_mag <= player_mag * 0.625 then + kb = kb + ((math.abs(hv.x) + math.abs(hv.z)) * r) + end + elseif luaentity and luaentity._knockback and die == false then kb = kb + luaentity._knockback + elseif luaentity and luaentity._knockback and die == true then + kb = kb + luaentity._knockback * 0.25 end self._kb_turn = true self._turn_to=self.object:get_yaw()-1.57 diff --git a/mods/ENTITIES/mcl_mobs/init.lua b/mods/ENTITIES/mcl_mobs/init.lua index 843315039..630548f12 100644 --- a/mods/ENTITIES/mcl_mobs/init.lua +++ b/mods/ENTITIES/mcl_mobs/init.lua @@ -171,6 +171,7 @@ function mcl_mobs.register_mob(name, def) xp_min = def.xp_min or 0, xp_max = def.xp_max or 0, xp_timestamp = 0, + invul_timestamp = 0, breath_max = def.breath_max or 15, breathes_in_water = def.breathes_in_water or false, physical = true, diff --git a/mods/ITEMS/mcl_bows/bow.lua b/mods/ITEMS/mcl_bows/bow.lua index 23b6b4310..174208c3c 100644 --- a/mods/ITEMS/mcl_bows/bow.lua +++ b/mods/ITEMS/mcl_bows/bow.lua @@ -48,7 +48,7 @@ function mcl_bows.shoot_arrow(arrow_item, pos, dir, yaw, shooter, power, damage, damage = damage + (enchantments.power + 1) / 4 end if enchantments.punch then - knockback = enchantments.punch * 3 + knockback = enchantments.punch * 21 end if enchantments.flame then mcl_burning.set_on_fire(obj, math.huge) diff --git a/mods/PLAYER/mcl_hunger/init.lua b/mods/PLAYER/mcl_hunger/init.lua index 321139c5f..cc3965f57 100644 --- a/mods/PLAYER/mcl_hunger/init.lua +++ b/mods/PLAYER/mcl_hunger/init.lua @@ -146,8 +146,9 @@ minetest.register_globalstep(function(dtime) local food_level = mcl_hunger.get_hunger(player) local food_saturation_level = mcl_hunger.get_saturation(player) local player_health = player:get_hp() + local max_tick_timer = tonumber(minetest.settings:get("mcl_health_regen_delay")) or 4 - if food_tick_timer > 4.0 then + if food_tick_timer > max_tick_timer then food_tick_timer = 0 -- let hunger work always @@ -173,7 +174,7 @@ minetest.register_globalstep(function(dtime) end end - elseif food_tick_timer > 0.5 and food_level == 20 and food_saturation_level > 0 then -- fast regeneration + elseif food_tick_timer > max_tick_timer and food_level == 20 and food_saturation_level > 0 then -- fast regeneration if player_health > 0 and player_health < 20 then food_tick_timer = 0 player:set_hp(player_health+1) diff --git a/settingtypes.txt b/settingtypes.txt index 6d4bfb9e8..c2f97c817 100644 --- a/settingtypes.txt +++ b/settingtypes.txt @@ -95,6 +95,10 @@ mcl_creative_dig_speed (Creative mode dig speed) float 0.2 # If enabled the hunger mechanic will be active mcl_enable_hunger (Hunger mechanic) bool true +# Health regeneration delay when hunger bar is full +# Default:4 +mcl_health_regen_delay (Health regen delay) float 4 0 + [Mobs] # If enabled, mobs will spawn naturally. This does not affect # affect mob spawners.