draw: more flatshade_first changes
- Reduce the number of changes to the normal vertex ordering - Assume that the hardware knows how to do this in the standard case. - Add support to the passthrough vcache path.
This commit is contained in:
@@ -343,21 +343,11 @@ draw_prim( struct draw_context *draw,
|
||||
break;
|
||||
|
||||
case PIPE_PRIM_LINES:
|
||||
if (flatfirst) {
|
||||
for (i = 0; i+1 < count; i += 2) {
|
||||
do_line( draw,
|
||||
TRUE,
|
||||
start + i + 1,
|
||||
start + i + 0);
|
||||
}
|
||||
}
|
||||
else {
|
||||
for (i = 0; i+1 < count; i += 2) {
|
||||
do_line( draw,
|
||||
TRUE,
|
||||
start + i + 0,
|
||||
start + i + 1);
|
||||
}
|
||||
for (i = 0; i+1 < count; i += 2) {
|
||||
do_line( draw,
|
||||
TRUE,
|
||||
start + i + 0,
|
||||
start + i + 1);
|
||||
}
|
||||
break;
|
||||
|
||||
@@ -378,63 +368,31 @@ draw_prim( struct draw_context *draw,
|
||||
break;
|
||||
|
||||
case PIPE_PRIM_LINE_STRIP:
|
||||
if (flatfirst) {
|
||||
for (i = 1; i < count; i++) {
|
||||
do_line( draw,
|
||||
i == 1,
|
||||
start + i,
|
||||
start + i - 1 );
|
||||
}
|
||||
}
|
||||
else {
|
||||
for (i = 1; i < count; i++) {
|
||||
do_line( draw,
|
||||
i == 1,
|
||||
start + i - 1,
|
||||
start + i );
|
||||
}
|
||||
for (i = 1; i < count; i++) {
|
||||
do_line( draw,
|
||||
i == 1,
|
||||
start + i - 1,
|
||||
start + i );
|
||||
}
|
||||
break;
|
||||
|
||||
case PIPE_PRIM_TRIANGLES:
|
||||
if (flatfirst) {
|
||||
if (unfilled) {
|
||||
for (i = 0; i+2 < count; i += 3) {
|
||||
do_ef_triangle( draw,
|
||||
1,
|
||||
~0,
|
||||
start + i + 1,
|
||||
start + i + 2,
|
||||
start + i + 0 );
|
||||
}
|
||||
}
|
||||
else {
|
||||
for (i = 0; i+2 < count; i += 3) {
|
||||
do_triangle( draw,
|
||||
start + i + 1,
|
||||
start + i + 2,
|
||||
start + i + 0 );
|
||||
}
|
||||
if (unfilled) {
|
||||
for (i = 0; i+2 < count; i += 3) {
|
||||
do_ef_triangle( draw,
|
||||
1,
|
||||
~0,
|
||||
start + i + 0,
|
||||
start + i + 1,
|
||||
start + i + 2 );
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (unfilled) {
|
||||
for (i = 0; i+2 < count; i += 3) {
|
||||
do_ef_triangle( draw,
|
||||
1,
|
||||
~0,
|
||||
start + i + 0,
|
||||
start + i + 1,
|
||||
start + i + 2 );
|
||||
}
|
||||
}
|
||||
else {
|
||||
for (i = 0; i+2 < count; i += 3) {
|
||||
do_triangle( draw,
|
||||
start + i + 0,
|
||||
start + i + 1,
|
||||
start + i + 2 );
|
||||
}
|
||||
for (i = 0; i+2 < count; i += 3) {
|
||||
do_triangle( draw,
|
||||
start + i + 0,
|
||||
start + i + 1,
|
||||
start + i + 2 );
|
||||
}
|
||||
}
|
||||
break;
|
||||
@@ -444,15 +402,15 @@ draw_prim( struct draw_context *draw,
|
||||
for (i = 0; i+2 < count; i++) {
|
||||
if (i & 1) {
|
||||
do_triangle( draw,
|
||||
start + i + 0,
|
||||
start + i + 2,
|
||||
start + i + 1,
|
||||
start + i + 0 );
|
||||
start + i + 1 );
|
||||
}
|
||||
else {
|
||||
do_triangle( draw,
|
||||
start + i + 0,
|
||||
start + i + 1,
|
||||
start + i + 2,
|
||||
start + i + 0 );
|
||||
start + i + 2 );
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -479,9 +437,9 @@ draw_prim( struct draw_context *draw,
|
||||
if (flatfirst) {
|
||||
for (i = 0; i+2 < count; i++) {
|
||||
do_triangle( draw,
|
||||
start + i + 1,
|
||||
start + i + 2,
|
||||
start + 0,
|
||||
start + i + 1 );
|
||||
start + 0 );
|
||||
}
|
||||
}
|
||||
else {
|
||||
|
@@ -191,7 +191,7 @@ boolean draw_pt_init( struct draw_context *draw )
|
||||
if (!draw->pt.middle.fetch_emit)
|
||||
return FALSE;
|
||||
|
||||
draw->pt.front.vcache = draw_pt_vcache();
|
||||
draw->pt.front.vcache = draw_pt_vcache( draw );
|
||||
if (!draw->pt.front.vcache)
|
||||
return FALSE;
|
||||
|
||||
|
@@ -110,7 +110,7 @@ const void *draw_pt_elt_ptr( struct draw_context *draw,
|
||||
|
||||
/* Implementations:
|
||||
*/
|
||||
struct draw_pt_front_end *draw_pt_vcache( void );
|
||||
struct draw_pt_front_end *draw_pt_vcache( struct draw_context *draw );
|
||||
struct draw_pt_middle_end *draw_pt_fetch_emit( struct draw_context *draw );
|
||||
|
||||
|
||||
|
@@ -44,6 +44,7 @@
|
||||
|
||||
struct vcache_frontend {
|
||||
struct draw_pt_front_end base;
|
||||
struct draw_context *draw;
|
||||
|
||||
unsigned in[CACHE_MAX];
|
||||
ushort out[CACHE_MAX];
|
||||
@@ -157,14 +158,6 @@ static void vcache_quad( struct vcache_frontend *vcache,
|
||||
}
|
||||
|
||||
|
||||
static void vcache_prepare( struct draw_pt_front_end *frontend,
|
||||
struct draw_pt_middle_end *middle )
|
||||
{
|
||||
struct vcache_frontend *vcache = (struct vcache_frontend *)frontend;
|
||||
vcache->middle = middle;
|
||||
middle->prepare( middle );
|
||||
}
|
||||
|
||||
static unsigned reduced_prim[PIPE_PRIM_POLYGON + 1] = {
|
||||
PIPE_PRIM_POINTS,
|
||||
PIPE_PRIM_LINES,
|
||||
@@ -179,11 +172,11 @@ static unsigned reduced_prim[PIPE_PRIM_POLYGON + 1] = {
|
||||
};
|
||||
|
||||
|
||||
static void vcache_run( struct draw_pt_front_end *frontend,
|
||||
unsigned prim,
|
||||
pt_elt_func get_elt,
|
||||
const void *elts,
|
||||
unsigned count )
|
||||
static void vcache_run_pv2( struct draw_pt_front_end *frontend,
|
||||
unsigned prim,
|
||||
pt_elt_func get_elt,
|
||||
const void *elts,
|
||||
unsigned count )
|
||||
{
|
||||
struct vcache_frontend *vcache = (struct vcache_frontend *)frontend;
|
||||
unsigned i;
|
||||
@@ -309,6 +302,109 @@ static void vcache_run( struct draw_pt_front_end *frontend,
|
||||
vcache_flush( vcache );
|
||||
}
|
||||
|
||||
|
||||
static void vcache_run_pv0( struct draw_pt_front_end *frontend,
|
||||
unsigned prim,
|
||||
pt_elt_func get_elt,
|
||||
const void *elts,
|
||||
unsigned count )
|
||||
{
|
||||
struct vcache_frontend *vcache = (struct vcache_frontend *)frontend;
|
||||
unsigned i;
|
||||
|
||||
/* These are for validation only:
|
||||
*/
|
||||
vcache->elt_func = get_elt;
|
||||
vcache->elt_ptr = elts;
|
||||
vcache->output_prim = reduced_prim[prim];
|
||||
|
||||
switch (prim) {
|
||||
case PIPE_PRIM_POINTS:
|
||||
for (i = 0; i < count; i ++) {
|
||||
vcache_point( vcache,
|
||||
get_elt(elts, i) );
|
||||
}
|
||||
break;
|
||||
|
||||
case PIPE_PRIM_LINES:
|
||||
for (i = 0; i+1 < count; i += 2) {
|
||||
vcache_line( vcache,
|
||||
TRUE,
|
||||
get_elt(elts, i + 0),
|
||||
get_elt(elts, i + 1));
|
||||
}
|
||||
break;
|
||||
|
||||
case PIPE_PRIM_LINE_STRIP:
|
||||
for (i = 1; i < count; i++) {
|
||||
vcache_line( vcache,
|
||||
i == 1,
|
||||
get_elt(elts, i - 1),
|
||||
get_elt(elts, i) );
|
||||
}
|
||||
break;
|
||||
|
||||
case PIPE_PRIM_TRIANGLES:
|
||||
for (i = 0; i+2 < count; i += 3) {
|
||||
vcache_triangle( vcache,
|
||||
get_elt(elts, i + 0),
|
||||
get_elt(elts, i + 1),
|
||||
get_elt(elts, i + 2) );
|
||||
}
|
||||
break;
|
||||
|
||||
case PIPE_PRIM_TRIANGLE_STRIP:
|
||||
for (i = 0; i+2 < count; i++) {
|
||||
if (i & 1) {
|
||||
vcache_triangle( vcache,
|
||||
get_elt(elts, i + 0),
|
||||
get_elt(elts, i + 2),
|
||||
get_elt(elts, i + 1) );
|
||||
}
|
||||
else {
|
||||
vcache_triangle( vcache,
|
||||
get_elt(elts, i + 0),
|
||||
get_elt(elts, i + 1),
|
||||
get_elt(elts, i + 2) );
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case PIPE_PRIM_TRIANGLE_FAN:
|
||||
for (i = 0; i+2 < count; i++) {
|
||||
vcache_triangle( vcache,
|
||||
get_elt(elts, i + 1),
|
||||
get_elt(elts, i + 2),
|
||||
get_elt(elts, 0) );
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
|
||||
vcache_flush( vcache );
|
||||
}
|
||||
|
||||
static void vcache_prepare( struct draw_pt_front_end *frontend,
|
||||
struct draw_pt_middle_end *middle )
|
||||
{
|
||||
struct vcache_frontend *vcache = (struct vcache_frontend *)frontend;
|
||||
|
||||
if (vcache->draw->rasterizer->flatshade_first)
|
||||
vcache->base.run = vcache_run_pv0;
|
||||
else
|
||||
vcache->base.run = vcache_run_pv2;
|
||||
|
||||
vcache->middle = middle;
|
||||
middle->prepare( middle );
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
static void vcache_finish( struct draw_pt_front_end *frontend )
|
||||
{
|
||||
struct vcache_frontend *vcache = (struct vcache_frontend *)frontend;
|
||||
@@ -322,14 +418,15 @@ static void vcache_destroy( struct draw_pt_front_end *frontend )
|
||||
}
|
||||
|
||||
|
||||
struct draw_pt_front_end *draw_pt_vcache( void )
|
||||
struct draw_pt_front_end *draw_pt_vcache( struct draw_context *draw )
|
||||
{
|
||||
struct vcache_frontend *vcache = CALLOC_STRUCT( vcache_frontend );
|
||||
|
||||
vcache->base.prepare = vcache_prepare;
|
||||
vcache->base.run = vcache_run;
|
||||
vcache->base.run = NULL;
|
||||
vcache->base.finish = vcache_finish;
|
||||
vcache->base.destroy = vcache_destroy;
|
||||
vcache->draw = draw;
|
||||
|
||||
memset(vcache->in, ~0, sizeof(vcache->in));
|
||||
|
||||
|
@@ -76,10 +76,6 @@ draw_need_pipeline(const struct draw_context *draw,
|
||||
/* AA lines */
|
||||
if (draw->rasterizer->line_smooth && draw->pipeline.aaline)
|
||||
return TRUE;
|
||||
|
||||
/* first-vertex driven flatshading */
|
||||
if (draw->rasterizer->flatshade && draw->rasterizer->flatshade_first)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
if (points(prim))
|
||||
@@ -116,10 +112,6 @@ draw_need_pipeline(const struct draw_context *draw,
|
||||
/* two-side lighting */
|
||||
if (draw->rasterizer->light_twoside)
|
||||
return TRUE;
|
||||
|
||||
/* first-vertex driven flatshading */
|
||||
if (draw->rasterizer->flatshade && draw->rasterizer->flatshade_first)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* polygon cull - this is difficult - hardware can cull just fine
|
||||
|
Reference in New Issue
Block a user