package eu.jonahbauer.raytracing.render.material; import eu.jonahbauer.raytracing.math.Ray; import eu.jonahbauer.raytracing.math.Vec3; import eu.jonahbauer.raytracing.render.Color; import eu.jonahbauer.raytracing.scene.HitResult; import org.jetbrains.annotations.NotNull; import java.util.Objects; import java.util.Optional; import java.util.random.RandomGenerator; public record MetallicMaterial(@NotNull Color albedo, double fuzz) implements Material { public MetallicMaterial(@NotNull Color albedo) { this(albedo, 0); } public MetallicMaterial { Objects.requireNonNull(albedo, "albedo"); if (fuzz < 0 || !Double.isFinite(fuzz)) throw new IllegalArgumentException("fuzz must be non-negative"); } @Override public @NotNull Optional scatter(@NotNull Ray ray, @NotNull HitResult hit, @NotNull RandomGenerator random) { var newDirection = Vec3.reflect(ray.direction(), hit.normal()); if (fuzz > 0) { newDirection = newDirection.unit().plus(Vec3.random(random, true).times(fuzz)); } return Optional.of(new ScatterResult(new Ray(hit.position(), newDirection), albedo)); } }