Scripting HelpersARCHIVE
A little piece of Roblox history. Preserved for everyone, one question at a time.Read about the archive →
COMMUNITY QUESTION

Using :ClosestPoint to find the distance between a part and point on ray?

Im trying to use ray:ClosestPoint() to get the distance between a part and the point on the ray closest to the part. Im not too sure how to use this function because of the poor documentation of the wiki but my current implementation looks like this:

ray = Ray.new(Tool.Barrel.CFrame.p,(Mouse.Hit.p-Tool.Barrel.CFrame.p).unit*999)
local part, position = workspace:FindPartOnRay(ray, workspace.RayModel, false, true)
			
local closestPoint = ray:ClosestPoint(workspace.DUDE.Head.Position)

for some reason, closest point is returning a Vector tens of thousands of studs off the map way out of sight at the end of the ray cast. Even when i make the ray shorter It still gives me this issue. pls help

3 comments

0

it also only seems to work when the ray is pointed away from the part

1

the function is broken. what r u trying to do exactly

0

@theluaBanana like I said, trying to find the closest point on a ray to a part in the workspace. the only other method I know of is using dot product but thats giving me trouble too

1 answer

You need to reject the point from the ray. I wrote this simple demonstration to showcase how it can be implemented on Roblox when we have to take into account that the ray doesn't start from (0, 0, 0).

Pardon me for possibly wrong terminology. I'd appreciate if somebody could look at it and clean up the math part. The equations may not be in their clearest form.

local part = workspace.Part
local RunService = game:GetService("RunService")

local rayOrigin = Vector3.new(-20, 0, -20)
local rayDir = Vector3.new(0, 1, 1)
local rayLen = 100

--

local function drawPoint(v3, p)
	p = p or Instance.new("Part")
	p.Anchored = true
	p.BrickColor = BrickColor.Red()
	p.Size = Vector3.new(2, 2, 2)
	p.CFrame = CFrame.new(v3)
	p.Parent = workspace
	return p
end

local function drawRay(ray)
	local p = Instance.new("Part")
	p.Anchored = true
	p.BrickColor = BrickColor.Green()
	p.CFrame = CFrame.new(ray.Origin, ray.Origin + ray.Direction) * CFrame.new(0, 0, -ray.Direction.Magnitude / 2)
	p.Size = Vector3.new(1, 1, ray.Direction.Magnitude)
	p.Parent = workspace
	return p
end

local function getRayClosestPoint(ray, point)
	--	shift point to be relative to the origin of the ray
	local a, b = ray.Origin - point, ray.Direction
	--	calculate rejection of a from b
	local v = a - ((a:Dot(b)) / (b:Dot(b))) * b
	--	add rejection to point to get the closest point on the ray
	return point + v
end

--

local ray = Ray.new(rayOrigin, rayDir * rayLen)
drawRay(ray)
local point = getRayClosestPoint(ray, part.Position)
local pointPart = drawPoint(point)

RunService.Stepped:Connect(function()
	point = getRayClosestPoint(ray, part.Position)
	drawPoint(point, pointPart)
end)

This discussion is preserved as it was. New answers, comments, and votes are closed.