Scripting HelpersARCHIVE
A little piece of Roblox history. Preserved for everyone, one question at a time.Read about the archive →
✓ ANSWER ACCEPTED

What's the proper way to prevent multiple touch events going off when providing rewards?

I have this obstacle course demo. It spawns a map, the player completes it and touches a win block. This block is meant to increment the number of wins the player has. However, it goes off more than once when the player initiates contact with the block. I have attempted to create a table to store past winners to avoid this, but it will not work.

local beenAwarded = {} --used to store winner names (those who touched the block)

script.Parent.Touched:connect(function(hit)
		if hit.Parent:FindFirstChild("Humanoid") then
			local character = hit.Parent.Humanoid
			print "human found"
			local plrname = hit.Parent.Name
			local plr = game.Players:FindFirstChild(plrname)
			if plr then
				local stats = plr:FindFirstChild("leaderstats")
				if stats then
					wait(.1)
					plr.Character.HumanoidRootPart.CFrame = CFrame.new(game.Workspace.SpawnLocation.Position)
					if beenAwarded[plr] then return end -- if the player has been added to the table it ends the function
					table.insert(beenAwarded, plr) -- otherwise the player is added here (i have tried the same thing using the player name, same result)
					local wins = stats.Wins
					wins.Value = wins.Value + 1
			end
		end
	end
end)

2 comments

0

what do you mean make the event a variable? & i can't use a debouce because the delay before the touch can be used again is not something i can have

0

Why not just use a debounce?

1 answer

✓ Accepted answer

1. Your script isn't working because you're attempting to find plr with a dictionary-style based type of search, yet you're using table.insert().

If you want to use the dictionary style, you'd do this.

if beenAwarded[plr.Name] then 
	return 
end

beenAwarded[plr.Name] = plr

2. Use GetPlayerFromCharacter() to get the player and base every variable after that on the player, not hit. local plr = game.Players:GetPlayerFromCharacter(hit.Parent)

local beenAwarded = {} --used to store winner names (those who touched the block)
local spawn_pos = workspace:WaitForChild("SpawnLocation")

script.Parent.Touched:connect(function(hit)
    if hit.Parent then
		local plr = game.Players:GetPlayerFromCharacter(hit.Parent)
		if plr then
	  		local plrname = plr.Name
			local character = plr.Character
	       	local stats = plr:FindFirstChild("leaderstats")
			local hum = character:findFirstChild("Humanoid")
			if hum and hum.Health > 0 then 
				if stats and not beenAwarded[plrname]  then
					beenAwarded[plrname] = plr
					local wins = stats.Wins
					wins.Value = wins.Value + 1					
				end
				character:MoveTo(spawn_pos.Position)
			end
		end
	end
end)

2 comments

0

Why not just use a debounce?

0

If he doesn't want them to be-able to win again, debounce won't stop that. He should continue to use a table and remove them from it after the player gets teleported though.

This discussion is preserved as it was. New answers, comments, and votes are closed.