Humanoid.Died running multiple times, or logic error in my code

Hello. I am currently making an RPG just to play around and stuff, and I am currently writing a script to make all of the AI’s respawn after they have died after 5 seconds, or a specific time that I specify with an attribute. The thing is, after I kill the AI once, the same AI respawns twice. I’ve tried to use debounces and attributes to cancel it out once it is done, but it still does not work.

Here is the snippet of code which is causing the problem:

local function initAI(char)
    char.Humanoid.Died:Connect(function()
		if (char:GetAttribute("RespawnCF") ~= nil) then -- the respawn cframe which is initialized in the beginning, works
			delay(char:GetAttribute("RespawnTime") or 5, function()
					local cf = CFrame.new(table.unpack(char:GetAttribute("RespawnCF"):gsub(" ",""):split(","))) -- compiles the serialized cframe
					local newChar = game.ServerStorage.NPCs[char.Name]:Clone()
					newChar:SetPrimaryPartCFrame(cf)

					for name, value in pairs(char:GetAttributes()) do
						newChar:SetAttribute(name, value)
					end

					char:Destroy()

					newChar.Parent = game.Workspace.NPCs
					initAI(newChar)
				end
			end)
		end
	end)

	if (isFirstTime == true) then
		char:SetAttribute("RespawnCF", tostring(char:GetPrimaryPartCFrame())) -- serialize the cframe
		char:Clone().Parent = game.ServerStorage.NPCs
	end
end

I’m thinking it is a logic error in my code, and the answer is in plain sight but I think another pair of eyes looking at it will help.

Thanks.

EDIT: Behavior shown here:

I believe this is. logic error in your code, although I may be incorrect due to a lack of knowledge with how your system works. I believe the problem is that you are calling initAI on all new characters that spawn in as well. This would lead to duplicates because every new character that is spawned in would then have this function called on them and thus respawn new characters when they die and so on.

What you want instead is to call RBXScriptConnection:Disconnect on the event when you spawn a new npc in and then connect the new npc to the event. I made a respawn system awhile back that accomplished this same thing and I also ran into this issue. Here’s two models that I ended up creating to suite my needs. You can probably adapt one of them to fit your needs or just steal the code from it. Do know that I haven’t used them in a while so I’ve forgotten the differences between them other than that one is an R6 and the other is an R15 and has a spawnplate. Based off of what you showed me you’ll most likely want to use the first one, but the second ones there if you need it:
https://www.roblox.com/library/5967291252/Crash-Dummy
https://www.roblox.com/library/5864987253/TestDummy

3 Likes

Thank you for the solution! I decided to go with this solution instead since I already tried using a connection.

local function initAI(char, isFirstTime, allowRespawn)
	char.Humanoid.Died:Connect(function()
		
		if (allowRespawn == true) then
			if (char:GetAttribute("RespawnCF") ~= nil) then
				delay(char:GetAttribute("RespawnTime") or 5, function()
					local cf = CFrame.new(table.unpack(char:GetAttribute("RespawnCF"):gsub(" ",""):split(",")))
					local newChar = game.ServerStorage.NPCs[char.Name]:Clone()
					newChar:SetPrimaryPartCFrame(cf)

					for name, value in pairs(char:GetAttributes()) do
						newChar:SetAttribute(name, value)
					end

					char:Destroy()

					newChar.Parent = game.Workspace.NPCs
					initAI(newChar, nil, true)
				end)
			end
		end
	end)

	if (isFirstTime == true) then
		char:SetAttribute("RespawnCF", tostring(char:GetPrimaryPartCFrame()))
		char:Clone().Parent = game.ServerStorage.NPCs
	end
end
1 Like

If @BuilderBob25620’s explanation was too long, you basically have to stop listening for the event. You do that by calling :Disconnect() on the connection. Well how do you get the connection? Create a variable set it to nil. Then, when connecting to the event, set the variable to the connection. Here’s what I mean:

local DiedConnection = nil
DiedConnection = char.Humanoid.Died:Connect(function()
    -- put the code you had
    DiedConnection:Disconnect() -- stops listening for when humanoid died
    -- NOTE: you have to reconnect it when it respawns 
end)
1 Like

I forgot to mention in the original thread that I already tried this method and it did not work. Refer to my post above for the solution that worked.

Whoops, I forgot to add something to my reply.

Anyways, after disconnecting the event, you want to reconnect it if you want to listen to it again.So you do the same process that I said in my reply.

Also, it is better practice to disconnect connections that you aren’t using right now.

Thanks! I was having trouble putting into words what I wanted to say.

1 Like