#version 330 core

in vec2 TexCoord;
flat in int TexIndex;
out vec4 FragColor;

uniform sampler2D Texture0;
uniform sampler2D Texture1;
uniform sampler2D Texture2;
uniform sampler2D Texture3;
uniform sampler2D Texture4;
uniform sampler2D Texture5;
uniform sampler2D Texture6;
uniform sampler2D Texture7;
uniform sampler2D Texture8;
uniform sampler2D Texture9;
uniform sampler2D Texture10;
uniform sampler2D Texture11;
uniform sampler2D Texture12;
uniform sampler2D Texture13;
uniform sampler2D Texture14;
uniform sampler2D Texture15;

uniform float u_time;
uniform float u_battery;
uniform vec2 u_resolution;
uniform float u_hit_timer;
uniform int	u_enabled;

float rand(vec2 co) {
    return fract(sin(dot(co.xy, vec2(12.9898,78.233))) * 43758.5453);
}

float hash(vec2 p) {
    p = fract(p * vec2(123.34, 456.21));
    p += dot(p, p + 45.32);
    return fract(p.x * p.y);
}

void main()
{
    vec4 texColor;
	vec4 noiseColor;

    switch (TexIndex) {
        case 0: texColor = texture(Texture0, TexCoord); break;
        case 1: texColor = texture(Texture1, TexCoord); break;
        case 2: texColor = texture(Texture2, TexCoord); break;
        case 3: texColor = texture(Texture3, TexCoord); break;
        case 4: texColor = texture(Texture4, TexCoord); break;
        case 5: texColor = texture(Texture5, TexCoord); break;
        case 6: texColor = texture(Texture6, TexCoord); break;
        case 7: texColor = texture(Texture7, TexCoord); break;
        case 8: texColor = texture(Texture8, TexCoord); break;
        case 9: texColor = texture(Texture9, TexCoord); break;
        case 10: texColor = texture(Texture10, TexCoord); break;
        case 11: texColor = texture(Texture11, TexCoord); break;
        case 12: texColor = texture(Texture12, TexCoord); break;
        case 13: texColor = texture(Texture13, TexCoord); break;
        case 14: texColor = texture(Texture14, TexCoord); break;
        case 15: texColor = texture(Texture15, TexCoord); break;
        default: texColor = vec4(1.0, 0.0, 0.0, 1.0); break;
    }
	if (u_enabled == 0) {
		FragColor = texColor;
		return;
	}
	if (TexIndex == 1) {
		vec2 uv = gl_FragCoord.xy / u_resolution.xy;
		uv.x *= u_resolution.x / u_resolution.y;
		float blockSize = 6.0;
		float strength =  1.0 - u_battery;

		vec2 blockUV = floor(gl_FragCoord.xy / blockSize);
		float noise = hash(blockUV + vec2(u_time * 3.0, u_time * 7.0));
		float noise2 = hash(blockUV + vec2(u_time * 13.0, u_time * 3.0));
		float noise3 = hash(blockUV + vec2(u_time * 17.0, u_time * 13.0));

		// Horizontal bands
		noise *= 0.9 + 0.1 * sin(uv.y * 400.0);
		noise2 *= 0.9 + 0.1 * sin(uv.y * 400.0);
		noise3 *= 0.9 + 0.1 * sin(uv.y * 400.0);

		float offset = 0.001 / (u_battery * u_battery + 0.001 );
		offset = offset > .05 ? .05 : offset;
		float r = texture(Texture1, TexCoord + vec2(offset * 5, 0.0)).r;
		float g = texture(Texture1, TexCoord + vec2(0.0, offset * 2.0)).g;
		float b = texture(Texture1, TexCoord - vec2(offset, 0.0)).b;
		vec3 color = vec3(r, g, b);

		vec3 noisyColor = mix(color.rgb, vec3(noise, noise2, noise3), (strength / 2 + .2));
		// float flicker = 0.75 + sin(u_time * 6.0 + sin(u_time * 3)) * 0.25;
		float flicker = (1 - strength * 0.5) + 0.25 * (strength * sin(u_time + sin(u_time * 7.0) + 1));

		float dim = u_battery < 0.1 ? u_battery * 10.0 : 1;
		noiseColor = vec4(noisyColor, texColor.a * flicker * dim);
		if (u_hit_timer > 0.0) {
			vec2 uv = gl_FragCoord.xy / u_resolution.xy;
			uv *=  1.0 - uv.yx;
			float vig = uv.x*uv.y * 15.0;
			vig = pow(vig, 0.25);
			float inv_hit = 1.0 - u_hit_timer;
			noiseColor *= vec4(vig) * vec4(1.0, inv_hit, inv_hit, 1.0); 
		} 
		FragColor = noiseColor;
	} else {
		FragColor = texColor;
	}
}

