diff --git a/plugins/GSdx/GS.cpp b/plugins/GSdx/GS.cpp index 972fe0c5a0..cecc1019e7 100644 --- a/plugins/GSdx/GS.cpp +++ b/plugins/GSdx/GS.cpp @@ -126,9 +126,11 @@ static INT32 GSopen(void* dsp, char* title, int mt, int renderer) case 3: s_gs = new GSRendererHW10(s_basemem, !!mt, s_irq); break; case 4: s_gs = new GSRendererSW(s_basemem, !!mt, s_irq, new GSDevice10()); break; case 5: s_gs = new GSRendererNull(s_basemem, !!mt, s_irq, new GSDevice10()); break; + #if 0 case 6: s_gs = new GSRendererOGL(s_basemem, !!mt, s_irq); break; case 7: s_gs = new GSRendererSW(s_basemem, !!mt, s_irq, new GSDeviceOGL()); break; case 8: s_gs = new GSRendererNull(s_basemem, !!mt, s_irq, new GSDeviceOGL()); break; + #endif case 9: s_gs = new GSRendererSW(s_basemem, !!mt, s_irq, new GSDeviceNull()); break; case 10: s_gs = new GSRendererNull(s_basemem, !!mt, s_irq, new GSDeviceNull()); break; } diff --git a/plugins/GSdx/GSDevice10.cpp b/plugins/GSdx/GSDevice10.cpp index 2a59eaa644..084b8d191a 100644 --- a/plugins/GSdx/GSDevice10.cpp +++ b/plugins/GSdx/GSDevice10.cpp @@ -221,7 +221,7 @@ bool GSDevice10::Create(GSWnd* wnd, bool vsync) // - Reset(1, 1, true); + Reset(1, 1, false); // diff --git a/plugins/GSdx/GSDevice10.h b/plugins/GSdx/GSDevice10.h index d12bdd9bad..5739532105 100644 --- a/plugins/GSdx/GSDevice10.h +++ b/plugins/GSdx/GSDevice10.h @@ -26,7 +26,6 @@ class GSDevice10 : public GSDevice { -private: ID3D10Buffer* m_vb; size_t m_vb_stride; ID3D10InputLayout* m_layout; diff --git a/plugins/GSdx/GSDevice7.cpp b/plugins/GSdx/GSDevice7.cpp index 6995fedd5a..2481fe5c0f 100644 --- a/plugins/GSdx/GSDevice7.cpp +++ b/plugins/GSdx/GSDevice7.cpp @@ -75,7 +75,7 @@ bool GSDevice7::Create(GSWnd* wnd, bool vsync) return false; } - Reset(1, 1, true); + Reset(1, 1, false); return true; } diff --git a/plugins/GSdx/GSDeviceNull.cpp b/plugins/GSdx/GSDeviceNull.cpp index 75112a544f..a2bca4dd4f 100644 --- a/plugins/GSdx/GSDeviceNull.cpp +++ b/plugins/GSdx/GSDeviceNull.cpp @@ -29,7 +29,7 @@ bool GSDeviceNull::Create(GSWnd* wnd, bool vsync) return false; } - Reset(1, 1, true); + Reset(1, 1, false); return true; } diff --git a/plugins/GSdx/GSDeviceOGL.cpp b/plugins/GSdx/GSDeviceOGL.cpp index 55ffa50648..c503b7c084 100644 --- a/plugins/GSdx/GSDeviceOGL.cpp +++ b/plugins/GSdx/GSDeviceOGL.cpp @@ -27,11 +27,21 @@ GSDeviceOGL::GSDeviceOGL() : m_hDC(NULL) , m_hGLRC(NULL) + , m_vbo(0) + , m_fbo(0) + , m_topology(-1) { + m_vertices.stride = 0; + m_vertices.start = 0; + m_vertices.count = 0; + m_vertices.limit = 0; } GSDeviceOGL::~GSDeviceOGL() { + if(m_vbo) glDeleteBuffers(1, &m_vbo); + if(m_fbo) glDeleteFramebuffers(1, &m_fbo); + #ifdef _WINDOWS if(m_hGLRC) {wglMakeCurrent(NULL, NULL); wglDeleteContext(m_hGLRC);} @@ -75,24 +85,40 @@ bool GSDeviceOGL::Create(GSWnd* wnd, bool vsync) if(!m_hDC) return false; if(!SetPixelFormat(m_hDC, ChoosePixelFormat(m_hDC, &pfd), &pfd)) + { return false; + } m_hGLRC = wglCreateContext(m_hDC); if(!m_hGLRC) return false; if(!wglMakeCurrent(m_hDC, m_hGLRC)) + { return false; + } + + if(WGLEW_EXT_swap_control) + { + wglSwapIntervalEXT(vsync ? 1 : 0); + } #endif + if(glewInit() != GLEW_OK) + { + return false; + } + // const char* exts = (const char*)glGetString(GL_EXTENSIONS); - // TODO + glGenBuffers(1, &m_vbo); + glBindBuffer(GL_ARRAY_BUFFER, m_vbo); + // TODO: setup layout? - Reset(1, 1, true); + GSVector4i r = wnd->GetClientRect(); - // + Reset(r.width(), r.height(), false); return true; } @@ -102,12 +128,12 @@ bool GSDeviceOGL::Reset(int w, int h, bool fs) if(!__super::Reset(w, h, fs)) return false; - m_backbuffer = new GSTextureOGL(0); // ??? + m_backbuffer = new GSTextureOGL(0, GSTexture::RenderTarget, w, h); glCullFace(GL_FRONT_AND_BACK); glDisable(GL_LIGHTING); glDisable(GL_ALPHA_TEST); - glDisable(GL_SCISSOR_TEST); + glEnable(GL_SCISSOR_TEST); glMatrixMode(GL_PROJECTION); glLoadIdentity(); @@ -116,76 +142,134 @@ bool GSDeviceOGL::Reset(int w, int h, bool fs) glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST); - // glViewport(0, 0, ?, ?); + // glViewport(0, 0, w, h); + + if(m_fbo) {glDeleteFramebuffersEXT(1, &m_fbo); m_fbo = 0;} + + glGenFramebuffers(1, &m_fbo); + + if(m_fbo == 0) return false; + + glBindFramebuffer(GL_FRAMEBUFFER, m_fbo); return true; } void GSDeviceOGL::Flip() { - // TODO + #ifdef _WINDOWS + + SwapBuffers(m_hDC); + + #endif } void GSDeviceOGL::BeginScene() { - // TODO } void GSDeviceOGL::DrawPrimitive() { - // TODO + glDrawArrays(m_topology, m_vertices.count, m_vertices.start); } void GSDeviceOGL::EndScene() { - // TODO + m_vertices.start += m_vertices.count; + m_vertices.count = 0; } void GSDeviceOGL::ClearRenderTarget(GSTexture* t, const GSVector4& c) { - // TODO + // TODO: disable scissor, color mask + + glClearColor(c.r, c.g, c.b, c.a); + glClear(GL_COLOR_BUFFER_BIT); } void GSDeviceOGL::ClearRenderTarget(GSTexture* t, uint32 c) { - // TODO + ClearRenderTarget(t, GSVector4(c) * (1.0f / 255)); } void GSDeviceOGL::ClearDepth(GSTexture* t, float c) { - // TODO + // TODO: disable scissor, depth mask + + glClearDepth(c); + glClear(GL_DEPTH_BUFFER_BIT); } void GSDeviceOGL::ClearStencil(GSTexture* t, uint8 c) { - // TODO + // TODO: disable scissor, depth (?) mask + + glClearStencil((GLint)c); + glClear(GL_STENCIL_BUFFER_BIT); } GSTexture* GSDeviceOGL::Create(int type, int w, int h, int format) { - // TODO + GLuint texture = 0; - return NULL; + switch(type) + { + case GSTexture::RenderTarget: + glGenTextures(1, &texture); + glBindTexture(GL_TEXTURE_2D, texture); + glTexImage2D(GL_TEXTURE_2D, 0, format, w, h, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL); + break; + case GSTexture::DepthStencil: + glGenRenderbuffersEXT(1, &texture); + glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, texture); + glRenderbufferStorageEXT(GL_RENDERBUFFER_EXT, GL_DEPTH32F_STENCIL8, w, h); + // TODO: depth textures? + break; + case GSTexture::Texture: + glGenTextures(1, &texture); + glBindTexture(GL_TEXTURE_2D, texture); + glTexImage2D(GL_TEXTURE_2D, 0, format, w, h, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL); + break; + case GSTexture::Offscreen: + // TODO: ??? + break; + } + + if(!texture) return false; + + GSTextureOGL* t = new GSTextureOGL(texture, type, w, h, format); + + switch(type) + { + case GSTexture::RenderTarget: + ClearRenderTarget(t, 0); + break; + case GSTexture::DepthStencil: + ClearDepth(t, 0); + break; + } + + return t; } GSTexture* GSDeviceOGL::CreateRenderTarget(int w, int h, int format) { - return __super::CreateRenderTarget(w, h, format ? format : 0); // TODO + return __super::CreateRenderTarget(w, h, format ? format : GL_RGBA8); } GSTexture* GSDeviceOGL::CreateDepthStencil(int w, int h, int format) { - return __super::CreateDepthStencil(w, h, format ? format : 0); // TODO + return __super::CreateDepthStencil(w, h, format ? format : GL_DEPTH32F_STENCIL8); // TODO: GL_DEPTH24_STENCIL8_EXT, GL_DEPTH24_STENCIL8 } GSTexture* GSDeviceOGL::CreateTexture(int w, int h, int format) { - return __super::CreateTexture(w, h, format ? format : 0); // TODO + return __super::CreateTexture(w, h, format ? format : GL_RGBA8); } GSTexture* GSDeviceOGL::CreateOffscreen(int w, int h, int format) { - return __super::CreateOffscreen(w, h, format ? format : 0); // TODO + return __super::CreateOffscreen(w, h, format ? format : GL_RGBA8); } GSTexture* GSDeviceOGL::CopyOffscreen(GSTexture* src, const GSVector4& sr, int w, int h, int format) @@ -209,3 +293,50 @@ void GSDeviceOGL::DoInterlace(GSTexture* st, GSTexture* dt, int shader, bool lin { // TODO } + +void GSDeviceOGL::IASetVertexBuffer(const void* vertices, size_t stride, size_t count) +{ + ASSERT(m_vertices.count == 0); + + glBindBuffer(GL_ARRAY_BUFFER, m_vbo); + + if(count * stride > m_vertices.limit * m_vertices.stride) + { + m_vertices.start = 0; + m_vertices.count = 0; + m_vertices.limit = 0; + } + + if(m_vertices.limit == 0) + { + m_vertices.limit = max(count * 3 / 2, 10000); + + glBufferData(GL_ARRAY_BUFFER, m_vertices.limit * stride, NULL, GL_DYNAMIC_DRAW); // GL_STREAM_DRAW? + } + + if(m_vertices.start + count > m_vertices.limit || stride != m_vertices.stride) + { + m_vertices.start = 0; // TODO: how to discard and not overwrite previous data? + } + + if(GLvoid* v = glMapBuffer(GL_ARRAY_BUFFER, GL_WRITE_ONLY)) + { + GSVector4i::storent((uint8*)v + m_vertices.start * stride, vertices, count * stride); + + glUnmapBuffer(GL_ARRAY_BUFFER); + } + + m_vertices.count = count; + m_vertices.stride = stride; +} + +void GSDeviceOGL::IASetInputLayout() +{ + // TODO +} + +void GSDeviceOGL::IASetPrimitiveTopology(int topology) +{ + m_topology = topology; +} + diff --git a/plugins/GSdx/GSDeviceOGL.h b/plugins/GSdx/GSDeviceOGL.h index 0b7ab393f4..32c510b2d1 100644 --- a/plugins/GSdx/GSDeviceOGL.h +++ b/plugins/GSdx/GSDeviceOGL.h @@ -33,9 +33,23 @@ class GSDeviceOGL : public GSDevice #endif + GLuint m_vbo; + GLuint m_fbo; + + struct + { + size_t stride, start, count, limit; + } m_vertices; + + int m_topology; + + // + static void OnStaticCgError(CGcontext ctx, CGerror err, void* p) {((GSDeviceOGL*)p)->OnCgError(ctx, err);} void OnCgError(CGcontext ctx, CGerror err); + // + GSTexture* Create(int type, int w, int h, int format); void DoMerge(GSTexture* st[2], GSVector4* sr, GSVector4* dr, GSTexture* dt, bool slbg, bool mmod, const GSVector4& c); @@ -67,4 +81,8 @@ public: GSTexture* CopyOffscreen(GSTexture* src, const GSVector4& sr, int w, int h, int format = 0); void StretchRect(GSTexture* st, const GSVector4& sr, GSTexture* dt, const GSVector4& dr, int shader = 0, bool linear = true); + + void IASetVertexBuffer(const void* vertices, size_t stride, size_t count); + void IASetInputLayout(); // TODO + void IASetPrimitiveTopology(int topology); }; diff --git a/plugins/GSdx/GSRendererHW10.cpp b/plugins/GSdx/GSRendererHW10.cpp index 09bec8dbe1..c8d4dfaa67 100644 --- a/plugins/GSdx/GSRendererHW10.cpp +++ b/plugins/GSdx/GSRendererHW10.cpp @@ -336,16 +336,15 @@ void GSRendererHW10::Draw(int prim, GSTexture* rt, GSTexture* ds, GSTextureCache GSTextureFX10::PSConstantBuffer ps_cb; - ps_cb.FogColorAREF = GSVector4((int)env.FOGCOL.FCR, (int)env.FOGCOL.FCG, (int)env.FOGCOL.FCB, (int)context->TEST.AREF) / 255; - ps_cb.TA = GSVector4((int)env.TEXA.TA0, (int)env.TEXA.TA1) / 255; + ps_cb.FogColor_AREF = GSVector4((int)env.FOGCOL.FCR, (int)env.FOGCOL.FCG, (int)env.FOGCOL.FCB, (int)context->TEST.AREF) / 255; if(context->TEST.ATST == 2 || context->TEST.ATST == 5) { - ps_cb.FogColorAREF.a -= 0.9f / 255; + ps_cb.FogColor_AREF.a -= 0.9f / 255; } else if(context->TEST.ATST == 3 || context->TEST.ATST == 6) { - ps_cb.FogColorAREF.a += 0.9f / 255; + ps_cb.FogColor_AREF.a += 0.9f / 255; } if(tex) @@ -355,28 +354,27 @@ void GSRendererHW10::Draw(int prim, GSTexture* rt, GSTexture* ds, GSTextureCache int w = tex->m_texture->GetWidth(); int h = tex->m_texture->GetHeight(); + ps_cb.WH_TA = GSVector4((int)(1 << context->TEX0.TW), (int)(1 << context->TEX0.TH), env.TEXA.TA0, env.TEXA.TA1) / GSVector4(1, 255).xxyy(); + ps_cb.HalfTexel = GSVector4(-0.5f, 0.5f).xxyy() / GSVector4(w, h).xyxy(); + switch(context->CLAMP.WMS) { case 0: - ps_cb.MinMax.x = w - 1; - ps_cb.MinMax.z = 0; ps_ssel.tau = 1; break; case 1: - ps_cb.MinMax.x = 0; - ps_cb.MinMax.z = w - 1; ps_ssel.tau = 0; break; case 2: - ps_cb.MinMax.x = (int)context->CLAMP.MINU * w / (1 << context->TEX0.TW); - ps_cb.MinMax.z = (int)context->CLAMP.MAXU * w / (1 << context->TEX0.TW); + ps_cb.MinMax.x = ((float)(int)context->CLAMP.MINU) / (1 << context->TEX0.TW); + ps_cb.MinMax.z = ((float)(int)context->CLAMP.MAXU) / (1 << context->TEX0.TW); ps_cb.MinMaxF.x = ((float)(int)context->CLAMP.MINU + 0.5f) / (1 << context->TEX0.TW); ps_cb.MinMaxF.z = ((float)(int)context->CLAMP.MAXU) / (1 << context->TEX0.TW); ps_ssel.tau = 0; break; case 3: - ps_cb.MinMax.x = context->CLAMP.MINU; - ps_cb.MinMax.z = context->CLAMP.MAXU; + ps_cb.MskFix.x = context->CLAMP.MINU; + ps_cb.MskFix.z = context->CLAMP.MAXU; ps_ssel.tau = 1; break; default: @@ -386,25 +384,21 @@ void GSRendererHW10::Draw(int prim, GSTexture* rt, GSTexture* ds, GSTextureCache switch(context->CLAMP.WMT) { case 0: - ps_cb.MinMax.y = h - 1; - ps_cb.MinMax.w = 0; ps_ssel.tav = 1; break; case 1: - ps_cb.MinMax.y = 0; - ps_cb.MinMax.w = h - 1; ps_ssel.tav = 0; break; case 2: - ps_cb.MinMax.y = (int)context->CLAMP.MINV * h / (1 << context->TEX0.TH); - ps_cb.MinMax.w = (int)context->CLAMP.MAXV * h / (1 << context->TEX0.TH); + ps_cb.MinMax.y = ((float)(int)context->CLAMP.MINV) / (1 << context->TEX0.TH); + ps_cb.MinMax.w = ((float)(int)context->CLAMP.MAXV) / (1 << context->TEX0.TH); ps_cb.MinMaxF.y = ((float)(int)context->CLAMP.MINV + 0.5f) / (1 << context->TEX0.TH); ps_cb.MinMaxF.w = ((float)(int)context->CLAMP.MAXV) / (1 << context->TEX0.TH); ps_ssel.tav = 0; break; case 3: - ps_cb.MinMax.y = context->CLAMP.MINV; - ps_cb.MinMax.w = context->CLAMP.MAXV; + ps_cb.MskFix.y = context->CLAMP.MINV; + ps_cb.MskFix.w = context->CLAMP.MAXV; ps_ssel.tav = 1; break; default: diff --git a/plugins/GSdx/GSRendererHW9.cpp b/plugins/GSdx/GSRendererHW9.cpp index f88143c334..5a37df2530 100644 --- a/plugins/GSdx/GSRendererHW9.cpp +++ b/plugins/GSdx/GSRendererHW9.cpp @@ -308,17 +308,15 @@ void GSRendererHW9::Draw(int prim, GSTexture* rt, GSTexture* ds, GSTextureCache: GSTextureFX9::PSConstantBuffer ps_cb; - ps_cb.FogColorAREF = GSVector4((int)env.FOGCOL.FCR, (int)env.FOGCOL.FCG, (int)env.FOGCOL.FCB, (int)context->TEST.AREF) / 255; - ps_cb.TA0 = (float)(int)env.TEXA.TA0 / 255; - ps_cb.TA1 = (float)(int)env.TEXA.TA1 / 255; + ps_cb.FogColor_AREF = GSVector4((int)env.FOGCOL.FCR, (int)env.FOGCOL.FCG, (int)env.FOGCOL.FCB, (int)context->TEST.AREF) / 255; if(context->TEST.ATST == 2 || context->TEST.ATST == 5) { - ps_cb.FogColorAREF.a -= 0.9f / 255; + ps_cb.FogColor_AREF.a -= 0.9f / 255; } else if(context->TEST.ATST == 3 || context->TEST.ATST == 6) { - ps_cb.FogColorAREF.a += 0.9f / 255; + ps_cb.FogColor_AREF.a += 0.9f / 255; } if(tex) @@ -328,8 +326,8 @@ void GSRendererHW9::Draw(int prim, GSTexture* rt, GSTexture* ds, GSTextureCache: int w = tex->m_texture->GetWidth(); int h = tex->m_texture->GetHeight(); - ps_cb.WH = GSVector2(w, h); - ps_cb.HalfTexel = GSVector4(-0.5f / w, -0.5f / h, +0.5f / w, +0.5f / h); + ps_cb.WH_TA = GSVector4(w, h, env.TEXA.TA0, env.TEXA.TA1) / GSVector4(1, 255).xxyy(); + ps_cb.HalfTexel = GSVector4(-0.5f, 0.5f).xxyy() / GSVector4(w, h).xyxy(); switch(context->CLAMP.WMS) { diff --git a/plugins/GSdx/GSSettingsDlg.cpp b/plugins/GSdx/GSSettingsDlg.cpp index abd06df0d3..3c84591fc9 100644 --- a/plugins/GSdx/GSSettingsDlg.cpp +++ b/plugins/GSdx/GSSettingsDlg.cpp @@ -33,9 +33,11 @@ GSSetting GSSettingsDlg::g_renderers[] = {3, "Direct3D10 (Hardware)", NULL}, {4, "Direct3D10 (Software)", NULL}, {5, "Direct3D10 (Null)", NULL}, + #if 0 {6, "OpenGL (Hardware)", NULL}, {7, "OpenGL (Software)", NULL}, {8, "OpenGL (Null)", NULL}, + #endif {9, "Null (Software)", NULL}, {10, "Null (Null)", NULL}, }; diff --git a/plugins/GSdx/GSTextureFX10.h b/plugins/GSdx/GSTextureFX10.h index 3775879d5f..f50617052b 100644 --- a/plugins/GSdx/GSTextureFX10.h +++ b/plugins/GSdx/GSTextureFX10.h @@ -77,10 +77,12 @@ public: __declspec(align(16)) struct PSConstantBuffer { - GSVector4 FogColorAREF; - GSVector4 TA; - GSVector4i MinMax; + GSVector4 FogColor_AREF; + GSVector4 HalfTexel; + GSVector4 WH_TA; + GSVector4 MinMax; GSVector4 MinMaxF; + GSVector4i MskFix; struct PSConstantBuffer() {memset(this, 0, sizeof(*this));} @@ -93,13 +95,17 @@ public: GSVector4i b1 = b[1]; GSVector4i b2 = b[2]; GSVector4i b3 = b[3]; + GSVector4i b4 = b[4]; + GSVector4i b5 = b[5]; - if(!((a[0] == b0) & (a[1] == b1) & (a[2] == b2) & (a[3] == b3)).alltrue()) + if(!((a[0] == b0) & (a[1] == b1) & (a[2] == b2) & (a[3] == b3) & (a[4] == b4) & (a[5] == b5)).alltrue()) { a[0] = b0; a[1] = b1; a[2] = b2; a[3] = b3; + a[4] = b4; + a[5] = b5; return true; } diff --git a/plugins/GSdx/GSTextureFX9.h b/plugins/GSdx/GSTextureFX9.h index c657a2b06d..b47c227a7b 100644 --- a/plugins/GSdx/GSTextureFX9.h +++ b/plugins/GSdx/GSTextureFX9.h @@ -53,11 +53,9 @@ public: struct PSConstantBuffer { - GSVector4 FogColorAREF; + GSVector4 FogColor_AREF; GSVector4 HalfTexel; - GSVector2 WH; - float TA0; - float TA1; + GSVector4 WH_TA; GSVector4 MinMax; GSVector4 MinMaxF; GSVector4i MskFix; diff --git a/plugins/GSdx/GSTextureOGL.cpp b/plugins/GSdx/GSTextureOGL.cpp index 35749fb43d..3e8f1f97eb 100644 --- a/plugins/GSdx/GSTextureOGL.cpp +++ b/plugins/GSdx/GSTextureOGL.cpp @@ -22,19 +22,29 @@ #include "stdafx.h" #include "GSTextureOGL.h" -GSTextureOGL::GSTextureOGL(GLuint texture) +GSTextureOGL::GSTextureOGL(GLuint texture, int type, int width, int height, int format) : m_texture(texture) - , m_type(None) - , m_width(0) - , m_height(0) - , m_format(0) + , m_type(type) + , m_width(width) + , m_height(height) + , m_format(format) { - // TODO: m_type, m_format, fb/ds? +} - glBindTexture(GL_TEXTURE_2D, texture); - - glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH, &m_width); - glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_HEIGHT, &m_height); +GSTextureOGL::~GSTextureOGL() +{ + if(m_texture) + { + switch(m_type) + { + case DepthStencil: + glDeleteRenderbuffersEXT(1, &m_texture); + break; + default: + glDeleteTextures(1, &m_texture); + break; + } + } } int GSTextureOGL::GetType() const @@ -59,7 +69,7 @@ int GSTextureOGL::GetFormat() const bool GSTextureOGL::Update(const GSVector4i& r, const void* data, int pitch) { - // TODO + // TODO: glTexSubImage2D looks like UpdateSubresource but does not take a pitch return false; } diff --git a/plugins/GSdx/GSTextureOGL.h b/plugins/GSdx/GSTextureOGL.h index 402aef62c6..5e6e2a7926 100644 --- a/plugins/GSdx/GSTextureOGL.h +++ b/plugins/GSdx/GSTextureOGL.h @@ -33,7 +33,8 @@ class GSTextureOGL : public GSTexture int m_format; public: - explicit GSTextureOGL(GLuint texture); + GSTextureOGL(GLuint texture, int type, int width, int height, int format = 0); + virtual ~GSTextureOGL(); int GetType() const; int GetWidth() const; diff --git a/plugins/GSdx/res/tfx10.fx b/plugins/GSdx/res/tfx10.fx index 97f1893032..a2b067a93b 100644 --- a/plugins/GSdx/res/tfx10.fx +++ b/plugins/GSdx/res/tfx10.fx @@ -155,9 +155,12 @@ cbuffer cb1 { float3 FogColor; float AREF; - float4 TA; - uint4 MinMax; + float4 HalfTexel; + float2 WH; + float2 TA; + float4 MinMax; float4 MinMaxF; + uint4 MskFix; }; struct PS_INPUT @@ -175,15 +178,15 @@ struct PS_OUTPUT #ifndef FST #define FST 0 -#define WMS 1 -#define WMT 1 +#define WMS 3 +#define WMT 3 #define BPP 0 #define AEM 0 #define TFX 0 #define TCC 1 -#define ATE 1 +#define ATE 0 #define ATST 4 -#define FOG 1 +#define FOG 0 #define CLR1 0 #define FBA 0 #define AOUT 0 @@ -207,58 +210,83 @@ float4 Extract16(uint i) return f; } -int4 wrapuv(int4 uv) +float4 wrapuv(float4 uv) { - // TODO: bitwise ops don't work with render target textures that were not rendered at the native resolution. - if(WMS == WMT) { - switch(WMS) + if(WMS == 0) { - case 0: uv &= MinMax.xyxy; break; - case 1: uv = clamp(uv, 0, MinMax.zwzw); break; - case 2: uv = clamp(uv, MinMax.xyxy, MinMax.zwzw); break; - case 3: uv = (uv & MinMax.xyxy) | MinMax.zwzw; break; + uv = frac(uv); + } + else if(WMS == 1) + { + uv = saturate(uv); + } + else if(WMS == 2) + { + uv = clamp(uv, MinMax.xyxy, MinMax.zwzw); + } + else if(WMS == 3) + { + uv = (float4)(((int4)(uv * WH.xyxy) & MskFix.xyxy) | MskFix.zwzw) / WH.xyxy; } } else { - switch(WMS) + if(WMS == 0) { - case 0: uv.xz &= MinMax.xx; break; - case 1: uv.xz = clamp(uv.xz, 0, MinMax.zz); break; - case 2: uv.xz = clamp(uv.xz, MinMax.xx, MinMax.zz); break; - case 3: uv.xz = (uv.xz & MinMax.xx) | MinMax.zz; break; + uv.xz = frac(uv.xz); } - - switch(WMT) + else if(WMS == 1) { - case 0: uv.yw &= MinMax.yy; break; - case 1: uv.yw = clamp(uv.yw, 0, MinMax.ww); break; - case 2: uv.yw = clamp(uv.yw, MinMax.yy, MinMax.ww); break; - case 3: uv.yw = (uv.yw & MinMax.yy) | MinMax.ww; break; + uv.xz = saturate(uv.xz); + } + else if(WMS == 2) + { + uv.xz = clamp(uv.xz, MinMax.xx, MinMax.zz); + } + else if(WMS == 3) + { + uv.xz = (float2)(((int2)(uv * WH.xyxy).xz & MskFix.xx) | MskFix.zz) / WH; + } + + if(WMT == 0) + { + uv.yw = frac(uv.yw); + } + else if(WMT == 1) + { + uv.yw = saturate(uv.yw); + } + else if(WMT == 2) + { + uv.yw = clamp(uv.yw, MinMax.yy, MinMax.ww); + } + else if(WMT == 3) + { + uv.yw = (float2)(((int2)(uv * WH.xyxy).yw & MskFix.yy) | MskFix.ww) / WH; } } return uv; } -float2 clampuv(float2 tc) +float2 clampuv(float2 uv) { if(WMS == 2 && WMT == 2) { - tc = clamp(tc, MinMaxF.xy, MinMaxF.zw); + uv = clamp(uv, MinMaxF.xy, MinMaxF.zw); } else if(WMS == 2) { - tc.x = clamp(tc.x, MinMaxF.x, MinMaxF.z); + uv.x = clamp(uv.x, MinMaxF.x, MinMaxF.z); } else if(WMT == 2) { - tc.y = clamp(tc.y, MinMaxF.y, MinMaxF.w); + uv.y = clamp(uv.y, MinMaxF.y, MinMaxF.w); } - return tc; + return uv; } float4 sample(float2 tc, float w) @@ -282,12 +310,11 @@ float4 sample(float2 tc, float w) else { float w, h; - Texture.GetDimensions(w, h); - float4 tc2 = (tc * float2(w, h)).xyxy + float4(-0.499, -0.499, 0.501, 0.501); - float2 dd = frac(tc2.xy); - int4 uv = wrapuv((int4)tc2); + float4 uv2 = tc.xyxy + HalfTexel; + float2 dd = frac(uv2.xy * float2(w, h)); + float4 uv = wrapuv(uv2); float4 t00, t01, t10, t11; @@ -295,15 +322,15 @@ float4 sample(float2 tc, float w) { float4 a; - a.x = Texture.Load(int3(uv.xy, 0)).a; - a.y = Texture.Load(int3(uv.zy, 0)).a; - a.z = Texture.Load(int3(uv.xw, 0)).a; - a.w = Texture.Load(int3(uv.zw, 0)).a; + a.x = Texture.Sample(TextureSampler, uv.xy).a; + a.y = Texture.Sample(TextureSampler, uv.zy).a; + a.z = Texture.Sample(TextureSampler, uv.xw).a; + a.w = Texture.Sample(TextureSampler, uv.zw).a; - t00 = Palette.Load(a.x); - t01 = Palette.Load(a.y); - t10 = Palette.Load(a.z); - t11 = Palette.Load(a.w); + t00 = Palette.Sample(PaletteSampler, a.x); + t01 = Palette.Sample(PaletteSampler, a.y); + t10 = Palette.Sample(PaletteSampler, a.z); + t11 = Palette.Sample(PaletteSampler, a.w); } else if(BPP == 4) // 8HP + 16-bit palette { @@ -313,10 +340,10 @@ float4 sample(float2 tc, float w) { float4 r; - r.x = Texture.Load(int3(uv.xy, 0)).r; - r.y = Texture.Load(int3(uv.zy, 0)).r; - r.z = Texture.Load(int3(uv.xw, 0)).r; - r.w = Texture.Load(int3(uv.zw, 0)).r; + r.x = Texture.Sample(TextureSampler, uv.xy).r; + r.y = Texture.Sample(TextureSampler, uv.zy).r; + r.z = Texture.Sample(TextureSampler, uv.xw).r; + r.w = Texture.Sample(TextureSampler, uv.zw).r; uint4 i = r * 65535; @@ -327,10 +354,10 @@ float4 sample(float2 tc, float w) } else { - t00 = Texture.Load(int3(uv.xy, 0)); - t01 = Texture.Load(int3(uv.zy, 0)); - t10 = Texture.Load(int3(uv.xw, 0)); - t11 = Texture.Load(int3(uv.zw, 0)); + t00 = Texture.Sample(TextureSampler, uv.xy); + t01 = Texture.Sample(TextureSampler, uv.zy); + t10 = Texture.Sample(TextureSampler, uv.xw); + t11 = Texture.Sample(TextureSampler, uv.zw); } if(LTF) diff --git a/plugins/GSdx/res/tfx9.fx b/plugins/GSdx/res/tfx9.fx index 9c1011f735..1cbc591387 100644 --- a/plugins/GSdx/res/tfx9.fx +++ b/plugins/GSdx/res/tfx9.fx @@ -96,12 +96,12 @@ struct PS_INPUT #define AEM 0 #define TFX 0 #define TCC 1 -#define ATE 1 +#define ATE 0 #define ATST 4 -#define FOG 1 +#define FOG 0 #define CLR1 0 #define RT 0 -#define LTF 1 +#define LTF 0 #endif sampler Texture : register(s0); @@ -113,63 +113,84 @@ float4 wrapuv(float4 uv) { if(WMS == WMT) { - switch(WMS) + if(WMS == 0) + { + uv = frac(uv); + } + else if(WMS == 1) + { + uv = saturate(uv); + } + else if(WMS == 2) + { + uv = clamp(uv, MinMax.xyxy, MinMax.zwzw); + } + else if(WMS == 3) { - case 0: uv = frac(uv); break; - case 1: uv = saturate(uv); break; - case 2: uv = clamp(uv, MinMax.xyxy, MinMax.zwzw); break; - case 3: uv.x = tex1D(UMSKFIX, uv.x); uv.y = tex1D(VMSKFIX, uv.y); uv.z = tex1D(UMSKFIX, uv.z); uv.w = tex1D(VMSKFIX, uv.w); - break; } } else { - switch(WMS) + if(WMS == 0) + { + uv.xz = frac(uv.xz); + } + else if(WMS == 1) + { + uv.xz = saturate(uv.xz); + } + else if(WMS == 2) + { + uv.xz = clamp(uv.xz, MinMax.xx, MinMax.zz); + } + else if(WMS == 3) { - case 0: uv.xz = frac(uv.xz); break; - case 1: uv.xz = saturate(uv.xz); break; - case 2: uv.xz = clamp(uv.xz, MinMax.xx, MinMax.zz); break; - case 3: uv.x = tex1D(UMSKFIX, uv.x); uv.z = tex1D(UMSKFIX, uv.z); - break; } - switch(WMT) + if(WMT == 0) + { + uv.yw = frac(uv.yw); + } + else if(WMT == 1) + { + uv.yw = saturate(uv.yw); + } + else if(WMT == 2) + { + uv.yw = clamp(uv.yw, MinMax.yy, MinMax.ww); + } + else if(WMT == 3) { - case 0: uv.yw = frac(uv.yw); break; - case 1: uv.yw = saturate(uv.yw); break; - case 2: uv.yw = clamp(uv.yw, MinMax.yy, MinMax.ww); break; - case 3: uv.y = tex1D(VMSKFIX, uv.y); uv.w = tex1D(VMSKFIX, uv.w); - break; } } return uv; } -float2 clampuv(float2 tc) +float2 clampuv(float2 uv) { if(WMS == 2 && WMT == 2) { - tc = clamp(tc, MinMaxF.xy, MinMaxF.zw); + uv = clamp(uv, MinMaxF.xy, MinMaxF.zw); } else if(WMS == 2) { - tc.x = clamp(tc.x, MinMaxF.x, MinMaxF.z); + uv.x = clamp(uv.x, MinMaxF.x, MinMaxF.z); } else if(WMT == 2) { - tc.y = clamp(tc.y, MinMaxF.y, MinMaxF.w); + uv.y = clamp(uv.y, MinMaxF.y, MinMaxF.w); } - return tc; + return uv; } float4 sample(float2 tc, float w) @@ -192,9 +213,9 @@ float4 sample(float2 tc, float w) } else { - float4 tc2 = tc.xyxy + HalfTexel; - float2 dd = frac(tc2.xy * WH); - float4 uv = wrapuv(tc2); + float4 uv2 = tc.xyxy + HalfTexel; + float2 dd = frac(uv2.xy * WH); + float4 uv = wrapuv(uv2); float4 t00, t01, t10, t11; diff --git a/plugins/GSdx/stdafx.h b/plugins/GSdx/stdafx.h index eef0a46699..ddc67531b0 100644 --- a/plugins/GSdx/stdafx.h +++ b/plugins/GSdx/stdafx.h @@ -115,10 +115,15 @@ typedef signed long long int64; // opengl +#include #include #include #include +#ifdef _WINDOWS +#include +#endif + // sse #if !defined(_M_SSE) && (defined(_M_AMD64) || defined(_M_IX86_FP) && _M_IX86_FP >= 2)