/////////////////////////////////////////////////////////////////////////////
// hair.gsl - simple hair shader
//
// Parameters:
//   Ka - scaling of ambient contribution
//   Kd - scaling of diffuse contribution
//   Ks - scaling of specular contribution
//   roughness - smaller values make tighter specular highlight
//   specularcolor - specular color of hair
//   rootcolor, tipcolor - diffuse color of hair, at root and tip
//   roottippower - how quickly color transitions from root to tip
//
/////////////////////////////////////////////////////////////////////////////
// Copyright 2006 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)
/////////////////////////////////////////////////////////////////////////////


/*
 * LocIllumHair - an illumination model suitable to hairs.
 * Inputs:
 *    T - unit vector along the length of the hair
 *    V - unit view vector 
 *    Kd - diffuse color of the hair
 *    Ks - specular highlight color of the hair
 *    roughness - size of specular highlights
*/
color LocIllumHair (vector T, vector V, 
                    color Kd, color Ks, float roughness)
{
    color C = 0;
    lights (P) {
	float theta = acos (dot(T,normalize(L)));
        // diffuse component
	color diff = sin(theta);
        // specular component
	float cosang = cos (abs (theta - acos (dot(-T,V))));
	float spec = pow (cosang, 1/roughness);
	C += Cl * (Kd*diff + Ks*spec);
    }
    return C;
}




surface
hair 
(
    float Ka = 1
        [[  string description = "Ambient scaling",
            float UImin = 0, float UIsoftmax = 1 ]],
    float Kd = .6
        [[  string description = "Diffuse scaling",
            float UImin = 0, float UIsoftmax = 1 ]],
    float Ks = 0.15
        [[  string description = "Specular scaling",
            float UImin = 0, float UIsoftmax = 1 ]],
    float roughness = 0.025
        [[  string description = "Surface roughness (specular highlight size)",
            float UImin = 0, float UImax = 1,
            string UIenabler = "Ks" ]],
    color specularcolor = 1
        [[  string description = "Specular highlight color",
            string UIenabler = "Ks" ]],
    color rootcolor = color (.109, .037, .007)
        [[  string description = "Hair color at the root" ]],
    color tipcolor = color (.519, .325, .125)
        [[  string description = "Hair color at the tip" ]],
    float roottippower = 2
        [[  string description = "How rapidly the color transitions from root to tip",
            float UImin = 0, float UIsoftmax = 10 ]],
    vector T = dPdv
        [[  string description = "Tangents (default dPdv)" ]]
    )
{
    color hcolor = mix (rootcolor, tipcolor, pow(v,roottippower));

    vector TN = normalize (T);
    vector V = -normalize(I);

    C = Ka*ambient()*hcolor + 
        LocIllumHair (TN, V, Kd*hcolor, Ks*specularcolor, roughness);
    C *= opacity;
}
