Hi,
I have some problems using task.spawn(). I need to run the code for every object in the for loop at the same time, but I get it running one after another only if the first object ends executing the code and it may take alot of time. I have The following code bellow if you have any suggestions!
local function regen(player)
local profile = Manager.Profiles[player]
if not profile then return end
local run = game:GetService("RunService")
local defVal = player:WaitForChild("def")
local defFolder = game.Workspace:WaitForChild("defFolder")
local randTime = {}
run.Heartbeat:Connect(function()
for _, def in pairs(defVal:GetChildren())do
task.spawn(function()
if profile.Data[def.Name].hp < profile.Data[def.Name].maxHp then
if #randTime == 0 then
table.insert(randTime, os.time())
end
local diffTime = os.time() - randTime[#randTime]
if diffTime == profile.Data[def.Name].coolDown and def then
profile.Data[def.Name].hp += profile.Data[def.Name].regenEffect
defVal[def.Name].hp.Value = profile.Data[def.Name].hp
if #defFolder:GetChildren() > 0 then
defFolder[def.Name].PrimaryPart.regen:Emit()
end
table.remove(randTime, #randTime)
end
end
end)
end
end)
end
I hope I understood correctly, here I send you a code that I hope solves your problem
local function regen(player)
local profile = Manager.Profiles[player]
if not profile then return end
local run = game:GetService("RunService")
local defVal = player:WaitForChild("def")
local defFolder = game.Workspace:WaitForChild("defFolder")
run.Heartbeat:Connect(function()
for _, def in pairs(defVal:GetChildren()) do
task.spawn(function()
if profile.Data[def.Name].hp < profile.Data[def.Name].maxHp then
local randTime = os.time()
local diffTime = randTime - profile.Data[def.Name].lastRegenTime
if diffTime >= profile.Data[def.Name].coolDown then
profile.Data[def.Name].lastRegenTime = randTime
profile.Data[def.Name].hp = math.min(profile.Data[def.Name].hp + profile.Data[def.Name].regenEffect, profile.Data[def.Name].maxHp)
defVal[def.Name].hp.Value = profile.Data[def.Name].hp
if #defFolder:GetChildren() > 0 then
defFolder[def.Name].PrimaryPart.regen:Emit()
end
end
end
end)
end
end)
end
Actually regenEffect is stored in profile service and I don’t change it at all. The problem I have is that the objects from the for loop are not running all at once, they run one after another. Every object has its own values stored in profile service. And I am looping on the object folder to check if their “hp” value is decreasing and then executing the code.
Then use task.spawn outside the loop to parallelize the regeneration process for each object, and may need to ensure that the values specific to each object are captured correctly within the spawned tasks.
local function regen(player)
local profile = Manager.Profiles[player]
if not profile then return end
local run = game:GetService("RunService")
local defVal = player:WaitForChild("def")
local defFolder = game.Workspace:WaitForChild("defFolder")
run.Heartbeat:Connect(function()
for _, def in pairs(defVal:GetChildren()) do
local defProfile = profile.Data[def.Name] -- capture object-specific profile data
task.spawn(function()
if defProfile.hp < defProfile.maxHp then
local randTime = os.time()
local diffTime = randTime - defProfile.lastRegenTime
if diffTime >= defProfile.coolDown then
defProfile.lastRegenTime = randTime
defProfile.hp = math.min(defProfile.hp + defProfile.regenEffect, defProfile.maxHp)
defVal[def.Name].hp.Value = defProfile.hp
if #defFolder:GetChildren() > 0 then
defFolder[def.Name].PrimaryPart.regen:Emit()
end
end
end
end)
end
end)
end
I think the problem is that I have the time checking and its just waiting for that to past and then start from the first object again until the task is complete and then jumping to the next one. It annoying because I have to check if the past time is equal with my waiting till regen time and the only way to do it is with os.time() which I have to reset every time the checking is complete, but I think that time is not applying for every individual object. So I have to find a way to do it.
I managed to solve it. It was indeed the time problem. The thing was that I had if #randTime == 0 then. The first object always managed to pass because the condition was true, but for the next one the condition was false because #randTime was not 0 anymore so I changed it like this if #randTime < #defVal:GetChildren() then. Thank you for your time wasted to reply me!