过程纹理和抗锯齿:ProceduralTexture & Anti aliasing - MartinRGB/GLES30_ProgrammingGuide_NDK GitHub Wiki

过程纹理

以过程而非图像描述的纹理,描述了给定输入,生成纹理颜色或深度值的算法

优点:小,不损失细节

缺点:占用指令带宽,可能有锯齿。

14_8_ProceduralTextures

Vert:


void main() {

    v_st = a_texcoord;
    gl_Position = mvp_matrix * vec4( position, 1.0 );

}

Frag:

void main() {
    vec2 texcoord = mod(floor(v_st * float(u_frequency *2)),2.0);
    float delta = abs(texcoord.x - texcoord.y);
    gl_FragColor = mix(vec4(0.,1.,0.,1.),vec4(1.,0.,0.,1.),delta);
}

抗锯齿

为了防止抗锯齿,需要估计像素覆盖区域的平均纹理值。OpenGL ES 包含了导数函数 dFdx dFdy 计算 函数在 x y 的变化率,称之为 梯度向量fwidth 可以计算出梯度向量的幅度。

在上个粒子中,可以用 fwidth计算出v_st.x v_st.y的过滤宽度

假设过滤宽度w,过滤宽度最小值k:

1.w < k/2,不产生锯齿,使用 smoothstep 在真正的函数和平均值之间渐变。

2.w > k/2 会产生锯齿,使用函数平均值。

AA

Frag:

    vec4 color;
    vec4 color0 = vec4(1.,0.,0.,1.);
    vec4 color1 = vec4(0.,1.,0.,1.);
    vec2 st_width;
    vec2 fuzz;
    vec2 check_pos;
    float fuzz_max;
    
    st_width = fwidth(v_st);
    fuzz = st_width * float(u_frequency) * 2.0;
    fuzz_max = max(fuzz.s,fuzz.t);
    check_pos = fract(vUv * float(u_frequency));
    
    // w < k/2,不产生锯齿,使用 smoothstep 在真正的函数和平均值之间渐变。
    if(fuzz_max <=0.5){
        vec2 p = smoothstep(vec2(0.5),fuzz+vec2(0.5),check_pos) + (1.0 - smoothstep(vec2(0.),fuzz,check_pos));
        color = mix(color0,color1,p.x*p.y+(1.0-p.x)*(1.0-p.y));
        
        color = mix(color,(color0+color1)/2.0,smoothstep(0.125,0.5,fuzz_max));
    }
    // w > k/2,产生锯齿,使用平均值
    else
    {
        color = (color0+color1)/2.0;    
    }
    
    
    gl_FragColor = color;