When depth buffering coplanar polygons (e.g. when one polygon is used as a “detail” polygon on another), precision problems with coplanar polygons may result in “poke through” artifacts if the vertices of the two polygons are not the same. To eliminate the artifacts, an application should apply a “depth bias” when it renders two coplanar polygons, so that Glide understands which polygon is on top of the other. grDepthBiasLevel() allows an application to specify a depth bias.
void grDepthBiasLevel( FxI16 level )
Specifically, if two polygons are coplanar but do not share vertices, e.g. a surface detail polygon sits on top of a larger polygon, the depth bias level should be incremented or decremented as appropriate for the depth buffer mode and function, per coplanar polygon. For left-handed coordinate systems, where 0x0000 corresponds to “nearest to viewer” and 0xFFFF corresponds “farthest from viewer”, depth bias levels should be decremented on successive renderings of coplanar polygons. When the coplanar polygons have been rendered, the depth bias mode should be reset to 0.
Example Depth Buffering.3 Using a depth bias.
In this code segment, an underlying polygon is rendered, a depth bias is established, and then another polygon is rendered on top of the first one.
/* Render the underlying polygon */
grDrawPolygon( /* base polygon’s parameters */ );
/* Render the composite polygon by first enabling depth bias */
grDepthBiasLevel( -1 );
grDrawPolygon( /* composite polygon’s parameters */ );
/* Disable depth bias */
grDepthBiasLevel( 0 );
When a scene is rendered, some of the objects will undoubtedly obscure other objects. If the viewpoint never changes, you can sort the polygons on z, and draw the scene from back to front.
But what if the viewpoint can change from one frame to the next? Say it’s tracking a cursor controlled by a mouse. The computation cost of re-sorting the scene for each frame can be prohibitive, depending on the complexity of the scene. But a z buffer will solve the problem.
You will still need to transform world coordinates to screen coordinates for each object in the scene, but the transformed vertices can be drawn in any order, without regard to their distance from the viewpoint.
The code segment in Example Depth Buffering.4 shows the depth buffer in action.
Example Depth Buffering.4 Hidden surface removal using a z buffer.
The code segment below leaves out the details of converting a mouse position or movement into a viewpoint and transforming the world coordinates to new screen coordinates.
/* set up a z buffer and depth test */
grDepthBufferMode( GR_DEPTHBUFFER_ZBUFFER );
grDepthBufferFunction( GR_CMPFNC_GREATER ); // 1/Z decreases as Z increases!
grDepthMask( FXTRUE ) ;
while (1) {
/* clear the buffers for each frame */
grBufferClear(0, 0, 0);
/* get the new viewpoint and transform the coordinates */
set_viewpoint_from_mouse();
transform_coordinates();
/*draw the objects in the scene */
draw_objects();
/* display the frame */
grBufferSwap(1);
}
Share with your friends: |