Even better, all Full Bore pre-order customers, [...]]]>
Even better, all Full Bore pre-order customers, current and future, will be able to download The First Dig starting September 10th, 2013.
Full Bore has come a long way since last year’s Kickstarter demo. The First Dig takes place in the same region, but has a new story, new characters, many new areas and puzzles. Even more, there’s tons of extra polish— more animations, enhanced lighting, and actual talking boars! Even if you’ve seen the old demo in action or played it yourself, The First Dig will feel like a totally new experience.
The three of us here at Whole Hog are really proud of this release. It’s not all the content we want to deliver, and that’s why we’re going right back to work on second half, but The First Dig is a complete, polished experience. We hope you enjoy it.
-Casey, Finn, and Jake
Whole Hog Games
For More Information:
Pre-orders and more at the Full Bore website: http://gofullbore.com
Full Bore on Youtube: http://www.youtube.com/wholehoggames
The First Dig FAQ: http://gofullbore.com/firstdig.php
Press Resources: http://www.wholehog-games.com/press/sheet.php?p=full_bore
This write-up is meant a conceptual tutorial- I will go over everything that needs to be in place to do lighting in Full Bore but I will not be getting into specific implementation details. My hope is that anyone reading this who is familiar enough with their tools (be it C++ or Unity or what-have-you) will be able apply some or all of what I’ve written here to their own games. For reference, Full Bore was written from scratch in C++ and has both Direct3D and OpenGL back-ends, but a tool or engine that gives you decent control over your rendering pipeline should be able accommodate this technique. Of course, I have no experience using higher-level tools like Unity so please do as the internet does and tell me how wrong I am in the comments!
First, here’s a quick look at what it being rendered behind the scenes in Full Bore:
The previous three images (click to embiggen) combined with a list of lights and their properties, are used to produce a final image:
For those of you familiar with graphics programming this is pretty much a bog-standard deferred shading implementation like you would expect to see in a modern FPS game. For those of you just getting started with graphics programming this is reasonably radical departure from the more textbook method, so there are few things that need to come together for this particular technique to work. First off…
In a 3D game, normal maps are used to add extra detail to models without the expense of adding in extra geometry. In a 2D game, Normal maps similarly let us pretend that the scenes we’re making have depth so that we can light things in a way that reveals extra surface detail. In Full Bore just about every sprite in the game has a normal map.
It is possible to make all of the normal maps you need by making a greyscale height map and then using the NVIDIA Texture Tools for Photoshop or this excellent GIMP plugin to compute the resulting normal map. These plugins all blur the source height map at some point so small per-pixel details are usually obliterated or obscured, but if you’re working on a higher resolution game like, say, Escape Goat 2, computing normal maps from height maps could very well be all you need.
But what if you are working on a low-resolution game? Full Bore’s art is particularly low-res, so many normal maps are computed and then hand-tweaked or completely hand-drawn, and in order to do that we had to develop a good understanding of what, exactly, is encoded in a normal map.
Mathematically, a normal map encodes a 3D vector that describes the direction that pixel is facing into the red, green and blue color channels. However, looking at a normal map you may notice the image shows some human-comprehensible surface detail. If you separate the color channels of a normal map out this becomes even more apparent. From a purely visual point of view, a normal map is the combination of a shape lit from the right or left by a red light, from above or below by a green light, and from head-on by a blue
light. The numbers are still a bit important, so, to rephrase:
For sanity’s sake, be sure familiarize yourself with how to turn editing and visibility on and off for color channels in your image editing program.
When computing normal maps from height maps, high-detail and low-detail areas will look better when computed with different filters.
In this case it helps to split the height maps into layers and combine them post-normal-filter.
Lastly it is possible to merge normal maps in an image editing program with mostly correct results. This lets you do things like add detailed noise to a smooth normal map, or merge different shapes.
In order to do this, you have to do the following:
By now should have enough to get you started making your own normal maps, so now…
Well, you don’t need to, but directly rendering sprites with normal mapped lighting severely limits the number of lights you can have on the screen. To get around this limitation, Full Bore uses deferred shading, a technique more often seen in 3D games but also one perfectly suited to what we’re trying to do here. When doing deferred shading, rendering happens in two stages.
First you write all the information you need to run your light shader into one or more frame buffers, this can be accomplished efficiently by using multiple render targets and appropriately written shaders (how exactly you do that depends on what library or tool you’re using.) In Full Bore, every texture has a corresponding normal and luminance texture which lines up exactly with the original color texture, so when a given sprite is drawn out, it’s trivial to draw the other data to the appropriate frame buffer by doing another texture lookup. The set of three screenshots near the beginning of the article show what Full Bore’s 3 frame buffers look like.
Second, to actually light up the game, you use your frame buffers as textures to draw your lights. Oh, did I not tell you?
Your light shader can only be executed by drawing some geometry to the screen. There are a lot of different ways that you can go about doing this but there is some common ground.
Arranging lights in an aesthetically pleasing manner is a subject for another article, but it’s safe to say there is a lot of interesting stuff to play with once you have a working lighting system.
And that’s the basics: you need to make a lot of normal maps, and you should probably use deferred shading for rendering your lighting. Have at it!
I’ve tried to keep this as non-platform-specific as I can, and I am sure that has created some blank spots in my explanations. Please feel free to ask me questions in the comments and I will update the article as needed. If there is any interest I can write about Direct3D or OpenGL implementation details, just be sure to let me know!]]>
A good illustration of contrast is known as the windmill principle.
The blades of the windmill demonstrate the different kinds of contrast: light on light, dark on light and dark on dark.
Firstly, the blocks that are in the foreground and can be interacted with have to be separated from those in the background that serve as decoration only. We added a darkening overlay to the background tiles, which gave them a clear difference in value range, even though the same tiles were being used in the background as the foreground. Next, the environments are made up of different tiles with specific behaviors. Different block types are drawn in front of or behind one another depending on type, while overlays cause groups of blocks to read as a mass, and overlap blocks behind them in the draw order. This prevents visual tangents, which cause a representation of space to look flat.
(The shape on the left implies a spatial relationship more clearly than the one on the right, where all the lines tangent each other.)
One of my first attempts at creating a tile set for full bore resulted in too much contrast within each tile individually, but not enough contrast between different tile types. For example, the stone tile had very dark darks and very light lights, causing large formations of them on screen to “jangle” visually. The team and I knew those tiles weren’t working, but since this was my first pixel art tileset, I hadn’t quite integrated it in my mind with what I knew about design. Casey got Mimi, a graphic designer friend of his, to take a stab at making some tiles, since I was focused on animating the main character at the time. The tiles she came back with were much more iconic and restrained than the ones I had made, and I was able to realize my error. Our current tile set embodies (for the most part) a hierarchy of function related to how much contrast is contained within the tile. Tiles that are unbreakable and unmovable have the least contrast within themselves, being very close to a flat color. Tiles that are moveable and perform some function, such as the laser block, have a wider range of contrast so that the player’s attention is drawn to it. This is of course one of the areas our game can improve on.
Even with this hierarchy of value, a full screen of blocks can be quite visually overwhelming. Some of the tools we used to break up the tiles on screen were paths through the environment from puzzle to puzzle and decorations, which give the player’s eye something to look at that is different than the environment blocks. Varying the size of the path helps as well, from small, one-tile high tunnels to large caves, providing additional visual interest. The puzzles that Jake has designed often take up unique spaces due to their function and what blocks are used, creating interesting places for the player to navigate.
Something was still missing, though, and that something was lighting. Casey had been planning on implementing a lighting system, time permitting, and when he was able to put it in place, we suddenly had a lot more options when it came to visually designing our environments. For one, Full Bore being a game that takes place in caves and tunnels underground, it needs some darkness. A person’s eye will always go to the area of largest contrast first, and so, with varying size and brightness of light, we can highlight what is important in a level, and let what is less important drop into shadow. Light is the vehicle of mood and drama, both of which are very important to storytelling (which is what I love most in games). We are still trying to use the lighting system to its fullest, including making normal maps for all the tiles, objects and characters so that they will pick up the light to convey 3d form in our 2d world.
Full Bore is still a work in progress, and now that our programming and game play systems are in place, we want to focus on making the game look and feel the best that it can. Some of the things we still want to work on are environmental storytelling, further refining block designs to show their function, and designing the lighting to better direct the player’s attention to puzzles and paths. Our Kickstarter has been doing really well, and we are all excited to be able to make the game better with everyone’s support.]]>