// vert // out vec3 view_dir; uniform vec4 view_corners[4]; void main(void) { gl_Position = qgl_ftransform(); view_dir = view_corners[gl_VertexID].xyz; } // frag // in vec3 view_dir; uniform vec2 dt; uniform float z_near; uniform sampler2D tex_0, tex_1, tex_2, tex_3, tex_4; uniform int lights_start, lights_count; const vec3 luma = vec3(0.299, 0.587, 0.114); const float _pe = 2.4e-7; vec4 pos, lpos, shp; vec3 li, si, ldir, halfV, bn, bn2, lwdir; //vec3 vds, vds2; float shm_diff, shm_spec, dist, NdotL, NdotH, spot, ldist, diff, sdist, shadow; void calcLight(in int index, in vec3 n, in vec3 v) { lpos = qgl_light_position[index].position; ldir = lpos.xyz - (pos.xyz * lpos.w); ldist = length(ldir); ldir = normalize(ldir); //ldir = vec3(0,0,1); halfV = normalize(ldir + v); NdotL = max(dot(n, ldir), 1E-6); NdotH = max(dot(n, halfV), 1E-6); spot = step(1.001E-6, NdotL) * qgl_light_parameter[index].intensity; #ifdef SPOT float scos = max(dot(-ldir, qgl_light_position[index].direction.xyz), 0.); spot *= scos * step(qgl_light_parameter[index].endAngleCos, scos); spot *= smoothstep(qgl_light_parameter[index].endAngleCos, qgl_light_parameter[index].startAngleCos, scos); /*//lwdir = mat3(mat_viewi) * qgl_Light[index].direction.xyz; //bn = normalize(cross(lwdir, vec3(1, 0, 0))); //bn2 = normalize(cross(lwdir, bn)); float ds = ldist/200.;//max(abs(sdist) / 5000, 0.02); //spot *= clamp(1. - sdist, 0, 1); vds = ds * bn.xyz; vds2 = ds * bn2.xyz; float shadow = getShadow(index, pos.xyz, vec3(0)) * 3.; shadow += getShadow(index, pos.xyz, vds ) * 2.; shadow += getShadow(index, pos.xyz, - vds ) * 2.; shadow += getShadow(index, pos.xyz, - vds2 ) * 2.; shadow += getShadow(index, pos.xyz, + vds2 ) * 2.; //shadow += getShadow(index, pos.xyz, vds - vds2 ) * 1.5; //shadow += getShadow(index, pos.xyz, vds + vds2 ) * 1.5; //shadow += getShadow(index, pos.xyz, - vds - vds2 ) * 1.5; //shadow += getShadow(index, pos.xyz, - vds + vds2 ) * 1.5; //shadow += getShadow(index, pos.xyz, vds + vds ); //shadow += getShadow(index, pos.xyz, - vds - vds ); //shadow += getShadow(index, pos.xyz, - vds2 - vds2); //shadow += getShadow(index, pos.xyz, + vds2 + vds2); //shadow += getShadow(index, pos.xyz, vds + vds - vds2 ); //shadow += getShadow(index, pos.xyz, - vds - vds - vds2 ); //shadow += getShadow(index, pos.xyz, vds + vds + vds2 ); //shadow += getShadow(index, pos.xyz, - vds - vds + vds2 ); //shadow += getShadow(index, pos.xyz, vds - vds2 - vds2); //shadow += getShadow(index, pos.xyz, vds + vds2 + vds2); //shadow += getShadow(index, pos.xyz, - vds - vds2 - vds2); //shadow += getShadow(index, pos.xyz, - vds + vds2 + vds2); //shadow += shadow += getShadow(index, pos.xyz, vds+vds2)*10; spot *= mix(1., shadow / 11., shadow_on);*/ #endif spot /= (qgl_light_parameter[index].constantAttenuation + ldist * (qgl_light_parameter[index].linearAttenuation + ldist * qgl_light_parameter[index].quadraticAttenuation)); float NdotLs = NdotL*NdotL; float NdotHs = NdotH*NdotH; float ndlc = (1. - NdotLs) / NdotLs; float der = NdotLs * (shm_diff + ndlc); diff = 2. / (1. + sqrt(1. + (1. - shm_diff) * ndlc)); li += spot * diff * qgl_light_parameter[index].color.rgb;// * light_diffuse(0, ldir, n); ndlc = (1. - NdotHs) / NdotHs; der = NdotHs * (shm_spec + ndlc); si += spot * (shm_spec / (der*der) / 3.1416) * qgl_light_parameter[index].color.rgb; } void main(void) { ivec2 tc = ivec2(gl_FragCoord.xy); vec4 v1 = texelFetch(tex_1, tc, 0); float z = v1.w; if (z == 1.) { qgl_FragColor = vec4(0); return; } vec4 v0 = texelFetch(tex_0, tc, 0), v2 = texelFetch(tex_2, tc, 0), v3 = texelFetch(tex_3, tc, 0), v4 = texelFetch(tex_4, tc, 0); pos.w = 1; pos.xyz = view_dir * z; vec3 v = normalize(-pos.xyz); vec3 diffuse = v0.rgb; vec3 normal = v1.xyz; vec3 specular = v2.rgb; vec3 emission = v3.rgb; float reflectivity = v0.w; float height = v2.w; float roughness = v3.w; //bn = normalize(vec3(v3.w, v4.zw)); //bn2 = normalize(cross(n, bn)); shm_diff = max(roughness, 0.00001); roughness = roughness*roughness*roughness; shm_spec = max(roughness, 0.00001); //sh_pow = 1. / max(roughness, 0.00001); li = vec3(0.);//qgl_AmbientLight.color.rgb * qgl_AmbientLight.intensity; si = vec3(0.); for (int i = 0; i < lights_count; ++i) calcLight(lights_start + i, normal, v); qgl_FragColor = vec4(max(vec3(0), li * diffuse + si * specular + emission), 1); //qgl_FragColor.rgb = vec3(pos.xyz/100); }