Hi, yet another question on SAT (sorry!).
What are some robust approaches to swept SAT collision detection in 3D. I have implemented the algorithm for this thanks to the help from many articles on this website, however, none of these articles address the problem of making the collision detection numerically robust.
While my current implmentation is able to successfully detect swept collisions, often the objects will interpenetrate thanks to floating point errors, thus causing the objects to become stuck. How can these floating point errors be adrressed?
Furthermore, none of the articles address the problem of collision resolution, for example, calculating the collision normal vector for a swept test so that objects can be slided along one another. How can my algorithm be modified such that this value can be returned?
This seems like a fairly common thing to want to do, why can I find no information for this on the internet, most articles I find consider non swept cases but my particular scenario requires continuous collision detection so this is not an option for me.
This has massively stumped me for weeks now, so any help is genuinely massively appreciated.
I will include the code for my swept intersection testing function below.
function testAxes(corners1, corners2, axes, velocity)
local tFirst = 0
local tLast = 100000
local T
local bestAxis
for i, axis in pairs(axes) do
if axis.Magnitude ~= 0 and tostring(axis) ~= "NAN, NAN, NAN" then
local adists, bdists = {}, {};
for i = 1, 8 do
table.insert(adists, corners1[i]:Dot(axis));
table.insert(bdists, corners2[i]:Dot(axis));
end;
local max0, min0 = math.max(unpack(adists)), math.min(unpack(adists));
local max1, min1 = math.max(unpack(bdists)), math.min(unpack(bdists));
local speed = axis:Dot(velocity)
if max1 < min0 then
if speed <= 0 then
return false, tFirst, tLast
end
T = (min0 - max1)/speed;
if T > tFirst then
tFirst = T
bestAxis = axis
end
if tFirst > 1 then
return false, tFirst, tLast
end
T = (max0 - min1) / speed;
if T < tLast then
tLast = T
end
if tFirst > tLast then
return false, tFirst, tLast
end
elseif max0 < min1 then
if speed >= 0 then
return false, tFirst, tLast
end
T = (max0 - min1)/speed;
if T > tFirst then
tFirst = T
bestAxis = -axis
end
if tFirst > 1 then
return false, tFirst, tLast
end
T = (min0 - max1) / speed;
if T < tLast then
tLast = T
end
if tFirst > tLast then
return false, tFirst, tLast
end
else -- overlapping
if speed > 0 then
T = (max0-min1)/speed;
if T < tLast then tLast = T end
if tFirst > tLast then
return false, tFirst, tLast
end
elseif speed < 0 then
T = (min0 - max1)/speed;
if T < tLast then tLast = T end
if tFirst > tLast then
return false, tFirst, tLast
end
end
end
end
end
return true, tFirst, tLast, bestAxis
end;