RandyGaul / cute_headers

Collection of cross-platform one-file C/C++ libraries with no dependencies, primarily used for games
4.21k stars 264 forks source link

Fix raycasts ending right on the edge of an AABB #378

Closed lmbarros closed 2 months ago

lmbarros commented 2 months ago

Alright, I'd be lying if said I fully understand what I am doing here, but this will not stop me :sweat_smile:

I am (very) slowly porting cute_c2 to Go for a project of mine, and as part of this effort I am writing unit tests for everything in the library. That's how I found the issue I describe in the commit message:


The time (t) component of the raycast result was incorrect when the ray ended right on the edge of the AABB. For example:

c2AABB aabb = {-2.0, -1.0, 3.0, 4.0};
c2Ray ray = {{-4.0, 2.0}, {1.0, 0.0}, 2.0};
c2Raycast out;

int res = c2RaytoAABB(ray, aabb, &out);
printf("t=%f\n", out.t);

This would print a t value of 0.0 when it should be 2.0.


Very important: I tested this just very briefly on the C library, so you may want to at least do any sanity checking you'd normally do.

Anyway, as far as I can tell, my proposed change makes sense -- but I also believe it works because it fixes these cases of the ray ending right on the edge of an AABB, and not breaking any of the numerous other test cases I have for raycasts to AABBs.

Worth mentioning: I think the change to c2RayToPlane_OneDimensional() isn't really necessary. I believe the end result will be same if you leave it out. However, I believe my proposed change makes the code match the comments regarding which branch deal with the "ray ending directly on the plane" case.

I hope you find this useful! Loving cute_c2! :smile:

RandyGaul commented 2 months ago

Looks pretty good, thanks for taking the time on the writeup, very helpful :)