Contribution Overview

  • Mesh VFX system

  • Animation system

  • Sprites and special sprite effect shaders

  • Model effect system and accompanying shaders

  • Binary file format (Model- and animation data)

  • Water shader

  • Directional soft shadows


 

Mesh VFX System

The mesh VFX system is based on a JSON file with an array of “components“. A component consists of one mesh, one texture and three arrays of keyframes: scale, colour and UV. A VFX file can contain however many components as one pleases. This data is then used to determine the state of the VFX at a certain moment in time and subsequently rendered to the screen. There are some features that I didn’t have the time to implement, such as alpha blending and particle- and light source components. Examples of the use of this system are shown in the following video.

 

Animation System

The animation system makes use of my binary file format for animation data, the .myr format. I made the format because we wanted our engine to be free of third-party dependencies, such as AssImp, as well as drastically decrease the load times. I wrote a program that reads .fbx files and writes .erc (mesh data) and .myr (animation data) files for our engine to use, so it’s not something our graphics designers have to think about. The animation system supports the blending of animations as well as setting fallback animations and whether to loop them or not. The system itself took me quite a while to develop. I hadn’t delved deep enough into hierarchal transformations and it took me some time to wrap my head around it.

 
 
 

Sprites

In addition to the sprite system itself, I developed two sprite effect shaders that can alter how a sprite is rendered; Fish Eye and Circular Fill. Both are on display in the following video. For this system to work every sprite stores what type of shader it uses and a float of data that is used, depending on the shader, to produce the result. Another feature I added to the sprites is masking. With this, a circular sprite (such as the resource orbs) can be rendered even if the texture is not circular. This accompanied by the ability to modify the sample rectangle of the sprite in texture space enabled us to animate the resource orb. The rectangle is simply moved to the side, the mask rounds the edges and the fisheye shader gives the illusion of protrusion.

 
 
 
 

Post-Process Model Effect System

 
 

Every model in our engine can be assigned post-process effects to alter how they are shown in some way. In this game, we made use of two effects: highlight and outline (both of which I happen to have made). The way I accomplished this is by storing which models use which effects in a vector and rendering them to a GBuffer based on the effect type. The textures are then used by the effect shaders and blended onto the frame texture using the alpha value of their pixel colour.

 
 

Water Shader

 

For the water shader, I pretended that there was an infinite plane with normal (0, 1, 0) and variable position of (0, X, 0). What I then did was run a fullscreen pixel shader pass and calculate the direction of a ray, cast from the camera to that pixel. I then calculated where that ray intersected the plane in world coordinates and filled a GBuffer with that data, as well as the normal, colour and material and such to put it through our PBR pipeline. I used the xz components of the intersection position to wrap sample the texture to apply it to the water. To scale the texture I simply divided the position data by however many units an entire texture would cover in world coordinates. To create the illusion of depth and light attenuation I used the distance between the water's surface and whatever lay behind following the ray. The reflection is an entirely different render pass of the scene where the camera is flipped along the xz plane. The result of that pass is later added to the water texture to complete the illusion.