Wednesday, May 11, 2011

A Few Technical Problems

Slight hold on the new video and screenshots thanks to final exams and some unanticipated texturing issues.  Good news is that it gives me an opportunity to write a post about the problems I encountered and how I solved them :)

Since my world terrain uses only a handful of textures which are largely repeated and tiled, it makes sense to use a Texture Atlas to organize everything.  However, there are a few problems with this approach.  In the interest of avoiding an extremely long post, I'll only discuss the big one:
 
Mipmapping With Atlased Tiles:

Mipmapping is a fairly ubiquitous technique used to improve both the visual fidelity and performance of interactive 3D environments.  However, it doesn't like to play nicely with texture atlases.  Mipmaps require a series of power-of-two textures receding down from the highest-res base texture to the point at which that texture is reduced to one pixel.

The number of mip levels calculated usually depends on the resolution of the base mip level.  However, in the case my texture atlas, I only want the number of mip levels proceeding until each individual subtexture/tile of the atlas is one pixel, which is a smaller number than that automatically generated for the entire atlas.  The "excess" mip levels contain an invalid mishmash of adjacent tiles, which can cause some really bad visual artifacts in-game.

I solved this problem by artificially "capping" the smallest mip level that the program is allowed to sample texels from.  Normally doing this is fairly trivial, but Unity does not expose any functionality for capping the mip levels in an intuitive way.  I was therefore forced to devise a hack in the fragment shader that clamps the screen-space gradients of texture coordinates -- which are used to calculate which mip level is sampled -- to a range that I found through trial-and-error to restrict the mip level appropriately.

It's an ugly hack, but it works.  I'm tempted to praise Unity for its effective workflow that allowed me to find the appropriate range so quickly through trial and error.  Then again, I wouldn't have needed to resort to such a tactic if Unity exposed the basic functionality that I needed to begin with.

Further reading:  This GPU Gems segment was very helpful; I doubt I would have solved my problem so easily without it.  If anyone else reading this finds themselves pulling their hair out over mipmaps and atlases/tiling, give it a read-through.

------------------

That's it for this one.  Big design post on its way soon!

No comments:

Post a Comment