DrawSubset and Transparent Materials
Hi all,
i'm having a problem when using m_Mesh->DrawSubset(i) on some loaded X files, when one of the subset materials is semi (or fully) transparent (depending on what order the subset meshes are stored in the x file), my output is incorrect (blank spaces where the transparent object is). I'm sure the problem is that when an object is transparent it is writing to the ZBuffer which in turn is occluding other subset objects that it should not.
My question is, how can I sort a meshes subsets so that they are rendered in depth order, thus making any transparent objects appear correctly?
I hate doing this (BUMP), but I really would like some help on sorting sub items of a mesh.
Did you turn alpha blending on?
http://www.gamedev.net/community/forums/topic.asp?topic_id=284682
http://www.gamedev.net/community/forums/topic.asp?topic_id=284682
For sorting them from back-to-front you need to get the distance between your object and camera. For fast sorting use for example binary tree.
Quote:Original post by royteusink
Did you turn alpha blending on?
http://www.gamedev.net/community/forums/topic.asp?topic_id=284682
yes, alpha blend is on. The problem is that the zbuffer is being written even if a majority of the texture is see through. So with a rectilinear shape, for instance, if one of the faces has a transparent texture then that whole face is written to the zbuffer. In order to compensate for this I need not to rely on the zbuffer and to render in reverse order.
It boils down to using a 2-phase approach. Fill your frame buffer with ALL opaque geometry (ideally not just the current object) and then go back and render any semi-transparent geometry in back-to-front order.
Ideally you want to sort the transparent geometry but this is non-trivial especially when you start to consider how painful it is for performance. A rough "bucket sort" should be sufficient for most cases - divide depth (or distance from camera) into 5 buckets (for example) and then put each subset into the corresponding bucket, then just render in the order of those buckets. Don't bother sorting within each bucket.
If you implement any sorting I would highly recommend you complement it with some temporal coherency. At a mid to high frame rate the drawing order is unlikely to change much between frames (unless you have fast moving objects and/or cameras) such that you can simply store the previous frames draw-order and maybe run a very quick check to ensure nothing is badly out of order.
As for the finer details of rendering...
For the semi-transparent geometry try rendering with D3DRS_ZWRITEENABLE = FALSE but still allow Z-testing (D3DRS_ZENABLE = TRUE). This is a common approach used when rendering particle systems where the artifacts from z-reject clipping are much more noticeable than incorrect blending. It's a trivial change that might well work for you...
hth
Jack
Ideally you want to sort the transparent geometry but this is non-trivial especially when you start to consider how painful it is for performance. A rough "bucket sort" should be sufficient for most cases - divide depth (or distance from camera) into 5 buckets (for example) and then put each subset into the corresponding bucket, then just render in the order of those buckets. Don't bother sorting within each bucket.
If you implement any sorting I would highly recommend you complement it with some temporal coherency. At a mid to high frame rate the drawing order is unlikely to change much between frames (unless you have fast moving objects and/or cameras) such that you can simply store the previous frames draw-order and maybe run a very quick check to ensure nothing is badly out of order.
As for the finer details of rendering...
For the semi-transparent geometry try rendering with D3DRS_ZWRITEENABLE = FALSE but still allow Z-testing (D3DRS_ZENABLE = TRUE). This is a common approach used when rendering particle systems where the artifacts from z-reject clipping are much more noticeable than incorrect blending. It's a trivial change that might well work for you...
hth
Jack
I understand completly about drawing order and distance from the camera etc, my query is really about the mesh subset data. Should I use something like D3DXConvertMeshSubsetToSingleStrip to get at the subset data in order to calculate a mean z distance (obviously on load time) then use this value to perform a depth sort?
OK, thanks for your help everyone. In the end I used GetAttributeTable on the mesh to give me the offsets to each of the subsets vertices. From here I was able to work out an average z position of each subset and then render in depth order.
One thing that threw me for a while was the get attribute table call worked on some x files and not others, this seems to be a problem with the export and a solution to this is to issue an OptimizeInplace call:-
this ensures that the attributes are sorted correctly before issueing the GetAttributeTable call.
One thing that threw me for a while was the get attribute table call worked on some x files and not others, this seems to be a problem with the export and a solution to this is to issue an OptimizeInplace call:-
opimism_Mesh->OptimizeInplace(D3DXMESHOPT_ATTRSORT, NULL, NULL, NULL, NULL);
this ensures that the attributes are sorted correctly before issueing the GetAttributeTable call.
This topic is closed to new replies.
Advertisement
Popular Topics
Advertisement