blob: d2b15cc5c8aedb89fef3877ac1eb8ebd8fa38d8e (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
|
#include <math.h>
#include "vector.h"
#include "ray.h"
// https://en.wikipedia.org/wiki/Line%E2%80%93sphere_intersection
// http://viclw17.github.io/2018/07/16/raytracing-ray-sphere-intersection/
COORD_T ray_intersect_sphere(sphere_t *s, ray_t *ray)
{
// Vector between vector start and center of circle
vector_t oc;
vector_sub(&oc, ray->start, s->center);
// Solve quadratic function
// TODO Not sure if this step i neccesary because dir is unit
COORD_T a = vector_dot(&ray->direction, &ray->direction);
COORD_T b = 2 * vector_dot(&oc, &ray->direction);
COORD_T c = vector_dot(&oc, &oc) - s->radius * s->radius;
COORD_T d = b * b - 4 * a * c;
// no intersection
if (d < 0) {
return -1;
}
// Else take the closest intersection
return (-b - sqrt(d) ) / (2.0 * a);
}
// Requires that vectors are normalized
// https://www.scratchapixel.com/lessons/3d-basic-rendering/minimal-ray-tracer-rendering-simple-shapes/ray-plane-and-ray-disk-intersection
COORD_T ray_intersect_plane(plane_t *p, ray_t *ray)
{
// If zero ray is parralel to plane
COORD_T nr = vector_dot(&p->norm, &ray->direction);
vector_print(&ray->direction);
//
// Take care of rounding errors
if (nr < ZERO_APROX && nr > -ZERO_APROX) {
return -1;
}
// Calculate distance
vector_t tmp;
vector_copy(&tmp, p->start);
vector_sub(&tmp, &tmp, ray->start);
COORD_T t = vector_dot(&tmp, &p->norm) / nr;
return t;
}
|