Hello forum. i am trying to raycast a bezier curve for hit detection in my volleyball game. The problem is that I have no idea how to do it. Since i have a custom physics system, I need to raycast the curve before the ball gets hit to detect any obstacles on the path. My bezier curve uses three points, so I have thought about raycasting between these positions, but that would be pretty inaccurate. I’ve heard about fastcast curve detection, but I’m not sure if that would suit my situation.
Thank you in advance
You could raycast small segments?
I’m not sure how i would do that before starting the bezier curve though (without causing lag)
Are you trying to calculate collision anywhere along the curve all at once?
yeah thats what im trying to do
Typically raycasting systems are optimized for situations like this where there will be no detection the majority of the time. I would try raycasting small segments of the curve, enough that a player couldn’t see the discrepency from a smooth curve. If you can run this at 10 times the rate that would ever happen in a game and its not lagging, it will probably be fine.
It keeps timing out my script when I use a while loop to loop through the bezier curve, but if I add a wait it is way too slow
There shouldn’t be a wait. How many segments are you doing?
i think around 6-10 should be good enough, but shouldnt it also depend on the length of the curve?
Yes it should. You should use an arc length estimate of some kind to decide how many segments. It should not be freezing with 10 segments, show your code?
Beziers are not parabolas, by the way. Shouldn’t you use parabolas for projectile motion? They also have a defined length formula so you don’t need an estimate.
local t = 0
local ts = 0.2
local destination = pos3
local currentpos = pos1
local rp = RaycastParams.new()
rp.FilterType = Enum.RaycastFilterType.Include
rp.FilterDescendantsInstances = {workspace.Net}
while t ~= 10 do
t += ts
local dist = (currentpos - quadbezier(t, pos1, pos2, pos3)).Magnitude
local r = workspace:Raycast(currentpos, (currentpos - quadbezier(t, pos1, pos2, pos3)).Unit *dist, rp)
if r and r.Instance then
print(r.Instance)
end
currentpos = quadbezier(t, pos1, pos2, pos3)
end
lua format isnt working for some reason
also heres the quadratic equation + lerp if it matters:
local function lerp(a,b,c)
return a + (b-a) *c
end
local function quadbezier(t, a, b ,c)
local l1 = lerp(a,b,t)
local l2 = lerp(b,c,t)
local quad = lerp(l1,l2,t)
return quad
end
Im pretty sure dist will always be zero here I think you meant to do t + ts in that line. In any case it should run 50 times not infinity, so maybe something else is stuck?
dist wont be zero because the time adds at the beginning of each loop
I know thats what you meant to do but it looks like you’ve put the time increment in the wrong place.
Nevermind I see it now.
123123
I got it to work. heres the new code:
local t = 0
local ts = 0.2
local destination = pos3
local currentpos = pos1
local rp = RaycastParams.new()
rp.FilterType = Enum.RaycastFilterType.Include
rp.FilterDescendantsInstances = {workspace.Net}
while t ~= 1 do
t += ts
local dist = (currentpos - quadbezier(t, pos1, pos2, pos3)).Magnitude
local r = workspace:Raycast(currentpos, (quadbezier(t, pos1, pos2, pos3) - currentpos).Unit *dist, rp)
if r and r.Instance then
print(r.Instance)
end
currentpos = quadbezier(t, pos1, pos2, pos3)
end
its only 5 segments but that should be enough