Creating Human readable and Binary Files for Effects
As discussed in the previous posts, having a human readable file to edit data and having a binary file to load that data is more useful, compared to hardcoding the data in code. In this assignment, we have to create a Human readable format for effects and then convert it into binary format during build time and then load the required data from the binary file during runtime.
Human Readable effect file:
The file contains the locations to vertex and fragment shader and the type of Render state which can be “AlphaTransparency”, “DepthBuffering” or “DrawBothTriangleSides”. The file looks
return { Effect = { VertexShaderLocation = "Shaders/Vertex/standard.shader", FragmentShaderLocation = "Shaders/Fragment/standard.shader", RenderState = "DepthBuffering", }, }
Binary File:
The binary file saves the above information, but also saves the length of the path to Vertex Shader. I am storing this value to find where the path to fragment shader starts in the binary file. If I do not include that info, I have to iterate through every byte to check where the null termination character is and then point the next byte as fragment shader location. I am also adding a null terminator after the vertex and fragment shader locations, so that we can directly load the values as strings.
The input shaders are stored to our $(GameInstallDir)/data folder, but our working directory for game is the $(GameInstallDir) folder. I Chose to append “data/” in front of the file names, so that we do not have to add that during runtime. The upside of this method is that it is faster to load the paths during runtime, while the downside is increased file size. I think the improvements in load speeds offset the increase in file size, hence I included those.
The red rectangle is the Renderstate. The blue one is the length of path for vertex shader and the violet rectangles show the null terminators after each path.
Size
RenderState = uint8_t = 1Byte
Length of Path = uint8_t = 1Byte
Vertex Shader Path = 35 characters = 35 Bytes
null character = 1 Byte
Fragment Shader Path = 37 Characters = 37 Bytes
null character = 1 Byte
Total = 76 Bytes
Extracting data:
The above screenshot shows the code to extract data from the file. First we are extracting renderstate, length of vertex path, the vertex path. To know where the path to fragment shader starts. We add the length of vertex path plus 1, to account for the null termination character, to the offset.
Since most code is changed in the backend, there are no visible changes to the output.
Output:
Downloads: