I resolved my rendering issue thanks to this XNA forum post which indicates that Viewports (which determine which portion of the screen actually gets drawn on) initialize with maximum and minimum depth set to zero. This explains why the problem on xbox only showed up when I was using split-screen, as it involves creating new viewports. So basically all the depth calculations were getting clamped between 0 and 0, effectively rendering the depth buffer useless. A quick change to explicitly set appropriate minimum and maximum depths (0 and 1) fixed the problem completely.
What I don't understand now is why the problem DIDN'T show up on Windows, but I really don't care at this point. There are other weird problems happening on Windows that don't happen on xbox (for some reason, my game sounds don't work on Windows, but they work on Xbox), and I can't be bothered to track down the cause. Probably I need to do a fresh reinstallation on my laptop, but again, can't be bothered.
Anyway, the important thing is it's working correctly now! I can carry on with fruitful development instead of banging my head against bugs.
Monday, October 24, 2011
Render WTF
This past weekend I successfully got a four-player local split-screen demo running on the xbox, and encountered a severe render bug that I have yet to quash, because it only occurs on xbox.
For some reason that I haven't even begun to uncover, my models on xbox render as though the depth buffer is turned off. I've checked the code and the depth buffer is definitely turned on; in fact, the same code renders the same model at a different point in the game with no errors whatsoever. This one's gonna be tough to track down.
Anyway, it does work correctly on my development machine, and I'll post a video soon. It looks pretty awesome if I have to say so myself. ;-)
For some reason that I haven't even begun to uncover, my models on xbox render as though the depth buffer is turned off. I've checked the code and the depth buffer is definitely turned on; in fact, the same code renders the same model at a different point in the game with no errors whatsoever. This one's gonna be tough to track down.
Anyway, it does work correctly on my development machine, and I'll post a video soon. It looks pretty awesome if I have to say so myself. ;-)
Thursday, October 20, 2011
Billboards, an Update
Last night I finally had a breakthrough moment with the billboard thing I discussed in my previous post. It took some time to get it right, because my bullets (which are modeled after a popular open-source game's design) have alpha gradients. The trouble with alpha in general is that it doesn't look right if objects are drawn out of depth order.
To illustrate, imagine two objects, A and B. A is nearer the viewer and a semi-transparent color. B is farther from the viewer, partially obscured by A (i.e. visually overlapping), and nearly opaque.
If B is drawn first followed by A, you'll get what you expect: a view of A, with the obscured part of B semi-visible through A. However, if A is drawn first, the portion of B overlapped by A will appear in front of A, even though foreshortening and other depth cues would indicate it is behind.
This would be easier to explain with a diagram, but I'm not somewhere I can easily draw one. Google around for alpha blend depth sort if you want to learn more.
Anyway, the well-known solution to this is to always draw alpha-blended objects in reverse depth order; that is, draw objects that are farther away from the viewer before drawing objects that are nearer. This of course requires additional processing to sort the objects prior to passing them to the render pipeline.
After doing a lot of searching and seeking of examples, I finally landed on the solution of creating an unsorted vertex buffer and a sorted index buffer. This helps to minimize computational overhead in the sorting process, as it needs only to move 4-byte integers around instead of entire vertex declarations (which, in this example, are 64 bytes in size). Of course, sorting does require knowing the distance from the viewer, which means doing extra work in the form of applying the view and perspective transformations to every vertex to discover their depth. Fortunately that happens pretty quickly, even in software.
I also decided to reduce the likelihood of garbage collection trouble and made the vertex buffer a static array, and use it in a ring queue form. The index buffers are destroyed and recreated every frame, but the vertex array stays put in memory for the lifetime of the containing object. Since the index buffers are usually fairly short (six indices per shot, times however many shots are active on the screen at once which usually isn't many and can be limited by game rules), garbage collection isn't too much of a concern. Again, it's 6 x 4 (six 4-byte indices), or 24 bytes per shot, instead of 4 x 64 (four 64-byte vertices), or 256 bytes per shot.
SO, after a wild evening of coding, I now have a working blaster. I may post a video; I'm rather proud of my accomplishment!
To illustrate, imagine two objects, A and B. A is nearer the viewer and a semi-transparent color. B is farther from the viewer, partially obscured by A (i.e. visually overlapping), and nearly opaque.
If B is drawn first followed by A, you'll get what you expect: a view of A, with the obscured part of B semi-visible through A. However, if A is drawn first, the portion of B overlapped by A will appear in front of A, even though foreshortening and other depth cues would indicate it is behind.
This would be easier to explain with a diagram, but I'm not somewhere I can easily draw one. Google around for alpha blend depth sort if you want to learn more.
Anyway, the well-known solution to this is to always draw alpha-blended objects in reverse depth order; that is, draw objects that are farther away from the viewer before drawing objects that are nearer. This of course requires additional processing to sort the objects prior to passing them to the render pipeline.
After doing a lot of searching and seeking of examples, I finally landed on the solution of creating an unsorted vertex buffer and a sorted index buffer. This helps to minimize computational overhead in the sorting process, as it needs only to move 4-byte integers around instead of entire vertex declarations (which, in this example, are 64 bytes in size). Of course, sorting does require knowing the distance from the viewer, which means doing extra work in the form of applying the view and perspective transformations to every vertex to discover their depth. Fortunately that happens pretty quickly, even in software.
I also decided to reduce the likelihood of garbage collection trouble and made the vertex buffer a static array, and use it in a ring queue form. The index buffers are destroyed and recreated every frame, but the vertex array stays put in memory for the lifetime of the containing object. Since the index buffers are usually fairly short (six indices per shot, times however many shots are active on the screen at once which usually isn't many and can be limited by game rules), garbage collection isn't too much of a concern. Again, it's 6 x 4 (six 4-byte indices), or 24 bytes per shot, instead of 4 x 64 (four 64-byte vertices), or 256 bytes per shot.
SO, after a wild evening of coding, I now have a working blaster. I may post a video; I'm rather proud of my accomplishment!
Tuesday, September 27, 2011
Billboards
No, not the things you see on the highway. A billboard is a special kind of flat surface in a 3D environment that is always oriented toward the observer. Billboarding is a technique often used to put objects into a scene that would be too costly to model out of polygons, by texturing the billboard with an image of the object. Frequently this technique is used for foliage; the illusion is good enough as long as the observer isn't right up on top of the actual billboard polygon.
So, I've been learning to use billboards, after making a remarkable discovery about an open-source game (which is providing much of the inspiration for my main current project). That game involves lots of round projectiles flying about, and instead of modeling the projectiles, they're rendered using billboards. Consider: A sphere that will look reasonably smooth is made up of hundreds of individual triangles, whereas a billboard is (typically) made up of just two. That's a savings of hundreds-less-two per projectile! Brilliant!
Anyhow, that's what I've been up to most recently. That and a bit of music composition. I've decided that this game, which is a shooting game, will be complemented best by a downtempo soundtrack. A little comedic dichotomy of violent gameplay married with soothing music.
So, I've been learning to use billboards, after making a remarkable discovery about an open-source game (which is providing much of the inspiration for my main current project). That game involves lots of round projectiles flying about, and instead of modeling the projectiles, they're rendered using billboards. Consider: A sphere that will look reasonably smooth is made up of hundreds of individual triangles, whereas a billboard is (typically) made up of just two. That's a savings of hundreds-less-two per projectile! Brilliant!
Anyhow, that's what I've been up to most recently. That and a bit of music composition. I've decided that this game, which is a shooting game, will be complemented best by a downtempo soundtrack. A little comedic dichotomy of violent gameplay married with soothing music.
Wednesday, August 17, 2011
Lone Wolf
Woof.
This lone wolf game company thing is a lot of work! And more often than not, I don't want to actually do the work, ya know?
Mostly the setbacks are artistic ones. Anyone want to make models or textures for me?
This weekend I am going to try to buckle down and make some progress. Recently I did complete the main menu system for the current focus of my efforts (I've mentioned before that I've got four different projects in progress, right?). The one I'm working on right now is a multiplayer tank combat game. The other three are a unique approach to brick-breaker games, a maze navigation game, and a racing game.
So, hopefully that means I'll have something worthwhile to report next week. Some actual progress, hey? That'll be novel.
This lone wolf game company thing is a lot of work! And more often than not, I don't want to actually do the work, ya know?
Mostly the setbacks are artistic ones. Anyone want to make models or textures for me?
This weekend I am going to try to buckle down and make some progress. Recently I did complete the main menu system for the current focus of my efforts (I've mentioned before that I've got four different projects in progress, right?). The one I'm working on right now is a multiplayer tank combat game. The other three are a unique approach to brick-breaker games, a maze navigation game, and a racing game.
So, hopefully that means I'll have something worthwhile to report next week. Some actual progress, hey? That'll be novel.
Tuesday, August 2, 2011
What Were They Thinking?
I am stepping slightly out of character and significantly off-topic because I am watching Stargate Atlantis on Netflix.
Why is Tayla singing?!?!?!
In other news, I'm working on menus for the next game I think is most likely to hit the market.
Why is Tayla singing?!?!?!
In other news, I'm working on menus for the next game I think is most likely to hit the market.
Tuesday, July 26, 2011
Simplify, Simplify, Simplify
I've realized that my biggest obstacle to releasing a game is my tendency to over-complicate it. Not necessarily in the sense of complicated game-play, but in the sense of thinking of feature after feature to add. That of course means more time spent developing and debugging.
The reality is that this is a game I'm going to sell for a dollar. One measly dollar! So, I've reached a conclusion. Simplify! Simpler features, simpler graphics, simpler everything.
This'll be hard to stick to! We'll see how it goes.
The reality is that this is a game I'm going to sell for a dollar. One measly dollar! So, I've reached a conclusion. Simplify! Simpler features, simpler graphics, simpler everything.
This'll be hard to stick to! We'll see how it goes.
Subscribe to:
Posts (Atom)