Merge pull request #1578 from LukeUsher/fix-render-texture-states
Minor Cleanup of Render State and Texture State handling
This commit is contained in:
commit
13daf887c0
|
@ -195,10 +195,12 @@ bool Settings::Init()
|
|||
int iRet = MessageBox(nullptr, szSettings_save_user_option_message, "Cxbx-Reloaded", MB_YESNOCANCEL | MB_ICONQUESTION);
|
||||
|
||||
if (iRet == IDYES) {
|
||||
saveFile = GenerateExecDirectoryStr();
|
||||
saveFile = GenerateExecDirectoryStr();
|
||||
m_gui.DataStorageToggle = CXBX_DATA_EXECDIR;
|
||||
}
|
||||
else if (iRet == IDNO){
|
||||
saveFile = GenerateUserProfileDirectoryStr();
|
||||
saveFile = GenerateUserProfileDirectoryStr();
|
||||
m_gui.DataStorageToggle = CXBX_DATA_APPDATA;
|
||||
if (saveFile.size() == 0) {
|
||||
return false;
|
||||
}
|
||||
|
@ -221,7 +223,7 @@ bool Settings::Init()
|
|||
saveFile.append(szSettings_settings_file);
|
||||
|
||||
// Call LoadConfig, this will load the config, applying defaults for any missing fields
|
||||
bRet = LoadConfig();
|
||||
bRet = LoadConfig();
|
||||
|
||||
if (!bRet) {
|
||||
MessageBox(nullptr, szSettings_setup_error, "Cxbx-Reloaded", MB_OK);
|
||||
|
@ -293,7 +295,7 @@ bool Settings::LoadConfig()
|
|||
m_gui.szCxbxDebugFile = si_data;
|
||||
}
|
||||
|
||||
m_gui.DataStorageToggle = m_si.GetLongValue(section_gui, sect_gui_keys.DataStorageToggle, /*Default=*/CXBX_DATA_APPDATA);
|
||||
m_gui.DataStorageToggle = m_si.GetLongValue(section_gui, sect_gui_keys.DataStorageToggle, /*Default=*/m_gui.DataStorageToggle);
|
||||
si_data = m_si.GetValue(section_gui, sect_gui_keys.DataCustomLocation, /*Default=*/nullptr);
|
||||
// Fallback to null string if value is empty or contains a bigger string.
|
||||
if (si_data == nullptr || std::strlen(si_data) >= MAX_PATH) {
|
||||
|
|
|
@ -6006,213 +6006,158 @@ VOID __fastcall XTL::EMUPATCH(D3DDevice_SetRenderState_Simple)
|
|||
(
|
||||
DWORD Method,
|
||||
DWORD Value
|
||||
)
|
||||
)
|
||||
{
|
||||
LOG_FUNC_BEGIN
|
||||
LOG_FUNC_ARG(Method)
|
||||
LOG_FUNC_ARG(Value)
|
||||
LOG_FUNC_END;
|
||||
LOG_FUNC_BEGIN
|
||||
LOG_FUNC_ARG(Method)
|
||||
LOG_FUNC_ARG(Value)
|
||||
LOG_FUNC_END;
|
||||
|
||||
XB_trampoline(VOID, __fastcall, D3DDevice_SetRenderState_Simple, (DWORD, DWORD));
|
||||
XB_D3DDevice_SetRenderState_Simple(Method, Value);
|
||||
XB_trampoline(VOID, __fastcall, D3DDevice_SetRenderState_Simple, (DWORD, DWORD));
|
||||
XB_D3DDevice_SetRenderState_Simple(Method, Value);
|
||||
|
||||
// Special Case: Handle PixelShader related Render States
|
||||
// TODO: Port over EmuMappedD3DRenderState and related code from Dxbx or Wip_LessVertexPatching
|
||||
// After this, we don't need to do this part anymore
|
||||
switch (Method & 0x00001FFC) {
|
||||
case NV2A_RC_IN_ALPHA(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS0] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS1] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS2] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS3] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS4] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS5] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS6] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS7] = Value; return;
|
||||
case NV2A_RC_FINAL0: TemporaryPixelShaderRenderStates[X_D3DRS_PSFINALCOMBINERINPUTSABCD] = Value; return;
|
||||
case NV2A_RC_FINAL1: TemporaryPixelShaderRenderStates[X_D3DRS_PSFINALCOMBINERINPUTSEFG] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_0] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_1] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_2] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_3] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_4] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_5] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_6] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_7] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_0] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_1] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_2] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_3] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_4] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_5] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_6] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_7] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS0] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS1] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS2] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS3] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS4] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS5] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS6] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS7] = Value; return;
|
||||
case NV2A_RC_IN_RGB(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS0] = Value; return;
|
||||
case NV2A_RC_IN_RGB(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS1] = Value; return;
|
||||
case NV2A_RC_IN_RGB(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS2] = Value; return;
|
||||
case NV2A_RC_IN_RGB(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS3] = Value; return;
|
||||
case NV2A_RC_IN_RGB(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS4] = Value; return;
|
||||
case NV2A_RC_IN_RGB(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS5] = Value; return;
|
||||
case NV2A_RC_IN_RGB(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS6] = Value; return;
|
||||
case NV2A_RC_IN_RGB(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS7] = Value; return;
|
||||
case NV2A_TX_SHADER_CULL_MODE: TemporaryPixelShaderRenderStates[X_D3DRS_PSCOMPAREMODE] = Value; return;
|
||||
case NV2A_RC_COLOR0: TemporaryPixelShaderRenderStates[X_D3DRS_PSFINALCOMBINERCONSTANT0] = Value; return;
|
||||
case NV2A_RC_COLOR1: TemporaryPixelShaderRenderStates[X_D3DRS_PSFINALCOMBINERCONSTANT1] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS0] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS1] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS2] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS3] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS4] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS5] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS6] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS7] = Value; return;
|
||||
case NV2A_RC_ENABLE: TemporaryPixelShaderRenderStates[X_D3DRS_PSCOMBINERCOUNT] = Value; return;
|
||||
case NV2A_NOP: TemporaryPixelShaderRenderStates[X_D3DRS_PS_RESERVED] = Value; return; // Dxbx note : This takes the slot of X_D3DPIXELSHADERDEF.PSTextureModes, set by D3DDevice_SetRenderState_LogicOp?
|
||||
case NV2A_TX_SHADER_DOTMAPPING: TemporaryPixelShaderRenderStates[X_D3DRS_PSDOTMAPPING] = Value; return;
|
||||
case NV2A_TX_SHADER_PREVIOUS: TemporaryPixelShaderRenderStates[X_D3DRS_PSINPUTTEXTURE] = Value; return;
|
||||
}
|
||||
// Special Case: Handle PixelShader related Render States
|
||||
// TODO: Port over EmuMappedD3DRenderState and related code from Dxbx or Wip_LessVertexPatching
|
||||
// After this, we don't need to do this part anymore
|
||||
switch (Method & 0x00001FFC) {
|
||||
case NV2A_RC_IN_ALPHA(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS0] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS1] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS2] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS3] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS4] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS5] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS6] = Value; return;
|
||||
case NV2A_RC_IN_ALPHA(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAINPUTS7] = Value; return;
|
||||
case NV2A_RC_FINAL0: TemporaryPixelShaderRenderStates[X_D3DRS_PSFINALCOMBINERINPUTSABCD] = Value; return;
|
||||
case NV2A_RC_FINAL1: TemporaryPixelShaderRenderStates[X_D3DRS_PSFINALCOMBINERINPUTSEFG] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_0] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_1] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_2] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_3] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_4] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_5] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_6] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR0(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT0_7] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_0] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_1] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_2] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_3] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_4] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_5] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_6] = Value; return;
|
||||
case NV2A_RC_CONSTANT_COLOR1(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSCONSTANT1_7] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS0] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS1] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS2] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS3] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS4] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS5] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS6] = Value; return;
|
||||
case NV2A_RC_OUT_ALPHA(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSALPHAOUTPUTS7] = Value; return;
|
||||
case NV2A_RC_IN_RGB(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS0] = Value; return;
|
||||
case NV2A_RC_IN_RGB(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS1] = Value; return;
|
||||
case NV2A_RC_IN_RGB(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS2] = Value; return;
|
||||
case NV2A_RC_IN_RGB(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS3] = Value; return;
|
||||
case NV2A_RC_IN_RGB(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS4] = Value; return;
|
||||
case NV2A_RC_IN_RGB(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS5] = Value; return;
|
||||
case NV2A_RC_IN_RGB(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS6] = Value; return;
|
||||
case NV2A_RC_IN_RGB(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBINPUTS7] = Value; return;
|
||||
case NV2A_TX_SHADER_CULL_MODE: TemporaryPixelShaderRenderStates[X_D3DRS_PSCOMPAREMODE] = Value; return;
|
||||
case NV2A_RC_COLOR0: TemporaryPixelShaderRenderStates[X_D3DRS_PSFINALCOMBINERCONSTANT0] = Value; return;
|
||||
case NV2A_RC_COLOR1: TemporaryPixelShaderRenderStates[X_D3DRS_PSFINALCOMBINERCONSTANT1] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(0): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS0] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(1): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS1] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(2): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS2] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(3): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS3] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(4): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS4] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(5): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS5] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(6): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS6] = Value; return;
|
||||
case NV2A_RC_OUT_RGB(7): TemporaryPixelShaderRenderStates[X_D3DRS_PSRGBOUTPUTS7] = Value; return;
|
||||
case NV2A_RC_ENABLE: TemporaryPixelShaderRenderStates[X_D3DRS_PSCOMBINERCOUNT] = Value; return;
|
||||
case NV2A_NOP: TemporaryPixelShaderRenderStates[X_D3DRS_PS_RESERVED] = Value; return; // Dxbx note : This takes the slot of X_D3DPIXELSHADERDEF.PSTextureModes, set by D3DDevice_SetRenderState_LogicOp?
|
||||
case NV2A_TX_SHADER_DOTMAPPING: TemporaryPixelShaderRenderStates[X_D3DRS_PSDOTMAPPING] = Value; return;
|
||||
case NV2A_TX_SHADER_PREVIOUS: TemporaryPixelShaderRenderStates[X_D3DRS_PSINPUTTEXTURE] = Value; return;
|
||||
}
|
||||
|
||||
// Fallback to non-shader render state handling
|
||||
int State = -1;
|
||||
|
||||
// Todo: make this faster and more elegant
|
||||
for (int v = 0; v<174; v++)
|
||||
{
|
||||
if (EmuD3DRenderStateSimpleEncoded[v] == Method)
|
||||
{
|
||||
State = v;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (State == -1) {
|
||||
// Attempt to determine renderstate name for unsupported types
|
||||
std::string name = "Unknown";
|
||||
for (int i = 0; i <= X_D3DRS_DONOTCULLUNCOMPRESSED; i++) {
|
||||
if (DxbxRenderStateInfo[i].M == (Method & 0x00001FFC)) {
|
||||
name = DxbxRenderStateInfo[i].S;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
EmuLog(LOG_LEVEL::WARNING, "RenderState_Simple(0x%.08X (%s), 0x%.08X) is unsupported!", Method, name.c_str(), Value);
|
||||
}
|
||||
else
|
||||
{
|
||||
switch(State)
|
||||
{
|
||||
case D3DRS_COLORWRITEENABLE:
|
||||
{
|
||||
DWORD OrigValue = Value;
|
||||
|
||||
Value = 0;
|
||||
|
||||
if(OrigValue & (1L<<16))
|
||||
Value |= D3DCOLORWRITEENABLE_RED;
|
||||
if(OrigValue & (1L<<8))
|
||||
Value |= D3DCOLORWRITEENABLE_GREEN;
|
||||
if(OrigValue & (1L<<0))
|
||||
Value |= D3DCOLORWRITEENABLE_BLUE;
|
||||
if(OrigValue & (1L<<24))
|
||||
Value |= D3DCOLORWRITEENABLE_ALPHA;
|
||||
|
||||
DBG_PRINTF("D3DRS_COLORWRITEENABLE := 0x%.08X\n", Value);
|
||||
}
|
||||
// Fetch the RenderState conversion info for the given input
|
||||
int XboxRenderStateIndex = -1;
|
||||
for (int i = 0; i <= X_D3DRS_DONOTCULLUNCOMPRESSED; i++) {
|
||||
if (DxbxRenderStateInfo[i].M == (Method & 0x00001FFC)) {
|
||||
XboxRenderStateIndex = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
case D3DRS_SHADEMODE:
|
||||
Value = EmuXB2PC_D3DSHADEMODE(Value);
|
||||
DBG_PRINTF("D3DRS_SHADEMODE := 0x%.08X\n", Value);
|
||||
break;
|
||||
// If we could not map it, log and return
|
||||
if (XboxRenderStateIndex == -1) {
|
||||
EmuLog(LOG_LEVEL::WARNING, "RenderState_Simple(0x%.08X (%s), 0x%.08X) could not be found in RenderState table", Method, DxbxRenderStateInfo[XboxRenderStateIndex].S, Value);
|
||||
return;
|
||||
}
|
||||
|
||||
case D3DRS_BLENDOP:
|
||||
Value = EmuXB2PC_D3DBLENDOP(Value);
|
||||
DBG_PRINTF("D3DRS_BLENDOP := 0x%.08X\n", Value);
|
||||
break;
|
||||
DBG_PRINTF("RenderState_Simple: %s = 0x%08X", DxbxRenderStateInfo[XboxRenderStateIndex].S, Value);
|
||||
|
||||
case D3DRS_SRCBLEND:
|
||||
Value = EmuXB2PC_D3DBLEND(Value);
|
||||
DBG_PRINTF("D3DRS_SRCBLEND := 0x%.08X\n", Value);
|
||||
break;
|
||||
// Perform Conversion
|
||||
switch (XboxRenderStateIndex) {
|
||||
case X_D3DRS_COLORWRITEENABLE: {
|
||||
DWORD OrigValue = Value;
|
||||
Value = 0;
|
||||
|
||||
case D3DRS_DESTBLEND:
|
||||
Value = EmuXB2PC_D3DBLEND(Value);
|
||||
DBG_PRINTF("D3DRS_DESTBLEND := 0x%.08X\n", Value);
|
||||
break;
|
||||
if (OrigValue & (1L << 16)) {
|
||||
Value |= D3DCOLORWRITEENABLE_RED;
|
||||
}
|
||||
|
||||
case D3DRS_ZFUNC:
|
||||
Value = EmuXB2PC_D3DCMPFUNC(Value);
|
||||
DBG_PRINTF("D3DRS_ZFUNC := 0x%.08X\n", Value);
|
||||
break;
|
||||
if (OrigValue & (1L << 8)) {
|
||||
Value |= D3DCOLORWRITEENABLE_GREEN;
|
||||
}
|
||||
|
||||
case D3DRS_ALPHAFUNC:
|
||||
Value = EmuXB2PC_D3DCMPFUNC(Value);
|
||||
DBG_PRINTF("D3DRS_ALPHAFUNC := 0x%.08X\n", Value);
|
||||
break;
|
||||
if (OrigValue & (1L << 0)) {
|
||||
Value |= D3DCOLORWRITEENABLE_BLUE;
|
||||
}
|
||||
|
||||
case D3DRS_ALPHATESTENABLE:
|
||||
DBG_PRINTF("D3DRS_ALPHATESTENABLE := 0x%.08X\n", Value);
|
||||
break;
|
||||
if (OrigValue & (1L << 24)) {
|
||||
Value |= D3DCOLORWRITEENABLE_ALPHA;
|
||||
}
|
||||
} break;
|
||||
case X_D3DRS_SHADEMODE:
|
||||
Value = EmuXB2PC_D3DSHADEMODE(Value);
|
||||
break;
|
||||
case X_D3DRS_BLENDOP:
|
||||
Value = EmuXB2PC_D3DBLENDOP(Value);
|
||||
break;
|
||||
case X_D3DRS_SRCBLEND:
|
||||
case X_D3DRS_DESTBLEND:
|
||||
Value = EmuXB2PC_D3DBLEND(Value);
|
||||
break;
|
||||
case X_D3DRS_ZFUNC:
|
||||
case X_D3DRS_ALPHAFUNC:
|
||||
case X_D3DRS_STENCILFUNC:
|
||||
Value = EmuXB2PC_D3DCMPFUNC(Value);
|
||||
break;
|
||||
case X_D3DRS_STENCILZFAIL:
|
||||
case X_D3DRS_STENCILPASS:
|
||||
Value = EmuXB2PC_D3DSTENCILOP(Value);
|
||||
break;
|
||||
case X_D3DRS_SWATHWIDTH:
|
||||
// X_D3DRS_SWATHWIDTH safely ignored as it has no visible behavior:
|
||||
// It simply changes the fill-rate for performance tweaking
|
||||
// Just log and return
|
||||
EmuLog(LOG_LEVEL::DEBUG, "RenderState_Simple(0x%.08X (%s), 0x%.08X) was ignored!", Method, DxbxRenderStateInfo[XboxRenderStateIndex].S, Value);
|
||||
return;
|
||||
case X_D3DRS_ALPHATESTENABLE: case X_D3DRS_ALPHABLENDENABLE:
|
||||
case X_D3DRS_ALPHAREF: case X_D3DRS_ZWRITEENABLE:
|
||||
case X_D3DRS_DITHERENABLE: case X_D3DRS_STENCILREF:
|
||||
case X_D3DRS_STENCILMASK: case X_D3DRS_STENCILWRITEMASK:
|
||||
// These render states require no conversion, so we simply
|
||||
// allow SetRenderState to be called with no changes
|
||||
break;
|
||||
default:
|
||||
// RenderState is unsupported/unimplemented, report and return
|
||||
EmuLog(LOG_LEVEL::WARNING, "RenderState_Simple(0x%.08X (%s), 0x%.08X) is unsupported!", Method, DxbxRenderStateInfo[XboxRenderStateIndex].S, Value);
|
||||
return;
|
||||
}
|
||||
|
||||
case D3DRS_ALPHABLENDENABLE:
|
||||
DBG_PRINTF("D3DRS_ALPHABLENDENABLE := 0x%.08X\n", Value);
|
||||
break;
|
||||
|
||||
case D3DRS_ALPHAREF:
|
||||
DBG_PRINTF("D3DRS_ALPHAREF := %lf\n", DWtoF(Value));
|
||||
break;
|
||||
|
||||
case D3DRS_ZWRITEENABLE:
|
||||
DBG_PRINTF("D3DRS_ZWRITEENABLE := 0x%.08X\n", Value);
|
||||
break;
|
||||
|
||||
case D3DRS_DITHERENABLE:
|
||||
DBG_PRINTF("D3DRS_DITHERENABLE := 0x%.08X\n", Value);
|
||||
break;
|
||||
|
||||
case D3DRS_STENCILZFAIL:
|
||||
Value = EmuXB2PC_D3DSTENCILOP(Value);
|
||||
DBG_PRINTF("D3DRS_STENCILZFAIL := 0x%.08X\n", Value);
|
||||
break;
|
||||
|
||||
case D3DRS_STENCILPASS:
|
||||
Value = EmuXB2PC_D3DSTENCILOP(Value);
|
||||
DBG_PRINTF("D3DRS_STENCILPASS := 0x%.08X\n", Value);
|
||||
break;
|
||||
|
||||
case D3DRS_STENCILFUNC:
|
||||
Value = EmuXB2PC_D3DCMPFUNC(Value);
|
||||
DBG_PRINTF("D3DRS_STENCILFUNC := 0x%.08X\n", Value);
|
||||
break;
|
||||
|
||||
case D3DRS_STENCILREF:
|
||||
DBG_PRINTF("D3DRS_STENCILREF := 0x%.08X\n", Value);
|
||||
break;
|
||||
|
||||
case D3DRS_STENCILMASK:
|
||||
DBG_PRINTF("D3DRS_STENCILMASK := 0x%.08X\n", Value);
|
||||
break;
|
||||
|
||||
case D3DRS_STENCILWRITEMASK:
|
||||
DBG_PRINTF("D3DRS_STENCILWRITEMASK := 0x%.08X\n", Value);
|
||||
break;
|
||||
|
||||
default:
|
||||
CxbxKrnlCleanup("Unsupported RenderState (0x%.08X)", State);
|
||||
break;
|
||||
};
|
||||
|
||||
// TODO: verify these params as you add support for them!
|
||||
HRESULT hRet = g_pD3DDevice->SetRenderState((D3DRENDERSTATETYPE)State, Value);
|
||||
DEBUG_D3DRESULT(hRet, "g_pD3DDevice->SetRenderState");
|
||||
}
|
||||
HRESULT hRet = g_pD3DDevice->SetRenderState((D3DRENDERSTATETYPE)(DxbxRenderStateInfo[XboxRenderStateIndex].PC), Value);
|
||||
DEBUG_D3DRESULT(hRet, "g_pD3DDevice->SetRenderState");
|
||||
}
|
||||
|
||||
// ******************************************************************
|
||||
|
|
|
@ -1215,101 +1215,6 @@ XTL::D3DPRIMITIVETYPE XTL::EmuPrimitiveTypeLookup[] =
|
|||
/* D3DPT_MAX = 11, */ (XTL::D3DPRIMITIVETYPE)11
|
||||
};
|
||||
|
||||
// render state conversion table
|
||||
CONST DWORD XTL::EmuD3DRenderStateSimpleEncoded[174] =
|
||||
{
|
||||
// WARNING: This lookup table strongly binds us to an SDK with these
|
||||
// specific #define values for D3DRS_*. Make VERY sure that you have
|
||||
// the correct lookup values;
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 0
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 2
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 4
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 6
|
||||
X_D3DRSSE_UNK, 0x0004037c, // 8 - , D3DRS_SHADEMODE
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 10
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 12
|
||||
0x0004035c, 0x00040300, // 14 - D3DRS_ZWRITEENABLE, D3DRS_ALPHATESTENABLE
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 16
|
||||
X_D3DRSSE_UNK, 0x00040344, // 18 - , D3DRS_SRCBLEND
|
||||
0x00040348, X_D3DRSSE_UNK, // 20 - D3DRS_DESTBLEND
|
||||
X_D3DRSSE_UNK, 0x00040354, // 22 - , D3DRS_ZFUNC
|
||||
0x00040340, 0x0004033c, // 24 - D3DRS_ALPHAREF, D3DRS_ALPHAFUNC
|
||||
0x00040310, 0x00040304, // 26 - D3DRS_DITHERENABLE, D3DRS_ALPHABLENDENABLE
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 28
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 30
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 32
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 34
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 36
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 38
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 40
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 42
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 44
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 46
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 48
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 50
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 52
|
||||
0x00040374, 0x00040378, // 54 - D3DRS_STENCILZFAIL, D3DRS_STENCILPASS
|
||||
0x00040364, 0x00040368, // 56 - D3DRS_STENCILFUNC, D3DRS_STENCILREF
|
||||
0x0004036c, 0x00040360, // 58 - D3DRS_STENCILMASK, D3DRS_STENCILWRITEMASK
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 60
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 62
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 64
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 66
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 68
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 70
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 72
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 74
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 76
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 78
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 80
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 82
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 84
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 86
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 88
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 90
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 92
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 94
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 96
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 98
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 100
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 102
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 104
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 106
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 108
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 110
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 112
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 114
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 116
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 118
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 120
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 122
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 124
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 126
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 128
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 130
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 132
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 134
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 136
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 138
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 140
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 142
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 144
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 146
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 148
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 150
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 152
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 154
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 156
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 158
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 160
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 162
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 164
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 166
|
||||
0x00040358, X_D3DRSSE_UNK, // 168 - D3DRS_COLORWRITEENABLE
|
||||
X_D3DRSSE_UNK, 0x00040350, // 170
|
||||
X_D3DRSSE_UNK, X_D3DRSSE_UNK, // 172
|
||||
};
|
||||
|
||||
void XTL::EmuUnswizzleBox
|
||||
(
|
||||
CONST PVOID pSrcBuff,
|
||||
|
|
|
@ -35,7 +35,6 @@
|
|||
|
||||
// simple render state encoding lookup table
|
||||
#define X_D3DRSSE_UNK 0x7fffffff
|
||||
extern CONST DWORD EmuD3DRenderStateSimpleEncoded[174];
|
||||
|
||||
typedef void(*FormatToARGBRow)(const uint8_t* src, uint8_t* dst_argb, int width);
|
||||
|
||||
|
@ -156,10 +155,8 @@ inline D3DBLEND EmuXB2PC_D3DBLEND(X_D3DBLEND Value)
|
|||
case 0x306: return D3DBLEND_DESTCOLOR;
|
||||
case 0x307: return D3DBLEND_INVDESTCOLOR;
|
||||
case 0x308: return D3DBLEND_SRCALPHASAT;
|
||||
// Unsupported (on host) Xbox Extensions
|
||||
// TODO: Find a way to implement these: Xbox sets a constant blend colour using D3DRS_BLENDCOLOR
|
||||
case 0x8001: EmuLogEx(LOG_PREFIX_D3DCVT, LOG_LEVEL::WARNING, "Unsupported Xbox D3DBlend Extension: D3DBLEND_CONSTANTCOLOR"); return D3DBLEND_ONE;
|
||||
case 0x8002: EmuLogEx(LOG_PREFIX_D3DCVT, LOG_LEVEL::WARNING, "Unsupported Xbox D3DBlend Extension: D3DBLEND_INVCONSTANTCOLOR "); return D3DBLEND_ONE;
|
||||
case 0x8001:return D3DBLEND_BLENDFACTOR; // Maps Xbox D3DBLEND_CONSTANTCOLOR
|
||||
case 0x8002:return D3DBLEND_INVBLENDFACTOR; // Maps Xbox D3DBLEND_INVCONSTANTCOLOR
|
||||
case 0x8003: EmuLogEx(LOG_PREFIX_D3DCVT, LOG_LEVEL::WARNING, "Unsupported Xbox D3DBlend Extension: D3DBLEND_CONSTANTALPHA"); return D3DBLEND_ONE;
|
||||
case 0x8004: EmuLogEx(LOG_PREFIX_D3DCVT, LOG_LEVEL::WARNING, "Unsupported Xbox D3DBlend Extension: D3DBLEND_INVCONSTANTALPHA"); return D3DBLEND_ONE;
|
||||
}
|
||||
|
|
|
@ -1041,6 +1041,14 @@ constexpr DWORD X_D3DTADDRESS_CLAMP = 3;
|
|||
constexpr DWORD X_D3DTADDRESS_BORDER = 4;
|
||||
constexpr DWORD X_D3DTADDRESS_CLAMPTOEDGE = 5;
|
||||
|
||||
// X_D3DTEXTUREFILTERTYPE Values
|
||||
constexpr DWORD X_D3DTEXF_NONE = 0;
|
||||
constexpr DWORD X_D3DTEXF_POINT = 1;
|
||||
constexpr DWORD X_D3DTEXF_LINEAR = 2;
|
||||
constexpr DWORD X_D3DTEXF_ANISOTROPIC = 3;
|
||||
constexpr DWORD X_D3DTEXF_QUINCUNX = 4; // Xbox extension
|
||||
constexpr DWORD X_D3DTEXF_GAUSSIANCUBIC = 5;
|
||||
|
||||
// X_D3DCLEAR values :
|
||||
constexpr DWORD X_D3DCLEAR_ZBUFFER = 0x00000001;
|
||||
constexpr DWORD X_D3DCLEAR_STENCIL = 0x00000002;
|
||||
|
|
|
@ -38,346 +38,476 @@ extern uint32_t g_BuildVersion;
|
|||
|
||||
#include "core\hle\Intercept.hpp" // For g_SymbolAddresses
|
||||
|
||||
void VerifyAndFixEmuDeferredRenderStateOffset()
|
||||
{
|
||||
// Verify that EmuD3DDeferredRenderState is correct, if not, we can programatically correct it
|
||||
// We should also flag up a warning so this can be fixed upstream in XboxSymbolDatabase!
|
||||
// This is made possible by the registration of D3DRS_CULLMODE by XboxSymbolDatabase
|
||||
static bool verifiedRenderStateOffset = false;
|
||||
if (verifiedRenderStateOffset) {
|
||||
return;
|
||||
}
|
||||
|
||||
verifiedRenderStateOffset = true;
|
||||
|
||||
DWORD CullModeOffset = g_SymbolAddresses["D3DRS_CULLMODE"];
|
||||
|
||||
// If we found a valid CullMode offset, verify the symbol location
|
||||
if (CullModeOffset == 0) {
|
||||
EmuLog(LOG_LEVEL::WARNING, "D3DRS_CULLMODE could not be found. Please update the XbSymbolDatabase submodule");
|
||||
return;
|
||||
}
|
||||
|
||||
// Calculate index of D3DRS_CULLMODE for this XDK. We start counting from the first deferred state (D3DRS_FOGENABLE)
|
||||
DWORD CullModeIndex = 0;
|
||||
for (int i = XTL::X_D3DRS_FOGENABLE; i < XTL::X_D3DRS_CULLMODE; i++) {
|
||||
if (XTL::DxbxRenderStateInfo[i].V <= g_BuildVersion) {
|
||||
CullModeIndex++;
|
||||
}
|
||||
}
|
||||
|
||||
// If the offset was incorrect, calculate the correct offset, log it, and fix it
|
||||
if ((DWORD)(&XTL::EmuD3DDeferredRenderState[CullModeIndex]) != CullModeOffset) {
|
||||
DWORD CorrectOffset = CullModeOffset - (CullModeIndex * sizeof(DWORD));
|
||||
EmuLog(LOG_LEVEL::WARNING, "EmuD3DDeferredRenderState returned by XboxSymbolDatabase (0x%08X) was incorrect. Correcting to be 0x%08X.\nPlease file an issue with the XbSymbolDatabase project", XTL::EmuD3DDeferredRenderState, CorrectOffset);
|
||||
XTL::EmuD3DDeferredRenderState = (DWORD*)CorrectOffset;
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateDeferredRenderStates()
|
||||
{
|
||||
// Certain D3DRS values need to be checked on each Draw[Indexed]Vertices
|
||||
if (XTL::EmuD3DDeferredRenderState != 0) {
|
||||
// Loop through all deferred render states
|
||||
for (unsigned int RenderState = XTL::X_D3DRS_FOGENABLE; RenderState <= XTL::X_D3DRS_PRESENTATIONINTERVAL; RenderState++) {
|
||||
uint8_t index = RenderState - XTL::X_D3DRS_FOGENABLE;
|
||||
DWORD Value = XTL::EmuD3DDeferredRenderState[index];
|
||||
|
||||
// Convert from Xbox Data Formats to PC
|
||||
switch (RenderState) {
|
||||
case XTL::X_D3DRS_FOGENABLE:
|
||||
case XTL::X_D3DRS_FOGTABLEMODE:
|
||||
case XTL::X_D3DRS_FOGSTART:
|
||||
case XTL::X_D3DRS_FOGEND:
|
||||
case XTL::X_D3DRS_FOGDENSITY:
|
||||
case XTL::X_D3DRS_RANGEFOGENABLE:
|
||||
case XTL::X_D3DRS_LIGHTING:
|
||||
case XTL::X_D3DRS_SPECULARENABLE:
|
||||
case XTL::X_D3DRS_LOCALVIEWER:
|
||||
case XTL::X_D3DRS_COLORVERTEX:
|
||||
case XTL::X_D3DRS_SPECULARMATERIALSOURCE:
|
||||
case XTL::X_D3DRS_DIFFUSEMATERIALSOURCE:
|
||||
case XTL::X_D3DRS_AMBIENTMATERIALSOURCE:
|
||||
case XTL::X_D3DRS_EMISSIVEMATERIALSOURCE:
|
||||
case XTL::X_D3DRS_AMBIENT:
|
||||
case XTL::X_D3DRS_POINTSIZE:
|
||||
case XTL::X_D3DRS_POINTSIZE_MIN:
|
||||
case XTL::X_D3DRS_POINTSPRITEENABLE:
|
||||
case XTL::X_D3DRS_POINTSCALEENABLE:
|
||||
case XTL::X_D3DRS_POINTSCALE_A:
|
||||
case XTL::X_D3DRS_POINTSCALE_B:
|
||||
case XTL::X_D3DRS_POINTSCALE_C:
|
||||
case XTL::X_D3DRS_POINTSIZE_MAX:
|
||||
case XTL::X_D3DRS_PATCHEDGESTYLE:
|
||||
case XTL::X_D3DRS_PATCHSEGMENTS:
|
||||
// These render states require no conversion, so we can use them as-is
|
||||
break;
|
||||
case XTL::X_D3DRS_BACKSPECULARMATERIALSOURCE:
|
||||
case XTL::X_D3DRS_BACKDIFFUSEMATERIALSOURCE:
|
||||
case XTL::X_D3DRS_BACKAMBIENTMATERIALSOURCE:
|
||||
case XTL::X_D3DRS_BACKEMISSIVEMATERIALSOURCE:
|
||||
case XTL::X_D3DRS_BACKAMBIENT:
|
||||
case XTL::X_D3DRS_SWAPFILTER:
|
||||
case XTL::X_D3DRS_PRESENTATIONINTERVAL:
|
||||
// These render states are unsupported by the host, so we skip them entirely
|
||||
continue;
|
||||
case XTL::X_D3DRS_WRAP0:
|
||||
case XTL::X_D3DRS_WRAP1:
|
||||
case XTL::X_D3DRS_WRAP2:
|
||||
case XTL::X_D3DRS_WRAP3: {
|
||||
DWORD OldValue = Value;
|
||||
Value = 0;
|
||||
|
||||
Value |= (OldValue & 0x00000010) ? D3DWRAPCOORD_0 : 0;
|
||||
Value |= (OldValue & 0x00001000) ? D3DWRAPCOORD_1 : 0;
|
||||
Value |= (OldValue & 0x00100000) ? D3DWRAPCOORD_2 : 0;
|
||||
Value |= (OldValue & 0x01000000) ? D3DWRAPCOORD_3 : 0;
|
||||
} break;
|
||||
default:
|
||||
EmuLog(LOG_LEVEL::WARNING, "Unimplemented Deferred Render State: %s", XTL::DxbxRenderStateInfo[RenderState].S);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (XTL::DxbxRenderStateInfo[RenderState].PC == 0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
g_pD3DDevice->SetRenderState(XTL::DxbxRenderStateInfo[RenderState].PC, Value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
DWORD GetDeferredTextureStateFromIndex(DWORD State)
|
||||
{
|
||||
// On early XDKs, we need to shuffle the values around a little
|
||||
// TODO: Verify which XDK version this change occurred at
|
||||
if (g_BuildVersion <= 3948) {
|
||||
// Values range 0-9 (D3DTSS_COLOROP to D3DTSS_TEXTURETRANSFORMFLAGS) become 12-21
|
||||
if (State <= 9) {
|
||||
return State + 12;
|
||||
}
|
||||
|
||||
// All Remaining values 10-21 (D3DTSS_ADDRESSU to D3DTSS_ALPHAKILL) become 0-11
|
||||
return State - 10;
|
||||
}
|
||||
|
||||
// On later XDKs, the mapping is identical to our representation
|
||||
return State;
|
||||
}
|
||||
|
||||
DWORD Map3911ToCxbxD3DTOP(DWORD Value)
|
||||
{
|
||||
switch (Value) {
|
||||
case 1: return XTL::X_D3DTOP_DISABLE;
|
||||
case 2: return XTL::X_D3DTOP_SELECTARG1;
|
||||
case 3: return XTL::X_D3DTOP_SELECTARG2;
|
||||
case 4: return XTL::X_D3DTOP_MODULATE;
|
||||
case 5: return XTL::X_D3DTOP_MODULATE2X;
|
||||
case 6: return XTL::X_D3DTOP_MODULATE4X;
|
||||
case 7: return XTL::X_D3DTOP_ADD;
|
||||
case 8: return XTL::X_D3DTOP_ADDSIGNED;
|
||||
case 9: return XTL::X_D3DTOP_ADDSIGNED2X;
|
||||
case 10: return XTL::X_D3DTOP_SUBTRACT;
|
||||
case 11: return XTL::X_D3DTOP_ADDSMOOTH;
|
||||
case 12: return XTL::X_D3DTOP_BLENDDIFFUSEALPHA;
|
||||
case 13: return XTL::X_D3DTOP_BLENDTEXTUREALPHA;
|
||||
case 14: return XTL::X_D3DTOP_BLENDFACTORALPHA;
|
||||
case 15: return XTL::X_D3DTOP_BLENDTEXTUREALPHAPM;
|
||||
case 16: return XTL::X_D3DTOP_BLENDCURRENTALPHA;
|
||||
case 17: return XTL::X_D3DTOP_PREMODULATE;
|
||||
case 18: return XTL::X_D3DTOP_MODULATEALPHA_ADDCOLOR;
|
||||
case 19: return XTL::X_D3DTOP_MODULATECOLOR_ADDALPHA;
|
||||
case 20: return XTL::X_D3DTOP_MODULATEINVALPHA_ADDCOLOR;
|
||||
case 21: return XTL::X_D3DTOP_MODULATEINVCOLOR_ADDALPHA;
|
||||
case 22: return XTL::X_D3DTOP_BUMPENVMAP;
|
||||
case 23: return XTL::X_D3DTOP_BUMPENVMAPLUMINANCE;
|
||||
case 24: return XTL::X_D3DTOP_DOTPRODUCT3;
|
||||
case 25: return XTL::X_D3DTOP_MULTIPLYADD;
|
||||
case 26: return XTL::X_D3DTOP_LERP;
|
||||
}
|
||||
|
||||
EmuLog(LOG_LEVEL::WARNING, "Unknown X_D3DTOP Value");
|
||||
return Value;
|
||||
}
|
||||
|
||||
DWORD TranslateXDKSpecificD3DTOP(DWORD Value)
|
||||
{
|
||||
// TODO: Determine when exactly these values changed
|
||||
// So far, 4134 is the earliest version we've seen using these mappings
|
||||
// But this may change
|
||||
if (g_BuildVersion >= 4134) {
|
||||
// For these XDKs, the mapping has been confirmed to match our internal mapping
|
||||
return Value;
|
||||
}
|
||||
|
||||
return Map3911ToCxbxD3DTOP(Value);
|
||||
}
|
||||
|
||||
void UpdateDeferredTextureStates()
|
||||
{
|
||||
// Iterate through all deferred texture states/stages
|
||||
|
||||
// Track if we need to overwrite state 0 with 3 because of Point Sprites
|
||||
// The Xbox NV2A uses only Stage 3 for point-sprites, so we emulate this
|
||||
// by mapping Stage 3 to Stage 0, and disabling all stages > 0
|
||||
bool pointSpriteOverride = false;
|
||||
if (XTL::EmuD3DDeferredRenderState[XTL::X_D3DRS_POINTSPRITEENABLE - XTL::X_D3DRS_FOGENABLE] == TRUE) {
|
||||
pointSpriteOverride = true;
|
||||
}
|
||||
|
||||
for (int XboxStage = 0; XboxStage < XTL::X_D3DTS_STAGECOUNT; XboxStage++) {
|
||||
// If point sprites are enabled, we need to overwrite our existing state 0 with State 3 also
|
||||
DWORD HostStage = (pointSpriteOverride && XboxStage == 3) ? 0 : XboxStage;
|
||||
|
||||
for (int StateIndex = XTL::X_D3DTSS_DEFERRED_FIRST; StateIndex <= XTL::X_D3DTSS_DEFERRED_LAST; StateIndex++) {
|
||||
// Read the value of the current stage/state from the Xbox data structure
|
||||
DWORD Value = XTL::EmuD3DDeferredTextureState[(XboxStage * XTL::X_D3DTS_STAGESIZE) + StateIndex];
|
||||
|
||||
// Convert the index of the current state to an index that we can use
|
||||
// This handles the case when XDKs have different state values
|
||||
DWORD XboxState = GetDeferredTextureStateFromIndex(StateIndex);
|
||||
|
||||
switch (XboxState) {
|
||||
case XTL::X_D3DTSS_ADDRESSU: case XTL::X_D3DTSS_ADDRESSV: case XTL::X_D3DTSS_ADDRESSW:
|
||||
if (Value == XTL::X_D3DTADDRESS_CLAMPTOEDGE) {
|
||||
EmuLog(LOG_LEVEL::WARNING, "ClampToEdge is unsupported");
|
||||
break;
|
||||
}
|
||||
|
||||
// These states match the PC counterpart IDs
|
||||
g_pD3DDevice->SetSamplerState(HostStage, (XTL::D3DSAMPLERSTATETYPE)(XboxState + 1), Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_MAGFILTER: case XTL::X_D3DTSS_MINFILTER: case XTL::X_D3DTSS_MIPFILTER:
|
||||
if (Value == XTL::X_D3DTEXF_QUINCUNX) {
|
||||
EmuLog(LOG_LEVEL::WARNING, "QuinCunx is unsupported");
|
||||
break;
|
||||
}
|
||||
|
||||
// These states (when incremented by 2) match the PC counterpart IDs
|
||||
g_pD3DDevice->SetSamplerState(HostStage, (XTL::D3DSAMPLERSTATETYPE)(XboxState + 2), Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_MIPMAPLODBIAS:
|
||||
g_pD3DDevice->SetSamplerState(HostStage, XTL::D3DSAMP_MIPMAPLODBIAS, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_MAXMIPLEVEL:
|
||||
g_pD3DDevice->SetSamplerState(HostStage, XTL::D3DSAMP_MAXMIPLEVEL, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_MAXANISOTROPY:
|
||||
g_pD3DDevice->SetSamplerState(HostStage, XTL::D3DSAMP_MAXANISOTROPY, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_COLORKEYOP: // Xbox ext
|
||||
// Logging Disabled: Causes Dashboard to slow down massively
|
||||
//EmuLog(LOG_LEVEL::WARNING, "D3DTSS_COLORKEYOP is unsupported");
|
||||
break;
|
||||
case XTL::X_D3DTSS_COLORSIGN: // Xbox ext
|
||||
// Logging Disabled: Causes Dashboard to slow down massively
|
||||
//EmuLog(LOG_LEVEL::WARNING, "D3DTSS_COLORSIGN is unsupported");
|
||||
break;
|
||||
case XTL::X_D3DTSS_ALPHAKILL: // Xbox ext
|
||||
// Logging Disabled: Causes Dashboard to slow down massively
|
||||
//EmuLog(LOG_LEVEL::WARNING, "D3DTSS_ALPHAKILL is unsupported");
|
||||
break;
|
||||
case XTL::X_D3DTSS_COLOROP:
|
||||
switch (TranslateXDKSpecificD3DTOP(Value)) {
|
||||
case XTL::X_D3DTOP_DISABLE:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_DISABLE);
|
||||
break;
|
||||
case XTL::X_D3DTOP_SELECTARG1:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_SELECTARG1);
|
||||
break;
|
||||
case XTL::X_D3DTOP_SELECTARG2:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_SELECTARG2);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATE:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_MODULATE);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATE2X:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_MODULATE2X);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATE4X:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_MODULATE4X);
|
||||
break;
|
||||
case XTL::X_D3DTOP_ADD:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_ADD);
|
||||
break;
|
||||
case XTL::X_D3DTOP_ADDSIGNED:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_ADDSIGNED);
|
||||
break;
|
||||
case XTL::X_D3DTOP_ADDSIGNED2X:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_ADDSIGNED2X);
|
||||
break;
|
||||
case XTL::X_D3DTOP_SUBTRACT:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_SUBTRACT);
|
||||
break;
|
||||
case XTL::X_D3DTOP_ADDSMOOTH:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_ADDSMOOTH);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDDIFFUSEALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_BLENDDIFFUSEALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDCURRENTALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_BLENDCURRENTALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDTEXTUREALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_BLENDTEXTUREALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDFACTORALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_BLENDFACTORALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDTEXTUREALPHAPM:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_BLENDTEXTUREALPHAPM);
|
||||
break;
|
||||
case XTL::X_D3DTOP_PREMODULATE:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_PREMODULATE);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATEALPHA_ADDCOLOR:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_MODULATEALPHA_ADDCOLOR);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATECOLOR_ADDALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_MODULATECOLOR_ADDALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATEINVALPHA_ADDCOLOR:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_MODULATEINVALPHA_ADDCOLOR);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATEINVCOLOR_ADDALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_MODULATEINVCOLOR_ADDALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_DOTPRODUCT3:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_DOTPRODUCT3);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MULTIPLYADD:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_MULTIPLYADD);
|
||||
break;
|
||||
case XTL::X_D3DTOP_LERP:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_LERP);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BUMPENVMAP:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_BUMPENVMAP);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BUMPENVMAPLUMINANCE:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLOROP, XTL::D3DTOP_BUMPENVMAPLUMINANCE);
|
||||
break;
|
||||
default:
|
||||
EmuLog(LOG_LEVEL::WARNING, "Unsupported D3DTSS_COLOROP Value (%d)", Value);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case XTL::X_D3DTSS_COLORARG0:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLORARG0, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_COLORARG1:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLORARG1, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_COLORARG2:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_COLORARG2, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_ALPHAOP:
|
||||
// TODO: Use a lookup table, this is not always a 1:1 map (same as D3DTSS_COLOROP)
|
||||
if (Value != X_D3DTSS_UNK) {
|
||||
switch (TranslateXDKSpecificD3DTOP(Value)) {
|
||||
case XTL::X_D3DTOP_DISABLE:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_DISABLE);
|
||||
break;
|
||||
case XTL::X_D3DTOP_SELECTARG1:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_SELECTARG1);
|
||||
break;
|
||||
case XTL::X_D3DTOP_SELECTARG2:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_SELECTARG2);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATE:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_MODULATE);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATE2X:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_MODULATE2X);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATE4X:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_MODULATE4X);
|
||||
break;
|
||||
case XTL::X_D3DTOP_ADD:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_ADD);
|
||||
break;
|
||||
case XTL::X_D3DTOP_ADDSIGNED:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_ADDSIGNED);
|
||||
break;
|
||||
case XTL::X_D3DTOP_ADDSIGNED2X:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_ADDSIGNED2X);
|
||||
break;
|
||||
case XTL::X_D3DTOP_SUBTRACT:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_SUBTRACT);
|
||||
break;
|
||||
case XTL::X_D3DTOP_ADDSMOOTH:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_ADDSMOOTH);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDDIFFUSEALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_BLENDDIFFUSEALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDTEXTUREALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_BLENDTEXTUREALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDFACTORALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_BLENDFACTORALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDTEXTUREALPHAPM:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_BLENDTEXTUREALPHAPM);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BLENDCURRENTALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_BLENDCURRENTALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_PREMODULATE:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_PREMODULATE);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATEALPHA_ADDCOLOR:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_MODULATEALPHA_ADDCOLOR);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATECOLOR_ADDALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_MODULATECOLOR_ADDALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATEINVALPHA_ADDCOLOR:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_MODULATEINVALPHA_ADDCOLOR);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MODULATEINVCOLOR_ADDALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_MODULATEINVCOLOR_ADDALPHA);
|
||||
break;
|
||||
case XTL::X_D3DTOP_DOTPRODUCT3:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_DOTPRODUCT3);
|
||||
break;
|
||||
case XTL::X_D3DTOP_MULTIPLYADD:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_MULTIPLYADD);
|
||||
break;
|
||||
case XTL::X_D3DTOP_LERP:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_LERP);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BUMPENVMAP:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_BUMPENVMAP);
|
||||
break;
|
||||
case XTL::X_D3DTOP_BUMPENVMAPLUMINANCE:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_BUMPENVMAPLUMINANCE);
|
||||
break;
|
||||
default:
|
||||
EmuLog(LOG_LEVEL::WARNING, "Unsupported D3DTSS_ALPHAOP Value (%d)", Value);
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case XTL::X_D3DTSS_ALPHAARG0:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAARG0, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_ALPHAARG1:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAARG1, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_ALPHAARG2:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_ALPHAARG2, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_RESULTARG:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_RESULTARG, Value);
|
||||
break;
|
||||
case XTL::X_D3DTSS_TEXTURETRANSFORMFLAGS:
|
||||
g_pD3DDevice->SetTextureStageState(HostStage, XTL::D3DTSS_TEXTURETRANSFORMFLAGS, Value);
|
||||
break;
|
||||
default:
|
||||
EmuLog(LOG_LEVEL::WARNING, "Unkown Xbox D3DTSS Value: %d", XboxState);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Make sure we only do this once
|
||||
if (pointSpriteOverride && XboxStage == 3) {
|
||||
pointSpriteOverride = false;
|
||||
XboxStage--;
|
||||
}
|
||||
}
|
||||
|
||||
if (XTL::EmuD3DDeferredRenderState[XTL::X_D3DRS_POINTSPRITEENABLE - XTL::X_D3DRS_FOGENABLE] == TRUE) {
|
||||
XTL::IDirect3DBaseTexture *pTexture;
|
||||
|
||||
// set the point sprites texture
|
||||
g_pD3DDevice->GetTexture(3, &pTexture);
|
||||
g_pD3DDevice->SetTexture(0, pTexture);
|
||||
|
||||
// disable all other stages
|
||||
g_pD3DDevice->SetTextureStageState(1, XTL::D3DTSS_COLOROP, XTL::D3DTOP_DISABLE);
|
||||
g_pD3DDevice->SetTextureStageState(1, XTL::D3DTSS_ALPHAOP, XTL::D3DTOP_DISABLE);
|
||||
|
||||
// no need to actually copy here, since it was handled in the loop above
|
||||
}
|
||||
}
|
||||
|
||||
// ******************************************************************
|
||||
// * patch: UpdateDeferredStates
|
||||
// ******************************************************************
|
||||
void XTL::EmuUpdateDeferredStates()
|
||||
{
|
||||
using namespace XTL;
|
||||
|
||||
// Verify that EmuD3DDeferredRenderState is correct, if not, we can programatically correct it
|
||||
// We should also flag up a warning so this can be fixed upstream in XboxSymbolDatabase!
|
||||
// This is made possible by the registration of D3DRS_CULLMODE by XboxSymbolDatabase
|
||||
static bool verifiedRenderStateOffset = false;
|
||||
if (!verifiedRenderStateOffset) {
|
||||
DWORD CullModeOffset = g_SymbolAddresses["D3DRS_CULLMODE"];
|
||||
|
||||
// If we found a valid CullMode offset, verify the symbol location
|
||||
if (CullModeOffset != 0) {
|
||||
// Calculate index of D3DRS_CULLMODE for this XDK. We start counting from the first deferred state (D3DRS_FOGENABLE)
|
||||
DWORD CullModeIndex = 0;
|
||||
for (int i = X_D3DRS_FOGENABLE; i < X_D3DRS_CULLMODE; i++) {
|
||||
if (DxbxRenderStateInfo[i].V <= g_BuildVersion) {
|
||||
CullModeIndex++;
|
||||
}
|
||||
}
|
||||
|
||||
// If the offset was incorrect, calculate the correct offset, log it, and fix it
|
||||
if ((DWORD)(&EmuD3DDeferredRenderState[CullModeIndex]) != CullModeOffset) {
|
||||
DWORD CorrectOffset = CullModeOffset - (CullModeIndex * sizeof(DWORD));
|
||||
EmuLog(LOG_LEVEL::WARNING, "EmuD3DDeferredRenderState returned by XboxSymbolDatabase (0x%08X) was incorrect. Correcting to be 0x%08X.\nPlease file an issue with the XbSymbolDatabase project", EmuD3DDeferredRenderState, CorrectOffset);
|
||||
EmuD3DDeferredRenderState = (DWORD*)CorrectOffset;
|
||||
}
|
||||
} else {
|
||||
EmuLog(LOG_LEVEL::WARNING, "D3DRS_CULLMODE could not be found. Please update the XbSymbolDatabase submodule");
|
||||
}
|
||||
|
||||
verifiedRenderStateOffset = true;
|
||||
}
|
||||
|
||||
// Certain D3DRS values need to be checked on each Draw[Indexed]Vertices
|
||||
if(EmuD3DDeferredRenderState != 0)
|
||||
{
|
||||
// Loop through all deferred render states
|
||||
for (unsigned int RenderState = X_D3DRS_FOGENABLE; RenderState <= X_D3DRS_PATCHSEGMENTS; RenderState++) {
|
||||
// If this render state does not have a PC counterpart, skip it
|
||||
if (DxbxRenderStateInfo[RenderState].PC == 0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
uint8_t index = RenderState - X_D3DRS_FOGENABLE;
|
||||
// Some render states require special handling to convert to host, but most can be mapped 1:1
|
||||
// We use a switch/case to handle the special states
|
||||
switch (RenderState) {
|
||||
case X_D3DRS_WRAP0: {
|
||||
::DWORD dwConv = 0;
|
||||
|
||||
dwConv |= (XTL::EmuD3DDeferredRenderState[index] & 0x00000010) ? D3DWRAP_U : 0;
|
||||
dwConv |= (XTL::EmuD3DDeferredRenderState[index] & 0x00001000) ? D3DWRAP_V : 0;
|
||||
dwConv |= (XTL::EmuD3DDeferredRenderState[index] & 0x00100000) ? D3DWRAP_W : 0;
|
||||
|
||||
g_pD3DDevice->SetRenderState(D3DRS_WRAP0, dwConv);
|
||||
} break;
|
||||
case X_D3DRS_WRAP1: {
|
||||
::DWORD dwConv = 0;
|
||||
|
||||
dwConv |= (XTL::EmuD3DDeferredRenderState[index] & 0x00000010) ? D3DWRAP_U : 0;
|
||||
dwConv |= (XTL::EmuD3DDeferredRenderState[index] & 0x00001000) ? D3DWRAP_V : 0;
|
||||
dwConv |= (XTL::EmuD3DDeferredRenderState[index] & 0x00100000) ? D3DWRAP_W : 0;
|
||||
|
||||
g_pD3DDevice->SetRenderState(D3DRS_WRAP1, dwConv);
|
||||
} break;
|
||||
default:
|
||||
g_pD3DDevice->SetRenderState(DxbxRenderStateInfo[RenderState].PC, EmuD3DDeferredRenderState[index]);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// For below XDK 3948, the actual D3DTSS flags have different values.
|
||||
int Adjust1 = (g_BuildVersion <= 3948) ? 12 : 0;
|
||||
int Adjust2 = (g_BuildVersion <= 3948) ? 10 : 0;
|
||||
|
||||
// Certain D3DTS values need to be checked on each Draw[Indexed]Vertices
|
||||
if(EmuD3DDeferredTextureState != 0)
|
||||
{
|
||||
for(int v=0;v<4;v++)
|
||||
{
|
||||
::DWORD *pCur = &EmuD3DDeferredTextureState[v*32];
|
||||
|
||||
if(pCur[0+Adjust2] != X_D3DTSS_UNK)
|
||||
{
|
||||
if(pCur[0+Adjust2] == 5)
|
||||
EmuLog(LOG_LEVEL::WARNING, "ClampToEdge is unsupported (temporarily)");
|
||||
else
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_ADDRESSU, pCur[0 + Adjust2]);
|
||||
}
|
||||
|
||||
if(pCur[1+Adjust2] != X_D3DTSS_UNK)
|
||||
{
|
||||
if(pCur[1+Adjust2] == 5)
|
||||
EmuLog(LOG_LEVEL::WARNING, "ClampToEdge is unsupported (temporarily)");
|
||||
else
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_ADDRESSV, pCur[1 + Adjust2]);
|
||||
}
|
||||
|
||||
if(pCur[2+Adjust2] != X_D3DTSS_UNK)
|
||||
{
|
||||
if(pCur[2+Adjust2] == 5)
|
||||
EmuLog(LOG_LEVEL::WARNING, "ClampToEdge is unsupported (temporarily)");
|
||||
else
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_ADDRESSW, pCur[2 + Adjust2]);
|
||||
}
|
||||
|
||||
if(pCur[3+Adjust2] != X_D3DTSS_UNK)
|
||||
{
|
||||
if(pCur[3+Adjust2] == 4)
|
||||
EmuLog(LOG_LEVEL::WARNING, "QuinCunx is unsupported (temporarily)");
|
||||
else
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_MAGFILTER, pCur[3 + Adjust2]);
|
||||
}
|
||||
|
||||
if(pCur[4+Adjust2] != X_D3DTSS_UNK)
|
||||
{
|
||||
if(pCur[4+Adjust2] == 4)
|
||||
EmuLog(LOG_LEVEL::WARNING, "QuinCunx is unsupported (temporarily)");
|
||||
else
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_MINFILTER, pCur[4 + Adjust2]);
|
||||
}
|
||||
|
||||
if(pCur[5+Adjust2] != X_D3DTSS_UNK)
|
||||
{
|
||||
if(pCur[5+Adjust2] == 4)
|
||||
EmuLog(LOG_LEVEL::WARNING, "QuinCunx is unsupported (temporarily)");
|
||||
else
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_MIPFILTER, pCur[5 + Adjust2]);
|
||||
}
|
||||
|
||||
if(pCur[6+Adjust2] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_MIPMAPLODBIAS, pCur[6 + Adjust2]);
|
||||
|
||||
if(pCur[7+Adjust2] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_MAXMIPLEVEL, pCur[7 + Adjust2]);
|
||||
|
||||
if(pCur[8+Adjust2] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_MAXANISOTROPY, pCur[8 + Adjust2]);
|
||||
|
||||
if(pCur[12-Adjust1] != X_D3DTSS_UNK)
|
||||
{
|
||||
// TODO: This would be better split into it's own function, or a lookup array
|
||||
switch (pCur[12 - Adjust1])
|
||||
{
|
||||
case X_D3DTOP_DISABLE:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_DISABLE);
|
||||
break;
|
||||
case X_D3DTOP_SELECTARG1:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
|
||||
break;
|
||||
case X_D3DTOP_SELECTARG2:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_SELECTARG2);
|
||||
break;
|
||||
case X_D3DTOP_MODULATE:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
break;
|
||||
case X_D3DTOP_MODULATE2X:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_MODULATE2X);
|
||||
break;
|
||||
case X_D3DTOP_MODULATE4X:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_MODULATE4X);
|
||||
break;
|
||||
case X_D3DTOP_ADD:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_ADD);
|
||||
break;
|
||||
case X_D3DTOP_ADDSIGNED:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_ADDSIGNED);
|
||||
break;
|
||||
case X_D3DTOP_ADDSIGNED2X:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_ADDSIGNED2X);
|
||||
break;
|
||||
case X_D3DTOP_SUBTRACT:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_SUBTRACT);
|
||||
break;
|
||||
case X_D3DTOP_ADDSMOOTH:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_ADDSMOOTH);
|
||||
break;
|
||||
case X_D3DTOP_BLENDDIFFUSEALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_BLENDDIFFUSEALPHA);
|
||||
break;
|
||||
case X_D3DTOP_BLENDCURRENTALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_BLENDCURRENTALPHA);
|
||||
break;
|
||||
case X_D3DTOP_BLENDTEXTUREALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_BLENDTEXTUREALPHA);
|
||||
break;
|
||||
case X_D3DTOP_BLENDFACTORALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_BLENDFACTORALPHA);
|
||||
break;
|
||||
case X_D3DTOP_BLENDTEXTUREALPHAPM:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_BLENDTEXTUREALPHAPM);
|
||||
break;
|
||||
case X_D3DTOP_PREMODULATE:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_PREMODULATE);
|
||||
break;
|
||||
case X_D3DTOP_MODULATEALPHA_ADDCOLOR:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_MODULATEALPHA_ADDCOLOR);
|
||||
break;
|
||||
case X_D3DTOP_MODULATECOLOR_ADDALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_MODULATECOLOR_ADDALPHA);
|
||||
break;
|
||||
case X_D3DTOP_MODULATEINVALPHA_ADDCOLOR:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_MODULATEINVALPHA_ADDCOLOR);
|
||||
break;
|
||||
case X_D3DTOP_MODULATEINVCOLOR_ADDALPHA:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_MODULATEINVCOLOR_ADDALPHA);
|
||||
break;
|
||||
case X_D3DTOP_DOTPRODUCT3:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_DOTPRODUCT3);
|
||||
break;
|
||||
case X_D3DTOP_MULTIPLYADD:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_MULTIPLYADD);
|
||||
break;
|
||||
case X_D3DTOP_LERP:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_LERP);
|
||||
break;
|
||||
case X_D3DTOP_BUMPENVMAP:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_BUMPENVMAP);
|
||||
break;
|
||||
case X_D3DTOP_BUMPENVMAPLUMINANCE:
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLOROP, D3DTOP_BUMPENVMAPLUMINANCE);
|
||||
break;
|
||||
default:
|
||||
EmuLog(LOG_LEVEL::WARNING, "(Temporarily) Unsupported D3DTSS_COLOROP Value (%d)", pCur[12 - Adjust1]);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(pCur[13-Adjust1] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLORARG0, pCur[13-Adjust1]);
|
||||
|
||||
if(pCur[14-Adjust1] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLORARG1, pCur[14-Adjust1]);
|
||||
|
||||
if(pCur[15-Adjust1] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_COLORARG2, pCur[15-Adjust1]);
|
||||
|
||||
// TODO: Use a lookup table, this is not always a 1:1 map (same as D3DTSS_COLOROP)
|
||||
if(pCur[16-Adjust1] != X_D3DTSS_UNK)
|
||||
{
|
||||
if(pCur[16-Adjust1] > 12 && pCur[16-Adjust1] != 14 && pCur[16-Adjust1] != 13)
|
||||
EmuLog(LOG_LEVEL::WARNING, "(Temporarily) Unsupported D3DTSS_ALPHAOP Value (%d)", pCur[16-Adjust1]);
|
||||
else
|
||||
if( pCur[16-Adjust1] == 14 )
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_ALPHAOP, D3DTOP_BLENDTEXTUREALPHA);
|
||||
if( pCur[16-Adjust1] == 15 )
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_ALPHAOP, D3DTOP_BLENDFACTORALPHA);
|
||||
if( pCur[16-Adjust1] == 13 )
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_ALPHAOP, D3DTOP_BLENDCURRENTALPHA);
|
||||
else
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_ALPHAOP, pCur[16-Adjust1]);
|
||||
}
|
||||
|
||||
if(pCur[17-Adjust1] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_ALPHAARG0, pCur[17-Adjust1]);
|
||||
|
||||
if(pCur[18-Adjust1] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_ALPHAARG1, pCur[18-Adjust1]);
|
||||
|
||||
if(pCur[19-Adjust1] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_ALPHAARG2, pCur[19-Adjust1]);
|
||||
|
||||
if(pCur[20-Adjust1] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_RESULTARG, pCur[20-Adjust1]);
|
||||
|
||||
if(pCur[21-Adjust1] != X_D3DTSS_UNK)
|
||||
g_pD3DDevice->SetTextureStageState(v, D3DTSS_TEXTURETRANSFORMFLAGS, pCur[21-Adjust1]);
|
||||
|
||||
/*if(pCur[29] != X_D3DTSS_UNK) // This is NOT a deferred texture state!
|
||||
g_pD3DDevice->SetSamplerState(v, D3DSAMP_BORDERCOLOR, pCur[29]);
|
||||
*/
|
||||
|
||||
/** To check for unhandled texture stage state changes
|
||||
for(int r=0;r<32;r++)
|
||||
{
|
||||
static const int unchecked[] =
|
||||
{
|
||||
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 29, 30, 31
|
||||
};
|
||||
|
||||
if(pCur[r] != X_D3DTSS_UNK)
|
||||
{
|
||||
bool pass = true;
|
||||
|
||||
for(int q=0;q<sizeof(unchecked)/sizeof(int);q++)
|
||||
{
|
||||
if(r == unchecked[q])
|
||||
{
|
||||
pass = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(pass)
|
||||
EmuLog(LOG_LEVEL::WARNING, "Unhandled TextureState Change @ %d->%d", v, r);
|
||||
}
|
||||
}
|
||||
//**/
|
||||
}
|
||||
|
||||
// if point sprites are enabled, copy stage 3 over to 0
|
||||
if(EmuD3DDeferredRenderState[26] == TRUE)
|
||||
{
|
||||
// pCur = Texture Stage 3 States
|
||||
::DWORD *pCur = &EmuD3DDeferredTextureState[2*32];
|
||||
|
||||
IDirect3DBaseTexture *pTexture;
|
||||
|
||||
// set the point sprites texture
|
||||
g_pD3DDevice->GetTexture(3, &pTexture);
|
||||
g_pD3DDevice->SetTexture(0, pTexture);
|
||||
|
||||
// disable all other stages
|
||||
g_pD3DDevice->SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_DISABLE);
|
||||
g_pD3DDevice->SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
|
||||
|
||||
// in that case we have to copy over the stage by hand
|
||||
for(int v=0;v<30;v++)
|
||||
{
|
||||
if(pCur[v] != X_D3DTSS_UNK)
|
||||
{
|
||||
::DWORD dwValue;
|
||||
|
||||
// For Direct3D9, everything below X_D3DSAMP_MAXANISOTROPY needs to call GetSamplerState / SetSamplerState :
|
||||
if (v <= X_D3DTSS_MAXANISOTROPY) {
|
||||
g_pD3DDevice->GetSamplerState(3, (D3DSAMPLERSTATETYPE)v, &dwValue);
|
||||
g_pD3DDevice->SetSamplerState(0, (D3DSAMPLERSTATETYPE)v, dwValue);
|
||||
}
|
||||
else
|
||||
{
|
||||
g_pD3DDevice->GetTextureStageState(3, (D3DTEXTURESTAGESTATETYPE)v, &dwValue);
|
||||
g_pD3DDevice->SetTextureStageState(0, (D3DTEXTURESTAGESTATETYPE)v, dwValue);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
VerifyAndFixEmuDeferredRenderStateOffset();
|
||||
UpdateDeferredRenderStates();
|
||||
UpdateDeferredTextureStates();
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue