Thursday, February 21, 2013

96 – Run forest, run!

Today's post ain't no filler. I am trying to make and interesting landscape that uses a higher number of assets. So one boulder mesh won't be enough. So let's add another, first without textures:

Now let's see the two meshes together, using the same texture:

If you squint you can tell that there are two different meshes, but otherwise it looks like there is only one. To marginally improve this situation, I change the texture on the new boulder:

It is a little bit easier to tell the difference, but still not great. I need better textures (with some baked AO) and better UV mapping. Up close you can tell that the two boulders are different:

I also added huge barrels just for fun in the idea that I'll stop right here and refactor the physics mesh support. Because it is badly needed. Physics impostor meshes are polluting the resource list and the whole system does more than it is was designed to through hacks.

Here is a sample of the barrel landscape:

The barrels use their current mesh as a physics mesh. This is probably too complicated and could do with a reduction is complexity:

The interesting fact is that barrels can have multiple physics forms and representations. The above one is a full detailed static mesh, but my mobile barrels use a simple mobile cylinder. You can see the two interacting when I place a mobile barrel on a huge static one:

The plan was to stop right here and refactor the physics mesh system, but Chris from Electronic Meteor was kind enough to give me a link to the tree models he is using. I could use any mesh and I have a few available (plus the procedural trees I showed before and never touched since then), but using the same mesh allows for easier screenshot comparison. So I also added tree support.

Still, I couldn't just add trees like that. I did a partial refactor. I started with the resource locations. In the beginning I though that a very convention based system, with a rigid structure where you can easily tell where a resource is located was a good idea. This turned out not to be a great idea. It complicates the pipeline and ultimately flexibility is better.

So I transitioned over all terrain clutter resources and the new one were added using this paradigm. All other resources are yet to be converted. This was done by small incremental changes, each time processing all resources in order to not to break the pipeline and existing resources.

Then I updated the physics impostor system. They no longer pollute the resource list. If you want an object to use a physics impostor, you just set a flag for that mesh and you use it as usual. The engine takes care of all the details behind the background, automatically using the impostor when needed. By default, the physics impostor mash has the same name as the mesh on disk, but with a ".physics" added to the end, before the extension.

So with these two changes, let's add the a tree, first just an untextured trunk:

Oooo... What is this? After some digging, I determine that this is related to bones. My system is very poor at handling bones because I wrote it before I understood the concept. I still need to study bones and after this post I'll be sure to write a proper bone handling system, but for now I just hack it away by adding a rotation:

The next obstacle comes when I try to add the canopy. My system can't handle meshes made out of submeshes that have multiple meshparts. I edit the model in Blender, making each submesh have a single meshpart.

And now another obstacle appears. These tree meshes have vertex colors. I used vertex colors before, but my latest shaders don't support this and neither does the mesh importer. So I update it to ignore the colors. I also log the colors and notice something strange. The colors are all very dark, close to black. What kind of three will this turn out to be with black vertex colors? Maybe I need to use the negative color. Anyway, ignoring colors, we finally get the full mesh:

Next is to load up the textures:

Rendering the canopy requires a similar shader to the grass one, that does not render and does not update the depth buffer for transparent pixels. For grass to work properly with this technique, you need to render grass twice for maximal quality. Strangely for trees, rendering the canopy once or twice makes little difference. I can tells which one is from screenshots, but for the untrained eyes this makes no difference, so I might skip the second render pass for performance reasons. Here is the tree with transparency:

You can also see the trunk texture. Amusingly, this texture eats up 28 MiB on disk and is a total waste for this model :).

And the finals step is to disable face-culling for the canopy to get a richer looking tree. Here is a landscape:

Performance is not great. The main reason is that I decided for the canopy to not have physics. My engine is very physics based. Everything has physics. And when the engine finds the canopy without physics, it gets confused and it can not do frustum culling for the canopies. So all canopies are rendered two times even if not in view. And I am using antialiasing. And a high quality terrain renderer.

The results are very promising, but as you can see, there are tons of smaller issues to fix. I need to do this before I can continue.

No comments:

Post a Comment