updated dilation and erosion

This commit is contained in:
Sven Vogel 2023-08-07 19:20:59 +02:00
parent 8ebb7b181a
commit eed7f3ce21
2 changed files with 45 additions and 27 deletions

View File

@ -1,35 +1,43 @@
//#define DIAMOND_KERNEL //#define DIAMOND_KERNEL
#define CIRCULAR_KERNEL
float lum(in vec3 rgb) float luminance(in vec3 rgb)
{ {
return dot(rgb, vec3(0.21, 0.72, 0.07)); return dot(rgb, vec3(0.21, 0.72, 0.07));
} }
/**
* Intensifies the brightest pixels of the applied kernel based on the luminance() function
*/
vec3 dilate(in sampler2D tex, in vec2 uv, in int size, in float sep, in float minb, in float maxb) vec3 dilate(in sampler2D tex, in vec2 uv, in int size, in float sep, in float minb, in float maxb)
{ {
vec3 cc = texture(tex, uv).rgb; vec3 cc = texture(tex, uv).rgb;
vec3 tc = cc; vec3 tc = cc;
float cl = lum(cc); float cl = luminance(cc);
vec2 texSize = sep/vec2(textureSize(tex, 0));
for (int x = -size; x <= size; ++x) for (int x = -size; x <= size; ++x)
for (int y = -size; y <= size; ++y) for (int y = -size; y <= size; ++y)
{ {
// default kernel is box shaped
#ifdef DIAMOND_KERNEL // diamond shaped kernel (45° rotated square)
#if defined(DIAMOND_KERNEL)
if (abs(x) > size - abs(y)) if (abs(x) > size - abs(y))
continue; continue;
#else #elif defined(CIRCULAR_KERNEL)
if (distance(vec2(x, y), vec2(0, 0)) > float(size)) if (distance(vec2(x, y), vec2(0, 0)) > float(size))
continue; continue;
#endif #endif
vec3 s = texture(tex, uv + vec2(x,y)/iResolution.xy*sep).rgb; vec3 s = texture(tex, uv + vec2(x,y)*texSize).rgb;
float b = lum(s); float b = luminance(s);
if (cl < b) if (cl < b)
{ {
@ -41,30 +49,37 @@ vec3 dilate(in sampler2D tex, in vec2 uv, in int size, in float sep, in float mi
return mix(cc, tc, smoothstep(minb, maxb, cl)); return mix(cc, tc, smoothstep(minb, maxb, cl));
} }
/**
* Intensifies the darkest pixels of the applied kernel based on the luminance() function
*/
vec3 erode(in sampler2D tex, in vec2 uv, in int size, in float sep, in float minb, in float maxb) vec3 erode(in sampler2D tex, in vec2 uv, in int size, in float sep, in float minb, in float maxb)
{ {
vec3 cc = texture(tex, uv).rgb; vec3 cc = texture(tex, uv).rgb;
vec3 tc = cc; vec3 tc = cc;
float cl = lum(cc); float cl = luminance(cc);
vec2 texSize = sep/vec2(textureSize(tex, 0));
for (int x = -size; x <= size; ++x) for (int x = -size; x <= size; ++x)
for (int y = -size; y <= size; ++y) for (int y = -size; y <= size; ++y)
{ {
// default kernel is box shaped
#ifdef DIAMOND_KERNEL // diamond shaped kernel (45° rotated square)
#if defined(DIAMOND_KERNEL)
if (abs(x) > size - abs(y)) if (abs(x) > size - abs(y))
continue; continue;
#else #elif defined(CIRCULAR_KERNEL)
if (distance(vec2(x, y), vec2(0, 0)) > float(size)) if (distance(vec2(x, y), vec2(0, 0)) > float(size))
continue; continue;
#endif #endif
vec3 s = texture(tex, uv + vec2(x,y)/iResolution.xy*sep).rgb; vec3 s = texture(tex, uv + vec2(x,y)*texSize).rgb;
float b = lum(s); float b = luminance(s);
if (cl > b) if (cl > b)
{ {
@ -76,16 +91,16 @@ vec3 erode(in sampler2D tex, in vec2 uv, in int size, in float sep, in float min
return mix(tc, cc, smoothstep(minb, maxb, cl)); return mix(tc, cc, smoothstep(minb, maxb, cl));
} }
void mainImage( out vec4 fragColor, in vec2 fragCoord ) void mainImage(out vec4 fragColor, in vec2 fragCoord)
{ {
// Normalized pixel coordinates (from 0 to 1) vec2 uv = (fragCoord-0.5*iResolution.xy)/iResolution.y;
vec2 uv = fragCoord/iResolution.xy;
vec3 dil = dilate(iChannel0, uv, 12, (uv.x-.5)*3., 0.0, 1.0); float separation = (uv.x)*1.5;
vec3 er = erode(iChannel0, uv, 12, (uv.x-.5)*3., 0.0, 1.0);
vec3 col = uv.x > 0.5 ? er : dil; vec3 dilation = dilate(iChannel0, uv, 16, separation, 0.0, 1.0);
vec3 erosion = erode (iChannel0, uv, 16, separation, 0.0, 1.0);
vec3 col = uv.x > 0.0 ? erosion : dilation;
// Output to screen
fragColor = vec4(col,1.0); fragColor = vec4(col,1.0);
} }

View File

@ -2,3 +2,6 @@
![overview.png](https://git.teridax.de/teridax/Shadertoy-Shaders/raw/branch/main/Image-Filtering/Dilation-Erosion/overview.png) ![overview.png](https://git.teridax.de/teridax/Shadertoy-Shaders/raw/branch/main/Image-Filtering/Dilation-Erosion/overview.png)
Dilation is the process of intesifying the brightessed pixel of a kernel, where as erosion intesifies the darkesed pixel of a kernel. Dilation is the process of intesifying the brightessed pixel of a kernel, where as erosion intesifies the darkesed pixel of a kernel.
## Demo
<iframe width="640" height="360" frameborder="0" src="https://www.shadertoy.com/embed/dljcRz?gui=true&t=10&paused=true&muted=false" allowfullscreen></iframe>