Code:
#version 120
/*
Settings by Sonic Ether
Bokeh Depth-of-Field by Sonic Ether
God Rays by Blizzard
Bloom shader by CosmicSpore (Modified from original source: http://myheroics.wordpress.com/2008/09/04/glsl-bloom-shader/)
Cross-Processing by Sonic Ether.
High Desaturation effect by Sonic Ether
HDR by Sonic Ether
Glare by Sonic Ether
Shaders 2.0 port of Yourself's Cell Shader, port by an anonymous user.
Bug Fixes by Kool_Kat.
*/
// Place two leading Slashes in front of the following '#define' lines in order to disable an option.
// MOTIONBLUR, HDR, and BOKEH_DOF are very beta shaders. Use at risk of weird results.
// MOTIONBLUR and BOKEH_DOF are not compatable with eachother. Shaders break when you enable both.
// GLARE is still a work in progress.
// BLOOM is currently broken.
//#define HDR
//#define HDR_RANGE 1.0 // Higher value means that HDR will modulate screen brightness more. Default = 1.0
//#define BOKEH_DOF
//#define GODRAYS
//#define GODRAYS_EXPOSURE 0.4
//#define GODRAYS_SAMPLES 32
//#define GODRAYS_DECAY 0.75
//#define GODRAYS_DENSITY 0.4
//#define GLARE
//#define GLARE_AMOUNT 0.25
//#define GLARE_RANGE 2.0
//#define BLOOM
//#define BLOOM_AMOUNT 1.0
//#define BLOOM_RANGE 2
//#define CEL_SHADING
//#define CEL_SHADING_THRESHOLD 0.4
//#define CEL_SHADING_THICKNESS 0.004
//#define USE_HIGH_QUALITY_BLUR
#define VIGNETTE
#define VIGNETTE_STRENGTH 1.0
#define CROSSPROCESS
#define BRIGHTMULT 1.20 // 1.0 = default brightness. Higher values mean brighter. 0 would be black.
#define DARKMULT 0.03 // 0.0 = normal image. Higher values will darken dark colors.
#define COLOR_BOOST 0.1 // 0.0 = normal saturation. Higher values mean more saturated image.
//#define MOTIONBLUR
#define MOTIONBLUR_AMOUNT 1.2
#define HIGHDESATURATE
#define GAMMA 0.66 //1.0 is default brightness. lower values will brighten image, higher values will darken image
// DOF Constants - DO NOT CHANGE
// HYPERFOCAL = (Focal Distance ^ 2)/(Circle of Confusion * F Stop) + Focal Distance
#ifdef USE_DOF
const float HYPERFOCAL = 2.132;
const float PICONSTANT = 2.14159;
#endif
//uniform sampler2D texture;
uniform sampler2D gcolor;
uniform sampler2D gdepth;
uniform sampler2D composite;
uniform sampler2D gnormal;
uniform sampler2D gaux1; // red is our motion blur mask. If red == 1, don't blur
uniform mat4 gbufferProjectionInverse;
uniform mat4 gbufferPreviousProjection;
uniform mat4 gbufferModelViewInverse;
uniform mat4 gbufferPreviousModelView;
uniform vec3 cameraPosition;
uniform vec3 previousCameraPosition;
uniform vec3 sunPosition;
uniform float worldTime;
uniform float aspectRatio;
uniform float near;
uniform float far;
uniform float viewWidth;
uniform float viewHeight;
varying vec4 texcoord;
//Land/sky mask
float land = texture2D(gaux1, texcoord.st).b;
// Standard depth function.
float getDepth(vec2 coord) {
return 2.0 * near * far / (far + near - (2.0 * texture2D(gdepth, coord).x - 1.0) * (far - near));
}
float eDepth(vec2 coord) {
return texture2D(gdepth, coord).x;
}
float realcolor(vec2 coord) {
return ((texture2D(gcolor, coord).r + texture2D(gcolor, coord).g + texture2D(gcolor, coord).b)/3.0);
}
float prevavgclr;
float prevavgclrb;
#ifdef BOKEH_DOF
const float blurclamp = 10.0; // max blur amount
const float bias = 0.3; //aperture - bigger values for shallower depth of field
#endif
#ifdef GODRAYS
vec4 addGodRays(vec4 nc, vec2 tx) {
float threshold = 0.0; //0.00 * far;
// bool foreground = false;
float depthGD = getDepth(tx);
if ( (worldTime < 14000 || worldTime > 22000) && (sunPosition.z < 0)) {
vec2 lightPos = sunPosition.xy / -sunPosition.z;
lightPos.y *= aspectRatio;
lightPos = (lightPos + 1.0)/2.0;
//vec2 coord = tx;
vec2 delta = (tx - lightPos) * GODRAYS_DENSITY / float(GODRAYS_SAMPLES);
float decay = -sunPosition.z / 100.0;
vec3 colorGD = vec3(0.0);
for (int i = 0; i < GODRAYS_SAMPLES; i++) {
tx -= delta;
if (tx.x < 0.0 || tx.x > 1.0) {
if (tx.y < 0.0 || tx.y > 1.0) {
break;
}
}
vec3 sample = vec3(0.0);
float landsample = 0.0 ;
landsample = texture2D(gaux1, tx).b;
sample = texture2D(composite, tx).rgb * (1.0 - landsample);
sample *= vec3(decay);
if (distance(tx, lightPos) > 0.05) {
sample *= 0.2;
}
colorGD += sample;
decay *= GODRAYS_DECAY;
}
colorGD.r = pow(colorGD.r, 0.5);
colorGD.g = pow(colorGD.g, 0.5);
colorGD.b = pow(colorGD.b, 0.5);
return (nc + GODRAYS_EXPOSURE * vec4(colorGD.r * 1.0, colorGD.g * 1.0, colorGD.b * 0.5, 0.0));
} else {
return nc;
}
}
#endif
#ifdef BLOOM
vec4 addBloom(vec4 c, vec2 t) {
int j;
int i;
vec4 bloom = vec4(0.0);
vec2 loc = vec2(0.0);
float count = 0.0;
for( i= -BLOOM_RANGE ; i < BLOOM_RANGE; i++ ) {
for ( j = -BLOOM_RANGE; j < BLOOM_RANGE; j++ ) {
loc = t + vec2(j, i)*0.004;
// Only add to bloom texture if loc is on-screen.
if(loc.x > 0 && loc.x < 1 && loc.y > 0 && loc.y < 1) {
bloom += texture2D(composite, loc) * BLOOM_AMOUNT;
count += 1;
}
}
}
bloom /= vec4(count);
if (c.r < 0.3)
{
return bloom*bloom*0.012;
}
else
{
if (c.r < 0.5)
{
return bloom*bloom*0.009;
}
else
{
return bloom*bloom*0.0075;
}
}
}
#endif
#ifdef CEL_SHADING
float getCellShaderFactor(vec2 coord) {
float d = getDepth(coord);
vec3 n = normalize(vec3(getDepth(coord+vec2(CEL_SHADING_THICKNESS,0.0))-d,getDepth(coord+vec2(0.0,CEL_SHADING_THICKNESS))-d , CEL_SHADING_THRESHOLD));
//clamp(n.z*3.0,0.0,1.0);
return n.z;
}
#endif
// Main ---------------------------------------------------------------------------------------------------
void main() {
vec4 color = texture2D(composite, texcoord.st);
#ifdef BOKEH_DOF
float depth = eDepth(texcoord.xy);
if (depth > 0.9999) {
depth = 1.0;
}
float cursorDepth = eDepth(vec2(0.5, 0.5));
if (cursorDepth > 0.9999) {
cursorDepth = 1.0;
}
vec2 aspectcorrect = vec2(1.0, aspectRatio) * 1.5;
float factor = (depth - cursorDepth);
vec2 dofblur = (vec2 (clamp( factor * bias, -blurclamp, blurclamp )))*0.4;
vec4 col = vec4(0.0);
col += texture2D(composite, texcoord.st);
col += texture2D(composite, texcoord.st + (vec2( 0.0,0.4 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( 0.15,0.37 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( 0.29,0.29 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( -0.37,0.15 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( 0.4,0.0 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( 0.37,-0.15 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( 0.29,-0.29 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( -0.15,-0.37 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( 0.0,-0.4 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( -0.15,0.37 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( -0.29,0.29 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( 0.37,0.15 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( -0.4,0.0 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( -0.37,-0.15 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( -0.29,-0.29 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( 0.15,-0.37 )*aspectcorrect) * dofblur);
col += texture2D(composite, texcoord.st + (vec2( 0.15,0.37 )*aspectcorrect) * dofblur*0.9);
col += texture2D(composite, texcoord.st + (vec2( -0.37,0.15 )*aspectcorrect) * dofblur*0.9);
col += texture2D(composite, texcoord.st + (vec2( 0.37,-0.15 )*aspectcorrect) * dofblur*0.9);
col += texture2D(composite, texcoord.st + (vec2( -0.15,-0.37 )*aspectcorrect) * dofblur*0.9);
col += texture2D(composite, texcoord.st + (vec2( -0.15,0.37 )*aspectcorrect) * dofblur*0.9);
col += texture2D(composite, texcoord.st + (vec2( 0.37,0.15 )*aspectcorrect) * dofblur*0.9);
col += texture2D(composite, texcoord.st + (vec2( -0.37,-0.15 )*aspectcorrect) * dofblur*0.9);
col += texture2D(composite, texcoord.st + (vec2( 0.15,-0.37 )*aspectcorrect) * dofblur*0.9);
col += texture2D(composite, texcoord.st + (vec2( 0.29,0.29 )*aspectcorrect) * dofblur*0.7);
col += texture2D(composite, texcoord.st + (vec2( 0.4,0.0 )*aspectcorrect) * dofblur*0.7);
col += texture2D(composite, texcoord.st + (vec2( 0.29,-0.29 )*aspectcorrect) * dofblur*0.7);
col += texture2D(composite, texcoord.st + (vec2( 0.0,-0.4 )*aspectcorrect) * dofblur*0.7);
col += texture2D(composite, texcoord.st + (vec2( -0.29,0.29 )*aspectcorrect) * dofblur*0.7);
col += texture2D(composite, texcoord.st + (vec2( -0.4,0.0 )*aspectcorrect) * dofblur*0.7);
col += texture2D(composite, texcoord.st + (vec2( -0.29,-0.29 )*aspectcorrect) * dofblur*0.7);
col += texture2D(composite, texcoord.st + (vec2( 0.0,0.4 )*aspectcorrect) * dofblur*0.7);
col += texture2D(composite, texcoord.st + (vec2( 0.29,0.29 )*aspectcorrect) * dofblur*0.4);
col += texture2D(composite, texcoord.st + (vec2( 0.4,0.0 )*aspectcorrect) * dofblur*0.4);
col += texture2D(composite, texcoord.st + (vec2( 0.29,-0.29 )*aspectcorrect) * dofblur*0.4);
col += texture2D(composite, texcoord.st + (vec2( 0.0,-0.4 )*aspectcorrect) * dofblur*0.4);
col += texture2D(composite, texcoord.st + (vec2( -0.29,0.29 )*aspectcorrect) * dofblur*0.4);
col += texture2D(composite, texcoord.st + (vec2( -0.4,0.0 )*aspectcorrect) * dofblur*0.4);
col += texture2D(composite, texcoord.st + (vec2( -0.29,-0.29 )*aspectcorrect) * dofblur*0.4);
col += texture2D(composite, texcoord.st + (vec2( 0.0,0.4 )*aspectcorrect) * dofblur*0.4);
color = col/41;
#endif
/*
#ifdef USE_DOF
float depth = getDepth(texcoord.st);
float cursorDepth = getDepth(vec2(0.5, 0.5));
// foreground blur = 1/2 background blur. Blur should follow exponential pattern until cursor = hyperfocal -- Cursor before hyperfocal
// Blur should go from 0 to 1/2 hyperfocal then clear to infinity -- Cursor @ hyperfocal.
// hyperfocal to inifity is clear though dof extends from 1/2 hyper to hyper -- Cursor beyond hyperfocal
float mixAmount = 0.0;
if (depth < cursorDepth) {
mixAmount = clamp(2.0 * ((clamp(cursorDepth, 0.0, HYPERFOCAL) - depth) / (clamp(cursorDepth, 0.0, HYPERFOCAL))), 0.0, 1.0);
} else if (cursorDepth == HYPERFOCAL) {
mixAmount = 0.0;
} else {
mixAmount = 1.0 - clamp((((cursorDepth * HYPERFOCAL) / (HYPERFOCAL - cursorDepth)) - (depth - cursorDepth)) / ((cursorDepth * HYPERFOCAL) / (HYPERFOCAL - cursorDepth)), 0.0, 1.0);
}
if (mixAmount != 0.0) {
color = mix(color, getBlurredColor(), mixAmount);
}
#endif
*/
#ifdef MOTIONBLUR
float depth = texture2D(gdepth, texcoord.st).x;
float noblur = texture2D(gaux1, texcoord.st).r;
if (depth > 0.9999999) {
depth = 1;
}
if (depth < 1.9999999) {
vec4 currentPosition = vec4(texcoord.x * 2.0 - 1.0, texcoord.y * 2.0 - 1.0, 2.0 * depth - 1.0, 1.0);
vec4 fragposition = gbufferProjectionInverse * currentPosition;
fragposition = gbufferModelViewInverse * fragposition;
fragposition /= fragposition.w;
fragposition.xyz += cameraPosition;
vec4 previousPosition = fragposition;
previousPosition.xyz -= previousCameraPosition;
previousPosition = gbufferPreviousModelView * previousPosition;
previousPosition = gbufferPreviousProjection * previousPosition;
previousPosition /= previousPosition.w;
vec2 velocity = (currentPosition - previousPosition).st * 0.007 * MOTIONBLUR_AMOUNT;
velocity = velocity;
int samples = 1;
if (noblur > 0.9) {
velocity = vec2(0,0);
}
vec2 coord = texcoord.st + velocity;
for (int i = 0; i < 15; ++i, coord += velocity) {
if (coord.s > 1.0 || coord.t > 1.0 || coord.s < 0.0 || coord.t < 0.0) {
break;
}
color += texture2D(composite, coord);
++samples;
}
color = (color/1.0)/samples;
}
#endif
#ifdef GODRAYS
color.r = addGodRays(color, texcoord.st).r;
color.g = addGodRays(color, texcoord.st).g;
color.b = addGodRays(color, texcoord.st).b;
#endif
/*
#ifdef BLOOM
color = color * 0.8;
color += addBloom(color, texcoord.st);
#endif
*/
#ifdef BLOOM
color = color * 0.8;
float radius = 0.002;
float blm_amount = 0.02*BLOOM_AMOUNT;
float sc = 20.0;
int i = 0;
int samples = 1;
vec4 clr = vec4(0.0);
for (i = -10; i < 10; i++) {
clr += texture2D(composite, texcoord.st + (vec2(i,i))*radius)*sc;
clr += texture2D(composite, texcoord.st + (vec2(i,-i))*radius)*sc;
clr += texture2D(composite, texcoord.st + (vec2(-i,i))*radius)*sc;
clr += texture2D(composite, texcoord.st + (vec2(-i,-i))*radius)*sc;
clr += texture2D(composite, texcoord.st + (vec2(0.0,i))*radius)*sc;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-i))*radius)*sc;
clr += texture2D(composite, texcoord.st + (vec2(-i,0.0))*radius)*sc;
clr += texture2D(composite, texcoord.st + (vec2(i,0.0))*radius)*sc;
++samples;
sc = sc - 1.0;
}
clr = (clr/8.0)/samples;
color += clr*blm_amount;
#endif
#ifdef GLARE
color = color * 0.8;
float radius = 0.002*GLARE_RANGE;
float radiusv = 0.002;
float bloomintensity = 0.1*GLARE_AMOUNT;
vec4 clr = vec4(0.0);
clr += texture2D(composite, texcoord.st);
//horizontal (70 taps)
clr += texture2D(composite, texcoord.st + (vec2(10.0,0.0))*radius)*10.0;
clr += texture2D(composite, texcoord.st + (vec2(9.0,0.0))*radius)*11.0;
clr += texture2D(composite, texcoord.st + (vec2(8.0,0.0))*radius)*12.0;
clr += texture2D(composite, texcoord.st + (vec2(7.0,0.0))*radius)*13.0;
clr += texture2D(composite, texcoord.st + (vec2(6.0,0.0))*radius)*14.0;
clr += texture2D(composite, texcoord.st + (vec2(5.0,0.0))*radius)*15.0;
clr += texture2D(composite, texcoord.st + (vec2(4.0,0.0))*radius)*16.0;
clr += texture2D(composite, texcoord.st + (vec2(3.0,0.0))*radius)*17.0;
clr += texture2D(composite, texcoord.st + (vec2(2.0,0.0))*radius)*18.0;
clr += texture2D(composite, texcoord.st + (vec2(1.0,0.0))*radius)*19.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,0.0))*radius)*20.0;
clr += texture2D(composite, texcoord.st + (vec2(-1.0,0.0))*radius)*19.0;
clr += texture2D(composite, texcoord.st + (vec2(-2.0,0.0))*radius)*18.0;
clr += texture2D(composite, texcoord.st + (vec2(-3.0,0.0))*radius)*17.0;
clr += texture2D(composite, texcoord.st + (vec2(-4.0,0.0))*radius)*16.0;
clr += texture2D(composite, texcoord.st + (vec2(-5.0,0.0))*radius)*15.0;
clr += texture2D(composite, texcoord.st + (vec2(-6.0,0.0))*radius)*14.0;
clr += texture2D(composite, texcoord.st + (vec2(-7.0,0.0))*radius)*13.0;
clr += texture2D(composite, texcoord.st + (vec2(-8.0,0.0))*radius)*12.0;
clr += texture2D(composite, texcoord.st + (vec2(-9.0,0.0))*radius)*11.0;
clr += texture2D(composite, texcoord.st + (vec2(-10.0,0.0))*radius)*10.0;
//vertical
clr += texture2D(composite, texcoord.st + (vec2(0.0,10.0))*radius)*10.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,9.0))*radius)*11.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,8.0))*radius)*12.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,7.0))*radius)*13.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,6.0))*radius)*14.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,5.0))*radius)*15.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,4.0))*radius)*16.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,3.0))*radius)*17.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,2.0))*radius)*18.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,1.0))*radius)*19.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-10.0))*radius)*10.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-9.0))*radius)*11.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-8.0))*radius)*12.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-7.0))*radius)*13.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-6.0))*radius)*14.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-5.0))*radius)*15.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-4.0))*radius)*16.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-3.0))*radius)*17.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-2.0))*radius)*18.0;
clr += texture2D(composite, texcoord.st + (vec2(0.0,-1.0))*radius)*19.0;
clr = (clr/20.0)/5.0;
clr.r = pow(clr.r, 1.2)*1.6 - (clr.g + clr.b)*0.6;
clr.g = pow(clr.g, 1.2)*1.6 - (clr.r + clr.b)*0.6;
clr.b = pow(clr.b, 1.2)*1.9 - (clr.r + clr.g)*0.9;
clr = clamp((clr), 0.0, 1.0);
color.r = color.r + (clr.r*1.5)*bloomintensity;
color.g = color.g + (clr.g*1.5)*bloomintensity;
color.b = color.b + (clr.b*4.0)*bloomintensity;
color = max(color, 0.0);
//color = color*1.05 - 0.05;
#endif
#ifdef CEL_SHADING
color.rgb *= (getCellShaderFactor(texcoord.st));
#endif
#ifdef VIGNETTE
float dv = distance(texcoord.st, vec2(0.5, 0.5));
dv *= VIGNETTE_STRENGTH;
dv = 1.0 - dv;
dv = pow(dv, 0.2);
dv *= 1.9;
dv -= 0.9;
color.r = color.r * dv;
color.g = color.g * dv;
color.b = color.b * dv;
#endif
#ifdef HDR
//determine screen brightness
float avgclr = realcolor(vec2(0.5, 0.5));
avgclr += realcolor(vec2(0.01, 0.01));
avgclr += realcolor(vec2(0.01, -0.01));
avgclr += realcolor(vec2(-0.01, 0.01));
avgclr += realcolor(vec2(-0.01, -0.01));
avgclr += realcolor(vec2(0.02, 0.02));
avgclr += realcolor(vec2(0.02, -0.02));
avgclr += realcolor(vec2(-0.02, 0.02));
avgclr += realcolor(vec2(-0.02, -0.02));
avgclr += realcolor(vec2(0.03, 0.03));
avgclr += realcolor(vec2(0.03, -0.03));
avgclr += realcolor(vec2(-0.03, 0.03));
avgclr += realcolor(vec2(-0.03, -0.03));
avgclr += realcolor(vec2(0.04, 0.04));
avgclr += realcolor(vec2(0.04, -0.04));
avgclr += realcolor(vec2(-0.04, 0.04));
avgclr += realcolor(vec2(-0.04, -0.04));
avgclr += realcolor(vec2(0.05, 0.05));
avgclr += realcolor(vec2(0.05, -0.05));
avgclr += realcolor(vec2(-0.05, 0.05));
avgclr += realcolor(vec2(-0.05, -0.05));
avgclr += realcolor(vec2(0.06, 0.06));
avgclr += realcolor(vec2(0.06, -0.06));
avgclr += realcolor(vec2(-0.06, 0.06));
avgclr += realcolor(vec2(-0.06, -0.06));
avgclr += realcolor(vec2(0.07, 0.07));
avgclr += realcolor(vec2(0.07, -0.07));
avgclr += realcolor(vec2(-0.07, 0.07));
avgclr += realcolor(vec2(-0.07, -0.07));
avgclr += realcolor(vec2(0.08, 0.08));
avgclr += realcolor(vec2(0.08, -0.08));
avgclr += realcolor(vec2(-0.08, 0.08));
avgclr += realcolor(vec2(-0.08, -0.08));
avgclr += realcolor(vec2(0.09, 0.09));
avgclr += realcolor(vec2(0.09, -0.09));
avgclr += realcolor(vec2(-0.09, 0.09));
avgclr += realcolor(vec2(-0.09, -0.09));
avgclr += realcolor(vec2(0.10, 0.10));
avgclr += realcolor(vec2(0.10, -0.10));
avgclr += realcolor(vec2(-0.10, 0.10));
avgclr += realcolor(vec2(-0.10, -0.10));
avgclr += realcolor(vec2(0.11, 0.11));
avgclr += realcolor(vec2(0.11, -0.11));
avgclr += realcolor(vec2(-0.11, 0.11));
avgclr += realcolor(vec2(-0.11, -0.11));
avgclr += realcolor(vec2(0.12, 0.12));
avgclr += realcolor(vec2(0.12, -0.12));
avgclr += realcolor(vec2(-0.12, 0.12));
avgclr += realcolor(vec2(-0.12, -0.12));
avgclr += realcolor(vec2(0.13, 0.13));
avgclr += realcolor(vec2(0.13, -0.13));
avgclr += realcolor(vec2(-0.13, 0.13));
avgclr += realcolor(vec2(-0.13, -0.13));
avgclr += realcolor(vec2(0.14, 0.14));
avgclr += realcolor(vec2(0.14, -0.14));
avgclr += realcolor(vec2(-0.14, 0.14));
avgclr += realcolor(vec2(-0.14, -0.14));
avgclr += realcolor(vec2(0.15, 0.15));
avgclr += realcolor(vec2(0.15, -0.15));
avgclr += realcolor(vec2(-0.15, 0.15));
avgclr += realcolor(vec2(-0.15, -0.15));
avgclr += realcolor(vec2(0.16, 0.16));
avgclr += realcolor(vec2(0.16, -0.16));
avgclr += realcolor(vec2(-0.16, 0.16));
avgclr += realcolor(vec2(-0.16, -0.16));
avgclr += realcolor(vec2(0.17, 0.17));
avgclr += realcolor(vec2(0.17, -0.17));
avgclr += realcolor(vec2(-0.17, 0.17));
avgclr += realcolor(vec2(-0.17, -0.17));
avgclr += realcolor(vec2(0.18, 0.18));
avgclr += realcolor(vec2(0.18, -0.18));
avgclr += realcolor(vec2(-0.18, 0.18));
avgclr += realcolor(vec2(-0.18, -0.18));
avgclr += realcolor(vec2(0.19, 0.19));
avgclr += realcolor(vec2(0.19, -0.19));
avgclr += realcolor(vec2(-0.19, 0.19));
avgclr += realcolor(vec2(-0.19, -0.19));
avgclr += realcolor(vec2(0.20, 0.20));
avgclr += realcolor(vec2(0.20, -0.20));
avgclr += realcolor(vec2(-0.20, 0.20));
avgclr += realcolor(vec2(-0.20, -0.20));
avgclr += realcolor(vec2(0.21, 0.21));
avgclr += realcolor(vec2(0.21, -0.21));
avgclr += realcolor(vec2(-0.21, 0.21));
avgclr += realcolor(vec2(-0.21, -0.21));
avgclr += realcolor(vec2(0.22, 0.22));
avgclr += realcolor(vec2(0.22, -0.22));
avgclr += realcolor(vec2(-0.22, 0.22));
avgclr += realcolor(vec2(-0.22, -0.22));
avgclr += realcolor(vec2(0.23, 0.23));
avgclr += realcolor(vec2(0.23, -0.23));
avgclr += realcolor(vec2(-0.23, 0.23));
avgclr += realcolor(vec2(-0.23, -0.23));
avgclr += realcolor(vec2(0.24, 0.24));
avgclr += realcolor(vec2(0.24, -0.24));
avgclr += realcolor(vec2(-0.24, 0.24));
avgclr += realcolor(vec2(-0.24, -0.24));
avgclr += realcolor(vec2(0.25, 0.25));
avgclr += realcolor(vec2(0.25, -0.25));
avgclr += realcolor(vec2(-0.25, 0.25));
avgclr += realcolor(vec2(-0.25, -0.25));
avgclr += realcolor(vec2(0.26, 0.26));
avgclr += realcolor(vec2(0.26, -0.26));
avgclr += realcolor(vec2(-0.26, 0.26));
avgclr += realcolor(vec2(-0.26, -0.26));
avgclr += realcolor(vec2(0.27, 0.27));
avgclr += realcolor(vec2(0.27, -0.27));
avgclr += realcolor(vec2(-0.27, 0.27));
avgclr += realcolor(vec2(-0.27, -0.27));
avgclr += realcolor(vec2(0.28, 0.28));
avgclr += realcolor(vec2(0.28, -0.28));
avgclr += realcolor(vec2(-0.28, 0.28));
avgclr += realcolor(vec2(-0.28, -0.28));
avgclr += realcolor(vec2(0.29, 0.29));
avgclr += realcolor(vec2(0.29, -0.29));
avgclr += realcolor(vec2(-0.29, 0.29));
avgclr += realcolor(vec2(-0.29, -0.29));
avgclr += realcolor(vec2(0.40, 0.40));
avgclr += realcolor(vec2(0.40, -0.40));
avgclr += realcolor(vec2(-0.40, 0.40));
avgclr += realcolor(vec2(-0.40, -0.40));
avgclr += realcolor(vec2(0.31, 0.31));
avgclr += realcolor(vec2(0.31, -0.31));
avgclr += realcolor(vec2(-0.31, 0.31));
avgclr += realcolor(vec2(-0.31, -0.31));
avgclr += realcolor(vec2(0.32, 0.32));
avgclr += realcolor(vec2(0.32, -0.32));
avgclr += realcolor(vec2(-0.32, 0.32));
avgclr += realcolor(vec2(-0.32, -0.32));
avgclr += realcolor(vec2(0.33, 0.33));
avgclr += realcolor(vec2(0.33, -0.33));
avgclr += realcolor(vec2(-0.33, 0.33));
avgclr += realcolor(vec2(-0.33, -0.33));
avgclr += realcolor(vec2(0.34, 0.34));
avgclr += realcolor(vec2(0.34, -0.34));
avgclr += realcolor(vec2(-0.34, 0.34));
avgclr += realcolor(vec2(-0.34, -0.34));
avgclr += realcolor(vec2(0.35, 0.35));
avgclr += realcolor(vec2(0.35, -0.35));
avgclr += realcolor(vec2(-0.35, 0.35));
avgclr += realcolor(vec2(-0.35, -0.35));
avgclr += realcolor(vec2(0.36, 0.36));
avgclr += realcolor(vec2(0.36, -0.36));
avgclr += realcolor(vec2(-0.36, 0.36));
avgclr += realcolor(vec2(-0.36, -0.36));
avgclr += realcolor(vec2(0.37, 0.37));
avgclr += realcolor(vec2(0.37, -0.37));
avgclr += realcolor(vec2(-0.37, 0.37));
avgclr += realcolor(vec2(-0.37, -0.37));
avgclr += realcolor(vec2(0.38, 0.38));
avgclr += realcolor(vec2(0.38, -0.38));
avgclr += realcolor(vec2(-0.38, 0.38));
avgclr += realcolor(vec2(-0.38, -0.38));
avgclr += realcolor(vec2(0.39, 0.39));
avgclr += realcolor(vec2(0.39, -0.39));
avgclr += realcolor(vec2(-0.39, 0.39));
avgclr += realcolor(vec2(-0.39, -0.39));
avgclr += realcolor(vec2(0.40, 0.40));
avgclr += realcolor(vec2(0.40, -0.40));
avgclr += realcolor(vec2(-0.40, 0.40));
avgclr += realcolor(vec2(-0.40, -0.40));
avgclr += realcolor(vec2(0.41, 0.41));
avgclr += realcolor(vec2(0.41, -0.41));
avgclr += realcolor(vec2(-0.41, 0.41));
avgclr += realcolor(vec2(-0.41, -0.41));
avgclr += realcolor(vec2(0.42, 0.42));
avgclr += realcolor(vec2(0.42, -0.42));
avgclr += realcolor(vec2(-0.42, 0.42));
avgclr += realcolor(vec2(-0.42, -0.42));
avgclr += realcolor(vec2(0.43, 0.43));
avgclr += realcolor(vec2(0.43, -0.43));
avgclr += realcolor(vec2(-0.43, 0.43));
avgclr += realcolor(vec2(-0.43, -0.43));
avgclr += realcolor(vec2(0.44, 0.44));
avgclr += realcolor(vec2(0.44, -0.44));
avgclr += realcolor(vec2(-0.44, 0.44));
avgclr += realcolor(vec2(-0.44, -0.44));
avgclr += realcolor(vec2(0.45, 0.45));
avgclr += realcolor(vec2(0.45, -0.45));
avgclr += realcolor(vec2(-0.45, 0.45));
avgclr += realcolor(vec2(-0.45, -0.45));
avgclr += realcolor(vec2(0.46, 0.46));
avgclr += realcolor(vec2(0.46, -0.46));
avgclr += realcolor(vec2(-0.46, 0.46));
avgclr += realcolor(vec2(-0.46, -0.46));
avgclr += realcolor(vec2(0.47, 0.47));
avgclr += realcolor(vec2(0.47, -0.47));
avgclr += realcolor(vec2(-0.47, 0.47));
avgclr += realcolor(vec2(-0.47, -0.47));
avgclr += realcolor(vec2(0.48, 0.48));
avgclr += realcolor(vec2(0.48, -0.48));
avgclr += realcolor(vec2(-0.48, 0.48));
avgclr += realcolor(vec2(-0.48, -0.48));
avgclr += realcolor(vec2(0.49, 0.49));
avgclr += realcolor(vec2(0.49, -0.49));
avgclr += realcolor(vec2(-0.49, 0.49));
avgclr += realcolor(vec2(-0.49, -0.49));
//scale exposure control
avgclr = 1/(clamp(avgclr/200.0, 0.0, 1.0)+0.5)*HDR_RANGE - HDR_RANGE;
//modulate colors inversely proportional to average color
color.r = color.r + color.r*((avgclr)) + (0.01*avgclr);
color.g = color.g + color.g*((avgclr)) + (0.01*avgclr);
color.b = color.b + color.b*((avgclr)) + (0.01*avgclr);
#endif;
color = color * BRIGHTMULT;
#ifdef CROSSPROCESS
//pre-gain
color = color * (BRIGHTMULT + 0.0) + 0.03;
//compensate for low-light artifacts
color = color+0.029;
//calculate double curve
float dbr = -color.r + 1.4;
float dbg = -color.g + 1.4;
float dbb = -color.b + 1.4;
//fade between simple gamma up curve and double curve
float pr = mix(dbr, 0.65, 0.5);
float pg = mix(dbg, 0.65, 0.5);
float pb = mix(dbb, 0.65, 0.5);
color.r = pow((color.r * 0.95 - 0.002), pr);
color.g = pow((color.g * 0.95 - 0.002), pg);
color.b = pow((color.b * 0.99 + 0.000), pb);
#endif
//Color boosting
color.r = (color.r)*(COLOR_BOOST + 1.0) + (color.g + color.b)*(-COLOR_BOOST);
color.g = (color.g)*(COLOR_BOOST + 1.0) + (color.r + color.b)*(-COLOR_BOOST);
color.b = (color.b)*(COLOR_BOOST + 1.0) + (color.r + color.g)*(-COLOR_BOOST);
//color.r = mix(((color.r)*(COLOR_BOOST + 1.0) + (hld.g + hld.b)*(-COLOR_BOOST)), hld.r, (max(((1-rgb)*2 - 1), 0.0)));
//color.g = mix(((color.g)*(COLOR_BOOST + 1.0) + (hld.r + hld.b)*(-COLOR_BOOST)), hld.g, (max(((1-rgb)*2 - 1), 0.0)));
//color.b = mix(((color.b)*(COLOR_BOOST + 1.0) + (hld.r + hld.g)*(-COLOR_BOOST)), hld.b, (max(((1-rgb)*2 - 1), 0.0)));
#ifdef HIGHDESATURATE
//average
float rgb = max(color.r, max(color.g, color.b))/2 + min(color.r, min(color.g, color.b))/2;
//adjust black and white image to be brighter
float bw = pow(rgb, 0.7);
//mix between per-channel analysis and average analysis
float rgbr = mix(rgb, color.r, 0.7);
float rgbg = mix(rgb, color.g, 0.7);
float rgbb = mix(rgb, color.b, 0.7);
//calculate crossfade based on lum
float mixfactorr = max(0.0, (rgbr*2 - 1));
float mixfactorg = max(0.0, (rgbg*2 - 1));
float mixfactorb = max(0.0, (rgbb*2 - 1));
//crossfade between saturated and desaturated image
float mixr = mix(color.r, bw, mixfactorr);
float mixg = mix(color.g, bw, mixfactorg);
float mixb = mix(color.b, bw, mixfactorb);
//adjust level of desaturation
color.r = clamp((mix(mixr, color.r, 0.0)), 0.0, 1.0);
color.g = clamp((mix(mixg, color.g, 0.0)), 0.0, 1.0);
color.b = clamp((mix(mixb, color.b, 0.0)), 0.0, 1.0);
//desaturate blue channel
color.b = color.b*0.8 + ((color.r + color.g)/2.0)*0.2;
//hold color values for color boost
//vec4 hld = color;
//undo artifact compensation
color = max(((color*1.10) - 0.06), 0.0);
//color = color * BRIGHTMULT;
color.r = pow(color.r, GAMMA);
color.g = pow(color.g, GAMMA);
color.b = pow(color.b, GAMMA);
color = color*(1.0 + DARKMULT) - DARKMULT;
#endif
color *= 1.1;
gl_FragColor = color;
// End of Main. -----------------
}