/////////////////////////////////////////////////////////////////////////////
// fakeglass.osl -- Shiny reflective glass.
//
// Description:
//   Makes semi-transparent glass, with environment reflections, but
//   just using a fake opacity trick for transparency.  This is great
//   for window glass, or any glass that is a thin enough sheet that you
//   don't really need to see the warping of the refracted image.  It's
//   much faster than ray tracing the refractions.
// 
// Parameters:
//    Ka, Kd, Ks, roughness - The usual meaning
//    Kr - coefficient for mirror-like reflections of environment
//    blur - how blurry are the reflections? (0 = perfectly sharp)
//    envname, envspace - controls for reflection
//    Kt - coefficient for refracted transmission
//    eta - the coefficient of refraction of the glass
//    transmitcolor - filter color for refracted light
//
/////////////////////////////////////////////////////////////////////////////
// Copyright 2004 NVIDIA Corporation.  All Rights Reserved.
// 
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
// 
// * Redistributions of source code must retain the above copyright
//   notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above copyright
//   notice, this list of conditions and the following disclaimer in the
//   documentation and/or other materials provided with the distribution.
// * Neither the name of NVIDIA nor the names of its contributors
//   may be used to endorse or promote products derived from this software
//   without specific prior written permission.
// 
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
//
// (This is the Modified BSD License)
/////////////////////////////////////////////////////////////////////////////



#include "material.h"


surface
fakeglass
    [[ string description = "Glass, fake (opacity-based) refractions" ]]
(
    float Ka = 0.2
        [[  string description = "Ambient scaling",
            float UImin = 0, float UIsoftmax = 1 ]],
    float Kd = 0
        [[  string description = "Diffuse scaling",
            float UImin = 0, float UIsoftmax = 1 ]],
    float Ks = 0.5
        [[  string description = "Specular scaling",
            float UImin = 0, float UIsoftmax = 1 ]],
    float roughness = 0.05
        [[  string description = "Surface roughness (specular highlight size)",
            float UImin = 0, float UImax = 1,
            string UIenabler = "Ks" ]],

    float Kr = 1
        [[  string description = "Reflectivity / Environment scaling",
            string UIlabel = "Reflectivity",
            float UImin = 0, float UIsoftmax = 1,
            string UIgroupbegin = "Reflections" ]],
    float reflblur = 0
        [[  string description = "Reflection environment blur",
            string UIenabler = "Kr",
            float UImin = 0, float UIsoftmax = 1 ]],
    string envname = ""
        [[  string description = "Map or geometry set name for reflections",
            string UIlabel = "Environment name",
            string UIenabler = "Kr",
            string UItype = "environment" ]],
    string envspace = "world"
        [[  string description = "Coordinate system for environment map lookup",
            string UIlabel = "Environment space",
            string UIenabler = "Kr",
            string UItype = "coordsys" ]],
    float samples = 1
        [[  string description = "Reflection samples (for ray tracing)",
            string UIlabel = "Reflection samples",
            string UIenabler = "Kr",
            string UItype = "int", float UImin = 1, float UIsoftmax = 64,
            string UIgroupend = "Reflections" ]],

    float Kt = 1
        [[  string description = "Refraction scaling",
            float UImin = 0, float UIsoftmax = 1,
            string UIgroupbegin = "Refraction" ]],
    float eta = 1.5
        [[  string description = "Index of refraction",
            float UImin = 1, float UIsoftmax = 2 ]],
    color transmitcolor = 1
        [[  string description = "Refraction tint color",
            string UIenabler = "Kt", string UIgroupend = "Refraction" ]]
  )
{
    normal Nf = faceforward (normalize(N), I);
    vector IN = normalize (I);

    // Compute the reflection & refraction directions and amounts
    vector Rfldir, Rfrdir;   // Smooth reflection/refraction directions
    float kr, kt;
    fresnel (IN, Nf, 1/eta, kr, kt, Rfldir, Rfrdir);
    kt = 1-kr;   // Physically incorrect, but portable
    kr *= Kr;
    kt *= Kt;
    // Speedup -- at deep ray levels, reflection is unimportant
    if (raylevel() > 0)
	kr = 0;

    // Calculate the reflection & refraction color
    color Crefl = Environment (envname, normalize(Rfldir), envspace,
			       reflblur, samples, kr);
    C = (C * (Ka*ambient() + Kd*diffuse(Nf)) +
         (kr*Crefl + Ks*LocIllumGlossy(Nf,-IN,roughness,0.5)));
    opacity = 1-kt*transmitcolor;
}
