Quick answer: Compute derivative inputs unconditionally; branch only on the final value. Use fwidth(v) + smoothstep for AA edges. For texture sampling inside conditionals, use textureLod with explicit mip.

A signed-distance icon shader uses dFdx inside an if to anti-alias an edge. The AA bands or breaks because the derivative was wrong on the divergent side.

The Symptom

Visible banding at edges, especially near pixel-boundary thresholds. Smooth gradient shows discontinuities.

The Fix

// Bad — dFdx inside divergent branch
if (some_condition) {
    float w = fwidth(uv.x);
    color = smoothstep(0.5 - w, 0.5 + w, uv.x);
}

// Good — derivative computed unconditionally
float w = fwidth(uv.x);
float aa = smoothstep(0.5 - w, 0.5 + w, uv.x);
if (some_condition) {
    color = vec4(aa);
}

Compute fwidth at the top of fragment, branch on the use later. Derivatives valid for every pixel.

Texture Mip in Branches

vec4 c = textureLod(tex, uv, 0.0);   // explicit mip 0
if (cond) ALBEDO = c.rgb;

textureLod skips automatic mip selection (which depends on derivatives), making sampling safe inside conditionals.

Verifying

Render the edge close to the camera. AA should be smooth. With derivatives in branches: bands. Hoist; bands disappear.

“Derivative outside branches. Smoothstep on the result. Edges anti-alias.”

Related Issues

For shader uniform array, see uniform array. For shader uniform runtime, see runtime uniform.

Hoist derivatives. Smooth edges.