How can i make a detect function if a player touch one part among many?

Hello devs,

I’m trying to make a claim area script.

I made 6 parts and I want to show a Gui (TweenPos) when the player is on the part and the gui has to disparears when the player isn’t on the part or if the player claim the area.

It is in a local script ( Detect if the player is on the part (magnitude to check if the player isn’t anymore on the part) and then put the output script to :FireServer(). )

Wich path should I follow to do that?
And how can I detect if the player is in one of all my parts?
If you have any questions, ask them ! :smiley:

1 Like

You can use Basepart:GetTouchingParts() to get the parts the player is in. This is an example in a local script, normally you would want it in a server script.

local player = game.Players.LocalPlayer
local triggerParts = game.Workspace.Triggers:GetChildren() -- change to whatever you feel like
local function processTouchingParts(touchingParts)
    for _, part in pairs(touchingParts) do
        for _, trigger in pairs(triggerParts) do
            if part == trigger then
                print("Trigger ".. trigger.Name .." fired!")
            end
        end
    end
end
player.CharacterAdded:Connect(function(character)
    character.PrimaryPart.Touched:Connect(function()
        local touchingParts = character.PrimaryPart:GetTouchingParts()
        processTouchingParts(touchingParts)
    end)
    character.PrimaryPart.TouchEnded:Connect(function()
        local touchingParts = character.PrimaryPart:GetTouchingParts()
        processTouchingParts(touchingParts)
    end)
end)

Okay, all of this is new for me.
So if I put this script into a serv script I have to fire the client and then show the Gui and if the plr press “E” it will fire the server again and it will claim the area for the plr (in a serv script) that’s it?

You can do all the userinput and Gui things in a localscript if it isn’t a monetary good exchange. For things such as buying from a shop just use a local script until it comes time to use a datastore or do changes for other clients.

Yeah I already now this.
In my game I already have tools and backpacks, pets, inventory, DSS, and a lot of features.

I’m trying to make a claim area script. I’m trying to do something like the “Claim hive” in Bee Swarm Simulator"

You could do a simple Position check; First of all, you want to get the area.
This can be done like so

local p = part
local pSize = p.Size
local y_top = 50 --can be naything
local y_bottom = -50 -- can be anything
local cfTop = p.CFrame * CFrame.new(p.Size.X / 2, y_top, p.Size.Z / 2)
local cfBottom = p.CFrame * CFrame.new(-p.Size.X / 2, y_Bottom, -p.Size.Z / 2)

Then from here, you will want to go through each player every second and make sure that CFrame is within these extents

This can be done with >= <= operators;

You will have to check x, y, z values

So the order you need to do things is:

  1. Detect input [E button]
  2. Check if in area
  3. Fire the server
  4. server does checks if u have certain items required [enough gold etc.]
  5. server updates client using another remote

Okay,
but I noticed some things on step 1 and step 4:
Step1 : I want to show a Gui (“Press E to Claim”) in the plr’s screen when he’s on a part and then if the plr’s press E it will trigger step 3 so i think I have to change step 1 with step 2.
Step 4: I don’t want to check anything because the plr has to claim the area when he joins the game, like in bee swarm.

Or I can do step 1 and then step 2 if I do another script to show the gui

Ok that sounds good, if you need any help with anything contact me.

So I did the detect E pressed, so now I have to check the distance from the parts and the plr. I will try using the script you gave me (in a local script)

Can you check what I did pls:

This is my input script and this is your script :
The input works but when I fuse them it doesn’t do anything. :confused:
This is the fused script :

local UserInputService = game:GetService("UserInputService")

UserInputService.InputBegan:Connect(function(input, gameProccesedEvent)
	if input.KeyCode == Enum.KeyCode.E then
		local player = game.Players.LocalPlayer
		local triggerParts = game.Workspace.TouchPartToClaim:GetChildren() -- change to whatever you feel like
		local function processTouchingParts(touchingParts)
		    for _, part in pairs(touchingParts) do
		        for _, trigger in pairs(triggerParts) do
		            if part == trigger then
		                print("Trigger ".. trigger.Name .." fired!")
		            end
		        end
		    end
		end
		player.CharacterAdded:Connect(function(character)
		    character.PrimaryPart.Touched:Connect(function()
		        local touchingParts = character.PrimaryPart:GetTouchingParts()
		        processTouchingParts(touchingParts)
		    end)
		    character.PrimaryPart.TouchEnded:Connect(function()
		        local touchingParts = character.PrimaryPart:GetTouchingParts()
		        processTouchingParts(touchingParts)
		    end)
		end)
	end
end)

I’m trying to seperate the UserInputScript to your script:

this is the local script :

local UserInputService = game:GetService("UserInputService")

UserInputService.InputBegan:Connect(function(input, gameProccesedEvent)
	if input.KeyCode == Enum.KeyCode.E then
		game.ReplicatedStorage.Remotes.TryingToClaimArea:FireServer()
	end
end)

this is the server script :

game.ReplicatedStorage.Remotes.TryingToClaimArea.OnServerEvent:Connect(function(plr)
	local triggerParts = game.Workspace.TouchPartToClaim:GetChildren() -- change to whatever you feel like
	local function processTouchingParts(touchingParts)
	    for _, part in pairs(touchingParts) do
	        for _, trigger in pairs(triggerParts) do
	            if part == trigger then
	                print("Trigger ".. trigger.Name .." fired!")
	            end
	        end
	    end
	end
	plr.CharacterAdded:Connect(function(character)
	    character.PrimaryPart.Touched:Connect(function()
	        local touchingParts = character.PrimaryPart:GetTouchingParts()
	        processTouchingParts(touchingParts)
	    end)
	    character.PrimaryPart.TouchEnded:Connect(function()
	        local touchingParts = character.PrimaryPart:GetTouchingParts()
	        processTouchingParts(touchingParts)
	    end)
	end)
end)

It doesn’t work :frowning: (30 characters)

I will change it for you needs I will send the working one.

alright replace the segment of code in the server script with this:

local function processTouchingParts(touchingParts)
    for _, part in pairs(touchingParts) do
        for _, trigger in pairs(triggerParts) do
            if part == trigger then
                return true, trigger
            end
        end
    end
end

game.ReplicatedStorage.Remotes.TryingToClaimArea.OnServerEvent:Connect(function(plr)
	local triggerParts = game.Workspace.TouchPartToClaim:GetChildren() -- change to whatever you feel like, if this is a part remove the :GetChildren(), if it has lots of parts, keep :GetChildren()
	local touchingParts = character.PrimaryPart:GetTouchingParts()
	local inTrigger, triggerName = processTouchingParts(touchingParts)
	if inTrigger == true then
		print("Trigger", triggerName, "has been fired")
	end
end)

and for local triggerParts = change to whatever you feel like, if this is a part remove the :GetChildren(), if it has lots of parts, keep :GetChildren()

A major issue I have spotted; Make sure the Server check for the area
Exploiters can fire a remote event and claim areas even though they are not within them

Oh and I forgot, add an empty touched event for the primarypart of the character and disconnect it after the script checks the primary parts. So put this before

local connection
connection = character.PrimaryPart.Touched:Connect(function() end)

And after

connection:Disconnect()

The line in question is the one declaring touchingParts

Ok I’ll try that, thx you for your support, I will give you a feedback later.
@AbstractCo I don’t care about exploits cause this functin is just here to claim an area when the player joins the game. Like the claim hive in bee swarm simulator.
(I think it’s not a problem if an exploiter claim an area without being on the part xD