I want to set a boolean to true when a player touches a part, and set it to false if the player walk off, and set it back to true if the player touches the part again, but the boolean keeps switching between true and false when the player walks all over the part, i would love some help, this is my script so far.
local debounce = false
local foobar = false
script.Parent.Touched:Connect(function(hit)
if hit.Parent:FindFirstChild("Humanoid") then
if debounce == false then
print("touched")
debounce = true
foobar = true
end
end
end)
script.Parent.TouchEnded:Connect(function(hit)
if hit.Parent:FindFirstChild("Humanoid") then
debounce = false
foobar = false
end
end)
Is this really the only code you have here? I just tested this on my end and it prints “touched” once and doesn’t do anything else, as expected since debounce is never set back to false and remains true forever.
Would you happen to have any other code? There’s just no possible way that with this code alone, it’s switching back and forth between true and false.
This does not help… Adding a wait() before the debounce is turned on results in the possibility of multiple print statements instead of exactly one before debounce is turned on. The whole purpose of a debounce is to prevent things from repeatedly happening. A wait() makes no sense before debounce is set to true.
I tested this code on my end. I put it in a script parented to a part in workspace and it only printed once when a humanoid touched it. The debounce isn’t even switching back to false in this case, it’s just being set to true and then never changing. I’m not quite sure how this code could be causing the debounce to switch back and forth
Excuse moi, absolutely. The Debounce = true should be the first line right after the if statement, the wait() needs to at about the end right before the Debounce = false statement is added
What’s happening is when your character walks all over the part, the legs of the character are moving up and down, causing multiple Touched events and then multiple TouchEnded events to occur. That’s why this occurs.
I also honestly don’t recommend using TouchEnded at all as it’s notoriously unreliable, but if you have to, I would have it to where the code makes sure that it only triggers when the player’s HumanoidRootPart is the one touching it. This is because the HumanoidRootPart is a special part of the player that doesn’t shake around or anything during animations.
This is of course a bit of a problem as I assume the part in question is being walked on which means the HumanoidRootPart can’t even reach it. You could have an invisible part on top of the part in question that is just high enough for the HumanoidRootPart to reach and have the Touched and TouchEnded events be connected to that instead.
Alternatively, you could abandon TouchEnded altogether and wait for the player to be a certain distance away from the part before setting the debounce back to false. Use (part.Position - player.HumanoidRootPart.Position).Magnitude to get the distance between the player and the part.
My favorite alternative would probably be GetTouchingParts(). You can use this on the part to get all the parts touching it and just check if its parent is the player. Then, to determine when the player has left the part, if GetTouchingParts() returns no parts parented to the player, you just set the debounce to false again.
Here, I’m using it in combination with Touched:
local debounce = false
part.Touched:Connect(function(part)
if part.Parent:FindFirstChild("Humanoid") and debounce == false then
debounce = true
-- now using GetTouchingParts()
while debounce == true do
local touchingParts = part:GetTouchingParts()
local foundPlayerPart = nil
for _, part in pairs(touchingParts) do
if part.Parent:FindFirstChild("Humanoid") then
foundPlayerPart = true
break
end
end
if foundPlayerPart == true then
debounce = false
else
wait()
end
end
end
end)