Raytracing done :3
This commit is contained in:
parent
95c7fcaa33
commit
64449e18f7
2 changed files with 809675 additions and 89648 deletions
113
main.go
113
main.go
|
@ -164,7 +164,7 @@ func Reflect(v Vec3, n Vec3) Vec3 {
|
|||
func Refract(uv, n Vec3, etai_over_etat float32) Vec3 {
|
||||
cos_theta := float32(math.Min(float64(Dot(uv.Neg(), n)), 1.0))
|
||||
r_out_perp := uv.Add(n.Mult(cos_theta)).Mult(etai_over_etat)
|
||||
r_out_parallel := n.Mult(-float32(math.Sqrt(math.Abs(1.0 - float64(r_out_perp.Length_squared())))))
|
||||
r_out_parallel := n.Mult(float32(math.Sqrt(math.Abs(1.0 - float64(r_out_perp.Length_squared())))))
|
||||
return r_out_perp.Add(r_out_parallel)
|
||||
}
|
||||
|
||||
|
@ -347,6 +347,15 @@ func (s Sphere) Hit_sphere(r *Ray, ray_t *Interval, rec *Hit_record) bool {
|
|||
return true
|
||||
}
|
||||
|
||||
func NewSphere(center Vec3, radius float32, mat Material) Sphere {
|
||||
return Sphere{
|
||||
center: center,
|
||||
radius: radius,
|
||||
mat: mat,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// =============== HITTABLE ==================
|
||||
type Hittable struct {
|
||||
spheres []Sphere
|
||||
|
@ -432,9 +441,9 @@ func (mat Material) Scatter(r_in *Ray, rec *Hit_record, attenuation *Vec3, scatt
|
|||
}
|
||||
} else if (mat.material == 2) { //Dielectric
|
||||
*attenuation = NewColor(1.0, 1.0, 1.0)
|
||||
var refraction_ration float32
|
||||
var refraction_ration float32 = 1.0
|
||||
if rec.front_face {
|
||||
refraction_ration = 1.0/mat.ir
|
||||
refraction_ration /= mat.ir
|
||||
} else {
|
||||
refraction_ration = mat.ir
|
||||
}
|
||||
|
@ -442,11 +451,8 @@ func (mat Material) Scatter(r_in *Ray, rec *Hit_record, attenuation *Vec3, scatt
|
|||
|
||||
cos_theta := float32(math.Min(float64(Dot(unit_direction.Neg(), rec.normal)), 1.0))
|
||||
sin_theta := float32(math.Sqrt(float64(1.0 - cos_theta*cos_theta)))
|
||||
var cannot_refract bool
|
||||
var direction Vec3
|
||||
if (refraction_ration * sin_theta > 1.0) {
|
||||
cannot_refract = true
|
||||
}
|
||||
cannot_refract := refraction_ration*sin_theta > 1.0
|
||||
|
||||
if (cannot_refract || Reflectance(cos_theta, refraction_ration) > RandomDouble()) {
|
||||
direction = Reflect(unit_direction, rec.normal)
|
||||
|
@ -597,56 +603,77 @@ func (cam *Camera) Pixel_sample_square() Vec3 {
|
|||
|
||||
// =============== MAIN =====================
|
||||
func main() {
|
||||
|
||||
// Materials
|
||||
material_ground := NewMaterial(0, NewColor(0.8, 0.8, 0.0), 0.0, 0.0)
|
||||
material_center := NewMaterial(0, NewColor(0.1, 0.2, 0.5), 0.0, 0.0)
|
||||
material_left := NewMaterial(2, NewColor(1.0, 1.0, 1.0), 0.0, 1.5)
|
||||
material_right := NewMaterial(1, NewColor(0.8, 0.6, 0.2), 0.0, 0.0)
|
||||
|
||||
// World
|
||||
|
||||
world := NewHittable()
|
||||
|
||||
groundMaterial := NewMaterial(0, NewColor(0.5, 0.5, 0.5), 0.0, 0.0)
|
||||
world.Add(Sphere{
|
||||
center: NewVec3(0.0, -100.5, -1.0),
|
||||
radius: 100.0,
|
||||
mat: material_ground,
|
||||
center: NewVec3(0, -1000, 0),
|
||||
radius: 1000,
|
||||
mat: groundMaterial,
|
||||
})
|
||||
|
||||
for a := -11; a < 11; a++ {
|
||||
for b := -11; b < 11; b++ {
|
||||
chooseMat := RandomDouble()
|
||||
center := NewVec3(float32(a)+0.9*RandomDouble(), 0.2, float32(b)+0.9*RandomDouble())
|
||||
|
||||
if (center.Sub(NewVec3(4, 0.2, 0)).Length() > 0.9) {
|
||||
var sphereMaterial Material
|
||||
|
||||
if chooseMat < 0.8 {
|
||||
// diffuse
|
||||
albedo := RandomVec3().MultVec(RandomVec3())
|
||||
sphereMaterial = NewMaterial(0, albedo, 0.0, 0.0)
|
||||
} else if chooseMat < 0.95 {
|
||||
// metal
|
||||
albedo := RandomVec3(0.5, 1)
|
||||
fuzz := RandomDoubleInRange(0, 0.5)
|
||||
sphereMaterial = NewMaterial(1, albedo, fuzz, 0.0)
|
||||
} else {
|
||||
// glass
|
||||
sphereMaterial = NewMaterial(2, NewColor(1.0, 1.0, 1.0), 0.0, 1.5)
|
||||
}
|
||||
world.Add(Sphere{
|
||||
center: NewVec3(0, 0, -1),
|
||||
radius: 0.5,
|
||||
mat: material_center,
|
||||
center: center,
|
||||
radius: 0.2,
|
||||
mat: sphereMaterial,
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
material1 := NewMaterial(2, NewColor(1.0, 1.0, 1.0), 0.0, 1.5)
|
||||
world.Add(Sphere{
|
||||
center: NewVec3(-1, 0, -1),
|
||||
radius: 0.5,
|
||||
mat: material_left,
|
||||
center: NewVec3(0, 1, 0),
|
||||
radius: 1.0,
|
||||
mat: material1,
|
||||
})
|
||||
|
||||
material2 := NewMaterial(0, NewColor(0.4, 0.2, 0.1), 0.0, 0.0)
|
||||
world.Add(Sphere{
|
||||
center: NewVec3(-1, 0, -1),
|
||||
radius: -0.4,
|
||||
mat: material_left,
|
||||
center: NewVec3(-4, 1, 0),
|
||||
radius: 1.0,
|
||||
mat: material2,
|
||||
})
|
||||
|
||||
material3 := NewMaterial(1, NewColor(0.7, 0.6, 0.5), 0.0, 0.0)
|
||||
world.Add(Sphere{
|
||||
center: NewVec3(1.0, 0, -1.0),
|
||||
radius: 0.5,
|
||||
mat: material_right,
|
||||
center: NewVec3(4, 1, 0),
|
||||
radius: 1.0,
|
||||
mat: material3,
|
||||
})
|
||||
// Image
|
||||
|
||||
cam := NewCamera()
|
||||
cam.aspect_ratio = 16.0 / 9.0
|
||||
cam.image_width = 400
|
||||
cam.samples_per_pixel = 100
|
||||
cam.max_depth = 50
|
||||
cam.image_width = 1200
|
||||
cam.samples_per_pixel = 200
|
||||
cam.max_depth = 45
|
||||
cam.vfov = 20
|
||||
cam.lookfrom = NewVec3(-2,2,1)
|
||||
cam.lookat = NewVec3(0,0,-1)
|
||||
cam.vup = NewVec3(0,1,0)
|
||||
cam.defocus_angle = 10.0
|
||||
cam.focus_dist = 3.4
|
||||
cam.lookfrom = NewVec3(13, 2, 3)
|
||||
cam.lookat = NewVec3(0, 0, 0)
|
||||
cam.vup = NewVec3(0, 1, 0)
|
||||
cam.defocus_angle = 0.6
|
||||
cam.focus_dist = 10.0
|
||||
|
||||
cam.Render(world)
|
||||
// INFO: The pixels are written out in rows.
|
||||
// Image file can be created with
|
||||
// go run main.go > image.ppm
|
||||
}
|
Loading…
Reference in a new issue