Detecting water touching

I’m making a bucket filling script, and I want to make it so that you can only fill the bucket if your character is touching water. I’ve tried using .Material for this, but all the terrain materials return as Enum.Material.Plastic. Is there a way I can get different terrain materials with the touch event?

3 Likes

There actually is a way to check the terrain material using the touch event!
local function onPartTouch(hitPart)

   local humanoid = hitPart.Parent:FindFirstChildOfClass("Humanoid")
    local terrainMaterial = game:GetService("Workspace"):GetMaterialAt(humanoid.RootPart.Position)
    
    if terrainMaterial == Enum.Material.Water then
       
    else
        
    end
end

game.Workspace.Part.Touched:Connect(onPartTouch)
2 Likes

Would this be something that’s put in the player, or Terrain?

This script would typically be placed in a Script object that is a child of a part within the Workspace.

Would it be possible to take this concept and use it for something to go inside of a player part?

Yes, it is possible to modify this concept to work with a player part. Instead of using “hitPart.Parent” to find the humanoid, you can use the player object itself. For example:

local player = game.Players:GetPlayerFromCharacter(hitPart.Parent)local humanoid = player.Character:FindFirstChildOfClass(“Humanoid”)local terrainMaterial = game:GetService(“Workspace”):GetMaterialAt(humanoid.RootPart.Position)

I made a script:

script.Parent.Touched:Connect(function(part)
	local Player = game.Players:GetPlayerFromCharacter(part.Parent)
	local Humanoid = Player.Character:FindFirstChildOfClass("Humanoid")
	local TerrainMaterial = game:GetService("Workspace"):GetMaterialAt(Humanoid.RootPart.Position)
	print(TerrainMaterial)
end)

Player comes out as nil though. Should this be a local script instead? Does it being in the RightLeg limb of the test Dummy affect it?

Just put a part inside the water and detect when that part is touched.

My only issue is that it’s a river, and the river is not all flat.

Why not fire a Blockcast (similar to a Raycast) straight down from the player HumanoidRootPart to detect what the Player is standing on? It’ll detect if the player is touching water without using the buggy Touched event.

1 Like

I haven’t really tested it but I think you might be looking for this (I’ve written this on mobile so please excuse any typos:

local hum =... -- you probably know how to get the humanoid

hum:GetPropertyChangedSignal("FloorMaterial"):Connect(function()
	if hum.FloorMaterial == Enum.Material.Water then
		--code here
	end
end)

I’ve attempted to make a LocalScript that will perform a BlockCast, but nothing is happening. I’m testing this with a Dummy rolling into water, and the script is located in the Dummy’s HumanoidRootPart. Apologizes if this is horrible code. I’m still trying to understand BlockCasts, as it’s a new thing for me.

while true do
local R = RaycastParams.new()
R.FilterType = Enum.RaycastFilterType.Whitelist
R.FilterDescendantsInstances = {Enum.Material.Water}
local Start = script.Parent.Position
local End = script.Parent.Position - Vector3.new(0,10,0)
local Size = Vector3.new(3,3,3)
R.FilterDescendantsInstances = {Enum.Material.Water}
	local BlockCast = workspace:Blockcast(Start,Size,End,R)
	print(BlockCast)
	wait(0.5)
end

Edit: I made a new post for this code so that it’s the focus, since now figuring out what to do is done, now it’s just how to do it.

You could insert a value into the water part named “water” and check if the value is there in a script when touched

I can do that with terrain water?

wait nvm i thought u could were talking about the part water

No, it’s a river. If you scroll up in the replies, I responded to a person with an image of it.

2 Likes

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.