Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Segment-Segment Distance in 3D - Sublucid Geometry #21

Open
utterances-bot opened this issue Feb 21, 2021 · 4 comments
Open

Segment-Segment Distance in 3D - Sublucid Geometry #21

utterances-bot opened this issue Feb 21, 2021 · 4 comments

Comments

@utterances-bot
Copy link

Segment-Segment Distance in 3D - Sublucid Geometry

One of my favorite functions projects points onto line segments.

https://zalo.github.io/blog/closest-point-between-segments/

Copy link
Owner

zalo commented Feb 21, 2021

The wonderful thing about vector math is that it (should) work in any number of dimensions!

Word Vector Geometry, anyone?

Copy link
Owner

zalo commented Feb 21, 2021

Earlier Comment (before switching to utteranc.es):

Laccer

Thank you for creating this article and making this topic accessible and beautiful!

Copy link

Love the visuals, interesting method for sure. I never thought to solve it this way!
I was inspired to try an approach, but make it completely symmetrical. This is written in lua, so it should be pretty straight forward.

--[[
	line segments defined as
	segmentA(s) = a + s*u where 0 <= s <= 1
	segmentB(t) = b + t*v where 0 <= t <= 1
]]

local function lineSegClosestPoints(a, u, b, v)
	local r = b - a

	local ru = r:Dot(u)
	local rv = r:Dot(v)
	local uu = u:Dot(u)
	local uv = u:Dot(v)
	local vv = v:Dot(v)

	local det = uu*vv - uv*uv

	-- if det is too close to 0, then they're parallel
	-- you can work out a way to handle this case

	-- compute optimal values for s and t
	local s = (ru*vv - rv*uv)/det
	local t = (ru*uv - rv*uu)/det

	-- constrain values s and t so that they describe points on the segments
	s = math.clamp(s, 0, 1)
	t = math.clamp(t, 0, 1)

	-- convert value s for segA into the corresponding closest value t for segB
	-- and vice versa
	local S = (t*uv + ru)/uu
	local T = (s*uv - rv)/vv

	-- constrain
	S = math.clamp(S, 0, 1)
	T = math.clamp(T, 0, 1)

	return a + S*u, b + T*v
end

Copy link

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants