- The code cleanup continues.
This commit is contained in:
rogerman 2015-05-11 08:54:01 +00:00
parent 28d40ffcf5
commit b41c194c10
8 changed files with 330 additions and 305 deletions

View File

@ -1054,7 +1054,7 @@ Render3DError OpenGLRenderer_3_2::BeginRender(const GFX3D &engine)
// safe to use.
glBindBuffer(GL_UNIFORM_BUFFER, OGLRef.uboRenderStatesID);
OGLRenderStates *state = (OGLRenderStates *)glMapBufferRange(GL_UNIFORM_BUFFER, 0, sizeof(OGLRenderStates), GL_MAP_WRITE_BIT | GL_MAP_UNSYNCHRONIZED_BIT);
OGLRenderStates *state = (OGLRenderStates *)glMapBufferRange(GL_UNIFORM_BUFFER, 0, sizeof(OGLRenderStates), GL_MAP_WRITE_BIT | GL_MAP_INVALIDATE_RANGE_BIT | GL_MAP_UNSYNCHRONIZED_BIT);
state->framebufferSize.x = this->_framebufferWidth;
state->framebufferSize.y = this->_framebufferHeight;

View File

@ -260,7 +260,7 @@ CACHE_ALIGN u8 mixTable555[32][32][32];
CACHE_ALIGN u32 dsDepthExtend_15bit_to_24bit[32768];
//is this a crazy idea? this table spreads 5 bits evenly over 31 from exactly 0 to INT_MAX
CACHE_ALIGN const int material_5bit_to_31bit[] = {
CACHE_ALIGN const u32 material_5bit_to_31bit[] = {
0x00000000, 0x04210842, 0x08421084, 0x0C6318C6,
0x10842108, 0x14A5294A, 0x18C6318C, 0x1CE739CE,
0x21084210, 0x25294A52, 0x294A5294, 0x2D6B5AD6,
@ -325,7 +325,7 @@ int _hack_getMatrixStackLevel(int which) { return mtxStack[which].position; }
static CACHE_ALIGN s32 mtxCurrent [4][16];
static CACHE_ALIGN s32 mtxTemporal[16];
static u32 mode = 0;
static MatrixMode mode = MATRIXMODE_PROJECTION;
// Indexes for matrix loading/multiplication
static u8 ML4x4ind = 0;
@ -337,7 +337,7 @@ static u8 MM3x3ind = 0;
// Data for vertex submission
static CACHE_ALIGN s16 s16coord[4] = {0, 0, 0, 0};
static char coordind = 0;
static u32 vtxFormat = GFX3D_TRIANGLES;
static PolygonPrimitiveType vtxFormat = GFX3D_TRIANGLES;
static BOOL inBegin = FALSE;
// Data for basic transforms
@ -405,7 +405,8 @@ int listTwiddle = 1;
int triStripToggle;
//list-building state
struct tmpVertInfo {
struct tmpVertInfo
{
//the number of verts registered in this list
int count;
//indices to the main vert list
@ -415,7 +416,8 @@ struct tmpVertInfo {
} tempVertInfo;
static void twiddleLists() {
static void twiddleLists()
{
listTwiddle++;
listTwiddle &= 1;
polylist = &polylists[listTwiddle];
@ -436,7 +438,7 @@ static void makeTables() {
//produce the color bits of a 24bpp color from a DS RGB15 using bit logic (internal use only). RGB are reverse of usual
#define RGB15TO24_BITLOGIC_REVERSE(col) ( (material_5bit_to_8bit[(col)&0x1F]<<16) | (material_5bit_to_8bit[((col)>>5)&0x1F]<<8) | material_5bit_to_8bit[((col)>>10)&0x1F] )
for(u16 i=0;i<32768;i++)
for (size_t i = 0; i < 32768; i++)
{
color_15bit_to_24bit[i] = LE_TO_LOCAL_32( RGB15TO24_BITLOGIC(i) );
color_15bit_to_24bit_reverse[i] = LE_TO_LOCAL_32( RGB15TO24_BITLOGIC_REVERSE(i) );
@ -446,21 +448,22 @@ static void makeTables() {
dsDepthExtend_15bit_to_24bit[i] = LE_TO_LOCAL_32( (i*0x200)+((i+1)>>15)*0x01FF );
}
for (int i = 0; i < 65536; i++)
for (size_t i = 0; i < 65536; i++)
float16table[i] = fix2float((signed short)i);
for (int i = 0; i < 1024; i++)
for (size_t i = 0; i < 1024; i++)
float10Table[i] = ((signed short)(i<<6)) / (float)(1<<12);
for (int i = 0; i < 1024; i++)
for (size_t i = 0; i < 1024; i++)
float10RelTable[i] = ((signed short)(i<<6)) / (float)(1<<18);
for (int i = 0; i < 1024; i++)
for (size_t i = 0; i < 1024; i++)
normalTable[i] = ((signed short)(i<<6)) / (float)(1<<15);
for(int r=0;r<=31;r++)
for(int oldr=0;oldr<=31;oldr++)
for(int a=0;a<=31;a++) {
for (size_t r = 0; r <= 31; r++)
for (size_t oldr = 0; oldr <= 31; oldr++)
for (size_t a = 0; a <= 31; a++)
{
int temp = (r*a + oldr*(31-a)) / 31;
mixTable555[a][r][oldr] = temp;
}
@ -601,7 +604,7 @@ void gfx3d_reset()
textureFormat = 0;
texturePalette = 0;
polyAttrPending = 0;
mode = 0;
mode = MATRIXMODE_PROJECTION;
s16coord[0] = s16coord[1] = s16coord[2] = s16coord[3] = 0;
coordind = 0;
vtxFormat = GFX3D_TRIANGLES;
@ -753,10 +756,12 @@ static void SetVertex()
//record the vertex
//VERT &vert = tempVertList.list[tempVertList.count];
int vertIndex = vertlist->count + tempVertInfo.count - continuation;
if(vertIndex<0) {
const size_t vertIndex = vertlist->count + tempVertInfo.count - continuation;
if (vertIndex >= VERTLIST_SIZE)
{
printf("wtf\n");
}
VERT &vert = vertlist->list[vertIndex];
//printf("%f %f %f\n",coordTransformed[0],coordTransformed[1],coordTransformed[2]);
@ -787,7 +792,8 @@ static void SetVertex()
//possibly complete a polygon
{
polygonListCompleted = 2;
switch(vtxFormat) {
switch(vtxFormat)
{
case GFX3D_TRIANGLES:
if(tempVertInfo.count!=3)
break;
@ -797,9 +803,10 @@ static void SetVertex()
SUBMITVERTEX(1,1);
SUBMITVERTEX(2,2);
vertlist->count+=3;
polylist->list[polylist->count].type = 3;
polylist->list[polylist->count].type = POLYGON_TYPE_TRIANGLE;
tempVertInfo.count = 0;
break;
case GFX3D_QUADS:
if(tempVertInfo.count!=4)
break;
@ -809,9 +816,10 @@ static void SetVertex()
SUBMITVERTEX(2,2);
SUBMITVERTEX(3,3);
vertlist->count+=4;
polylist->list[polylist->count].type = 4;
polylist->list[polylist->count].type = POLYGON_TYPE_QUAD;
tempVertInfo.count = 0;
break;
case GFX3D_TRIANGLE_STRIP:
if(tempVertInfo.count!=3)
break;
@ -819,7 +827,7 @@ static void SetVertex()
SUBMITVERTEX(0,0);
SUBMITVERTEX(1,1);
SUBMITVERTEX(2,2);
polylist->list[polylist->count].type = 3;
polylist->list[polylist->count].type = POLYGON_TYPE_TRIANGLE;
if(triStripToggle)
tempVertInfo.map[1] = vertlist->count+2-continuation;
@ -835,6 +843,7 @@ static void SetVertex()
tempVertInfo.first = false;
tempVertInfo.count = 2;
break;
case GFX3D_QUAD_STRIP:
if(tempVertInfo.count!=4)
break;
@ -843,7 +852,7 @@ static void SetVertex()
SUBMITVERTEX(1,1);
SUBMITVERTEX(2,3);
SUBMITVERTEX(3,2);
polylist->list[polylist->count].type = 4;
polylist->list[polylist->count].type = POLYGON_TYPE_QUAD;
tempVertInfo.map[0] = vertlist->count+2-continuation;
tempVertInfo.map[1] = vertlist->count+3-continuation;
if(tempVertInfo.first)
@ -852,6 +861,7 @@ static void SetVertex()
tempVertInfo.first = false;
tempVertInfo.count = 2;
break;
default:
return;
}
@ -867,9 +877,9 @@ static void SetVertex()
if (!(textureFormat & (7 << 26))) // no texture
{
bool duplicated = false;
VERT &vert0 = vertlist->list[poly.vertIndexes[0]];
VERT &vert1 = vertlist->list[poly.vertIndexes[1]];
VERT &vert2 = vertlist->list[poly.vertIndexes[2]];
const VERT &vert0 = vertlist->list[poly.vertIndexes[0]];
const VERT &vert1 = vertlist->list[poly.vertIndexes[1]];
const VERT &vert2 = vertlist->list[poly.vertIndexes[2]];
if ( (vert0.x == vert1.x) && (vert0.y == vert1.y) ) duplicated = true;
else
if ( (vert1.x == vert2.x) && (vert1.y == vert2.y) ) duplicated = true;
@ -880,7 +890,7 @@ static void SetVertex()
if (duplicated)
{
//printf("Line Segmet detected (poly type %i, mode %i, texparam %08X)\n", poly.type, poly.vtxFormat, textureFormat);
poly.vtxFormat = vtxFormat + 4;
poly.vtxFormat = (PolygonPrimitiveType)(vtxFormat + 4);
}
}
@ -910,7 +920,7 @@ static void gfx3d_glTexImage_cache()
texCoordinateTransform = (textureFormat>>30);
}
static void gfx3d_glLightDirection_cache(int index)
static void gfx3d_glLightDirection_cache(const size_t index)
{
s32 v = lightDirection[index];
@ -928,7 +938,7 @@ static void gfx3d_glLightDirection_cache(int index)
//Calculate the half angle vector
s32 lineOfSight[4] = {0, 0, (-1)<<12, 0};
for(int i = 0; i < 4; i++)
for (size_t i = 0; i < 4; i++)
{
cacheHalfVector[index][i] = ((cacheLightDirection[index][i] + lineOfSight[i]));
}
@ -941,7 +951,7 @@ static void gfx3d_glLightDirection_cache(int index)
{
halfLength = abs(halfLength);
halfLength >>= 6;
for(int i = 0; i < 4; i++)
for (size_t i = 0; i < 4; i++)
{
s32 temp = cacheHalfVector[index][i];
temp <<= 6;
@ -955,7 +965,7 @@ static void gfx3d_glLightDirection_cache(int index)
//===============================================================================
static void gfx3d_glMatrixMode(u32 v)
{
mode = (v&3);
mode = (MatrixMode)(v & 0x03);
GFX_DELAY(1);
}
@ -963,13 +973,13 @@ static void gfx3d_glMatrixMode(u32 v)
static void gfx3d_glPushMatrix()
{
//this command always works on both pos and vector when either pos or pos-vector are the current mtx mode
short mymode = (mode==1?2:mode);
const MatrixMode mymode = ((mode == MATRIXMODE_POSITION) ? MATRIXMODE_POSITION_VECTOR : mode);
MatrixStackPushMatrix(&mtxStack[mymode], mtxCurrent[mymode]);
GFX_DELAY(17);
if(mymode==2)
if (mymode == MATRIXMODE_POSITION_VECTOR)
MatrixStackPushMatrix(&mtxStack[1], mtxCurrent[1]);
}
@ -977,10 +987,10 @@ static void gfx3d_glPopMatrix(s32 i)
{
// The stack has only one level (at address 0) in projection mode,
// in that mode, the parameter value is ignored, the offset is always +1 in that mode.
if (mode == 0) i = 1;
if (mode == MATRIXMODE_PROJECTION) i = 1;
//this command always works on both pos and vector when either pos or pos-vector are the current mtx mode
short mymode = (mode==1?2:mode);
const MatrixMode mymode = ((mode == MATRIXMODE_POSITION) ? MATRIXMODE_POSITION_VECTOR : mode);
//i = (i<<26)>>26;
//previously, we sign extended here. that isnt really necessary since the stacks are apparently modularly addressed. so i am somewhat doubtful that this is a real concept.
@ -994,18 +1004,18 @@ static void gfx3d_glPopMatrix(s32 i)
GFX_DELAY(36);
if (mymode == 2)
if (mymode == MATRIXMODE_POSITION_VECTOR)
MatrixStackPopMatrix(mtxCurrent[1], &mtxStack[1], i);
}
static void gfx3d_glStoreMatrix(u32 v)
{
//this command always works on both pos and vector when either pos or pos-vector are the current mtx mode
short mymode = (mode==1?2:mode);
const MatrixMode mymode = ((mode == MATRIXMODE_POSITION) ? MATRIXMODE_POSITION_VECTOR : mode);
//limit height of these stacks.
//without the mymode==3 namco classics galaxian will try to use pos=1 and overrun the stack, corrupting emu
if(mymode==0 || mymode==3)
if (mymode == MATRIXMODE_PROJECTION || mymode == MATRIXMODE_TEXTURE)
v = 0;
v &= 31;
@ -1021,18 +1031,18 @@ static void gfx3d_glStoreMatrix(u32 v)
GFX_DELAY(17);
if(mymode==2)
if (mymode == MATRIXMODE_POSITION_VECTOR)
MatrixStackLoadMatrix(&mtxStack[1], v, mtxCurrent[1]);
}
static void gfx3d_glRestoreMatrix(u32 v)
{
//this command always works on both pos and vector when either pos or pos-vector are the current mtx mode
short mymode = (mode==1?2:mode);
const MatrixMode mymode = ((mode == MATRIXMODE_POSITION) ? MATRIXMODE_POSITION_VECTOR : mode);
//limit height of these stacks
//without the mymode==3 namco classics galaxian will try to use pos=1 and overrun the stack, corrupting emu
if(mymode==0 || mymode==3)
if (mymode == MATRIXMODE_PROJECTION || mymode == MATRIXMODE_TEXTURE)
v = 0;
v &= 31;
@ -1049,7 +1059,7 @@ static void gfx3d_glRestoreMatrix(u32 v)
GFX_DELAY(36);
if (mymode == 2)
if (mymode == MATRIXMODE_POSITION_VECTOR)
MatrixCopy(mtxCurrent[1], MatrixStackGetPos(&mtxStack[1], v));
}
@ -1059,7 +1069,7 @@ static void gfx3d_glLoadIdentity()
GFX_DELAY(19);
if (mode == 2)
if (mode == MATRIXMODE_POSITION_VECTOR)
MatrixIdentity(mtxCurrent[1]);
//printf("identity: %d to: \n",mode); MatrixPrint(mtxCurrent[1]);
@ -1077,7 +1087,7 @@ static BOOL gfx3d_glLoadMatrix4x4(s32 v)
//vector_fix2float<4>(mtxCurrent[mode], 4096.f);
if (mode == 2)
if (mode == MATRIXMODE_POSITION_VECTOR)
MatrixCopy(mtxCurrent[1], mtxCurrent[2]);
//printf("load4x4: matrix %d to: \n",mode); MatrixPrint(mtxCurrent[1]);
@ -1101,7 +1111,7 @@ static BOOL gfx3d_glLoadMatrix4x3(s32 v)
GFX_DELAY(30);
if (mode == 2)
if (mode == MATRIXMODE_POSITION_VECTOR)
MatrixCopy(mtxCurrent[1], mtxCurrent[2]);
//printf("load4x3: matrix %d to: \n",mode); MatrixPrint(mtxCurrent[1]);
return TRUE;
@ -1121,7 +1131,7 @@ static BOOL gfx3d_glMultMatrix4x4(s32 v)
MatrixMultiply(mtxCurrent[mode], mtxTemporal);
if (mode == 2)
if (mode == MATRIXMODE_POSITION_VECTOR)
{
MatrixMultiply(mtxCurrent[1], mtxTemporal);
GFX_DELAY_M2(30);
@ -1152,7 +1162,7 @@ static BOOL gfx3d_glMultMatrix4x3(s32 v)
MatrixMultiply (mtxCurrent[mode], mtxTemporal);
if (mode == 2)
if (mode == MATRIXMODE_POSITION_VECTOR)
{
MatrixMultiply (mtxCurrent[1], mtxTemporal);
GFX_DELAY_M2(30);
@ -1169,7 +1179,6 @@ static BOOL gfx3d_glMultMatrix3x3(s32 v)
{
mtxTemporal[MM3x3ind] = v;
MM3x3ind++;
if ((MM3x3ind & 0x03) == 3) MM3x3ind++;
if (MM3x3ind<12) return FALSE;
@ -1186,7 +1195,7 @@ static BOOL gfx3d_glMultMatrix3x3(s32 v)
MatrixMultiply(mtxCurrent[mode], mtxTemporal);
if (mode == 2)
if (mode == MATRIXMODE_POSITION_VECTOR)
{
MatrixMultiply(mtxCurrent[1], mtxTemporal);
GFX_DELAY_M2(30);
@ -1209,7 +1218,7 @@ static BOOL gfx3d_glScale(s32 v)
if (scaleind < 3) return FALSE;
scaleind = 0;
MatrixScale (mtxCurrent[(mode==2?1:mode)], scale);
MatrixScale(mtxCurrent[(mode == MATRIXMODE_POSITION_VECTOR ? MATRIXMODE_POSITION : mode)], scale);
//printf("scale: matrix %d to: \n",mode); MatrixPrint(mtxCurrent[1]);
GFX_DELAY(22);
@ -1235,7 +1244,7 @@ static BOOL gfx3d_glTranslate(s32 v)
GFX_DELAY(22);
if (mode == 2)
if (mode == MATRIXMODE_POSITION_VECTOR)
{
MatrixTranslate(mtxCurrent[1], trans);
GFX_DELAY_M2(30);
@ -1295,7 +1304,7 @@ static void gfx3d_glNormal(s32 v)
int vertexColor[3] = { emission[0], emission[1], emission[2] };
for(int i=0; i<4; i++)
for (size_t i = 0; i < 4; i++)
{
if (!((lightMask>>i)&1)) continue;
@ -1335,7 +1344,7 @@ static void gfx3d_glNormal(s32 v)
fixedshininess = gfx3d.state.shininessTable[fixedshininess>>5]<<4;
}
for(int c = 0; c < 3; c++)
for (size_t c = 0; c < 3; c++)
{
s32 specComp = ((specular[c] * _lightColor[c] * fixedshininess)>>17); //5 bits for color*color and 12 bits for the shininess
s32 diffComp = ((diffuse[c] * _lightColor[c] * fixed_diffuse)>>17); //5bits for the color*color and 12 its for the diffuse
@ -1344,7 +1353,7 @@ static void gfx3d_glNormal(s32 v)
}
}
for(int c=0;c<3;c++)
for (size_t c = 0; c < 3; c++)
{
colorRGB[c] = std::min(31,vertexColor[c]);
}
@ -1494,7 +1503,7 @@ static void gfx3d_glMaterial1(u32 val)
*/
static void gfx3d_glLightDirection(u32 v)
{
int index = v>>30;
const size_t index = v >> 30;
lightDirection[index] = (s32)(v & 0x3FFFFFFF);
gfx3d_glLightDirection_cache(index);
@ -1503,7 +1512,7 @@ static void gfx3d_glLightDirection (u32 v)
static void gfx3d_glLightColor(u32 v)
{
int index = v>>30;
const size_t index = v >> 30;
lightColor[index] = v;
GFX_DELAY(1);
}
@ -1524,7 +1533,7 @@ static BOOL gfx3d_glShininess (u32 val)
static void gfx3d_glBegin(u32 v)
{
inBegin = TRUE;
vtxFormat = v&0x03;
vtxFormat = (PolygonPrimitiveType)(v & 0x03);
triStripToggle = 0;
tempVertInfo.count = 0;
tempVertInfo.first = true;
@ -1644,7 +1653,7 @@ static BOOL gfx3d_glBoxTest(u32 v)
////---------------------
//transform all coords
for(int i=0;i<8;i++)
for (size_t i = 0; i < 8; i++)
{
//this cant work. its left as a reminder that we could (and probably should) do the boxtest in all fixed point values
//MatrixMultVec4x4_M2(mtxCurrent[0], verts[i].coord);
@ -1660,7 +1669,7 @@ static BOOL gfx3d_glBoxTest(u32 v)
}
//clip each poly
for(int i=0;i<6;i++)
for (size_t i = 0; i < 6; i++)
{
const POLY &thePoly = polys[i];
const VERT *vertTable[4] = {
@ -1673,7 +1682,8 @@ static BOOL gfx3d_glBoxTest(u32 v)
boxtestClipper.clipPoly<false>(thePoly, vertTable);
//if any portion of this poly was retained, then the test passes.
if(boxtestClipper.clippedPolyCounter>0) {
if (boxtestClipper.clippedPolyCounter > 0)
{
//printf("%06d PASS %d\n",boxcounter,gxFIFO.size);
MMU_new.gxstat.tr = 1;
break;
@ -1748,12 +1758,12 @@ static void gfx3d_glVecTest(u32 v)
//================================================================================= (end)
//=================================================================================
void VIEWPORT::decode(u32 v)
void VIEWPORT::decode(const u32 v)
{
x = (v&0xFF);
y = std::min(191,(int)(((v>>8)&0xFF)));
width = (((v>>16)&0xFF)+1)-(v&0xFF);
height = ((v>>24)+1)-((v>>8)&0xFF);
this->x = (v & 0xFF);
this->y = std::min<u8>(191, (v >> 8) & 0xFF);
this->width = ((v >> 16) & 0xFF) + 1 - this->x;
this->height = std::min<u8>(191, (v >> 24) & 0xFF) + 1 - this->y;
}
void gfx3d_glFogColor(u32 v)
@ -1763,7 +1773,7 @@ void gfx3d_glFogColor(u32 v)
void gfx3d_glFogOffset(u32 v)
{
gfx3d.state.fogOffset = (v&0x7fff);
gfx3d.state.fogOffset = (v & 0x7FFF);
}
void gfx3d_glClearDepth(u32 v)
@ -1805,18 +1815,15 @@ void gfx3d_UpdateToonTable(u8 offset, u32 val)
//printf("toon %d set to %04X\n",offset+1,gfx3d.state.u16ToonTable[offset+1]);
}
s32 gfx3d_GetClipMatrix (unsigned int index)
s32 gfx3d_GetClipMatrix(const u32 index)
{
s32 val = MatrixGetMultipliedIndex (index, mtxCurrent[0], mtxCurrent[1]);
//printf("reading clip matrix: %d\n",index);
return (s32)val;
return (s32)MatrixGetMultipliedIndex(index, mtxCurrent[0], mtxCurrent[1]);
}
s32 gfx3d_GetDirectionalMatrix (unsigned int index)
s32 gfx3d_GetDirectionalMatrix(const u32 index)
{
int _index = (((index / 3) * 4) + (index % 3));
const size_t _index = (((index / 3) * 4) + (index % 3));
//return (s32)(mtxCurrent[2][_index]*(1<<12));
return mtxCurrent[2][_index];
@ -1824,12 +1831,12 @@ s32 gfx3d_GetDirectionalMatrix (unsigned int index)
void gfx3d_glAlphaFunc(u32 v)
{
gfx3d.state.alphaTestRef = v&31;
gfx3d.state.alphaTestRef = v & 0x1F;
}
unsigned int gfx3d_glGetPosRes(unsigned int index)
u32 gfx3d_glGetPosRes(const size_t index)
{
return (unsigned int)(PTcoords[index] * 4096.0f);
return (u32)(PTcoords[index] * 4096.0f);
}
//#define _3D_LOG_EXEC
@ -2095,9 +2102,10 @@ void gfx3d_execute3D()
//this is a SPEED HACK
//fifo is currently emulated more accurately than it probably needs to be.
//without this batch size the emuloop will escape way too often to run fast.
const int HACK_FIFO_BATCH_SIZE = 64;
static const size_t HACK_FIFO_BATCH_SIZE = 64;
for(int i=0;i<HACK_FIFO_BATCH_SIZE;i++) {
for (size_t i = 0; i < HACK_FIFO_BATCH_SIZE; i++)
{
if (GFX_PIPErecv(&cmd, &param))
{
//if (isSwapBuffers) printf("Executing while swapbuffers is pending: %d:%08X\n",cmd,param);
@ -2229,7 +2237,7 @@ static void gfx3d_doFlush()
gfx3d.state.activeFlushCommand = gfx3d.state.pendingFlushCommand;
int polycount = polylist->count;
const size_t polycount = polylist->count;
#ifdef _SHOW_VTX_COUNTERS
max_polys = max((u32)polycount, max_polys);
max_verts = max((u32)vertlist->count, max_verts);
@ -2242,7 +2250,7 @@ static void gfx3d_doFlush()
//TODO - this _MUST_ be moved later in the pipeline, after clipping.
//the w-division here is just an approximation to fix the shop in harvest moon island of happiness
//also the buttons in the knights in the nightmare frontend depend on this
for(int i=0; i<polycount; i++)
for (size_t i = 0; i < polycount; i++)
{
// TODO: Possible divide by zero with the w-coordinate.
// Is the vertex being read correctly? Is 0 a valid value for w?
@ -2254,7 +2262,7 @@ static void gfx3d_doFlush()
verty = 1.0f-(verty+vertw)/(2*vertw);
poly.miny = poly.maxy = verty;
for(int j=1; j<poly.type; j++)
for (size_t j = 1; j < poly.type; j++)
{
verty = vertlist->list[poly.vertIndexes[j]].y;
vertw = (vertlist->list[poly.vertIndexes[j]].w != 0.0f) ? vertlist->list[poly.vertIndexes[j]].w : 0.00000001f;
@ -2267,16 +2275,19 @@ static void gfx3d_doFlush()
//we need to sort the poly list with alpha polys last
//first, look for opaque polys
int ctr=0;
for(int i=0;i<polycount;i++) {
POLY &poly = polylist->list[i];
size_t ctr = 0;
for (size_t i = 0; i < polycount; i++)
{
const POLY &poly = polylist->list[i];
if (!poly.isTranslucent())
gfx3d.indexlist.list[ctr++] = i;
}
int opaqueCount = ctr;
const size_t opaqueCount = ctr;
//then look for translucent polys
for(int i=0;i<polycount;i++) {
POLY &poly = polylist->list[i];
for (size_t i = 0; i < polycount; i++)
{
const POLY &poly = polylist->list[i];
if (poly.isTranslucent())
gfx3d.indexlist.list[ctr++] = i;
}
@ -2434,18 +2445,19 @@ void gfx3d_glGetMatrix(unsigned int m_mode, int index, float* dest)
if (index == -1)
src = mtxCurrent[m_mode];
else src = MatrixStackGetPos(&mtxStack[m_mode], index);
for(int i=0;i<16;i++)
for (size_t i = 0; i < 16; i++)
dest[i] = src[i]/4096.0f;
}
void gfx3d_glGetLightDirection(unsigned int index, unsigned int* dest)
void gfx3d_glGetLightDirection(const size_t index, u32 &dst)
{
*dest = lightDirection[index];
dst = lightDirection[index];
}
void gfx3d_glGetLightColor(unsigned int index, unsigned int* dest)
void gfx3d_glGetLightColor(const size_t index, u32 &dst)
{
*dest = lightColor[index];
dst = lightColor[index];
}
void gfx3d_GetLineData(int line, u8** dst)
@ -2462,13 +2474,13 @@ void gfx3d_GetLineData15bpp(int line, u16** dst)
u8* lineData;
gfx3d_GetLineData(line, &lineData);
for(int i=0; i<GFX3D_FRAMEBUFFER_WIDTH; i++)
for (size_t i = 0; i < GFX3D_FRAMEBUFFER_WIDTH; i++)
{
const u8 r = lineData[i*4+0];
const u8 g = lineData[i*4+1];
const u8 b = lineData[i*4+2];
const u8 a = lineData[i*4+3];
buf[i] = R6G6B6TORGB15(r,g,b) | (a==0?0:0x8000);
buf[i] = R6G6B6TORGB15(r,g,b) | ((a == 0) ? 0x0000 : 0x8000);
}
}
@ -2573,16 +2585,16 @@ void gfx3d_savestate(EMUFILE* os)
//dump the render lists
OSWRITE(vertlist->count);
for(int i=0;i<vertlist->count;i++)
for (size_t i = 0; i < vertlist->count; i++)
vertlist->list[i].save(os);
OSWRITE(polylist->count);
for(int i=0;i<polylist->count;i++)
for (size_t i = 0; i < polylist->count; i++)
polylist->list[i].save(os);
for(int i=0;i<4;i++)
for (size_t i = 0; i < 4; i++)
{
OSWRITE(mtxStack[i].position);
for(int j=0;j<mtxStack[i].size*16;j++)
for(size_t j = 0; j < mtxStack[i].size*16; j++)
OSWRITE(mtxStack[i].matrix[j]);
}
@ -2615,24 +2627,25 @@ bool gfx3d_loadstate(EMUFILE* is, int size)
if (version >= 1)
{
OSREAD(vertlist->count);
for(int i=0;i<vertlist->count;i++)
for (size_t i = 0; i < vertlist->count; i++)
vertlist->list[i].load(is);
OSREAD(polylist->count);
for(int i=0;i<polylist->count;i++)
for (size_t i = 0; i < polylist->count; i++)
polylist->list[i].load(is);
}
if (version >= 2)
{
for(int i=0;i<4;i++)
for (size_t i=0; i < 4; i++)
{
OSREAD(mtxStack[i].position);
for(int j=0;j<mtxStack[i].size*16;j++)
for(size_t j = 0; j < mtxStack[i].size*16; j++)
OSREAD(mtxStack[i].matrix[j]);
}
}
if(version>=3) {
if (version >= 3)
{
gxf_hardware.loadstate(is);
}
@ -2664,11 +2677,11 @@ bool gfx3d_loadstate(EMUFILE* is, int size)
#define CLIPLOG2(X,Y,Z)
template<typename T>
static T interpolate(const float ratio, const T& x0, const T& x1) {
static T interpolate(const float ratio, const T& x0, const T& x1)
{
return (T)(x0 + (float)(x1-x0) * (ratio));
}
//http://www.cs.berkeley.edu/~ug/slide/pipeline/assignments/as6/discussion.shtml
#ifdef OPTIMIZED_CLIPPING_METHOD
template<int coord, int which> static FORCEINLINE VERT clipPoint(bool hirez, const VERT *inside, const VERT *outside)
@ -2677,28 +2690,17 @@ static FORCEINLINE VERT clipPoint(const VERT *inside, const VERT *outside, int c
#endif
{
VERT ret;
float coord_inside = inside->coord[coord];
float coord_outside = outside->coord[coord];
float w_inside = inside->coord[3];
float w_outside = outside->coord[3];
float t;
if(which==-1) {
w_outside = -w_outside;
w_inside = -w_inside;
}
t = (coord_inside - w_inside)/ ((w_outside-w_inside) - (coord_outside-coord_inside));
const float coord_inside = inside->coord[coord];
const float coord_outside = outside->coord[coord];
const float w_inside = (which == -1) ? -inside->coord[3] : inside->coord[3];
const float w_outside = (which == -1) ? -outside->coord[3] : outside->coord[3];
const float t = (coord_inside - w_inside) / ((w_outside-w_inside) - (coord_outside-coord_inside));
#define INTERP(X) ret . X = interpolate(t, inside-> X ,outside-> X )
INTERP(coord[0]); INTERP(coord[1]); INTERP(coord[2]); INTERP(coord[3]);
INTERP(texcoord[0]); INTERP(texcoord[1]);
//if(CommonSettings.GFX3D_HighResolutionInterpolateColor)
if (hirez)
{
INTERP(fcolor[0]); INTERP(fcolor[1]); INTERP(fcolor[2]);
@ -2755,7 +2757,6 @@ public:
}
private:
VERT* m_prevVert;
VERT* m_firstVert;
Next& m_next;
@ -2764,15 +2765,8 @@ private:
{
const float *vert0coord = vert0->coord;
const float *vert1coord = vert1->coord;
bool out0, out1;
if(which==-1)
out0 = vert0coord[coord] < -vert0coord[3];
else
out0 = vert0coord[coord] > vert0coord[3];
if(which==-1)
out1 = vert1coord[coord] < -vert1coord[3];
else
out1 = vert1coord[coord] > vert1coord[3];
const bool out0 = (which == -1) ? (vert0coord[coord] < -vert0coord[3]) : (vert0coord[coord] > vert0coord[3]);
const bool out1 = (which == -1) ? (vert1coord[coord] < -vert1coord[3]) : (vert1coord[coord] > vert1coord[3]);
//CONSIDER: should we try and clip things behind the eye? does this code even successfully do it? not sure.
//if(coord==2 && which==1) {
@ -2781,7 +2775,8 @@ private:
//}
//both outside: insert no points
if(out0 && out1) {
if (out0 && out1)
{
CLIPLOG(" both outside\n");
}
@ -2802,7 +2797,8 @@ private:
}
//entering volume: insert clipped point and the next (interior) point
if(out0 && !out1) {
if (out0 && !out1)
{
CLIPLOG(" entering\n");
assert((u32)numScratchClipVerts < MAX_SCRATCH_CLIP_VERTS);
scratchClipVerts[numScratchClipVerts] = clipPoint<coord, which>(hirez, vert1, vert0);
@ -2820,16 +2816,19 @@ public:
m_nextDestVert = verts;
m_numVerts = 0;
}
void clipVert(bool hirez, const VERT *vert)
{
assert((u32)m_numVerts < MAX_CLIPPED_VERTS);
*m_nextDestVert++ = *vert;
m_numVerts++;
}
int finish(bool hirez)
{
return m_numVerts;
}
private:
VERT* m_nextDestVert;
int m_numVerts;
@ -2845,20 +2844,22 @@ typedef ClipperPlane<1,-1,Stage4> Stage3; static Stage3 clipper3 (clipper
typedef ClipperPlane<0, 1,Stage3> Stage2; static Stage2 clipper2 (clipper3); // right plane
typedef ClipperPlane<0,-1,Stage2> Stage1; static Stage1 clipper (clipper2); // left plane
template<bool hirez> void GFX3D_Clipper::clipPoly(const POLY &poly, const VERT **verts)
template<bool useHiResInterpolate>
void GFX3D_Clipper::clipPoly(const POLY &poly, const VERT **verts)
{
CLIPLOG("==Begin poly==\n");
int type = poly.type;
const PolygonType type = poly.type;
numScratchClipVerts = 0;
clipper.init(clippedPolys[clippedPolyCounter].clipVerts);
for(int i=0;i<type;i++)
clipper.clipVert(hirez, verts[i]);
int outType = clipper.finish(hirez);
for (size_t i = 0; i < type; i++)
clipper.clipVert(useHiResInterpolate, verts[i]);
const PolygonType outType = (PolygonType)clipper.finish(useHiResInterpolate);
assert((u32)outType < MAX_CLIPPED_VERTS);
if(outType < 3)
if (outType < POLYGON_TYPE_TRIANGLE)
{
//a totally clipped poly. discard it.
//or, a degenerate poly. we're not handling these right now
@ -2890,15 +2891,8 @@ void GFX3D_Clipper::clipPolyVsPlane(const int coord, int which)
FORCEINLINE void GFX3D_Clipper::clipSegmentVsPlane(VERT** verts, const int coord, int which)
{
bool out0, out1;
if(which==-1)
out0 = verts[0]->coord[coord] < -verts[0]->coord[3];
else
out0 = verts[0]->coord[coord] > verts[0]->coord[3];
if(which==-1)
out1 = verts[1]->coord[coord] < -verts[1]->coord[3];
else
out1 = verts[1]->coord[coord] > verts[1]->coord[3];
const bool out0 = (which == -1) ? (verts[0]->coord[coord] < -verts[0]->coord[3]) : (verts[0]->coord[coord] > verts[0]->coord[3]);
const bool out1 = (which == -1) ? (verts[1]->coord[coord] < -verts[1]->coord[3]) : (verts[1]->coord[coord] > verts[1]->coord[3]);
//CONSIDER: should we try and clip things behind the eye? does this code even successfully do it? not sure.
//if(coord==2 && which==1) {
@ -2907,7 +2901,8 @@ FORCEINLINE void GFX3D_Clipper::clipSegmentVsPlane(VERT** verts, const int coord
//}
//both outside: insert no points
if(out0 && out1) {
if (out0 && out1)
{
CLIPLOG(" both outside\n");
}
@ -2926,11 +2921,11 @@ FORCEINLINE void GFX3D_Clipper::clipSegmentVsPlane(VERT** verts, const int coord
}
//entering volume: insert clipped point
if(out0 && !out1) {
if (out0 && !out1)
{
CLIPLOG(" entering\n");
outClippedPoly.clipVerts[outClippedPoly.type++] = clipPoint(verts[1],verts[0], coord, which);
outClippedPoly.clipVerts[outClippedPoly.type++] = *verts[1];
}
}
@ -2938,7 +2933,7 @@ FORCEINLINE void GFX3D_Clipper::clipPolyVsPlane(const int coord, int which)
{
outClippedPoly.type = 0;
CLIPLOG2("Clipping coord %d against %f\n",coord,x);
for(int i=0;i<tempClippedPoly.type;i++)
for (size_t i = 0; i < tempClippedPoly.type; i++)
{
VERT *testverts[2] = { &tempClippedPoly.clipVerts[i], &tempClippedPoly.clipVerts[(i+1)%tempClippedPoly.type] };
clipSegmentVsPlane(testverts, coord, which);
@ -2958,7 +2953,7 @@ FORCEINLINE void GFX3D_Clipper::clipPolyVsPlane(const int coord, int which)
void GFX3D_Clipper::clipPoly(const POLY &poly, const VERT **verts)
{
int type = poly.type;
const PolygonType type = poly.type;
CLIPLOG("==Begin poly==\n");
@ -2980,7 +2975,7 @@ void GFX3D_Clipper::clipPoly(const POLY &poly, const VERT **verts)
//TODO - we need to parameterize back plane clipping
if(tempClippedPoly.type < 3)
if (tempClippedPoly.type < POLYGON_TYPE_TRIANGLE)
{
//a totally clipped poly. discard it.
//or, a degenerate poly. we're not handling these right now
@ -2992,6 +2987,6 @@ void GFX3D_Clipper::clipPoly(const POLY &poly, const VERT **verts)
clippedPolys[clippedPolyCounter].poly = &poly;
clippedPolyCounter++;
}
}
#endif

View File

@ -122,14 +122,26 @@ inline u32 RGB15TO6665(u16 col, u8 alpha5)
// 15-bit to 24-bit depth formula from http://nocash.emubase.de/gbatek.htm#ds3drearplane
#define DS_DEPTH15TO24(depth) ( dsDepthExtend_15bit_to_24bit[(depth) & 0x7FFF] )
// MATRIX MODES
enum MatrixMode
{
MATRIXMODE_PROJECTION = 0,
MATRIXMODE_POSITION = 1,
MATRIXMODE_POSITION_VECTOR = 2,
MATRIXMODE_TEXTURE = 3
};
// POLYGON PRIMITIVE TYPES
enum
enum PolygonPrimitiveType
{
GFX3D_TRIANGLES = 0,
GFX3D_QUADS = 1,
GFX3D_TRIANGLE_STRIP = 2,
GFX3D_QUAD_STRIP = 3,
GFX3D_LINE = 4
GFX3D_TRIANGLES_LINE = 4,
GFX3D_QUADS_LINE = 5,
GFX3D_TRIANGLE_STRIP_LINE = 6,
GFX3D_QUAD_STRIP_LINE = 7
};
// POLYGON MODES
@ -141,6 +153,13 @@ enum PolygonMode
POLYGON_MODE_SHADOW = 3
};
// POLYGON TYPES
enum PolygonType
{
POLYGON_TYPE_TRIANGLE = 3,
POLYGON_TYPE_QUAD = 4
};
// POLYGON ATTRIBUTES - BIT LOCATIONS
enum
{
@ -271,8 +290,8 @@ typedef struct
} PolygonTexParams;
struct POLY {
int type; //tri or quad
u8 vtxFormat;
PolygonType type; //tri or quad
PolygonPrimitiveType vtxFormat;
u16 vertIndexes[4]; //up to four verts can be referenced by this poly
u32 polyAttr, texParam, texPalette; //the hardware rendering params
u32 viewport;
@ -283,8 +302,8 @@ struct POLY {
vertIndexes[0] = a;
vertIndexes[1] = b;
vertIndexes[2] = c;
if(d != -1) { vertIndexes[3] = d; type = 4; }
else type = 3;
if(d != -1) { vertIndexes[3] = d; type = POLYGON_TYPE_QUAD; }
else type = POLYGON_TYPE_TRIANGLE;
}
u8 getAttributeEnableLightFlags() const
@ -580,7 +599,8 @@ struct INDEXLIST {
struct VIEWPORT {
int x, y, width, height;
u8 x, y;
u16 width, height;
void decode(u32 v);
};
@ -595,7 +615,7 @@ public:
struct TClippedPoly
{
int type; //otherwise known as "count" of verts
PolygonType type; //otherwise known as "count" of verts
POLY *poly;
VERT clipVerts[MAX_CLIPPED_VERTS];
};
@ -721,7 +741,7 @@ extern CACHE_ALIGN u32 color_15bit_to_24bit_reverse[32768];
extern CACHE_ALIGN u16 color_15bit_to_16bit_reverse[32768];
extern CACHE_ALIGN u32 dsDepthExtend_15bit_to_24bit[32768];
extern CACHE_ALIGN u8 mixTable555[32][32][32];
extern CACHE_ALIGN const int material_5bit_to_31bit[32];
extern CACHE_ALIGN const u32 material_5bit_to_31bit[32];
extern CACHE_ALIGN const u8 material_5bit_to_8bit[32];
extern CACHE_ALIGN const u8 material_3bit_to_5bit[8];
extern CACHE_ALIGN const u8 material_3bit_to_6bit[8];
@ -745,11 +765,11 @@ int gfx3d_GetNumPolys();
int gfx3d_GetNumVertex();
void gfx3d_UpdateToonTable(u8 offset, u16 val);
void gfx3d_UpdateToonTable(u8 offset, u32 val);
s32 gfx3d_GetClipMatrix (u32 index);
s32 gfx3d_GetDirectionalMatrix (u32 index);
s32 gfx3d_GetClipMatrix (const u32 index);
s32 gfx3d_GetDirectionalMatrix(const u32 index);
void gfx3d_glAlphaFunc(u32 v);
u32 gfx3d_glGetPosRes(u32 index);
u16 gfx3d_glGetVecRes(u32 index);
u32 gfx3d_glGetPosRes(const size_t index);
u16 gfx3d_glGetVecRes(const size_t index);
void gfx3d_VBlankSignal();
void gfx3d_VBlankEndSignal(bool skipFrame);
void gfx3d_Control(u32 v);

View File

@ -157,9 +157,9 @@ void MatrixIdentity (s32 *matrix)
matrix[0] = matrix[5] = matrix[10] = matrix[15] = 1<<12;
}
s32 MatrixGetMultipliedIndex (int index, s32 *matrix, s32 *rightMatrix)
s32 MatrixGetMultipliedIndex(const u32 index, s32 *matrix, s32 *rightMatrix)
{
int iMod = index%4, iDiv = (index>>2)<<2;
const size_t iMod = index%4, iDiv = (index>>2)<<2;
s64 temp = ((s64)matrix[iMod ]*rightMatrix[iDiv ])+((s64)matrix[iMod+ 4]*rightMatrix[iDiv+1])+
((s64)matrix[iMod+8]*rightMatrix[iDiv+2])+((s64)matrix[iMod+12]*rightMatrix[iDiv+3]);
@ -271,7 +271,7 @@ void MatrixStackPopMatrix (s32 *mtxCurr, MatrixStack *stack, int size)
MatrixCopy (mtxCurr, &stack->matrix[stack->position*16]);
}
s32 * MatrixStackGetPos (MatrixStack *stack, int pos)
s32* MatrixStackGetPos(MatrixStack *stack, const size_t pos)
{
assert(pos<31);
return &stack->matrix[pos*16];
@ -282,7 +282,7 @@ s32 * MatrixStackGet (MatrixStack *stack)
return &stack->matrix[stack->position*16];
}
void MatrixStackLoadMatrix (MatrixStack *stack, int pos, const s32 *ptr)
void MatrixStackLoadMatrix (MatrixStack *stack, const size_t pos, const s32 *ptr)
{
assert(pos<31);
MatrixCopy(&stack->matrix[pos*16], ptr);

View File

@ -49,8 +49,8 @@ void MatrixInit (s32 *matrix);
//without having to make new build types to exclude the assembly files.
//a bit sloppy, but there aint much to it
float MatrixGetMultipliedIndex (int index, float *matrix, float *rightMatrix);
s32 MatrixGetMultipliedIndex (int index, s32 *matrix, s32 *rightMatrix);
float MatrixGetMultipliedIndex (const u32 index, float *matrix, float *rightMatrix);
s32 MatrixGetMultipliedIndex (const u32 index, s32 *matrix, s32 *rightMatrix);
void MatrixSet (s32 *matrix, int x, int y, s32 value);
void MatrixCopy (s32 * matrixDST, const s32 * matrixSRC);
int MatrixCompare (const s32 * matrixDST, const float * matrixSRC);
@ -60,9 +60,9 @@ void MatrixStackInit (MatrixStack *stack);
void MatrixStackSetMaxSize (MatrixStack *stack, int size);
void MatrixStackPushMatrix (MatrixStack *stack, const s32 *ptr);
void MatrixStackPopMatrix (s32 *mtxCurr, MatrixStack *stack, int size);
s32* MatrixStackGetPos (MatrixStack *stack, int pos);
s32* MatrixStackGetPos (MatrixStack *stack, const size_t pos);
s32* MatrixStackGet (MatrixStack *stack);
void MatrixStackLoadMatrix (MatrixStack *stack, int pos, const s32 *ptr);
void MatrixStackLoadMatrix (MatrixStack *stack, const size_t pos, const s32 *ptr);
void Vector2Copy(float *dst, const float *src);
void Vector2Add(float *dst, const float *src);

View File

@ -1004,8 +1004,8 @@ public:
lastTexKey = NULL;
GFX3D_Clipper::TClippedPoly &firstClippedPoly = this->_softRender->clippedPolys[0];
POLY &firstPoly = *firstClippedPoly.poly;
const GFX3D_Clipper::TClippedPoly &firstClippedPoly = this->_softRender->clippedPolys[0];
const POLY &firstPoly = *firstClippedPoly.poly;
PolygonAttributes polyAttr = firstPoly.getAttributes();
u32 lastPolyAttr = firstPoly.polyAttr;
u32 lastTexParams = firstPoly.texParam;
@ -1020,8 +1020,8 @@ public:
polynum = i;
GFX3D_Clipper::TClippedPoly &clippedPoly = this->_softRender->clippedPolys[i];
POLY &thePoly = *clippedPoly.poly;
int type = clippedPoly.type;
const POLY &thePoly = *clippedPoly.poly;
const PolygonType type = clippedPoly.type;
if (lastPolyAttr != thePoly.polyAttr)
{
@ -1265,7 +1265,8 @@ Render3DError SoftRasterizerRenderer::InitTables()
return RENDER3DERROR_NOERR;
}
size_t SoftRasterizerRenderer::performClipping(bool hirez, const VERTLIST *vertList, const POLYLIST *polyList, const INDEXLIST *indexList)
template<bool useHiResInterpolate>
size_t SoftRasterizerRenderer::performClipping(const VERTLIST *vertList, const POLYLIST *polyList, const INDEXLIST *indexList)
{
//submit all polys to clipper
clipper.reset();
@ -1276,15 +1277,12 @@ size_t SoftRasterizerRenderer::performClipping(bool hirez, const VERTLIST *vertL
&vertList->list[poly.vertIndexes[0]],
&vertList->list[poly.vertIndexes[1]],
&vertList->list[poly.vertIndexes[2]],
poly.type==4
poly.type==POLYGON_TYPE_QUAD
?&vertList->list[poly.vertIndexes[3]]
:NULL
};
if(hirez)
clipper.clipPoly<true>(poly, clipVerts);
else
clipper.clipPoly<false>(poly, clipVerts);
clipper.clipPoly<useHiResInterpolate>(poly, clipVerts);
}
return clipper.clippedPolyCounter;
@ -1347,7 +1345,7 @@ void SoftRasterizerRenderer::performCoordAdjustment()
for (size_t i = 0; i < this->_clippedPolyCount; i++)
{
GFX3D_Clipper::TClippedPoly &clippedPoly = clippedPolys[i];
int type = clippedPoly.type;
const PolygonType type = clippedPoly.type;
VERT *verts = &clippedPoly.clipVerts[0];
//here is a hack which needs to be removed.
@ -1359,28 +1357,33 @@ void SoftRasterizerRenderer::performCoordAdjustment()
}
}
void SoftRasterizerRenderer::setupTextures()
{
TexCacheItem *lastTexKey = NULL;
u32 lastTextureFormat = 0, lastTexturePalette = 0;
bool needInitTexture = true;
if (this->_clippedPolyCount == 0)
{
return;
}
const GFX3D_Clipper::TClippedPoly &firstClippedPoly = this->clippedPolys[0];
const POLY &firstPoly = *firstClippedPoly.poly;
u32 lastTexParams = firstPoly.texParam;
u32 lastTexPalette = firstPoly.texPalette;
TexCacheItem *lastTexKey = TexCache_SetTexture(TexFormat_15bpp, firstPoly.texParam, firstPoly.texPalette);
for (size_t i = 0; i < this->_clippedPolyCount; i++)
{
GFX3D_Clipper::TClippedPoly &clippedPoly = clippedPolys[i];
POLY *thePoly = clippedPoly.poly;
const GFX3D_Clipper::TClippedPoly &clippedPoly = clippedPolys[i];
const POLY &thePoly = *clippedPoly.poly;
//make sure all the textures we'll need are cached
//(otherwise on a multithreaded system there will be multiple writers--
//this SHOULD be read-only, although some day the texcache may collect statistics or something
//and then it won't be safe.
if (needInitTexture || lastTextureFormat != thePoly->texParam || lastTexturePalette != thePoly->texPalette)
if (lastTexParams != thePoly.texParam || lastTexPalette != thePoly.texPalette)
{
lastTexKey = TexCache_SetTexture(TexFormat_15bpp, thePoly->texParam, thePoly->texPalette);
lastTextureFormat = thePoly->texParam;
lastTexturePalette = thePoly->texPalette;
needInitTexture = false;
lastTexKey = TexCache_SetTexture(TexFormat_15bpp, thePoly.texParam, thePoly.texPalette);
lastTexParams = thePoly.texParam;
lastTexPalette = thePoly.texPalette;
}
//printf("%08X %d\n",poly->texParam,rasterizerUnit[0].textures.currentNum);
@ -1415,11 +1418,11 @@ void SoftRasterizerRenderer::performBackfaceTests()
{
for (size_t i = 0; i < this->_clippedPolyCount; i++)
{
GFX3D_Clipper::TClippedPoly &clippedPoly = clippedPolys[i];
POLY *thePoly = clippedPoly.poly;
int type = clippedPoly.type;
VERT* verts = &clippedPoly.clipVerts[0];
const PolygonAttributes polyAttr = thePoly->getAttributes();
const GFX3D_Clipper::TClippedPoly &clippedPoly = clippedPolys[i];
const POLY &thePoly = *clippedPoly.poly;
const PolygonType type = clippedPoly.type;
const VERT *verts = &clippedPoly.clipVerts[0];
const PolygonAttributes polyAttr = thePoly.getAttributes();
//HACK: backface culling
//this should be moved to gfx3d, but first we need to redo the way the lists are built
@ -1434,11 +1437,11 @@ void SoftRasterizerRenderer::performBackfaceTests()
//a better approach
// we have to support somewhat non-convex polygons (see NSMB world map 1st screen).
// this version should handle those cases better.
size_t n = type - 1;
const size_t n = type - 1;
float facing = (verts[0].y + verts[n].y) * (verts[0].x - verts[n].x)
+ (verts[1].y + verts[0].y) * (verts[1].x - verts[0].x)
+ (verts[2].y + verts[1].y) * (verts[2].x - verts[1].x);
for(int j = 2; j < n; j++)
for (size_t j = 2; j < n; j++)
facing += (verts[j+1].y + verts[j].y) * (verts[j+1].x - verts[j].x);
polyBackfacing[i] = (facing < 0);
@ -1460,7 +1463,14 @@ Render3DError SoftRasterizerRenderer::BeginRender(const GFX3D &engine)
// Keep the current render states for later use
this->currentRenderState = (GFX3D_State *)&engine.renderState;
this->_clippedPolyCount = this->performClipping(CommonSettings.GFX3D_HighResolutionInterpolateColor, engine.vertlist, engine.polylist, &engine.indexlist);
if (CommonSettings.GFX3D_HighResolutionInterpolateColor)
{
this->_clippedPolyCount = this->performClipping<true>(engine.vertlist, engine.polylist, &engine.indexlist);
}
else
{
this->_clippedPolyCount = this->performClipping<false>(engine.vertlist, engine.polylist, &engine.indexlist);
}
if (rasterizerCores >= 4)
{
@ -1561,7 +1571,7 @@ Render3DError SoftRasterizerRenderer::RenderEdgeMarking(const u16 *colorTable, c
// also note that the edge generally goes on the outside, not the inside, (maybe needs to change later)
// and that polys with the same edge color can make edges against each other.
FragmentColor edgeColor = this->edgeMarkTable[polyID>>3];
const FragmentColor edgeColor = this->edgeMarkTable[polyID>>3];
#define PIXOFFSET(dx,dy) ((dx)+(this->_framebufferWidth*(dy)))
#define ISEDGE(dx,dy) ((x+(dx) < this->_framebufferWidth) && (y+(dy) < this->_framebufferHeight) && polyID > this->_framebufferAttributes[i+PIXOFFSET(dx,dy)].opaquePolyID)
@ -1706,12 +1716,12 @@ Render3DError SoftRasterizerRenderer::RenderFog(const u8 *densityTable, const u3
{
for (size_t i = 0; i < framebufferFragmentCount; i++)
{
const FragmentAttributes &destFragment = _framebufferAttributes[i];
const FragmentAttributes &destFragment = this->_framebufferAttributes[i];
const size_t fogIndex = destFragment.depth >> 9;
assert(fogIndex < 32768);
const u8 fog = (destFragment.isFogged) ? this->fogTable[fogIndex] : 0;
FragmentColor &destFragmentColor = _framebufferColor[i];
FragmentColor &destFragmentColor = this->_framebufferColor[i];
destFragmentColor.r = ((128-fog)*destFragmentColor.r + r*fog)>>7;
destFragmentColor.g = ((128-fog)*destFragmentColor.g + g*fog)>>7;
destFragmentColor.b = ((128-fog)*destFragmentColor.b + b*fog)>>7;
@ -1722,12 +1732,12 @@ Render3DError SoftRasterizerRenderer::RenderFog(const u8 *densityTable, const u3
{
for (size_t i = 0; i < framebufferFragmentCount; i++)
{
const FragmentAttributes &destFragment = _framebufferAttributes[i];
const FragmentAttributes &destFragment = this->_framebufferAttributes[i];
const size_t fogIndex = destFragment.depth >> 9;
assert(fogIndex < 32768);
const u8 fog = (destFragment.isFogged) ? this->fogTable[fogIndex] : 0;
FragmentColor &destFragmentColor = _framebufferColor[i];
FragmentColor &destFragmentColor = this->_framebufferColor[i];
destFragmentColor.a = ((128-fog)*destFragmentColor.a + a*fog)>>7;
}
}
@ -1741,7 +1751,7 @@ Render3DError SoftRasterizerRenderer::RenderEdgeMarkingAndFog(const SoftRasteriz
{
for (size_t x = 0; x < this->_framebufferWidth; x++, i++)
{
FragmentColor &dstColor = _framebufferColor[i];
FragmentColor &dstColor = this->_framebufferColor[i];
const FragmentAttributes dstAttributes = this->_framebufferAttributes[i];
const u32 depth = dstAttributes.depth;
const u8 polyID = dstAttributes.opaquePolyID;

View File

@ -53,7 +53,7 @@ protected:
// SoftRasterizer-specific methods
virtual Render3DError InitTables();
size_t performClipping(bool hirez, const VERTLIST *vertList, const POLYLIST *polyList, const INDEXLIST *indexList);
template<bool useHiResInterpolate> size_t performClipping(const VERTLIST *vertList, const POLYLIST *polyList, const INDEXLIST *indexList);
// Base rendering methods
virtual Render3DError BeginRender(const GFX3D &engine);