Jump to content

[Help]Weird behavior of DoTaskInTime


Recommended Posts

I am trying to build an armor that when its owner gets hit, the armor will enable the character to regenerate health 2 points per second for the next 10 seconds. So I write the following code:

 

local function OnTakeDamage(attacked, data)
	local attacker = data.attacker
	if attacker ~= nil then
    	local target = attacker.components.combat.target
    	if target and target:IsValid() and target.components.health and target.components.health.currenthealth > 0 then
        	for i = 1, 10 do
				target:DoTaskInTime(1.0, function()
					target.components.health:DoDelta(2.0)
				end)
			end        
    	end
    end
end

local function OnEquip(inst, owner) 
    owner.AnimState:OverrideSymbol("swap_body", "armor_wood", "swap_body")
    inst:ListenForEvent("attacked", OnTakeDamage, owner)
end

local function OnUnequip(inst, owner) 
    owner.AnimState:ClearOverrideSymbol("swap_body")
    inst:RemoveEventCallback("attacked", OnTakeDamage, owner)
end

However, when the character is attacked while wearing this armor, the health regeneration starts 1 second later than the attack and increase 10 times of 2 points all at once instead of 2 points per second over 10 seconds. So I would like to know which part goes wrong? Is there anyone who have encountered similar problem? Thank you very much if you can help me with this!

Link to comment
Share on other sites

for i = 1, 10 do
    target:DoTaskInTime(1.0, function()
        target.components.health:DoDelta(2.0)
    end)
end

So here you are saying, "I want to do ten times, to spawn a task that after 1 second passes, the target will gain health".

Where does "i" go?

Another question for the future is, what would happen if a character got hit 10 times within 1 second? Would he regen 20 health, or 200 health?

Link to comment
Share on other sites

Ah...would it be more appropriate to write:

for i = 1, 10 do
	if target and target:IsValid() and target.components.health and target.components.health.currenthealth > 0 then
		target:DoTaskInTime(1.0 + i, function()
			target.components.health:DoDelta(2.0)
		end)
	end
end   

But similar code works well when it comes to a weapon that can trigger multiple hit on target:

local function OnAttack(inst, owner, target)
   local value = 35
   if owner.components.combat.damagemultiplier ~= nil then
    value = owner.components.combat.damagemultiplier * 35
   end
   for i = 1, 4 do
		inst:DoTaskInTime(1.0, function()
			if target and target:IsValid() and target.components.health and target.components.health.currenthealth > 0 then
				target.components.combat:GetAttacked(owner, value, inst)
			end
		end)
	end
end

Here, the target will get attacked 1 second after the real hit and automatically get the next hit after next 1 second until 4 triggered hits. So, I am wondering why this cannot work when I use it on an armor?

Link to comment
Share on other sites

4 hours ago, Frank Sym said:

So, I am wondering why this cannot work when I use it on an armor?

I tried it myself and it doesn't work like you say. After the target gets the initial hit, when 1 second passes, it receives 4 hits at the same time.

Maybe there is something else, but only that doesn't make the cut.

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

×
  • Create New...