GFX3D:
- Improve ClearImage/Rear-plane emulation accuracy and performance for both 3D renderers. OpenGL Renderer: - Do additional optimizations to ClearImage/Rear-plane emulation. - Make FBO support check a little less strict. - Some minor code cleanup.
This commit is contained in:
parent
887f78a0d0
commit
dcf601ebb2
|
@ -109,11 +109,11 @@ static bool isShaderSupported = false;
|
|||
// ClearImage/Rear-plane (FBO)
|
||||
static GLenum oglClearImageTextureID[2] = {0}; // 0 - image, 1 - depth
|
||||
static GLuint oglClearImageBuffers = 0;
|
||||
static u32 *oglClearImageColor = NULL;
|
||||
static float *oglClearImageDepth = NULL;
|
||||
static GLushort *oglClearImageColor = NULL;
|
||||
static GLuint *oglClearImageDepth = NULL;
|
||||
static u16 *oglClearImageColorTemp = NULL;
|
||||
static u16 *oglClearImageDepthTemp = NULL;
|
||||
static u32 oglClearImageScrollOld = 0;
|
||||
static u16 oglClearImageScrollOld = 0;
|
||||
|
||||
// VBO
|
||||
static GLuint vboVertexID;
|
||||
|
@ -148,6 +148,7 @@ static GLfloat *color4fBuffer = NULL;
|
|||
static GLushort *vertIndexBuffer = NULL;
|
||||
|
||||
static CACHE_ALIGN GLfloat material_8bit_to_float[255] = {0};
|
||||
static CACHE_ALIGN GLuint dsDepthToD24S8_LUT[32768] = {0};
|
||||
static const GLfloat divide5bitBy31LUT[32] = {0.0, 0.03225806451613, 0.06451612903226, 0.09677419354839,
|
||||
0.1290322580645, 0.1612903225806, 0.1935483870968, 0.2258064516129,
|
||||
0.258064516129, 0.2903225806452, 0.3225806451613, 0.3548387096774,
|
||||
|
@ -495,8 +496,8 @@ static void OGLReset()
|
|||
|
||||
if (isFBOSupported)
|
||||
{
|
||||
memset(oglClearImageColor, 0, 256*192*sizeof(u32));
|
||||
memset(oglClearImageDepth, 0, 256*192*sizeof(float));
|
||||
memset(oglClearImageColor, 0, 256*192*sizeof(GLushort));
|
||||
memset(oglClearImageDepth, 0, 256*192*sizeof(GLuint));
|
||||
memset(oglClearImageColorTemp, 0, 256*192*sizeof(u16));
|
||||
memset(oglClearImageDepthTemp, 0, 256*192*sizeof(u16));
|
||||
oglClearImageScrollOld = 0;
|
||||
|
@ -566,6 +567,9 @@ static char OGLInit(void)
|
|||
for (u8 i = 0; i < 255; i++)
|
||||
material_8bit_to_float[i] = (GLfloat)(i<<2)/255.f;
|
||||
|
||||
for (unsigned int i = 0; i < 32768; i++)
|
||||
dsDepthToD24S8_LUT[i] = (GLuint)DS_DEPTH15TO24(i) << 8;
|
||||
|
||||
expandFreeTextures();
|
||||
|
||||
// Maintain our own vertex index buffer for vertex batching and primitive
|
||||
|
@ -719,7 +723,11 @@ static char OGLInit(void)
|
|||
}
|
||||
|
||||
// FBO Setup
|
||||
isFBOSupported = (strstr(extString, "GL_ARB_framebuffer_object") == NULL)?false:true;
|
||||
isFBOSupported = ( (strstr(extString, "GL_ARB_framebuffer_object") == NULL) &&
|
||||
(strstr(extString, "GL_EXT_framebuffer_object") == NULL ||
|
||||
strstr(extString, "GL_EXT_framebuffer_blit") == NULL ||
|
||||
strstr(extString, "GL_EXT_packed_depth_stencil") == NULL) ) ? false: true;
|
||||
|
||||
if (isFBOSupported)
|
||||
{
|
||||
// ClearImage/Rear-plane
|
||||
|
@ -740,11 +748,10 @@ static char OGLInit(void)
|
|||
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_WRAP_T,GL_CLAMP_TO_BORDER);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_MODE, GL_NONE);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_DEPTH_TEXTURE_MODE, GL_LUMINANCE);
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, 256, 192, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL);
|
||||
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH24_STENCIL8_EXT, 256, 192, 0, GL_DEPTH_STENCIL_EXT, GL_UNSIGNED_INT_24_8_EXT, NULL);
|
||||
|
||||
// FBO - init
|
||||
glGenFramebuffersEXT(1, &oglClearImageBuffers);
|
||||
|
||||
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, oglClearImageBuffers);
|
||||
glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, oglClearImageTextureID[0], 0);
|
||||
glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT, GL_TEXTURE_2D, oglClearImageTextureID[1], 0);
|
||||
|
@ -759,9 +766,9 @@ static char OGLInit(void)
|
|||
|
||||
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
|
||||
|
||||
oglClearImageColor = new u32[256*192];
|
||||
oglClearImageColor = new GLushort[256*192];
|
||||
oglClearImageColorTemp = new u16[256*192];
|
||||
oglClearImageDepth = new float[256*192];
|
||||
oglClearImageDepth = new GLuint[256*192];
|
||||
oglClearImageDepthTemp = new u16[256*192];
|
||||
}
|
||||
else
|
||||
|
@ -1203,21 +1210,23 @@ static void GL_ReadFramebuffer()
|
|||
}
|
||||
}
|
||||
|
||||
// TODO: optimize
|
||||
// Tested: Sonic Chronicles Dark Brotherhood
|
||||
// The Chronicles of Narnia - The Lion, The Witch and The Wardrobe
|
||||
// Harry Potter and the Order of the Phoenix
|
||||
static void oglClearImageFBO()
|
||||
{
|
||||
if (!isFBOSupported) return;
|
||||
//printf("enableClearImage\n");
|
||||
if (!isFBOSupported)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
u16* clearImage = (u16*)MMU.texInfo.textureSlotAddr[2];
|
||||
u16* clearDepth = (u16*)MMU.texInfo.textureSlotAddr[3];
|
||||
u16 scroll = T1ReadWord(MMU.ARM9_REG,0x356); //CLRIMAGE_OFFSET
|
||||
|
||||
if ((oglClearImageScrollOld != scroll)||
|
||||
(memcmp(clearImage, oglClearImageColorTemp, 256*192*2) != 0) ||
|
||||
(memcmp(clearDepth, oglClearImageDepthTemp, 256*192*2) != 0))
|
||||
if (oglClearImageScrollOld != scroll ||
|
||||
memcmp(clearImage, oglClearImageColorTemp, 256*192*2) ||
|
||||
memcmp(clearDepth, oglClearImageDepthTemp, 256*192*2) )
|
||||
{
|
||||
oglClearImageScrollOld = scroll;
|
||||
memcpy(oglClearImageColorTemp, clearImage, 256*192*2);
|
||||
|
@ -1225,21 +1234,19 @@ static void oglClearImageFBO()
|
|||
|
||||
u16 xscroll = scroll&0xFF;
|
||||
u16 yscroll = (scroll>>8)&0xFF;
|
||||
|
||||
u32 dd = 256*192-256;
|
||||
for(int iy=0;iy<192;iy++)
|
||||
unsigned int dd = 256*192-256;
|
||||
|
||||
for(unsigned int iy=0;iy<192;iy++)
|
||||
{
|
||||
int y = ((iy + yscroll)&255)<<8;
|
||||
for(int ix=0;ix<256;ix++)
|
||||
unsigned int y = ((iy + yscroll)&255)<<8;
|
||||
|
||||
for(unsigned int ix=0;ix<256;ix++)
|
||||
{
|
||||
int x = (ix + xscroll)&255;
|
||||
int adr = y + x;
|
||||
unsigned int x = (ix + xscroll)&255;
|
||||
unsigned int adr = y + x;
|
||||
|
||||
u16 col = clearImage[adr];
|
||||
oglClearImageColor[dd] = RGB15TO32(col,255*(col>>15));
|
||||
|
||||
u16 depth = clearDepth[adr] & 0x7FFF;
|
||||
oglClearImageDepth[dd] = (float)gfx3d_extendDepth_15_to_24(depth) / (float)0x00FFFFFF;
|
||||
oglClearImageColor[dd] = clearImage[adr];
|
||||
oglClearImageDepth[dd] = dsDepthToD24S8_LUT[clearDepth[adr] & 0x7FFF];
|
||||
|
||||
dd++;
|
||||
}
|
||||
|
@ -1251,9 +1258,9 @@ static void oglClearImageFBO()
|
|||
glActiveTexture(GL_TEXTURE2);
|
||||
|
||||
glBindTexture(GL_TEXTURE_2D, oglClearImageTextureID[0]);
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 256, 192, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8_REV, oglClearImageColor);
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 256, 192, GL_RGBA, GL_UNSIGNED_SHORT_1_5_5_5_REV, oglClearImageColor);
|
||||
glBindTexture(GL_TEXTURE_2D, oglClearImageTextureID[1]);
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 256, 192, GL_DEPTH_COMPONENT, GL_FLOAT, oglClearImageDepth);
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 256, 192, GL_DEPTH_STENCIL_EXT, GL_UNSIGNED_INT_24_8_EXT, oglClearImageDepth);
|
||||
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
}
|
||||
|
|
|
@ -253,6 +253,7 @@ CACHE_ALIGN u32 color_15bit_to_24bit_reverse[32768];
|
|||
CACHE_ALIGN u32 color_15bit_to_24bit[32768];
|
||||
CACHE_ALIGN u16 color_15bit_to_16bit_reverse[32768];
|
||||
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[] = {
|
||||
|
@ -435,6 +436,9 @@ static void makeTables() {
|
|||
{
|
||||
color_15bit_to_24bit_reverse[i] = RGB15TO24_BITLOGIC_REVERSE((u16)i);
|
||||
color_15bit_to_16bit_reverse[i] = (((i & 0x001F) << 11) | (material_5bit_to_6bit[(i & 0x03E0) >> 5] << 5) | ((i & 0x7C00) >> 10));
|
||||
|
||||
// 15-bit to 24-bit depth formula from http://nocash.emubase.de/gbatek.htm#ds3drearplane
|
||||
dsDepthExtend_15bit_to_24bit[i] = (i*0x200)+((i+1)>>15)*0x01FF;
|
||||
}
|
||||
|
||||
for (int i = 0; i < 65536; i++)
|
||||
|
@ -555,7 +559,7 @@ void gfx3d_reset()
|
|||
|
||||
memset(gfx3d_convertedScreen,0,sizeof(gfx3d_convertedScreen));
|
||||
|
||||
gfx3d.state.clearDepth = gfx3d_extendDepth_15_to_24(0x7FFF);
|
||||
gfx3d.state.clearDepth = DS_DEPTH15TO24(0x7FFF);
|
||||
|
||||
clInd2 = 0;
|
||||
isSwapBuffers = FALSE;
|
||||
|
@ -1643,8 +1647,7 @@ void gfx3d_glFogOffset (u32 v)
|
|||
|
||||
void gfx3d_glClearDepth(u32 v)
|
||||
{
|
||||
v &= 0x7FFF;
|
||||
gfx3d.state.clearDepth = gfx3d_extendDepth_15_to_24(v);
|
||||
gfx3d.state.clearDepth = DS_DEPTH15TO24(v);
|
||||
}
|
||||
|
||||
// Ignored for now
|
||||
|
|
|
@ -110,14 +110,8 @@ inline u32 RGB15TO6665(u16 col, u8 alpha5)
|
|||
|
||||
#define GFX3D_5TO6(x) ((x)?(((x)<<1)+1):0)
|
||||
|
||||
inline u32 gfx3d_extendDepth_15_to_24(u32 depth)
|
||||
{
|
||||
//formula from http://nocash.emubase.de/gbatek.htm#ds3drearplane
|
||||
//return (depth*0x200)+((depth+1)>>15)*0x01FF;
|
||||
//I think this might be slightly faster
|
||||
if(depth==0x7FFF) return 0x00FFFFFF;
|
||||
else return depth<<9;
|
||||
}
|
||||
// 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] )
|
||||
|
||||
// POLYGON ATTRIBUTES - BIT LOCATIONS
|
||||
enum
|
||||
|
@ -696,6 +690,7 @@ extern GFX3D gfx3d;
|
|||
extern CACHE_ALIGN u32 color_15bit_to_24bit[32768];
|
||||
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 u8 material_5bit_to_8bit[32];
|
||||
|
|
|
@ -1223,10 +1223,9 @@ void SoftRasterizerEngine::initFramebuffer(const int width, const int height, co
|
|||
|
||||
//this is tested quite well in the sonic chronicles main map mode
|
||||
//where depth values are used for trees etc you can walk behind
|
||||
u32 depth = clearDepth[adr];
|
||||
u16 depth = clearDepth[adr];
|
||||
dst->fogged = BIT15(depth);
|
||||
//TODO - might consider a lookup table for this
|
||||
dst->depth = gfx3d_extendDepth_15_to_24(depth&0x7FFF);
|
||||
dst->depth = DS_DEPTH15TO24(depth);
|
||||
|
||||
dstColor++;
|
||||
dst++;
|
||||
|
|
Loading…
Reference in New Issue