-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathhittable.go
63 lines (55 loc) · 1.31 KB
/
hittable.go
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
52
53
54
55
56
57
58
59
60
61
62
63
package main
import (
"math"
)
type Hittable interface {
Hit(Ray, float32, float32, HitRecord) bool
}
type IHitRecord interface {
setFaceNormal(Ray, Vec3)
}
type HitRecord struct {
p point3
normal Vec3
t float32
front_face bool
}
type Sphere struct {
Center point3
Radius float32
}
func (obj Sphere) Hit(r Ray, t_min, t_max float32, rec *HitRecord) bool {
oc := Minus(r.Orig, obj.Center)
a := LengthSquared(r.Dir)
half_b := Dot(oc, r.Dir)
c := LengthSquared(oc) - obj.Radius*obj.Radius
discriminant := half_b*half_b - a*c
if discriminant > 0 {
root := float32(math.Sqrt(float64(discriminant)))
temp := (-half_b - root) / a
if temp < t_max && temp > t_min {
rec.t = temp
rec.p = r.At(rec.t)
outward_normal := DivedC(Minus(rec.p, obj.Center), obj.Radius)
rec.setFaceNormal(r, outward_normal)
return true
}
temp = (-half_b + root) / a
if temp < t_max && temp > t_min {
rec.t = temp
rec.p = r.At(rec.t)
outward_normal := DivedC(Minus(rec.p, obj.Center), obj.Radius)
rec.setFaceNormal(r, outward_normal)
return true
}
}
return false
}
func (hr *HitRecord) setFaceNormal(r Ray, outward_normal Vec3) {
hr.front_face = Dot(r.Dir, outward_normal) < 0
if hr.front_face {
hr.normal = outward_normal
} else {
hr.normal = TimesC(outward_normal, -1)
}
}