poly.h: Minor naming/consistency cleanups.

This commit is contained in:
Aaron Giles 2021-09-04 16:06:52 -07:00
parent 32267e4852
commit 6abcbde7b3
2 changed files with 83 additions and 78 deletions

View File

@ -119,6 +119,7 @@ public:
// return an item by index // return an item by index
ArrayType &byindex(u32 index) ArrayType &byindex(u32 index)
{ {
assert(index < m_next);
if (index < m_allocated) if (index < m_allocated)
return *item_ptr(index); return *item_ptr(index);
assert(m_chain); assert(m_chain);
@ -128,6 +129,8 @@ public:
// return a contiguous chunk of items // return a contiguous chunk of items
ArrayType *contiguous(u32 index, u32 count, u32 &chunk) ArrayType *contiguous(u32 index, u32 count, u32 &chunk)
{ {
assert(index < m_next);
assert(index + count <= m_next);
if (index < m_allocated) if (index < m_allocated)
{ {
chunk = std::min(count, m_allocated - index); chunk = std::min(count, m_allocated - index);
@ -164,7 +167,7 @@ public:
} }
// allocate a return a new item // allocate a return a new item
ArrayType &next(int index = 0) ArrayType &next(int tracking_index = 0)
{ {
// track the maximum // track the maximum
if (m_next > m_max) if (m_next > m_max)
@ -187,24 +190,25 @@ public:
m_next++; m_next++;
if (TrackingCount > 0) if (TrackingCount > 0)
{ {
assert(index < TrackingCount); assert(tracking_index < TrackingCount);
m_last[index] = item; m_last[tracking_index] = item;
} }
return *item; return *item;
} }
// return the last // return the last
ArrayType &last(int index = 0) const ArrayType &last(int tracking_index = 0) const
{ {
assert(index < TrackingCount); assert(tracking_index < TrackingCount);
assert(m_last[index] != nullptr); assert(m_last[tracking_index] != nullptr);
return *m_last[index]; return *m_last[tracking_index];
} }
private: private:
// internal helper to make size pointers // internal helper to make size pointers
ArrayType *item_ptr(u32 index) ArrayType *item_ptr(u32 index)
{ {
assert(index < m_allocated);
return reinterpret_cast<ArrayType *>(m_base + index * ITEM_SIZE); return reinterpret_cast<ArrayType *>(m_base + index * ITEM_SIZE);
} }
@ -232,13 +236,13 @@ private:
// repopulate items // repopulate items
void repopulate() void repopulate()
{ {
for (int index = 0; index < TrackingCount; index++) for (int tracking_index = 0; tracking_index < TrackingCount; tracking_index++)
if (m_last[index] != nullptr) if (m_last[tracking_index] != nullptr)
{ {
if (m_last[index] == item_ptr(m_next)) if (m_last[tracking_index] == item_ptr(m_next))
m_next++; m_next++;
else else
next(index) = *m_last[index]; next(tracking_index) = *m_last[tracking_index];
} }
} }
@ -291,9 +295,6 @@ public:
poly_manager(running_machine &machine); poly_manager(running_machine &machine);
virtual ~poly_manager(); virtual ~poly_manager();
// getters
uint32_t triangles_drawn() const { return m_triangles; }
// synchronization // synchronization
void wait(char const *debug_reason = "general"); void wait(char const *debug_reason = "general");
@ -314,15 +315,18 @@ public:
uint32_t render_triangle_fan(rectangle const &cliprect, render_delegate callback, int numverts, vertex_t const *v); uint32_t render_triangle_fan(rectangle const &cliprect, render_delegate callback, int numverts, vertex_t const *v);
template<int ParamCount> template<int ParamCount>
uint32_t render_triangle_strip(rectangle const &cliprect, render_delegate callback, int numverts, vertex_t const *v); uint32_t render_triangle_strip(rectangle const &cliprect, render_delegate callback, int numverts, vertex_t const *v);
uint32_t render_triangle_custom(const rectangle &cliprect, render_delegate callback, int startscanline, int numscanlines, const extent_t *extents);
// polygons // polygons
template<int NumVerts, int ParamCount> template<int NumVerts, int ParamCount>
uint32_t render_polygon(const rectangle &cliprect, render_delegate callback, const vertex_t *v); uint32_t render_polygon(rectangle const &cliprect, render_delegate callback, vertex_t const *v);
// direct custom extents
template<int ParamCount>
uint32_t render_extents(rectangle const &cliprect, render_delegate callback, int startscanline, int numscanlines, extent_t const *extents);
// public helpers // public helpers
template<int ParamCount> template<int ParamCount>
int zclip_if_less(int numverts, const vertex_t *v, vertex_t *outv, BaseType clipval); int zclip_if_less(int numverts, vertex_t const *v, vertex_t *outv, BaseType clipval);
private: private:
// number of profiling ticks before we consider a wait "long" // number of profiling ticks before we consider a wait "long"
@ -331,8 +335,8 @@ private:
static constexpr int SCANLINES_PER_BUCKET = 32; static constexpr int SCANLINES_PER_BUCKET = 32;
static constexpr int TOTAL_BUCKETS = (512 / SCANLINES_PER_BUCKET); static constexpr int TOTAL_BUCKETS = (512 / SCANLINES_PER_BUCKET);
// polygon_info describes a single polygon, which includes the poly_params // primitive_info describes a single primitive
struct polygon_info struct primitive_info
{ {
poly_manager * m_owner; // pointer back to the poly manager poly_manager * m_owner; // pointer back to the poly manager
ObjectType * m_object; // object data pointer ObjectType * m_object; // object data pointer
@ -349,14 +353,14 @@ private:
} }
std::atomic<uint32_t> count_next; // number of scanlines and index of next item to process std::atomic<uint32_t> count_next; // number of scanlines and index of next item to process
polygon_info * polygon; // pointer to polygon primitive_info * primitive; // pointer to primitive
int32_t scanline; // starting scanline int32_t scanline; // starting scanline
uint32_t previtem; // index of previous item in the same bucket uint32_t previtem; // index of previous item in the same bucket
extent_t extent[SCANLINES_PER_BUCKET]; // array of scanline extents extent_t extent[SCANLINES_PER_BUCKET]; // array of scanline extents
}; };
// internal array types // internal array types
using polygon_array = poly_array<polygon_info, 0>; using primitive_array = poly_array<primitive_info, 0>;
using unit_array = poly_array<work_unit, 0>; using unit_array = poly_array<work_unit, 0>;
// round in a cross-platform consistent manner // round in a cross-platform consistent manner
@ -369,14 +373,14 @@ private:
} }
// internal helpers // internal helpers
polygon_info &polygon_alloc(int minx, int maxx, int miny, int maxy, render_delegate callback) primitive_info &primitive_alloc(int minx, int maxx, int miny, int maxy, render_delegate callback)
{ {
// return and initialize the next one // return and initialize the next one
polygon_info &polygon = m_polygon.next(); primitive_info &primitive = m_primitive.next();
polygon.m_owner = this; primitive.m_owner = this;
polygon.m_object = &m_object.last(); primitive.m_object = &m_object.last();
polygon.m_callback = callback; primitive.m_callback = callback;
return polygon; return primitive;
} }
// enqueue work items in contiguous chunks // enqueue work items in contiguous chunks
@ -403,7 +407,7 @@ private:
osd_work_queue *m_queue; // work queue osd_work_queue *m_queue; // work queue
// arrays // arrays
polygon_array m_polygon; // array of polygons primitive_array m_primitive; // array of primitives
objectdata_array m_object; // array of object data objectdata_array m_object; // array of object data
unit_array m_unit; // array of work units unit_array m_unit; // array of work units
std::vector<poly_array_base *> m_arrays; // list of arrays we are managing std::vector<poly_array_base *> m_arrays; // list of arrays we are managing
@ -414,7 +418,7 @@ private:
// statistics // statistics
uint32_t m_tiles; // number of tiles queued uint32_t m_tiles; // number of tiles queued
uint32_t m_triangles; // number of triangles queued uint32_t m_triangles; // number of triangles queued
uint32_t m_quads; // number of quads queued uint32_t m_polygons; // number of polygons queued
uint64_t m_pixels; // number of pixels rendered uint64_t m_pixels; // number of pixels rendered
#if KEEP_POLY_STATISTICS #if KEEP_POLY_STATISTICS
uint32_t m_conflicts[WORK_MAX_THREADS] = { 0 }; // number of conflicts found, per thread uint32_t m_conflicts[WORK_MAX_THREADS] = { 0 }; // number of conflicts found, per thread
@ -462,7 +466,7 @@ poly_manager<BaseType, ObjectType, MaxParams, Flags>::poly_manager(running_machi
m_queue(nullptr), m_queue(nullptr),
m_tiles(0), m_tiles(0),
m_triangles(0), m_triangles(0),
m_quads(0), m_polygons(0),
m_pixels(0) m_pixels(0)
{ {
// create the work queue // create the work queue
@ -473,7 +477,7 @@ poly_manager<BaseType, ObjectType, MaxParams, Flags>::poly_manager(running_machi
std::fill_n(&m_unit_bucket[0], std::size(m_unit_bucket), 0xffffffff); std::fill_n(&m_unit_bucket[0], std::size(m_unit_bucket), 0xffffffff);
// register our arrays for reset // register our arrays for reset
register_poly_array(m_polygon); register_poly_array(m_primitive);
register_poly_array(m_object); register_poly_array(m_object);
register_poly_array(m_unit); register_poly_array(m_unit);
@ -524,7 +528,7 @@ poly_manager<BaseType, ObjectType, MaxParams, Flags>::~poly_manager()
// output global stats // output global stats
osd_printf_info("Total triangles = %d\n", m_triangles); osd_printf_info("Total triangles = %d\n", m_triangles);
osd_printf_info("Total quads = %d\n", m_quads); osd_printf_info("Total polygons = %d\n", m_polygons);
if (m_pixels > 1000000000) if (m_pixels > 1000000000)
osd_printf_info("Total pixels = %d%09d\n", uint32_t(m_pixels / 1000000000), uint32_t(m_pixels % 1000000000)); osd_printf_info("Total pixels = %d%09d\n", uint32_t(m_pixels / 1000000000), uint32_t(m_pixels % 1000000000));
else else
@ -532,7 +536,7 @@ poly_manager<BaseType, ObjectType, MaxParams, Flags>::~poly_manager()
osd_printf_info("Conflicts: %d resolved, %d total\n", resolved, conflicts); osd_printf_info("Conflicts: %d resolved, %d total\n", resolved, conflicts);
osd_printf_info("Units: %5d used, %5d allocated, %4d bytes each, %7d total\n", m_unit.max(), m_unit.allocated(), int(m_unit.itemsize()), int(m_unit.allocated() * m_unit.itemsize())); osd_printf_info("Units: %5d used, %5d allocated, %4d bytes each, %7d total\n", m_unit.max(), m_unit.allocated(), int(m_unit.itemsize()), int(m_unit.allocated() * m_unit.itemsize()));
osd_printf_info("Polygons: %5d used, %5d allocated, %4d bytes each, %7d total\n", m_polygon.max(), m_polygon.allocated(), int(m_polygon.itemsize()), int(m_polygon.allocated() * m_polygon.itemsize())); osd_printf_info("Primitives: %5d used, %5d allocated, %4d bytes each, %7d total\n", m_primitive.max(), m_primitive.allocated(), int(m_primitive.itemsize()), int(m_primitive.allocated() * m_primitive.itemsize()));
osd_printf_info("Object data: %5d used, %5d allocated, %4d bytes each, %7d total\n", m_object.max(), m_object.allocated(), int(m_object.itemsize()), int(m_object.allocated() * m_object.itemsize())); osd_printf_info("Object data: %5d used, %5d allocated, %4d bytes each, %7d total\n", m_object.max(), m_object.allocated(), int(m_object.itemsize()), int(m_object.allocated() * m_object.itemsize()));
} }
#endif #endif
@ -584,17 +588,17 @@ void *poly_manager<BaseType, ObjectType, MaxParams, Flags>::work_item_callback(v
while (1) while (1)
{ {
work_unit &unit = *(work_unit *)param; work_unit &unit = *(work_unit *)param;
polygon_info &polygon = *unit.polygon; primitive_info &primitive = *unit.primitive;
int count = unit.count_next & 0xff; int count = unit.count_next & 0xff;
uint32_t orig_count_next; uint32_t orig_count_next;
// if our previous item isn't done yet, enqueue this item to the end and proceed // if our previous item isn't done yet, enqueue this item to the end and proceed
if (unit.previtem != 0xffffffff) if (unit.previtem != 0xffffffff)
{ {
work_unit &prevunit = polygon.m_owner->m_unit.byindex(unit.previtem); work_unit &prevunit = primitive.m_owner->m_unit.byindex(unit.previtem);
if (prevunit.count_next != 0) if (prevunit.count_next != 0)
{ {
uint32_t unitnum = polygon.m_owner->m_unit.indexof(unit); uint32_t unitnum = primitive.m_owner->m_unit.indexof(unit);
uint32_t new_count_next; uint32_t new_count_next;
// attempt to atomically swap in this new value // attempt to atomically swap in this new value
@ -606,9 +610,9 @@ void *poly_manager<BaseType, ObjectType, MaxParams, Flags>::work_item_callback(v
#if KEEP_POLY_STATISTICS #if KEEP_POLY_STATISTICS
// track resolved conflicts // track resolved conflicts
polygon.m_owner->m_conflicts[threadid]++; primitive.m_owner->m_conflicts[threadid]++;
if (orig_count_next != 0) if (orig_count_next != 0)
polygon.m_owner->m_resolved[threadid]++; primitive.m_owner->m_resolved[threadid]++;
#endif #endif
// if we succeeded, skip out early so we can do other work // if we succeeded, skip out early so we can do other work
if (orig_count_next != 0) if (orig_count_next != 0)
@ -618,7 +622,7 @@ void *poly_manager<BaseType, ObjectType, MaxParams, Flags>::work_item_callback(v
// iterate over extents // iterate over extents
for (int curscan = 0; curscan < count; curscan++) for (int curscan = 0; curscan < count; curscan++)
polygon.m_callback(unit.scanline + curscan, unit.extent[curscan], *polygon.m_object, threadid); primitive.m_callback(unit.scanline + curscan, unit.extent[curscan], *primitive.m_object, threadid);
// set our count to 0 and re-fetch the original count value // set our count to 0 and re-fetch the original count value
do do
@ -630,7 +634,7 @@ void *poly_manager<BaseType, ObjectType, MaxParams, Flags>::work_item_callback(v
orig_count_next >>= 8; orig_count_next >>= 8;
if (orig_count_next == 0) if (orig_count_next == 0)
break; break;
param = &polygon.m_owner->m_unit.byindex(orig_count_next); param = &primitive.m_owner->m_unit.byindex(orig_count_next);
} }
return nullptr; return nullptr;
} }
@ -641,7 +645,7 @@ void *poly_manager<BaseType, ObjectType, MaxParams, Flags>::work_item_callback(v
//------------------------------------------------- //-------------------------------------------------
template<typename BaseType, class ObjectType, int MaxParams, u8 Flags> template<typename BaseType, class ObjectType, int MaxParams, u8 Flags>
void poly_manager<BaseType, ObjectType, MaxParams, Flags>::wait(const char *debug_reason) void poly_manager<BaseType, ObjectType, MaxParams, Flags>::wait(char const *debug_reason)
{ {
// early out if no units outstanding // early out if no units outstanding
if (m_unit.count() == 0) if (m_unit.count() == 0)
@ -682,8 +686,8 @@ template<typename BaseType, class ObjectType, int MaxParams, u8 Flags>
template<int ParamCount> template<int ParamCount>
uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_tile(rectangle const &cliprect, render_delegate callback, vertex_t const &_v1, vertex_t const &_v2) uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_tile(rectangle const &cliprect, render_delegate callback, vertex_t const &_v1, vertex_t const &_v2)
{ {
const vertex_t *v1 = &_v1; vertex_t const *v1 = &_v1;
const vertex_t *v2 = &_v2; vertex_t const *v2 = &_v2;
// first sort by Y // first sort by Y
if (v2->y < v1->y) if (v2->y < v1->y)
@ -710,8 +714,8 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_tile(recta
if (minx > maxx) if (minx > maxx)
return 0; return 0;
// allocate and populate a new polygon // allocate and populate a new primitive
polygon_info &polygon = polygon_alloc(round_coordinate(minx), round_coordinate(maxx), v1yclip, v2yclip, callback); primitive_info &primitive = primitive_alloc(round_coordinate(minx), round_coordinate(maxx), v1yclip, v2yclip, callback);
// compute parameter deltas // compute parameter deltas
std::array<BaseType, ParamCount> param_dpdx; std::array<BaseType, ParamCount> param_dpdx;
@ -758,7 +762,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_tile(recta
scaninc = SCANLINES_PER_BUCKET - uint32_t(curscan) % SCANLINES_PER_BUCKET; scaninc = SCANLINES_PER_BUCKET - uint32_t(curscan) % SCANLINES_PER_BUCKET;
// fill in the work unit basics // fill in the work unit basics
unit.polygon = &polygon; unit.primitive = &primitive;
unit.count_next = std::min(v2yclip - curscan, scaninc); unit.count_next = std::min(v2yclip - curscan, scaninc);
unit.scanline = curscan; unit.scanline = curscan;
unit.previtem = m_unit_bucket[bucketnum]; unit.previtem = m_unit_bucket[bucketnum];
@ -806,9 +810,9 @@ template<typename BaseType, class ObjectType, int MaxParams, u8 Flags>
template<int ParamCount> template<int ParamCount>
uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle(const rectangle &cliprect, render_delegate callback, const vertex_t &_v1, const vertex_t &_v2, const vertex_t &_v3) uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle(const rectangle &cliprect, render_delegate callback, const vertex_t &_v1, const vertex_t &_v2, const vertex_t &_v3)
{ {
const vertex_t *v1 = &_v1; vertex_t const *v1 = &_v1;
const vertex_t *v2 = &_v2; vertex_t const *v2 = &_v2;
const vertex_t *v3 = &_v3; vertex_t const *v3 = &_v3;
// first sort by Y // first sort by Y
if (v2->y < v1->y) if (v2->y < v1->y)
@ -839,8 +843,8 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle(c
BaseType minx = std::min(std::min(v1->x, v2->x), v3->x); BaseType minx = std::min(std::min(v1->x, v2->x), v3->x);
BaseType maxx = std::max(std::max(v1->x, v2->x), v3->x); BaseType maxx = std::max(std::max(v1->x, v2->x), v3->x);
// allocate and populate a new polygon // allocate and populate a new primitive
polygon_info &polygon = polygon_alloc(round_coordinate(minx), round_coordinate(maxx), v1yclip, v3yclip, callback); primitive_info &primitive = primitive_alloc(round_coordinate(minx), round_coordinate(maxx), v1yclip, v3yclip, callback);
// compute the slopes for each portion of the triangle // compute the slopes for each portion of the triangle
BaseType dxdy_v1v2 = (v2->y == v1->y) ? BaseType(0.0) : (v2->x - v1->x) / (v2->y - v1->y); BaseType dxdy_v1v2 = (v2->y == v1->y) ? BaseType(0.0) : (v2->x - v1->x) / (v2->y - v1->y);
@ -899,7 +903,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle(c
scaninc = SCANLINES_PER_BUCKET - uint32_t(curscan) % SCANLINES_PER_BUCKET; scaninc = SCANLINES_PER_BUCKET - uint32_t(curscan) % SCANLINES_PER_BUCKET;
// fill in the work unit basics // fill in the work unit basics
unit.polygon = &polygon; unit.primitive = &primitive;
unit.count_next = std::min(v3yclip - curscan, scaninc); unit.count_next = std::min(v3yclip - curscan, scaninc);
unit.scanline = curscan; unit.scanline = curscan;
unit.previtem = m_unit_bucket[bucketnum]; unit.previtem = m_unit_bucket[bucketnum];
@ -967,7 +971,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle(c
template<typename BaseType, class ObjectType, int MaxParams, u8 Flags> template<typename BaseType, class ObjectType, int MaxParams, u8 Flags>
template<int ParamCount> template<int ParamCount>
uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_fan(const rectangle &cliprect, render_delegate callback, int numverts, const vertex_t *v) uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_fan(rectangle const &cliprect, render_delegate callback, int numverts, vertex_t const *v)
{ {
// iterate over vertices // iterate over vertices
uint32_t pixels = 0; uint32_t pixels = 0;
@ -984,7 +988,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_f
template<typename BaseType, class ObjectType, int MaxParams, u8 Flags> template<typename BaseType, class ObjectType, int MaxParams, u8 Flags>
template<int ParamCount> template<int ParamCount>
uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_strip(const rectangle &cliprect, render_delegate callback, int numverts, const vertex_t *v) uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_strip(rectangle const &cliprect, render_delegate callback, int numverts, vertex_t const *v)
{ {
// iterate over vertices // iterate over vertices
uint32_t pixels = 0; uint32_t pixels = 0;
@ -995,12 +999,13 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_s
//------------------------------------------------- //-------------------------------------------------
// render_triangle_custom - perform a custom // render_extents - perform a custom render of
// render of an object, given specific extents // an object, given specific extents
//------------------------------------------------- //-------------------------------------------------
template<typename BaseType, class ObjectType, int MaxParams, u8 Flags> template<typename BaseType, class ObjectType, int MaxParams, u8 Flags>
uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_custom(const rectangle &cliprect, render_delegate callback, int startscanline, int numscanlines, const extent_t *extents) template<int ParamCount>
uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_extents(rectangle const &cliprect, render_delegate callback, int startscanline, int numscanlines, extent_t const *extents)
{ {
// clip coordinates // clip coordinates
int32_t v1yclip = startscanline; int32_t v1yclip = startscanline;
@ -1013,8 +1018,8 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_c
return 0; return 0;
} }
// allocate and populate a new polygon // allocate and populate a new primitive
polygon_info &polygon = polygon_alloc(0, 0, v1yclip, v3yclip, callback); primitive_info &primitive = primitive_alloc(0, 0, v1yclip, v3yclip, callback);
// compute the X extents for each scanline // compute the X extents for each scanline
int32_t pixels = 0; int32_t pixels = 0;
@ -1030,7 +1035,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_c
scaninc = SCANLINES_PER_BUCKET - uint32_t(curscan) % SCANLINES_PER_BUCKET; scaninc = SCANLINES_PER_BUCKET - uint32_t(curscan) % SCANLINES_PER_BUCKET;
// fill in the work unit basics // fill in the work unit basics
unit.polygon = &polygon; unit.primitive = &primitive;
unit.count_next = std::min(v3yclip - curscan, scaninc); unit.count_next = std::min(v3yclip - curscan, scaninc);
unit.scanline = curscan; unit.scanline = curscan;
unit.previtem = m_unit_bucket[bucketnum]; unit.previtem = m_unit_bucket[bucketnum];
@ -1039,7 +1044,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_c
// iterate over extents // iterate over extents
for (int extnum = 0; extnum < unit.count_next; extnum++) for (int extnum = 0; extnum < unit.count_next; extnum++)
{ {
const extent_t &srcextent = extents[(curscan + extnum) - startscanline]; extent_t const &srcextent = extents[(curscan + extnum) - startscanline];
int32_t istartx = srcextent.startx, istopx = srcextent.stopx; int32_t istartx = srcextent.startx, istopx = srcextent.stopx;
// apply left/right clipping // apply left/right clipping
@ -1057,7 +1062,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_c
extent.stopx = istopx; extent.stopx = istopx;
// fill in the parameters for the extent // fill in the parameters for the extent
for (int paramnum = 0; paramnum < MaxParams; paramnum++) for (int paramnum = 0; paramnum < ParamCount; paramnum++)
{ {
extent.param[paramnum].start = srcextent.param[paramnum].start; extent.param[paramnum].start = srcextent.param[paramnum].start;
extent.param[paramnum].dpdx = srcextent.param[paramnum].dpdx; extent.param[paramnum].dpdx = srcextent.param[paramnum].dpdx;
@ -1088,7 +1093,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_triangle_c
template<typename BaseType, class ObjectType, int MaxParams, u8 Flags> template<typename BaseType, class ObjectType, int MaxParams, u8 Flags>
template<int NumVerts, int ParamCount> template<int NumVerts, int ParamCount>
uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_polygon(const rectangle &cliprect, render_delegate callback, const vertex_t *v) uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_polygon(rectangle const &cliprect, render_delegate callback, vertex_t const *v)
{ {
// determine min/max Y vertices // determine min/max Y vertices
BaseType minx = v[0].x; BaseType minx = v[0].x;
@ -1120,16 +1125,16 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_polygon(co
return 0; return 0;
} }
// allocate a new polygon // allocate a new primitive
polygon_info &polygon = polygon_alloc(round_coordinate(minx), round_coordinate(maxx), minyclip, maxyclip, callback); primitive_info &primitive = primitive_alloc(round_coordinate(minx), round_coordinate(maxx), minyclip, maxyclip, callback);
// walk forward to build up the forward edge list // walk forward to build up the forward edge list
struct poly_edge struct poly_edge
{ {
poly_edge *next; // next edge in sequence poly_edge *next; // next edge in sequence
int index; // index of this edge int index; // index of this edge
const vertex_t *v1; // pointer to first vertex vertex_t const *v1; // pointer to first vertex
const vertex_t *v2; // pointer to second vertex vertex_t const *v2; // pointer to second vertex
BaseType dxdy; // dx/dy along the edge BaseType dxdy; // dx/dy along the edge
std::array<BaseType, MaxParams> dpdy; // per-parameter dp/dy values std::array<BaseType, MaxParams> dpdy; // per-parameter dp/dy values
}; };
@ -1177,7 +1182,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_polygon(co
// determine which list is left/right: // determine which list is left/right:
// if the first vertex is shared, compare the slopes // if the first vertex is shared, compare the slopes
// if the first vertex is not shared, compare the X coordinates // if the first vertex is not shared, compare the X coordinates
const poly_edge *ledge, *redge; poly_edge const *ledge, *redge;
if ((fedgelist[0].v1 == bedgelist[0].v1 && fedgelist[0].dxdy < bedgelist[0].dxdy) || if ((fedgelist[0].v1 == bedgelist[0].v1 && fedgelist[0].dxdy < bedgelist[0].dxdy) ||
(fedgelist[0].v1 != bedgelist[0].v1 && fedgelist[0].v1->x < bedgelist[0].v1->x)) (fedgelist[0].v1 != bedgelist[0].v1 && fedgelist[0].v1->x < bedgelist[0].v1->x))
{ {
@ -1204,7 +1209,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_polygon(co
scaninc = SCANLINES_PER_BUCKET - uint32_t(curscan) % SCANLINES_PER_BUCKET; scaninc = SCANLINES_PER_BUCKET - uint32_t(curscan) % SCANLINES_PER_BUCKET;
// fill in the work unit basics // fill in the work unit basics
unit.polygon = &polygon; unit.primitive = &primitive;
unit.count_next = std::min(maxyclip - curscan, scaninc); unit.count_next = std::min(maxyclip - curscan, scaninc);
unit.scanline = curscan; unit.scanline = curscan;
unit.previtem = m_unit_bucket[bucketnum]; unit.previtem = m_unit_bucket[bucketnum];
@ -1271,8 +1276,8 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_polygon(co
// enqueue the work items // enqueue the work items
queue_items(startunit); queue_items(startunit);
// return the total number of pixels in the triangle // return the total number of pixels in the polygon
m_quads++; m_polygons++;
m_pixels += pixels; m_pixels += pixels;
return pixels; return pixels;
} }
@ -1285,7 +1290,7 @@ uint32_t poly_manager<BaseType, ObjectType, MaxParams, Flags>::render_polygon(co
template<typename BaseType, class ObjectType, int MaxParams, u8 Flags> template<typename BaseType, class ObjectType, int MaxParams, u8 Flags>
template<int ParamCount> template<int ParamCount>
int poly_manager<BaseType, ObjectType, MaxParams, Flags>::zclip_if_less(int numverts, const vertex_t *v, vertex_t *outv, BaseType clipval) int poly_manager<BaseType, ObjectType, MaxParams, Flags>::zclip_if_less(int numverts, vertex_t const *v, vertex_t *outv, BaseType clipval)
{ {
bool prevclipped = (v[numverts - 1].p[0] < clipval); bool prevclipped = (v[numverts - 1].p[0] < clipval);
vertex_t *nextout = outv; vertex_t *nextout = outv;
@ -1298,8 +1303,8 @@ int poly_manager<BaseType, ObjectType, MaxParams, Flags>::zclip_if_less(int numv
// if we switched from clipped to non-clipped, interpolate a vertex // if we switched from clipped to non-clipped, interpolate a vertex
if (thisclipped != prevclipped) if (thisclipped != prevclipped)
{ {
const vertex_t &v1 = v[(vertnum == 0) ? (numverts - 1) : (vertnum - 1)]; vertex_t const &v1 = v[(vertnum == 0) ? (numverts - 1) : (vertnum - 1)];
const vertex_t &v2 = v[vertnum]; vertex_t const &v2 = v[vertnum];
BaseType frac = (clipval - v1.p[0]) / (v2.p[0] - v1.p[0]); BaseType frac = (clipval - v1.p[0]) / (v2.p[0] - v1.p[0]);
nextout->x = v1.x + frac * (v2.x - v1.x); nextout->x = v1.x + frac * (v2.x - v1.x);
nextout->y = v1.y + frac * (v2.y - v1.y); nextout->y = v1.y + frac * (v2.y - v1.y);

View File

@ -3302,19 +3302,19 @@ void n64_rdp::render_spans(int32_t start, int32_t end, int32_t tilenum, bool fli
switch(m_other_modes.cycle_type) switch(m_other_modes.cycle_type)
{ {
case CYCLE_TYPE_1: case CYCLE_TYPE_1:
render_triangle_custom(clip, render_delegate(&n64_rdp::span_draw_1cycle, this), start, (end - start) + 1, spans + offset); render_extents<8>(clip, render_delegate(&n64_rdp::span_draw_1cycle, this), start, (end - start) + 1, spans + offset);
break; break;
case CYCLE_TYPE_2: case CYCLE_TYPE_2:
render_triangle_custom(clip, render_delegate(&n64_rdp::span_draw_2cycle, this), start, (end - start) + 1, spans + offset); render_extents<8>(clip, render_delegate(&n64_rdp::span_draw_2cycle, this), start, (end - start) + 1, spans + offset);
break; break;
case CYCLE_TYPE_COPY: case CYCLE_TYPE_COPY:
render_triangle_custom(clip, render_delegate(&n64_rdp::span_draw_copy, this), start, (end - start) + 1, spans + offset); render_extents<8>(clip, render_delegate(&n64_rdp::span_draw_copy, this), start, (end - start) + 1, spans + offset);
break; break;
case CYCLE_TYPE_FILL: case CYCLE_TYPE_FILL:
render_triangle_custom(clip, render_delegate(&n64_rdp::span_draw_fill, this), start, (end - start) + 1, spans + offset); render_extents<8>(clip, render_delegate(&n64_rdp::span_draw_fill, this), start, (end - start) + 1, spans + offset);
break; break;
} }
wait("render spans"); wait("render spans");