def color(ray: Ray, world: HittableList) -> Vec3: hit_attempt: Optional[HitRecord] = world.hit(ray, 0.0, sys.float_info.max) if hit_attempt is not None: return 0.5 * Vec3(hit_attempt.normal.x + 1, hit_attempt.normal.y + 1, hit_attempt.normal.z + 1) else: unit_direction: Vec3 = ray.direction.unit_vector() t: float = 0.5 * (unit_direction.y + 1) return ((1.0 - t) * UNIT_VEC3) + (t * Vec3(0.5, 0.7, 1.0))
def color(ray: Ray, world: HittableList) -> Vec3: # Some reflected rays hit not at zero but at some near-zero value due to # floating point shennanigans. So we try to compensate for that. hit_attempt: Optional[HitRecord] = world.hit(ray, 0.001, sys.float_info.max) if hit_attempt is not None: target: Vec3 = hit_attempt.p + hit_attempt.normal + random_unit_sphere_point( ) # FIXME mmm recursion # reflector_rate * reflected_color # So in this case, the matterial is a 50% reflector. return 0.5 * color(Ray(hit_attempt.p, target - hit_attempt.p), world) else: unit_direction: Vec3 = ray.direction.unit_vector() t: float = 0.5 * (unit_direction.y + 1) return ((1.0 - t) * UNIT_VEC3) + (t * Vec3(0.5, 0.7, 1.0))
def color(ray: Ray, world: HittableList, depth: int = 0) -> Vec3: # Some reflected rays hit not at zero but at some near-zero value due to # floating point shennanigans. So we try to compensate for that. hit_attempt: Optional[HitRecord] = world.hit(ray, 0.001, sys.float_info.max) if hit_attempt is not None: reflection: ReflectionRecord = hit_attempt.material.scatter( ray, hit_attempt) if depth < 50 and reflection is not None: return reflection.attenuation * color(reflection.scattering, world, depth + 1) else: return Vec3(0, 0, 0) else: unit_direction: Vec3 = ray.direction.unit_vector() t: float = 0.5 * (unit_direction.y + 1) return ((1.0 - t) * UNIT_VEC3) + (t * Vec3(0.5, 0.7, 1.0))
def color(ray: Ray, world: HittableList, depth: int) -> Vec3: # Some reflected rays hit not at zero but at some near-zero value due to # floating point shennanigans. So we try to compensate for that. hit_attempt: Optional[HitRecord] = world.hit(ray, 0.001, sys.float_info.max) if hit_attempt is not None: scattering: ReflectionRecord = hit_attempt.material.scatter(ray, hit_attempt) # FIXME Is it really worthwhile to check if reflection is not None here? # All our Materials assume that a hit has been made, and therefore some # reflection should happen (unless it is Vanta). if depth < 50 and scattering is not None: # Compare this with the hard-coded reflection in 6_matterial. return scattering.attenuation * color(scattering.scattering, world, depth + 1) else: return Vec3(0, 0, 0) else: unit_direction: Vec3 = ray.direction.unit_vector() t: float = 0.5 * (unit_direction.y + 1) return ((1.0 - t) * UNIT_VEC3) + (t * Vec3(0.5, 0.7, 1.0))