Player catches frisbee, and it goes past them at the same time

In my game, sometimes a player should catch the frisbee, but it bounces off of them and hits the wall behind them. For context, you do not want the frisbee getting past you and once it hits the wall, the opposing player gains points and ends the volley.
You can see in this drawing what is happening. It hits the player, which should then parent the frisbee to the player, but it doesn’t happen fast enough and it bounces off the player and hits the wall behind them, giving the opposing player points. Then, the frisbee will get parented to the player, but the opposing player already got their points.


In the video I’m not demonstrating the problem, but you can get a clearer idea of the game, there is usually another person.

Here is the code that the frisbee runs to detect when it hits a player:

Body.Touched:Connect(function(hit)
	if hit.Parent:FindFirstChild("Humanoid") then
		if Frisbee.Parent==workspace then
			local player = game.Players:GetPlayerFromCharacter(hit.Parent)
			if player then
				Frisbee.Parent=player.Character
			end
		end
	end
end)

Also about the frisbee; it has to main parts, the handle and the body. the script above runs on the body to detect a touch. The handle is small and on the edge so it looks like the player is holding the edge of the frisbee.

This is the script that detects when the frisbee hits a wall:

local t
			repeat
	           --irrelevant game code
				t = frisbee.Handle.Body.Touched:Wait()
			until (t == blueWall or t==redWall) and frisbee.Parent==workspace

Since the detection script is working on the server (I assume), there will always be some delay. A simple fix can be that after the frisbee hits a wall, it waits for a short time (say 0.2s), and then, the script checks whether the frisbee is parented to a player’s character or not. If it is parented to a character, the point does not count, and vice versa.

local t
		repeat
	    --irrelevant game code
		t = frisbee.Handle.Body.Touched:Wait()
		until (t == blueWall or t==redWall) and frisbee.Parent==workspace
        task.wait(0.2)
        if frisbee.Parent ~= workspace then
        -- make the point not count
        end

You can also try making the frisbee stop when it comes in contact with a player. Not sure if it would work or not.

I like your first idea I just don’t know if it would be possible to implement it. I still need the repeat section to be running even if there is a false hit.

local t
			repeat
				if  game:GetService("Players"):GetPlayerFromCharacter(frisbee.Parent)~=lastCaughtBy and (game:GetService("Players"):GetPlayerFromCharacter(frisbee.Parent)==redPlayer or game:GetService("Players"):GetPlayerFromCharacter(frisbee.Parent)==bluePlayer) then 
					lastCaughtBy=game:GetService("Players"):GetPlayerFromCharacter(frisbee.Parent)
					pointTracker+=1
					
				end
				t = frisbee.Handle.Body.Touched:Wait()
			until (t == blueWall or t==redWall or blueSetsWon>1 or redSetsWon>1) and frisbee.Parent==workspace 

As for your second idea, wouldn’t it be the same problem with the lag because it would be running on a server script and basically have the same code from what I originally posted?


Actually i have an idea: Have a client side script on every player that detects when a tool touches them. If a tool touches them then it sets its velocity to 0. This should act faster than if it was a server script right?