#version 450

layout(binding = 0) uniform global {
    mat4 view;
    mat4 proj;
};

layout(binding = 1) uniform entity {
    mat4 model;
    vec3 color;
    vec4 material;
};

layout(location = 0) in vec3 iFragPos;
layout(location = 1) in vec3 iNormal;
layout(location = 2) in vec2 iFragTexCoord;

layout(location = 0) out vec4 oColor;

layout(binding = 2) uniform sampler2D textureSampler;

vec3 dirLight = vec3(0.0f, -1.0f, 0.0f);

float ka = material.r;
float kd = material.g;
float ks = material.b;
float alpha = material.a;

vec3 calculateDirLight(vec3 normal) {
    vec3 N = normalize(normal);
    vec3 L = normalize(vec3(view * vec4(-dirLight, 0.0f))); // transform from world to view space, 4th element is 0 because it represents a direction, not position
    vec3 V = normalize(-iFragPos);
    vec3 H = normalize(L + V);

    float NL = max(dot(N, L), 0.0f);
    float VR = pow(max(dot(N, H), 0.0), alpha);

    vec3 diffuse, specular;
    if (color.r != 0.0 || color.g != 0.0 || color.b != 0.0) {
        diffuse  = kd * NL * color;
        specular = ks * vec3(VR) * color;
    } else {
        diffuse  = kd * NL * texture(textureSampler, iFragTexCoord).rgb; // dirLight.color;
        specular = ks * vec3(VR); // dirLight.color * texture(specular_texture, UV).rgb;
    }

    return diffuse + specular;
}

void main() {
    // oColor = texture(textureSampler, iFragTexCoord);
    // return;

    vec3 result = vec3(0.0f);

    vec3 ambient;
    if (color.r != 0.0 || color.g != 0.0 || color.b != 0.0) {
        ambient = ka * color;
    } else {
        ambient = ka * texture(textureSampler, iFragTexCoord).rgb;
    }

    result += ambient + calculateDirLight(iNormal);

    oColor = vec4(result, 1.0f);
}
