[Scummvm-git-logs] scummvm-shaders master -> a027ce1c6ca2707165674ab67b5ea53493238906

lotharsm noreply at scummvm.org
Sat Jan 7 23:35:30 UTC 2023


This automated email contains information about 1 new commit which have been
pushed to the 'scummvm-shaders' repo located at https://github.com/scummvm/scummvm-shaders .

Summary:
a027ce1c6c SHADERS: Add more related sharpening and denoising filters


Commit: a027ce1c6ca2707165674ab67b5ea53493238906
    https://github.com/scummvm/scummvm-shaders/commit/a027ce1c6ca2707165674ab67b5ea53493238906
Author: Lothar Serra Mari (mail at serra.me)
Date: 2023-01-08T00:35:24+01:00

Commit Message:
SHADERS: Add more related sharpening and denoising filters

Changed paths:
  A base/ddt/ddt.glslp
  A base/ddt/shaders/ddt.glsl
  A base/denoisers/crt-fast-bilateral-super-xbr.glslp
  A base/denoisers/fast-bilateral-super-xbr-4p.glslp
  A base/denoisers/fast-bilateral-super-xbr-6p.glslp
  A base/denoisers/fast-bilateral-super-xbr.glslp
  A base/denoisers/fast-bilateral.glslp
  A base/denoisers/shaders/fast-bilateral-3d.glsl
  A base/denoisers/shaders/fast-bilateral.glsl
  A base/denoisers/shaders/median_3x3.glsl
  A base/denoisers/shaders/median_5x5.glsl
  A base/denoisers/shaders/slow-bilateral.glsl
  A base/denoisers/slow-bilateral.glslp
  A base/dithering/bayer-matrix-dithering.glslp
  A base/dithering/cbod_v1.glslp
  A base/dithering/gdapt.glslp
  A base/dithering/gendither.glslp
  A base/dithering/mdapt.glslp
  A base/dithering/sgenpt-mix.glslp
  A base/dithering/shaders/bayer-matrix-dithering.glsl
  A base/dithering/shaders/cbod-v1/cbod-v1-pass1.glsl
  A base/dithering/shaders/cbod-v1/cbod-v1-pass2.glsl
  A base/dithering/shaders/gdapt/gdapt-pass0.glsl
  A base/dithering/shaders/gdapt/gdapt-pass1.glsl
  A base/dithering/shaders/gendither.glsl
  A base/dithering/shaders/jinc2-dedither.glsl
  A base/dithering/shaders/mdapt/passes/mdapt-pass0.glsl
  A base/dithering/shaders/mdapt/passes/mdapt-pass1.glsl
  A base/dithering/shaders/mdapt/passes/mdapt-pass2.glsl
  A base/dithering/shaders/mdapt/passes/mdapt-pass3.glsl
  A base/dithering/shaders/mdapt/passes/mdapt-pass4.glsl
  A base/dithering/shaders/sgenpt-mix.glsl
  A base/windowed/jinc2-params.glslp
  A base/windowed/jinc2-sharp.glslp
  A base/windowed/jinc2-sharper.glslp
  A base/windowed/jinc2.glslp
  A base/windowed/lanczos2-sharp.glslp
  A base/windowed/shaders/jinc2-params.glsl
  A base/windowed/shaders/jinc2-sharp.glsl
  A base/windowed/shaders/jinc2-sharper.glsl
  A base/windowed/shaders/jinc2.glsl
  A base/windowed/shaders/lanczos2-sharp.glsl


