mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-01-26 15:55:31 +01:00
Fix some potential issues when blending on EFB formats without alpha.
Clean up state transition tables.
This commit is contained in:
parent
0ebe35e0ef
commit
6870c1fdd5
@ -456,6 +456,7 @@ void BPWritten(const BPCmd& bp)
|
|||||||
|
|
||||||
case BPMEM_ZCOMPARE: // Set the Z-Compare and EFB pixel format
|
case BPMEM_ZCOMPARE: // Set the Z-Compare and EFB pixel format
|
||||||
g_renderer->SetColorMask(); // alpha writing needs to be disabled if the new pixel format doesn't have an alpha channel
|
g_renderer->SetColorMask(); // alpha writing needs to be disabled if the new pixel format doesn't have an alpha channel
|
||||||
|
g_renderer->SetBlendMode(true);
|
||||||
OnPixelFormatChange();
|
OnPixelFormatChange();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -54,8 +54,6 @@ static int s_fps = 0;
|
|||||||
|
|
||||||
static u32 s_LastAA = 0;
|
static u32 s_LastAA = 0;
|
||||||
|
|
||||||
static u32 s_blendMode;
|
|
||||||
|
|
||||||
static Television s_television;
|
static Television s_television;
|
||||||
|
|
||||||
ID3D11Buffer* access_efb_cbuf = NULL;
|
ID3D11Buffer* access_efb_cbuf = NULL;
|
||||||
@ -76,151 +74,6 @@ struct
|
|||||||
D3D11_RASTERIZER_DESC rastdc;
|
D3D11_RASTERIZER_DESC rastdc;
|
||||||
} gx_state;
|
} gx_state;
|
||||||
|
|
||||||
// State translation lookup tables
|
|
||||||
static const D3D11_BLEND d3dSrcFactors[8] =
|
|
||||||
{
|
|
||||||
D3D11_BLEND_ZERO,
|
|
||||||
D3D11_BLEND_ONE,
|
|
||||||
D3D11_BLEND_DEST_COLOR,
|
|
||||||
D3D11_BLEND_INV_DEST_COLOR,
|
|
||||||
D3D11_BLEND_SRC_ALPHA,
|
|
||||||
D3D11_BLEND_INV_SRC_ALPHA, // NOTE: Use SRC1_ALPHA if dst alpha is enabled!
|
|
||||||
D3D11_BLEND_DEST_ALPHA,
|
|
||||||
D3D11_BLEND_INV_DEST_ALPHA
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3D11_BLEND d3dDestFactors[8] =
|
|
||||||
{
|
|
||||||
D3D11_BLEND_ZERO,
|
|
||||||
D3D11_BLEND_ONE,
|
|
||||||
D3D11_BLEND_SRC_COLOR,
|
|
||||||
D3D11_BLEND_INV_SRC_COLOR,
|
|
||||||
D3D11_BLEND_SRC_ALPHA,
|
|
||||||
D3D11_BLEND_INV_SRC_ALPHA, // NOTE: Use SRC1_ALPHA if dst alpha is enabled!
|
|
||||||
D3D11_BLEND_DEST_ALPHA,
|
|
||||||
D3D11_BLEND_INV_DEST_ALPHA
|
|
||||||
};
|
|
||||||
|
|
||||||
// 0 0x00
|
|
||||||
// 1 Source & destination
|
|
||||||
// 2 Source & ~destination
|
|
||||||
// 3 Source
|
|
||||||
// 4 ~Source & destination
|
|
||||||
// 5 Destination
|
|
||||||
// 6 Source ^ destination = Source & ~destination | ~Source & destination
|
|
||||||
// 7 Source | destination
|
|
||||||
|
|
||||||
// 8 ~(Source | destination)
|
|
||||||
// 9 ~(Source ^ destination) = ~Source & ~destination | Source & destination
|
|
||||||
// 10 ~Destination
|
|
||||||
// 11 Source | ~destination
|
|
||||||
// 12 ~Source
|
|
||||||
// 13 ~Source | destination
|
|
||||||
// 14 ~(Source & destination)
|
|
||||||
// 15 0xff
|
|
||||||
|
|
||||||
static const D3D11_BLEND_OP d3dLogicOps[16] =
|
|
||||||
{
|
|
||||||
D3D11_BLEND_OP_ADD,//0
|
|
||||||
D3D11_BLEND_OP_ADD,//1
|
|
||||||
D3D11_BLEND_OP_SUBTRACT,//2
|
|
||||||
D3D11_BLEND_OP_ADD,//3
|
|
||||||
D3D11_BLEND_OP_REV_SUBTRACT,//4
|
|
||||||
D3D11_BLEND_OP_ADD,//5
|
|
||||||
D3D11_BLEND_OP_MAX,//6
|
|
||||||
D3D11_BLEND_OP_ADD,//7
|
|
||||||
|
|
||||||
D3D11_BLEND_OP_MAX,//8
|
|
||||||
D3D11_BLEND_OP_MAX,//9
|
|
||||||
D3D11_BLEND_OP_ADD,//10
|
|
||||||
D3D11_BLEND_OP_ADD,//11
|
|
||||||
D3D11_BLEND_OP_ADD,//12
|
|
||||||
D3D11_BLEND_OP_ADD,//13
|
|
||||||
D3D11_BLEND_OP_ADD,//14
|
|
||||||
D3D11_BLEND_OP_ADD//15
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3D11_BLEND d3dLogicOpSrcFactors[16] =
|
|
||||||
{
|
|
||||||
D3D11_BLEND_ZERO,//0
|
|
||||||
D3D11_BLEND_DEST_COLOR,//1
|
|
||||||
D3D11_BLEND_ONE,//2
|
|
||||||
D3D11_BLEND_ONE,//3
|
|
||||||
D3D11_BLEND_DEST_COLOR,//4
|
|
||||||
D3D11_BLEND_ZERO,//5
|
|
||||||
D3D11_BLEND_INV_DEST_COLOR,//6
|
|
||||||
D3D11_BLEND_INV_DEST_COLOR,//7
|
|
||||||
|
|
||||||
D3D11_BLEND_INV_SRC_COLOR,//8
|
|
||||||
D3D11_BLEND_INV_SRC_COLOR,//9
|
|
||||||
D3D11_BLEND_INV_DEST_COLOR,//10
|
|
||||||
D3D11_BLEND_ONE,//11
|
|
||||||
D3D11_BLEND_INV_SRC_COLOR,//12
|
|
||||||
D3D11_BLEND_INV_SRC_COLOR,//13
|
|
||||||
D3D11_BLEND_INV_DEST_COLOR,//14
|
|
||||||
D3D11_BLEND_ONE//15
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3D11_BLEND d3dLogicOpDestFactors[16] =
|
|
||||||
{
|
|
||||||
D3D11_BLEND_ZERO,//0
|
|
||||||
D3D11_BLEND_ZERO,//1
|
|
||||||
D3D11_BLEND_INV_SRC_COLOR,//2
|
|
||||||
D3D11_BLEND_ZERO,//3
|
|
||||||
D3D11_BLEND_ONE,//4
|
|
||||||
D3D11_BLEND_ONE,//5
|
|
||||||
D3D11_BLEND_INV_SRC_COLOR,//6
|
|
||||||
D3D11_BLEND_ONE,//7
|
|
||||||
|
|
||||||
D3D11_BLEND_INV_DEST_COLOR,//8
|
|
||||||
D3D11_BLEND_SRC_COLOR,//9
|
|
||||||
D3D11_BLEND_INV_DEST_COLOR,//10
|
|
||||||
D3D11_BLEND_INV_DEST_COLOR,//11
|
|
||||||
D3D11_BLEND_INV_SRC_COLOR,//12
|
|
||||||
D3D11_BLEND_ONE,//13
|
|
||||||
D3D11_BLEND_INV_SRC_COLOR,//14
|
|
||||||
D3D11_BLEND_ONE//15
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3D11_CULL_MODE d3dCullModes[4] =
|
|
||||||
{
|
|
||||||
D3D11_CULL_NONE,
|
|
||||||
D3D11_CULL_BACK,
|
|
||||||
D3D11_CULL_FRONT,
|
|
||||||
D3D11_CULL_BACK
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3D11_COMPARISON_FUNC d3dCmpFuncs[8] =
|
|
||||||
{
|
|
||||||
D3D11_COMPARISON_NEVER,
|
|
||||||
D3D11_COMPARISON_LESS,
|
|
||||||
D3D11_COMPARISON_EQUAL,
|
|
||||||
D3D11_COMPARISON_LESS_EQUAL,
|
|
||||||
D3D11_COMPARISON_GREATER,
|
|
||||||
D3D11_COMPARISON_NOT_EQUAL,
|
|
||||||
D3D11_COMPARISON_GREATER_EQUAL,
|
|
||||||
D3D11_COMPARISON_ALWAYS
|
|
||||||
};
|
|
||||||
|
|
||||||
#define TEXF_NONE 0
|
|
||||||
#define TEXF_POINT 1
|
|
||||||
#define TEXF_LINEAR 2
|
|
||||||
static const unsigned int d3dMipFilters[4] =
|
|
||||||
{
|
|
||||||
TEXF_NONE,
|
|
||||||
TEXF_POINT,
|
|
||||||
TEXF_LINEAR,
|
|
||||||
TEXF_NONE, //reserved
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3D11_TEXTURE_ADDRESS_MODE d3dClamps[4] =
|
|
||||||
{
|
|
||||||
D3D11_TEXTURE_ADDRESS_CLAMP,
|
|
||||||
D3D11_TEXTURE_ADDRESS_WRAP,
|
|
||||||
D3D11_TEXTURE_ADDRESS_MIRROR,
|
|
||||||
D3D11_TEXTURE_ADDRESS_WRAP //reserved
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
void SetupDeviceObjects()
|
void SetupDeviceObjects()
|
||||||
{
|
{
|
||||||
@ -338,7 +191,6 @@ void CreateScreenshotTexture()
|
|||||||
Renderer::Renderer()
|
Renderer::Renderer()
|
||||||
{
|
{
|
||||||
int x, y, w_temp, h_temp;
|
int x, y, w_temp, h_temp;
|
||||||
s_blendMode = 0;
|
|
||||||
|
|
||||||
InitFPSCounter();
|
InitFPSCounter();
|
||||||
|
|
||||||
@ -833,6 +685,32 @@ void SetBlendOp(D3D11_BLEND_OP val)
|
|||||||
|
|
||||||
void Renderer::SetBlendMode(bool forceUpdate)
|
void Renderer::SetBlendMode(bool forceUpdate)
|
||||||
{
|
{
|
||||||
|
// Our render target always uses an alpha channel, so we need to override the blend functions to assume a destination alpha of 1 if the render target isn't supposed to have an alpha channel
|
||||||
|
// Example: D3DBLEND_DESTALPHA needs to be D3DBLEND_ONE since the result without an alpha channel is assumed to always be 1.
|
||||||
|
bool target_has_alpha = bpmem.zcontrol.pixel_format == PIXELFMT_RGBA6_Z24;
|
||||||
|
const D3D11_BLEND d3dSrcFactors[8] =
|
||||||
|
{
|
||||||
|
D3D11_BLEND_ZERO,
|
||||||
|
D3D11_BLEND_ONE,
|
||||||
|
D3D11_BLEND_DEST_COLOR,
|
||||||
|
D3D11_BLEND_INV_DEST_COLOR,
|
||||||
|
D3D11_BLEND_SRC_ALPHA,
|
||||||
|
D3D11_BLEND_INV_SRC_ALPHA, // NOTE: Use SRC1_ALPHA if dst alpha is enabled!
|
||||||
|
(target_has_alpha) ? D3D11_BLEND_DEST_ALPHA : D3D11_BLEND_ONE,
|
||||||
|
(target_has_alpha) ? D3D11_BLEND_INV_DEST_ALPHA : D3D11_BLEND_ZERO
|
||||||
|
};
|
||||||
|
const D3D11_BLEND d3dDestFactors[8] =
|
||||||
|
{
|
||||||
|
D3D11_BLEND_ZERO,
|
||||||
|
D3D11_BLEND_ONE,
|
||||||
|
D3D11_BLEND_SRC_COLOR,
|
||||||
|
D3D11_BLEND_INV_SRC_COLOR,
|
||||||
|
D3D11_BLEND_SRC_ALPHA,
|
||||||
|
D3D11_BLEND_INV_SRC_ALPHA, // NOTE: Use SRC1_ALPHA if dst alpha is enabled!
|
||||||
|
(target_has_alpha) ? D3D11_BLEND_DEST_ALPHA : D3D11_BLEND_ONE,
|
||||||
|
(target_has_alpha) ? D3D11_BLEND_INV_DEST_ALPHA : D3D11_BLEND_ZERO
|
||||||
|
};
|
||||||
|
|
||||||
if (bpmem.blendmode.logicopenable && !forceUpdate)
|
if (bpmem.blendmode.logicopenable && !forceUpdate)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
@ -845,8 +723,8 @@ void Renderer::SetBlendMode(bool forceUpdate)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
gx_state.blenddc.RenderTarget[0].BlendEnable = bpmem.blendmode.blendenable && (!( bpmem.blendmode.srcfactor == 1 && bpmem.blendmode.dstfactor == 0));
|
gx_state.blenddc.RenderTarget[0].BlendEnable = bpmem.blendmode.blendenable;
|
||||||
if (bpmem.blendmode.blendenable && (!( bpmem.blendmode.srcfactor == 1 && bpmem.blendmode.dstfactor == 0)))
|
if (bpmem.blendmode.blendenable)
|
||||||
{
|
{
|
||||||
SetBlendOp(D3D11_BLEND_OP_ADD);
|
SetBlendOp(D3D11_BLEND_OP_ADD);
|
||||||
SetSrcBlend(d3dSrcFactors[bpmem.blendmode.srcfactor]);
|
SetSrcBlend(d3dSrcFactors[bpmem.blendmode.srcfactor]);
|
||||||
@ -1331,12 +1209,32 @@ void Renderer::RestoreCull()
|
|||||||
|
|
||||||
void Renderer::SetGenerationMode()
|
void Renderer::SetGenerationMode()
|
||||||
{
|
{
|
||||||
|
const D3D11_CULL_MODE d3dCullModes[4] =
|
||||||
|
{
|
||||||
|
D3D11_CULL_NONE,
|
||||||
|
D3D11_CULL_BACK,
|
||||||
|
D3D11_CULL_FRONT,
|
||||||
|
D3D11_CULL_BACK
|
||||||
|
};
|
||||||
|
|
||||||
// rastdc.FrontCounterClockwise must be false for this to work
|
// rastdc.FrontCounterClockwise must be false for this to work
|
||||||
gx_state.rastdc.CullMode = d3dCullModes[bpmem.genMode.cullmode];
|
gx_state.rastdc.CullMode = d3dCullModes[bpmem.genMode.cullmode];
|
||||||
}
|
}
|
||||||
|
|
||||||
void Renderer::SetDepthMode()
|
void Renderer::SetDepthMode()
|
||||||
{
|
{
|
||||||
|
const D3D11_COMPARISON_FUNC d3dCmpFuncs[8] =
|
||||||
|
{
|
||||||
|
D3D11_COMPARISON_NEVER,
|
||||||
|
D3D11_COMPARISON_LESS,
|
||||||
|
D3D11_COMPARISON_EQUAL,
|
||||||
|
D3D11_COMPARISON_LESS_EQUAL,
|
||||||
|
D3D11_COMPARISON_GREATER,
|
||||||
|
D3D11_COMPARISON_NOT_EQUAL,
|
||||||
|
D3D11_COMPARISON_GREATER_EQUAL,
|
||||||
|
D3D11_COMPARISON_ALWAYS
|
||||||
|
};
|
||||||
|
|
||||||
if (bpmem.zmode.testenable)
|
if (bpmem.zmode.testenable)
|
||||||
{
|
{
|
||||||
gx_state.depthdc.DepthEnable = TRUE;
|
gx_state.depthdc.DepthEnable = TRUE;
|
||||||
@ -1353,9 +1251,85 @@ void Renderer::SetDepthMode()
|
|||||||
|
|
||||||
void Renderer::SetLogicOpMode()
|
void Renderer::SetLogicOpMode()
|
||||||
{
|
{
|
||||||
if (bpmem.blendmode.logicopenable && bpmem.blendmode.logicmode != 3)
|
// D3D11 doesn't support logic blending, so this is a huge hack
|
||||||
|
// TODO: Make use of D3D11.1's logic blending support
|
||||||
|
|
||||||
|
// 0 0x00
|
||||||
|
// 1 Source & destination
|
||||||
|
// 2 Source & ~destination
|
||||||
|
// 3 Source
|
||||||
|
// 4 ~Source & destination
|
||||||
|
// 5 Destination
|
||||||
|
// 6 Source ^ destination = Source & ~destination | ~Source & destination
|
||||||
|
// 7 Source | destination
|
||||||
|
// 8 ~(Source | destination)
|
||||||
|
// 9 ~(Source ^ destination) = ~Source & ~destination | Source & destination
|
||||||
|
// 10 ~Destination
|
||||||
|
// 11 Source | ~destination
|
||||||
|
// 12 ~Source
|
||||||
|
// 13 ~Source | destination
|
||||||
|
// 14 ~(Source & destination)
|
||||||
|
// 15 0xff
|
||||||
|
const D3D11_BLEND_OP d3dLogicOps[16] =
|
||||||
|
{
|
||||||
|
D3D11_BLEND_OP_ADD,//0
|
||||||
|
D3D11_BLEND_OP_ADD,//1
|
||||||
|
D3D11_BLEND_OP_SUBTRACT,//2
|
||||||
|
D3D11_BLEND_OP_ADD,//3
|
||||||
|
D3D11_BLEND_OP_REV_SUBTRACT,//4
|
||||||
|
D3D11_BLEND_OP_ADD,//5
|
||||||
|
D3D11_BLEND_OP_MAX,//6
|
||||||
|
D3D11_BLEND_OP_ADD,//7
|
||||||
|
D3D11_BLEND_OP_MAX,//8
|
||||||
|
D3D11_BLEND_OP_MAX,//9
|
||||||
|
D3D11_BLEND_OP_ADD,//10
|
||||||
|
D3D11_BLEND_OP_ADD,//11
|
||||||
|
D3D11_BLEND_OP_ADD,//12
|
||||||
|
D3D11_BLEND_OP_ADD,//13
|
||||||
|
D3D11_BLEND_OP_ADD,//14
|
||||||
|
D3D11_BLEND_OP_ADD//15
|
||||||
|
};
|
||||||
|
const D3D11_BLEND d3dLogicOpSrcFactors[16] =
|
||||||
|
{
|
||||||
|
D3D11_BLEND_ZERO,//0
|
||||||
|
D3D11_BLEND_DEST_COLOR,//1
|
||||||
|
D3D11_BLEND_ONE,//2
|
||||||
|
D3D11_BLEND_ONE,//3
|
||||||
|
D3D11_BLEND_DEST_COLOR,//4
|
||||||
|
D3D11_BLEND_ZERO,//5
|
||||||
|
D3D11_BLEND_INV_DEST_COLOR,//6
|
||||||
|
D3D11_BLEND_INV_DEST_COLOR,//7
|
||||||
|
D3D11_BLEND_INV_SRC_COLOR,//8
|
||||||
|
D3D11_BLEND_INV_SRC_COLOR,//9
|
||||||
|
D3D11_BLEND_INV_DEST_COLOR,//10
|
||||||
|
D3D11_BLEND_ONE,//11
|
||||||
|
D3D11_BLEND_INV_SRC_COLOR,//12
|
||||||
|
D3D11_BLEND_INV_SRC_COLOR,//13
|
||||||
|
D3D11_BLEND_INV_DEST_COLOR,//14
|
||||||
|
D3D11_BLEND_ONE//15
|
||||||
|
};
|
||||||
|
const D3D11_BLEND d3dLogicOpDestFactors[16] =
|
||||||
|
{
|
||||||
|
D3D11_BLEND_ZERO,//0
|
||||||
|
D3D11_BLEND_ZERO,//1
|
||||||
|
D3D11_BLEND_INV_SRC_COLOR,//2
|
||||||
|
D3D11_BLEND_ZERO,//3
|
||||||
|
D3D11_BLEND_ONE,//4
|
||||||
|
D3D11_BLEND_ONE,//5
|
||||||
|
D3D11_BLEND_INV_SRC_COLOR,//6
|
||||||
|
D3D11_BLEND_ONE,//7
|
||||||
|
D3D11_BLEND_INV_DEST_COLOR,//8
|
||||||
|
D3D11_BLEND_SRC_COLOR,//9
|
||||||
|
D3D11_BLEND_INV_DEST_COLOR,//10
|
||||||
|
D3D11_BLEND_INV_DEST_COLOR,//11
|
||||||
|
D3D11_BLEND_INV_SRC_COLOR,//12
|
||||||
|
D3D11_BLEND_ONE,//13
|
||||||
|
D3D11_BLEND_INV_SRC_COLOR,//14
|
||||||
|
D3D11_BLEND_ONE//15
|
||||||
|
};
|
||||||
|
|
||||||
|
if (bpmem.blendmode.logicopenable)
|
||||||
{
|
{
|
||||||
s_blendMode = 0;
|
|
||||||
gx_state.blenddc.RenderTarget[0].BlendEnable = true;
|
gx_state.blenddc.RenderTarget[0].BlendEnable = true;
|
||||||
SetBlendOp(d3dLogicOps[bpmem.blendmode.logicmode]);
|
SetBlendOp(d3dLogicOps[bpmem.blendmode.logicmode]);
|
||||||
SetSrcBlend(d3dLogicOpSrcFactors[bpmem.blendmode.logicmode]);
|
SetSrcBlend(d3dLogicOpSrcFactors[bpmem.blendmode.logicmode]);
|
||||||
@ -1379,18 +1353,32 @@ void Renderer::SetLineWidth()
|
|||||||
|
|
||||||
void Renderer::SetSamplerState(int stage, int texindex)
|
void Renderer::SetSamplerState(int stage, int texindex)
|
||||||
{
|
{
|
||||||
|
#define TEXF_NONE 0
|
||||||
|
#define TEXF_POINT 1
|
||||||
|
#define TEXF_LINEAR 2
|
||||||
|
const unsigned int d3dMipFilters[4] =
|
||||||
|
{
|
||||||
|
TEXF_NONE,
|
||||||
|
TEXF_POINT,
|
||||||
|
TEXF_LINEAR,
|
||||||
|
TEXF_NONE, //reserved
|
||||||
|
};
|
||||||
|
const D3D11_TEXTURE_ADDRESS_MODE d3dClamps[4] =
|
||||||
|
{
|
||||||
|
D3D11_TEXTURE_ADDRESS_CLAMP,
|
||||||
|
D3D11_TEXTURE_ADDRESS_WRAP,
|
||||||
|
D3D11_TEXTURE_ADDRESS_MIRROR,
|
||||||
|
D3D11_TEXTURE_ADDRESS_WRAP //reserved
|
||||||
|
};
|
||||||
|
|
||||||
const FourTexUnits &tex = bpmem.tex[texindex];
|
const FourTexUnits &tex = bpmem.tex[texindex];
|
||||||
const TexMode0 &tm0 = tex.texMode0[stage];
|
const TexMode0 &tm0 = tex.texMode0[stage];
|
||||||
const TexMode1 &tm1 = tex.texMode1[stage];
|
const TexMode1 &tm1 = tex.texMode1[stage];
|
||||||
|
|
||||||
unsigned int mip;
|
unsigned int mip = d3dMipFilters[tm0.min_filter & 3];
|
||||||
mip = (tm0.min_filter == 8) ? TEXF_NONE:d3dMipFilters[tm0.min_filter & 3];
|
|
||||||
if ((tm0.min_filter & 3) && (tm0.min_filter != 8) && ((tm1.max_lod >> 4) == 0)) mip = TEXF_NONE;
|
|
||||||
|
|
||||||
if (texindex) stage += 4;
|
if (texindex) stage += 4;
|
||||||
|
|
||||||
// TODO: Clarify whether these values are correct
|
|
||||||
// NOTE: since there's no "no filter" in DX11 we're using point filters in these cases
|
|
||||||
if (g_ActiveConfig.bForceFiltering)
|
if (g_ActiveConfig.bForceFiltering)
|
||||||
{
|
{
|
||||||
gx_state.sampdc[stage].Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR;
|
gx_state.sampdc[stage].Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR;
|
||||||
|
@ -73,148 +73,6 @@ static char *st;
|
|||||||
static LPDIRECT3DSURFACE9 ScreenShootMEMSurface = NULL;
|
static LPDIRECT3DSURFACE9 ScreenShootMEMSurface = NULL;
|
||||||
|
|
||||||
|
|
||||||
// State translation lookup tables
|
|
||||||
static const D3DBLEND d3dSrcFactors[8] =
|
|
||||||
{
|
|
||||||
D3DBLEND_ZERO,
|
|
||||||
D3DBLEND_ONE,
|
|
||||||
D3DBLEND_DESTCOLOR,
|
|
||||||
D3DBLEND_INVDESTCOLOR,
|
|
||||||
D3DBLEND_SRCALPHA,
|
|
||||||
D3DBLEND_INVSRCALPHA,
|
|
||||||
D3DBLEND_DESTALPHA,
|
|
||||||
D3DBLEND_INVDESTALPHA
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3DBLEND d3dDestFactors[8] =
|
|
||||||
{
|
|
||||||
D3DBLEND_ZERO,
|
|
||||||
D3DBLEND_ONE,
|
|
||||||
D3DBLEND_SRCCOLOR,
|
|
||||||
D3DBLEND_INVSRCCOLOR,
|
|
||||||
D3DBLEND_SRCALPHA,
|
|
||||||
D3DBLEND_INVSRCALPHA,
|
|
||||||
D3DBLEND_DESTALPHA,
|
|
||||||
D3DBLEND_INVDESTALPHA
|
|
||||||
};
|
|
||||||
|
|
||||||
// 0 0x00
|
|
||||||
// 1 Source & destination
|
|
||||||
// 2 Source & ~destination
|
|
||||||
// 3 Source
|
|
||||||
// 4 ~Source & destination
|
|
||||||
// 5 Destination
|
|
||||||
// 6 Source ^ destination = Source & ~destination | ~Source & destination
|
|
||||||
// 7 Source | destination
|
|
||||||
|
|
||||||
// 8 ~(Source | destination)
|
|
||||||
// 9 ~(Source ^ destination) = ~Source & ~destination | Source & destination
|
|
||||||
// 10 ~Destination
|
|
||||||
// 11 Source | ~destination
|
|
||||||
// 12 ~Source
|
|
||||||
// 13 ~Source | destination
|
|
||||||
// 14 ~(Source & destination)
|
|
||||||
// 15 0xff
|
|
||||||
|
|
||||||
static const D3DBLENDOP d3dLogicOpop[16] =
|
|
||||||
{
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
D3DBLENDOP_SUBTRACT,
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
D3DBLENDOP_REVSUBTRACT,
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
D3DBLENDOP_MAX,
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
|
|
||||||
D3DBLENDOP_MAX,
|
|
||||||
D3DBLENDOP_MAX,
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
D3DBLENDOP_ADD,
|
|
||||||
D3DBLENDOP_ADD
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3DBLEND d3dLogicOpSrcFactors[16] =
|
|
||||||
{
|
|
||||||
D3DBLEND_ZERO,
|
|
||||||
D3DBLEND_DESTCOLOR,
|
|
||||||
D3DBLEND_ONE,
|
|
||||||
D3DBLEND_ONE,
|
|
||||||
D3DBLEND_DESTCOLOR,
|
|
||||||
D3DBLEND_ZERO,
|
|
||||||
D3DBLEND_INVDESTCOLOR,
|
|
||||||
D3DBLEND_INVDESTCOLOR,
|
|
||||||
|
|
||||||
D3DBLEND_INVSRCCOLOR,
|
|
||||||
D3DBLEND_INVSRCCOLOR,
|
|
||||||
D3DBLEND_INVDESTCOLOR,
|
|
||||||
D3DBLEND_ONE,
|
|
||||||
D3DBLEND_INVSRCCOLOR,
|
|
||||||
D3DBLEND_INVSRCCOLOR,
|
|
||||||
D3DBLEND_INVDESTCOLOR,
|
|
||||||
D3DBLEND_ONE
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3DBLEND d3dLogicOpDestFactors[16] =
|
|
||||||
{
|
|
||||||
D3DBLEND_ZERO,
|
|
||||||
D3DBLEND_ZERO,
|
|
||||||
D3DBLEND_INVSRCCOLOR,
|
|
||||||
D3DBLEND_ZERO,
|
|
||||||
D3DBLEND_ONE,
|
|
||||||
D3DBLEND_ONE,
|
|
||||||
D3DBLEND_INVSRCCOLOR,
|
|
||||||
D3DBLEND_ONE,
|
|
||||||
|
|
||||||
D3DBLEND_INVDESTCOLOR,
|
|
||||||
D3DBLEND_SRCCOLOR,
|
|
||||||
D3DBLEND_INVDESTCOLOR,
|
|
||||||
D3DBLEND_INVDESTCOLOR,
|
|
||||||
D3DBLEND_INVSRCCOLOR,
|
|
||||||
D3DBLEND_ONE,
|
|
||||||
D3DBLEND_INVSRCCOLOR,
|
|
||||||
D3DBLEND_ONE
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3DCULL d3dCullModes[4] =
|
|
||||||
{
|
|
||||||
D3DCULL_NONE,
|
|
||||||
D3DCULL_CCW,
|
|
||||||
D3DCULL_CW,
|
|
||||||
D3DCULL_CCW
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3DCMPFUNC d3dCmpFuncs[8] =
|
|
||||||
{
|
|
||||||
D3DCMP_NEVER,
|
|
||||||
D3DCMP_LESS,
|
|
||||||
D3DCMP_EQUAL,
|
|
||||||
D3DCMP_LESSEQUAL,
|
|
||||||
D3DCMP_GREATER,
|
|
||||||
D3DCMP_NOTEQUAL,
|
|
||||||
D3DCMP_GREATEREQUAL,
|
|
||||||
D3DCMP_ALWAYS
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3DTEXTUREFILTERTYPE d3dMipFilters[4] =
|
|
||||||
{
|
|
||||||
D3DTEXF_NONE,
|
|
||||||
D3DTEXF_POINT,
|
|
||||||
D3DTEXF_LINEAR,
|
|
||||||
D3DTEXF_NONE, //reserved
|
|
||||||
};
|
|
||||||
|
|
||||||
static const D3DTEXTUREADDRESS d3dClamps[4] =
|
|
||||||
{
|
|
||||||
D3DTADDRESS_CLAMP,
|
|
||||||
D3DTADDRESS_WRAP,
|
|
||||||
D3DTADDRESS_MIRROR,
|
|
||||||
D3DTADDRESS_WRAP //reserved
|
|
||||||
};
|
|
||||||
|
|
||||||
void SetupDeviceObjects()
|
void SetupDeviceObjects()
|
||||||
{
|
{
|
||||||
D3D::font.Init();
|
D3D::font.Init();
|
||||||
@ -796,6 +654,32 @@ void Renderer::ReinterpretPixelData(unsigned int convtype)
|
|||||||
|
|
||||||
void Renderer::SetBlendMode(bool forceUpdate)
|
void Renderer::SetBlendMode(bool forceUpdate)
|
||||||
{
|
{
|
||||||
|
// Our render target always uses an alpha channel, so we need to override the blend functions to assume a destination alpha of 1 if the render target isn't supposed to have an alpha channel
|
||||||
|
// Example: D3DBLEND_DESTALPHA needs to be D3DBLEND_ONE since the result without an alpha channel is assumed to always be 1.
|
||||||
|
bool target_has_alpha = bpmem.zcontrol.pixel_format == PIXELFMT_RGBA6_Z24;
|
||||||
|
const D3DBLEND d3dSrcFactors[8] =
|
||||||
|
{
|
||||||
|
D3DBLEND_ZERO,
|
||||||
|
D3DBLEND_ONE,
|
||||||
|
D3DBLEND_DESTCOLOR,
|
||||||
|
D3DBLEND_INVDESTCOLOR,
|
||||||
|
D3DBLEND_SRCALPHA,
|
||||||
|
D3DBLEND_INVSRCALPHA,
|
||||||
|
(target_has_alpha) ? D3DBLEND_DESTALPHA : D3DBLEND_ONE,
|
||||||
|
(target_has_alpha) ? D3DBLEND_INVDESTALPHA : D3DBLEND_ZERO
|
||||||
|
};
|
||||||
|
const D3DBLEND d3dDestFactors[8] =
|
||||||
|
{
|
||||||
|
D3DBLEND_ZERO,
|
||||||
|
D3DBLEND_ONE,
|
||||||
|
D3DBLEND_SRCCOLOR,
|
||||||
|
D3DBLEND_INVSRCCOLOR,
|
||||||
|
D3DBLEND_SRCALPHA,
|
||||||
|
D3DBLEND_INVSRCALPHA,
|
||||||
|
(target_has_alpha) ? D3DBLEND_DESTALPHA : D3DBLEND_ONE,
|
||||||
|
(target_has_alpha) ? D3DBLEND_INVDESTALPHA : D3DBLEND_ZERO
|
||||||
|
};
|
||||||
|
|
||||||
if (bpmem.blendmode.logicopenable && !forceUpdate)
|
if (bpmem.blendmode.logicopenable && !forceUpdate)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
@ -808,8 +692,8 @@ void Renderer::SetBlendMode(bool forceUpdate)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
D3D::SetRenderState(D3DRS_ALPHABLENDENABLE, bpmem.blendmode.blendenable && (!( bpmem.blendmode.srcfactor == 1 && bpmem.blendmode.dstfactor == 0)));
|
D3D::SetRenderState(D3DRS_ALPHABLENDENABLE, bpmem.blendmode.blendenable);
|
||||||
if (bpmem.blendmode.blendenable && (!( bpmem.blendmode.srcfactor == 1 && bpmem.blendmode.dstfactor == 0)))
|
if (bpmem.blendmode.blendenable)
|
||||||
{
|
{
|
||||||
D3D::SetRenderState(D3DRS_BLENDOP, D3DBLENDOP_ADD);
|
D3D::SetRenderState(D3DRS_BLENDOP, D3DBLENDOP_ADD);
|
||||||
D3D::SetRenderState(D3DRS_SRCBLEND, d3dSrcFactors[bpmem.blendmode.srcfactor]);
|
D3D::SetRenderState(D3DRS_SRCBLEND, d3dSrcFactors[bpmem.blendmode.srcfactor]);
|
||||||
@ -1261,11 +1145,31 @@ void Renderer::RestoreAPIState()
|
|||||||
|
|
||||||
void Renderer::SetGenerationMode()
|
void Renderer::SetGenerationMode()
|
||||||
{
|
{
|
||||||
|
const D3DCULL d3dCullModes[4] =
|
||||||
|
{
|
||||||
|
D3DCULL_NONE,
|
||||||
|
D3DCULL_CCW,
|
||||||
|
D3DCULL_CW,
|
||||||
|
D3DCULL_CCW
|
||||||
|
};
|
||||||
|
|
||||||
D3D::SetRenderState(D3DRS_CULLMODE, d3dCullModes[bpmem.genMode.cullmode]);
|
D3D::SetRenderState(D3DRS_CULLMODE, d3dCullModes[bpmem.genMode.cullmode]);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Renderer::SetDepthMode()
|
void Renderer::SetDepthMode()
|
||||||
{
|
{
|
||||||
|
const D3DCMPFUNC d3dCmpFuncs[8] =
|
||||||
|
{
|
||||||
|
D3DCMP_NEVER,
|
||||||
|
D3DCMP_LESS,
|
||||||
|
D3DCMP_EQUAL,
|
||||||
|
D3DCMP_LESSEQUAL,
|
||||||
|
D3DCMP_GREATER,
|
||||||
|
D3DCMP_NOTEQUAL,
|
||||||
|
D3DCMP_GREATEREQUAL,
|
||||||
|
D3DCMP_ALWAYS
|
||||||
|
};
|
||||||
|
|
||||||
if (bpmem.zmode.testenable)
|
if (bpmem.zmode.testenable)
|
||||||
{
|
{
|
||||||
D3D::SetRenderState(D3DRS_ZENABLE, TRUE);
|
D3D::SetRenderState(D3DRS_ZENABLE, TRUE);
|
||||||
@ -1282,7 +1186,83 @@ void Renderer::SetDepthMode()
|
|||||||
|
|
||||||
void Renderer::SetLogicOpMode()
|
void Renderer::SetLogicOpMode()
|
||||||
{
|
{
|
||||||
if (bpmem.blendmode.logicopenable && bpmem.blendmode.logicmode != 3)
|
// D3D9 doesn't support logic blending, so this is a huge hack
|
||||||
|
|
||||||
|
// 0 0x00
|
||||||
|
// 1 Source & destination
|
||||||
|
// 2 Source & ~destination
|
||||||
|
// 3 Source
|
||||||
|
// 4 ~Source & destination
|
||||||
|
// 5 Destination
|
||||||
|
// 6 Source ^ destination = Source & ~destination | ~Source & destination
|
||||||
|
// 7 Source | destination
|
||||||
|
// 8 ~(Source | destination)
|
||||||
|
// 9 ~(Source ^ destination) = ~Source & ~destination | Source & destination
|
||||||
|
// 10 ~Destination
|
||||||
|
// 11 Source | ~destination
|
||||||
|
// 12 ~Source
|
||||||
|
// 13 ~Source | destination
|
||||||
|
// 14 ~(Source & destination)
|
||||||
|
// 15 0xff
|
||||||
|
const D3DBLENDOP d3dLogicOpop[16] =
|
||||||
|
{
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_SUBTRACT,
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_REVSUBTRACT,
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_MAX,
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_MAX,
|
||||||
|
D3DBLENDOP_MAX,
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_ADD,
|
||||||
|
D3DBLENDOP_ADD
|
||||||
|
};
|
||||||
|
const D3DBLEND d3dLogicOpSrcFactors[16] =
|
||||||
|
{
|
||||||
|
D3DBLEND_ZERO,
|
||||||
|
D3DBLEND_DESTCOLOR,
|
||||||
|
D3DBLEND_ONE,
|
||||||
|
D3DBLEND_ONE,
|
||||||
|
D3DBLEND_DESTCOLOR,
|
||||||
|
D3DBLEND_ZERO,
|
||||||
|
D3DBLEND_INVDESTCOLOR,
|
||||||
|
D3DBLEND_INVDESTCOLOR,
|
||||||
|
D3DBLEND_INVSRCCOLOR,
|
||||||
|
D3DBLEND_INVSRCCOLOR,
|
||||||
|
D3DBLEND_INVDESTCOLOR,
|
||||||
|
D3DBLEND_ONE,
|
||||||
|
D3DBLEND_INVSRCCOLOR,
|
||||||
|
D3DBLEND_INVSRCCOLOR,
|
||||||
|
D3DBLEND_INVDESTCOLOR,
|
||||||
|
D3DBLEND_ONE
|
||||||
|
};
|
||||||
|
const D3DBLEND d3dLogicOpDestFactors[16] =
|
||||||
|
{
|
||||||
|
D3DBLEND_ZERO,
|
||||||
|
D3DBLEND_ZERO,
|
||||||
|
D3DBLEND_INVSRCCOLOR,
|
||||||
|
D3DBLEND_ZERO,
|
||||||
|
D3DBLEND_ONE,
|
||||||
|
D3DBLEND_ONE,
|
||||||
|
D3DBLEND_INVSRCCOLOR,
|
||||||
|
D3DBLEND_ONE,
|
||||||
|
D3DBLEND_INVDESTCOLOR,
|
||||||
|
D3DBLEND_SRCCOLOR,
|
||||||
|
D3DBLEND_INVDESTCOLOR,
|
||||||
|
D3DBLEND_INVDESTCOLOR,
|
||||||
|
D3DBLEND_INVSRCCOLOR,
|
||||||
|
D3DBLEND_ONE,
|
||||||
|
D3DBLEND_INVSRCCOLOR,
|
||||||
|
D3DBLEND_ONE
|
||||||
|
};
|
||||||
|
|
||||||
|
if (bpmem.blendmode.logicopenable)
|
||||||
{
|
{
|
||||||
D3D::SetRenderState(D3DRS_ALPHABLENDENABLE, true);
|
D3D::SetRenderState(D3DRS_ALPHABLENDENABLE, true);
|
||||||
D3D::SetRenderState(D3DRS_BLENDOP, d3dLogicOpop[bpmem.blendmode.logicmode]);
|
D3D::SetRenderState(D3DRS_BLENDOP, d3dLogicOpop[bpmem.blendmode.logicmode]);
|
||||||
@ -1310,6 +1290,21 @@ void Renderer::SetLineWidth()
|
|||||||
|
|
||||||
void Renderer::SetSamplerState(int stage, int texindex)
|
void Renderer::SetSamplerState(int stage, int texindex)
|
||||||
{
|
{
|
||||||
|
const D3DTEXTUREFILTERTYPE d3dMipFilters[4] =
|
||||||
|
{
|
||||||
|
D3DTEXF_NONE,
|
||||||
|
D3DTEXF_POINT,
|
||||||
|
D3DTEXF_LINEAR,
|
||||||
|
D3DTEXF_NONE, //reserved
|
||||||
|
};
|
||||||
|
const D3DTEXTUREADDRESS d3dClamps[4] =
|
||||||
|
{
|
||||||
|
D3DTADDRESS_CLAMP,
|
||||||
|
D3DTADDRESS_WRAP,
|
||||||
|
D3DTADDRESS_MIRROR,
|
||||||
|
D3DTADDRESS_WRAP //reserved
|
||||||
|
};
|
||||||
|
|
||||||
const FourTexUnits &tex = bpmem.tex[texindex];
|
const FourTexUnits &tex = bpmem.tex[texindex];
|
||||||
const TexMode0 &tm0 = tex.texMode0[stage];
|
const TexMode0 &tm0 = tex.texMode0[stage];
|
||||||
const TexMode1 &tm1 = tex.texMode1[stage];
|
const TexMode1 &tm1 = tex.texMode1[stage];
|
||||||
@ -1323,13 +1318,11 @@ void Renderer::SetSamplerState(int stage, int texindex)
|
|||||||
{
|
{
|
||||||
min = (tm0.min_filter & 4) ? D3DTEXF_LINEAR : D3DTEXF_POINT;
|
min = (tm0.min_filter & 4) ? D3DTEXF_LINEAR : D3DTEXF_POINT;
|
||||||
mag = tm0.mag_filter ? D3DTEXF_LINEAR : D3DTEXF_POINT;
|
mag = tm0.mag_filter ? D3DTEXF_LINEAR : D3DTEXF_POINT;
|
||||||
mip = (tm0.min_filter == 8) ? D3DTEXF_NONE : d3dMipFilters[tm0.min_filter & 3];
|
mip = d3dMipFilters[tm0.min_filter & 3];
|
||||||
if((tm0.min_filter & 3) && (tm0.min_filter != 8) && ((tm1.max_lod >> 4) == 0))
|
|
||||||
mip = D3DTEXF_NONE;
|
|
||||||
}
|
}
|
||||||
if (texindex)
|
if (texindex)
|
||||||
stage += 4;
|
stage += 4;
|
||||||
|
|
||||||
if (mag == D3DTEXF_LINEAR && min == D3DTEXF_LINEAR && g_ActiveConfig.iMaxAnisotropy)
|
if (mag == D3DTEXF_LINEAR && min == D3DTEXF_LINEAR && g_ActiveConfig.iMaxAnisotropy)
|
||||||
{
|
{
|
||||||
min = D3DTEXF_ANISOTROPIC;
|
min = D3DTEXF_ANISOTROPIC;
|
||||||
@ -1340,8 +1333,7 @@ void Renderer::SetSamplerState(int stage, int texindex)
|
|||||||
|
|
||||||
D3D::SetSamplerState(stage, D3DSAMP_ADDRESSU, d3dClamps[tm0.wrap_s]);
|
D3D::SetSamplerState(stage, D3DSAMP_ADDRESSU, d3dClamps[tm0.wrap_s]);
|
||||||
D3D::SetSamplerState(stage, D3DSAMP_ADDRESSV, d3dClamps[tm0.wrap_t]);
|
D3D::SetSamplerState(stage, D3DSAMP_ADDRESSV, d3dClamps[tm0.wrap_t]);
|
||||||
//float SuperSampleCoeficient = (s_LastAA < 3)? s_LastAA + 1 : s_LastAA - 1;// uncoment this changes to conserve detail when incresing ssaa level
|
float lodbias = tm0.lod_bias / 32.0f;
|
||||||
float lodbias = (tm0.lod_bias / 32.0f);// + (s_LastAA)?(log(SuperSampleCoeficient) / log(2.0f)):0;
|
|
||||||
D3D::SetSamplerState(stage, D3DSAMP_MIPMAPLODBIAS, *(DWORD*)&lodbias);
|
D3D::SetSamplerState(stage, D3DSAMP_MIPMAPLODBIAS, *(DWORD*)&lodbias);
|
||||||
D3D::SetSamplerState(stage, D3DSAMP_MAXMIPLEVEL, tm1.min_lod >> 4);
|
D3D::SetSamplerState(stage, D3DSAMP_MAXMIPLEVEL, tm1.min_lod >> 4);
|
||||||
}
|
}
|
||||||
|
@ -132,58 +132,6 @@ const u32 EFB_CACHE_HEIGHT = (EFB_HEIGHT + EFB_CACHE_RECT_SIZE - 1) / EFB_CACHE_
|
|||||||
static bool s_efbCacheValid[2][EFB_CACHE_WIDTH * EFB_CACHE_HEIGHT];
|
static bool s_efbCacheValid[2][EFB_CACHE_WIDTH * EFB_CACHE_HEIGHT];
|
||||||
static std::vector<u32> s_efbCache[2][EFB_CACHE_WIDTH * EFB_CACHE_HEIGHT]; // 2 for PEEK_Z and PEEK_COLOR
|
static std::vector<u32> s_efbCache[2][EFB_CACHE_WIDTH * EFB_CACHE_HEIGHT]; // 2 for PEEK_Z and PEEK_COLOR
|
||||||
|
|
||||||
static const GLenum glSrcFactors[8] =
|
|
||||||
{
|
|
||||||
GL_ZERO,
|
|
||||||
GL_ONE,
|
|
||||||
GL_DST_COLOR,
|
|
||||||
GL_ONE_MINUS_DST_COLOR,
|
|
||||||
GL_SRC_ALPHA,
|
|
||||||
GL_ONE_MINUS_SRC_ALPHA, // NOTE: If dual-source blending is enabled, use SRC1_ALPHA
|
|
||||||
GL_DST_ALPHA,
|
|
||||||
GL_ONE_MINUS_DST_ALPHA
|
|
||||||
};
|
|
||||||
|
|
||||||
static const GLenum glDestFactors[8] = {
|
|
||||||
GL_ZERO,
|
|
||||||
GL_ONE,
|
|
||||||
GL_SRC_COLOR,
|
|
||||||
GL_ONE_MINUS_SRC_COLOR,
|
|
||||||
GL_SRC_ALPHA,
|
|
||||||
GL_ONE_MINUS_SRC_ALPHA, // NOTE: If dual-source blending is enabled, use SRC1_ALPHA
|
|
||||||
GL_DST_ALPHA,
|
|
||||||
GL_ONE_MINUS_DST_ALPHA
|
|
||||||
};
|
|
||||||
|
|
||||||
static const GLenum glCmpFuncs[8] = {
|
|
||||||
GL_NEVER,
|
|
||||||
GL_LESS,
|
|
||||||
GL_EQUAL,
|
|
||||||
GL_LEQUAL,
|
|
||||||
GL_GREATER,
|
|
||||||
GL_NOTEQUAL,
|
|
||||||
GL_GEQUAL,
|
|
||||||
GL_ALWAYS
|
|
||||||
};
|
|
||||||
|
|
||||||
static const GLenum glLogicOpCodes[16] = {
|
|
||||||
GL_CLEAR,
|
|
||||||
GL_AND,
|
|
||||||
GL_AND_REVERSE,
|
|
||||||
GL_COPY,
|
|
||||||
GL_AND_INVERTED,
|
|
||||||
GL_NOOP,
|
|
||||||
GL_XOR,
|
|
||||||
GL_OR,
|
|
||||||
GL_NOR,
|
|
||||||
GL_EQUIV,
|
|
||||||
GL_INVERT,
|
|
||||||
GL_OR_REVERSE,
|
|
||||||
GL_COPY_INVERTED,
|
|
||||||
GL_OR_INVERTED,
|
|
||||||
GL_NAND,
|
|
||||||
GL_SET
|
|
||||||
};
|
|
||||||
|
|
||||||
#if defined HAVE_CG && HAVE_CG
|
#if defined HAVE_CG && HAVE_CG
|
||||||
void HandleCgError(CGcontext ctx, CGerror err, void* appdata)
|
void HandleCgError(CGcontext ctx, CGerror err, void* appdata)
|
||||||
@ -908,6 +856,32 @@ void Renderer::ReinterpretPixelData(unsigned int convtype)
|
|||||||
|
|
||||||
void Renderer::SetBlendMode(bool forceUpdate)
|
void Renderer::SetBlendMode(bool forceUpdate)
|
||||||
{
|
{
|
||||||
|
// Our render target always uses an alpha channel, so we need to override the blend functions to assume a destination alpha of 1 if the render target isn't supposed to have an alpha channel
|
||||||
|
// Example: D3DBLEND_DESTALPHA needs to be D3DBLEND_ONE since the result without an alpha channel is assumed to always be 1.
|
||||||
|
bool target_has_alpha = bpmem.zcontrol.pixel_format == PIXELFMT_RGBA6_Z24;
|
||||||
|
const GLenum glSrcFactors[8] =
|
||||||
|
{
|
||||||
|
GL_ZERO,
|
||||||
|
GL_ONE,
|
||||||
|
GL_DST_COLOR,
|
||||||
|
GL_ONE_MINUS_DST_COLOR,
|
||||||
|
GL_SRC_ALPHA,
|
||||||
|
GL_ONE_MINUS_SRC_ALPHA, // NOTE: If dual-source blending is enabled, use SRC1_ALPHA
|
||||||
|
(target_has_alpha) ? GL_DST_ALPHA : (GLenum)GL_ONE,
|
||||||
|
(target_has_alpha) ? GL_ONE_MINUS_DST_ALPHA : (GLenum)GL_ZERO
|
||||||
|
};
|
||||||
|
const GLenum glDestFactors[8] =
|
||||||
|
{
|
||||||
|
GL_ZERO,
|
||||||
|
GL_ONE,
|
||||||
|
GL_SRC_COLOR,
|
||||||
|
GL_ONE_MINUS_SRC_COLOR,
|
||||||
|
GL_SRC_ALPHA,
|
||||||
|
GL_ONE_MINUS_SRC_ALPHA, // NOTE: If dual-source blending is enabled, use SRC1_ALPHA
|
||||||
|
(target_has_alpha) ? GL_DST_ALPHA : (GLenum)GL_ONE,
|
||||||
|
(target_has_alpha) ? GL_ONE_MINUS_DST_ALPHA : (GLenum)GL_ZERO
|
||||||
|
};
|
||||||
|
|
||||||
// blend mode bit mask
|
// blend mode bit mask
|
||||||
// 0 - blend enable
|
// 0 - blend enable
|
||||||
// 2 - reverse subtract enable (else add)
|
// 2 - reverse subtract enable (else add)
|
||||||
@ -951,10 +925,10 @@ void Renderer::SetBlendMode(bool forceUpdate)
|
|||||||
|
|
||||||
if (changes & 0x1F8)
|
if (changes & 0x1F8)
|
||||||
{
|
{
|
||||||
#ifdef USE_DUAL_SOURCE_BLEND
|
|
||||||
GLenum srcFactor = glSrcFactors[(newval >> 3) & 7];
|
GLenum srcFactor = glSrcFactors[(newval >> 3) & 7];
|
||||||
GLenum srcFactorAlpha = srcFactor;
|
|
||||||
GLenum dstFactor = glDestFactors[(newval >> 6) & 7];
|
GLenum dstFactor = glDestFactors[(newval >> 6) & 7];
|
||||||
|
#ifdef USE_DUAL_SOURCE_BLEND
|
||||||
|
GLenum srcFactorAlpha = srcFactor;
|
||||||
GLenum dstFactorAlpha = dstFactor;
|
GLenum dstFactorAlpha = dstFactor;
|
||||||
if (useDualSource)
|
if (useDualSource)
|
||||||
{
|
{
|
||||||
@ -975,7 +949,7 @@ void Renderer::SetBlendMode(bool forceUpdate)
|
|||||||
// blend RGB change
|
// blend RGB change
|
||||||
glBlendFuncSeparate(srcFactor, dstFactor, srcFactorAlpha, dstFactorAlpha);
|
glBlendFuncSeparate(srcFactor, dstFactor, srcFactorAlpha, dstFactorAlpha);
|
||||||
#else
|
#else
|
||||||
glBlendFunc(glSrcFactors[(newval >> 3) & 7], glDestFactors[(newval >> 6) & 7]);
|
glBlendFunc(srcFactor, dstFactor);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1438,6 +1412,18 @@ void Renderer::SetGenerationMode()
|
|||||||
|
|
||||||
void Renderer::SetDepthMode()
|
void Renderer::SetDepthMode()
|
||||||
{
|
{
|
||||||
|
const GLenum glCmpFuncs[8] =
|
||||||
|
{
|
||||||
|
GL_NEVER,
|
||||||
|
GL_LESS,
|
||||||
|
GL_EQUAL,
|
||||||
|
GL_LEQUAL,
|
||||||
|
GL_GREATER,
|
||||||
|
GL_NOTEQUAL,
|
||||||
|
GL_GEQUAL,
|
||||||
|
GL_ALWAYS
|
||||||
|
};
|
||||||
|
|
||||||
if (bpmem.zmode.testenable)
|
if (bpmem.zmode.testenable)
|
||||||
{
|
{
|
||||||
glEnable(GL_DEPTH_TEST);
|
glEnable(GL_DEPTH_TEST);
|
||||||
@ -1454,7 +1440,27 @@ void Renderer::SetDepthMode()
|
|||||||
|
|
||||||
void Renderer::SetLogicOpMode()
|
void Renderer::SetLogicOpMode()
|
||||||
{
|
{
|
||||||
if (bpmem.blendmode.logicopenable && bpmem.blendmode.logicmode != 3)
|
const GLenum glLogicOpCodes[16] =
|
||||||
|
{
|
||||||
|
GL_CLEAR,
|
||||||
|
GL_AND,
|
||||||
|
GL_AND_REVERSE,
|
||||||
|
GL_COPY,
|
||||||
|
GL_AND_INVERTED,
|
||||||
|
GL_NOOP,
|
||||||
|
GL_XOR,
|
||||||
|
GL_OR,
|
||||||
|
GL_NOR,
|
||||||
|
GL_EQUIV,
|
||||||
|
GL_INVERT,
|
||||||
|
GL_OR_REVERSE,
|
||||||
|
GL_COPY_INVERTED,
|
||||||
|
GL_OR_INVERTED,
|
||||||
|
GL_NAND,
|
||||||
|
GL_SET
|
||||||
|
};
|
||||||
|
|
||||||
|
if (bpmem.blendmode.logicopenable)
|
||||||
{
|
{
|
||||||
glEnable(GL_COLOR_LOGIC_OP);
|
glEnable(GL_COLOR_LOGIC_OP);
|
||||||
glLogicOp(glLogicOpCodes[bpmem.blendmode.logicmode]);
|
glLogicOp(glLogicOpCodes[bpmem.blendmode.logicmode]);
|
||||||
|
@ -58,24 +58,6 @@ namespace OGL
|
|||||||
|
|
||||||
static u32 s_TempFramebuffer = 0;
|
static u32 s_TempFramebuffer = 0;
|
||||||
|
|
||||||
static const GLint c_MinLinearFilter[8] = {
|
|
||||||
GL_NEAREST,
|
|
||||||
GL_NEAREST_MIPMAP_NEAREST,
|
|
||||||
GL_NEAREST_MIPMAP_LINEAR,
|
|
||||||
GL_NEAREST,
|
|
||||||
GL_LINEAR,
|
|
||||||
GL_LINEAR_MIPMAP_NEAREST,
|
|
||||||
GL_LINEAR_MIPMAP_LINEAR,
|
|
||||||
GL_LINEAR,
|
|
||||||
};
|
|
||||||
|
|
||||||
static const GLint c_WrapSettings[4] = {
|
|
||||||
GL_CLAMP_TO_EDGE,
|
|
||||||
GL_REPEAT,
|
|
||||||
GL_MIRRORED_REPEAT,
|
|
||||||
GL_REPEAT,
|
|
||||||
};
|
|
||||||
|
|
||||||
bool SaveTexture(const char* filename, u32 textarget, u32 tex, int virtual_width, int virtual_height, unsigned int level)
|
bool SaveTexture(const char* filename, u32 textarget, u32 tex, int virtual_width, int virtual_height, unsigned int level)
|
||||||
{
|
{
|
||||||
int width = std::max(virtual_width >> level, 1);
|
int width = std::max(virtual_width >> level, 1);
|
||||||
@ -357,32 +339,41 @@ void TextureCache::TCacheEntry::FromRenderTarget(u32 dstAddr, unsigned int dstFo
|
|||||||
|
|
||||||
void TextureCache::TCacheEntry::SetTextureParameters(const TexMode0 &newmode, const TexMode1 &newmode1)
|
void TextureCache::TCacheEntry::SetTextureParameters(const TexMode0 &newmode, const TexMode1 &newmode1)
|
||||||
{
|
{
|
||||||
// TODO: not used anywhere
|
const GLint c_MinLinearFilter[8] =
|
||||||
TexMode0 mode = newmode;
|
{
|
||||||
//mode1 = newmode1;
|
GL_NEAREST,
|
||||||
|
GL_NEAREST_MIPMAP_NEAREST,
|
||||||
|
GL_NEAREST_MIPMAP_LINEAR,
|
||||||
|
GL_NEAREST,
|
||||||
|
GL_LINEAR,
|
||||||
|
GL_LINEAR_MIPMAP_NEAREST,
|
||||||
|
GL_LINEAR_MIPMAP_LINEAR,
|
||||||
|
GL_LINEAR,
|
||||||
|
};
|
||||||
|
const GLint c_WrapSettings[4] =
|
||||||
|
{
|
||||||
|
GL_CLAMP_TO_EDGE,
|
||||||
|
GL_REPEAT,
|
||||||
|
GL_MIRRORED_REPEAT,
|
||||||
|
GL_REPEAT,
|
||||||
|
};
|
||||||
|
|
||||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER,
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER,
|
||||||
(newmode.mag_filter || g_Config.bForceFiltering) ? GL_LINEAR : GL_NEAREST);
|
(newmode.mag_filter || g_Config.bForceFiltering) ? GL_LINEAR : GL_NEAREST);
|
||||||
|
|
||||||
if (bHaveMipMaps)
|
int filt = newmode.min_filter;
|
||||||
{
|
if (g_ActiveConfig.bForceFiltering && filt < 4)
|
||||||
// TODO: not used anywhere
|
filt += 4; // take equivalent forced linear
|
||||||
if (g_ActiveConfig.bForceFiltering && newmode.min_filter < 4)
|
|
||||||
mode.min_filter += 4; // take equivalent forced linear
|
|
||||||
|
|
||||||
int filt = newmode.min_filter;
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, c_MinLinearFilter[filt]);
|
||||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, c_MinLinearFilter[filt & 7]);
|
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_BASE_LEVEL, newmode1.min_lod / 16.f);
|
||||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_BASE_LEVEL, newmode1.min_lod >> 4);
|
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, newmode1.max_lod / 16.f);
|
||||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, newmode1.max_lod >> 4);
|
glTexEnvf(GL_TEXTURE_FILTER_CONTROL, GL_TEXTURE_LOD_BIAS, newmode.lod_bias / 32.0f);
|
||||||
glTexEnvf(GL_TEXTURE_FILTER_CONTROL, GL_TEXTURE_LOD_BIAS, (newmode.lod_bias / 32.0f));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
|
|
||||||
(g_ActiveConfig.bForceFiltering || newmode.min_filter >= 4) ? GL_LINEAR : GL_NEAREST);
|
|
||||||
|
|
||||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, c_WrapSettings[newmode.wrap_s]);
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, c_WrapSettings[newmode.wrap_s]);
|
||||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, c_WrapSettings[newmode.wrap_t]);
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, c_WrapSettings[newmode.wrap_t]);
|
||||||
|
|
||||||
|
// TODO: Reset anisotrop when changed to 1
|
||||||
if (g_Config.iMaxAnisotropy >= 1)
|
if (g_Config.iMaxAnisotropy >= 1)
|
||||||
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT,
|
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT,
|
||||||
(float)(1 << g_ActiveConfig.iMaxAnisotropy));
|
(float)(1 << g_ActiveConfig.iMaxAnisotropy));
|
||||||
|
Loading…
x
Reference in New Issue
Block a user