#version 330 #define MAX_LIGHTS 4 #define LIGHT_DIRECTIONAL 0 #define LIGHT_POINT 1 #define PI 3.14159265358979323846 struct Light { int enabled; int type; vec3 position; vec3 target; vec4 color; float intensity; }; // Input vertex attributes (from vertex shader) in vec3 fragPosition; in vec2 fragTexCoord; in vec4 fragColor; in vec3 fragNormal; in vec4 shadowPos; in mat3 TBN; // Output fragment color out vec4 finalColor; // Input uniform values uniform int numOfLights; uniform sampler2D albedoMap; uniform sampler2D mraMap; uniform sampler2D normalMap; uniform sampler2D emissiveMap; // r: Hight g:emissive uniform vec2 tiling; uniform vec2 offset; uniform int useTexAlbedo; uniform int useTexNormal; uniform int useTexMRA; uniform int useTexEmissive; uniform vec4 albedoColor; uniform vec4 emissiveColor; uniform float normalValue; uniform float metallicValue; uniform float roughnessValue; uniform float aoValue; uniform float emissivePower; // Input lighting values uniform Light lights[MAX_LIGHTS]; uniform vec3 viewPos; uniform vec3 ambientColor; uniform float ambient; // refl in range 0 to 1 // returns base reflectivity to 1 // incrase reflectivity when surface view at larger angle vec3 schlickFresnel(float hDotV,vec3 refl) { return refl + (1.0 - refl) * pow(1.0 - hDotV,5.0); } float ggxDistribution(float nDotH,float roughness) { float a = roughness * roughness * roughness * roughness; float d = nDotH * nDotH * (a - 1.0) + 1.0; d = PI * d * d; return a / max(d,0.0000001); } float geomSmith(float nDotV,float nDotL,float roughness) { float r = roughness + 1.0; float k = r * r / 8.0; float ik = 1.0 - k; float ggx1 = nDotV / (nDotV * ik + k); float ggx2 = nDotL / (nDotL * ik + k); return ggx1 * ggx2; } vec3 pbr(){ vec3 albedo = texture(albedoMap,vec2(fragTexCoord.x*tiling.x+offset.x,fragTexCoord.y*tiling.y+offset.y)).rgb; albedo = vec3(albedoColor.x*albedo.x,albedoColor.y*albedo.y,albedoColor.z*albedo.z); float metallic = clamp(metallicValue,0.0,1.0); float roughness = clamp(roughnessValue,0.0,1.0); float ao = clamp(aoValue,0.0,1.0); if(useTexMRA == 1) { vec4 mra = texture(mraMap, vec2(fragTexCoord.x * tiling.x + offset.x, fragTexCoord.y * tiling.y + offset.y)) * useTexMRA; metallic = clamp(mra.r+metallicValue,0.04,1.0); roughness = clamp(mra.g+roughnessValue,0.04,1.0); ao = (mra.b+aoValue)*0.5; } vec3 N = normalize(fragNormal); if(useTexNormal == 1) { N = texture(normalMap, vec2(fragTexCoord.x * tiling.x + offset.y, fragTexCoord.y * tiling.y + offset.y)).rgb; N = normalize(N * 2.0 - 1.0); N = normalize(N * TBN); } vec3 V = normalize(viewPos - fragPosition); vec3 e = vec3(0); e = (texture(emissiveMap, vec2(fragTexCoord.x*tiling.x+offset.x, fragTexCoord.y*tiling.y+offset.y)).rgb).g * emissiveColor.rgb*emissivePower * useTexEmissive; //return N;//vec3(metallic,metallic,metallic); //if dia-electric use base reflectivity of 0.04 otherwise ut is a metal use albedo as base reflectivity vec3 baseRefl = mix(vec3(0.04),albedo.rgb,metallic); vec3 Lo = vec3(0.0); // acumulate lighting lum for(int i=0;i