Im trying to debug my simple raytracer that simulates rays from one spot crossing a lens. I just need the refraction effect for this.
I tried to do it by hand but finally i found refract
from GLSL, which is documented in GLSL 1.1 like this:
//For a given incident vector I, surface normal N and ratio of
//indices of refraction, eta, refract returns the refraction vector, R.
//R is calculated as:
k = 1.0 - eta * eta * (1.0 - dot(N, I) * dot(N, I));
if (k < 0.0)
R = genType(0.0); // or genDType(0.0)
else
R = eta * I - (eta * dot(N, I) + sqrt(k)) * N;
//The input parameters I and N should be normalized in order to
//achieve the desired result.
I wonder where these equations came from. I searched over the internet and books i own (Real Time Rendering bible, or Phisically Based Rendering last ed.) and all of them refer to this implementation, without explanation, or just tell the solution.
Trying to do it by hand from the begining using geometry brings me to other answers but obviously is hard work just for a very common function like GLSL's. So i prefer to use this optimiced notation.
I only have this:
a.b = |a||b|cos(angle) (Dot product)
angleOut = eta * sin(angleIn) (Snell's Law).
Do you know where it comes from? Any document or reference to read?
You can find an explanation in section 16.5 of the book:
FOLEY, James D. (ed.). Computer graphics: Principles and practice, Second Edition in C. Addison-Wesley Professional, 1996.
These are the relevant pages, they came from this Google Books search (consulted at 2013-12-29T10:15:00+01:00):
The reference [HECK84] is
and has a detailed appendix with title "Reflection and Refraction Transformations".