以IQ写的函数为例:
float sdBox( in vec2 p, in vec2 b ){
vec2 d = abs(p)-b;
return length(max(d,0.0)) + min(max(d.x,d.y),0.0);
}
-
点p
:归一化后的坐标点,横纵坐标范围都是是[-1,1]
一般情况下:vec2 p = (2.0*fragCoord-iResolution.xy)/iResolution.y;
-
点b
:宽,高的一半
但看vec2 d = abs(p)-b;
:假设bvec2(0.4,0.3)
则当p在矩形内时d的坐标在第三象限,当p在矩形外时d的坐标在非第三象限
我们在但单看length(max(d,0.0))
:假设d在第三象限,则函数表达式的结果为0.0;
假设d不在第三象限,则函数表达式的结果为sqrt(Nx*Nx+Ny*Ny)=N
; N为[0,1]中的所有实数
我们再看一下min(max(d.x,d.y),0.0)
:假设d在第三象限,则函数表达结果为max(d.x,d.y)=-N,
假设在非第三象限,则函数表达式的结果为0.0
综合来看length(max(d,0.0)) + min(max(d.x,d.y),0.0);
:当函数在第三象限时,函数表达式的结果为一个负数,当函数在非第三象限时,函数表达式的结果为一个非负数。
综合来看整个函数:sdBox(vec2 p,vec2 b)
:当坐标点在矩形内部时,函数的取值时一个负数,坐标点在矩形边界时,函数的取值为0,坐标点在矩形外部时,函数的取值为正数。
矩形
shaderToy矩形源码示例
float sdBox( in vec2 p, in vec2 b ){
vec2 d = abs(p)-b;
return length(max(d,0.0)) + min(max(d.x,d.y),0.0);
}
void mainImage( out vec4 fragColor, in vec2 fragCoord )
{
// Normalized pixel coordinates (from 0 to 1)
vec2 uv = fragCoord/iResolution.xy;
vec2 p = (2.0*fragCoord-iResolution.xy)/iResolution.y;
// Time varying pixel color
vec3 col = 0.5 + 0.5*cos(iTime+uv.xyx+vec3(0,2,4));
col = mix(col,vec3(0.0),step(0.0,sdBox(p,vec2(0.4,0.3))));
// Output to screen
fragColor = vec4(col,1.0);
}
网友评论