#version 330 core
out vec4 FragColor;

in VS_OUT {
    vec3 FragPos;
    vec3 OriginalNormal;
    vec3 Normal;
    vec2 TexCoords;
} fsIn;

uniform samplerCube skybox;
uniform samplerCube skybox2;
uniform vec3 lightPos;
uniform vec3 viewPos;
uniform vec3 flashColor;

vec3 calcRim(vec3 N, vec3 V)
{
	float rimPower = 10.0f;
	vec3 rimColor = vec3(0.3);
	float f = 1 - dot(N,V);
	f = smoothstep(0.0,1.0,f);
	f = pow(f, rimPower);
	return rimColor * f;
}

void main()
{           
    vec3 color = vec3(0.0, 0.0, 0.0);

    vec3 lightDir = normalize(lightPos - fsIn.FragPos);
    vec3 normal = normalize(fsIn.Normal);
    float diff = max(dot(lightDir, normal), 0.0);
    vec3 diffuse = diff * vec3(.05);

    vec3 viewDir = normalize(viewPos - fsIn.FragPos);
    
    float spec = 0.0;
    float spec2 = 0.0;
    vec3 halfwayDir = normalize(lightDir + viewDir);  
    spec = pow(max(dot(normal, halfwayDir), 0.0), 2048.0);
    spec2 = pow(max(dot(fsIn.OriginalNormal, halfwayDir), 0.0), 512.0);
    
    vec3 specular = vec3(2.0) * spec;
    vec3 specular2 = vec3(2.0) * spec2;

	vec3 ReflectO = normalize(fsIn.OriginalNormal);
	vec4 reflectionColorO = texture(skybox, ReflectO);
	
	vec3 Reflect = normalize(2 * diff * lightDir-normal);
	vec4 reflectionColor = texture(skybox, Reflect);
	vec3 Reflect2 = normalize(lightDir);
	vec4 reflectionColor2 = texture(skybox, Reflect2);
	vec3 rimC = calcRim(ReflectO, viewDir);
	vec4 reflectionColor3 = texture(skybox2, Reflect2);
	
    float diffRR = max(dot(viewDir, fsIn.OriginalNormal), 0.0);
	vec3 fLightInside = diffRR * diffRR * diffRR * reflectionColorO.xyz*vec3(0.1)*((vec3(1.0)-rimC)*flashColor);

	float insideCorrection = 1.4;
    fLightInside = pow(fLightInside, vec3(1.0/insideCorrection));
	
	vec3 dL = reflectionColor.xyz * diffuse;
	float generalHighlight = 1.6;
    dL.xyz = pow(dL.xyz, vec3(1.0/generalHighlight));

    //FragColor = vec4(reflectionColorO.xyz*vec3(0.02)*((vec3(1.0)-rimC)*flashColor) + reflectionColor.xyz * diffuse + (vec3(.08)*diffuse) + rimC*reflectionColor.xyz + specular, 1.0f);
	FragColor = vec4(fLightInside + dL + (vec3(.1)*diffuse) + rimC*reflectionColor.xyz + specular + specular2 + reflectionColor3.xyz*vec3(0.4), 1.0);
	//FragColor = vec4(diffuse,1);
	
}