Hello, the following code prints "Enum.Material.Plastic" when my mouse is moving over the Mud Terrain Enum Material. I would like to detect only the Mud.
mouse.Move:Connect(function() if mouse.Target ~= nil then if mouse.Target:IsA("Terrain") then print(mouse.Target.Material) end end end)
Edit: The following code yields no output because the the game thinks that the Mud is plastic. So checking if it is mud with this method won't work.
mouse.Move:Connect(function() if mouse.Target ~= nil then if mouse.Target:IsA("Terrain") then if mouse.Target.Material == Enum.Material.Mud then print(mouse.Target.Material) end end end end)
To see what material a terrain object is at a specific point, you would have to use the ReadVoxels function of terrain objects.
You may be asking, "what is voxels?", well, a voxel is basically a point in 3d space, often arranged in a grid.In Roblox, each cell in the voxel grid measures 4x4x4 studs.
To create the terrain effect, points in the voxel grid are assigned a material. This material is then filled in around the voxel to create the terrain. With Smooth Terrain each voxel contains an occupancy value along with its material value. This occupancy value defines how full the voxel is with the given material. This value can be anywhere between 0 (almost completely empty) to 1 (very full, sometimes overflowing). When Roblox generates terrain based on these values, the shape of the terrain is organically generated to create smooth curves to accommodate varying occupancy values.
The ReadVoxels function takes a region in the form of a region3 and a resolution ranging from 1-4, and returns the raw voxel data for the region specified. This data is returned as 2 3d arrays, the first containing the material values, the second containing the occupancy.
Ex of 3d array :
local 3dArr = { { {"oof"} } } print(3rdArr[1][1][1])
Both arrays also have a Vector3 property called Size that can be used to determine the size of the arrays in each of their dimensions.
ExpandToGrid can be used to ensure that the correct region is used.
With all that said, here is an example of how you can use this:
local mouse = game.Players.LocalPlayer:GetMouse() local rs = game:GetService("RunService") local vector = Vector.new(1,1,1) local resolution = 4 rs.RenderStepped:Connect(function() local Mpos = mouse.Hit.Position local MRegion = Region3.new(MPos - vector,MPos + Vector) MRegion = MRegion:ExpandToGrid(4) local material = workspace.Terrain:ReadVoxels(region,resolution) local size = material.Size for x = 1, size.X do for y = 1, size.Y do for z = 1, size.Z do local mat = material[x][y][z] if mat == Enum.Material.Mud then print("it's mud") end end end end end)
Note that I did not use the array for occupancy for this example, as that has no apparent use for the purpose you are trying to achieve. But remember, ReadVoxel returns both the materials and occupancies arrays.
Reference link:
Hopefully this helped you with your problem!