NonDeterministic Rendering Order?!?!??
by Takuan Daikon · in Torque X 2D · 11/26/2008 (6:49 pm) · 1 replies
This has been driving me absolutely bonkers!
Apparently, the SkyRenderManager's rendering order is non-deterministic and things can be rendered in exactly the wrong order from what you intended. When I say non-deterministic, I only mean after the program starts. The rendering order does not appear to change after the program starts, but it may start with a seemingly random order.
I had suspected this might be the problem, after a day and a half of thinking that my rendering code was completely messed up and double-checking the implementation against my straight-XNA implementation over 20 times, so I put some debug statements in loop of the RenderOpaquePass() method of the SkyRenderManager to determine whether I was right, which simply tells me the name of the material being rendered at each iteration of the loop, so that I could easily determine the rendering order.
It turns out that I was absolutely correct. I have two objects whose RenderInstance objects have the Type property set to RenderInstanceType.Sky, and sometimes at startup they are in the correct order (Skydome then cloud plane), and sometimes they are backwards (cloud plane then sky dome).
It (should be?) fairly quick and simple thing for me to throw in a workaround, but I figured I would at least try to bring this to the attention of the GG devs, as it can be quite a frustrating experience for someone new to the TorqueX engine.
Apparently, the SkyRenderManager's rendering order is non-deterministic and things can be rendered in exactly the wrong order from what you intended. When I say non-deterministic, I only mean after the program starts. The rendering order does not appear to change after the program starts, but it may start with a seemingly random order.
I had suspected this might be the problem, after a day and a half of thinking that my rendering code was completely messed up and double-checking the implementation against my straight-XNA implementation over 20 times, so I put some debug statements in loop of the RenderOpaquePass() method of the SkyRenderManager to determine whether I was right, which simply tells me the name of the material being rendered at each iteration of the loop, so that I could easily determine the rendering order.
It turns out that I was absolutely correct. I have two objects whose RenderInstance objects have the Type property set to RenderInstanceType.Sky, and sometimes at startup they are in the correct order (Skydome then cloud plane), and sometimes they are backwards (cloud plane then sky dome).
It (should be?) fairly quick and simple thing for me to throw in a workaround, but I figured I would at least try to bring this to the attention of the GG devs, as it can be quite a frustrating experience for someone new to the TorqueX engine.
Torque Owner Takuan Daikon
Since the hash code used for sorting seems to change at every compile, it's not exactly ideal when you do in fact have a specific order you wish to use for rendering. My saying it was nondeterministic wasn't exactly correct, it's technically completely deterministic, but it's not controllable by the game developer without changes to the engine, and it's not possible to anticipate what the resulting rendering order will be ahead of time.
Okay, fine, I can deal with the fact that I've run in to an edge case :) I'm just posting this here for information.
I haven't bothered to check, but I doubt this will be a problem anywhere else, since I would suspect that 'regular' 3d meshes are sorted not only by Material but by distance from the camera. I would be VERY surprised if that were not the case, so I guess it's not that big a deal overall.
But still, *why* are so many things in the engine marked internal that would be useful outside of the engine?
I'll give you a perfect example...
If you are creating a custom Material that has to use a RenderTarget, you will need to set that RenderTarget, do your shader passes, resolve the RenderTarget, and get your rendered texture. Pretty standard stuff, "nothing to see here, move along please", right?
However, there are many cases when the TorqueX engine already has a RenderTarget set, such as when any kind of post-processing is in effect, when reflections are being used, when doing split-screen, etc. There are also cases where the terrain engine's clipmaps are leaving their RenderTargets set, and if you can't restore them, you trash the terrain with your custom Material.
And yet, TorqueEngineComponent._ReapplyMainRenderTarget() appears to be the only way to set the engine's RenderTarget back to what it was before your Material was rendered. And it's marked internal.
Okay, yeah, it's easy to just go in there and mark it public, but you get the point, right?