softpipe: do our own culling, don't rely on the draw module.

May not always happen due to passthrough modes, etc.
This commit is contained in:
Keith Whitwell 2008-04-14 11:32:50 +01:00
parent 0c1cb54923
commit 8e7326832a
2 changed files with 42 additions and 21 deletions

View file

@ -120,8 +120,9 @@ sp_vbuf_set_primitive(struct vbuf_render *vbr, unsigned prim)
/**
* Recalculate prim's determinant.
* XXX is this needed?
* Recalculate prim's determinant. This is needed as we don't have
* get this information through the vbuf_render interface & we must
* calculate it here.
*/
static float
calc_det( const float (*v0)[4],
@ -144,12 +145,21 @@ sp_vbuf_draw(struct vbuf_render *vbr, const ushort *indices, uint nr_indices)
{
struct softpipe_vbuf_render *cvbr = softpipe_vbuf_render(vbr);
struct softpipe_context *softpipe = cvbr->softpipe;
struct draw_stage *setup = softpipe->setup;
unsigned vertex_size = softpipe->vertex_info_vbuf.size * sizeof(float);
unsigned i, j;
void *vertex_buffer = cvbr->vertex_buffer;
cptrf4 v[3];
struct setup_context *setup_ctx = sp_draw_setup_context(setup);
/* XXX: break this dependency - make setup_context live under
* softpipe, rename the old "setup" draw stage to something else.
*/
struct draw_stage *setup = softpipe->setup;
struct setup_context *setup_ctx = sp_draw_setup_context(softpipe->setup);
/* XXX: call this from allocate_vertices:
*/
setup_prepare( setup_ctx );
switch (cvbr->prim) {
case PIPE_PRIM_TRIANGLES:
@ -189,6 +199,9 @@ sp_vbuf_draw(struct vbuf_render *vbr, const ushort *indices, uint nr_indices)
break;
}
/* XXX: why are we calling this??? If we had to call something, it
* would be a function in sp_setup.c:
*/
sp_draw_flush( setup );
}

View file

@ -97,31 +97,35 @@ struct setup_context {
uint numFragsEmitted; /**< per primitive */
uint numFragsWritten; /**< per primitive */
#endif
unsigned winding; /* which winding to cull */
};
/**
* Recalculate prim's determinant.
* XXX is this needed?
*/
static INLINE float
calc_det( const float (*v0)[4],
const float (*v1)[4],
const float (*v2)[4] )
static boolean cull_tri( struct setup_context *setup,
float det )
{
/* edge vectors e = v0 - v2, f = v1 - v2 */
const float ex = v0[0][0] - v2[0][0];
const float ey = v0[0][1] - v2[0][1];
const float fx = v1[0][0] - v2[0][0];
const float fy = v1[0][1] - v2[0][1];
if (det != 0)
{
/* if (det < 0 then Z points toward camera and triangle is
* counter-clockwise winding.
*/
unsigned winding = (det < 0) ? PIPE_WINDING_CCW : PIPE_WINDING_CW;
if ((winding & setup->winding) == 0)
return FALSE;
}
/* det = cross(e,f).z */
return ex * fy - ey * fx;
/* Culled:
*/
return TRUE;
}
/**
* Clip setup->quad against the scissor/surface bounds.
*/
@ -709,8 +713,10 @@ void setup_tri( struct setup_context *setup,
setup->numFragsWritten = 0;
#endif
setup_sort_vertices( setup, calc_det(v0, v1, v2),
v0, v1, v2 );
if (cull_tri( setup, det ))
return;
setup_sort_vertices( setup, det, v0, v1, v2 );
setup_tri_coefficients( setup );
setup_tri_edges( setup );
@ -1223,6 +1229,8 @@ void setup_prepare( struct setup_context *setup )
setup->quad.nr_attrs = fs->info.num_inputs;
sp->quad.first->begin(sp->quad.first);
}
setup->winding = sp->rasterizer->cull_mode;
}