Waits in coroutines are stopping the whole script

I’m making a gun and I’m now working on reload animation. I can see that I’m using an inefficent way of doing this but problem is, script doesn’t run after this coroutine.

These are my functions about this:

local function setToolGrip(var)
	if var == "idle" then
		gunModel.GripForward = grips.NormalGrip.gripForward
		gunModel.GripPos = grips.NormalGrip.gripPos
		gunModel.GripRight = grips.NormalGrip.gripRight
		gunModel.GripUp = grips.NormalGrip.gripUp
	elseif var == "reload" then
		gunModel.GripForward = grips.ReloadGrip.gripForward
		gunModel.GripPos = grips.ReloadGrip.gripPos
		gunModel.GripRight = grips.ReloadGrip.gripRight
		gunModel.GripUp = grips.ReloadGrip.gripUp
	else
		warn("Unknown tool grip set.")
	end
end
local function reloadAnim(hum)
	local animation = Instance.new("Animation")
	animation.AnimationId = baseurl..anims.reload
	local loadedAnim = hum:LoadAnimation(animation)
	setToolGrip("reload")
	repeat wait() until loadedAnim.TimePosition == 0.5
	mag.Transparency = 1
	local clone = mag:Clone()
	clone:ClearAllChildren()
	clone.Transparency = 0
	Debris:AddItem(clone, 10)
	repeat wait() until loadedAnim.TimePosition == 0.25
	mag.Transparency = 0
	repeat wait() until loadedAnim.Stopped:Wait()
	setToolGrip("idle")
end

And I used this for the animation:

reload.OnServerEvent:Connect(function(sender)
	coroutine.wrap(reloadAnim(sender.Character.Humanoid))()
	reloading.Value = true -- this doesn't run after adding this
	for ammo0 = Ammo.Value, MaxAmmo do
		if Ammo.Value < 15 then
			Ammo.Value = Ammo.Value + 1
			wait(0.094)
		end
	end
	reloading.Value = false
end)

You do notice that a wait is also in the OnServerEvent connection right. It is not possible for the a wait inside of a coroutine to affect the calling thread. Furthermore, wait does not work properly with those small numbers: Avoiding wait() and why. This could easily be your source of error because calling wait like that can result in it waiting for a longer period of time than expected, instead use the heartbeat event of the run service .

I didn’t understand what do you mean but it shall be alright, I’m calling it in first place.

It works for me like how I wanted.

coroutine.wrap takes directly the function and returns a function to be called which resumes the Coroutine, the arguments you pass to calling it will be passed when it calls the function. As of now, you’re calling the function yourself and therefore not Coroutined.

For example:

coroutine.wrap(reloadAnim)(sender.Character.Humanoid);
1 Like

That worked. I can now see my other code has problems.