From 1e5b7def3d52e4e37267b803a27332b17dc137ea Mon Sep 17 00:00:00 2001 From: Sergey Lipskiy Date: Thu, 5 Mar 2015 19:43:32 +0600 Subject: [PATCH] Replace DEPTH_CLEAR_COLOR constant by game dependant variable. Several games use non-standart value for depth buffer clear. This value must be known beforehand for correct emulation. Fixed NFL Quarterback Club 2000: gfx screwed up #148 --- RSP.cpp | 16 ++++++++++++++++ RSP.h | 2 ++ gDP.cpp | 11 ++++------- 3 files changed, 22 insertions(+), 7 deletions(-) diff --git a/RSP.cpp b/RSP.cpp index eae87000..1eff206a 100644 --- a/RSP.cpp +++ b/RSP.cpp @@ -267,6 +267,21 @@ void RSP_SetDefaultState() gDPPipelineMode(G_PM_NPRIMITIVE); } +u32 DepthClearColor = 0xfffcfffc; + +static +void setDepthClearColor() +{ + if (strstr(RSP.romname, (const char *)"Elmo's") != NULL) + DepthClearColor = 0xFFFFFFFF; + else if (strstr(RSP.romname, (const char *)"Taz Express") != NULL) + DepthClearColor = 0xFFBCFFBC; + else if (strstr(RSP.romname, (const char *)"NFL QBC 2000") != NULL || strstr(RSP.romname, (const char *)"NFL Quarterback Club") != NULL) + DepthClearColor = 0xFFFDFFFC; + else + DepthClearColor = 0xFFFCFFFC; +} + void RSP_Init() { #ifdef OS_WINDOWS @@ -306,6 +321,7 @@ void RSP_Init() TFH.shutdown(); strncpy(RSP.romname, romname, 21); + setDepthClearColor(); if (strstr(RSP.romname, (const char *)"OgreBattle64") != NULL) config.generalEmulation.hacks |= hack_Ogre64; else if (strstr(RSP.romname, (const char *)"MarioGolf64") != NULL || strstr(RSP.romname, (const char *)"CONKER BFD") != NULL) diff --git a/RSP.h b/RSP.h index f09998a5..42154418 100644 --- a/RSP.h +++ b/RSP.h @@ -14,6 +14,8 @@ typedef struct extern RSPInfo RSP; +extern u32 DepthClearColor; + #define RSP_SegmentToPhysical( segaddr ) ((gSP.segment[(segaddr >> 24) & 0x0F] + (segaddr & 0x00FFFFFF)) & 0x00FFFFFF) void RSP_Init(); diff --git a/gDP.cpp b/gDP.cpp index f115f84e..a56b5876 100644 --- a/gDP.cpp +++ b/gDP.cpp @@ -18,8 +18,6 @@ #include "Config.h" #include "Combiner.h" -#define DEPTH_CLEAR_COLOR 0xfffcfffc // The value usually used to clear depth buffer - using namespace std; gDPInfo gDP; @@ -545,7 +543,7 @@ bool CheckForFrameBufferTexture(u32 _address, u32 _bytes) if (bRes && pBuffer->m_cleared && pBuffer->m_size == 2 && !config.frameBufferEmulation.copyToRDRAM - && (!config.frameBufferEmulation.copyDepthToRDRAM || pBuffer->m_fillcolor != DEPTH_CLEAR_COLOR) + && (!config.frameBufferEmulation.copyDepthToRDRAM || pBuffer->m_fillcolor != DepthClearColor) ) { const u32 endAddress = min(texEndAddress, pBuffer->m_endAddress); const u32 color = pBuffer->m_fillcolor&0xFFFEFFFE; @@ -864,7 +862,7 @@ void gDPSetScissor( u32 mode, f32 ulx, f32 uly, f32 lrx, f32 lry ) const bool g_bDepthClearOnly = false; void gDPFillRDRAM(u32 address, s32 ulx, s32 uly, s32 lrx, s32 lry, u32 width, u32 size, u32 color, bool scissor) { - if (g_bDepthClearOnly && color != DEPTH_CLEAR_COLOR) + if (g_bDepthClearOnly && color != DepthClearColor) return; FrameBufferList & fbList = frameBufferList(); if (fbList.isFboMode()) { @@ -905,13 +903,12 @@ void gDPFillRectangle( s32 ulx, s32 uly, s32 lrx, s32 lry ) if (gDP.depthImageAddress == gDP.colorImage.address) { // Game may use depth texture as auxilary color texture. Example: Mario Tennis // If color is not depth clear color, that is most likely the case - if (gDP.fillColor.color == DEPTH_CLEAR_COLOR || - (((gDP.fillColor.color & 0xFFFF) == (gDP.fillColor.color >> 16)) && abs((int)(DEPTH_CLEAR_COLOR & 0xFFFF) - (int)(gDP.fillColor.color & 0xFFFF)) < 100)) { + if (gDP.fillColor.color == DepthClearColor) { gDPFillRDRAM(gDP.colorImage.address, ulx, uly, lrx, lry, gDP.colorImage.width, gDP.colorImage.size, gDP.fillColor.color); render.clearDepthBuffer(); return; } - } else if (gDP.fillColor.color == DEPTH_CLEAR_COLOR && gDP.otherMode.cycleType == G_CYC_FILL) { + } else if (gDP.fillColor.color == DepthClearColor && gDP.otherMode.cycleType == G_CYC_FILL) { depthBufferList().saveBuffer(gDP.colorImage.address); gDPFillRDRAM(gDP.colorImage.address, ulx, uly, lrx, lry, gDP.colorImage.width, gDP.colorImage.size, gDP.fillColor.color); render.clearDepthBuffer();