Ok, so we finally have a graphic. This is a raster graphic, preferably a PNG file, and we need to put it in to a game.
If you're not sure what I'm talking about, check the first part of this article: Game Programming and 2d Art
As a programmer, the first step to get this art in game is to load the png file in to memory and get to the raw RGB data. This is ideally suited for libpng (google for tech examples how to do use this library).
Once you get the pixel data, you can load it in to your favorite graphics library (opengl for example) and start putting it on quads/triangles/whatever. Of course, other problems can come up before you might actually see your graphic (like orthogonal viewport, etc). Those concepts are beyond this article (if you're interested, check out nehe's website for their tutorials).
This is all well and good and ideally you can finally put some basic png file to direct use in a game. Already this probably could be a rollercoaster of learning and complexities, but the fun doesn't stop there!
The "better" way of handling 2d graphics is to use texture atlases. Or rather, a collection of individual png files crammed in to one larger png file. If you've ever opened "skins" or texture packs for various games (quake, minecraft, etc), you may have noticed that the graphics are all over the place in a larger raster graphic file (png). The face is upside down and is connected to the chest, which is in turn connected to their legs and maybe their shoes below that. It basically looks like someone took a steamroller to a player or monster and flattened them all out in to one graphic file.
Welcome to the wonderful world of texture atlases. Before we begin, let's talk about some considerations you should take in to account.
First, atlas dimensions and memory.
Not everyone is running a desktop, especially with amazing graphics cards. More over, if you're going to deploy on a mobile device or tablet, this is a major problematic area. That said, you need to consider how big your atlas is.
Powers of two (1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 2056, etc) or PoT is a very critical concept to understand when it comes to texture memory. Your texture atlases should always be in perfect power of two dimensions. Specifically, if your atlas is 256 pixels tall, it should be 256 pixels wide.
Why?
Well, if you understand basic computer science, you should understand that computers work in base 2 (0, 1). Powers of two are significant in that it aligns memory perfectly with memory offset techniques. It's complicated, but it boils down to optimizing how a CPU and GPU process data. More over, older graphics cards were completely unable to use Non-Powers of Two (nPoT) at all. Trying to load graphic data with nPoT dimensions would result in garbled graphic data... usually like someone took the bottom of your graphic and ripped it sideways as it is rendered from top to bottom... if it renders anything at all other than a white box.
So, your PoT texture atlas is fine, but there's still a problem. There are a lot of things that can go wrong when rendering graphic data, but a common issue is that you may have exceeded a maximum amount of memory (like try loading a 2056x2056 texture atlas), while it would be nice if your program told you when you exceeded a maximum, it will likely instead crash when trying to load or use the data.
Of course, it isn't this simple, some graphics cards and computer systems will load this just fine (dependent on hardware per device), leaving you very confused when your masterpiece of a game simply won't work on your friend's computer, but works fine on yours. Worse, sometimes hardware may actually do some sort of complicated emulation or paging to force large texture data to work. The major drawback here is that you will be swapping data in and out of the CPU/GPU so constantly that the performance of your game will suffer tremendously.
At the end of the day, working with large atlases can give you various scenarios. Sometimes it will work, others will make your game run like terrible, and others will out right crash the program.
There really isn't any "best" answer here other than to select some maximum atlas size during your technical design phase and stick with it. There are software strategies to attempt to figure out a device's max texture size and to parse that large atlas data in to smaller pixel data clumps (that likely need to also follow PoT rules), but again, that can be very complicated, but may be necessary if you want to be a serious game/graphics engine programmer.
The final result that you will want to work with isn't even the atlas itself, but rather the texture objects inside the atlas that you will want to use! All this headache just to find there's even more to it!
There is a tool that simplifies this a bit, and I talk about it here in the last article.
Technical blog posts about programming, graphics, technology, animation, games, maybe some politics or game reviews.
Showing posts with label vector art. Show all posts
Showing posts with label vector art. Show all posts
Friday, May 10, 2013
Wednesday, May 8, 2013
Game Programming and 2d Art
If you're a game developer, specifically working on 2d games, you will probably want some sort of graphics sooner or later.
Suffice to say, graphics aren't an easy topic for a programmer to really "get" aside from binary values for R G B A. Yet, for art people, it's all about hues, lighting, perspective, and all that other non-programmer-technical stuff...
Why am I rambling about all of this? Because if you want to incorporate 2d graphics, you will likely need to interact with artists (unless you're the artist, but you should still take heed!), and likewise, they will have to interact with you... and this is where things can get interesting.
Through some miracle, programmers and artists are working together, but how exactly does all this neat 2d art actually work and get in to a game? Texture atlases.
Well, let's rewind a bit, the most basic thing is a single graphic.
Now, how you take a single graphic and display it in a game is dependent on your environment, game engine, and all that other stuff. For the sake of this article, I will not be delving in to any technical examples of how to use any graphics libraries (you won't be seeing any code!) -- I'm more going to focus on *methods* of putting art in to a game.
Now, some programmers might think "methods" and think of programming -- well, reminder, not everyone thinks the same words mean the same things... "methods" can also mean the process of how you accomplish some task... like an artist might use a certain method to create your art, but that has nothing to do with your actual programmatic method used to display that art in your game... or your method of how to implement your method to display the art...
Anyways, back to graphics!
There are some technical issues that you and/or your artist should know right at the get go. First, some terminology.
Raster Graphics - This refers to graphics that are pixel data. Stuff like png files, raw RGBA binary data, bitmaps, things that are defined by pixels. All of this stuff is collectively called "raster graphics". This is as opposed to...
Vector Graphics - These graphics are a bit more complicated and usually not useful to implement directly in to games. However, there are some pretty huge perks to having an artist use this format as opposed to raster graphics. With vector graphics, the artwork is now a collection of mathematical shapes assigned various colors. This means that, like all math, the original will always remain true, regardless of "zoom level" or how much you scale it; unlike raster graphics which use filters to "approximate" when scaling.
The issue of scaling graphics is complex and is worthwhile to research, but the skinny version is that raster graphics lose quality every time you scale up or down from the original until you will just end up with a blob. With vector graphics, you can essentially scale up, down, shear, or do anything else to it without losing quality, as much as you want to.
Now, I mentioned vector isn't directly useful to games. This is true, rendering vector graphics is a massively difficulty task for even today's hardware. Sure, you could render a couple dozen vector graphics, but you need to realize that the graphic being displayed is generated by math, and if that needs to be refreshed (like during a screen redraw!), it could potentially need to be regenerated; so if the shape is complex enough, it will ruin your game's performance.
Ok, now that we got all that out there, it is really only practical to use raster graphics in games! Graphics programming is all about using pixel data to feed directly in to some framebuffer, or use as texels for polygons, or things like this. Someone will need to convert vector in to raster before it can be directly useful in a game. Thankfully, most (all?) vector programs have an export feature and will allow someone to export vector art (which is flawless!) in to a rasterized version of that art. What's even better is that you can essentially export to some given scale right away!
I was once confronted with the idea that an artist could "just give me a really large original" from photoshop and then I could just scale it down based on my need at the time. While this may sound "ok", this is not ok.
Let's talk about graphics scaling some more to hopefully highlight why this isn't acceptable.
We're living in a day and age of thousands of devices, smartphones, tablets, computer monitors, etc. All of them have different display sizes and capacities (what a nightmare!). If you want to deploy your game to some/any/all of them, you will need different sizes for all of your art... meaning a LOT of scaling up and down. But, how do you know what size art you need, or rather, what size would look the best on some given device?
The lazy answer is "just use a big version and scale down", but this actually isn't a good answer at all for 2 reasons. One, you use excessive amounts of memory/cpu/gpu when you scale it in your game engine. Two, the scaled version will look much worse regardless if you did the scaling in-engine or pre-rendered the scaled version (ie, you scaled it down ahead of time in gimp/photoshop).
The correct answer is you have to have an exact pixel match for your art to any given display size (read: not feasible).
Anyways, if those 2 lazy reasons don't scare you away, then consider this: scaling graphics up or down too much will always look bad regardless of the originals' size. I believe the magic cutoff is about 50% up or down before it really starts looking terrible.
Example time. Let's say I have a 5000x5000 original, which should be considered excessive. Yet, it does fit the artists' idea of a very large original, and if we can just scale it down to fit our needs, what's the problem as long as we scale it down before we actually use it?
Think like an artist here. a 5000x5000 original will look absolutely amazing, and the art going in a game should look amazing, so what's the problem? Well, aside from the obvious memory issue (5000x5000 = 25 million pixels, at 4 bytes per pixel... 100 million bytes to even open that graphic in game!), the appearance will be very terrible if you have to scale it down to something like 128x128. Go ahead and try it in your favorite raster art program, make a doodle at 5000x5000 and scale it to 128x128 and look what happens, especially around the edges!
Now, this issue is actually more problematic, not only will this scaled version look horrendous, it will actually likely get scaled again when you go to display it in game! A scaled version of an already bad scaled version will look catastrophic at best.
We could take some less absurd examples, but hopefully you get the idea that a scale of a scale is bad... with larger scaling happening anywhere meaning exponentially bad results.
Vector art sort of fixes this (it's not a panacea though). The original export will get you a more or less "perfect" raster version at your specified dimensions during the export process. There isn't any scaling of a raster, there is just a mathematically generated piece of art. This doesn't work too well with very small graphics (like exporting to say under 32x32ish), so if you're dealing with very small graphics, it is probably best to start doing pixel art.
This generated/exported art will still probably get scaled when it comes time to use in your game and this is the reason why you will likely want various versions of each art asset for different display densities (which is a whole other topic). Long story short though, you will want to export new originals from the vector art at different pixel sizes rather than scaling your already generated raster art. The result will likely be much sharper looking art in the end product! I said likely because there are other steps that can mess up your art all along the way.
Next article I'll cover more about finally putting some of these graphics to work and texture atlases.
Check out part 2
Suffice to say, graphics aren't an easy topic for a programmer to really "get" aside from binary values for R G B A. Yet, for art people, it's all about hues, lighting, perspective, and all that other non-programmer-technical stuff...
Why am I rambling about all of this? Because if you want to incorporate 2d graphics, you will likely need to interact with artists (unless you're the artist, but you should still take heed!), and likewise, they will have to interact with you... and this is where things can get interesting.
Through some miracle, programmers and artists are working together, but how exactly does all this neat 2d art actually work and get in to a game? Texture atlases.
Well, let's rewind a bit, the most basic thing is a single graphic.
Now, how you take a single graphic and display it in a game is dependent on your environment, game engine, and all that other stuff. For the sake of this article, I will not be delving in to any technical examples of how to use any graphics libraries (you won't be seeing any code!) -- I'm more going to focus on *methods* of putting art in to a game.
Now, some programmers might think "methods" and think of programming -- well, reminder, not everyone thinks the same words mean the same things... "methods" can also mean the process of how you accomplish some task... like an artist might use a certain method to create your art, but that has nothing to do with your actual programmatic method used to display that art in your game... or your method of how to implement your method to display the art...
Anyways, back to graphics!
There are some technical issues that you and/or your artist should know right at the get go. First, some terminology.
Raster Graphics - This refers to graphics that are pixel data. Stuff like png files, raw RGBA binary data, bitmaps, things that are defined by pixels. All of this stuff is collectively called "raster graphics". This is as opposed to...
Vector Graphics - These graphics are a bit more complicated and usually not useful to implement directly in to games. However, there are some pretty huge perks to having an artist use this format as opposed to raster graphics. With vector graphics, the artwork is now a collection of mathematical shapes assigned various colors. This means that, like all math, the original will always remain true, regardless of "zoom level" or how much you scale it; unlike raster graphics which use filters to "approximate" when scaling.
The issue of scaling graphics is complex and is worthwhile to research, but the skinny version is that raster graphics lose quality every time you scale up or down from the original until you will just end up with a blob. With vector graphics, you can essentially scale up, down, shear, or do anything else to it without losing quality, as much as you want to.
Now, I mentioned vector isn't directly useful to games. This is true, rendering vector graphics is a massively difficulty task for even today's hardware. Sure, you could render a couple dozen vector graphics, but you need to realize that the graphic being displayed is generated by math, and if that needs to be refreshed (like during a screen redraw!), it could potentially need to be regenerated; so if the shape is complex enough, it will ruin your game's performance.
Ok, now that we got all that out there, it is really only practical to use raster graphics in games! Graphics programming is all about using pixel data to feed directly in to some framebuffer, or use as texels for polygons, or things like this. Someone will need to convert vector in to raster before it can be directly useful in a game. Thankfully, most (all?) vector programs have an export feature and will allow someone to export vector art (which is flawless!) in to a rasterized version of that art. What's even better is that you can essentially export to some given scale right away!
I was once confronted with the idea that an artist could "just give me a really large original" from photoshop and then I could just scale it down based on my need at the time. While this may sound "ok", this is not ok.
Let's talk about graphics scaling some more to hopefully highlight why this isn't acceptable.
We're living in a day and age of thousands of devices, smartphones, tablets, computer monitors, etc. All of them have different display sizes and capacities (what a nightmare!). If you want to deploy your game to some/any/all of them, you will need different sizes for all of your art... meaning a LOT of scaling up and down. But, how do you know what size art you need, or rather, what size would look the best on some given device?
The lazy answer is "just use a big version and scale down", but this actually isn't a good answer at all for 2 reasons. One, you use excessive amounts of memory/cpu/gpu when you scale it in your game engine. Two, the scaled version will look much worse regardless if you did the scaling in-engine or pre-rendered the scaled version (ie, you scaled it down ahead of time in gimp/photoshop).
The correct answer is you have to have an exact pixel match for your art to any given display size (read: not feasible).
Anyways, if those 2 lazy reasons don't scare you away, then consider this: scaling graphics up or down too much will always look bad regardless of the originals' size. I believe the magic cutoff is about 50% up or down before it really starts looking terrible.
Example time. Let's say I have a 5000x5000 original, which should be considered excessive. Yet, it does fit the artists' idea of a very large original, and if we can just scale it down to fit our needs, what's the problem as long as we scale it down before we actually use it?
Think like an artist here. a 5000x5000 original will look absolutely amazing, and the art going in a game should look amazing, so what's the problem? Well, aside from the obvious memory issue (5000x5000 = 25 million pixels, at 4 bytes per pixel... 100 million bytes to even open that graphic in game!), the appearance will be very terrible if you have to scale it down to something like 128x128. Go ahead and try it in your favorite raster art program, make a doodle at 5000x5000 and scale it to 128x128 and look what happens, especially around the edges!
Now, this issue is actually more problematic, not only will this scaled version look horrendous, it will actually likely get scaled again when you go to display it in game! A scaled version of an already bad scaled version will look catastrophic at best.
We could take some less absurd examples, but hopefully you get the idea that a scale of a scale is bad... with larger scaling happening anywhere meaning exponentially bad results.
Vector art sort of fixes this (it's not a panacea though). The original export will get you a more or less "perfect" raster version at your specified dimensions during the export process. There isn't any scaling of a raster, there is just a mathematically generated piece of art. This doesn't work too well with very small graphics (like exporting to say under 32x32ish), so if you're dealing with very small graphics, it is probably best to start doing pixel art.
This generated/exported art will still probably get scaled when it comes time to use in your game and this is the reason why you will likely want various versions of each art asset for different display densities (which is a whole other topic). Long story short though, you will want to export new originals from the vector art at different pixel sizes rather than scaling your already generated raster art. The result will likely be much sharper looking art in the end product! I said likely because there are other steps that can mess up your art all along the way.
Next article I'll cover more about finally putting some of these graphics to work and texture atlases.
Check out part 2
Monday, February 13, 2012
Design to Product on Android - Art Design (8 / 17)
Ahh, what the game will look like. More importantly, how does the art work in a game title anyways? What is the visual play experience? Also, the design of the art had better match the programming capabilities of the game engine! No point in making beautiful 3d graphics if the software you're making cannot do 3d anything!
For sake of simplicity, our studio is currently using mostly Inkscape (it's free!) for high quality Scalable Vector Graphics. We have limited talent in-house for art, so this takes us a little while to "get right".
Android apps require some special handling when it comes to the artwork, specifically with catering to different graphics densities on various displays. This means that ideally, we will have a couple different versions of the same piece of art so that displays that can do "high definition" can use higher quality graphics, while displays that are from forever-ago can still render something (albeit very pixelly - hah new word).
The design of the art should be such that the same art can be easily scaled up and down. This requirement led us to Inkscape (or Illustrator I suppose if you wanna pay money) so that we retain ultimate flexibility with scaling stuff up or down while using the same piece of art. Short of pixel art, vector graphics are simply amazing and save a ton of time later down the road when you want to recycle graphics.
To keep things simple, we usually try to make hard colored, cartoony like graphics. The lighting and shading usually translate very well to small display sizes, and that is a big bonus for small displays.
Something that we learned from our earlier title Blocks Away! Is that we can use a grayscale version of a graphic and apply colors (using a multiply colorfilter) to the graphic in the game engine, this reduces the graphics work needed by quite a lot if the graphics themselves are simple enough and don't require too much recoloring work. For example, in that game, we used a single white block, then just recolored the other blocks in the engine. For this new game, we will try to reuse this trick to save work on the art, but ultimately, we may need to have different graphics for differing colors of game pieces.
Regardless of what we do, we need to consider the design of the art itself. Shy away from ultra realistic and super mega amazing high quality stuff -- it simply does not translate well to small screens of phones, plus the production time and cost involved can be astronomical for small studios if this is outsourced, meaning we sort of have to do this ourselves with out limited experience in this area.
Some of the graphics we're probably going to use are here, don't worry, these are just samples and are really low quality -- they are meant to be teasers, rather than directly useful to you the reader. Let's not go stealing people's work now (something that is rampant in the app markets as it is anyways!).
I probably should have mentioned this in the beginning of this article, but our first step here was to more or less finalize what the game visual layout would be. In other words, we took our doodles, cleaned them up, and made actual graphics that represented what the game layout would be. Where does the ad go? How much space would it take up? Where is the playing field, how big is it relative to other graphical assets? From there, then we started making the actual graphics that filled in those zones.
The pic here is our first draft of the layout of the playable game area and where stuff goes. Naturally, this can change a bit over the course of development, but this serves us sufficiently for now.
As a bonus to this article I should mention a bit about display densities. When first developing for Android, I was accustomed to dealing directly with pixel sizes and spaces. This is not generally a good thing for the novice Android developer.
Each Android device has something called a display density, or how many pixels per inch exists on the physical display. This is stupendously important for knowing about how your graphics work with Android apps (specifically for placing them in the correct position!).
A point of reference:
Low density (LDPI) -> 120 dpi
Medium density (MDPI) -> 160 dpi
High density (HDPI) -> 240 dpi
Extra high density (XDPI?) -> 320 dpi (used for tablets probably)
In other words, when making mobile apps and games, you will likely need code that handles each specific density because you definitely have no guarantee that all your customers will be running on the same display density!
For example, if you want to place a graphic "in the middle of the screen", what does that mean? How do you know at what pixel location is the middle of the screen? I will get to these answers during the development cycle in a couple of articles from now. However, an honorable mention happened here because when designing your artwork, you will likely want separate graphic assets for each different density that exists. This directly translates to additional time required to make your product, catering to differing hardware by your customers, and this is only the graphics end of the deal.
Next up, we will start talking about some code (finally!).
For sake of simplicity, our studio is currently using mostly Inkscape (it's free!) for high quality Scalable Vector Graphics. We have limited talent in-house for art, so this takes us a little while to "get right".
Android apps require some special handling when it comes to the artwork, specifically with catering to different graphics densities on various displays. This means that ideally, we will have a couple different versions of the same piece of art so that displays that can do "high definition" can use higher quality graphics, while displays that are from forever-ago can still render something (albeit very pixelly - hah new word).
The design of the art should be such that the same art can be easily scaled up and down. This requirement led us to Inkscape (or Illustrator I suppose if you wanna pay money) so that we retain ultimate flexibility with scaling stuff up or down while using the same piece of art. Short of pixel art, vector graphics are simply amazing and save a ton of time later down the road when you want to recycle graphics.
To keep things simple, we usually try to make hard colored, cartoony like graphics. The lighting and shading usually translate very well to small display sizes, and that is a big bonus for small displays.
Something that we learned from our earlier title Blocks Away! Is that we can use a grayscale version of a graphic and apply colors (using a multiply colorfilter) to the graphic in the game engine, this reduces the graphics work needed by quite a lot if the graphics themselves are simple enough and don't require too much recoloring work. For example, in that game, we used a single white block, then just recolored the other blocks in the engine. For this new game, we will try to reuse this trick to save work on the art, but ultimately, we may need to have different graphics for differing colors of game pieces.
Regardless of what we do, we need to consider the design of the art itself. Shy away from ultra realistic and super mega amazing high quality stuff -- it simply does not translate well to small screens of phones, plus the production time and cost involved can be astronomical for small studios if this is outsourced, meaning we sort of have to do this ourselves with out limited experience in this area.
Some of the graphics we're probably going to use are here, don't worry, these are just samples and are really low quality -- they are meant to be teasers, rather than directly useful to you the reader. Let's not go stealing people's work now (something that is rampant in the app markets as it is anyways!).
![]() |
| Sampling of actual game graphics |
I probably should have mentioned this in the beginning of this article, but our first step here was to more or less finalize what the game visual layout would be. In other words, we took our doodles, cleaned them up, and made actual graphics that represented what the game layout would be. Where does the ad go? How much space would it take up? Where is the playing field, how big is it relative to other graphical assets? From there, then we started making the actual graphics that filled in those zones.
The pic here is our first draft of the layout of the playable game area and where stuff goes. Naturally, this can change a bit over the course of development, but this serves us sufficiently for now.
![]() |
| Layout |
As a bonus to this article I should mention a bit about display densities. When first developing for Android, I was accustomed to dealing directly with pixel sizes and spaces. This is not generally a good thing for the novice Android developer.
Each Android device has something called a display density, or how many pixels per inch exists on the physical display. This is stupendously important for knowing about how your graphics work with Android apps (specifically for placing them in the correct position!).
A point of reference:
Low density (LDPI) -> 120 dpi
Medium density (MDPI) -> 160 dpi
High density (HDPI) -> 240 dpi
Extra high density (XDPI?) -> 320 dpi (used for tablets probably)
In other words, when making mobile apps and games, you will likely need code that handles each specific density because you definitely have no guarantee that all your customers will be running on the same display density!
For example, if you want to place a graphic "in the middle of the screen", what does that mean? How do you know at what pixel location is the middle of the screen? I will get to these answers during the development cycle in a couple of articles from now. However, an honorable mention happened here because when designing your artwork, you will likely want separate graphic assets for each different density that exists. This directly translates to additional time required to make your product, catering to differing hardware by your customers, and this is only the graphics end of the deal.
Next up, we will start talking about some code (finally!).
Subscribe to:
Posts (Atom)

