Simplified PBR
An efficiently-computable approximation of physically-based rendering from Unreal Engine 4 and Disney.

This page documents a subset of the current physically-based rendering (PBR) models; in particular, it is the subset selected by Unreal Engine team1 Brian Karis, 2013. Real shading in Unreal Engine 4 https://cdn2.unrealengine.com/Resources/files/2013SiggraphPresentationsNotes-26915738.pdf of the model popularized by Disney2 Brent Burley, 2012. Physically Based Shading at Disney https://media.disneyanimation.com/uploads/production/publication_asset/48/asset/s2012_pbs_disney_brdf_notes_v3.pdf.

1 Diffuse

The Unreal Engine 4 team determined that for diffuse lighting, using Lambert’s law was visually adequate. This leaves out three terms included by the Disney team led by Brent Burley:

While these are all important for the appearance of some materials, many materials are smooth enough that the two effects of bumps nearly cancel out and opaque enough that light entering the material does not travel far enough to have a strong visual appearance.

2 Specular

The specular model got much more attention. Lambert’s law is based on an actual physical property, but Blinn and Phong’s models are not based on anything physical and need to be fully replaced. In particular, most PBR models replace it with what is called the Microfacet Model, which consists of three optical terms (plus a normalization factor to make it energy-preserving) as well as change in how we define scenes:

In addition to these three physical reflectence terms, we also need to handle another aspects of Blinn and Phong’s models. Real light sources are not tiny mathematical points; they have area, which makes their shine spots bigger. If we start using physically-based specular computation with dimensionless lights the shine spots will become far too small to be believable, so we’ll need a separate way of making lights look bigger, preferably without the overhead of sampling many light points. Karis defined several ways to do this, but we’ll use just one: a representative point method for spherical light sources.

3 Implementation

  1. The lighting models we showed in class used direction to light as an uniform parameter. Replace that with position of light and compute direction to light as position of lightposition of fragment.

    If you put the light far from the model this will have little visual impact, but move it closer and most of the model will become darker.

  2. Add a radius of light parameter and use Karis’s representative point computation5 Note: Karis had a sign error in the formula for closestPoint, which is corrected below:

    1. r\vec r = reflection of vectorToEye over surfaceNormal
    2. centerToRay = directionToLight − (vectorToEye dot r\vec r) r\vec r
    3. closestPoint = directionToLight − centerToRay clamp01(lightRadius / distanceToLight)
    4. newDirectionToLight = normalized(closestPoint)
    5. use the newDirectionToLight for specular but not for diffuse lighting

    If you make the light radius only a bit smaller than the distance from the model to the light, the shines should get very large.

  3. Change parameters to be more believable.

    • Most things you see absorb most of the light that hits them. Only have a color parameter above 0.5 if you want the object to look intensely bright in that spectrum.
    • Increase light intensity until the colors no longer look muted.
  4. Add a roughness material parameter, and a constant F0=0.04F_0 = 0.04. For roughness we’ll use Disney’s α\alpha, the square of the roughness parameter in the GGX definition of roughness, because that scaling is more intuitive to artists. It will always be between 0 and 1.

    For now this has no visual impact because we’re not using it for anything.

  5. Add functions to compute DD, GG, and FF, which use n\vec n the normal vector, h\vec h the halfway vector, l\vec l the direction to the light and v\vec v the direction to the eye:

    D=α2((nh)2(α21)+1)2πk=(α+1)28G1(x)=nx(nvecv)(1k)+kG=G1(l)G1(v)c=vhF=F0+(1F0)2(5.55473c6.98316)c\begin{align} D &= \dfrac{\alpha^2}{\big((\vec n \cdot \vec h)^2(\alpha^2-1) + 1\big)^2\pi} \\ k &= \dfrac{(\sqrt{\alpha}+1)^2}{8}\\ G_1(\vec x) &= \frac{\vec n \cdot \vec x}{(\vec n \cdot vec v)(1 - k) + k}\\ G &= G_1(\vec l) G_1(\vec v)\\ c &= \vec v \cdot \vec h\\ F &= F_0 + (1-F_0)2^{(-5.55473c - 6.98316)c} \end{align}