Home       About Me       Contact       Downloads       Part 41    Part 43   

Part 42: Planets are Complicated

November 27, 2011

At the end of the last part, I had coded up a shader which draws a sphere as a texture. I wanted to continue on with this until I rendered atmosphere correctly with blue skies and red sunsets. However, I am finding it a real chore to debug shaders.

I'm not sure what tools other people use. Google finds something called GLSL Devil that looks like a complete tool, but other comments on the net don't seem to think too highly of it. I also didn't want to risk messing up my development environment installing that or another low-level debugger. Instead, I did something else.

The problem with debugging the shaders isn't the syntax or other details of the code. The compiler messages are terse but they do the job. Instead, the problem is debugging the algorithm. I want to walk through statements and see intermediate results, and put out trace files. Some of the advice on the net tells you to just draw intermediate results as graphical output. If the shader variable is 0, you'll see black. If it's 1, you'll see white, etc. That's not what I'm used to.

So I coded up a little testbed for shader logic. In the full app, I can hit my debug key, which sets a flag causing the shader inputs to be written to the trace file. This is only for the quad and shader I used to render the planet. I write out the vertexes and the transform matrices.

The testbed takes this input and renders the quad. This is not an OpenGL application. A simple rendering path is implemented in C++, with the code setting pixels in a bitmap. The important thing is the inner loop. After I have all the interpolated shader inputs for a pixel, I call a "shader" method. This method has all the same logic as the real fragment shader does, but written in C++. I can step through it and debug it normally. When the logic is right, I can translate that into GLSL without much trouble.

It took me a couple of days to get that the way I wanted it, but then I continued with rendering the planet.

More Planet Shading

First, I added diffuse lighting, then a specular highlight from the sun. This makes the entire surface shiny, including clouds and land. To make only the water shiny, I needed to mask everything else. I regenerated the terrain texture and used the alpha component to indicate the "shininess factor". Currently, this is just the percentage of water showing at that pixel.

A couple of weeks ago, I ran into this video of Earth from the space station (Figure 1). Flying over city lights looked so neat that I decided to add some to my planet image. I'm tempted to add an aurora, but I'm not sure how to get the effect you see in the video. I also need to do something more with clouds.

Fig 1: Earth from space

All three of these elements -- lights, clouds and (maybe) aurora, should be dynamic. As people build, there will be more lights. Cloud cover will change with the weather, and an aurora slowly shifts pattern around the poles. I can compute a completely new texture pattern for the world in the background, but a single texture isn't enough. Lights from the ground show on the dark side, but not so much on the light side. They are also dimmed by the clouds. To do this right, I needed a second texture, which currently has lights (on the red channel) and clouds (on green.) I changed the shader to combine these elements with the terrain, applying diffuse and specular lighting.

This all seems like overkill, but if I use a static pattern of clouds or lights, it will be noticeable in the game. It will be raining at ground level (since I want weather to change there), but when you get high enough, the pattern would change to the static texture. It might even be useful to game play to see city lights, since it makes it easier to find communities. Of course, so would a map...

Coding up a realistic city light pattern was more of a project than I wanted to do now, so I just used some simplex noise to make a lava pattern over the world. In Figure 2, you can see the results so far. We're looking at the dark side of the planet with bright lava below, partially obscured by clouds. You can see the specular highlight on the ocean, and see that it does not reflect off the clouds or land.

Fig 2: The Planet So Far

This doesn't look too bad, but I still have things to do here:

  • I need a more complex terrain. This version was just a quick stand-in done months ago to get continent outlines. I really need to do a serious job on terrain, so that there's something nice at ground level, and then rebuild the planet texture based on that.

  • Clouds look nice, but the scale is wrong. To cover the entire planet, a much more complex weather system needs to be mocked up. How much should I do on that? Are storms really going to swirl across the world, etc?

  • If I had good landscape, how much difference would bump mapping make? Clouds are also irritatingly three dimensional. Should I bump map them too?

  • An aurora is overkill, but I'm still tempted. It looks so cool!

  • I'm currently using six 1024 by 1024 textures, one for terrain and another for clouds/lights. That's a lot of texture memory (48 meg!), and you can still see the pixels even at 1000km high. I still have the moon and ring to do as well. I'm not sure what to do about that.

I spent the rest of the week fooling with some other shader experiments that didn't pan out at all, so I'm not going to write them up.

Home       About Me       Contact       Downloads       Part 41    Part 43   

blog comments powered by Disqus