【ShaderToy】抗锯齿相关函数

*示例代码可以直接在ShaderToy中运行。

*我放在这里咯ShaderToy基础学习中~欢迎交流(ノ>ω<)ノ

先上未抗锯齿的两个圆形图案,可以清楚看清图案边缘像素块,即“锯齿”。

【ShaderToy】抗锯齿相关函数

附代码:

void mainImage( out vec4 fragColor, in vec2 fragCoord )
{
vec2 r = 2.0*vec2(fragCoord.xy - 0.5*iResolution.xy)/iResolution.y;
vec2 center1 = vec2(-0.75,);
vec2 center2 = vec2(0.75,); vec3 bgcol = vec3(1.0,0.5,0.5);//bg color
vec3 col1 = vec3(0.4,0.6,0.6);//circle1
vec3 col2 = vec3(0.4,0.2,0.5);//circle2
vec3 pixel; pixel = bgcol; if(length(r-center1)<0.4)
pixel = col1; if(length(r-center2)<0.4)
pixel = col2; fragColor = vec4(pixel,1.0);
}

要消除锯齿,这里借助几个GLSL内置函数,下面一个一个做笔记QAQ:

①mix()函数

原型:

//x为下限,y为上限,a为权重
//mix函数返回以a为权重,(x,y)为范围的线性插值
//返回值计算公式:x ×(1−a)+y×a float mix(float x, float y, float a)
vec2 mix(vec2 x, vec2 y, vec2 a)
vec3 mix(vec3 x, vec3 y, vec3 a)
vec4 mix(vec4 x, vec4 y, vec4 a)

②clamp函数:

原型:

//返回值计算公式:
// min(max(x, minVal), maxVal)
//超出下界即等于下界
//超出上界即等于上界
float clamp(float x, float minVal, float maxVal)
vec2 clamp(vec2 x, vec2 minVal, vec2 maxVal)
vec3 clamp(vec3 x, vec3 minVal, vec3 maxVal)
vec4 clamp(vec4 x, vec4 minVal, vec4 maxVal)

③smoothstep函数:

原型:

//在x、y间进行Hermite插值
//等价代码:
//  genType t;
//  t = clamp((x - edge0) / (edge1 - edge0), 0.0, 1.0);
//  return t * t * (3.0 - 2.0 * t); float smoothstep(float edge0, float edge1, float x)
vec2 smoothstep(vec2 edge0, vec2 edge1, vec2 x)
vec3 smoothstep(vec3 edge0, vec3 edge1, vec3 x)
vec4 smoothstep(vec4 edge0, vec4 edge1, vec4 x)

④step函数:

原型:

//step函数返回小于edge的值,否则返回1

float step(float edge, float x)
vec2 step(vec2 edge, vec2 x)
vec3 step(vec3 edge, vec3 x)
vec4 step(vec4 edge, vec4 x)

下面用一个简单明了的小例子来体现mix等函数的功能:

【ShaderToy】抗锯齿相关函数

代码如下:

void mainImage( out vec4 fragColor, in vec2 fragCoord )
{
vec2 p = fragCoord.xy / iResolution.xy;
vec3 col1 = vec3(1.0,0.2,0.4);
vec3 col2 = vec3(0.4,0.6,1.0);
vec3 pixel;
float m; //area 1
//展示用作示例的两种颜色
if(p.x<0.2){
if(p.y<0.5)
pixel = col1;
else
pixel = col2;
}
//area 2
//step函数效果
else if(p.x<0.4){
m = step(0.5,p.y);
pixel = mix(col1,col2,m); }
//area 3
//根据纵坐标数值线性变化效果
else if(p.x<0.6){
m = p.y;
pixel = mix(col1,col2,m);
} //area 4
//clamp函数效果
else if(p.x<0.8){
m = clamp(p.y,0.4,0.8);//即将线性变化区间从完整的[0,1]变成[0.4,0.8]
pixel = mix(col1,col2,m);
}
//area 5
//smoothstep函数效果
else{
m = smoothstep(0.45, 0.55, p.y);
pixel = mix(col1,col2,m);
}
//区域分界线
for(float i=0.2;i<1.0;i += 0.2){
if(p.x<i&&p.x>i-0.005)
pixel = vec3(1.0);
} fragColor = vec4((pixel),1.0);
}

回到最初的圆形。

用上述函数对原始圆形图案进行处理,弱化锯齿:

【ShaderToy】抗锯齿相关函数

附代码:

float linearstep(float edge0, float edge1, float x) {
float t = (x - edge0)/(edge1 - edge0);
return clamp(t, 0.0, 1.0);
} float smootherstep(float edge0, float edge1, float x) {
float t = (x - edge0)/(edge1 - edge0);
float t1 = t*t*t*(t*(t*. - .) + .);
return clamp(t1, 0.0, 1.0);
} void mainImage( out vec4 fragColor, in vec2 fragCoord )
{
vec2 r = 2.0*vec2(fragCoord.xy - 0.5*iResolution.xy)/iResolution.y;
vec3 bgcol = vec3(1.0,0.3,0.5);//bg color
vec3 col1 = vec3(0.4,0.2,0.5);//circle
vec2 center1 = vec2(-1.35,);
vec2 center2 = vec2(-0.45,);
vec2 center3 = vec2(0.45,);
vec2 center4 = vec2(1.35,);
vec3 pixel = bgcol;
float m=0.4; pixel = bgcol; //circle 0
//未经任何处理
/*
if(r.x<-0.9){
if(length(r-center1)<m){
pixel = col1;
}
}
*/ //circle 1
//step处理,等同于未经任何处理的circle 0
if(r.x<-0.9){
m = step(m,length(r-center1));
pixel = mix(col1,bgcol,m);
} //circle 2
//linearstep处理
else if(r.x<-0.0){
m = linearstep(m-0.005,m+0.005,length(r-center2));
pixel = mix(col1,bgcol,m);
} //circle 3
//smoothstep处理
else if(r.x<0.9){
m = smoothstep(m-0.005,m+0.005,length(r-center3));
pixel = mix(col1,bgcol,m);
} //circle 4
//自定义smootherstep处理
else if(r.x<1.8){
m = smootherstep(m-0.005,m+0.005,length(r-center4));
pixel = mix(col1,bgcol,m);
} //区域分解线
for(float i=-0.9;i<2.0;i += 0.9){
if(r.x<i&&r.x>i-0.005)
pixel = vec3(1.0);
} fragColor = vec4(pixel,1.0);
}

上图可能不太明显,在shadertoy网站运行代码全屏会更清楚点。事实是从左到右四个图的圆形锯齿越来越不明显。

这里有段代码蛮有意思的:

float t = (x - edge0)/(edge1 - edge0);
return clamp(t, 0.0, 1.0);

第一行代码的作用是判断x和edge1之间的关系,结合第二行clamp函数,如果>1说明x>edge1;如果<1则反之。

【over.】

上一篇:Oracle 10046 event


下一篇:CodeForces 731F Video Cards (数论+暴力)