Shub's logo

T-1: Shaders

23 May, 2020

4 min read

Shaders are pixel manipulation tools. To create shaders, we use some kind of Shading Language.

Some interesting details on Shaders can be found in this Abstract

We would be using GLSL as our Shading Language in our Demo.

Before moving forward, we should know what SPIR-V is!!! SPIR-V is an intermediate language defined by Khronos Group for Vulkan. It is the language that Vulkan understands and thus gfx-hal too. So to work with shaders in gfx-hal we can use any Shading Language, but we need to first convert those Shader Code into SPIR-V format and then can we use it directly in gfx-hal.

Currently Rust does not have any native module to support JIT compilation of any Shading Language to SPIR-V. Thus, currently setting up Shaders in Rust is quite difficult.

There is an ongoing discussion for this on rust-gamedev working group, but is far from any conclusion.

There are ways to work with shaders ingfx-hal, but they are quite complex to setup.

Easiest way is to pre-compile your GLSLor HLSL code to SPIR-V format and use that directly in gfx-hal.

To get a JIT compilation in native Rust, we will have to wait. Currently there is an ongoing project ingfx community, named naga, to support cross-platform, multi Shader Languages all in pure Rust.

GLSL support is on it's way

Details on naga, can be found here

Understanding GLSL

I am new to shaders completely. For me choosing any Shading Language was difficult, let aside understanding SPIR-V and overcoming Rust's support for any stable Shader language support.

I am just following people here, and have found HLSL and GLSL to be used more often. GLSL being used more effectively in the Open Source Community. Thus, will understand and use GLSL in our projects as well.

If you have no prior knowledge on Shaders, I would recommend to read this post once, just to get some quick hands on.

I am keeping link a to GLSL language specs here, as a reference.

Moving forward!! Teaching GLSL is out of scope for this post, but you can go through this awesome shaders list for resources to teach you GLSL.

We would be testing two shaders

Pre Compilation of GLSL Shaders

I would recommend you to try the solution mentioned in Compiling GLSL to SPIR-V, for simplicity of converting GLSL shader files to SPIR-V files.

Though I failed to run the script mentioned in Compiling GLSL to SPIR-V. Also, glsl-to-spirv is outdated. It was part of project vulkano, but is abandoned in support of google's shaderc project, which we will be using as well.

I would like to warn you though!! shadercis a C/C++project and thus setting it up is tedious and harder compared to Rust's Cargoecosystem.

It is also good to note that, either we can use it as a command line tool, using glslc binary, to pre-compile our GLSL/HLSL Shaders, or we can use Rust Shaderc Bindings  in our rust code, so as to compile our GLSL/HLSL shaders at runtime.
We will discuss both. If you are able to compile and useglslc binary, than usingshaderc-rs in rust won't be of any trouble.

Before moving forward, you can use Shader Playground to get some basic understanding on how GLSL get's converted into SPIR-V format.

Details on compilation of shaderc can be found in there doc. Though I would like to mention some dependencies, to be present before compilation, in short here, assuming you are using Linux or Mac OS (Mac OS should have brew installed for simplicity).

If everything goes fine, you will find glslc binary inside $SOURCE_DIR/build/glslc. We can now directly use glslc to pre-compile our GLSL shaders to SPIR-V.

© Copyright 2020 Subroto Biswas