Some coding problems are stubborn – I find myself looking back at a week of working realizing that all I really did was prove that a bunch of theoretical improvements don’t work in practice.
Improving OBJ throughput is one of those problems. On a high-end machine, even drastic changes to the OBJ engine make only the slightest difference in throughput – 2 or 3% at best. Every improvement counts, but a 3% improvement doesn’t change the game for how we draw scenery.
There is at least one route I haven’t had time to go down yet: object instancing. The theory is that by making many objects appear with only one object drawn, we get a multiplier, e.g. a 2x or 4x or larger amplification of the number of objects we can have.
In practice it won’t be that simple:
- To get such an amplification we have to recognize groups of the exact same object. Grouped objects will have to be culled together. So we might get a hit in performance as we draw more objects that are off-screen, just to use instancing.
- It may be that the grouping requirement is so severe that it is not practical to find and group objects arbitrarily (instead we would have to group objects that are built together, like clusters of runway lights). That might limit the scope of where we can instance.
- The objects have to look more or less the same, so some categories of very complex objects won’t be subject to instancing. (E.g. objects with animation where each object might look different.)
- I have already coded some experiments with geometry shaders, and the results are just dreadful – geometry shaders simply don’t output a huge number of vertices efficiently, so they don’t help us increase our total vertex throughput. The experience has left me with a “prove it” attitude toward GL extensions that are supposed to make things faster.
When will we know whether instancing can help? I don’t know — I suspect that I won’t be able to find time for code experiments for a bit, due to other work, particularly on scenery creation and tools.