I’ve been quite busy in the last couple of weeks, my MacBook tells me that I had an increase of 46% in screen-time, which is a bit scary.
In my last devlog I had turned my sights from shadows to shaders and had implemented a Blinn shader. The next logical step was PBR materials.
Change Log
- Implemented PBR material
- Implemented EnvLight and HDR image-based lighting [1]
- Added an optional 'skybox' render pass
- Added a final composite pass for tone-mapping etc.
- Removed AmbientLight (superceded by EnvLight) [2]
- Refactored lights to descriptor-based approach
- Implemented screenspace reflections
- Fixed race conditions in pipeline creation of the LineRenderer
- Improved materials to support UV properties (scale, offset, tiling etc.)
- Refactored UI controls
SSR)Blinn shader. I also just finished refactoring the Light too, these things happen.Physically Based Rendering
Before PBR, materials were mostly artist-driven. You’d tweak diffuse, crank specular and bake lighting to fake complex materials and real-world lighting.
There’s nothing inherently wrong with that approach and in many cases, even today, it’s still the go-to workflow. Not just for non-photorealistic rendering (NPR) styles like cel shading either, but for plenty of real-time applications too.
A common issue is that if you author materials to look good under specific lighting conditions and they change, it doesn’t always hold up.
With PBR, materials you describe what something is, not how it should look and the lighting model calculates the rest. That means metals look like metal, plastics look like plastic, and they keep looking correct no matter where you put them.
PBR materials rely on a different (and more physically meaningful) set of properties compared to models like Lambert or Blinn.
- Albedo (Base Color) – the true surface color, without lighting baked in.
- Metallic – defines whether a surface behaves like a metal or a dielectric.
- Roughness – controls how smooth or rough a surface is, affecting how light scatters in reflections.
- Normal maps – adds surface detail without changing the underlying geometry. (not specific to PBR but more important as it has a strong impact on realism.)
In the Metallic/Roughness workflow, you describe a material using just two core ideas:
- Is it a metal?
- How rough is it?
That’s enough for the lighting model to determine:
- Whether light is absorbed or reflected diffusely
- Whether reflections are tinted
- How sharp or blurry those reflections are
or practically…
| Material | Metallic | Roughness | Result |
|---|---|---|---|
| Plastic | 0.1 | 0.4 | Colored surface with soft white highlights |
| Polished Steel | 1.0 | 0.1 | Sharp, tinted reflections |
| Concrete | 01.0 | 0.9 | Mostly diffuse, barely visible reflections |
Image Based Lighting
I’ll save the details for the next post, but it would be remiss for me not to mention this version of StaticRectangle has IBL (Image Based Lighting) in support of the PBR materials.
While Image Based Lighting isn’t strictly necessary for PBR materials, they do work together to reproduce realistic real-world lighting.
I got the implementation of the PBR materials done reasonably quick (all this shader math is already well established and the infrastructure was already in place), but the metals were quite lackluster without something to reflect.
Adding IBL which encompasses the irradiance map, prefiltered environment map, and BRDF LUT (tech loves a good acronym…) bumps the realism significantly, and it’s needed to really test that the PBR materials are behaving correctly.
Barrels of Fun
I bought an HDRI pack 6 months ago1 which came in handy here. I don’t have any of my own PBR assets yet so the barrel (model and textures)2 and the ground PBR material3 I grabbed for free online.
https://www.simonlachapelle.com/hdris highly recommend this resource if you’re in the market for high quality HDRI ↩︎
https://www.turbosquid.com/3d-models/wooden-barrel-2371986 ↩︎