summaryrefslogtreecommitdiff
path: root/Source/Plugins
diff options
context:
space:
mode:
authorNolan Check <Nolan.Check@gmail.com>2010-10-23 19:55:19 +0000
committerNolan Check <Nolan.Check@gmail.com>2010-10-23 19:55:19 +0000
commit2ec3db44edd83ef4d8a6b9db6ac9092f45b63acc (patch)
tree305b3b3fd4517f6b07bf978a87ec41a453e62955 /Source/Plugins
parent91186d2b8a714da4ddaa10b85a4d0165b615c4de (diff)
OpenGL plugin: Support for dual-source blending, CURRENTLY DISABLED. It doesn't work yet. To fix it, we may need to convert all our shaders to GLSL so that we can use glBindFragDataLocation.
git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@6306 8ced0084-cf51-0410-be5f-012b33b47a6e
Diffstat (limited to 'Source/Plugins')
-rw-r--r--Source/Plugins/Plugin_VideoOGL/Src/GLUtil.h5
-rw-r--r--Source/Plugins/Plugin_VideoOGL/Src/Render.cpp38
-rw-r--r--Source/Plugins/Plugin_VideoOGL/Src/VertexManager.cpp29
3 files changed, 64 insertions, 8 deletions
diff --git a/Source/Plugins/Plugin_VideoOGL/Src/GLUtil.h b/Source/Plugins/Plugin_VideoOGL/Src/GLUtil.h
index c0fb1a55f3..754a094cdb 100644
--- a/Source/Plugins/Plugin_VideoOGL/Src/GLUtil.h
+++ b/Source/Plugins/Plugin_VideoOGL/Src/GLUtil.h
@@ -136,4 +136,9 @@ extern CGcontext g_cgcontext;
extern CGprofile g_cgvProf, g_cgfProf;
#endif
+// XXX: Dual-source blending in OpenGL does not work correctly yet. To make it
+// work, we may need to use glBindFragDataLocation. To use that, we need to
+// use GLSL shaders across the whole pipeline. Yikes!
+const bool USE_DUAL_SOURCE_BLEND = false;
+
#endif // _GLINIT_H_
diff --git a/Source/Plugins/Plugin_VideoOGL/Src/Render.cpp b/Source/Plugins/Plugin_VideoOGL/Src/Render.cpp
index b9882f1087..44c84aaf8f 100644
--- a/Source/Plugins/Plugin_VideoOGL/Src/Render.cpp
+++ b/Source/Plugins/Plugin_VideoOGL/Src/Render.cpp
@@ -151,7 +151,7 @@ static const GLenum glSrcFactors[8] =
GL_DST_COLOR,
GL_ONE_MINUS_DST_COLOR,
GL_SRC_ALPHA,
- GL_ONE_MINUS_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
};
@@ -162,7 +162,7 @@ static const GLenum glDestFactors[8] = {
GL_SRC_COLOR,
GL_ONE_MINUS_SRC_COLOR,
GL_SRC_ALPHA,
- GL_ONE_MINUS_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
};
@@ -1034,17 +1034,47 @@ void Renderer::SetBlendMode(bool forceUpdate)
u32 changes = forceUpdate ? 0xFFFFFFFF : newval ^ s_blendMode;
+ bool useDstAlpha = !g_ActiveConfig.bDstAlphaPass && bpmem.dstalpha.enable && bpmem.blendmode.alphaupdate
+ && bpmem.zcontrol.pixel_format == PIXELFMT_RGBA6_Z24;
+ bool useDualSource = USE_DUAL_SOURCE_BLEND && useDstAlpha && GLEW_ARB_blend_func_extended;
+
if (changes & 1)
// blend enable change
(newval & 1) ? glEnable(GL_BLEND) : glDisable(GL_BLEND);
if (changes & 4)
+ {
// subtract enable change
- glBlendEquation(newval & 4 ? GL_FUNC_REVERSE_SUBTRACT : GL_FUNC_ADD);
+ GLenum equation = newval & 4 ? GL_FUNC_REVERSE_SUBTRACT : GL_FUNC_ADD;
+ GLenum equationAlpha = useDualSource ? GL_FUNC_ADD : equation;
+ glBlendEquationSeparate(equation, equationAlpha);
+ }
if (changes & 0x1F8)
+ {
+ GLenum srcFactor = glSrcFactors[(newval >> 3) & 7];
+ GLenum srcFactorAlpha = srcFactor;
+ GLenum dstFactor = glDestFactors[(newval >> 6) & 7];
+ GLenum dstFactorAlpha = dstFactor;
+ if (useDualSource)
+ {
+ srcFactorAlpha = GL_ONE;
+ dstFactorAlpha = GL_ZERO;
+
+ if (srcFactor == GL_SRC_ALPHA)
+ srcFactor = GL_SRC1_ALPHA;
+ else if (srcFactor == GL_ONE_MINUS_SRC_ALPHA)
+ srcFactor = GL_ONE_MINUS_SRC1_ALPHA;
+
+ if (dstFactor == GL_SRC_ALPHA)
+ dstFactor = GL_SRC1_ALPHA;
+ else if (dstFactor == GL_ONE_MINUS_SRC_ALPHA)
+ dstFactor = GL_ONE_MINUS_SRC1_ALPHA;
+ }
+
// blend RGB change
- glBlendFunc(glSrcFactors[(newval >> 3) & 7], glDestFactors[(newval >> 6) & 7]);
+ glBlendFuncSeparate(srcFactor, dstFactor, srcFactorAlpha, dstFactorAlpha);
+ }
s_blendMode = newval;
}
diff --git a/Source/Plugins/Plugin_VideoOGL/Src/VertexManager.cpp b/Source/Plugins/Plugin_VideoOGL/Src/VertexManager.cpp
index ef308524d7..58e677d563 100644
--- a/Source/Plugins/Plugin_VideoOGL/Src/VertexManager.cpp
+++ b/Source/Plugins/Plugin_VideoOGL/Src/VertexManager.cpp
@@ -184,8 +184,31 @@ void VertexManager::vFlush()
VertexShaderManager::SetConstants();
PixelShaderManager::SetConstants();
+ bool useDstAlpha = !g_ActiveConfig.bDstAlphaPass && bpmem.dstalpha.enable && bpmem.blendmode.alphaupdate
+ && bpmem.zcontrol.pixel_format == PIXELFMT_RGBA6_Z24;
+ bool dualSourcePossible = USE_DUAL_SOURCE_BLEND && GLEW_ARB_blend_func_extended;
+
// finally bind
- FRAGMENTSHADER* ps = PixelShaderCache::SetShader(DSTALPHA_NONE,g_nativeVertexFmt->m_components);
+ FRAGMENTSHADER* ps;
+ if (dualSourcePossible)
+ {
+ if (useDstAlpha)
+ {
+ // If host supports GL_ARB_blend_func_extended, we can do dst alpha in
+ // the same pass as regular rendering.
+ Renderer::SetBlendMode(true);
+ ps = PixelShaderCache::SetShader(DSTALPHA_DUAL_SOURCE_BLEND, g_nativeVertexFmt->m_components);
+ }
+ else
+ {
+ Renderer::SetBlendMode(true);
+ ps = PixelShaderCache::SetShader(DSTALPHA_NONE,g_nativeVertexFmt->m_components);
+ }
+ }
+ else
+ {
+ ps = PixelShaderCache::SetShader(DSTALPHA_NONE,g_nativeVertexFmt->m_components);
+ }
VERTEXSHADER* vs = VertexShaderCache::SetShader(g_nativeVertexFmt->m_components);
if (ps) PixelShaderCache::SetCurrentShader(ps->glprogid); // Lego Star Wars crashes here.
if (vs) VertexShaderCache::SetCurrentShader(vs->glprogid);
@@ -193,10 +216,8 @@ void VertexManager::vFlush()
Draw();
// run through vertex groups again to set alpha
- if (!g_ActiveConfig.bDstAlphaPass && bpmem.dstalpha.enable && bpmem.blendmode.alphaupdate)
+ if (useDstAlpha && !dualSourcePossible)
{
- // TODO: If host supports GL_ARB_blend_func_extended, use
- // DSTALPHA_DUAL_SOURCE_BLEND and set blend modes accordingly.
ps = PixelShaderCache::SetShader(DSTALPHA_ALPHA_PASS,g_nativeVertexFmt->m_components);
if (ps) PixelShaderCache::SetCurrentShader(ps->glprogid);