diff --git a/base/ddt/ddt.glslp b/base/ddt/ddt.glslp
new file mode 100644
index 0000000..5d1e983
--- /dev/null
+++ b/base/ddt/ddt.glslp
@@ -0,0 +1,4 @@
+shaders = 1
+
+shader0 = shaders/ddt.glsl
+filter_linear0 = false
diff --git a/base/ddt/shaders/ddt.glsl b/base/ddt/shaders/ddt.glsl
new file mode 100644
index 0000000..dcfbe71
--- /dev/null
+++ b/base/ddt/shaders/ddt.glsl
@@ -0,0 +1,198 @@
+#version 120
+
+/*
+   Hyllian's DDT Shader
+   
+   Copyright (C) 2011-2016 Hyllian/Jararaca - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+*/
+
+#define saturate(c) clamp(c, 0.0, 1.0)
+#define lerp(a,b,c) mix(a,b,c)
+#define mul(a,b) (b*a)
+#define fmod(c,d) mod(c,d)
+#define frac(c) fract(c)
+#define tex2D(c,d) COMPAT_TEXTURE(c,d)
+#define float2 vec2
+#define float3 vec3
+#define float4 vec4
+#define int2 ivec2
+#define int3 ivec3
+#define int4 ivec4
+#define bool2 bvec2
+#define bool3 bvec3
+#define bool4 bvec4
+#define float2x2 mat2x2
+#define float3x3 mat3x3
+#define float4x4 mat4x4
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying 
+#define COMPAT_ATTRIBUTE attribute 
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+COMPAT_VARYING vec4 t1;
+COMPAT_VARYING vec2 loc;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    COL0 = COLOR;
+    TEX0.xy = TexCoord.xy * 1.000001;
+   
+   float2 ps = float2(SourceSize.z, SourceSize.w);
+	float dx = ps.x;
+	float dy = ps.y;
+
+	t1.xy = float2( dx,  0.); // F
+	t1.zw = float2(  0., dy); // H
+	loc = vTexCoord*SourceSize.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+COMPAT_VARYING vec4 t1;
+COMPAT_VARYING vec2 loc;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+#define decal Source
+
+const COMPAT_PRECISION float3 Y = float3(.2126, .7152, .0722);
+
+float luma(float3 color)
+{
+	return dot(color, Y);
+}
+
+COMPAT_PRECISION float3 bilinear(float p, float q, float3 A, float3 B, float3 C, float3 D)
+{
+	return ((1.-p)*(1.-q)*A + p*(1.-q)*B + (1.-p)*q*C + p*q*D);
+}
+
+void main()
+{
+	float2 pos = frac(loc * 1.00001)-float2(0.4999, 0.4999); // pos = pixel position
+	float2 dir = sign(pos); // dir = pixel direction
+
+	float2 g1 = dir*t1.xy;
+	float2 g2 = dir*t1.zw;
+
+	float3 A = tex2D(decal, vTexCoord       ).xyz;
+	float3 B = tex2D(decal, vTexCoord +g1   ).xyz;
+	float3 C = tex2D(decal, vTexCoord    +g2).xyz;
+	float3 D = tex2D(decal, vTexCoord +g1+g2).xyz;
+
+	float a = luma(A);
+	float b = luma(B);
+	float c = luma(C);
+	float d = luma(D);
+
+	float p = abs(pos.x);
+	float q = abs(pos.y);
+
+	float k = distance(pos,g1);
+	float l = distance(pos,g2);
+
+	float wd1 = abs(a-d);
+	float wd2 = abs(b-c);
+
+	if ( wd1 < wd2 )
+	{
+		if (k < l)
+		{
+			C = A + D - B;
+		}
+		else
+		{
+			B = A + D - C;
+		}
+	}
+	else if (wd1 > wd2)
+	{
+		D = B + C - A;
+	}
+
+	float3 color = bilinear(p, q, A, B, C, D);
+	FragColor = vec4(color, 1.0);
+} 
+#endif
diff --git a/base/denoisers/crt-fast-bilateral-super-xbr.glslp b/base/denoisers/crt-fast-bilateral-super-xbr.glslp
new file mode 100644
index 0000000..935ba22
--- /dev/null
+++ b/base/denoisers/crt-fast-bilateral-super-xbr.glslp
@@ -0,0 +1,42 @@
+shaders = "6"
+shader0 = "shaders/fast-bilateral.glsl"
+filter_linear0 = "false"
+wrap_mode0 = "clamp_to_edge"
+scale_type_x0 = "source"
+scale_x0 = "1.000000"
+scale_type_y0 = "source"
+scale_y0 = "1.000000"
+shader1 = "../xbr/shaders/super-xbr/super-xbr-pass0.glsl"
+filter_linear1 = "false"
+wrap_mode1 = "clamp_to_edge"
+scale_type_x1 = "source"
+scale_x1 = "1.000000"
+scale_type_y1 = "source"
+scale_y1 = "1.000000"
+shader2 = "../xbr/shaders/super-xbr/super-xbr-pass1.glsl"
+filter_linear2 = "false"
+wrap_mode2 = "clamp_to_edge"
+scale_type_x2 = "source"
+scale_x2 = "2.000000"
+scale_type_y2 = "source"
+scale_y2 = "2.000000"
+shader3 = "../xbr/shaders/super-xbr/super-xbr-pass2.glsl"
+filter_linear3 = "false"
+wrap_mode3 = "clamp_to_edge"
+scale_type_x3 = "source"
+scale_x3 = "1.000000"
+scale_type_y3 = "source"
+scale_y3 = "1.000000"
+shader4 = "../windowed/shaders/jinc2-sharper.glsl"
+filter_linear4 = "false"
+wrap_mode4 = "clamp_to_edge"
+float_framebuffer4 = "false"
+scale_type_x4 = "source"
+scale_x4 = "1.000000"
+scale_type_y4 = "source"
+scale_y4 = "0.500000"
+shader5 = "../crt/shaders/hyllian/crt-hyllian.glsl"
+filter_linear5 = "false"
+wrap_mode5 = "clamp_to_edge"
+float_framebuffer5 = "false"
+
diff --git a/base/denoisers/fast-bilateral-super-xbr-4p.glslp b/base/denoisers/fast-bilateral-super-xbr-4p.glslp
new file mode 100644
index 0000000..ebc8b11
--- /dev/null
+++ b/base/denoisers/fast-bilateral-super-xbr-4p.glslp
@@ -0,0 +1,43 @@
+shaders = "6"
+shader0 = "shaders/fast-bilateral.glsl"
+filter_linear0 = "false"
+wrap_mode0 = "clamp_to_edge"
+scale_type_x0 = "source"
+scale_x0 = "1.000000"
+scale_type_y0 = "source"
+scale_y0 = "1.000000"
+shader1 = "../xbr/shaders/super-xbr/super-xbr-pass0.glsl"
+filter_linear1 = "false"
+wrap_mode1 = "clamp_to_edge"
+scale_type_x1 = "source"
+scale_x1 = "1.000000"
+scale_type_y1 = "source"
+scale_y1 = "1.000000"
+shader2 = "../xbr/shaders/super-xbr/super-xbr-pass1.glsl"
+filter_linear2 = "false"
+wrap_mode2 = "clamp_to_edge"
+scale_type_x2 = "source"
+scale_x2 = "2.000000"
+scale_type_y2 = "source"
+scale_y2 = "2.000000"
+shader3 = "../xbr/shaders/super-xbr/super-xbr-pass0.glsl"
+filter_linear3 = "false"
+wrap_mode3 = "clamp_to_edge"
+scale_type_x3 = "source"
+scale_x3 = "1.000000"
+scale_type_y3 = "source"
+scale_y3 = "1.000000"
+
+shader4 = "../xbr/shaders/super-xbr/super-xbr-pass1.glsl"
+filter_linear4 = "false"
+wrap_mode4 = "clamp_to_edge"
+scale_type_x4 = "source"
+scale_x4 = "2.000000"
+scale_type_y4 = "source"
+scale_y4 = "2.000000"
+
+
+shader5 = "../windowed/shaders/jinc2-sharper.glsl"
+filter_linear5 = "false"
+wrap_mode5 = "clamp_to_edge"
+
diff --git a/base/denoisers/fast-bilateral-super-xbr-6p.glslp b/base/denoisers/fast-bilateral-super-xbr-6p.glslp
new file mode 100644
index 0000000..6ee5ba5
--- /dev/null
+++ b/base/denoisers/fast-bilateral-super-xbr-6p.glslp
@@ -0,0 +1,57 @@
+shaders = "8"
+shader0 = "shaders/fast-bilateral.glsl"
+filter_linear0 = "false"
+wrap_mode0 = "clamp_to_edge"
+scale_type_x0 = "source"
+scale_x0 = "1.000000"
+scale_type_y0 = "source"
+scale_y0 = "1.000000"
+shader1 = "../xbr/shaders/super-xbr/super-xbr-pass0.glsl"
+filter_linear1 = "false"
+wrap_mode1 = "clamp_to_edge"
+scale_type_x1 = "source"
+scale_x1 = "1.000000"
+scale_type_y1 = "source"
+scale_y1 = "1.000000"
+shader2 = "../xbr/shaders/super-xbr/super-xbr-pass1.glsl"
+filter_linear2 = "false"
+wrap_mode2 = "clamp_to_edge"
+scale_type_x2 = "source"
+scale_x2 = "2.000000"
+scale_type_y2 = "source"
+scale_y2 = "2.000000"
+shader3 = "../xbr/shaders/super-xbr/super-xbr-pass2.glsl"
+filter_linear3 = "false"
+wrap_mode3 = "clamp_to_edge"
+scale_type_x3 = "source"
+scale_x3 = "1.000000"
+scale_type_y3 = "source"
+scale_y3 = "1.000000"
+
+shader4 = "../xbr/shaders/super-xbr/super-xbr-pass0.glsl"
+filter_linear4 = "false"
+wrap_mode4 = "clamp_to_edge"
+scale_type_x4 = "source"
+scale_x4 = "1.000000"
+scale_type_y4 = "source"
+scale_y4 = "1.000000"
+shader5 = "../xbr/shaders/super-xbr/super-xbr-pass1.glsl"
+filter_linear5 = "false"
+wrap_mode5 = "clamp_to_edge"
+scale_type_x5 = "source"
+scale_x5 = "2.000000"
+scale_type_y5 = "source"
+scale_y5 = "2.000000"
+shader6 = "../xbr/shaders/super-xbr/super-xbr-pass2.glsl"
+filter_linear6 = "false"
+wrap_mode6 = "clamp_to_edge"
+scale_type_x6 = "source"
+scale_x6 = "1.000000"
+scale_type_y6 = "source"
+scale_y6 = "1.000000"
+
+
+shader7 = "../windowed/shaders/jinc2-sharper.glsl"
+filter_linear7 = "false"
+wrap_mode7 = "clamp_to_edge"
+
diff --git a/base/denoisers/fast-bilateral-super-xbr.glslp b/base/denoisers/fast-bilateral-super-xbr.glslp
new file mode 100644
index 0000000..5ad69a5
--- /dev/null
+++ b/base/denoisers/fast-bilateral-super-xbr.glslp
@@ -0,0 +1,33 @@
+shaders = "5"
+shader0 = "shaders/fast-bilateral.glsl"
+filter_linear0 = "false"
+wrap_mode0 = "clamp_to_edge"
+scale_type_x0 = "source"
+scale_x0 = "1.000000"
+scale_type_y0 = "source"
+scale_y0 = "1.000000"
+shader1 = "../xbr/shaders/super-xbr/super-xbr-pass0.glsl"
+filter_linear1 = "false"
+wrap_mode1 = "clamp_to_edge"
+scale_type_x1 = "source"
+scale_x1 = "1.000000"
+scale_type_y1 = "source"
+scale_y1 = "1.000000"
+shader2 = "../xbr/shaders/super-xbr/super-xbr-pass1.glsl"
+filter_linear2 = "false"
+wrap_mode2 = "clamp_to_edge"
+scale_type_x2 = "source"
+scale_x2 = "2.000000"
+scale_type_y2 = "source"
+scale_y2 = "2.000000"
+shader3 = "../xbr/shaders/super-xbr/super-xbr-pass2.glsl"
+filter_linear3 = "false"
+wrap_mode3 = "clamp_to_edge"
+scale_type_x3 = "source"
+scale_x3 = "1.000000"
+scale_type_y3 = "source"
+scale_y3 = "1.000000"
+shader4 = "../windowed/shaders/jinc2-sharper.glsl"
+filter_linear4 = "false"
+wrap_mode4 = "clamp_to_edge"
+
diff --git a/base/denoisers/fast-bilateral.glslp b/base/denoisers/fast-bilateral.glslp
new file mode 100644
index 0000000..2987737
--- /dev/null
+++ b/base/denoisers/fast-bilateral.glslp
@@ -0,0 +1,4 @@
+shaders = 1
+
+shader0 = shaders/fast-bilateral.glsl
+filter_linear0 = false
\ No newline at end of file
diff --git a/base/denoisers/shaders/fast-bilateral-3d.glsl b/base/denoisers/shaders/fast-bilateral-3d.glsl
new file mode 100644
index 0000000..8b3888f
--- /dev/null
+++ b/base/denoisers/shaders/fast-bilateral-3d.glsl
@@ -0,0 +1,183 @@
+#version 120
+
+/*
+   Hyllian's Fast Bilateral 3D Shader
+   
+   Copyright (C) 2011/2016 Hyllian - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is 
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+
+*/
+
+// Parameter lines go here:
+#pragma parameter FB_RES "Bilateral Internal Res" 2.0 1.0 8.0 1.0
+#pragma parameter SIGMA_R "Bilateral Blur" 0.4 0.0 2.0 0.1
+#pragma parameter SIGMA_D "Bilateral Space" 3.0 0.0 10.0 0.2
+// END PARAMETERS //
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying 
+#define COMPAT_ATTRIBUTE attribute 
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    COL0 = COLOR;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+#ifdef PARAMETER_UNIFORM
+uniform float FB_RES;
+uniform float SIGMA_R;
+uniform float SIGMA_D;
+#else
+#define FB_RES 2.0
+#define SIGMA_R 0.4
+#define SIGMA_D 3.0
+#endif
+
+#define GET(M,K) (COMPAT_TEXTURE(Source,tc+M*dx+K*dy).xyz)
+
+#define BIL(M,K) {\
+	col=GET(M,K);\
+	ds=M*M+K*K;\
+	weight=exp(-ds/sd2)*exp(-(col-center)*(col-center)/si2);\
+	color+=(weight*col);\
+	wsum+=weight;\
+	}
+
+void main()
+{
+      float ds, sd2, si2;
+      float sigma_d = SIGMA_D;
+      float sigma_r = SIGMA_R*0.04;
+
+      vec3 color = vec3(0.0, 0.0, 0.0);
+      vec3 wsum = vec3(0.0, 0.0, 0.0);
+      vec3 weight;
+
+      vec2 dx = vec2(FB_RES, 0.0) * SourceSize.zw;
+      vec2 dy = vec2(0.0, FB_RES) * SourceSize.zw;
+
+      sd2 = 2.0 * sigma_d * sigma_d;
+      si2 = 2.0 * sigma_r * sigma_r;
+
+      vec2 tc = vTexCoord;
+
+      vec3 col;
+      vec3 center = GET(0,0);
+     // center = sqrt(center);
+
+      BIL(-2,-2)
+      BIL(-1,-2)
+      BIL( 0,-2)
+      BIL( 1,-2)
+      BIL( 2,-2)
+      BIL(-2,-1)
+      BIL(-1,-1)
+      BIL( 0,-1)
+      BIL( 1,-1)
+      BIL( 2,-1)
+      BIL(-2, 0)
+      BIL(-1, 0)
+      BIL( 0, 0)
+      BIL( 1, 0)
+      BIL( 2, 0)
+      BIL(-2, 1)
+      BIL(-1, 1)
+      BIL( 0, 1)
+      BIL( 1, 1)
+      BIL( 2, 1)
+      BIL(-2, 2)
+      BIL(-1, 2)
+      BIL( 0, 2)
+      BIL( 1, 2)
+      BIL( 2, 2)
+
+      // Weight normalization
+      color /= wsum;
+
+      FragColor = vec4(color, 1.);
+} 
+#endif
diff --git a/base/denoisers/shaders/fast-bilateral.glsl b/base/denoisers/shaders/fast-bilateral.glsl
new file mode 100644
index 0000000..b42efbb
--- /dev/null
+++ b/base/denoisers/shaders/fast-bilateral.glsl
@@ -0,0 +1,190 @@
+#version 120
+
+/*
+   Hyllian's Fast Bilateral Shader
+   
+   Copyright (C) 2011/2016 Hyllian - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is 
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+
+*/
+
+// Parameter lines go here:
+#pragma parameter SIGMA_R "Bilateral Blur" 0.4 0.0 1.0 0.1
+
+#define saturate(c) clamp(c, 0.0, 1.0)
+#define lerp(c) mix(c)
+#define mul(a,b) (b*a)
+#define fmod(c) mod(c)
+#define frac(c) fract(c)
+#define tex2D(c,d) COMPAT_TEXTURE(c,d)
+#define float2 vec2
+#define float3 vec3
+#define float4 vec4
+#define int2 ivec2
+#define int3 ivec3
+#define int4 ivec4
+#define bool2 bvec2
+#define bool3 bvec3
+#define bool4 bvec4
+#define float2x2 mat2x2
+#define float3x3 mat3x3
+#define float4x4 mat4x4
+
+#define decal Source
+
+#define BIL(M,K)  {col=GET(M,K);ds=M*M+K*K;weight=exp(-ds/sd2)*exp(-(col-center)*(col-center)/si2);color+=(weight*col);wsum+=weight;}
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying 
+#define COMPAT_ATTRIBUTE attribute 
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    COL0 = COLOR;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+#ifdef PARAMETER_UNIFORM
+// All parameter floats need to have COMPAT_PRECISION in front of them
+uniform COMPAT_PRECISION float SIGMA_R;
+#else
+#define SIGMA_R 0.4
+#endif
+
+#define GET(M,K) (tex2D(decal,tc+M*dx+K*dy).xyz)
+
+void main()
+{
+      float ds, sd2, si2;
+      float sigma_d = 3.0;
+      float sigma_r = SIGMA_R*0.04;
+
+      float3 color = float3(0.0, 0.0, 0.0);
+      float3 wsum = float3(0.0, 0.0, 0.0);
+      float3 weight;
+
+      float2 dx = float2(1.0, 0.0) * SourceSize.zw;
+      float2 dy = float2(0.0, 1.0) * SourceSize.zw;
+
+      sd2 = 2.0 * sigma_d * sigma_d;
+      si2 = 2.0 * sigma_r * sigma_r;
+
+      float2 tc = vTexCoord;
+
+      float3 col;
+      float3 center = GET(0.,0.);
+
+      BIL(-2.,-2.)
+      BIL(-1.,-2.)
+      BIL( 0.,-2.)
+      BIL( 1.,-2.)
+      BIL( 2.,-2.)
+      BIL(-2.,-1.)
+      BIL(-1.,-1.)
+      BIL( 0.,-1.)
+      BIL( 1.,-1.)
+      BIL( 2.,-1.)
+      BIL(-2., 0.)
+      BIL(-1., 0.)
+      BIL( 0., 0.)
+      BIL( 1., 0.)
+      BIL( 2., 0.)
+      BIL(-2., 1.)
+      BIL(-1., 1.)
+      BIL( 0., 1.)
+      BIL( 1., 1.)
+      BIL( 2., 1.)
+      BIL(-2., 2.)
+      BIL(-1., 2.)
+      BIL( 0., 2.)
+      BIL( 1., 2.)
+      BIL( 2., 2.)
+
+      // Weight normalization
+      color /= wsum;
+   FragColor = vec4(color, 1.0);
+} 
+#endif
diff --git a/base/denoisers/shaders/median_3x3.glsl b/base/denoisers/shaders/median_3x3.glsl
new file mode 100644
index 0000000..648b204
--- /dev/null
+++ b/base/denoisers/shaders/median_3x3.glsl
@@ -0,0 +1,167 @@
+/*
+3x3 Median optimized for GeForce 8800
+
+Morgan McGuire and Kyle Whitson
+Williams College
+
+Register allocation tips by Victor Huang Xiaohuang
+University of Illinois at Urbana-Champaign
+
+http://graphics.cs.williams.edu
+
+
+Copyright (c) Morgan McGuire and Williams College, 2006
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+Redistributions of source code must retain the above copyright notice,
+this list of conditions and the following disclaimer.
+
+Redistributions in binary form must reproduce the above copyright
+notice, this list of conditions and the following disclaimer in the
+documentation and/or other materials provided with the distribution.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+*/
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying
+#define COMPAT_ATTRIBUTE attribute
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+COMPAT_VARYING vec4 t1;
+COMPAT_VARYING vec4 t2;
+COMPAT_VARYING vec4 t3;
+
+vec4 _oPosition1;
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    vec4 _oColor;
+    vec2 _otexCoord;
+    gl_Position = VertexCoord.x * MVPMatrix[0] + VertexCoord.y * MVPMatrix[1] + VertexCoord.z * MVPMatrix[2] + VertexCoord.w * MVPMatrix[3];
+    _oPosition1 = gl_Position;
+    _oColor = COLOR;
+    _otexCoord = TexCoord.xy;
+    COL0 = COLOR;
+    TEX0.xy = TexCoord.xy;
+
+    vec2 ps = vec2(1.0).xy / TextureSize.xy;
+	float dx = ps.x;
+	float dy = ps.y;
+
+	t1 = TEX0.xxxy + vec4(-dx, 0, dx, -dy);
+	t2 = TEX0.xxxy + vec4(-dx, 0, dx,   0);
+	t3 = TEX0.xxxy + vec4(-dx, 0, dx,  dy);
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+//standard texture sample looks like this: COMPAT_TEXTURE(Texture, TEX0.xy);
+COMPAT_VARYING vec4 t1;
+COMPAT_VARYING vec4 t2;
+COMPAT_VARYING vec4 t3;
+
+#define s2(a, b)				temp = a; a = min(a, b); b = max(temp, b);
+#define mn3(a, b, c)			s2(a, b); s2(a, c);
+#define mx3(a, b, c)			s2(b, c); s2(a, c);
+
+#define mnmx3(a, b, c)			mx3(a, b, c); s2(a, b);                                   // 3 exchanges
+#define mnmx4(a, b, c, d)		s2(a, b); s2(c, d); s2(a, c); s2(b, d);                   // 4 exchanges
+#define mnmx5(a, b, c, d, e)	s2(a, b); s2(c, d); mn3(a, c, e); mx3(b, d, e);           // 6 exchanges
+#define mnmx6(a, b, c, d, e, f) s2(a, d); s2(b, e); s2(c, f); mn3(a, b, c); mx3(d, e, f); // 7 exchanges
+
+void main()
+{
+  vec3 v[6];
+
+  v[0] = COMPAT_TEXTURE(Texture, t1.xw).rgb;
+  v[1] = COMPAT_TEXTURE(Texture, t1.yw).rgb;
+  v[2] = COMPAT_TEXTURE(Texture, t1.zw).rgb;
+  v[3] = COMPAT_TEXTURE(Texture, t2.xw).rgb;
+  v[4] = COMPAT_TEXTURE(Texture, t2.yw).rgb;
+  v[5] = COMPAT_TEXTURE(Texture, t2.zw).rgb;
+
+  // Starting with a subset of size 6, remove the min and max each time
+  vec3 temp;
+  mnmx6(v[0], v[1], v[2], v[3], v[4], v[5]);
+
+  v[5] = COMPAT_TEXTURE(Texture, t3.xw).rgb;
+
+  mnmx5(v[1], v[2], v[3], v[4], v[5]);
+
+  v[5] = COMPAT_TEXTURE(Texture, t3.yw).rgb;
+
+  mnmx4(v[2], v[3], v[4], v[5]);
+
+  v[5] = COMPAT_TEXTURE(Texture, t3.zw).rgb;
+
+  mnmx3(v[3], v[4], v[5]);
+  FragColor = vec4(v[4], 1.0);
+}
+#endif
diff --git a/base/denoisers/shaders/median_5x5.glsl b/base/denoisers/shaders/median_5x5.glsl
new file mode 100644
index 0000000..f52917d
--- /dev/null
+++ b/base/denoisers/shaders/median_5x5.glsl
@@ -0,0 +1,230 @@
+/*
+5x5 Median
+
+Morgan McGuire and Kyle Whitson, 2006
+Williams College
+http://graphics.cs.williams.edu
+
+Copyright (c) Morgan McGuire and Williams College, 2006
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+Redistributions of source code must retain the above copyright notice,
+this list of conditions and the following disclaimer.
+
+Redistributions in binary form must reproduce the above copyright
+notice, this list of conditions and the following disclaimer in the
+documentation and/or other materials provided with the distribution.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+*/
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying
+#define COMPAT_ATTRIBUTE attribute
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+COMPAT_VARYING vec4 t01;
+COMPAT_VARYING vec4 t02;
+COMPAT_VARYING vec4 t03;
+COMPAT_VARYING vec4 t04;
+COMPAT_VARYING vec4 t05;
+COMPAT_VARYING vec4 t06;
+COMPAT_VARYING vec4 t07;
+COMPAT_VARYING vec4 t08;
+COMPAT_VARYING vec4 t09;
+COMPAT_VARYING vec4 t10;
+COMPAT_VARYING vec4 t11;
+COMPAT_VARYING vec4 t12;
+
+vec4 _oPosition1;
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    vec4 _oColor;
+    vec2 _otexCoord;
+    gl_Position = VertexCoord.x * MVPMatrix[0] + VertexCoord.y * MVPMatrix[1] + VertexCoord.z * MVPMatrix[2] + VertexCoord.w * MVPMatrix[3];
+    _oPosition1 = gl_Position;
+    _oColor = COLOR;
+    _otexCoord = TexCoord.xy;
+    COL0 = COLOR;
+    TEX0.xy = TexCoord.xy;
+
+	vec2 ps = vec2(1.0).xy / TextureSize.xy;
+	float dx1 = ps.x;
+	float dx2 = ps.x + ps.x;
+	float dy1 = ps.y;
+	float dy2 = ps.y + ps.y;
+
+	t01 = TEX0.xyxy + vec4(-dx2, -dy2, -dx1, -dy2);
+	t02 = TEX0.xyxy + vec4(   0, -dy2,  dx1, -dy2);
+	t03 = TEX0.xyxy + vec4( dx2, -dy2, -dx2, -dy1);
+	t04 = TEX0.xyxy + vec4(-dx1, -dy1,    0, -dy1);
+	t05 = TEX0.xyxy + vec4( dx1, -dy1,  dx2, -dy1);
+	t06 = TEX0.xyxy + vec4(-dx2,    0, -dx1,    0);
+
+	t07 = TEX0.xyxy + vec4( dx1,    0,  dx2,    0);
+	t08 = TEX0.xyxy + vec4(-dx2,  dy1, -dx1,  dy1);
+	t09 = TEX0.xyxy + vec4(   0,  dy1,  dx1,  dy1);
+	t10 = TEX0.xyxy + vec4( dx2,  dy1, -dx2,  dy2);
+	t11 = TEX0.xyxy + vec4(-dx1,  dy2,    0,  dy2);
+	t12 = TEX0.xyxy + vec4( dx1,  dy2,  dx2,  dy2);
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+COMPAT_VARYING vec4 t01;
+COMPAT_VARYING vec4 t02;
+COMPAT_VARYING vec4 t03;
+COMPAT_VARYING vec4 t04;
+COMPAT_VARYING vec4 t05;
+COMPAT_VARYING vec4 t06;
+COMPAT_VARYING vec4 t07;
+COMPAT_VARYING vec4 t08;
+COMPAT_VARYING vec4 t09;
+COMPAT_VARYING vec4 t10;
+COMPAT_VARYING vec4 t11;
+COMPAT_VARYING vec4 t12;
+
+//standard texture sample looks like this: COMPAT_COMPAT_TEXTURE(Texture, TEX0.xy);
+#define SourceSize		vec4(TextureSize, 1.0 / TextureSize)
+
+#define s2(a, b)				temp = a; a = min(a, b); b = max(temp, b);
+#define t2(a, b)				s2(v[a], v[b]);
+#define t24(a, b, c, d, e, f, g, h)			t2(a, b); t2(c, d); t2(e, f); t2(g, h);
+#define t25(a, b, c, d, e, f, g, h, i, j)		t24(a, b, c, d, e, f, g, h); t2(i, j);
+
+void main()
+{
+  vec3 v[25];
+  /*
+  // Add the pixels which make up our window to the pixel array.
+  for(int dX = -2; dX <= 2; ++dX) {
+    for(int dY = -2; dY <= 2; ++dY) {
+      vec2 offset = vec2(float(dX), float(dY));
+
+      // If a pixel in the window is located at (x+dX, y+dY), put it at index (dX + R)(2R + 1) + (dY + R) of the
+      // pixel array. This will fill the pixel array, with the top left pixel of the window at pixel[0] and the
+      // bottom right pixel of the window at pixel[N-1].
+      v[(dX + 2) * 5 + (dY + 2)] = COMPAT_TEXTURE(Texture, TEX0.xy + offset * SourceSize.zw).rgb;
+    }
+  }
+  */
+  v[0]  = COMPAT_TEXTURE(Texture, t01.xy).rgb;
+  v[5]  = COMPAT_TEXTURE(Texture, t01.zw).rgb;
+  v[10] = COMPAT_TEXTURE(Texture, t02.xy).rgb;
+  v[15] = COMPAT_TEXTURE(Texture, t02.zw).rgb;
+  v[20] = COMPAT_TEXTURE(Texture, t03.xy).rgb;
+  v[1]  = COMPAT_TEXTURE(Texture, t03.zw).rgb;
+  v[6]  = COMPAT_TEXTURE(Texture, t04.xy).rgb;
+  v[11] = COMPAT_TEXTURE(Texture, t04.zw).rgb;
+  v[16] = COMPAT_TEXTURE(Texture, t05.xy).rgb;
+  v[21] = COMPAT_TEXTURE(Texture, t05.zw).rgb;
+  v[2]  = COMPAT_TEXTURE(Texture, t06.xy).rgb;
+  v[7]  = COMPAT_TEXTURE(Texture, t06.zw).rgb;
+  v[12] = COMPAT_TEXTURE(Texture, TEX0.xy).rgb;
+  v[17] = COMPAT_TEXTURE(Texture, t07.xy).rgb;
+  v[22] = COMPAT_TEXTURE(Texture, t07.zw).rgb;
+  v[3]  = COMPAT_TEXTURE(Texture, t08.xy).rgb;
+  v[8]  = COMPAT_TEXTURE(Texture, t08.zw).rgb;
+  v[13] = COMPAT_TEXTURE(Texture, t09.xy).rgb;
+  v[18] = COMPAT_TEXTURE(Texture, t09.zw).rgb;
+  v[23] = COMPAT_TEXTURE(Texture, t10.xy).rgb;
+  v[4]  = COMPAT_TEXTURE(Texture, t10.zw).rgb;
+  v[9]  = COMPAT_TEXTURE(Texture, t11.xy).rgb;
+  v[14] = COMPAT_TEXTURE(Texture, t11.zw).rgb;
+  v[19] = COMPAT_TEXTURE(Texture, t12.xy).rgb;
+  v[24] = COMPAT_TEXTURE(Texture, t12.zw).rgb;
+
+
+
+  vec3 temp;
+
+  t25(0, 1,			3, 4,		2, 4,		2, 3,		6, 7);
+  t25(5, 7,			5, 6,		9, 7,		1, 7,		1, 4);
+  t25(12, 13,		11, 13,		11, 12,		15, 16,		14, 16);
+  t25(14, 15,		18, 19,		17, 19,		17, 18,		21, 22);
+  t25(20, 22,		20, 21,		23, 24,		2, 5,		3, 6);
+  t25(0, 6,			0, 3,		4, 7,		1, 7,		1, 4);
+  t25(11, 14,		8, 14,		8, 11,		12, 15,		9, 15);
+  t25(9, 12,		13, 16,		10, 16,		10, 13,		20, 23);
+  t25(17, 23,		17, 20,		21, 24,		18, 24,		18, 21);
+  t25(19, 22,		8, 17,		9, 18,		0, 18,		0, 9);
+  t25(10, 19,		1, 19,		1, 10,		11, 20,		2, 20);
+  t25(2, 11,		12, 21,		3, 21,		3, 12,		13, 22);
+  t25(4, 22,		4, 13,		14, 23,		5, 23,		5, 14);
+  t25(15, 24,		6, 24,		6, 15,		7, 16,		7, 19);
+  t25(3, 11,		5, 17,		11, 17,		9, 17,		4, 10);
+  t25(6, 12,		7, 14,		4, 6,		4, 7,		12, 14);
+  t25(10, 14,		6, 7,		10, 12,		6, 10,		6, 17);
+  t25(12, 17,		7, 17,		7, 10,		12, 18,		7, 12);
+  t24(10, 18,		12, 20,		10, 20,		10, 12);
+
+  FragColor = vec4(v[12], 1.0);
+}
+#endif
diff --git a/base/denoisers/shaders/slow-bilateral.glsl b/base/denoisers/shaders/slow-bilateral.glsl
new file mode 100644
index 0000000..4d44ab5
--- /dev/null
+++ b/base/denoisers/shaders/slow-bilateral.glsl
@@ -0,0 +1,141 @@
+#pragma parameter SIGMA "Sigma" 10.0 1.0 20.0 1.0
+#pragma parameter BSIGMA "BSigma" 0.1 0.01 0.5 0.01
+
+#define MSIZE 15 // needs to be macroed because array initialization needs compile-time constants
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying 
+#define COMPAT_ATTRIBUTE attribute 
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+vec4 _oPosition1; 
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+// compatibility #defines
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+precision mediump int;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+#ifdef PARAMETER_UNIFORM
+uniform COMPAT_PRECISION float SIGMA;
+uniform COMPAT_PRECISION float BSIGMA;
+#else
+#define SIGMA 10.0
+#define BSIGMA 0.1
+#endif
+
+float normpdf(in float x, in float sigma)
+{
+	return 0.39894*exp(-0.5*x*x/(sigma*sigma))/sigma;
+}
+
+float normpdf3(in vec3 v, in float sigma)
+{
+	return 0.39894*exp(-0.5*dot(v,v)/(sigma*sigma))/sigma;
+}
+
+
+void main()
+{
+	vec2 fragcoord = vTexCoord.xy * OutputSize.xy;
+	vec3 c = COMPAT_TEXTURE(Source,  (fragcoord.xy / OutputSize.xy)).rgb;
+	
+	//declare stuff
+	const int kSize = (MSIZE-1)/2;
+	float kernel[MSIZE];
+	vec3 final_colour = vec3(0.0);
+	
+	//create the 1-D kernel
+	float Z = 0.0;
+	for (int j = 0; j <= kSize; ++j)
+	{
+		kernel[kSize+j] = kernel[kSize-j] = normpdf(float(j), SIGMA);
+	}
+	
+	vec3 cc;
+	float factor;
+	float bZ = 1.0/normpdf(0.0, BSIGMA);
+	//read out the texels
+	for (int i=-kSize; i <= kSize; ++i)
+	{
+		for (int j=-kSize; j <= kSize; ++j)
+		{
+			cc = COMPAT_TEXTURE(Source, (fragcoord.xy+vec2(float(i),float(j))) / OutputSize.xy).rgb;
+			factor = normpdf3(cc-c, BSIGMA)*bZ*kernel[kSize+j]*kernel[kSize+i];
+			Z += factor;
+			final_colour += factor*cc;
+		}
+	}
+	
+	FragColor = vec4(final_colour/Z, 1.0);
+} 
+#endif
diff --git a/base/denoisers/slow-bilateral.glslp b/base/denoisers/slow-bilateral.glslp
new file mode 100644
index 0000000..17c06aa
--- /dev/null
+++ b/base/denoisers/slow-bilateral.glslp
@@ -0,0 +1,6 @@
+shaders = 1
+
+shader0 = shaders/slow-bilateral.glsl
+scale_type0 = source
+filter_linear0 = true
+scale0 = 1.0
\ No newline at end of file
diff --git a/base/dithering/bayer-matrix-dithering.glslp b/base/dithering/bayer-matrix-dithering.glslp
new file mode 100644
index 0000000..0c990de
--- /dev/null
+++ b/base/dithering/bayer-matrix-dithering.glslp
@@ -0,0 +1,4 @@
+shaders = 1
+
+shader0 = shaders/bayer-matrix-dithering.glsl
+filter_linear0 = false
diff --git a/base/dithering/cbod_v1.glslp b/base/dithering/cbod_v1.glslp
new file mode 100644
index 0000000..5a87081
--- /dev/null
+++ b/base/dithering/cbod_v1.glslp
@@ -0,0 +1,12 @@
+
+shaders = 2
+shader0 = shaders/cbod-v1/cbod-v1-pass1.glsl
+shader1 = shaders/cbod-v1/cbod-v1-pass2.glsl
+
+filter_linear0 = false
+scale_type0 = source
+scale0 = 1.0
+
+filter_linear1 = false
+scale_type1 = source
+scale1 = 1.0
diff --git a/base/dithering/gdapt.glslp b/base/dithering/gdapt.glslp
new file mode 100644
index 0000000..40c30f6
--- /dev/null
+++ b/base/dithering/gdapt.glslp
@@ -0,0 +1,11 @@
+shaders = 2
+
+shader0 = shaders/gdapt/gdapt-pass0.glsl
+filter_linear0 = false
+scale_type0 = source
+scale0 = 1.0
+
+shader1 = shaders/gdapt/gdapt-pass1.glsl
+filter_linear1 = false
+scale_type1 = source
+scale1 = 1.0
diff --git a/base/dithering/gendither.glslp b/base/dithering/gendither.glslp
new file mode 100644
index 0000000..777df69
--- /dev/null
+++ b/base/dithering/gendither.glslp
@@ -0,0 +1,4 @@
+shaders = 1
+
+shader0 = shaders/gendither.glsl
+filter_linear0 = false
diff --git a/base/dithering/mdapt.glslp b/base/dithering/mdapt.glslp
new file mode 100644
index 0000000..03ad8ac
--- /dev/null
+++ b/base/dithering/mdapt.glslp
@@ -0,0 +1,26 @@
+shaders = 5
+
+shader0 = shaders/mdapt/passes/mdapt-pass0.glsl
+filter_linear0 = false
+scale_type0 = source
+scale0 = 1.0
+
+shader1 = shaders/mdapt/passes/mdapt-pass1.glsl
+filter_linear1 = false
+scale_type1 = source
+scale1 = 1.0
+
+shader2 = shaders/mdapt/passes/mdapt-pass2.glsl
+filter_linear2 = false
+scale_type2 = source
+scale2 = 1.0
+
+shader3 = shaders/mdapt/passes/mdapt-pass3.glsl
+filter_linear3 = false
+scale_type3 = source
+scale3 = 1.0
+
+shader4 = shaders/mdapt/passes/mdapt-pass4.glsl
+filter_linear4 = false
+scale_type4 = source
+scale4 = 1.0
diff --git a/base/dithering/sgenpt-mix.glslp b/base/dithering/sgenpt-mix.glslp
new file mode 100644
index 0000000..3f6495a
--- /dev/null
+++ b/base/dithering/sgenpt-mix.glslp
@@ -0,0 +1,7 @@
+shaders = 1
+
+shader0 = shaders/sgenpt-mix.glsl
+filter_linear0 = false
+scale_type0 = source
+wrap_mode0 = "clamp_to_border"
+scale0 = 1.0
diff --git a/base/dithering/shaders/bayer-matrix-dithering.glsl b/base/dithering/shaders/bayer-matrix-dithering.glsl
new file mode 100644
index 0000000..d18cf15
--- /dev/null
+++ b/base/dithering/shaders/bayer-matrix-dithering.glsl
@@ -0,0 +1,142 @@
+#version 430
+
+// 8x8 Bayer matrix dithering
+// by Martins Upitis
+// license: "All the content here is and will be free to use for everyone, but a donation is always nice."
+// url: http://devlog-martinsh.blogspot.com/2011/03/glsl-8x8-bayer-matrix-dithering.html
+// adapted for RetroArch by hunterk
+
+// Parameter lines go here:
+#pragma parameter animate "Dithering Animation" 0.0 0.0 1.0 1.0
+#pragma parameter dither_size "Dither Size" 0.0 0.0 0.95 0.05
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying 
+#define COMPAT_ATTRIBUTE attribute 
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    COL0 = COLOR;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+precision mediump int;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+#ifdef PARAMETER_UNIFORM
+// All parameter floats need to have COMPAT_PRECISION in front of them
+uniform COMPAT_PRECISION float animate;
+uniform COMPAT_PRECISION float dither_size;
+#else
+#define animate 0.0
+#define dither_size 0.0
+#endif
+
+float find_closest(int x, int y, float c0)
+{
+int dither[8][8] = {
+{ 0, 32, 8, 40, 2, 34, 10, 42}, /* 8x8 Bayer ordered dithering */
+{48, 16, 56, 24, 50, 18, 58, 26}, /* pattern. Each input pixel */
+{12, 44, 4, 36, 14, 46, 6, 38}, /* is scaled to the 0..63 range */
+{60, 28, 52, 20, 62, 30, 54, 22}, /* before looking in this table */
+{ 3, 35, 11, 43, 1, 33, 9, 41}, /* to determine the action. */
+{51, 19, 59, 27, 49, 17, 57, 25},
+{15, 47, 7, 39, 13, 45, 5, 37},
+{63, 31, 55, 23, 61, 29, 53, 21} }; 
+
+float limit = 0.0;
+if(x < 8)
+{
+limit = (dither[x][y]+1)/64.0;
+}
+
+if(c0 < limit)
+return 0.0;
+return 1.0;
+}
+
+void main()
+{
+float Scale = 3.0 + mod(2.0 * FrameCount, 32.0) * animate + dither_size;
+vec4 lum = vec4(0.299, 0.587, 0.114, 0);
+float grayscale = dot(COMPAT_TEXTURE(Source, vTexCoord), lum);
+vec3 rgb = COMPAT_TEXTURE(Source, vTexCoord).rgb;
+
+vec2 xy = (vTexCoord * outsize.xy) * Scale;
+int x = int(mod(xy.x, 8));
+int y = int(mod(xy.y, 8));
+
+vec3 finalRGB;
+finalRGB.r = find_closest(x, y, rgb.r);
+finalRGB.g = find_closest(x, y, rgb.g);
+finalRGB.b = find_closest(x, y, rgb.b);
+
+float final = find_closest(x, y, grayscale);
+
+   FragColor = vec4(finalRGB, 1.0);
+} 
+#endif
diff --git a/base/dithering/shaders/cbod-v1/cbod-v1-pass1.glsl b/base/dithering/shaders/cbod-v1/cbod-v1-pass1.glsl
new file mode 100644
index 0000000..9a8838a
--- /dev/null
+++ b/base/dithering/shaders/cbod-v1/cbod-v1-pass1.glsl
@@ -0,0 +1,132 @@
+/*
+/   "Conditional Blending of Dither" Shader v1.0 - Pass 1
+/   Copyright (c) 2013, Alexander Kulagin <coastkid3d at gmail.com>
+/   All Rights reserved.
+/
+/   Redistribution and use in source and binary forms, with or without
+/   modification, are permitted provided that the following conditions are met:
+/
+/     * Redistributions of source code must retain the above copyright notice,
+/       this list of conditions and the following disclaimer.
+/
+/     * Redistributions in binary form must reproduce the above copyright
+/       notice, this list of conditions and the following disclaimer in the
+/       documentation and/or other materials provided with the distribution.
+/
+/   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+/   AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+/   IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+/   ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
+/   LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+/   CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+/   SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+/   INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+/   CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+/   ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+/   POSSIBILITY OF SUCH DAMAGE.
+*/
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying
+#define COMPAT_ATTRIBUTE attribute
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+vec4 _oPosition1;
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+// compatibility #defines
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+  vec2 uv = vTexCoord - (SourceSize.zw) * 0.25;
+  vec2 uv_shift = (SourceSize.zw);
+	vec3 src = COMPAT_TEXTURE(Source, uv).rgb;
+
+  // Searching for the Vertical Dithering Zones
+	vec3 dither_v_zone = vec3(COMPAT_TEXTURE(Source, uv + vec2(uv_shift.x, 0.)).rgb == COMPAT_TEXTURE(Source, uv - vec2(uv_shift.x, 0.)).rgb);
+  dither_v_zone = vec3(smoothstep(0.2, 1.0, dot(dither_v_zone, vec3(0.33333))));
+
+  // Searching for High Contrast "Safe" Zones
+  vec3 safe_zone = vec3(abs(dot(COMPAT_TEXTURE(Source, uv).rgb - COMPAT_TEXTURE(Source, uv - vec2(uv_shift.x, 0.)).rgb, vec3(0.3333))));
+  safe_zone = vec3(lessThan(safe_zone , vec3(0.45)));
+
+  // Horizontal Bluring by 1 pixel
+  vec3 blur_h = (COMPAT_TEXTURE(Source, uv).rgb + COMPAT_TEXTURE(Source, uv - vec2(uv_shift.x, 0.)).rgb) * 0.5;
+
+  // Final Blend between Source and Blur using Dithering Zone and Safe Zone
+  vec3 finalcolor = mix(src, blur_h, dither_v_zone * safe_zone);
+
+   FragColor = vec4(finalcolor, 1.0);
+}
+#endif
diff --git a/base/dithering/shaders/cbod-v1/cbod-v1-pass2.glsl b/base/dithering/shaders/cbod-v1/cbod-v1-pass2.glsl
new file mode 100644
index 0000000..c9e492d
--- /dev/null
+++ b/base/dithering/shaders/cbod-v1/cbod-v1-pass2.glsl
@@ -0,0 +1,132 @@
+/*
+/   "Conditional Blending of Dither" Shader v1.0 - Pass 2
+/   Copyright (c) 2013, Alexander Kulagin <coastkid3d at gmail.com>
+/   All Rights reserved.
+/
+/   Redistribution and use in source and binary forms, with or without
+/   modification, are permitted provided that the following conditions are met:
+/
+/     * Redistributions of source code must retain the above copyright notice,
+/       this list of conditions and the following disclaimer.
+/
+/     * Redistributions in binary form must reproduce the above copyright
+/       notice, this list of conditions and the following disclaimer in the
+/       documentation and/or other materials provided with the distribution.
+/
+/   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+/   AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+/   IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+/   ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
+/   LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+/   CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+/   SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+/   INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+/   CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+/   ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+/   POSSIBILITY OF SUCH DAMAGE.
+*/
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying
+#define COMPAT_ATTRIBUTE attribute
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+vec4 _oPosition1;
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+// compatibility #defines
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+  vec2 uv = vTexCoord - (SourceSize.zw) * 0.25;
+  vec2 uv_shift = (SourceSize.zw);
+	vec3 src = COMPAT_TEXTURE(Source, uv).rgb;
+
+  // Searching for the Horizontal Dithering Zones
+	vec3 dither_h_zone = vec3(COMPAT_TEXTURE(Source, uv + vec2(0., uv_shift.y)).rgb == COMPAT_TEXTURE(Source, uv - vec2(0., uv_shift.y)).rgb);
+  dither_h_zone = vec3(smoothstep(0.2, 1.0, dot(dither_h_zone, vec3(0.33333))));
+
+  // Searching for High Contrast "Safe" Zones
+  vec3 safe_zone = vec3(abs(dot(COMPAT_TEXTURE(Source, uv).rgb - COMPAT_TEXTURE(Source, uv - vec2(0., uv_shift.y)).rgb, vec3(0.3333))));
+  safe_zone = vec3(lessThan(safe_zone , vec3(0.45)));
+
+  // Vertical Bluring by 1 pixel
+  vec3 blur_v = (COMPAT_TEXTURE(Source, uv).rgb + COMPAT_TEXTURE(Source, uv - vec2(0., uv_shift.y)).rgb) * 0.5;
+
+  // Final Blend between Source and Blur using Dithering Zone and Safe Zone
+  vec3 finalcolor = mix(src, blur_v, dither_h_zone * safe_zone);
+
+   FragColor = vec4(finalcolor, 1.0);
+}
+#endif
diff --git a/base/dithering/shaders/gdapt/gdapt-pass0.glsl b/base/dithering/shaders/gdapt/gdapt-pass0.glsl
new file mode 100644
index 0000000..aa0b683
--- /dev/null
+++ b/base/dithering/shaders/gdapt/gdapt-pass0.glsl
@@ -0,0 +1,137 @@
+/*
+   Genesis Dithering and Pseudo Transparency Shader v1.3 - Pass 0
+   by Sp00kyFox, 2014
+
+   Neighbor anaylsis via dot product of the difference vectors.
+
+*/
+
+// Parameter lines go here:
+#pragma parameter MODE "GDAPT Monochrome Analysis"	0.0 0.0 1.0 1.0
+#pragma parameter PWR  "GDAPT Color Metric Exp"		2.0 0.0 10.0 0.1
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying 
+#define COMPAT_ATTRIBUTE attribute 
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+COMPAT_VARYING vec2 t1;
+
+vec4 _oPosition1; 
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    COL0 = COLOR;
+    TEX0.xy = TexCoord.xy;
+	t1 = 1.0 / SourceSize.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+COMPAT_VARYING vec2 t1;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+#ifdef PARAMETER_UNIFORM
+// All parameter floats need to have COMPAT_PRECISION in front of them
+uniform COMPAT_PRECISION float MODE;
+uniform COMPAT_PRECISION float PWR;
+#else
+#define MODE 0.0
+#define PWR 2.0
+#endif
+
+#define dotfix(x,y) clamp(dot(x,y), 0.0, 1.0)	// NVIDIA Fix
+#define TEX(dx,dy) COMPAT_TEXTURE(Source, vTexCoord+vec2((dx),(dy))*t1).xyz
+
+// Reference: http://www.compuphase.com/cmetric.htm
+COMPAT_PRECISION float eq(vec3 A, vec3 B)
+{
+	vec3 diff = A-B;
+	float  ravg = (A.x + B.x) * 0.5;
+
+	diff *= diff * vec3(2.0 + ravg, 4.0, 3.0 - ravg);
+	
+	return pow( smoothstep(3.0, 0.0, sqrt(diff.x + diff.y + diff.z)), PWR );
+}
+
+void main()
+{
+	vec3 C = TEX( 0, 0);
+	vec3 L = TEX(-1, 0);
+	vec3 R = TEX( 1, 0);
+
+	float tag = 0.0;
+
+	if(MODE > 0.5){
+		tag = ((L == R) && (C != L)) ? 1.0 : 0.0;
+	}
+	else{
+		tag = dotfix(normalize(C-L), normalize(C-R)) * eq(L,R);
+	}
+
+   FragColor = vec4(C, tag);
+} 
+#endif
diff --git a/base/dithering/shaders/gdapt/gdapt-pass1.glsl b/base/dithering/shaders/gdapt/gdapt-pass1.glsl
new file mode 100644
index 0000000..8b7fc76
--- /dev/null
+++ b/base/dithering/shaders/gdapt/gdapt-pass1.glsl
@@ -0,0 +1,162 @@
+/*
+   Genesis Dithering and Pseudo Transparency Shader v1.3 - Pass 1
+   by Sp00kyFox, 2014
+
+   Blends pixels based on detected dithering patterns.
+
+*/
+
+// Parameter lines go here:
+#pragma parameter STEPS "GDAPT Error Prevention LVL"	1.0 0.0 5.0 1.0
+#pragma parameter DEBUG "GDAPT Adjust View"		0.0 0.0 1.0 1.0
+#pragma parameter linear_gamma "Use Linear Gamma"		0.0 0.0 1.0 1.0
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying 
+#define COMPAT_ATTRIBUTE attribute 
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+COMPAT_VARYING vec2 t1;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    COL0 = COLOR;
+    TEX0.xy = TexCoord.xy;
+	t1 = 1.0 / SourceSize.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+COMPAT_VARYING vec2 t1;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+#ifdef PARAMETER_UNIFORM
+// All parameter floats need to have COMPAT_PRECISION in front of them
+uniform COMPAT_PRECISION float STEPS;
+uniform COMPAT_PRECISION float DEBUG;
+uniform COMPAT_PRECISION float linear_gamma;
+#else
+#define STEPS 1.0
+#define DEBUG 0.0
+#define linear_gamma 0.0
+#endif
+
+#define TEX(dx,dy) COMPAT_TEXTURE(Source, vTexCoord+vec2((dx),(dy))*t1)
+
+void main()
+{
+	vec4 C = TEX( 0, 0);
+	vec4 L = TEX(-1, 0);
+	vec4 R = TEX( 1, 0);
+	
+	if(linear_gamma > 0.5)
+	{
+		C.xyz = pow(TEX( 0, 0).xyz, vec3(2.2)).xyz;
+		L.xyz = pow(TEX(-1, 0).xyz, vec3(2.2)).xyz;
+		R.xyz = pow(TEX( 1, 0).xyz, vec3(2.2)).xyz;
+	}
+	
+	float str = 0.0;
+
+	if(STEPS == 0.0){
+		str = C.w;
+	}
+	else if(STEPS == 1.0){
+		str = min(max(L.w, R.w), C.w);
+	}
+	else if(STEPS == 2.0){
+		str = min(max(min(max(TEX(-2,0).w, R.w), L.w), min(R.w, TEX(2,0).w)), C.w);				
+	}
+	else if(STEPS == 3.0){
+		float tmp = min(R.w, TEX(2,0).w);
+		str = min(max(min(max(min(max(TEX(-3,0).w, R.w), TEX(-2,0).w), tmp), L.w), min(tmp, TEX(3,0).w)), C.w);
+	}
+	else if(STEPS == 4.0){
+		float tmp1 = min(R.w, TEX(2,0).w);
+		float tmp2 = min(tmp1, TEX(3,0).w);
+		str = min(max(min(max(min(max(min(max(TEX(-4,0).w, R.w), TEX(-3,0).w), tmp1), TEX(-2,0).w), tmp2), L.w), min(tmp2, TEX(4,0).w)), C.w);
+	}
+	else{
+		float tmp1 = min(R.w, TEX(2,0).w);
+		float tmp2 = min(tmp1, TEX(3,0).w);
+		float tmp3 = min(tmp2, TEX(4,0).w);
+		str = min(max(min(max(min(max(min(max(min(max(TEX(-5,0).w, R.w), TEX(-4,0).w), tmp1), TEX(-3,0).w), tmp2), TEX(-2,0).w), tmp3), L.w), min(tmp3, TEX(5,0).w)), C.w);
+	}
+
+
+	if(DEBUG > 0.5)
+		FragColor = vec4(str);
+
+	float sum  = L.w + R.w;
+	float wght = max(L.w, R.w);
+	      wght = (wght == 0.0) ? 1.0 : sum/wght;
+
+   vec4 final = vec4(mix(C.xyz, (wght*C.xyz + L.w*L.xyz + R.w*R.xyz)/(wght + sum), str), 1.0);
+   FragColor = final;
+   if(linear_gamma > 0.5) FragColor = pow(final, vec4(1.0 / 2.2));
+} 
+#endif
diff --git a/base/dithering/shaders/gendither.glsl b/base/dithering/shaders/gendither.glsl
new file mode 100644
index 0000000..af6e243
--- /dev/null
+++ b/base/dithering/shaders/gendither.glsl
@@ -0,0 +1,150 @@
+#version 130
+
+// Gendither
+// 
+// 	Copyright (C) 2013-2014 leilei
+//  adapted for slang format by hunterk
+// 
+// This program is free software; you can redistribute it and/or modify it
+// under the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 2 of the License, or (at your option)
+// any later version.
+
+// This table is a lazy jailbar pattern
+int erroredtable[16] = int[](
+	0,1,0,1,   
+	16,15,16,15,
+	0,1,0,1,   
+	16,15,16,15
+);
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying 
+#define COMPAT_ATTRIBUTE attribute 
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+precision COMPAT_PRECISION float;
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    COL0 = COLOR;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out mediump vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define outsize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+	vec3 final = COMPAT_TEXTURE(Source, vTexCoord).rgb;	
+	vec2 ditheu = vTexCoord.xy * SourceSize.xy;
+
+	// Dither
+	int ditdex = 	int(mod(ditheu.x, 4.0)) * 4 + int(mod(ditheu.y, 4.0)); // 4x4!
+	ivec3 color;
+	ivec3 colord;
+	color.r = int(final.r) * 224;
+	color.g = int(final.g) * 224;
+	color.b = int(final.b) * 224;
+	int yeh = 0;
+	int ohyes = 0;
+
+
+	// looping through a lookup table matrix
+	for (yeh=ditdex; yeh<(ditdex+16); yeh++) ohyes = erroredtable[yeh-15];
+
+	colord.r = color.r + ohyes;
+	colord.g = color.g + ohyes;
+	colord.b = color.b + ohyes;
+	final.rgb += float(colord.rgb) * 0.003921568627451; // divide by 255, i don't trust em
+
+	// Reduce color depth
+	float why = 1.0;
+	vec3 reduceme = vec3(1.0);
+	float radooct = 4.4;	// 32 is usually the proper value // 4.4 was eyeballed
+
+	reduceme.r = pow(final.r, why);  
+	reduceme.r *= radooct;	
+	reduceme.r = floor(reduceme.r);
+	reduceme.r /= radooct; 
+	reduceme.r = pow(reduceme.r, why);
+
+	reduceme.g = pow(final.g, why);  
+	reduceme.g *= radooct;		
+	reduceme.g = floor(reduceme.g);	
+	reduceme.g /= radooct;	
+	reduceme.g = pow(reduceme.g, why);
+
+	reduceme.b = pow(final.b, why);  
+	reduceme.b *= radooct;	
+	reduceme.b = floor(reduceme.b);	
+	reduceme.b /= radooct;	
+	reduceme.b = pow(reduceme.b, why);
+
+	// Brightness cap
+	reduceme.rgb = clamp(reduceme.rgb, vec3(0.0), vec3(0.875));
+	
+   FragColor = vec4(reduceme.rgb, 1.0);
+} 
+#endif
diff --git a/base/dithering/shaders/jinc2-dedither.glsl b/base/dithering/shaders/jinc2-dedither.glsl
new file mode 100644
index 0000000..22bb4af
--- /dev/null
+++ b/base/dithering/shaders/jinc2-dedither.glsl
@@ -0,0 +1,241 @@
+/*
+   Hyllian's jinc windowed-jinc 2-lobe sharper with anti-ringing Shader
+
+   Copyright (C) 2011-2016 Hyllian/Jararaca - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+
+*/
+
+#pragma parameter JINC_SHARP "Sharpness" 1.0 1.0 3.0 1.0
+
+#define texCoord TEX0
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define OUT out
+#define IN  in
+#define tex2D texture
+#else
+#define OUT varying
+#define IN attribute
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+
+IN  vec4 VertexCoord;
+IN  vec4 Color;
+IN  vec2 TexCoord;
+OUT vec2 texCoord;
+OUT float wa;
+OUT float wb;
+OUT float JINC2_AR_STRENGTH;
+OUT vec2 pc;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int  FrameDirection;
+uniform COMPAT_PRECISION int  FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+#ifdef PARAMETER_UNIFORM
+uniform COMPAT_PRECISION float JINC_SHARP;
+#else
+#define JINC_SHARP 1.0
+#endif
+
+const float pi = 3.1415926535897932384626433832795;
+
+vec4 resampler(vec4 x)
+{
+   vec4 res;
+
+    res.x = (x.x==0.0) ?  wa*wb  :  sin(x.x*wa)*sin(x.x*wb)/(x.x*x.x);
+    res.y = (x.y==0.0) ?  wa*wb  :  sin(x.y*wa)*sin(x.y*wb)/(x.y*x.y);
+    res.z = (x.z==0.0) ?  wa*wb  :  sin(x.z*wa)*sin(x.z*wb)/(x.z*x.z);
+    res.w = (x.w==0.0) ?  wa*wb  :  sin(x.w*wa)*sin(x.w*wb)/(x.w*x.w);
+
+   return res;
+}
+
+void main()
+{
+   gl_Position = MVPMatrix * VertexCoord;
+   texCoord = TexCoord * 1.0001;
+
+   float JINC2_WINDOW_SINC, JINC2_SINC;
+
+   if(int(floor(JINC_SHARP + 0.5)) == 1)
+   {
+      JINC2_WINDOW_SINC = 0.405;
+      JINC2_SINC = 0.79;
+   }
+   if(int(floor(JINC_SHARP + 0.5)) == 2)
+   {
+      JINC2_WINDOW_SINC = 0.377;
+      JINC2_SINC = 0.82;
+   }
+   if(int(floor(JINC_SHARP + 0.5)) == 3)
+   {
+      JINC2_WINDOW_SINC = 0.329;
+      JINC2_SINC = 0.87;
+   }
+   JINC2_AR_STRENGTH = 0.8;
+   wa = JINC2_WINDOW_SINC*pi;
+   wb = JINC2_SINC*pi;
+   pc = texCoord*TextureSize;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define IN in
+#define tex2D texture
+out vec4 FragColor;
+#else
+#define IN varying
+#define FragColor gl_FragColor
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D s_p;
+IN vec2 texCoord;
+IN float wa;
+IN float wb;
+IN float JINC2_AR_STRENGTH;
+IN vec2 pc;
+IN vec2 tc;
+
+// Calculates the distance between two points
+float d(vec2 pt1, vec2 pt2)
+{
+  vec2 v = pt2 - pt1;
+  return sqrt(dot(v,v));
+}
+
+vec3 min4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return min(a, min(b, min(c, d)));
+}
+
+vec3 max4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return max(a, max(b, max(c, d)));
+}
+
+vec4 resampler(vec4 x)
+{
+   vec4 res;
+
+   res = (x==vec4(0.0, 0.0, 0.0, 0.0)) ?  vec4(wa*wb)  :  sin(x*wa)*sin(x*wb)/(x*x);
+
+   return res;
+}
+
+void main()
+{
+    vec3 color;
+    vec4 weights[4];
+
+    vec2 dx = vec2(1.0, 0.0);
+    vec2 dy = vec2(0.0, 1.0);
+
+    vec2 tc = (floor(pc-vec2(0.5,0.5))+vec2(0.5,0.5));
+
+    weights[0] = resampler(vec4(d(pc, tc    -dx    -dy), d(pc, tc           -dy), d(pc, tc    +dx    -dy), d(pc, tc+2.0*dx    -dy)));
+    weights[1] = resampler(vec4(d(pc, tc    -dx       ), d(pc, tc              ), d(pc, tc    +dx       ), d(pc, tc+2.0*dx       )));
+    weights[2] = resampler(vec4(d(pc, tc    -dx    +dy), d(pc, tc           +dy), d(pc, tc    +dx    +dy), d(pc, tc+2.0*dx    +dy)));
+    weights[3] = resampler(vec4(d(pc, tc    -dx+2.0*dy), d(pc, tc       +2.0*dy), d(pc, tc    +dx+2.0*dy), d(pc, tc+2.0*dx+2.0*dy)));
+
+    dx = dx/TextureSize;
+    dy = dy/TextureSize;
+    tc = tc/TextureSize;
+
+    vec3 c00 = tex2D(s_p, tc    -dx    -dy).xyz;
+    vec3 c10 = tex2D(s_p, tc           -dy).xyz;
+    vec3 c20 = tex2D(s_p, tc    +dx    -dy).xyz;
+    vec3 c30 = tex2D(s_p, tc+2.0*dx    -dy).xyz;
+    vec3 c01 = tex2D(s_p, tc    -dx       ).xyz;
+    vec3 c11 = tex2D(s_p, tc              ).xyz;
+    vec3 c21 = tex2D(s_p, tc    +dx       ).xyz;
+    vec3 c31 = tex2D(s_p, tc+2.0*dx       ).xyz;
+    vec3 c02 = tex2D(s_p, tc    -dx    +dy).xyz;
+    vec3 c12 = tex2D(s_p, tc           +dy).xyz;
+    vec3 c22 = tex2D(s_p, tc    +dx    +dy).xyz;
+    vec3 c32 = tex2D(s_p, tc+2.0*dx    +dy).xyz;
+    vec3 c03 = tex2D(s_p, tc    -dx+2.0*dy).xyz;
+    vec3 c13 = tex2D(s_p, tc       +2.0*dy).xyz;
+    vec3 c23 = tex2D(s_p, tc    +dx+2.0*dy).xyz;
+    vec3 c33 = tex2D(s_p, tc+2.0*dx+2.0*dy).xyz;
+
+    color = tex2D(s_p, texCoord).xyz;
+
+    //  Get min/max samples
+    vec3 min_sample = min4(c11, c21, c12, c22);
+    vec3 max_sample = max4(c11, c21, c12, c22);
+/*
+      color = mat4x3(c00, c10, c20, c30) * weights[0];
+      color+= mat4x3(c01, c11, c21, c31) * weights[1];
+      color+= mat4x3(c02, c12, c22, c32) * weights[2];
+      color+= mat4x3(c03, c13, c23, c33) * weights[3];
+      mat4 wgts = mat4(weights[0], weights[1], weights[2], weights[3]);
+      vec4 wsum = wgts * vec4(1.0,1.0,1.0,1.0);
+      color = color/(dot(wsum, vec4(1.0,1.0,1.0,1.0)));
+*/
+
+
+    color = vec3(dot(weights[0], vec4(c00.x, c10.x, c20.x, c30.x)), dot(weights[0], vec4(c00.y, c10.y, c20.y, c30.y)), dot(weights[0], vec4(c00.z, c10.z, c20.z, c30.z)));
+    color+= vec3(dot(weights[1], vec4(c01.x, c11.x, c21.x, c31.x)), dot(weights[1], vec4(c01.y, c11.y, c21.y, c31.y)), dot(weights[1], vec4(c01.z, c11.z, c21.z, c31.z)));
+    color+= vec3(dot(weights[2], vec4(c02.x, c12.x, c22.x, c32.x)), dot(weights[2], vec4(c02.y, c12.y, c22.y, c32.y)), dot(weights[2], vec4(c02.z, c12.z, c22.z, c32.z)));
+    color+= vec3(dot(weights[3], vec4(c03.x, c13.x, c23.x, c33.x)), dot(weights[3], vec4(c03.y, c13.y, c23.y, c33.y)), dot(weights[3], vec4(c03.z, c13.z, c23.z, c33.z)));
+    color = color/(dot(weights[0], vec4(1,1,1,1)) + dot(weights[1], vec4(1,1,1,1)) + dot(weights[2], vec4(1,1,1,1)) + dot(weights[3], vec4(1,1,1,1)));
+
+    // Anti-ringing
+    vec3 aux = color;
+    color = clamp(color, min_sample, max_sample);
+    color = mix(aux, color, JINC2_AR_STRENGTH);
+
+    // final sum and weight normalization
+    FragColor.xyz = color;
+}
+#endif
diff --git a/base/dithering/shaders/mdapt/passes/mdapt-pass0.glsl b/base/dithering/shaders/mdapt/passes/mdapt-pass0.glsl
new file mode 100644
index 0000000..9687774
--- /dev/null
+++ b/base/dithering/shaders/mdapt/passes/mdapt-pass0.glsl
@@ -0,0 +1,153 @@
+/*
+   Merge Dithering and Pseudo Transparency Shader v2.8 - Pass 0
+   by Sp00kyFox, 2014
+
+   Neighbor analysis via color metric and dot product of the difference vectors.
+
+*/
+
+// Parameter lines go here:
+#pragma parameter MODE "MDAPT Monochrome Analysis"	0.0 0.0 1.0 1.0
+#pragma parameter PWR  "MDAPT Color Metric Exp"		2.0 0.0 10.0 0.1
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying
+#define COMPAT_ATTRIBUTE attribute
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+vec4 _oPosition1;
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+// compatibility #defines
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+#ifdef PARAMETER_UNIFORM
+// All parameter floats need to have COMPAT_PRECISION in front of them
+uniform COMPAT_PRECISION float MODE;
+uniform COMPAT_PRECISION float PWR;
+#else
+#define MODE 0.0
+#define PWR 2.0
+#endif
+
+#define dotfix(x,y) clamp(dot(x,y), 0.0, 1.0)	// NVIDIA Fix
+#define TEX(dx,dy) COMPAT_TEXTURE(Source, vTexCoord+vec2((dx),(dy))*SourceSize.zw)
+
+// Reference: http://www.compuphase.com/cmetric.htm
+float eq(vec3 A, vec3 B)
+{
+	vec3 diff = A-B;
+	float  ravg = (A.x + B.x) * 0.5;
+
+	diff *= diff * vec3(2.0 + ravg, 4.0, 3.0 - ravg);
+
+	return pow( smoothstep(3.0, 0.0, sqrt(diff.x + diff.y + diff.z)), PWR );
+}
+
+float and(float a, float b, float c, float d, float e, float f){
+	return min(a, min(b, min(c, min(d, min(e,f)))));
+}
+
+void main()
+{
+	/*
+		  U
+		L C R
+		  D
+	*/
+
+	vec3 C = TEX( 0., 0.).xyz;
+	vec3 L = TEX(-1., 0.).xyz;
+	vec3 R = TEX( 1., 0.).xyz;
+	vec3 U = TEX( 0.,-1.).xyz;
+	vec3 D = TEX( 0., 1.).xyz;
+
+
+	vec3 res = vec3(0.0);
+
+	if(MODE > 0.5){
+		res.x = float((L == R) && (C != L));
+		res.y = float((U == D) && (C != U));
+		res.z = float(bool(res.x) && bool(res.y) && (L == U));
+	}
+	else{
+		vec3 dCL = normalize(C-L), dCR = normalize(C-R), dCD = normalize(C-D), dCU = normalize(C-U);
+
+		res.x = dotfix(dCL, dCR) * eq(L,R);
+		res.y = dotfix(dCU, dCD) * eq(U,D);
+		res.z = and(res.x, res.y, dotfix(dCL, dCU) * eq(L,U), dotfix(dCL, dCD) * eq(L,D), dotfix(dCR, dCU) * eq(R,U), dotfix(dCR, dCD) * eq(R,D));
+	}
+
+   FragColor = vec4(res, 1.0);
+}
+#endif
diff --git a/base/dithering/shaders/mdapt/passes/mdapt-pass1.glsl b/base/dithering/shaders/mdapt/passes/mdapt-pass1.glsl
new file mode 100644
index 0000000..7692345
--- /dev/null
+++ b/base/dithering/shaders/mdapt/passes/mdapt-pass1.glsl
@@ -0,0 +1,138 @@
+/*
+   Merge Dithering and Pseudo Transparency Shader v2.8 - Pass 1
+   by Sp00kyFox, 2014
+
+   Preparing checkerboard patterns.
+
+*/
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying
+#define COMPAT_ATTRIBUTE attribute
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+vec4 _oPosition1;
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+// compatibility #defines
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+#define TEX(dx,dy) COMPAT_TEXTURE(Source, vTexCoord+vec2((dx),(dy))*SourceSize.zw)
+
+
+float and(float a, float b){
+	return min(a,b);
+}
+
+float and(float a, float b, float c){
+	return min(a, min(b,c));
+}
+
+float or(float a, float b){
+	return max(a,b);
+}
+
+float or(float a, float b, float c, float d, float e){
+	return max(a, max(b, max(c, max(d,e))));
+}
+
+
+
+void main()
+{
+	/*
+		UL U UR
+		L  C R
+		DL D DR
+	*/
+
+	vec3 C = TEX( 0., 0.).xyz;
+	vec3 L = TEX(-1., 0.).xyz;
+	vec3 R = TEX( 1., 0.).xyz;
+	vec3 D = TEX( 0., 1.).xyz;
+	vec3 U = TEX( 0.,-1.).xyz;
+
+	float UL = TEX(-1.,-1.).z;
+	float UR = TEX( 1.,-1.).z;
+	float DL = TEX(-1., 1.).z;
+	float DR = TEX( 1., 1.).z;
+
+	// Checkerboard Pattern Completion
+	float prCB = or(C.z,
+		and(L.z, R.z, or(U.x, D.x)),
+		and(U.z, D.z, or(L.y, R.y)),
+		and(C.x, or(and(UL, UR), and(DL, DR))),
+		and(C.y, or(and(UL, DL), and(UR, DR))));
+   FragColor = vec4(C.x, prCB, 0.0, 0.0);
+}
+#endif
diff --git a/base/dithering/shaders/mdapt/passes/mdapt-pass2.glsl b/base/dithering/shaders/mdapt/passes/mdapt-pass2.glsl
new file mode 100644
index 0000000..989efe1
--- /dev/null
+++ b/base/dithering/shaders/mdapt/passes/mdapt-pass2.glsl
@@ -0,0 +1,168 @@
+/*
+   Merge Dithering and Pseudo Transparency Shader v2.8 - Pass 2
+   by Sp00kyFox, 2014
+
+   Eliminating isolated detections.
+
+*/
+
+// Parameter lines go here:
+#pragma parameter VL_LO "MDAPT VL LO Thresh" 1.25 0.0 10.0 0.05
+#pragma parameter VL_HI "MDAPT VL HI Thresh" 1.75 0.0 10.0 0.05
+#pragma parameter CB_LO "MDAPT CB LO Thresh" 5.25 0.0 25.0 0.05
+#pragma parameter CB_HI "MDAPT CB HI Thresh" 5.75 0.0 25.0 0.05
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying
+#define COMPAT_ATTRIBUTE attribute
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+vec4 _oPosition1;
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+// compatibility #defines
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+#ifdef PARAMETER_UNIFORM
+// All parameter floats need to have COMPAT_PRECISION in front of them
+uniform COMPAT_PRECISION float VL_LO;
+uniform COMPAT_PRECISION float VL_HI;
+uniform COMPAT_PRECISION float CB_LO;
+uniform COMPAT_PRECISION float CB_HI;
+#else
+#define VL_LO 1.25
+#define VL_HI 1.75
+#define CB_LO 5.25
+#define CB_HI 5.75
+#endif
+
+#define TEX(dx,dy) COMPAT_TEXTURE(Source, vTexCoord+vec2((dx),(dy))*SourceSize.zw)
+#define and(x,y) min(x,y)
+#define or(x,y)  max(x,y)
+
+vec2 sigmoid(vec2 signal){
+	return smoothstep(vec2(VL_LO, CB_LO), vec2(VL_HI, CB_HI), signal);
+}
+
+void main()
+{
+	/*
+		NW  UUL U2 UUR NE
+		ULL UL  U1 UR  URR
+		L2  L1  C  R1  R2
+		DLL DL  D1 DR  DRR
+		SW  DDL D2 DDR SE
+	*/
+
+	vec2 C = TEX( 0., 0.).xy;
+
+
+	vec2 hits = vec2(0.0);
+
+	//phase 1
+	vec2 L1 = TEX(-1., 0.).xy;
+	vec2 R1 = TEX( 1., 0.).xy;
+	vec2 U1 = TEX( 0.,-1.).xy;
+	vec2 D1 = TEX( 0., 1.).xy;
+
+	//phase 2
+	vec2 L2 = and(TEX(-2., 0.).xy, L1);
+	vec2 R2 = and(TEX( 2., 0.).xy, R1);
+	vec2 U2 = and(TEX( 0.,-2.).xy, U1);
+	vec2 D2 = and(TEX( 0., 2.).xy, D1);
+	vec2 UL = and(TEX(-1.,-1.).xy, or(L1, U1));
+	vec2 UR = and(TEX( 1.,-1.).xy, or(R1, U1));
+	vec2 DL = and(TEX(-1., 1.).xy, or(L1, D1));
+	vec2 DR = and(TEX( 1., 1.).xy, or(R1, D1));
+
+	//phase 3
+	vec2 ULL = and(TEX(-2.,-1.).xy, or(L2, UL));
+	vec2 URR = and(TEX( 2.,-1.).xy, or(R2, UR));
+	vec2 DRR = and(TEX( 2., 1.).xy, or(R2, DR));
+	vec2 DLL = and(TEX(-2., 1.).xy, or(L2, DL));
+	vec2 UUL = and(TEX(-1.,-2.).xy, or(U2, UL));
+	vec2 UUR = and(TEX( 1.,-2.).xy, or(U2, UR));
+	vec2 DDR = and(TEX( 1., 2.).xy, or(D2, DR));
+	vec2 DDL = and(TEX(-1., 2.).xy, or(D2, DL));
+
+	//phase 4
+	hits += and(TEX(-2.,-2.).xy, or(UUL, ULL));
+	hits += and(TEX( 2.,-2.).xy, or(UUR, URR));
+	hits += and(TEX(-2., 2.).xy, or(DDL, DLL));
+	hits += and(TEX( 2., 2.).xy, or(DDR, DRR));
+
+	hits += (ULL + URR + DRR + DLL + L2 + R2) + vec2(0.0, 1.0) * (C + U1 + U2 + D1 + D2 + L1 + R1 + UL + UR + DL + DR + UUL + UUR + DDR + DDL);
+
+   FragColor = vec4(C * sigmoid(hits), C);
+}
+#endif
diff --git a/base/dithering/shaders/mdapt/passes/mdapt-pass3.glsl b/base/dithering/shaders/mdapt/passes/mdapt-pass3.glsl
new file mode 100644
index 0000000..64e2f36
--- /dev/null
+++ b/base/dithering/shaders/mdapt/passes/mdapt-pass3.glsl
@@ -0,0 +1,145 @@
+/*
+   Merge Dithering and Pseudo Transparency Shader v2.8 - Pass 3
+   by Sp00kyFox, 2014
+
+   Backpropagation and checkerboard smoothing.
+
+*/
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying
+#define COMPAT_ATTRIBUTE attribute
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+vec4 _oPosition1;
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+// compatibility #defines
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+uniform sampler2D OrigTexture;
+#define Original OrigTexture
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+#define TEX(dx,dy)   COMPAT_TEXTURE(Source, vTexCoord+vec2((dx),(dy))*SourceSize.zw)
+#define TEXt0(dx,dy) COMPAT_TEXTURE(Original, vTexCoord+vec2((dx),(dy))*SourceSize.zw)
+
+bool eq(vec3 A, vec3 B){
+	return (A == B);
+}
+
+float and(float a, float b){
+	return min(a,b);
+}
+
+float or(float a, float b, float c, float d, float e, float f, float g, float h, float i){
+	return max(a, max(b, max(c, max(d, max(e, max(f, max(g, max(h,i))))))));
+}
+
+vec2 and(vec2 a, vec2 b){
+	return min(a,b);
+}
+
+vec2 or(vec2 a, vec2 b){
+	return max(a,b);
+}
+
+vec2 or(vec2 a, vec2 b, vec2 c, vec2 d){
+	return max(a, max(b, max(c,d)));
+}
+
+void main()
+{
+	/*
+		UL U UR
+		L  C R
+		DL D DR
+	*/
+
+	vec4 C  = TEX( 0., 0.);		vec3 c  = TEXt0( 0., 0.).xyz;
+	vec2 L  = TEX(-1., 0.).xy;	vec3 l  = TEXt0(-1., 0.).xyz;
+	vec2 R  = TEX( 1., 0.).xy;	vec3 r  = TEXt0( 1., 0.).xyz;
+	vec2 U  = TEX( 0.,-1.).xy;	vec3 u  = TEXt0( 0.,-1.).xyz;
+	vec2 D  = TEX( 0., 1.).xy;	vec3 d  = TEXt0( 0., 1.).xyz;
+	float UL = TEX(-1.,-1.).y;	vec3 ul = TEXt0(-1.,-1.).xyz;
+	float UR = TEX( 1.,-1.).y;	vec3 ur = TEXt0( 1.,-1.).xyz;
+	float DL = TEX(-1., 1.).y;	vec3 dl = TEXt0(-1., 1.).xyz;
+	float DR = TEX( 1., 1.).y;	vec3 dr = TEXt0( 1., 1.).xyz;
+
+	// Backpropagation
+	C.xy = or(C.xy, and(C.zw, or(L, R, U, D)));
+
+	// Checkerboard Smoothing
+	C.y = or(C.y, min(U.y, float(eq(c,u))), min(D.y, float(eq(c,d))), min(L.y, float(eq(c,l))), min(R.y, float(eq(c,r))), min(UL, float(eq(c,ul))), min(UR, float(eq(c,ur))), min(DL, float(eq(c,dl))), min(DR, float(eq(c,dr))));
+
+   FragColor = vec4(C);
+}
+#endif
diff --git a/base/dithering/shaders/mdapt/passes/mdapt-pass4.glsl b/base/dithering/shaders/mdapt/passes/mdapt-pass4.glsl
new file mode 100644
index 0000000..9dbe2cb
--- /dev/null
+++ b/base/dithering/shaders/mdapt/passes/mdapt-pass4.glsl
@@ -0,0 +1,224 @@
+/*
+   Merge Dithering and Pseudo Transparency Shader v2.8 - Pass 4
+   by Sp00kyFox, 2014
+
+   Blends pixels based on detected dithering patterns.
+
+*/
+
+// Parameter lines go here:
+#pragma parameter VL    "MDAPT Vertical Lines"	0.0 0.0 1.0 1.0
+#pragma parameter CB    "MDAPT Checkerboard"	1.0 0.0 1.0 1.0
+#pragma parameter DEBUG "MDAPT Adjust View"	0.0 0.0 1.0 1.0
+#pragma parameter linear_gamma "MDAPT Linear Gamma Blend"	0.0 0.0 1.0 1.0
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING out
+#define COMPAT_ATTRIBUTE in
+#define COMPAT_TEXTURE texture
+#else
+#define COMPAT_VARYING varying
+#define COMPAT_ATTRIBUTE attribute
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+COMPAT_ATTRIBUTE vec4 VertexCoord;
+COMPAT_ATTRIBUTE vec4 COLOR;
+COMPAT_ATTRIBUTE vec4 TexCoord;
+COMPAT_VARYING vec4 COL0;
+COMPAT_VARYING vec4 TEX0;
+
+vec4 _oPosition1;
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+// compatibility #defines
+#define vTexCoord TEX0.xy
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    TEX0.xy = TexCoord.xy;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define COMPAT_VARYING in
+#define COMPAT_TEXTURE texture
+out vec4 FragColor;
+#else
+#define COMPAT_VARYING varying
+#define FragColor gl_FragColor
+#define COMPAT_TEXTURE texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D Texture;
+uniform sampler2D OrigTexture;
+#define Original OrigTexture
+COMPAT_VARYING vec4 TEX0;
+
+// compatibility #defines
+#define Source Texture
+#define vTexCoord TEX0.xy
+
+#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize
+#define OutSize vec4(OutputSize, 1.0 / OutputSize)
+
+#ifdef PARAMETER_UNIFORM
+uniform COMPAT_PRECISION float VL;
+uniform COMPAT_PRECISION float CB;
+uniform COMPAT_PRECISION float DEBUG;
+uniform COMPAT_PRECISION float linear_gamma;
+#else
+#define VL 0.0
+#define CB 1.0
+#define DEBUG 0.0
+#define linear_gamma 0.0
+#endif
+
+//#define TEX(dx,dy)   COMPAT_TEXTURE(Source, vTexCoord+vec2((dx),(dy))*SourceSize.zw)
+//#define TEXt0(dx,dy) COMPAT_TEXTURE(Original, vTexCoord+vec2((dx),(dy))*SourceSize.zw)
+
+vec4 TEX(float dx, float dy){
+	if(linear_gamma > 0.5) return pow(COMPAT_TEXTURE(Source, vTexCoord+vec2((dx),(dy))*SourceSize.zw), vec4(2.2));
+	else return COMPAT_TEXTURE(Source, vTexCoord+vec2((dx),(dy))*SourceSize.zw);
+}
+
+vec4 TEXt0(float dx, float dy){
+	if(linear_gamma > 0.5) return pow(COMPAT_TEXTURE(Original, vTexCoord+vec2((dx),(dy))*SourceSize.zw), vec4(2.2));
+	else return COMPAT_TEXTURE(Original, vTexCoord+vec2((dx),(dy))*SourceSize.zw);
+}
+
+bool eq(vec3 A, vec3 B){
+	return (A == B);
+}
+
+float and(float a, float b){
+	return min(a,b);
+}
+
+float or(float a, float b){
+	return max(a,b);
+}
+
+float or(float a, float b, float c, float d, float e, float f, float g, float h, float i){
+	return max(a, max(b, max(c, max(d, max(e, max(f, max(g, max(h,i))))))));
+}
+
+vec2 and(vec2 a, vec2 b){
+	return min(a,b);
+}
+
+vec2 or(vec2 a, vec2 b){
+	return max(a,b);
+}
+
+vec2 or(vec2 a, vec2 b, vec2 c, vec2 d){
+	return max(a, max(b, max(c,d)));
+}
+
+void main()
+{
+	/*
+		UL U UR
+		L  C R
+		DL D DR
+	*/
+
+	vec4 C = TEX( 0., 0.);		vec3 c = TEXt0( 0., 0.).xyz;
+	vec2 L = TEX(-1., 0.).xy;	vec3 l = TEXt0(-1., 0.).xyz;
+	vec2 R = TEX( 1., 0.).xy;	vec3 r = TEXt0( 1., 0.).xyz;
+	vec2 U = TEX( 0.,-1.).xy;
+	vec2 D = TEX( 0., 1.).xy;
+
+	float  prVL = 0.0,		prCB = 0.0;
+	vec3 fVL  = vec3(0.0),	fCB  = vec3(0.0);
+
+
+	// Backpropagation
+	C.xy = or(C.xy, and(C.zw, or(L.xy, R.xy, U.xy, D.xy)));
+
+
+	if(VL > 0.5){
+		float prSum = L.x + R.x;
+
+		prVL = max(L.x, R.x);
+		prVL = (prVL == 0.0) ? 1.0 : prSum/prVL;
+
+		fVL  = (prVL*c + L.x*l + R.x*r)/(prVL + prSum);
+		prVL = C.x;
+	}
+
+
+	if(CB > 0.5){
+		vec3 u = TEXt0( 0.,-1.).xyz;
+		vec3 d = TEXt0( 0., 1.).xyz;
+
+		float eqCL = float(eq(c,l));
+		float eqCR = float(eq(c,r));
+		float eqCU = float(eq(c,u));
+		float eqCD = float(eq(c,d));
+
+		float prU = or(U.y, eqCU);
+		float prD = or(D.y, eqCD);
+		float prL = or(L.y, eqCL);
+		float prR = or(R.y, eqCR);
+
+
+		float prSum = prU  + prD  + prL  + prR;
+
+		prCB = max(prL, max(prR, max(prU,prD)));
+		prCB = (prCB == 0.0) ? 1.0 : prSum/prCB;
+
+		//standard formula: C/2 + (L + R + D + U)/8
+		fCB = (prCB*c + prU*u + prD*d + prL*l + prR*r)/(prCB + prSum);
+
+
+		float UL = TEX(-1.,-1.).y;	vec3 ul = TEXt0(-1.,-1.).xyz;
+		float UR = TEX( 1.,-1.).y;	vec3 ur = TEXt0( 1.,-1.).xyz;
+		float DL = TEX(-1., 1.).y;	vec3 dl = TEXt0(-1., 1.).xyz;
+		float DR = TEX( 1., 1.).y;	vec3 dr = TEXt0( 1., 1.).xyz;
+
+		// Checkerboard Smoothing
+		prCB = or(C.y, and(L.y, eqCL), and(R.y, eqCR), and(U.y, eqCU), and(D.y, eqCD), and(UL, float(eq(c,ul))), and(UR, float(eq(c,ur))), and(DL, float(eq(c,dl))), and(DR, float(eq(c,dr))));
+	}
+
+
+	if(DEBUG > 0.5)
+		FragColor = vec4(prVL, prCB, 0.0, 0.0);
+
+	vec4 final = (prCB >= prVL) ? vec4(mix(c, fCB, prCB), 1.0) : vec4(mix(c, fVL, prVL), 1.0);
+	FragColor = (linear_gamma > 0.5) ? pow(final, vec4(1.0 / 2.2)) : final;
+}
+#endif
diff --git a/base/dithering/shaders/sgenpt-mix.glsl b/base/dithering/shaders/sgenpt-mix.glsl
new file mode 100644
index 0000000..22ea67d
--- /dev/null
+++ b/base/dithering/shaders/sgenpt-mix.glsl
@@ -0,0 +1,210 @@
+/*
+   SGENPT-MIX - Sega Genesis Pseudo Transparency Mixer Shader - v8b
+   
+   2011-2020 Hyllian - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is 
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+
+*/
+
+#pragma parameter SGPT_BLEND_OPTION "0.OFF | 1.VL | 2.CB | 3.CB-S | 4.Both | 5.Both2 | 6.Both-S" 4.0 0.0 6.0 1.0
+#pragma parameter SGPT_BLEND_LEVEL "SGENPT-MIX Both Blend Level" 1.0 0.0 1.0 0.1
+#pragma parameter SGPT_ADJUST_VIEW "SGENPT-MIX Adjust View" 0.0 0.0 1.0 1.0
+#pragma parameter SGPT_LINEAR_GAMMA "SGENPT-MIX Use Linear Gamma" 1.0 0.0 1.0 1.0
+
+
+#define texCoord TEX0
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define OUT out
+#define IN  in
+#define tex2D texture
+#else
+#define OUT varying
+#define IN attribute
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+
+IN  vec4 VertexCoord;
+IN  vec4 Color;
+IN  vec2 TexCoord;
+OUT vec4 color;
+OUT vec2 texCoord;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int  FrameDirection;
+uniform COMPAT_PRECISION int  FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    color = Color;
+    texCoord = TexCoord;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define IN in
+#define tex2D texture
+out vec4 FragColor;
+#else
+#define IN varying
+#define FragColor gl_FragColor
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D s_p;
+IN vec2 texCoord;
+
+#ifdef PARAMETER_UNIFORM
+uniform COMPAT_PRECISION float SGPT_BLEND_OPTION;
+uniform COMPAT_PRECISION float SGPT_BLEND_LEVEL;
+uniform COMPAT_PRECISION float SGPT_ADJUST_VIEW;
+uniform COMPAT_PRECISION float SGPT_LINEAR_GAMMA;
+#else
+#define SGPT_BLEND_OPTION 4.0
+#define SGPT_BLEND_LEVEL 1.0
+#define SGPT_ADJUST_VIEW 0.0
+#define SGPT_LINEAR_GAMMA 1.0
+#endif
+
+
+#define GAMMA_EXP		(SGPT_LINEAR_GAMMA+1.0)
+#define GAMMA_IN(color)		pow(color, vec3(GAMMA_EXP, GAMMA_EXP, GAMMA_EXP))
+#define GAMMA_OUT(color)	pow(color, vec3(1.0 / GAMMA_EXP, 1.0 / GAMMA_EXP, 1.0 / GAMMA_EXP))
+
+
+const vec3 Y = vec3(.2126, .7152, .0722);
+
+vec3 min_s(vec3 central, vec3 adj1, vec3 adj2) {return min(central, max(adj1, adj2));}
+vec3 max_s(vec3 central, vec3 adj1, vec3 adj2) {return max(central, min(adj1, adj2));}
+
+
+void main()
+{
+	vec2 dx = vec2(1.0, 0.0)/TextureSize;
+	vec2 dy = vec2(0.0, 1.0)/TextureSize;
+
+	// Reading the texels.
+	vec3 C = GAMMA_IN(tex2D(s_p, texCoord    ).xyz);
+	vec3 L = GAMMA_IN(tex2D(s_p, texCoord -dx).xyz);
+	vec3 R = GAMMA_IN(tex2D(s_p, texCoord +dx).xyz);
+	vec3 U = GAMMA_IN(tex2D(s_p, texCoord -dy).xyz);
+	vec3 D = GAMMA_IN(tex2D(s_p, texCoord +dy).xyz);
+	vec3 UL = GAMMA_IN(tex2D(s_p, texCoord -dx -dy).xyz);
+	vec3 UR = GAMMA_IN(tex2D(s_p, texCoord +dx -dy).xyz);
+	vec3 DL = GAMMA_IN(tex2D(s_p, texCoord -dx +dy).xyz);
+	vec3 DR = GAMMA_IN(tex2D(s_p, texCoord +dx +dy).xyz);
+
+	vec3 color = C;
+
+	//  Get min/max samples
+	vec3 min_sample = min_s(C, L, R);
+	vec3 max_sample = max_s(C, L, R);
+
+	float diff = dot(max(max(C, L), max(C, R)) - min(min(C, L), min(C, R)), Y);
+
+	if (int(SGPT_BLEND_OPTION) == 1) // Only Vertical Lines
+	{
+		min_sample = max_s(min_sample, min_s(C, DL, DR), min_s(C, UL, UR));
+		max_sample = min_s(max_sample, max_s(C, DL, DR), max_s(C, UL, UR));
+
+		diff *= (1.0 - SGPT_BLEND_LEVEL);
+
+		color = 0.5*( 1.0 + diff )*C + 0.25*( 1.0 - diff )*(L + R);
+	}
+	else if (int(SGPT_BLEND_OPTION) == 2) // Only Checkerboard
+	{
+		min_sample = max(min_sample, min_s(C, U, D));
+		max_sample = min(max_sample, max_s(C, U, D));
+
+		diff *= (1.0 - SGPT_BLEND_LEVEL);
+
+		color = 0.5*( 1.0 + diff )*C + 0.125*( 1.0 - diff )*(L + R + U + D);
+	}
+	else if (int(SGPT_BLEND_OPTION) == 3) // Only Checkerboard - Soft
+	{
+		min_sample = min_s(min_sample, U, D);
+		max_sample = max_s(max_sample, U, D);
+
+		diff *= (1.0 - SGPT_BLEND_LEVEL);
+
+		color = 0.5*( 1.0 + diff )*C + 0.125*( 1.0 - diff )*(L + R + U + D);
+	}
+	else if (int(SGPT_BLEND_OPTION) == 4) // VL-CB
+	{
+		diff *= (1.0 - SGPT_BLEND_LEVEL);
+
+		color = 0.5*( 1.0 + diff )*C + 0.25*( 1.0 - diff )*(L + R);
+	}
+	else if (int(SGPT_BLEND_OPTION) == 5) // VL-CB-2
+	{
+		min_sample = min_s(min_sample, U, D);
+		max_sample = max_s(max_sample, U, D);
+
+		diff *= (1.0 - SGPT_BLEND_LEVEL);
+
+		color = 0.5*( 1.0 + diff )*C + 0.25*( 1.0 - diff )*(L + R);
+	}
+	else if (int(SGPT_BLEND_OPTION) == 6) // VL-CB-Soft
+	{
+		min_sample = min(min_sample, min(min_s(D, DL, DR), min_s(U, UL, UR)));
+		max_sample = max(max_sample, max(max_s(D, DL, DR), max_s(U, UL, UR)));
+
+		diff *= (1.0 - SGPT_BLEND_LEVEL);
+
+		color = 0.5*( 1.0 + diff )*C + 0.25*( 1.0 - diff )*(L + R);
+	}
+
+	color = clamp(color, min_sample, max_sample);
+
+	color = mix(color, vec3(dot(abs(C-color), vec3(1.0, 1.0, 1.0))), SGPT_ADJUST_VIEW);
+
+	FragColor.xyz = GAMMA_OUT(color);
+}
+#endif
diff --git a/base/windowed/jinc2-params.glslp b/base/windowed/jinc2-params.glslp
new file mode 100644
index 0000000..6e252db
--- /dev/null
+++ b/base/windowed/jinc2-params.glslp
@@ -0,0 +1,4 @@
+shaders = 1
+
+shader0 = shaders/jinc2-params.glsl
+filter_linear0 = false
diff --git a/base/windowed/jinc2-sharp.glslp b/base/windowed/jinc2-sharp.glslp
new file mode 100644
index 0000000..3dd9834
--- /dev/null
+++ b/base/windowed/jinc2-sharp.glslp
@@ -0,0 +1,4 @@
+shaders = 1
+
+shader0 = shaders/jinc2-sharp.glsl
+filter_linear0 = false
diff --git a/base/windowed/jinc2-sharper.glslp b/base/windowed/jinc2-sharper.glslp
new file mode 100644
index 0000000..3ec6f0d
--- /dev/null
+++ b/base/windowed/jinc2-sharper.glslp
@@ -0,0 +1,4 @@
+shaders = 1
+
+shader0 = shaders/jinc2-sharper.glsl
+filter_linear0 = false
diff --git a/base/windowed/jinc2.glslp b/base/windowed/jinc2.glslp
new file mode 100644
index 0000000..987b422
--- /dev/null
+++ b/base/windowed/jinc2.glslp
@@ -0,0 +1,4 @@
+shaders = 1
+
+shader0 = shaders/jinc2.glsl
+filter_linear0 = false
diff --git a/base/windowed/lanczos2-sharp.glslp b/base/windowed/lanczos2-sharp.glslp
new file mode 100644
index 0000000..629cbc3
--- /dev/null
+++ b/base/windowed/lanczos2-sharp.glslp
@@ -0,0 +1,4 @@
+shaders = 1
+
+shader0 = shaders/lanczos2-sharp.glsl
+filter_linear0 = false
diff --git a/base/windowed/shaders/jinc2-params.glsl b/base/windowed/shaders/jinc2-params.glsl
new file mode 100644
index 0000000..b86ff8d
--- /dev/null
+++ b/base/windowed/shaders/jinc2-params.glsl
@@ -0,0 +1,216 @@
+/*
+   Hyllian's jinc windowed-jinc 2-lobe sharper with anti-ringing Shader
+   
+   Copyright (C) 2011-2016 Hyllian/Jararaca - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+
+*/
+
+#pragma parameter JINC2_WINDOW_SINC "Window Sinc Param" 0.44 0.0 1.0 0.01
+#pragma parameter JINC2_SINC "Sinc Param" 0.82 0.0 1.0 0.01
+#pragma parameter JINC2_AR_STRENGTH "Anti-ringing Strength" 0.5 0.0 1.0 0.1
+
+#define texCoord TEX0
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define OUT out
+#define IN  in
+#define tex2D texture
+#else
+#define OUT varying
+#define IN attribute
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+
+IN  vec4 VertexCoord;
+IN  vec4 Color;
+IN  vec2 TexCoord;
+OUT vec4 color;
+OUT vec2 texCoord;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int  FrameDirection;
+uniform COMPAT_PRECISION int  FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    color = Color;
+    texCoord = TexCoord * 1.0001;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define IN in
+#define tex2D texture
+out vec4 FragColor;
+#else
+#define IN varying
+#define FragColor gl_FragColor
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D s_p;
+IN vec2 texCoord;
+
+#ifdef PARAMETER_UNIFORM
+uniform COMPAT_PRECISION float JINC2_WINDOW_SINC;
+uniform COMPAT_PRECISION float JINC2_SINC;
+uniform COMPAT_PRECISION float JINC2_AR_STRENGTH;
+#else
+#define JINC2_WINDOW_SINC 0.44
+#define JINC2_SINC 0.82
+#define JINC2_AR_STRENGTH 0.5
+#endif
+
+#define halfpi  1.5707963267948966192313216916398
+#define pi      3.1415926535897932384626433832795
+#define wa      (JINC2_WINDOW_SINC*pi)
+#define wb      (JINC2_SINC*pi)
+
+
+// Calculates the distance between two points
+float d(vec2 pt1, vec2 pt2)
+{
+  vec2 v = pt2 - pt1;
+  return sqrt(dot(v,v));
+}
+
+vec3 min4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return min(a, min(b, min(c, d)));
+}
+
+vec3 max4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return max(a, max(b, max(c, d)));
+}
+
+vec4 resampler(vec4 x)
+{
+   vec4 res;
+
+    res.x = (x.x==0.0) ?  wa*wb  :  sin(x.x*wa)*sin(x.x*wb)/(x.x*x.x);
+    res.y = (x.y==0.0) ?  wa*wb  :  sin(x.y*wa)*sin(x.y*wb)/(x.y*x.y);
+    res.z = (x.z==0.0) ?  wa*wb  :  sin(x.z*wa)*sin(x.z*wb)/(x.z*x.z);
+    res.w = (x.w==0.0) ?  wa*wb  :  sin(x.w*wa)*sin(x.w*wb)/(x.w*x.w);
+
+   return res;
+}
+
+void main()
+{
+
+    vec3 color;
+    vec4 weights[4];
+
+    vec2 dx = vec2(1.0, 0.0);
+    vec2 dy = vec2(0.0, 1.0);
+
+    vec2 pc = texCoord*TextureSize;
+
+    vec2 tc = (floor(pc-vec2(0.5,0.5))+vec2(0.5,0.5));
+     
+    weights[0] = resampler(vec4(d(pc, tc    -dx    -dy), d(pc, tc           -dy), d(pc, tc    +dx    -dy), d(pc, tc+2.0*dx    -dy)));
+    weights[1] = resampler(vec4(d(pc, tc    -dx       ), d(pc, tc              ), d(pc, tc    +dx       ), d(pc, tc+2.0*dx       )));
+    weights[2] = resampler(vec4(d(pc, tc    -dx    +dy), d(pc, tc           +dy), d(pc, tc    +dx    +dy), d(pc, tc+2.0*dx    +dy)));
+    weights[3] = resampler(vec4(d(pc, tc    -dx+2.0*dy), d(pc, tc       +2.0*dy), d(pc, tc    +dx+2.0*dy), d(pc, tc+2.0*dx+2.0*dy)));
+
+    dx = dx/TextureSize;
+    dy = dy/TextureSize;
+    tc = tc/TextureSize;
+
+    vec3 c00 = tex2D(s_p, tc    -dx    -dy).xyz;
+    vec3 c10 = tex2D(s_p, tc           -dy).xyz;
+    vec3 c20 = tex2D(s_p, tc    +dx    -dy).xyz;
+    vec3 c30 = tex2D(s_p, tc+2.0*dx    -dy).xyz;
+    vec3 c01 = tex2D(s_p, tc    -dx       ).xyz;
+    vec3 c11 = tex2D(s_p, tc              ).xyz;
+    vec3 c21 = tex2D(s_p, tc    +dx       ).xyz;
+    vec3 c31 = tex2D(s_p, tc+2.0*dx       ).xyz;
+    vec3 c02 = tex2D(s_p, tc    -dx    +dy).xyz;
+    vec3 c12 = tex2D(s_p, tc           +dy).xyz;
+    vec3 c22 = tex2D(s_p, tc    +dx    +dy).xyz;
+    vec3 c32 = tex2D(s_p, tc+2.0*dx    +dy).xyz;
+    vec3 c03 = tex2D(s_p, tc    -dx+2.0*dy).xyz;
+    vec3 c13 = tex2D(s_p, tc       +2.0*dy).xyz;
+    vec3 c23 = tex2D(s_p, tc    +dx+2.0*dy).xyz;
+    vec3 c33 = tex2D(s_p, tc+2.0*dx+2.0*dy).xyz;
+
+    color = tex2D(s_p, texCoord).xyz;
+
+    //  Get min/max samples
+    vec3 min_sample = min4(c11, c21, c12, c22);
+    vec3 max_sample = max4(c11, c21, c12, c22);
+/*
+      color = mat4x3(c00, c10, c20, c30) * weights[0];
+      color+= mat4x3(c01, c11, c21, c31) * weights[1];
+      color+= mat4x3(c02, c12, c22, c32) * weights[2];
+      color+= mat4x3(c03, c13, c23, c33) * weights[3];
+      mat4 wgts = mat4(weights[0], weights[1], weights[2], weights[3]);
+      vec4 wsum = wgts * vec4(1.0,1.0,1.0,1.0);
+      color = color/(dot(wsum, vec4(1.0,1.0,1.0,1.0)));
+*/
+
+
+    color = vec3(dot(weights[0], vec4(c00.x, c10.x, c20.x, c30.x)), dot(weights[0], vec4(c00.y, c10.y, c20.y, c30.y)), dot(weights[0], vec4(c00.z, c10.z, c20.z, c30.z)));
+    color+= vec3(dot(weights[1], vec4(c01.x, c11.x, c21.x, c31.x)), dot(weights[1], vec4(c01.y, c11.y, c21.y, c31.y)), dot(weights[1], vec4(c01.z, c11.z, c21.z, c31.z)));
+    color+= vec3(dot(weights[2], vec4(c02.x, c12.x, c22.x, c32.x)), dot(weights[2], vec4(c02.y, c12.y, c22.y, c32.y)), dot(weights[2], vec4(c02.z, c12.z, c22.z, c32.z)));
+    color+= vec3(dot(weights[3], vec4(c03.x, c13.x, c23.x, c33.x)), dot(weights[3], vec4(c03.y, c13.y, c23.y, c33.y)), dot(weights[3], vec4(c03.z, c13.z, c23.z, c33.z)));
+    color = color/(dot(weights[0], vec4(1,1,1,1)) + dot(weights[1], vec4(1,1,1,1)) + dot(weights[2], vec4(1,1,1,1)) + dot(weights[3], vec4(1,1,1,1)));
+
+    // Anti-ringing
+    vec3 aux = color;
+    color = clamp(color, min_sample, max_sample);
+    color = mix(aux, color, JINC2_AR_STRENGTH);
+
+    // final sum and weight normalization
+    FragColor.xyz = color;
+}
+#endif
diff --git a/base/windowed/shaders/jinc2-sharp.glsl b/base/windowed/shaders/jinc2-sharp.glsl
new file mode 100644
index 0000000..bed1866
--- /dev/null
+++ b/base/windowed/shaders/jinc2-sharp.glsl
@@ -0,0 +1,204 @@
+/*
+   Hyllian's jinc windowed-jinc 2-lobe sharper with anti-ringing Shader
+   
+   Copyright (C) 2011-2016 Hyllian/Jararaca - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+
+*/
+
+#define JINC2_WINDOW_SINC 0.39
+#define JINC2_SINC 0.82
+#define JINC2_AR_STRENGTH 0.8
+
+#define texCoord TEX0
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define OUT out
+#define IN  in
+#define tex2D texture
+#else
+#define OUT varying
+#define IN attribute
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+IN  vec4 VertexCoord;
+IN  vec4 Color;
+IN  vec2 TexCoord;
+OUT vec4 color;
+OUT vec2 texCoord;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int  FrameDirection;
+uniform COMPAT_PRECISION int  FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    color = Color;
+    texCoord = TexCoord * 1.0001;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define IN in
+#define tex2D texture
+out vec4 FragColor;
+#else
+#define IN varying
+#define FragColor gl_FragColor
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define PRECISION mediump
+#else
+#define PRECISION
+#endif
+
+uniform PRECISION int FrameDirection;
+uniform PRECISION int FrameCount;
+uniform PRECISION vec2 OutputSize;
+uniform PRECISION vec2 TextureSize;
+uniform PRECISION vec2 InputSize;
+uniform sampler2D s_p;
+IN vec2 texCoord;
+
+const   float halfpi            = 1.5707963267948966192313216916398;
+const   float pi                = 3.1415926535897932384626433832795;
+const   float wa                = JINC2_WINDOW_SINC*pi;
+const   float wb                = JINC2_SINC*pi;
+
+// Calculates the distance between two points
+float d(vec2 pt1, vec2 pt2)
+{
+  vec2 v = pt2 - pt1;
+  return sqrt(dot(v,v));
+}
+
+vec3 min4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return min(a, min(b, min(c, d)));
+}
+
+vec3 max4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return max(a, max(b, max(c, d)));
+}
+
+vec4 resampler(vec4 x)
+{
+   vec4 res;
+
+    res.x = (x.x==0.0) ?  wa*wb  :  sin(x.x*wa)*sin(x.x*wb)/(x.x*x.x);
+    res.y = (x.y==0.0) ?  wa*wb  :  sin(x.y*wa)*sin(x.y*wb)/(x.y*x.y);
+    res.z = (x.z==0.0) ?  wa*wb  :  sin(x.z*wa)*sin(x.z*wb)/(x.z*x.z);
+    res.w = (x.w==0.0) ?  wa*wb  :  sin(x.w*wa)*sin(x.w*wb)/(x.w*x.w);
+
+   return res;
+}
+
+void main()
+{
+
+    vec3 color;
+    vec4 weights[4];
+
+    vec2 dx = vec2(1.0, 0.0);
+    vec2 dy = vec2(0.0, 1.0);
+
+    vec2 pc = texCoord*TextureSize;
+
+    vec2 tc = (floor(pc-vec2(0.5,0.5))+vec2(0.5,0.5));
+     
+    weights[0] = resampler(vec4(d(pc, tc    -dx    -dy), d(pc, tc           -dy), d(pc, tc    +dx    -dy), d(pc, tc+2.0*dx    -dy)));
+    weights[1] = resampler(vec4(d(pc, tc    -dx       ), d(pc, tc              ), d(pc, tc    +dx       ), d(pc, tc+2.0*dx       )));
+    weights[2] = resampler(vec4(d(pc, tc    -dx    +dy), d(pc, tc           +dy), d(pc, tc    +dx    +dy), d(pc, tc+2.0*dx    +dy)));
+    weights[3] = resampler(vec4(d(pc, tc    -dx+2.0*dy), d(pc, tc       +2.0*dy), d(pc, tc    +dx+2.0*dy), d(pc, tc+2.0*dx+2.0*dy)));
+
+    dx = dx/TextureSize;
+    dy = dy/TextureSize;
+    tc = tc/TextureSize;
+
+    vec3 c00 = tex2D(s_p, tc    -dx    -dy).xyz;
+    vec3 c10 = tex2D(s_p, tc           -dy).xyz;
+    vec3 c20 = tex2D(s_p, tc    +dx    -dy).xyz;
+    vec3 c30 = tex2D(s_p, tc+2.0*dx    -dy).xyz;
+    vec3 c01 = tex2D(s_p, tc    -dx       ).xyz;
+    vec3 c11 = tex2D(s_p, tc              ).xyz;
+    vec3 c21 = tex2D(s_p, tc    +dx       ).xyz;
+    vec3 c31 = tex2D(s_p, tc+2.0*dx       ).xyz;
+    vec3 c02 = tex2D(s_p, tc    -dx    +dy).xyz;
+    vec3 c12 = tex2D(s_p, tc           +dy).xyz;
+    vec3 c22 = tex2D(s_p, tc    +dx    +dy).xyz;
+    vec3 c32 = tex2D(s_p, tc+2.0*dx    +dy).xyz;
+    vec3 c03 = tex2D(s_p, tc    -dx+2.0*dy).xyz;
+    vec3 c13 = tex2D(s_p, tc       +2.0*dy).xyz;
+    vec3 c23 = tex2D(s_p, tc    +dx+2.0*dy).xyz;
+    vec3 c33 = tex2D(s_p, tc+2.0*dx+2.0*dy).xyz;
+
+    color = tex2D(s_p, texCoord).xyz;
+
+    //  Get min/max samples
+    vec3 min_sample = min4(c11, c21, c12, c22);
+    vec3 max_sample = max4(c11, c21, c12, c22);
+/*
+      color = mat4x3(c00, c10, c20, c30) * weights[0];
+      color+= mat4x3(c01, c11, c21, c31) * weights[1];
+      color+= mat4x3(c02, c12, c22, c32) * weights[2];
+      color+= mat4x3(c03, c13, c23, c33) * weights[3];
+      mat4 wgts = mat4(weights[0], weights[1], weights[2], weights[3]);
+      vec4 wsum = wgts * vec4(1.0,1.0,1.0,1.0);
+      color = color/(dot(wsum, vec4(1.0,1.0,1.0,1.0)));
+*/
+
+
+    color = vec3(dot(weights[0], vec4(c00.x, c10.x, c20.x, c30.x)), dot(weights[0], vec4(c00.y, c10.y, c20.y, c30.y)), dot(weights[0], vec4(c00.z, c10.z, c20.z, c30.z)));
+    color+= vec3(dot(weights[1], vec4(c01.x, c11.x, c21.x, c31.x)), dot(weights[1], vec4(c01.y, c11.y, c21.y, c31.y)), dot(weights[1], vec4(c01.z, c11.z, c21.z, c31.z)));
+    color+= vec3(dot(weights[2], vec4(c02.x, c12.x, c22.x, c32.x)), dot(weights[2], vec4(c02.y, c12.y, c22.y, c32.y)), dot(weights[2], vec4(c02.z, c12.z, c22.z, c32.z)));
+    color+= vec3(dot(weights[3], vec4(c03.x, c13.x, c23.x, c33.x)), dot(weights[3], vec4(c03.y, c13.y, c23.y, c33.y)), dot(weights[3], vec4(c03.z, c13.z, c23.z, c33.z)));
+    color = color/(dot(weights[0], vec4(1,1,1,1)) + dot(weights[1], vec4(1,1,1,1)) + dot(weights[2], vec4(1,1,1,1)) + dot(weights[3], vec4(1,1,1,1)));
+
+    // Anti-ringing
+    vec3 aux = color;
+    color = clamp(color, min_sample, max_sample);
+    color = mix(aux, color, JINC2_AR_STRENGTH);
+
+    // final sum and weight normalization
+    FragColor.xyz = color;
+}
+#endif
diff --git a/base/windowed/shaders/jinc2-sharper.glsl b/base/windowed/shaders/jinc2-sharper.glsl
new file mode 100644
index 0000000..4d25a54
--- /dev/null
+++ b/base/windowed/shaders/jinc2-sharper.glsl
@@ -0,0 +1,204 @@
+/*
+   Hyllian's jinc windowed-jinc 2-lobe sharper with anti-ringing Shader
+   
+   Copyright (C) 2011-2016 Hyllian/Jararaca - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+
+*/
+
+#define JINC2_WINDOW_SINC 0.42
+#define JINC2_SINC 0.92
+#define JINC2_AR_STRENGTH 0.8
+
+#define texCoord TEX0
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define OUT out
+#define IN  in
+#define tex2D texture
+#else
+#define OUT varying
+#define IN attribute
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+IN  vec4 VertexCoord;
+IN  vec4 Color;
+IN  vec2 TexCoord;
+OUT vec4 color;
+OUT vec2 texCoord;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int  FrameDirection;
+uniform COMPAT_PRECISION int  FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    color = Color;
+    texCoord = TexCoord * 1.0001;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define IN in
+#define tex2D texture
+out vec4 FragColor;
+#else
+#define IN varying
+#define FragColor gl_FragColor
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D s_p;
+IN vec2 texCoord;
+
+const   float halfpi            = 1.5707963267948966192313216916398;
+const   float pi                = 3.1415926535897932384626433832795;
+const   float wa                = JINC2_WINDOW_SINC*pi;
+const   float wb                = JINC2_SINC*pi;
+
+// Calculates the distance between two points
+float d(vec2 pt1, vec2 pt2)
+{
+  vec2 v = pt2 - pt1;
+  return sqrt(dot(v,v));
+}
+
+vec3 min4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return min(a, min(b, min(c, d)));
+}
+
+vec3 max4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return max(a, max(b, max(c, d)));
+}
+
+vec4 resampler(vec4 x)
+{
+   vec4 res;
+
+    res.x = (x.x==0.0) ?  wa*wb  :  sin(x.x*wa)*sin(x.x*wb)/(x.x*x.x);
+    res.y = (x.y==0.0) ?  wa*wb  :  sin(x.y*wa)*sin(x.y*wb)/(x.y*x.y);
+    res.z = (x.z==0.0) ?  wa*wb  :  sin(x.z*wa)*sin(x.z*wb)/(x.z*x.z);
+    res.w = (x.w==0.0) ?  wa*wb  :  sin(x.w*wa)*sin(x.w*wb)/(x.w*x.w);
+
+   return res;
+}
+
+void main()
+{
+
+    vec3 color;
+    vec4 weights[4];
+
+    vec2 dx = vec2(1.0, 0.0);
+    vec2 dy = vec2(0.0, 1.0);
+
+    vec2 pc = texCoord*TextureSize;
+
+    vec2 tc = (floor(pc-vec2(0.5,0.5))+vec2(0.5,0.5));
+     
+    weights[0] = resampler(vec4(d(pc, tc    -dx    -dy), d(pc, tc           -dy), d(pc, tc    +dx    -dy), d(pc, tc+2.0*dx    -dy)));
+    weights[1] = resampler(vec4(d(pc, tc    -dx       ), d(pc, tc              ), d(pc, tc    +dx       ), d(pc, tc+2.0*dx       )));
+    weights[2] = resampler(vec4(d(pc, tc    -dx    +dy), d(pc, tc           +dy), d(pc, tc    +dx    +dy), d(pc, tc+2.0*dx    +dy)));
+    weights[3] = resampler(vec4(d(pc, tc    -dx+2.0*dy), d(pc, tc       +2.0*dy), d(pc, tc    +dx+2.0*dy), d(pc, tc+2.0*dx+2.0*dy)));
+
+    dx = dx/TextureSize;
+    dy = dy/TextureSize;
+    tc = tc/TextureSize;
+
+    vec3 c00 = tex2D(s_p, tc    -dx    -dy).xyz;
+    vec3 c10 = tex2D(s_p, tc           -dy).xyz;
+    vec3 c20 = tex2D(s_p, tc    +dx    -dy).xyz;
+    vec3 c30 = tex2D(s_p, tc+2.0*dx    -dy).xyz;
+    vec3 c01 = tex2D(s_p, tc    -dx       ).xyz;
+    vec3 c11 = tex2D(s_p, tc              ).xyz;
+    vec3 c21 = tex2D(s_p, tc    +dx       ).xyz;
+    vec3 c31 = tex2D(s_p, tc+2.0*dx       ).xyz;
+    vec3 c02 = tex2D(s_p, tc    -dx    +dy).xyz;
+    vec3 c12 = tex2D(s_p, tc           +dy).xyz;
+    vec3 c22 = tex2D(s_p, tc    +dx    +dy).xyz;
+    vec3 c32 = tex2D(s_p, tc+2.0*dx    +dy).xyz;
+    vec3 c03 = tex2D(s_p, tc    -dx+2.0*dy).xyz;
+    vec3 c13 = tex2D(s_p, tc       +2.0*dy).xyz;
+    vec3 c23 = tex2D(s_p, tc    +dx+2.0*dy).xyz;
+    vec3 c33 = tex2D(s_p, tc+2.0*dx+2.0*dy).xyz;
+
+    color = tex2D(s_p, texCoord).xyz;
+
+    //  Get min/max samples
+    vec3 min_sample = min4(c11, c21, c12, c22);
+    vec3 max_sample = max4(c11, c21, c12, c22);
+/*
+      color = mat4x3(c00, c10, c20, c30) * weights[0];
+      color+= mat4x3(c01, c11, c21, c31) * weights[1];
+      color+= mat4x3(c02, c12, c22, c32) * weights[2];
+      color+= mat4x3(c03, c13, c23, c33) * weights[3];
+      mat4 wgts = mat4(weights[0], weights[1], weights[2], weights[3]);
+      vec4 wsum = wgts * vec4(1.0,1.0,1.0,1.0);
+      color = color/(dot(wsum, vec4(1.0,1.0,1.0,1.0)));
+*/
+
+
+    color = vec3(dot(weights[0], vec4(c00.x, c10.x, c20.x, c30.x)), dot(weights[0], vec4(c00.y, c10.y, c20.y, c30.y)), dot(weights[0], vec4(c00.z, c10.z, c20.z, c30.z)));
+    color+= vec3(dot(weights[1], vec4(c01.x, c11.x, c21.x, c31.x)), dot(weights[1], vec4(c01.y, c11.y, c21.y, c31.y)), dot(weights[1], vec4(c01.z, c11.z, c21.z, c31.z)));
+    color+= vec3(dot(weights[2], vec4(c02.x, c12.x, c22.x, c32.x)), dot(weights[2], vec4(c02.y, c12.y, c22.y, c32.y)), dot(weights[2], vec4(c02.z, c12.z, c22.z, c32.z)));
+    color+= vec3(dot(weights[3], vec4(c03.x, c13.x, c23.x, c33.x)), dot(weights[3], vec4(c03.y, c13.y, c23.y, c33.y)), dot(weights[3], vec4(c03.z, c13.z, c23.z, c33.z)));
+    color = color/(dot(weights[0], vec4(1,1,1,1)) + dot(weights[1], vec4(1,1,1,1)) + dot(weights[2], vec4(1,1,1,1)) + dot(weights[3], vec4(1,1,1,1)));
+
+    // Anti-ringing
+    vec3 aux = color;
+    color = clamp(color, min_sample, max_sample);
+    color = mix(aux, color, JINC2_AR_STRENGTH);
+
+    // final sum and weight normalization
+    FragColor.xyz = color;
+}
+#endif
diff --git a/base/windowed/shaders/jinc2.glsl b/base/windowed/shaders/jinc2.glsl
new file mode 100644
index 0000000..4376b55
--- /dev/null
+++ b/base/windowed/shaders/jinc2.glsl
@@ -0,0 +1,205 @@
+/*
+   Hyllian's jinc windowed-jinc 2-lobe sharper with anti-ringing Shader
+   
+   Copyright (C) 2011-2016 Hyllian/Jararaca - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+
+*/
+
+#define JINC2_WINDOW_SINC 0.44
+#define JINC2_SINC 0.82
+#define JINC2_AR_STRENGTH 0.8
+
+#define texCoord TEX0
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define OUT out
+#define IN  in
+#define tex2D texture
+#else
+#define OUT varying
+#define IN attribute
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+
+IN  vec4 VertexCoord;
+IN  vec4 Color;
+IN  vec2 TexCoord;
+OUT vec4 color;
+OUT vec2 texCoord;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int  FrameDirection;
+uniform COMPAT_PRECISION int  FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    color = Color;
+    texCoord = TexCoord * 1.0001;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define IN in
+#define tex2D texture
+out vec4 FragColor;
+#else
+#define IN varying
+#define FragColor gl_FragColor
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D s_p;
+IN vec2 texCoord;
+
+const   float halfpi            = 1.5707963267948966192313216916398;
+const   float pi                = 3.1415926535897932384626433832795;
+const   float wa                = JINC2_WINDOW_SINC*pi;
+const   float wb                = JINC2_SINC*pi;
+
+// Calculates the distance between two points
+float d(vec2 pt1, vec2 pt2)
+{
+  vec2 v = pt2 - pt1;
+  return sqrt(dot(v,v));
+}
+
+vec3 min4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return min(a, min(b, min(c, d)));
+}
+
+vec3 max4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return max(a, max(b, max(c, d)));
+}
+
+vec4 resampler(vec4 x)
+{
+   vec4 res;
+
+   res.x = (x.x==0.0) ?  wa*wb  :  sin(x.x*wa)*sin(x.x*wb)/(x.x*x.x);
+   res.y = (x.y==0.0) ?  wa*wb  :  sin(x.y*wa)*sin(x.y*wb)/(x.y*x.y);
+   res.z = (x.z==0.0) ?  wa*wb  :  sin(x.z*wa)*sin(x.z*wb)/(x.z*x.z);
+   res.w = (x.w==0.0) ?  wa*wb  :  sin(x.w*wa)*sin(x.w*wb)/(x.w*x.w);
+
+   return res;
+}
+
+void main()
+{
+
+    vec3 color;
+    vec4 weights[4];
+
+    vec2 dx = vec2(1.0, 0.0);
+    vec2 dy = vec2(0.0, 1.0);
+
+    vec2 pc = texCoord*TextureSize;
+
+    vec2 tc = (floor(pc-vec2(0.5,0.5))+vec2(0.5,0.5));
+     
+    weights[0] = resampler(vec4(d(pc, tc    -dx    -dy), d(pc, tc           -dy), d(pc, tc    +dx    -dy), d(pc, tc+2.0*dx    -dy)));
+    weights[1] = resampler(vec4(d(pc, tc    -dx       ), d(pc, tc              ), d(pc, tc    +dx       ), d(pc, tc+2.0*dx       )));
+    weights[2] = resampler(vec4(d(pc, tc    -dx    +dy), d(pc, tc           +dy), d(pc, tc    +dx    +dy), d(pc, tc+2.0*dx    +dy)));
+    weights[3] = resampler(vec4(d(pc, tc    -dx+2.0*dy), d(pc, tc       +2.0*dy), d(pc, tc    +dx+2.0*dy), d(pc, tc+2.0*dx+2.0*dy)));
+
+    dx = dx/TextureSize;
+    dy = dy/TextureSize;
+    tc = tc/TextureSize;
+
+    vec3 c00 = tex2D(s_p, tc    -dx    -dy).xyz;
+    vec3 c10 = tex2D(s_p, tc           -dy).xyz;
+    vec3 c20 = tex2D(s_p, tc    +dx    -dy).xyz;
+    vec3 c30 = tex2D(s_p, tc+2.0*dx    -dy).xyz;
+    vec3 c01 = tex2D(s_p, tc    -dx       ).xyz;
+    vec3 c11 = tex2D(s_p, tc              ).xyz;
+    vec3 c21 = tex2D(s_p, tc    +dx       ).xyz;
+    vec3 c31 = tex2D(s_p, tc+2.0*dx       ).xyz;
+    vec3 c02 = tex2D(s_p, tc    -dx    +dy).xyz;
+    vec3 c12 = tex2D(s_p, tc           +dy).xyz;
+    vec3 c22 = tex2D(s_p, tc    +dx    +dy).xyz;
+    vec3 c32 = tex2D(s_p, tc+2.0*dx    +dy).xyz;
+    vec3 c03 = tex2D(s_p, tc    -dx+2.0*dy).xyz;
+    vec3 c13 = tex2D(s_p, tc       +2.0*dy).xyz;
+    vec3 c23 = tex2D(s_p, tc    +dx+2.0*dy).xyz;
+    vec3 c33 = tex2D(s_p, tc+2.0*dx+2.0*dy).xyz;
+
+    color = tex2D(s_p, texCoord).xyz;
+
+    //  Get min/max samples
+    vec3 min_sample = min4(c11, c21, c12, c22);
+    vec3 max_sample = max4(c11, c21, c12, c22);
+/*
+      color = mat4x3(c00, c10, c20, c30) * weights[0];
+      color+= mat4x3(c01, c11, c21, c31) * weights[1];
+      color+= mat4x3(c02, c12, c22, c32) * weights[2];
+      color+= mat4x3(c03, c13, c23, c33) * weights[3];
+      mat4 wgts = mat4(weights[0], weights[1], weights[2], weights[3]);
+      vec4 wsum = wgts * vec4(1.0,1.0,1.0,1.0);
+      color = color/(dot(wsum, vec4(1.0,1.0,1.0,1.0)));
+*/
+
+
+    color = vec3(dot(weights[0], vec4(c00.x, c10.x, c20.x, c30.x)), dot(weights[0], vec4(c00.y, c10.y, c20.y, c30.y)), dot(weights[0], vec4(c00.z, c10.z, c20.z, c30.z)));
+    color+= vec3(dot(weights[1], vec4(c01.x, c11.x, c21.x, c31.x)), dot(weights[1], vec4(c01.y, c11.y, c21.y, c31.y)), dot(weights[1], vec4(c01.z, c11.z, c21.z, c31.z)));
+    color+= vec3(dot(weights[2], vec4(c02.x, c12.x, c22.x, c32.x)), dot(weights[2], vec4(c02.y, c12.y, c22.y, c32.y)), dot(weights[2], vec4(c02.z, c12.z, c22.z, c32.z)));
+    color+= vec3(dot(weights[3], vec4(c03.x, c13.x, c23.x, c33.x)), dot(weights[3], vec4(c03.y, c13.y, c23.y, c33.y)), dot(weights[3], vec4(c03.z, c13.z, c23.z, c33.z)));
+    color = color/(dot(weights[0], vec4(1,1,1,1)) + dot(weights[1], vec4(1,1,1,1)) + dot(weights[2], vec4(1,1,1,1)) + dot(weights[3], vec4(1,1,1,1)));
+
+    // Anti-ringing
+    vec3 aux = color;
+    color = clamp(color, min_sample, max_sample);
+    color = mix(aux, color, JINC2_AR_STRENGTH);
+
+    // final sum and weight normalization
+    FragColor.xyz = color;
+}
+#endif
diff --git a/base/windowed/shaders/lanczos2-sharp.glsl b/base/windowed/shaders/lanczos2-sharp.glsl
new file mode 100644
index 0000000..5f83af3
--- /dev/null
+++ b/base/windowed/shaders/lanczos2-sharp.glsl
@@ -0,0 +1,205 @@
+/*
+   Hyllian's jinc windowed-jinc 2-lobe sharper with anti-ringing Shader
+   
+   Copyright (C) 2011-2016 Hyllian/Jararaca - sergiogdb at gmail.com
+
+   Permission is hereby granted, free of charge, to any person obtaining a copy
+   of this software and associated documentation files (the "Software"), to deal
+   in the Software without restriction, including without limitation the rights
+   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+   copies of the Software, and to permit persons to whom the Software is
+   furnished to do so, subject to the following conditions:
+
+   The above copyright notice and this permission notice shall be included in
+   all copies or substantial portions of the Software.
+
+   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+   THE SOFTWARE.
+
+*/
+
+#define JINC2_WINDOW_SINC 0.5
+#define JINC2_SINC 1.0
+#define JINC2_AR_STRENGTH 0.8
+
+#define texCoord TEX0
+
+#if defined(VERTEX)
+
+#if __VERSION__ >= 130
+#define OUT out
+#define IN  in
+#define tex2D texture
+#else
+#define OUT varying
+#define IN attribute
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+
+IN  vec4 VertexCoord;
+IN  vec4 Color;
+IN  vec2 TexCoord;
+OUT vec4 color;
+OUT vec2 texCoord;
+
+uniform mat4 MVPMatrix;
+uniform COMPAT_PRECISION int  FrameDirection;
+uniform COMPAT_PRECISION int  FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+
+void main()
+{
+    gl_Position = MVPMatrix * VertexCoord;
+    color = Color;
+    texCoord = TexCoord;
+}
+
+#elif defined(FRAGMENT)
+
+#if __VERSION__ >= 130
+#define IN in
+#define tex2D texture
+out vec4 FragColor;
+#else
+#define IN varying
+#define FragColor gl_FragColor
+#define tex2D texture2D
+#endif
+
+#ifdef GL_ES
+#ifdef GL_FRAGMENT_PRECISION_HIGH
+precision highp float;
+#else
+precision mediump float;
+#endif
+#define COMPAT_PRECISION mediump
+#else
+#define COMPAT_PRECISION
+#endif
+
+uniform COMPAT_PRECISION int FrameDirection;
+uniform COMPAT_PRECISION int FrameCount;
+uniform COMPAT_PRECISION vec2 OutputSize;
+uniform COMPAT_PRECISION vec2 TextureSize;
+uniform COMPAT_PRECISION vec2 InputSize;
+uniform sampler2D s_p;
+IN vec2 texCoord;
+
+const   float halfpi            = 1.5707963267948966192313216916398;
+const   float pi                = 3.1415926535897932384626433832795;
+const   float wa                = JINC2_WINDOW_SINC*pi;
+const   float wb                = JINC2_SINC*pi;
+
+// Calculates the distance between two points
+float d(vec2 pt1, vec2 pt2)
+{
+  vec2 v = pt2 - pt1;
+  return sqrt(dot(v,v));
+}
+
+vec3 min4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return min(a, min(b, min(c, d)));
+}
+
+vec3 max4(vec3 a, vec3 b, vec3 c, vec3 d)
+{
+    return max(a, max(b, max(c, d)));
+}
+
+vec4 resampler(vec4 x)
+{
+   vec4 res;
+
+   res.x = (x.x==0.0) ?  wa*wb  :  sin(x.x*wa)*sin(x.x*wb)/(x.x*x.x);
+   res.y = (x.y==0.0) ?  wa*wb  :  sin(x.y*wa)*sin(x.y*wb)/(x.y*x.y);
+   res.z = (x.z==0.0) ?  wa*wb  :  sin(x.z*wa)*sin(x.z*wb)/(x.z*x.z);
+   res.w = (x.w==0.0) ?  wa*wb  :  sin(x.w*wa)*sin(x.w*wb)/(x.w*x.w);
+
+   return res;
+}
+
+void main()
+{
+
+    vec3 color;
+    vec4 weights[4];
+
+    vec2 dx = vec2(1.0, 0.0);
+    vec2 dy = vec2(0.0, 1.0);
+
+    vec2 pc = texCoord*TextureSize;
+
+    vec2 tc = (floor(pc-vec2(0.5,0.5))+vec2(0.5,0.5));
+     
+    weights[0] = resampler(vec4(d(pc, tc    -dx    -dy), d(pc, tc           -dy), d(pc, tc    +dx    -dy), d(pc, tc+2.0*dx    -dy)));
+    weights[1] = resampler(vec4(d(pc, tc    -dx       ), d(pc, tc              ), d(pc, tc    +dx       ), d(pc, tc+2.0*dx       )));
+    weights[2] = resampler(vec4(d(pc, tc    -dx    +dy), d(pc, tc           +dy), d(pc, tc    +dx    +dy), d(pc, tc+2.0*dx    +dy)));
+    weights[3] = resampler(vec4(d(pc, tc    -dx+2.0*dy), d(pc, tc       +2.0*dy), d(pc, tc    +dx+2.0*dy), d(pc, tc+2.0*dx+2.0*dy)));
+
+    dx = dx/TextureSize;
+    dy = dy/TextureSize;
+    tc = tc/TextureSize;
+
+    vec3 c00 = tex2D(s_p, tc    -dx    -dy).xyz;
+    vec3 c10 = tex2D(s_p, tc           -dy).xyz;
+    vec3 c20 = tex2D(s_p, tc    +dx    -dy).xyz;
+    vec3 c30 = tex2D(s_p, tc+2.0*dx    -dy).xyz;
+    vec3 c01 = tex2D(s_p, tc    -dx       ).xyz;
+    vec3 c11 = tex2D(s_p, tc              ).xyz;
+    vec3 c21 = tex2D(s_p, tc    +dx       ).xyz;
+    vec3 c31 = tex2D(s_p, tc+2.0*dx       ).xyz;
+    vec3 c02 = tex2D(s_p, tc    -dx    +dy).xyz;
+    vec3 c12 = tex2D(s_p, tc           +dy).xyz;
+    vec3 c22 = tex2D(s_p, tc    +dx    +dy).xyz;
+    vec3 c32 = tex2D(s_p, tc+2.0*dx    +dy).xyz;
+    vec3 c03 = tex2D(s_p, tc    -dx+2.0*dy).xyz;
+    vec3 c13 = tex2D(s_p, tc       +2.0*dy).xyz;
+    vec3 c23 = tex2D(s_p, tc    +dx+2.0*dy).xyz;
+    vec3 c33 = tex2D(s_p, tc+2.0*dx+2.0*dy).xyz;
+
+    color = tex2D(s_p, texCoord).xyz;
+
+    //  Get min/max samples
+    vec3 min_sample = min4(c11, c21, c12, c22);
+    vec3 max_sample = max4(c11, c21, c12, c22);
+/*
+      color = mat4x3(c00, c10, c20, c30) * weights[0];
+      color+= mat4x3(c01, c11, c21, c31) * weights[1];
+      color+= mat4x3(c02, c12, c22, c32) * weights[2];
+      color+= mat4x3(c03, c13, c23, c33) * weights[3];
+      mat4 wgts = mat4(weights[0], weights[1], weights[2], weights[3]);
+      vec4 wsum = wgts * vec4(1.0,1.0,1.0,1.0);
+      color = color/(dot(wsum, vec4(1.0,1.0,1.0,1.0)));
+*/
+
+
+    color = vec3(dot(weights[0], vec4(c00.x, c10.x, c20.x, c30.x)), dot(weights[0], vec4(c00.y, c10.y, c20.y, c30.y)), dot(weights[0], vec4(c00.z, c10.z, c20.z, c30.z)));
+    color+= vec3(dot(weights[1], vec4(c01.x, c11.x, c21.x, c31.x)), dot(weights[1], vec4(c01.y, c11.y, c21.y, c31.y)), dot(weights[1], vec4(c01.z, c11.z, c21.z, c31.z)));
+    color+= vec3(dot(weights[2], vec4(c02.x, c12.x, c22.x, c32.x)), dot(weights[2], vec4(c02.y, c12.y, c22.y, c32.y)), dot(weights[2], vec4(c02.z, c12.z, c22.z, c32.z)));
+    color+= vec3(dot(weights[3], vec4(c03.x, c13.x, c23.x, c33.x)), dot(weights[3], vec4(c03.y, c13.y, c23.y, c33.y)), dot(weights[3], vec4(c03.z, c13.z, c23.z, c33.z)));
+    color = color/(dot(weights[0], vec4(1,1,1,1)) + dot(weights[1], vec4(1,1,1,1)) + dot(weights[2], vec4(1,1,1,1)) + dot(weights[3], vec4(1,1,1,1)));
+
+    // Anti-ringing
+    vec3 aux = color;
+    color = clamp(color, min_sample, max_sample);
+    color = mix(aux, color, JINC2_AR_STRENGTH);
+
+    // final sum and weight normalization
+    FragColor.xyz = color;
+}
+#endif




More information about the Scummvm-git-logs mailing list