From 88cd9f3df1f1856439c4186e2174a5ba7c5e5982 Mon Sep 17 00:00:00 2001 From: skidau Date: Tue, 28 Sep 2010 02:15:02 +0000 Subject: [PATCH] Minor code formatting: First step to bring a level of consistency between the video plug-ins - variable names, spacing, function names, function order, comments, file names. This will help us identify common code for VideoMerge. git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@6235 8ced0084-cf51-0410-be5f-012b33b47a6e --- .../Plugin_VideoDX11/Plugin_VideoDX11.vcproj | 4 +- .../Plugin_VideoDX11/Src/BPFunctions.cpp | 24 +- .../Plugins/Plugin_VideoDX11/Src/D3DUtil.cpp | 43 +- .../Plugin_VideoDX11/Src/EmuWindow.cpp | 2 +- .../{FBManager.cpp => FramebufferManager.cpp} | 33 +- .../Src/{FBManager.h => FramebufferManager.h} | 6 +- .../Src/NativeVertexFormat.cpp | 11 +- .../Plugin_VideoDX11/Src/PixelShaderCache.cpp | 19 +- .../Plugins/Plugin_VideoDX11/Src/Render.cpp | 180 +-- .../Plugin_VideoDX11/Src/TextureCache.cpp | 102 +- .../Plugin_VideoDX11/Src/VertexManager.cpp | 119 +- .../Src/VertexShaderCache.cpp | 12 +- Source/Plugins/Plugin_VideoDX11/Src/main.cpp | 55 +- .../Plugin_VideoDX9/Src/BPFunctions.cpp | 17 +- .../Plugins/Plugin_VideoDX9/Src/D3DShader.cpp | 44 +- .../Plugins/Plugin_VideoDX9/Src/D3DShader.h | 2 +- .../Plugins/Plugin_VideoDX9/Src/D3DUtil.cpp | 19 +- .../Plugin_VideoDX9/Src/Debugger/Debugger.cpp | 6 +- .../Plugins/Plugin_VideoDX9/Src/EmuWindow.cpp | 9 +- .../Src/FramebufferManager.cpp | 6 +- .../Plugin_VideoDX9/Src/FramebufferManager.h | 3 +- Source/Plugins/Plugin_VideoDX9/Src/Globals.h | 2 +- .../Src/NativeVertexFormat.cpp | 6 +- .../Plugin_VideoDX9/Src/PixelShaderCache.cpp | 29 +- Source/Plugins/Plugin_VideoDX9/Src/Render.cpp | 283 ++-- .../Plugin_VideoDX9/Src/TextureCache.cpp | 113 +- .../Plugin_VideoDX9/Src/TextureConverter.cpp | 85 +- .../Plugin_VideoDX9/Src/VertexManager.cpp | 133 +- .../Plugin_VideoDX9/Src/VertexShaderCache.cpp | 21 +- Source/Plugins/Plugin_VideoDX9/Src/main.cpp | 82 +- Source/Plugins/Plugin_VideoDX9/Src/stdafx.cpp | 2 +- Source/Plugins/Plugin_VideoDX9/Src/stdafx.h | 1 - .../Plugin_VideoOGL/Plugin_VideoOGL.vcproj | 4 +- .../Plugin_VideoOGL/Src/BPFunctions.cpp | 19 +- .../Src/FramebufferManager.cpp | 51 +- .../Plugin_VideoOGL/Src/GUI/ConfigDlg.cpp | 6 +- Source/Plugins/Plugin_VideoOGL/Src/Globals.h | 2 +- .../Plugin_VideoOGL/Src/PixelShaderCache.cpp | 22 +- .../Plugin_VideoOGL/Src/PixelShaderCache.h | 2 +- Source/Plugins/Plugin_VideoOGL/Src/Render.cpp | 1140 +++++++++-------- Source/Plugins/Plugin_VideoOGL/Src/SConscript | 2 +- .../Src/{TextureMngr.cpp => TextureCache.cpp} | 257 ++-- .../Src/{TextureMngr.h => TextureCache.h} | 4 +- .../Plugin_VideoOGL/Src/TextureConverter.cpp | 76 +- .../Plugin_VideoOGL/Src/VertexManager.cpp | 118 +- .../Plugin_VideoOGL/Src/VertexShaderCache.cpp | 14 +- .../Plugin_VideoOGL/Src/VertexShaderCache.h | 2 +- Source/Plugins/Plugin_VideoOGL/Src/main.cpp | 71 +- Source/Plugins/Plugin_VideoOGL/Src/stdafx.cpp | 2 +- Source/Plugins/Plugin_VideoOGL/Src/stdafx.h | 3 +- 50 files changed, 1713 insertions(+), 1555 deletions(-) rename Source/Plugins/Plugin_VideoDX11/Src/{FBManager.cpp => FramebufferManager.cpp} (95%) rename Source/Plugins/Plugin_VideoDX11/Src/{FBManager.h => FramebufferManager.h} (95%) rename Source/Plugins/Plugin_VideoOGL/Src/{TextureMngr.cpp => TextureCache.cpp} (84%) rename Source/Plugins/Plugin_VideoOGL/Src/{TextureMngr.h => TextureCache.h} (98%) diff --git a/Source/Plugins/Plugin_VideoDX11/Plugin_VideoDX11.vcproj b/Source/Plugins/Plugin_VideoDX11/Plugin_VideoDX11.vcproj index 4c488eed50..2f7907e94c 100644 --- a/Source/Plugins/Plugin_VideoDX11/Plugin_VideoDX11.vcproj +++ b/Source/Plugins/Plugin_VideoDX11/Plugin_VideoDX11.vcproj @@ -716,11 +716,11 @@ Name="Render" > Map(buftex, 0, D3D11_MAP_WRITE_DISCARD, 0, &texmap); if (FAILED(hr)) PanicAlert("Failed to map a texture at %s %d\n", __FILE__, __LINE__); @@ -193,7 +194,7 @@ int CD3DFont::Init() } } - // clean up + // Done updating texture, so clean up used objects context->Unmap(buftex, 0); hr = D3D::device->CreateShaderResourceView(buftex, NULL, &m_pTexture); if (FAILED(hr)) PanicAlert("Failed to create shader resource view at %s %d\n", __FILE__, __LINE__); @@ -274,7 +275,8 @@ int CD3DFont::Shutdown() int CD3DFont::DrawTextScaled(float x, float y, float size, float spacing, u32 dwColor, const char* strText, bool center) { - if (!m_pVB) return 0; + if (!m_pVB) + return 0; UINT stride = sizeof(FONT2DVERTEX); UINT bufoffset = 0; @@ -288,7 +290,7 @@ int CD3DFont::DrawTextScaled(float x, float y, float size, float spacing, u32 dw float sy = 1.f - y * scaley; char c; - // fill vertex buffer + // Fill vertex buffer FONT2DVERTEX* pVertices; int dwNumTriangles = 0L; @@ -336,7 +338,8 @@ int CD3DFont::DrawTextScaled(float x, float y, float size, float spacing, u32 dw sx = fStartX; sy -= scaley * size; } - if (c < (' ')) continue; + if (c < (' ')) + continue; c -= 32; float tx1 = m_fTexCoords[c][0]; @@ -348,10 +351,10 @@ int CD3DFont::DrawTextScaled(float x, float y, float size, float spacing, u32 dw float h = (float)(ty1-ty2) * m_dwTexHeight * scaley * sizeratio; FONT2DVERTEX v[6]; - v[0] = InitFont2DVertex( sx, h+sy, dwColor, tx1, ty2); - v[1] = InitFont2DVertex( sx, sy, dwColor, tx1, ty1); - v[2] = InitFont2DVertex(w+sx, h+sy, dwColor, tx2, ty2); - v[3] = InitFont2DVertex(w+sx, sy, dwColor, tx2, ty1); + v[0] = InitFont2DVertex(sx, sy+h, dwColor, tx1, ty2); + v[1] = InitFont2DVertex(sx, sy, dwColor, tx1, ty1); + v[2] = InitFont2DVertex(sx+w, sy+h, dwColor, tx2, ty2); + v[3] = InitFont2DVertex(sx+w, sy, dwColor, tx2, ty1); v[4] = v[2]; v[5] = v[1]; diff --git a/Source/Plugins/Plugin_VideoDX11/Src/EmuWindow.cpp b/Source/Plugins/Plugin_VideoDX11/Src/EmuWindow.cpp index e30e8f1a29..ab8e295f60 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/EmuWindow.cpp +++ b/Source/Plugins/Plugin_VideoDX11/Src/EmuWindow.cpp @@ -164,7 +164,7 @@ void OSDMenu(WPARAM wParam) case '7': OSDChoice = 5; g_Config.bDisableLighting = !g_Config.bDisableLighting; - break; + break; } } diff --git a/Source/Plugins/Plugin_VideoDX11/Src/FBManager.cpp b/Source/Plugins/Plugin_VideoDX11/Src/FramebufferManager.cpp similarity index 95% rename from Source/Plugins/Plugin_VideoDX11/Src/FBManager.cpp rename to Source/Plugins/Plugin_VideoDX11/Src/FramebufferManager.cpp index 9c19546e8d..591fa20844 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/FBManager.cpp +++ b/Source/Plugins/Plugin_VideoDX11/Src/FramebufferManager.cpp @@ -19,12 +19,12 @@ #include "D3DTexture.h" #include "D3DUtil.h" #include "Render.h" -#include "FBManager.h" +#include "FramebufferManager.h" #include "VideoConfig.h" #include "PixelShaderCache.h" #include "VertexShaderCache.h" -FramebufferManager FBManager; +FramebufferManager g_framebufferManager; D3DTexture2D* &FramebufferManager::GetEFBColorTexture() { return m_efb.color_tex; } ID3D11Texture2D* &FramebufferManager::GetEFBColorStagingBuffer() { return m_efb.color_staging_buf; } @@ -120,19 +120,19 @@ FramebufferManager::VirtualXFBListType::iterator FramebufferManager::findVirtual return it; } - // that address is not in the Virtual XFB list. + // That address is not in the Virtual XFB list. return m_virtualXFBList.end(); } void FramebufferManager::replaceVirtualXFB() { - VirtualXFBListType::iterator it = m_virtualXFBList.begin(); + VirtualXFBListType::iterator it = m_virtualXFBList.begin(); s32 srcLower = it->xfbAddr; s32 srcUpper = it->xfbAddr + 2 * it->xfbWidth * it->xfbHeight; s32 lineSize = 2 * it->xfbWidth; - it++; + ++it; while (it != m_virtualXFBList.end()) { @@ -141,13 +141,13 @@ void FramebufferManager::replaceVirtualXFB() if (dstLower >= srcLower && dstUpper <= srcUpper) { - // invalidate the data + // Invalidate the data it->xfbAddr = 0; it->xfbHeight = 0; it->xfbWidth = 0; } else if (addrRangesOverlap(srcLower, srcUpper, dstLower, dstUpper)) - { + { s32 upperOverlap = (srcUpper - dstLower) / lineSize; s32 lowerOverlap = (dstUpper - srcLower) / lineSize; @@ -162,7 +162,7 @@ void FramebufferManager::replaceVirtualXFB() } } - it++; + ++it; } } @@ -195,15 +195,17 @@ void FramebufferManager::copyToVirtualXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight targetSource.right = (int)(sourceRc.right * scaleX); unsigned int target_width = targetSource.right - targetSource.left; unsigned int target_height = targetSource.bottom - targetSource.top; - if (it != m_virtualXFBList.end()) // overwrite an existing Virtual XFB + if (it != m_virtualXFBList.end()) { + // Overwrite an existing Virtual XFB. + it->xfbAddr = xfbAddr; it->xfbWidth = fbWidth; it->xfbHeight = fbHeight; it->xfbSource.srcAddr = xfbAddr; it->xfbSource.srcWidth = fbWidth; - it->xfbSource.srcHeight = fbHeight; + it->xfbSource.srcHeight = fbHeight; if (it->xfbSource.texWidth != target_width || it->xfbSource.texHeight != target_height || !(it->xfbSource.tex)) { @@ -222,8 +224,9 @@ void FramebufferManager::copyToVirtualXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight // keep stale XFB data from being used replaceVirtualXFB(); } - else // create a new Virtual XFB and place it at the front of the list + else { + // Create a new Virtual XFB and place it at the front of the list. VirtualXFB newVirt; newVirt.xfbSource.tex = D3DTexture2D::Create(target_width, target_height, (D3D11_BIND_FLAG)(D3D11_BIND_RENDER_TARGET|D3D11_BIND_SHADER_RESOURCE), D3D11_USAGE_DEFAULT, DXGI_FORMAT_R8G8B8A8_UNORM); @@ -253,7 +256,7 @@ void FramebufferManager::copyToVirtualXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight Renderer::ResetAPIState(); // reset any game specific settings - // copy EFB data to XFB and restore render target again + // Copy EFB data to XFB and restore render target again D3D11_RECT sourcerect = CD3D11_RECT(efbSource.left, efbSource.top, efbSource.right, efbSource.bottom); D3D11_VIEWPORT vp = CD3D11_VIEWPORT(0.f, 0.f, (float)target_width, (float)target_height); D3D::context->RSSetViewports(1, &vp); @@ -277,8 +280,11 @@ const XFBSource** FramebufferManager::getVirtualXFBSource(u32 xfbAddr, u32 fbWid { xfbCount = 0; - if (m_virtualXFBList.size() == 0) // no Virtual XFBs available + if (m_virtualXFBList.size() == 0) + { + // No Virtual XFBs available. return NULL; + } u32 srcLower = xfbAddr; u32 srcUpper = xfbAddr + 2 * fbWidth * fbHeight; @@ -297,5 +303,6 @@ const XFBSource** FramebufferManager::getVirtualXFBSource(u32 xfbAddr, u32 fbWid xfbCount++; } } + return &m_overlappingXFBArray[0]; } diff --git a/Source/Plugins/Plugin_VideoDX11/Src/FBManager.h b/Source/Plugins/Plugin_VideoDX11/Src/FramebufferManager.h similarity index 95% rename from Source/Plugins/Plugin_VideoDX11/Src/FBManager.h rename to Source/Plugins/Plugin_VideoDX11/Src/FramebufferManager.h index b06a0c40d0..ae98765355 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/FBManager.h +++ b/Source/Plugins/Plugin_VideoDX11/Src/FramebufferManager.h @@ -130,8 +130,8 @@ private: const XFBSource** getRealXFBSource(u32 xfbAddr, u32 fbWidth, u32 fbHeight, u32 &xfbCount); const XFBSource** getVirtualXFBSource(u32 xfbAddr, u32 fbWidth, u32 fbHeight, u32 &xfbCount); - XFBSource m_realXFBSource; // used in real XFB mode - VirtualXFBListType m_virtualXFBList; // used in virtual XFB mode + XFBSource m_realXFBSource; // Only used in Real XFB mode + VirtualXFBListType m_virtualXFBList; // Only used in Virtual XFB mode const XFBSource* m_overlappingXFBArray[MAX_VIRTUAL_XFB]; @@ -146,6 +146,6 @@ private: } m_efb; }; -extern FramebufferManager FBManager; +extern FramebufferManager g_framebufferManager; #endif diff --git a/Source/Plugins/Plugin_VideoDX11/Src/NativeVertexFormat.cpp b/Source/Plugins/Plugin_VideoDX11/Src/NativeVertexFormat.cpp index 0ef85c2840..f7f88845ad 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/NativeVertexFormat.cpp +++ b/Source/Plugins/Plugin_VideoDX11/Src/NativeVertexFormat.cpp @@ -23,7 +23,6 @@ #include "ABI.h" #include "MemoryUtil.h" #include "VertexShaderGen.h" -#include "VertexShaderCache.h" #include "CPMemory.h" #include "NativeVertexFormat.h" @@ -66,11 +65,11 @@ DXGI_FORMAT VarToD3D(VarType t, int size) switch (size) { - case 1: retval = lookup1[t]; break; - case 2: retval = lookup2[t]; break; - case 3: retval = lookup3[t]; break; - case 4: retval = lookup4[t]; break; - default: break; + case 1: retval = lookup1[t]; break; + case 2: retval = lookup2[t]; break; + case 3: retval = lookup3[t]; break; + case 4: retval = lookup4[t]; break; + default: break; } if (retval == DXGI_FORMAT_UNKNOWN) { diff --git a/Source/Plugins/Plugin_VideoDX11/Src/PixelShaderCache.cpp b/Source/Plugins/Plugin_VideoDX11/Src/PixelShaderCache.cpp index e482265c44..b63319f847 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/PixelShaderCache.cpp +++ b/Source/Plugins/Plugin_VideoDX11/Src/PixelShaderCache.cpp @@ -199,6 +199,9 @@ void PixelShaderCache::Init() if (!File::Exists(File::GetUserPath(D_SHADERCACHE_IDX))) File::CreateDir(File::GetUserPath(D_SHADERCACHE_IDX)); + SETSTAT(stats.numPixelShadersCreated, 0); + SETSTAT(stats.numPixelShadersAlive, 0); + char cache_filename[MAX_PATH]; sprintf(cache_filename, "%sdx11-%s-ps.cache", File::GetUserPath(D_SHADERCACHE_IDX), globals->unique_id); PixelShaderCacheInserter inserter; @@ -230,7 +233,7 @@ bool PixelShaderCache::SetShader(bool dstAlpha,u32 components) PIXELSHADERUID uid; GetPixelShaderId(&uid, dstAlpha); - // check if the shader is already set + // Check if the shader is already set if (uid == last_pixel_shader_uid && PixelShaders[uid].frameCount == frameCount) { PSCache::const_iterator iter = PixelShaders.find(uid); @@ -239,7 +242,7 @@ bool PixelShaderCache::SetShader(bool dstAlpha,u32 components) memcpy(&last_pixel_shader_uid, &uid, sizeof(PIXELSHADERUID)); - // check if the shader is already in the cache + // Check if the shader is already in the cache PSCache::iterator iter; iter = PixelShaders.find(uid); if (iter != PixelShaders.end()) @@ -252,7 +255,7 @@ bool PixelShaderCache::SetShader(bool dstAlpha,u32 components) return (entry.shader != NULL); } - // need to compile a new shader + // Need to compile a new shader const char* code = GeneratePixelShaderCode(dstAlpha, API_D3D11,components); D3DBlob* pbytecode; @@ -262,7 +265,7 @@ bool PixelShaderCache::SetShader(bool dstAlpha,u32 components) return false; } - // insert the bytecode into the caches + // Insert the bytecode into the caches g_ps_disk_cache.Append((u8*)&uid, sizeof(uid), (const u8*)pbytecode->Data(), pbytecode->Size()); g_ps_disk_cache.Sync(); @@ -283,15 +286,19 @@ bool PixelShaderCache::InsertByteCode(const PIXELSHADERUID &uid, void* bytecode, // TODO: Somehow make the debug name a bit more specific D3D::SetDebugObjectName((ID3D11DeviceChild*)shader, "a pixel shader of PixelShaderCache"); - // make an entry in the table + // Make an entry in the table PSCacheEntry newentry; newentry.shader = shader; newentry.frameCount = frameCount; PixelShaders[uid] = newentry; last_entry = &PixelShaders[uid]; + if (!shader) { + // INCSTAT(stats.numPixelShadersFailed); + return false; + } + INCSTAT(stats.numPixelShadersCreated); SETSTAT(stats.numPixelShadersAlive, PixelShaders.size()); - return true; } \ No newline at end of file diff --git a/Source/Plugins/Plugin_VideoDX11/Src/Render.cpp b/Source/Plugins/Plugin_VideoDX11/Src/Render.cpp index eb3e55acd1..98214cf6f7 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/Render.cpp +++ b/Source/Plugins/Plugin_VideoDX11/Src/Render.cpp @@ -42,7 +42,7 @@ #include "EmuWindow.h" #include "AVIDump.h" #include "OnScreenDisplay.h" -#include "FBManager.h" +#include "FramebufferManager.h" #include "Fifo.h" #include "DLCache.h" @@ -83,7 +83,7 @@ ID3D11RasterizerState* resetraststate = NULL; bool reset_called = false; -// state translation lookup tables +// State translation lookup tables static const D3D11_BLEND d3dSrcFactors[8] = { D3D11_BLEND_ZERO, @@ -230,7 +230,7 @@ static const D3D11_TEXTURE_ADDRESS_MODE d3dClamps[4] = void SetupDeviceObjects() { - FBManager.Create(); + g_framebufferManager.Create(); HRESULT hr; float colmat[20]= {0.0f}; @@ -296,9 +296,10 @@ void SetupDeviceObjects() D3D::SetDebugObjectName((ID3D11DeviceChild*)resetraststate, "rasterizer state for Renderer::ResetAPIState"); } +// Kill off all POOL_DEFAULT device objects. void TeardownDeviceObjects() { - FBManager.Destroy(); + g_framebufferManager.Destroy(); SAFE_RELEASE(access_efb_cbuf); SAFE_RELEASE(cleardepthstates[0]); SAFE_RELEASE(cleardepthstates[1]); @@ -342,14 +343,14 @@ bool Renderer::Init() D3D::gfxstate->samplerdesc[stage].MaxAnisotropy = g_ActiveConfig.iMaxAnisotropy; float ClearColor[4] = { 0.f, 0.f, 0.f, 0.f }; - D3D::context->ClearRenderTargetView(FBManager.GetEFBColorTexture()->GetRTV(), ClearColor); - D3D::context->ClearDepthStencilView(FBManager.GetEFBDepthTexture()->GetDSV(), D3D11_CLEAR_DEPTH, 1.f, 0); + D3D::context->ClearRenderTargetView(g_framebufferManager.GetEFBColorTexture()->GetRTV(), ClearColor); + D3D::context->ClearDepthStencilView(g_framebufferManager.GetEFBDepthTexture()->GetDSV(), D3D11_CLEAR_DEPTH, 1.f, 0); D3D11_VIEWPORT vp = CD3D11_VIEWPORT((float)(s_Fulltarget_width - s_target_width) / 2.f, (float)(s_Fulltarget_height - s_target_height) / 2.f, (float)s_target_width, (float)s_target_height); D3D::context->RSSetViewports(1, &vp); - D3D::context->OMSetRenderTargets(1, &FBManager.GetEFBColorTexture()->GetRTV(), FBManager.GetEFBDepthTexture()->GetDSV()); + D3D::context->OMSetRenderTargets(1, &g_framebufferManager.GetEFBColorTexture()->GetRTV(), g_framebufferManager.GetEFBDepthTexture()->GetDSV()); D3D::BeginFrame(); D3D::gfxstate->rastdesc.ScissorEnable = TRUE; @@ -372,16 +373,18 @@ int Renderer::GetFullTargetHeight() { return s_Fulltarget_height; } float Renderer::GetTargetScaleX() { return xScale; } float Renderer::GetTargetScaleY() { return yScale; } +// Return the framebuffer size int Renderer::GetFrameBufferWidth() { return s_backbuffer_width; } + int Renderer::GetFrameBufferHeight() { return s_backbuffer_height; } -// create On-Screen-Messages +// Create On-Screen-Messages void Renderer::DrawDebugText() { // OSD menu messages @@ -418,31 +421,35 @@ void Renderer::DrawDebugText() g_ActiveConfig.bCrop ? " (crop)" : ""; std::string OSDM3 = "Disabled"; - // if there is more text than this we will have a collission + // If there is more text than this we will have a collision if (g_ActiveConfig.bShowFPS) - { T1 += "\n\n"; T2 += "\n\n"; } + { + T1 += "\n\n"; + T2 += "\n\n"; + } + // The rows T0.push_back(StringFromFormat("3: Internal Resolution: %s\n", OSDM1.c_str())); T0.push_back(StringFromFormat("4: Aspect Ratio: %s%s\n", OSDM21.c_str(), OSDM22.c_str())); T0.push_back(StringFromFormat("5: Copy EFB: %s\n", OSDM3.c_str())); T0.push_back(StringFromFormat("6: Fog: %s\n", g_ActiveConfig.bDisableFog ? "Disabled" : "Enabled")); - T0.push_back(StringFromFormat("7: Material Lighting: %s\n", g_ActiveConfig.bDisableLighting ? "Disabled" : "Enabled")); + T0.push_back(StringFromFormat("7: Material Lighting: %s\n", g_ActiveConfig.bDisableLighting ? "Disabled" : "Enabled")); - // latest changed setting in yellow + // The latest changed setting in yellow T1 += (OSDChoice == -1) ? T0.at(0) : "\n"; T1 += (OSDChoice == -2) ? T0.at(1) : "\n"; T1 += (OSDChoice == -3) ? T0.at(2) : "\n"; T1 += (OSDChoice == -4) ? T0.at(3) : "\n"; T1 += (OSDChoice == -5) ? T0.at(4) : "\n"; - // other settings in cyan + // The other settings in cyan T2 += (OSDChoice != -1) ? T0.at(0) : "\n"; T2 += (OSDChoice != -2) ? T0.at(1) : "\n"; T2 += (OSDChoice != -3) ? T0.at(2) : "\n"; T2 += (OSDChoice != -4) ? T0.at(3) : "\n"; T2 += (OSDChoice != -5) ? T0.at(4) : "\n"; - // render a shadow, and then the text + // Render a shadow, and then the text Renderer::RenderText(T1.c_str(), 21, 21, 0xDD000000); Renderer::RenderText(T1.c_str(), 20, 20, 0xFFffff00); Renderer::RenderText(T2.c_str(), 21, 21, 0xDD000000); @@ -451,7 +458,7 @@ void Renderer::DrawDebugText() } } -void Renderer::RenderText(const char* text, int left, int top, u32 color) +void Renderer::RenderText(const char *text, int left, int top, u32 color) { D3D::font.DrawTextScaled((float)left, (float)top, 20.f, 0.0f, color, text, false); } @@ -468,6 +475,9 @@ TargetRectangle Renderer::ConvertEFBRectangle(const EFBRectangle& rc) return result; } + +// With D3D, we have to resize the backbuffer if the window changed +// size. void CheckForResize() { while (EmuWindow::IsSizing()) @@ -475,21 +485,22 @@ void CheckForResize() if (EmuWindow::GetParentWnd()) { - // re-stretch window to parent window size again, if it has a parent window. + // Re-stretch window to parent window size again, if it has a parent window. RECT rcParentWindow; GetWindowRect(EmuWindow::GetParentWnd(), &rcParentWindow); int width = rcParentWindow.right - rcParentWindow.left; int height = rcParentWindow.bottom - rcParentWindow.top; if (width != s_backbuffer_width || height != s_backbuffer_height) - ::MoveWindow(EmuWindow::GetWnd(), 0, 0, width, height, FALSE); + MoveWindow(EmuWindow::GetWnd(), 0, 0, width, height, FALSE); } RECT rcWindow; GetClientRect(EmuWindow::GetWnd(), &rcWindow); int client_width = rcWindow.right - rcWindow.left; int client_height = rcWindow.bottom - rcWindow.top; - // sanity check - if ((client_width != s_backbuffer_width || client_height != s_backbuffer_height) && + // Sanity check + if ((client_width != s_backbuffer_width || + client_height != s_backbuffer_height) && client_width >= 4 && client_height >= 4) { WindowResized = true; @@ -507,7 +518,7 @@ void Renderer::RenderToXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight, const EFBRect // just use progressive. if (g_ActiveConfig.bUseXFB) { - FBManager.CopyToXFB(xfbAddr, fbWidth, fbHeight, sourceRc); + g_framebufferManager.CopyToXFB(xfbAddr, fbWidth, fbHeight, sourceRc); } else { @@ -559,7 +570,7 @@ bool Renderer::SetScissorRect() rc.bottom = rc.top; rc.top = temp; } - + if (rc.right >= rc.left && rc.bottom >= rc.top) { D3D::context->RSSetScissorRects(1, &rc); @@ -599,7 +610,7 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) return 0; } - // get the rectangular target region covered by the EFB pixel + // Get the rectangular target region covered by the EFB pixel EFBRectangle efbPixelRc; efbPixelRc.left = x; efbPixelRc.top = y; @@ -624,15 +635,15 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) if ((RectToLock.right - RectToLock.left) > 4) RectToLock.left++; - ResetAPIState(); // reset any game specific settings + ResetAPIState(); // Reset any game specific settings // Stretch picture with increased internal resolution D3D11_VIEWPORT vp = CD3D11_VIEWPORT(0.f, 0.f, 4.f, 4.f); D3D::context->RSSetViewports(1, &vp); D3D::context->PSSetConstantBuffers(0, 1, &access_efb_cbuf); - D3D::context->OMSetRenderTargets(1, &FBManager.GetEFBDepthReadTexture()->GetRTV(), NULL); + D3D::context->OMSetRenderTargets(1, &g_framebufferManager.GetEFBDepthReadTexture()->GetRTV(), NULL); D3D::SetPointCopySampler(); - D3D::drawShadedTexQuad(FBManager.GetEFBDepthTexture()->GetSRV(), + D3D::drawShadedTexQuad(g_framebufferManager.GetEFBDepthTexture()->GetSRV(), &RectToLock, Renderer::GetFullTargetWidth(), Renderer::GetFullTargetHeight(), @@ -640,21 +651,21 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) VertexShaderCache::GetSimpleVertexShader(), VertexShaderCache::GetSimpleInputLayout()); - D3D::context->OMSetRenderTargets(1, &FBManager.GetEFBColorTexture()->GetRTV(), FBManager.GetEFBDepthTexture()->GetDSV()); + D3D::context->OMSetRenderTargets(1, &g_framebufferManager.GetEFBColorTexture()->GetRTV(), g_framebufferManager.GetEFBDepthTexture()->GetDSV()); RestoreAPIState(); RectToLock = CD3D11_RECT(0, 0, 4, 4); // copy to system memory D3D11_BOX box = CD3D11_BOX(0, 0, 0, 4, 4, 1); - read_tex = FBManager.GetEFBDepthStagingBuffer(); - D3D::context->CopySubresourceRegion(read_tex, 0, 0, 0, 0, FBManager.GetEFBDepthReadTexture()->GetTex(), 0, &box); + read_tex = g_framebufferManager.GetEFBDepthStagingBuffer(); + D3D::context->CopySubresourceRegion(read_tex, 0, 0, 0, 0, g_framebufferManager.GetEFBDepthReadTexture()->GetTex(), 0, &box); } else { // we can directly copy to system memory here - read_tex = FBManager.GetEFBColorStagingBuffer(); + read_tex = g_framebufferManager.GetEFBColorStagingBuffer(); D3D11_BOX box = CD3D11_BOX(RectToLock.left, RectToLock.top, 0, RectToLock.right, RectToLock.bottom, 1); - D3D::context->CopySubresourceRegion(read_tex, 0, 0, 0, 0, FBManager.GetEFBColorTexture()->GetTex(), 0, &box); + D3D::context->CopySubresourceRegion(read_tex, 0, 0, 0, 0, g_framebufferManager.GetEFBColorTexture()->GetTex(), 0, &box); RectToLock = CD3D11_RECT(0, 0, 1, 1); } @@ -662,21 +673,35 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) D3D11_MAPPED_SUBRESOURCE map; D3D::context->Map(read_tex, 0, D3D11_MAP_READ, 0, &map); - switch(type) { - case PEEK_Z: - val = ((float*)map.pData)[0]; - z = ((u32)(val * 0xffffff)); - break; + switch(type) + { + case PEEK_Z: + val = ((float*)map.pData)[0]; + z = ((u32)(val * 0xffffff)); + break; - case PEEK_COLOR: - z = ((u32*)map.pData)[0]; - break; + case POKE_Z: + // TODO: Implement + break; + + case PEEK_COLOR: + z = ((u32*)map.pData)[0]; + break; + + case POKE_COLOR: + // TODO: Implement. One way is to draw a tiny pixel-sized rectangle at + // the exact location. Note: EFB pokes are susceptible to Z-buffering + // and perhaps blending. + //WARN_LOG(VIDEOINTERFACE, "This is probably some kind of software rendering"); + break; // TODO: Implement POKE_Z and POKE_COLOR - default: - break; + default: + break; } + D3D::context->Unmap(read_tex, 0); + // TODO: in RE0 this value is often off by one, which causes lighting to disappear return z; } @@ -728,7 +753,7 @@ void UpdateViewport() { s_Fulltarget_height -= 2 * Y; Y = 0; - sizeChanged=true; + sizeChanged = true; } float newx = (float)X; @@ -755,29 +780,30 @@ void UpdateViewport() else { D3D::context->OMSetRenderTargets(1, &D3D::GetBackBuffer()->GetRTV(), NULL); - FBManager.Destroy(); - FBManager.Create(); - D3D::context->OMSetRenderTargets(1, &FBManager.GetEFBColorTexture()->GetRTV(), FBManager.GetEFBDepthTexture()->GetDSV()); + g_framebufferManager.Destroy(); + g_framebufferManager.Create(); + D3D::context->OMSetRenderTargets(1, &g_framebufferManager.GetEFBColorTexture()->GetRTV(), g_framebufferManager.GetEFBDepthTexture()->GetDSV()); } } - // some games set invalids values MinDepth and MaxDepth so fix them to the max an min allowed and let the shaders do this work + // Some games set invalids values for z min and z max so fix them to the max an min alowed and let the shaders do this work D3D11_VIEWPORT vp = CD3D11_VIEWPORT(newx, newy, newwidth, newheight, 0.f, // (xfregs.rawViewport[5] - xfregs.rawViewport[2]) / 16777216.0f; 1.f); // xfregs.rawViewport[5] / 16777216.0f; D3D::context->RSSetViewports(1, &vp); } + // Tino: color is passed in bgra mode so need to convert it to rgba void Renderer::ClearScreen(const EFBRectangle& rc, bool colorEnable, bool alphaEnable, bool zEnable, u32 color, u32 z) { + // Update the view port for clearing the picture TargetRectangle targetRc = Renderer::ConvertEFBRectangle(rc); - // update the view port for clearing the picture D3D11_VIEWPORT vp = CD3D11_VIEWPORT((float)targetRc.left, (float)targetRc.top, (float)targetRc.GetWidth(), (float)targetRc.GetHeight(), 0.f, 1.f); D3D::context->RSSetViewports(1, &vp); - // always set the scissor in case it was set by the game and has not been reset + // Always set the scissor in case it was set by the game and has not been reset D3D11_RECT sirc = CD3D11_RECT(targetRc.left, targetRc.top, targetRc.right, targetRc.bottom); D3D::context->RSSetScissorRects(1, &sirc); u32 rgbaColor = (color & 0xFF00FF00) | ((color >> 16) & 0xFF) | ((color << 16) & 0xFF0000); @@ -806,7 +832,7 @@ void Renderer::SetBlendMode(bool forceUpdate) D3D::gfxstate->SetSrcBlend(d3dSrcFactors[1]); D3D::gfxstate->SetDestBlend(d3dDestFactors[1]); } - else + else { D3D::gfxstate->SetAlphaBlendEnable(bpmem.blendmode.blendenable && (!( bpmem.blendmode.srcfactor == 1 && bpmem.blendmode.dstfactor == 0))); if (bpmem.blendmode.blendenable && (!( bpmem.blendmode.srcfactor == 1 && bpmem.blendmode.dstfactor == 0))) @@ -815,10 +841,10 @@ void Renderer::SetBlendMode(bool forceUpdate) D3D::gfxstate->SetSrcBlend(d3dSrcFactors[bpmem.blendmode.srcfactor]); D3D::gfxstate->SetDestBlend(d3dDestFactors[bpmem.blendmode.dstfactor]); } - } } +// This function has the final picture. We adjust the aspect ratio here. void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,const EFBRectangle& rc) { if (g_bSkipCurrentFrame || (!XFBWrited && !g_ActiveConfig.bUseRealXFB) || !fbWidth || !fbHeight) @@ -829,10 +855,10 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons // this function is called after the XFB field is changed, not after // EFB is copied to XFB. In this way, flickering is reduced in games // and seems to also give more FPS in ZTP - + if (field == FIELD_LOWER) xfbAddr -= fbWidth * 2; u32 xfbCount = 0; - const XFBSource** xfbSourceList = FBManager.GetXFBSource(xfbAddr, fbWidth, fbHeight, xfbCount); + const XFBSource** xfbSourceList = g_framebufferManager.GetXFBSource(xfbAddr, fbWidth, fbHeight, xfbCount); if ((!xfbSourceList || xfbCount == 0) && g_ActiveConfig.bUseXFB && !g_ActiveConfig.bUseRealXFB) { g_VideoInitialize.pCopiedToXFB(false); @@ -841,7 +867,7 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons Renderer::ResetAPIState(); - // prepare copying the XFBs to our backbuffer + // Prepare to copy the XFBs to our backbuffer TargetRectangle dst_rect; ComputeDrawRectangle(s_backbuffer_width, s_backbuffer_height, false, &dst_rect); D3D11_VIEWPORT vp = CD3D11_VIEWPORT(0.f, 0.f, (float)s_backbuffer_width, (float)s_backbuffer_height); @@ -876,13 +902,13 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons // draw each xfb source for (u32 i = 0; i < xfbCount; ++i) { - xfbSource = xfbSourceList[i]; + xfbSource = xfbSourceList[i]; MathUtil::Rectangle sourceRc; sourceRc.left = 0; sourceRc.top = 0; sourceRc.right = xfbSource->texWidth; - sourceRc.bottom = xfbSource->texHeight; + sourceRc.bottom = xfbSource->texHeight; MathUtil::Rectangle drawRc; @@ -893,11 +919,10 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons int xfbWidth = xfbSource->srcWidth; int hOffset = ((s32)xfbSource->srcAddr - (s32)xfbAddr) / ((s32)fbWidth * 2); - drawRc.bottom = 1.0f - 2.0f * ((hOffset) / (float)fbHeight); - drawRc.top = 1.0f - 2.0f * ((hOffset + xfbHeight) / (float)fbHeight); + drawRc.bottom = 1.0f - (2.0f * (hOffset) / (float)fbHeight); + drawRc.top = 1.0f - (2.0f * (hOffset + xfbHeight) / (float)fbHeight); drawRc.left = -(xfbWidth / (float)fbWidth); drawRc.right = (xfbWidth / (float)fbWidth); - if (!g_ActiveConfig.bAutoScale) { @@ -918,13 +943,14 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons drawRc.left = -1; drawRc.right = 1; } + D3D::drawShadedTexSubQuad(xfbSource->tex->GetSRV(), &sourceRc, xfbSource->texWidth, xfbSource->texHeight, &drawRc, PixelShaderCache::GetColorCopyProgram(),VertexShaderCache::GetSimpleVertexShader(), VertexShaderCache::GetSimpleInputLayout()); } } else { TargetRectangle targetRc = Renderer::ConvertEFBRectangle(rc); - D3DTexture2D* read_texture = FBManager.GetEFBColorTexture(); + D3DTexture2D* read_texture = g_framebufferManager.GetEFBColorTexture(); D3D::drawShadedTexQuad(read_texture->GetSRV(), targetRc.AsRECT(), Renderer::GetFullTargetWidth(), Renderer::GetFullTargetHeight(), PixelShaderCache::GetColorCopyProgram(),VertexShaderCache::GetSimpleVertexShader(), VertexShaderCache::GetSimpleInputLayout()); } // done with drawing the game stuff, good moment to save a screenshot @@ -958,12 +984,12 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons s_bScreenshot = false; } - // finally present some information + // Finish up the current frame, print some stats if (g_ActiveConfig.bShowFPS) { char fps[20]; StringCchPrintfA(fps, 20, "FPS: %d\n", s_fps); - D3D::font.DrawTextScaled(0,30,20,0.0f,0xFF00FFFF,fps,false); + D3D::font.DrawTextScaled(0, 30, 20, 0.0f, 0xFF00FFFF, fps, false); } Renderer::DrawDebugText(); @@ -971,13 +997,13 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons { char buf[32768]; Statistics::ToString(buf); - D3D::font.DrawTextScaled(0,30,20,0.0f,0xFF00FFFF,buf,false); + D3D::font.DrawTextScaled(0, 30, 20, 0.0f, 0xFF00FFFF, buf, false); } else if (g_ActiveConfig.bOverlayProjStats) { char buf[32768]; Statistics::ToStringProj(buf); - D3D::font.DrawTextScaled(0,30,20,0.0f,0xFF00FFFF,buf,false); + D3D::font.DrawTextScaled(0, 30, 20, 0.0f, 0xFF00FFFF, buf, false); } OSD::DrawMessages(); @@ -986,13 +1012,13 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons DLCache::ProgressiveCleanup(); TextureCache::Cleanup(); - // enable any configuration changes + // Enable any configuration changes UpdateActiveConfig(); WindowResized = false; CheckForResize(); bool xfbchanged = false; - + if (s_XFB_width != fbWidth || s_XFB_height != fbHeight) { xfbchanged = true; @@ -1007,18 +1033,21 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons // update FPS counter static int fpscount = 0; static unsigned long lasttime = 0; - if (Common::Timer::GetTimeMs() - lasttime >= 1000) + if (Common::Timer::GetTimeMs() - lasttime >= 1000) { lasttime = Common::Timer::GetTimeMs(); s_fps = fpscount; fpscount = 0; } - if (XFBWrited) ++fpscount; + if (XFBWrited) + ++fpscount; - // set default viewport and scissor, for the clear to work correctly + // Begin new frame + // Set default viewport and scissor, for the clear to work correctly + // New frame stats.ResetFrame(); - // done. Show our work ;) + // Flip/present backbuffer to frontbuffer here D3D::Present(); // resize the back buffers NOW to avoid flickering when resizing windows @@ -1038,16 +1067,20 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons s_target_height = (int)(EFB_HEIGHT * yScale); D3D::context->OMSetRenderTargets(1, &D3D::GetBackBuffer()->GetRTV(), NULL); - FBManager.Destroy(); - FBManager.Create(); + g_framebufferManager.Destroy(); + g_framebufferManager.Create(); } // begin next frame Renderer::RestoreAPIState(); D3D::BeginFrame(); - D3D::context->OMSetRenderTargets(1, &FBManager.GetEFBColorTexture()->GetRTV(), FBManager.GetEFBDepthTexture()->GetDSV()); + D3D::context->OMSetRenderTargets(1, &g_framebufferManager.GetEFBColorTexture()->GetRTV(), g_framebufferManager.GetEFBDepthTexture()->GetDSV()); UpdateViewport(); VertexShaderManager::SetViewportChanged(); + // For testing zbuffer targets. + // Renderer::SetZBufferRender(); + // SaveTexture("tex.tga", GL_TEXTURE_RECTANGLE_ARB, s_FakeZTarget, + // GetTargetWidth(), GetTargetHeight()); g_VideoInitialize.pCopiedToXFB(XFBWrited || g_ActiveConfig.bUseRealXFB); XFBWrited = false; } @@ -1065,7 +1098,7 @@ void Renderer::ResetAPIState() void Renderer::RestoreAPIState() { - // gets us back into a more game-like state. + // Gets us back into a more game-like state. if (reset_called) { D3D::stateman->PopBlendState(); @@ -1094,6 +1127,7 @@ void Renderer::SetDepthMode() } else { + // if the test is disabled write is disabled too D3D::gfxstate->depthdesc.DepthEnable = FALSE; D3D::gfxstate->depthdesc.DepthWriteMask = D3D11_DEPTH_WRITE_MASK_ZERO; } @@ -1184,7 +1218,7 @@ void Renderer::SetInterlacingMode() } // Save screenshot -void Renderer::SetScreenshot(const char* filename) +void Renderer::SetScreenshot(const char *filename) { s_criticalScreenshot.Enter(); strcpy_s(s_sScreenshotName, filename); diff --git a/Source/Plugins/Plugin_VideoDX11/Src/TextureCache.cpp b/Source/Plugins/Plugin_VideoDX11/Src/TextureCache.cpp index 5d4159a671..bce7ba6664 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/TextureCache.cpp +++ b/Source/Plugins/Plugin_VideoDX11/Src/TextureCache.cpp @@ -28,7 +28,7 @@ #include "D3DBase.h" #include "D3DTexture.h" #include "D3DUtil.h" -#include "FBManager.h" +#include "FramebufferManager.h" #include "PixelShaderCache.h" #include "PixelShaderManager.h" #include "VertexShaderManager.h" @@ -59,7 +59,7 @@ void TextureCache::TCacheEntry::Destroy(bool shutdown) if (!isRenderTarget && !shutdown && !g_ActiveConfig.bSafeTextureCache) { - u32* ptr = (u32*)g_VideoInitialize.pGetMemoryPointer(addr); + u32 *ptr = (u32*)g_VideoInitialize.pGetMemoryPointer(addr); if (ptr && *ptr == hash) *ptr = oldpixel; } @@ -123,30 +123,6 @@ void TextureCache::Invalidate(bool shutdown) HiresTextures::Shutdown(); } -void TextureCache::InvalidateRange(u32 start_address, u32 size) -{ - TexCache::iterator iter = textures.begin(); - while (iter != textures.end()) - { - if (iter->second.IntersectsMemoryRange(start_address, size)) - { - iter->second.Destroy(false); - textures.erase(iter++); - } - else - { - ++iter; - } - } -} - -bool TextureCache::TCacheEntry::IntersectsMemoryRange(u32 range_address, u32 range_size) -{ - if (addr + size_in_bytes < range_address) return false; - if (addr >= range_address + range_size) return false; - return true; -} - void TextureCache::Shutdown() { Invalidate(true); @@ -178,6 +154,31 @@ void TextureCache::Cleanup() } } +void TextureCache::InvalidateRange(u32 start_address, u32 size) +{ + TexCache::iterator iter = textures.begin(); + while (iter != textures.end()) + { + if (iter->second.IntersectsMemoryRange(start_address, size)) + { + iter->second.Destroy(false); + textures.erase(iter++); + } + else + { + ++iter; + } + } +} + +bool TextureCache::TCacheEntry::IntersectsMemoryRange(u32 range_address, u32 range_size) +{ + if (addr + size_in_bytes < range_address) return false; + if (addr >= range_address + range_size) return false; + return true; +} + + // returns the exponent of the smallest power of two which is greater than val unsigned int GetPow2(unsigned int val) { @@ -188,21 +189,47 @@ unsigned int GetPow2(unsigned int val) TextureCache::TCacheEntry* TextureCache::Load(unsigned int stage, u32 address, unsigned int width, unsigned int height, unsigned int tex_format, unsigned int tlutaddr, unsigned int tlutfmt, bool UseNativeMips, unsigned int maxlevel) { - if (address == 0) return NULL; + // notes (about "UNsafe texture cache"): + // Have to be removed soon. + // But we keep it until the "safe" way became rock solid + // pros: it has an unique ID held by the texture data itself (@address) once cached. + // cons: it writes this unique ID in the gc RAM <- very dangerous (break MP1) and ugly - u8* ptr = g_VideoInitialize.pGetMemoryPointer(address); + // notes (about "safe texture cache"): + // Metroids text issue (character table): + // Same addr, same GX_TF_C4 texture data but different TLUT (hence different outputs). + // That's why we have to hash the TLUT too for TLUT tex_format dependent textures (ie. GX_TF_C4, GX_TF_C8, GX_TF_C14X2). + // And since the address and tex data don't change, the key index in the cacheEntry map can't be the address but + // have to be a real unique ID. + // DONE but not satifiying yet -> may break copyEFBToTexture sometimes. + + // Pokemon Colosseum text issue (plain text): + // Use a GX_TF_I4 512x512 text-flush-texture at a const address. + // The problem here was just the sparse hash on the texture. This texture is partly overwrited (what is needed only) + // so lot's of remaning old text. Thin white chars on black bg too. + + // TODO: - clean this up when ready to kill old "unsafe texture cache" + // - fix the key index situation with CopyRenderTargetToTexture. + // Could happen only for GX_TF_C4, GX_TF_C8 and GX_TF_C14X2 fmt. + // Wonder if we can't use tex width&height to know if EFB might be copied to it... + // raw idea: TOCHECK if addresses are aligned we have few bits left... + + if (address == 0) + return NULL; + + u8 *ptr = g_VideoInitialize.pGetMemoryPointer(address); unsigned int bsw = TexDecoder_GetBlockWidthInTexels(tex_format) - 1; // TexelSizeInNibbles(format)*width*height/16; unsigned int bsh = TexDecoder_GetBlockHeightInTexels(tex_format) - 1; // TexelSizeInNibbles(format)*width*height/16; unsigned int bsdepth = TexDecoder_GetTexelSizeInNibbles(tex_format); - unsigned int expandedWidth = (width + bsw) & (~bsw); + unsigned int expandedWidth = (width + bsw) & (~bsw); unsigned int expandedHeight = (height + bsh) & (~bsh); - u64 hash_value; + u64 hash_value = 0; u32 texID = address; - u64 texHash; + u64 texHash = 0; u32 FullFormat = tex_format; if ((tex_format == GX_TF_C4) || (tex_format == GX_TF_C8) || (tex_format == GX_TF_C14X2)) - u32 FullFormat = (tex_format | (tlutfmt << 16)); + FullFormat = (tex_format | (tlutfmt << 16)); // hires textures and texture dumping not supported, yet if (g_ActiveConfig.bSafeTextureCache/* || g_ActiveConfig.bHiresTextures || g_ActiveConfig.bDumpTextures*/) @@ -264,7 +291,7 @@ TextureCache::TCacheEntry* TextureCache::Load(unsigned int stage, u32 address, u } } - // make an entry in the table + // Make an entry in the table TCacheEntry& entry = textures[texID]; PC_TexFormat pcfmt = PC_TEX_FMT_NONE; @@ -306,6 +333,7 @@ TextureCache::TCacheEntry* TextureCache::Load(unsigned int stage, u32 address, u { D3D::ReplaceRGBATexture2D(entry.texture->GetTex(), temp, width, height, expandedWidth, 0, usage); } + entry.addr = address; entry.size_in_bytes = TexDecoder_GetTextureSizeInBytes(expandedWidth, expandedHeight, tex_format); entry.isRenderTarget = false; @@ -340,7 +368,7 @@ TextureCache::TCacheEntry* TextureCache::Load(unsigned int stage, u32 address, u entry.fmt = FullFormat; INCSTAT(stats.numTexturesCreated); - SETSTAT(stats.numTexturesAlive, (int)textures.size()); + SETSTAT(stats.numTexturesAlive, textures.size()); D3D::gfxstate->SetShaderResource(stage, entry.texture->GetSRV()); @@ -370,7 +398,7 @@ void TextureCache::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, boo } else { - // remove it and recreate it as a render target + // Remove it and recreate it as a render target SAFE_RELEASE(iter->second.texture); textures.erase(iter); } @@ -557,13 +585,13 @@ void TextureCache::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, boo D3D::stateman->PushDepthState(efbcopydepthstate); D3D::context->OMSetRenderTargets(1, &tex->GetRTV(), NULL); D3D::drawShadedTexQuad( - (bFromZBuffer) ? FBManager.GetEFBDepthTexture()->GetSRV() : FBManager.GetEFBColorTexture()->GetSRV(), + (bFromZBuffer) ? g_framebufferManager.GetEFBDepthTexture()->GetSRV() : g_framebufferManager.GetEFBColorTexture()->GetSRV(), &sourcerect, Renderer::GetFullTargetWidth(), Renderer::GetFullTargetHeight(), (bFromZBuffer) ? PixelShaderCache::GetDepthMatrixProgram() : PixelShaderCache::GetColorMatrixProgram(), VertexShaderCache::GetSimpleVertexShader(), VertexShaderCache::GetSimpleInputLayout()); - D3D::context->OMSetRenderTargets(1, &FBManager.GetEFBColorTexture()->GetRTV(), FBManager.GetEFBDepthTexture()->GetDSV()); + D3D::context->OMSetRenderTargets(1, &g_framebufferManager.GetEFBColorTexture()->GetRTV(), g_framebufferManager.GetEFBDepthTexture()->GetDSV()); D3D::stateman->PopBlendState(); D3D::stateman->PopDepthState(); D3D::stateman->PopRasterizerState(); diff --git a/Source/Plugins/Plugin_VideoDX11/Src/VertexManager.cpp b/Source/Plugins/Plugin_VideoDX11/Src/VertexManager.cpp index da04ef5edd..d26088c0d3 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/VertexManager.cpp +++ b/Source/Plugins/Plugin_VideoDX11/Src/VertexManager.cpp @@ -24,7 +24,7 @@ #include "Fifo.h" #include "Statistics.h" #include "Profiler.h" -#include "FBManager.h" +#include "FramebufferManager.h" #include "VertexManager.h" #include "OpcodeDecoding.h" #include "IndexGenerator.h" @@ -47,11 +47,18 @@ using std::string; using namespace D3D; -extern NativeVertexFormat* g_nativeVertexFmt; +// internal state for loading vertices +extern NativeVertexFormat *g_nativeVertexFmt; namespace VertexManager { +static int lastPrimitive; + +static u8 *LocalVBuffer; +static u16 *TIBuffer; +static u16 *LIBuffer; +static u16 *PIBuffer; #define MAXVBUFFERSIZE 0x50000 #define MAXIBUFFERSIZE 0x10000 @@ -59,12 +66,6 @@ namespace VertexManager #define NUM_VERTEXBUFFERS 8 #define NUM_INDEXBUFFERS 10 -int lastPrimitive; - -u8* LocalVBuffer = NULL; -u16* TIBuffer = NULL; -u16* LIBuffer = NULL; -u16* PIBuffer = NULL; bool Flushed=false; ID3D11Buffer* indexbuffers[NUM_INDEXBUFFERS] = {NULL}; @@ -147,17 +148,17 @@ void Shutdown() ResetBuffer(); } -void AddIndices(int _primitive, int _numVertices) +void AddIndices(int primitive, int numVertices) { - switch (_primitive) + switch (primitive) { - case GX_DRAW_QUADS: IndexGenerator::AddQuads(_numVertices); break; - case GX_DRAW_TRIANGLES: IndexGenerator::AddList(_numVertices); break; - case GX_DRAW_TRIANGLE_STRIP: IndexGenerator::AddStrip(_numVertices); break; - case GX_DRAW_TRIANGLE_FAN: IndexGenerator::AddFan(_numVertices); break; - case GX_DRAW_LINE_STRIP: IndexGenerator::AddLineStrip(_numVertices); break; - case GX_DRAW_LINES: IndexGenerator::AddLineList(_numVertices); break; - case GX_DRAW_POINTS: IndexGenerator::AddPoints(_numVertices); break; + case GX_DRAW_QUADS: IndexGenerator::AddQuads(numVertices); break; + case GX_DRAW_TRIANGLES: IndexGenerator::AddList(numVertices); break; + case GX_DRAW_TRIANGLE_STRIP: IndexGenerator::AddStrip(numVertices); break; + case GX_DRAW_TRIANGLE_FAN: IndexGenerator::AddFan(numVertices); break; + case GX_DRAW_LINE_STRIP: IndexGenerator::AddLineStrip(numVertices); break; + case GX_DRAW_LINES: IndexGenerator::AddLineList(numVertices); break; + case GX_DRAW_POINTS: IndexGenerator::AddPoints(numVertices); break; } } @@ -170,53 +171,54 @@ int GetRemainingVertices(int primitive) { switch (primitive) { - case GX_DRAW_QUADS: - case GX_DRAW_TRIANGLES: - case GX_DRAW_TRIANGLE_STRIP: - case GX_DRAW_TRIANGLE_FAN: - return (MAXIBUFFERSIZE - IndexGenerator::GetTriangleindexLen())/3; - case GX_DRAW_LINE_STRIP: - case GX_DRAW_LINES: - return (MAXIBUFFERSIZE - IndexGenerator::GetLineindexLen())/2; - case GX_DRAW_POINTS: - return (MAXIBUFFERSIZE - IndexGenerator::GetPointindexLen()); - default: return 0; + case GX_DRAW_QUADS: + case GX_DRAW_TRIANGLES: + case GX_DRAW_TRIANGLE_STRIP: + case GX_DRAW_TRIANGLE_FAN: + return (MAXIBUFFERSIZE - IndexGenerator::GetTriangleindexLen())/3; + case GX_DRAW_LINE_STRIP: + case GX_DRAW_LINES: + return (MAXIBUFFERSIZE - IndexGenerator::GetLineindexLen())/2; + case GX_DRAW_POINTS: + return (MAXIBUFFERSIZE - IndexGenerator::GetPointindexLen()); + default: return 0; } } -void AddVertices(int _primitive, int _numVertices) +void AddVertices(int primitive, int numVertices) { - if (_numVertices <= 0) return; + if (numVertices <= 0) + return; - switch (_primitive) + switch (primitive) { - case GX_DRAW_QUADS: - case GX_DRAW_TRIANGLES: - case GX_DRAW_TRIANGLE_STRIP: - case GX_DRAW_TRIANGLE_FAN: - if (MAXIBUFFERSIZE - IndexGenerator::GetTriangleindexLen() < 3 * _numVertices) + case GX_DRAW_QUADS: + case GX_DRAW_TRIANGLES: + case GX_DRAW_TRIANGLE_STRIP: + case GX_DRAW_TRIANGLE_FAN: + if (MAXIBUFFERSIZE - IndexGenerator::GetTriangleindexLen() < 3 * numVertices) Flush(); - break; - case GX_DRAW_LINE_STRIP: - case GX_DRAW_LINES: - if (MAXIBUFFERSIZE - IndexGenerator::GetLineindexLen() < 2 * _numVertices) + break; + case GX_DRAW_LINE_STRIP: + case GX_DRAW_LINES: + if (MAXIBUFFERSIZE - IndexGenerator::GetLineindexLen() < 2 * numVertices) Flush(); - break; - case GX_DRAW_POINTS: - if (MAXIBUFFERSIZE - IndexGenerator::GetPointindexLen() < _numVertices) + break; + case GX_DRAW_POINTS: + if (MAXIBUFFERSIZE - IndexGenerator::GetPointindexLen() < numVertices) Flush(); - break; - default: return; + break; + default: return; } if (Flushed) { IndexGenerator::Start(TIBuffer,LIBuffer,PIBuffer); Flushed=false; } - lastPrimitive = _primitive; - ADDSTAT(stats.thisFrame.numPrims, _numVertices); + lastPrimitive = primitive; + ADDSTAT(stats.thisFrame.numPrims, numVertices); INCSTAT(stats.thisFrame.numPrimitiveJoins); - AddIndices(_primitive, _numVertices); + AddIndices(primitive, numVertices); } inline void Draw(u32 stride, bool alphapass) @@ -303,10 +305,8 @@ void Flush() u32 usedtextures = 0; for (u32 i = 0; i < (u32)bpmem.genMode.numtevstages + 1; ++i) - { - if (bpmem.tevorders[i/2].getEnable(i & 1)) + if (bpmem.tevorders[i / 2].getEnable(i & 1)) usedtextures |= 1 << bpmem.tevorders[i/2].getTexMap(i & 1); - } if (bpmem.genMode.numindstages > 0) for (unsigned int i = 0; i < bpmem.genMode.numtevstages + 1; ++i) @@ -320,24 +320,24 @@ void Flush() Renderer::SetSamplerState(i & 3, i >> 2); FourTexUnits &tex = bpmem.tex[i >> 2]; TextureCache::TCacheEntry* tentry = TextureCache::Load(i, - (tex.texImage3[i&3].image_base/* & 0x1FFFFF*/) << 5, - tex.texImage0[i&3].width + 1, tex.texImage0[i&3].height + 1, - tex.texImage0[i&3].format, tex.texTlut[i&3].tmem_offset<<9, - tex.texTlut[i&3].tlut_format, - (tex.texMode0[i&3].min_filter & 3) && (tex.texMode0[i&3].min_filter != 8) && g_ActiveConfig.bUseNativeMips, - (tex.texMode1[i&3].max_lod >> 4)); + (tex.texImage3[i&3].image_base/* & 0x1FFFFF*/) << 5, + tex.texImage0[i&3].width + 1, tex.texImage0[i&3].height + 1, + tex.texImage0[i&3].format, tex.texTlut[i&3].tmem_offset<<9, + tex.texTlut[i&3].tlut_format, + (tex.texMode0[i&3].min_filter & 3) && (tex.texMode0[i&3].min_filter != 8) && g_ActiveConfig.bUseNativeMips, + (tex.texMode1[i&3].max_lod >> 4)); if (tentry) { + // 0s are probably for no manual wrapping needed. PixelShaderManager::SetTexDims(i, tentry->w, tentry->h, 0, 0); } else - { ERROR_LOG(VIDEO, "error loading texture"); - } } } + // set global constants VertexShaderManager::SetConstants(); PixelShaderManager::SetConstants(); @@ -365,5 +365,4 @@ void Flush() shader_fail: ResetBuffer(); } - } // namespace diff --git a/Source/Plugins/Plugin_VideoDX11/Src/VertexShaderCache.cpp b/Source/Plugins/Plugin_VideoDX11/Src/VertexShaderCache.cpp index 56dfcaf9e6..b1419460db 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/VertexShaderCache.cpp +++ b/Source/Plugins/Plugin_VideoDX11/Src/VertexShaderCache.cpp @@ -33,7 +33,7 @@ #include "XFMemory.h" VertexShaderCache::VSCache VertexShaderCache::vshaders; -const VertexShaderCache::VSCacheEntry* VertexShaderCache::last_entry; +const VertexShaderCache::VSCacheEntry *VertexShaderCache::last_entry; static ID3D11VertexShader* SimpleVertexShader = NULL; static ID3D11VertexShader* ClearVertexShader = NULL; @@ -83,7 +83,7 @@ void SetMultiVSConstant4fv(unsigned int const_number, unsigned int count, const // this class will load the precompiled shaders into our cache class VertexShaderCacheInserter : public LinearDiskCacheReader { public: - void Read(const u8* key, int key_size, const u8* value, int value_size) + void Read(const u8 *key, int key_size, const u8 *value, int value_size) { VERTEXSHADERUID uid; if (key_size != sizeof(uid)) @@ -177,6 +177,9 @@ void VertexShaderCache::Init() if (!File::Exists(File::GetUserPath(D_SHADERCACHE_IDX))) File::CreateDir(File::GetUserPath(D_SHADERCACHE_IDX)); + SETSTAT(stats.numVertexShadersCreated, 0); + SETSTAT(stats.numVertexShadersAlive, 0); + char cache_filename[MAX_PATH]; sprintf(cache_filename, "%sdx11-%s-vs.cache", File::GetUserPath(D_SHADERCACHE_IDX), globals->unique_id); VertexShaderCacheInserter inserter; @@ -214,8 +217,7 @@ bool VertexShaderCache::SetShader(u32 components) memcpy(&last_vertex_shader_uid, &uid, sizeof(VERTEXSHADERUID)); - VSCache::iterator iter; - iter = vshaders.find(uid); + VSCache::iterator iter = vshaders.find(uid); if (iter != vshaders.end()) { iter->second.frameCount = frameCount; @@ -226,7 +228,7 @@ bool VertexShaderCache::SetShader(u32 components) return (entry.shader != NULL); } - const char* code = GenerateVertexShaderCode(components, API_D3D11); + const char *code = GenerateVertexShaderCode(components, API_D3D11); D3DBlob* pbytecode = NULL; D3D::CompileVertexShader(code, (int)strlen(code), &pbytecode); diff --git a/Source/Plugins/Plugin_VideoDX11/Src/main.cpp b/Source/Plugins/Plugin_VideoDX11/Src/main.cpp index 762b4ed000..47c60bcedd 100644 --- a/Source/Plugins/Plugin_VideoDX11/Src/main.cpp +++ b/Source/Plugins/Plugin_VideoDX11/Src/main.cpp @@ -52,19 +52,9 @@ #include "D3DUtil.h" #include "W32Util/Misc.h" #include "EmuWindow.h" -#include "FBManager.h" +#include "FramebufferManager.h" #include "DLCache.h" - -#if defined(DEBUGFAST) -#define DLL_PLUGIN_NAME "Dolphin Direct3D 11 (DebugFast)" -#elif defined(_DEBUG) -#define DLL_PLUGIN_NAME "Dolphin Direct3D 11 (Debug)" -#else -#define DLL_PLUGIN_NAME "Dolphin Direct3D 11" -#endif - - HINSTANCE g_hInstance = NULL; SVideoInitialize g_VideoInitialize; PLUGIN_GLOBALS* globals = NULL; @@ -148,7 +138,7 @@ unsigned int Callback_PeekMessages() } -void UpdateFPSDisplay(const char* text) +void UpdateFPSDisplay(const char *text) { char temp[512]; sprintf_s(temp, 512, "SVN R%s: DX11: %s", svn_rev_str, text); @@ -159,7 +149,13 @@ void GetDllInfo(PLUGIN_INFO* _PluginInfo) { _PluginInfo->Version = 0x0100; _PluginInfo->Type = PLUGIN_TYPE_VIDEO; - sprintf_s(_PluginInfo->Name, 100, DLL_PLUGIN_NAME); +#ifdef DEBUGFAST + sprintf_s(_PluginInfo->Name, 100, "Dolphin Direct3D11 (DebugFast)"); +#elif defined _DEBUG + sprintf_s(_PluginInfo->Name, 100, "Dolphin Direct3D11 (Debug)"); +#else + sprintf_s(_PluginInfo->Name, 100, "Dolphin Direct3D11"); +#endif } void SetDllGlobals(PLUGIN_GLOBALS* _pPluginGlobals) @@ -170,7 +166,7 @@ void SetDllGlobals(PLUGIN_GLOBALS* _pPluginGlobals) void DllAbout(HWND _hParent) { - MessageBoxA(NULL, "DllAbout not implemented, how did you come here? Anyway, report this to the devs.", "Error!", MB_OK); + //DialogBox(g_hInstance,(LPCTSTR)IDD_ABOUT,_hParent,(DLGPROC)AboutProc); } void DllConfig(void *_hParent) @@ -178,11 +174,12 @@ void DllConfig(void *_hParent) DlgSettings_Show(g_hInstance, (HWND)((wxWindow *)_hParent)->GetHandle()); } -void Initialize(void* init) +void Initialize(void *init) { frameCount = 0; - SVideoInitialize* _pVideoInitialize = (SVideoInitialize*)init; - g_VideoInitialize = *_pVideoInitialize; + SVideoInitialize *_pVideoInitialize = (SVideoInitialize*)init; + // Create a shortcut to _pVideoInitialize that can also update it + g_VideoInitialize = *(_pVideoInitialize); InitXFBConvTables(); g_Config.Load((std::string(File::GetUserPath(D_CONFIG_IDX)) + "gfx_dx11.ini").c_str()); @@ -201,14 +198,17 @@ void Initialize(void* init) _pVideoInitialize->pPeekMessages = g_VideoInitialize.pPeekMessages; _pVideoInitialize->pUpdateFPSDisplay = g_VideoInitialize.pUpdateFPSDisplay; + + // Now the window handle is written _pVideoInitialize->pWindowHandle = g_VideoInitialize.pWindowHandle; - OSD::AddMessage("Dolphin Direct3D 11 Video Plugin.", 5000); + OSD::AddMessage("Dolphin Direct3D11 Video Plugin.", 5000); s_PluginInitialized = true; } void Video_Prepare() { + // Better be safe... s_efbAccessRequested = FALSE; s_FifoShuttingDown = FALSE; s_swapRequested = FALSE; @@ -232,24 +232,26 @@ void Video_Prepare() PixelEngine::Init(); DLCache::Init(); - // tell the host that the window is ready + // Tell the host that the window is ready g_VideoInitialize.pCoreMessage(WM_USER_CREATE); } void Shutdown() { + s_PluginInitialized = false; + s_efbAccessRequested = FALSE; s_FifoShuttingDown = FALSE; s_swapRequested = FALSE; // VideoCommon DLCache::Shutdown(); + Fifo_Shutdown(); CommandProcessor::Shutdown(); PixelShaderManager::Shutdown(); VertexShaderManager::Shutdown(); OpcodeDecoder_Shutdown(); VertexLoaderManager::Shutdown(); - Fifo_Shutdown(); // internal interfaces D3D::ShutdownUtils(); @@ -263,13 +265,13 @@ void Shutdown() s_PluginInitialized = false; } -void DoState(unsigned char** ptr, int mode) +void DoState(unsigned char **ptr, int mode) { - // clear texture cache because it might have written to RAM + // Clear texture cache because it might have written to RAM CommandProcessor::FifoCriticalEnter(); TextureCache::Invalidate(false); CommandProcessor::FifoCriticalLeave(); - // no need to clear shader caches + // No need to clear shader caches PointerWrap p(ptr, mode); VideoCommon_DoState(p); } @@ -279,6 +281,7 @@ void EmuStateChange(PLUGIN_EMUSTATE newState) Fifo_RunLoop((newState == PLUGIN_EMUSTATE_PLAY) ? true : false); } +// Enter and exit the video loop void Video_EnterLoop() { Fifo_EnterLoop(g_VideoInitialize); @@ -349,6 +352,7 @@ void Video_BeginField(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight) } } +// Run from the CPU thread (from VideoInterface.cpp) void Video_EndField() { } @@ -358,7 +362,8 @@ void Video_AddMessage(const char* pstr, u32 milliseconds) OSD::AddMessage(pstr, milliseconds); } -void Video_Screenshot(const char* _szFilename) +// Screenshot +void Video_Screenshot(const char *_szFilename) { Renderer::SetScreenshot(_szFilename); } @@ -391,6 +396,7 @@ u32 Video_AccessEFB(EFBAccessType type, u32 x, u32 y, u32 InputData) s_accessEFBArgs.x = x; s_accessEFBArgs.y = y; s_accessEFBArgs.Data = InputData; + Common::AtomicStoreRelease(s_efbAccessRequested, TRUE); if (g_VideoInitialize.bOnThread) @@ -404,6 +410,7 @@ u32 Video_AccessEFB(EFBAccessType type, u32 x, u32 y, u32 InputData) return s_AccessEFBResult; } + return 0; } diff --git a/Source/Plugins/Plugin_VideoDX9/Src/BPFunctions.cpp b/Source/Plugins/Plugin_VideoDX9/Src/BPFunctions.cpp index c06cc5497a..3f116bf2c5 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/BPFunctions.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/BPFunctions.cpp @@ -16,24 +16,26 @@ // http://code.google.com/p/dolphin-emu/ #include "BPFunctions.h" -#include "D3DBase.h" -#include "VideoConfig.h" #include "Common.h" +#include "D3DBase.h" +#include "Debugger/Debugger.h" #include "TextureCache.h" #include "VertexManager.h" #include "VertexShaderManager.h" -#include "Debugger/Debugger.h" -#include "TextureConverter.h" - +#include "VideoConfig.h" bool textureChanged[8]; - const bool renderFog = false; using namespace D3D; namespace BPFunctions { +// ---------------------------------------------- +// State translation lookup tables +// Reference: Yet Another Gamecube Documentation +// ---------------------------------------------- + void FlushPipeline() { @@ -80,9 +82,10 @@ void SetColorMask(const BPCmd &bp) void CopyEFB(const BPCmd &bp, const EFBRectangle &rc, const u32 &address, const bool &fromZBuffer, const bool &isIntensityFmt, const u32 ©fmt, const int &scaleByHalf) { + // bpmem.zcontrol.pixel_format to PIXELFMT_Z24 is when the game wants to copy from ZBuffer (Zbuffer uses 24-bit Format) if (!g_ActiveConfig.bEFBCopyDisable) { - TextureCache::CopyRenderTargetToTexture(address, fromZBuffer, isIntensityFmt, copyfmt, scaleByHalf, rc); + TextureCache::CopyRenderTargetToTexture(address, fromZBuffer, isIntensityFmt, copyfmt, scaleByHalf, rc); } } diff --git a/Source/Plugins/Plugin_VideoDX9/Src/D3DShader.cpp b/Source/Plugins/Plugin_VideoDX9/Src/D3DShader.cpp index c93afda6fc..f3fec31e9d 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/D3DShader.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/D3DShader.cpp @@ -24,22 +24,24 @@ namespace D3D { -// Bytecode->shader. +// bytecode->shader. LPDIRECT3DVERTEXSHADER9 CreateVertexShaderFromByteCode(const u8 *bytecode, int len) { LPDIRECT3DVERTEXSHADER9 v_shader; HRESULT hr = D3D::dev->CreateVertexShader((DWORD *)bytecode, &v_shader); if (FAILED(hr)) - v_shader = 0; + { + PanicAlert("CreateVertexShaderFromByteCode failed from %p (size %d) at %s %d\n", bytecode, len, __FILE__, __LINE__); + v_shader = NULL; + } return v_shader; } -// Code->bytecode. +// code->bytecode. bool CompileVertexShader(const char *code, int len, u8 **bytecode, int *bytecodelen) { - //try to compile - LPD3DXBUFFER shaderBuffer = 0; - LPD3DXBUFFER errorBuffer = 0; + LPD3DXBUFFER shaderBuffer = NULL; + LPD3DXBUFFER errorBuffer = NULL; HRESULT hr = PD3DXCompileShader(code, len, 0, 0, "main", D3D::VertexShaderVersionString(), 0, &shaderBuffer, &errorBuffer, 0); if (FAILED(hr)) @@ -69,18 +71,20 @@ bool CompileVertexShader(const char *code, int len, u8 **bytecode, int *bytecode return SUCCEEDED(hr) ? true : false; } - -// Bytecode->shader. +// bytecode->shader LPDIRECT3DPIXELSHADER9 CreatePixelShaderFromByteCode(const u8 *bytecode, int len) { LPDIRECT3DPIXELSHADER9 p_shader; HRESULT hr = D3D::dev->CreatePixelShader((DWORD *)bytecode, &p_shader); if (FAILED(hr)) - p_shader = 0; + { + PanicAlert("CreatePixelShaderFromByteCode failed at %s %d\n", __FILE__, __LINE__); + p_shader = NULL; + } return p_shader; } - +// code->bytecode bool CompilePixelShader(const char *code, int len, u8 **bytecode, int *bytecodelen) { LPD3DXBUFFER shaderBuffer = 0; @@ -118,28 +122,32 @@ bool CompilePixelShader(const char *code, int len, u8 **bytecode, int *bytecodel return SUCCEEDED(hr) ? true : false; } -LPDIRECT3DVERTEXSHADER9 CompileAndCreateVertexShader(const char *code, int len) { +LPDIRECT3DVERTEXSHADER9 CompileAndCreateVertexShader(const char *code, int len) +{ u8 *bytecode; int bytecodelen; - if (CompileVertexShader(code, len, &bytecode, &bytecodelen)) { + if (CompileVertexShader(code, len, &bytecode, &bytecodelen)) + { LPDIRECT3DVERTEXSHADER9 v_shader = CreateVertexShaderFromByteCode(bytecode, len); delete [] bytecode; return v_shader; - } else { - return 0; } + PanicAlert("Failed to compile and create vertex shader from %p (size %d) at %s %d\n", code, len, __FILE__, __LINE__); + return NULL; } -LPDIRECT3DPIXELSHADER9 CompileAndCreatePixelShader(const char *code, int len) { +LPDIRECT3DPIXELSHADER9 CompileAndCreatePixelShader(const char* code, unsigned int len) +{ u8 *bytecode; int bytecodelen; - if (CompilePixelShader(code, len, &bytecode, &bytecodelen)) { + if (CompilePixelShader(code, len, &bytecode, &bytecodelen)) + { LPDIRECT3DPIXELSHADER9 p_shader = CreatePixelShaderFromByteCode(bytecode, len); delete [] bytecode; return p_shader; - } else { - return 0; } + PanicAlert("Failed to compile and create pixel shader, %s %d\n", __FILE__, __LINE__); + return NULL; } } // namespace diff --git a/Source/Plugins/Plugin_VideoDX9/Src/D3DShader.h b/Source/Plugins/Plugin_VideoDX9/Src/D3DShader.h index d6de8e4ed4..32bdb145e7 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/D3DShader.h +++ b/Source/Plugins/Plugin_VideoDX9/Src/D3DShader.h @@ -30,5 +30,5 @@ namespace D3D // Utility functions LPDIRECT3DVERTEXSHADER9 CompileAndCreateVertexShader(const char *code, int len); - LPDIRECT3DPIXELSHADER9 CompileAndCreatePixelShader(const char *code, int len); + LPDIRECT3DPIXELSHADER9 CompileAndCreatePixelShader(const char *code, unsigned int len); } diff --git a/Source/Plugins/Plugin_VideoDX9/Src/D3DUtil.cpp b/Source/Plugins/Plugin_VideoDX9/Src/D3DUtil.cpp index f94ebc08f2..195a10166f 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/D3DUtil.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/D3DUtil.cpp @@ -63,9 +63,9 @@ int CD3DFont::Init() m_fTextScale = 1.0f; // Draw fonts into texture without scaling // Prepare to create a bitmap - int *pBitmapBits; + unsigned int* pBitmapBits; BITMAPINFO bmi; - ZeroMemory(&bmi.bmiHeader, sizeof(BITMAPINFOHEADER)); + ZeroMemory(&bmi.bmiHeader, sizeof(BITMAPINFOHEADER)); bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); bmi.bmiHeader.biWidth = (int)m_dwTexWidth; bmi.bmiHeader.biHeight = -(int)m_dwTexHeight; @@ -74,8 +74,8 @@ int CD3DFont::Init() bmi.bmiHeader.biBitCount = 32; // Create a DC and a bitmap for the font - HDC hDC = CreateCompatibleDC(NULL); - HBITMAP hbmBitmap = CreateDIBSection(hDC, &bmi, DIB_RGB_COLORS, (VOID**)&pBitmapBits, NULL, 0); + HDC hDC = CreateCompatibleDC(NULL); + HBITMAP hbmBitmap = CreateDIBSection(hDC, &bmi, DIB_RGB_COLORS, (void**)&pBitmapBits, NULL, 0); SetMapMode(hDC, MM_TEXT); // Create a font. By specifying ANTIALIASED_QUALITY, we might get an @@ -99,7 +99,7 @@ int CD3DFont::Init() SetBkColor (hDC, 0); SetTextAlign(hDC, TA_TOP); - // Loop through all printable character and output them to the bitmap.. + // Loop through all printable characters and output them to the bitmap // Meanwhile, keep track of the corresponding tex coords for each character. int x = 0, y = 0; char str[2] = "\0"; @@ -120,10 +120,12 @@ int CD3DFont::Init() m_fTexCoords[c][2] = ((float)(x+0+size.cx))/m_dwTexWidth; m_fTexCoords[c][3] = ((float)(y+0+size.cy))/m_dwTexHeight; - x += size.cx + 3; //3 to work around annoying ij conflict (part of the j ends up with the i) + x += size.cx + 3; // 3 to work around annoying ij conflict (part of the j ends up with the i) } // Create a new texture for the font + // possible optimization: store the converted data in a buffer and fill the texture on creation. + // That way, we can use a static texture hr = dev->CreateTexture(m_dwTexWidth, m_dwTexHeight, 1, D3DUSAGE_DYNAMIC, D3DFMT_A4R4G4B4, D3DPOOL_DEFAULT, &m_pTexture, NULL); if (FAILED(hr)) @@ -245,7 +247,7 @@ int CD3DFont::DrawTextScaled(float x, float y, float fXScale, float fYScale, flo float invLineHeight = 1.0f / ((m_fTexCoords[0][3] - m_fTexCoords[0][1]) * m_dwTexHeight); // Fill vertex buffer FONT2DVERTEX* pVertices; - int dwNumTriangles = 0L; + int dwNumTriangles = 0L; m_pVB->Lock(0, 0, (void**)&pVertices, D3DLOCK_DISCARD); const char *oldstrText=strText; @@ -296,7 +298,7 @@ int CD3DFont::DrawTextScaled(float x, float y, float fXScale, float fYScale, flo if (c < (' ')) continue; - c-=32; + c -= 32; float tx1 = m_fTexCoords[c][0]; float ty1 = m_fTexCoords[c][1]; float tx2 = m_fTexCoords[c][2]; @@ -329,7 +331,6 @@ int CD3DFont::DrawTextScaled(float x, float y, float fXScale, float fYScale, flo m_pVB->Lock(0, 0, (void**)&pVertices, D3DLOCK_DISCARD); dwNumTriangles = 0; } - sx += w + spacing*fXScale*vpWidth; } diff --git a/Source/Plugins/Plugin_VideoDX9/Src/Debugger/Debugger.cpp b/Source/Plugins/Plugin_VideoDX9/Src/Debugger/Debugger.cpp index db939a6b6c..1fdeee1aae 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/Debugger/Debugger.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/Debugger/Debugger.cpp @@ -349,15 +349,15 @@ static void DX9DebuggerUpdateScreen() D3D::dev->SetRenderTarget(0, D3D::GetBackBufferSurface()); D3D::dev->SetDepthStencilSurface(NULL); - D3D::dev->StretchRect(FBManager.GetEFBColorRTSurface(), NULL, + D3D::dev->StretchRect(g_framebufferManager.GetEFBColorRTSurface(), NULL, D3D::GetBackBufferSurface(), NULL, D3DTEXF_LINEAR); D3D::dev->EndScene(); D3D::dev->Present(NULL, NULL, NULL, NULL); - D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); + D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); D3D::dev->BeginScene(); } else diff --git a/Source/Plugins/Plugin_VideoDX9/Src/EmuWindow.cpp b/Source/Plugins/Plugin_VideoDX9/Src/EmuWindow.cpp index 9cf1dfc213..c06fecf14a 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/EmuWindow.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/EmuWindow.cpp @@ -145,14 +145,6 @@ void OSDMenu(WPARAM wParam) case '3': OSDChoice = 1; // Toggle native resolution -/* - if (!(g_Config.bNativeResolution || g_Config.b2xResolution)) - g_Config.bNativeResolution = true; - else if (g_Config.bNativeResolution && Renderer::AllowCustom()) - { g_Config.bNativeResolution = false; if (Renderer::Allow2x()) {g_Config.b2xResolution = true;} } - else if (Renderer::AllowCustom()) - g_Config.b2xResolution = false; -*/ OSDInternalW = D3D::GetBackBufferWidth(); OSDInternalH = D3D::GetBackBufferHeight(); break; @@ -224,6 +216,7 @@ HWND Create(HWND hParent, HINSTANCE hInstance, const TCHAR *title) // TODO: // 1. Remove redundant window manipulation, // 2. Make DX9 in fullscreen can be overlapped by other dialogs + // 3. Request window sizes which actually make the client area map to a common resolution HWND Ret; int x=0, y=0, width=640, height=480; g_VideoInitialize.pRequestWindowSize(x, y, width, height); diff --git a/Source/Plugins/Plugin_VideoDX9/Src/FramebufferManager.cpp b/Source/Plugins/Plugin_VideoDX9/Src/FramebufferManager.cpp index 3fa1bbed49..ab83304b82 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/FramebufferManager.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/FramebufferManager.cpp @@ -26,7 +26,7 @@ #undef CHECK #define CHECK(hr, Message, ...) if (FAILED(hr)) { PanicAlert(__FUNCTION__ "Failed in %s at line %d: " Message, __FILE__, __LINE__, __VA_ARGS__); } -FramebufferManager FBManager; +FramebufferManager g_framebufferManager; LPDIRECT3DSURFACE9 FramebufferManager::GetEFBColorRTSurface() { @@ -313,7 +313,6 @@ void FramebufferManager::copyToVirtualXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight LPDIRECT3DTEXTURE9 xfbTexture; HRESULT hr = 0; - VirtualXFBListType::iterator it = findVirtualXFB(xfbAddr, fbWidth, fbHeight); if (it == m_virtualXFBList.end() && (int)m_virtualXFBList.size() >= MAX_VIRTUAL_XFB) @@ -393,8 +392,7 @@ void FramebufferManager::copyToVirtualXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight m_virtualXFBList.push_front(newVirt); } - // Copy EFB to XFB texture - + // Copy EFB data to XFB and restore render target again if(!xfbTexture) return; LPDIRECT3DTEXTURE9 read_texture = GetEFBColorTexture(sourceRc); diff --git a/Source/Plugins/Plugin_VideoDX9/Src/FramebufferManager.h b/Source/Plugins/Plugin_VideoDX9/Src/FramebufferManager.h index d99f3e54f6..bed3c53acf 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/FramebufferManager.h +++ b/Source/Plugins/Plugin_VideoDX9/Src/FramebufferManager.h @@ -107,7 +107,6 @@ public: void Destroy(); void CopyToXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight, const EFBRectangle& sourceRc); - const XFBSource** GetXFBSource(u32 xfbAddr, u32 fbWidth, u32 fbHeight, u32 &xfbCount); LPDIRECT3DTEXTURE9 GetEFBColorTexture(const EFBRectangle& sourceRc); @@ -168,6 +167,6 @@ private: D3DFORMAT s_efb_depth_ReadBuffer_Format;//Format of the Depth color Read Surface }; -extern FramebufferManager FBManager; +extern FramebufferManager g_framebufferManager; #endif diff --git a/Source/Plugins/Plugin_VideoDX9/Src/Globals.h b/Source/Plugins/Plugin_VideoDX9/Src/Globals.h index 6b02dd3c80..f1c13d728c 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/Globals.h +++ b/Source/Plugins/Plugin_VideoDX9/Src/Globals.h @@ -28,4 +28,4 @@ // A global plugin specification extern PLUGIN_GLOBALS* globals; -#endif // _GLOBALS_H_ +#endif // _GLOBALS_H_ \ No newline at end of file diff --git a/Source/Plugins/Plugin_VideoDX9/Src/NativeVertexFormat.cpp b/Source/Plugins/Plugin_VideoDX9/Src/NativeVertexFormat.cpp index f584066ac0..18f92bb50e 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/NativeVertexFormat.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/NativeVertexFormat.cpp @@ -27,7 +27,6 @@ #include "CPMemory.h" #include "NativeVertexFormat.h" - class D3DVertexFormat : public NativeVertexFormat { LPDIRECT3DVERTEXDECLARATION9 d3d_decl; @@ -76,12 +75,13 @@ D3DDECLTYPE VarToD3D(VarType t, int size) D3DDECLTYPE_UNUSED, D3DDECLTYPE_UBYTE4N, D3DDECLTYPE_SHORT4N, D3DDECLTYPE_USHORT4N, D3DDECLTYPE_FLOAT4, }; D3DDECLTYPE retval = D3DDECLTYPE_UNUSED; - switch (size) { + switch (size) + { case 1: retval = lookup1[t]; break; case 2: retval = lookup2[t]; break; case 3: retval = lookup3[t]; break; case 4: retval = lookup4[t]; break; - default: PanicAlert("VarToD3D: size wrong (%i)", size); break; + default: break; } if (retval == D3DDECLTYPE_UNUSED) { PanicAlert("VarToD3D: Invalid type/size combo %i , %i", (int)t, size); diff --git a/Source/Plugins/Plugin_VideoDX9/Src/PixelShaderCache.cpp b/Source/Plugins/Plugin_VideoDX9/Src/PixelShaderCache.cpp index eca26d8bdd..e686fc6e91 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/PixelShaderCache.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/PixelShaderCache.cpp @@ -239,14 +239,13 @@ void PixelShaderCache::Init() char cache_filename[MAX_PATH]; sprintf(cache_filename, "%sdx9-%s-ps.cache", File::GetUserPath(D_SHADERCACHE_IDX), globals->unique_id); PixelShaderCacheInserter inserter; - int read_items = g_ps_disk_cache.OpenAndRead(cache_filename, &inserter); + g_ps_disk_cache.OpenAndRead(cache_filename, &inserter); } // ONLY to be used during shutdown. void PixelShaderCache::Clear() { - PSCache::iterator iter = PixelShaders.begin(); - for (; iter != PixelShaders.end(); ++iter) + for (PSCache::iterator iter = PixelShaders.begin(); iter != PixelShaders.end(); iter++) iter->second.Destroy(); PixelShaders.clear(); @@ -279,19 +278,16 @@ bool PixelShaderCache::SetShader(bool dstAlpha,u32 components) PIXELSHADERUID uid; GetPixelShaderId(&uid, dstAlpha); - // Is the shader already set? + // Check if the shader is already set if (uid == last_pixel_shader_uid && PixelShaders[uid].frameCount == frameCount) { PSCache::const_iterator iter = PixelShaders.find(uid); - if (iter != PixelShaders.end() && iter->second.shader) - return true; // Sure, we're done. - else - return false; // ?? something is wrong. + return (iter != PixelShaders.end() && iter->second.shader); } memcpy(&last_pixel_shader_uid, &uid, sizeof(PIXELSHADERUID)); - - // Is the shader already in the cache? + + // Check if the shader is already in the cache PSCache::iterator iter; iter = PixelShaders.find(uid); if (iter != PixelShaders.end()) @@ -311,14 +307,14 @@ bool PixelShaderCache::SetShader(bool dstAlpha,u32 components) return false; } - // OK, need to generate and compile it. + // Need to compile a new shader const char *code = GeneratePixelShaderCode(dstAlpha, API_D3D9,components); u32 code_hash = HashAdler32((const u8 *)code, strlen(code)); unique_shaders.insert(code_hash); SETSTAT(stats.numUniquePixelShaders, unique_shaders.size()); - #if defined(_DEBUG) || defined(DEBUGFAST) +#if defined(_DEBUG) || defined(DEBUGFAST) if (g_ActiveConfig.iLog & CONF_SAVESHADERS && code) { static int counter = 0; char szTemp[MAX_PATH]; @@ -326,7 +322,7 @@ bool PixelShaderCache::SetShader(bool dstAlpha,u32 components) SaveData(szTemp, code); } - #endif +#endif u8 *bytecode = 0; int bytecodelen = 0; @@ -342,7 +338,7 @@ bool PixelShaderCache::SetShader(bool dstAlpha,u32 components) return false; } - // Here we have the UID and the byte code. Insert it into the disk cache. + // Insert the bytecode into the caches g_ps_disk_cache.Append((u8 *)&uid, sizeof(uid), bytecode, bytecodelen); g_ps_disk_cache.Sync(); @@ -352,7 +348,8 @@ bool PixelShaderCache::SetShader(bool dstAlpha,u32 components) return result; } -bool PixelShaderCache::InsertByteCode(const PIXELSHADERUID &uid, const u8 *bytecode, int bytecodelen, bool activate) { +bool PixelShaderCache::InsertByteCode(const PIXELSHADERUID &uid, const u8 *bytecode, int bytecodelen, bool activate) +{ LPDIRECT3DPIXELSHADER9 shader = D3D::CreatePixelShaderFromByteCode(bytecode, bytecodelen); // Make an entry in the table @@ -368,7 +365,7 @@ bool PixelShaderCache::InsertByteCode(const PIXELSHADERUID &uid, const u8 *bytec } INCSTAT(stats.numPixelShadersCreated); - SETSTAT(stats.numPixelShadersAlive, (int)PixelShaders.size()); + SETSTAT(stats.numPixelShadersAlive, PixelShaders.size()); if (activate) { D3D::SetPixelShader(shader); diff --git a/Source/Plugins/Plugin_VideoDX9/Src/Render.cpp b/Source/Plugins/Plugin_VideoDX9/Src/Render.cpp index 97d17955b7..2d6338a247 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/Render.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/Render.cpp @@ -51,7 +51,7 @@ #include "debugger/debugger.h" -int s_fps=0; +static int s_fps = 0; static bool WindowResized; static int s_target_width; @@ -75,14 +75,14 @@ static float EFByScale; static int s_recordWidth; static int s_recordHeight; -static bool s_LastFrameDumped; -static bool s_AVIDumping; +static bool s_bLastFrameDumped; +static bool s_bAVIDumping; static u32 s_blendMode; static u32 s_LastAA; static u32 s_LastEFBScale; static bool IS_AMD; -static bool XFBWrited; +static bool XFBWrited = false; // used extern by other files. need to clean this up at some point. int frameCount; @@ -120,6 +120,24 @@ static const D3DBLEND d3dDestFactors[8] = 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, @@ -223,7 +241,7 @@ void SetupDeviceObjects() { D3D::font.Init(); VertexLoaderManager::Init(); - FBManager.Create(); + g_framebufferManager.Create(); VertexShaderManager::Dirty(); PixelShaderManager::Dirty(); @@ -243,7 +261,7 @@ void TeardownDeviceObjects() ScreenShootMEMSurface = NULL; D3D::dev->SetRenderTarget(0, D3D::GetBackBufferSurface()); D3D::dev->SetDepthStencilSurface(D3D::GetBackBufferDepthSurface()); - FBManager.Destroy(); + g_framebufferManager.Destroy(); D3D::font.Shutdown(); TextureCache::Invalidate(false); VertexLoaderManager::Shutdown(); @@ -252,7 +270,8 @@ void TeardownDeviceObjects() TextureConverter::Shutdown(); } -bool Renderer::Init() +// Init functions +bool Renderer::Init() { st = new char[32768]; UpdateActiveConfig(); @@ -276,6 +295,8 @@ bool Renderer::Init() fullScreenRes, backbuffer_ms_mode, false); IS_AMD = D3D::IsATIDevice(); + + // Decide frambuffer size s_backbuffer_width = D3D::GetBackBufferWidth(); s_backbuffer_height = D3D::GetBackBufferHeight(); @@ -323,8 +344,8 @@ bool Renderer::Init() s_Fulltarget_width = s_target_width; s_Fulltarget_height = s_target_height; - s_LastFrameDumped = false; - s_AVIDumping = false; + s_bLastFrameDumped = false; + s_bAVIDumping = false; // We're not using fixed function. // Let's just set the matrices to identity to be sure. @@ -348,8 +369,8 @@ bool Renderer::Init() D3D::dev->SetViewport(&vp); D3D::dev->Clear(0, NULL, D3DCLEAR_TARGET, 0x0, 0, 0); - D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); + D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); vp.X = (s_Fulltarget_width - s_target_width) / 2; vp.Y = (s_Fulltarget_height - s_target_height) / 2; vp.Width = s_target_width; @@ -369,28 +390,60 @@ void Renderer::Shutdown() D3D::Present(); D3D::Close(); - if (s_AVIDumping) + if (s_bAVIDumping) { AVIDump::Stop(); } delete [] st; } -int Renderer::GetTargetWidth() { return s_target_width; } -int Renderer::GetTargetHeight() { return s_target_height; } -int Renderer::GetFullTargetWidth() { return s_Fulltarget_width; } -int Renderer::GetFullTargetHeight() { return s_Fulltarget_height; } -float Renderer::GetTargetScaleX() { return EFBxScale; } -float Renderer::GetTargetScaleY() { return EFByScale; } +// Return the rendering target width and height +int Renderer::GetTargetWidth() +{ + return s_target_width; +} -float Renderer::GetXFBScaleX() { return xScale; } -float Renderer::GetXFBScaleY() { return yScale; } +int Renderer::GetTargetHeight() +{ + return s_target_height; +} +int Renderer::GetFullTargetWidth() +{ + return s_Fulltarget_width; +} +int Renderer::GetFullTargetHeight() +{ + return s_Fulltarget_height; +} + +float Renderer::GetTargetScaleX() +{ + return EFBxScale; +} + +float Renderer::GetTargetScaleY() +{ + return EFByScale; +} + +float Renderer::GetXFBScaleX() +{ + return xScale; +} + +float Renderer::GetXFBScaleY() +{ + return yScale; +} + +// Return the framebuffer size int Renderer::GetFrameBufferWidth() { return s_backbuffer_width; } + int Renderer::GetFrameBufferHeight() { return s_backbuffer_height; @@ -399,7 +452,7 @@ int Renderer::GetFrameBufferHeight() // Create On-Screen-Messages void Renderer::DrawDebugText() { - // OSD Menu messages + // OSD menu messages if (g_ActiveConfig.bOSDHotKey) { if (OSDChoice > 0) @@ -434,9 +487,12 @@ void Renderer::DrawDebugText() std::string OSDM3 = g_ActiveConfig.bEFBCopyDisable ? "Disabled" : g_ActiveConfig.bCopyEFBToTexture ? "To Texture" : "To RAM"; - // If there is more text than this we will have a collission + // If there is more text than this we will have a collision if (g_ActiveConfig.bShowFPS) - { T1 += "\n\n"; T2 += "\n\n"; } + { + T1 += "\n\n"; + T2 += "\n\n"; + } // The rows T0.push_back(StringFromFormat("3: Internal Resolution: %s\n", OSDM1.c_str())); @@ -504,10 +560,8 @@ void formatBufferDump(const char *in, char *out, int w, int h, int p) void CheckForResize() { while (EmuWindow::IsSizing()) - { Sleep(10); - } - + if (EmuWindow::GetParentWnd()) { // Re-stretch window to parent window size again, if it has a parent window. @@ -522,7 +576,8 @@ void CheckForResize() GetClientRect(EmuWindow::GetWnd(), &rcWindow); int client_width = rcWindow.right - rcWindow.left; int client_height = rcWindow.bottom - rcWindow.top; - // Sanity check. + + // Sanity check if ((client_width != s_backbuffer_width || client_height != s_backbuffer_height) && client_width >= 4 && client_height >= 4) @@ -539,20 +594,18 @@ void CheckForResize() } } - - void Renderer::RenderToXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight, const EFBRectangle& sourceRc) { if (!fbWidth || !fbHeight) return; VideoFifo_CheckEFBAccess(); - VideoFifo_CheckSwapRequestAt(xfbAddr, fbWidth, fbHeight); + VideoFifo_CheckSwapRequestAt(xfbAddr, fbWidth, fbHeight); XFBWrited = true; // XXX: Without the VI, how would we know what kind of field this is? So // just use progressive. if (g_ActiveConfig.bUseXFB) { - FBManager.CopyToXFB(xfbAddr, fbWidth, fbHeight, sourceRc); + g_framebufferManager.CopyToXFB(xfbAddr, fbWidth, fbHeight, sourceRc); } else { @@ -618,7 +671,7 @@ bool Renderer::SetScissorRect() return false; } -void Renderer::SetColorMask() +void Renderer::SetColorMask() { DWORD color_mask = 0; if (bpmem.blendmode.alphaupdate) @@ -644,18 +697,18 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) // Get the working buffer LPDIRECT3DSURFACE9 pBuffer = (type == PEEK_Z || type == POKE_Z) ? - FBManager.GetEFBDepthRTSurface() : FBManager.GetEFBColorRTSurface(); + g_framebufferManager.GetEFBDepthRTSurface() : g_framebufferManager.GetEFBColorRTSurface(); // Get the temporal buffer to move 1pixel data LPDIRECT3DSURFACE9 RBuffer = (type == PEEK_Z || type == POKE_Z) ? - FBManager.GetEFBDepthReadSurface() : FBManager.GetEFBColorReadSurface(); + g_framebufferManager.GetEFBDepthReadSurface() : g_framebufferManager.GetEFBColorReadSurface(); // Get the memory buffer that can be locked LPDIRECT3DSURFACE9 pOffScreenBuffer = (type == PEEK_Z || type == POKE_Z) ? - FBManager.GetEFBDepthOffScreenRTSurface() : FBManager.GetEFBColorOffScreenRTSurface(); + g_framebufferManager.GetEFBDepthOffScreenRTSurface() : g_framebufferManager.GetEFBColorOffScreenRTSurface(); // Get the buffer format D3DFORMAT BufferFormat = (type == PEEK_Z || type == POKE_Z) ? - FBManager.GetEFBDepthRTSurfaceFormat() : FBManager.GetEFBColorRTSurfaceFormat(); + g_framebufferManager.GetEFBDepthRTSurfaceFormat() : g_framebufferManager.GetEFBColorRTSurfaceFormat(); D3DFORMAT ReadBufferFormat = (type == PEEK_Z || type == POKE_Z) ? - FBManager.GetEFBDepthReadSurfaceFormat() : BufferFormat; + g_framebufferManager.GetEFBDepthReadSurfaceFormat() : BufferFormat; if (BufferFormat == D3DFMT_D24X8) return 0; @@ -667,8 +720,7 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) PanicAlert("No %s!", (type == PEEK_Z || type == POKE_Z) ? "Z-Buffer" : "Color EFB"); return 0; } - // Get the rectangular target region covered by the EFB pixel. - + // Get the rectangular target region covered by the EFB pixel EFBRectangle efbPixelRc; efbPixelRc.left = x; efbPixelRc.top = y; @@ -700,6 +752,7 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) RectToLock.bottom--; if ((RectToLock.right - RectToLock.left) > 4) RectToLock.left++; + ResetAPIState(); // Reset any game specific settings hr = D3D::dev->SetDepthStencilSurface(NULL); hr = D3D::dev->SetRenderTarget(0, RBuffer); @@ -727,7 +780,7 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) colmat[0] = colmat[5] = colmat[10] = 1.0f; PixelShaderManager::SetColorMatrix(colmat, fConstAdd); // set transformation EFBRectangle source_rect; - LPDIRECT3DTEXTURE9 read_texture = FBManager.GetEFBDepthTexture(source_rect); + LPDIRECT3DTEXTURE9 read_texture = g_framebufferManager.GetEFBDepthTexture(source_rect); D3D::ChangeSamplerState(0, D3DSAMP_MINFILTER, D3DTEXF_POINT); @@ -742,8 +795,8 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) D3D::RefreshSamplerState(0, D3DSAMP_MINFILTER); - hr = D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - hr = D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); + hr = D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + hr = D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); RestoreAPIState(); RectToLock.bottom = 4; RectToLock.left = 0; @@ -771,8 +824,7 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) PanicAlert("Unable to copy data to mem buffer"); return 0; } - - + // The surface is good.. lock it if ((hr = pOffScreenBuffer->LockRect(&drect, &RectToLock, D3DLOCK_READONLY)) != D3D_OK) @@ -780,37 +832,48 @@ u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) PanicAlert("ERROR: %s", hr == D3DERR_WASSTILLDRAWING ? "Still drawing" : hr == D3DERR_INVALIDCALL ? "Invalid call" : "w00t"); return 0; } - - switch (type) { - case PEEK_Z: - { - switch (ReadBufferFormat) - { - case D3DFMT_R32F: - val = ((float*)drect.pBits)[6]; - break; - default: - float ffrac = 1.0f/255.0f; - z = ((u32*)drect.pBits)[6]; - val = ((float)((z>>16) & 0xFF)) * ffrac; - ffrac*= 1 / 255.0f; - val += ((float)((z>>8) & 0xFF)) * ffrac; - ffrac*= 1 / 255.0f; - val += ((float)(z & 0xFF)) * ffrac; - break; - }; - z = ((u32)(val * 0xffffff)); - } - break; - case PEEK_COLOR: - z = ((u32 *)drect.pBits)[0]; - break; - case POKE_COLOR: + switch (type) + { + case PEEK_Z: + { + switch (ReadBufferFormat) + { + case D3DFMT_R32F: + val = ((float*)drect.pBits)[6]; + break; + default: + float ffrac = 1.0f/255.0f; + z = ((u32*)drect.pBits)[6]; + val = ((float)((z>>16) & 0xFF)) * ffrac; + ffrac*= 1 / 255.0f; + val += ((float)((z>>8) & 0xFF)) * ffrac; + ffrac*= 1 / 255.0f; + val += ((float)(z & 0xFF)) * ffrac; + break; + }; + z = ((u32)(val * 0xffffff)); + } + break; + + case POKE_Z: + // TODO: Implement + break; + + case PEEK_COLOR: + z = ((u32*)drect.pBits)[0]; + break; + + case POKE_COLOR: + // TODO: Implement. One way is to draw a tiny pixel-sized rectangle at + // the exact location. Note: EFB pokes are susceptible to Z-buffering + // and perhaps blending. + //WARN_LOG(VIDEOINTERFACE, "This is probably some kind of software rendering"); + break; // TODO: Implement POKE_Z and POKE_COLOR - default: - break; + default: + break; } pOffScreenBuffer->UnlockRect(); @@ -905,10 +968,10 @@ void UpdateViewport() { D3D::dev->SetRenderTarget(0, D3D::GetBackBufferSurface()); D3D::dev->SetDepthStencilSurface(D3D::GetBackBufferDepthSurface()); - FBManager.Destroy(); - FBManager.Create(); - D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); + g_framebufferManager.Destroy(); + g_framebufferManager.Create(); + D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); } } vp.X = X; @@ -978,7 +1041,7 @@ void Renderer::SetBlendMode(bool forceUpdate) } static bool RightFrame = false; - +// This function has the final picture. We adjust the aspect ratio here. void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,const EFBRectangle& rc) { if (g_bSkipCurrentFrame || (!XFBWrited && !g_ActiveConfig.bUseRealXFB) || !fbWidth || !fbHeight) @@ -989,10 +1052,10 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons // this function is called after the XFB field is changed, not after // EFB is copied to XFB. In this way, flickering is reduced in games // and seems to also give more FPS in ZTP - + if (field == FIELD_LOWER) xfbAddr -= fbWidth * 2; u32 xfbCount = 0; - const XFBSource** xfbSourceList = FBManager.GetXFBSource(xfbAddr, fbWidth, fbHeight, xfbCount); + const XFBSource** xfbSourceList = g_framebufferManager.GetXFBSource(xfbAddr, fbWidth, fbHeight, xfbCount); if ((!xfbSourceList || xfbCount == 0) && g_ActiveConfig.bUseXFB && !g_ActiveConfig.bUseRealXFB) { g_VideoInitialize.pCopiedToXFB(false); @@ -1019,7 +1082,8 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons RightFrame = true; } } - // Set the backbuffer as the rendering target + + // Prepare to copy the XFBs to our backbuffer D3D::dev->SetDepthStencilSurface(NULL); D3D::dev->SetRenderTarget(0, D3D::GetBackBufferSurface()); @@ -1068,13 +1132,13 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons // draw each xfb source for (u32 i = 0; i < xfbCount; ++i) { - xfbSource = xfbSourceList[i]; + xfbSource = xfbSourceList[i]; MathUtil::Rectangle sourceRc; sourceRc.left = 0; sourceRc.top = 0; sourceRc.right = xfbSource->texWidth; - sourceRc.bottom = xfbSource->texHeight; + sourceRc.bottom = xfbSource->texHeight; MathUtil::Rectangle drawRc; @@ -1085,11 +1149,10 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons int xfbWidth = xfbSource->srcWidth; int hOffset = ((s32)xfbSource->srcAddr - (s32)xfbAddr) / ((s32)fbWidth * 2); - drawRc.bottom = 1.0f - 2.0f * ((hOffset) / (float)fbHeight); - drawRc.top = 1.0f - 2.0f * ((hOffset + xfbHeight) / (float)fbHeight); + drawRc.bottom = 1.0f - (2.0f * (hOffset) / (float)fbHeight); + drawRc.top = 1.0f - (2.0f * (hOffset + xfbHeight) / (float)fbHeight); drawRc.left = -(xfbWidth / (float)fbWidth); drawRc.right = (xfbWidth / (float)fbWidth); - if (!g_ActiveConfig.bAutoScale) { @@ -1117,7 +1180,7 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons else { TargetRectangle targetRc = Renderer::ConvertEFBRectangle(rc); - LPDIRECT3DTEXTURE9 read_texture = FBManager.GetEFBColorTexture(rc); + LPDIRECT3DTEXTURE9 read_texture = g_framebufferManager.GetEFBColorTexture(rc); D3D::drawShadedTexQuad(read_texture,targetRc.AsRECT(),Renderer::GetFullTargetWidth(),Renderer::GetFullTargetHeight(),Width,Height,PixelShaderCache::GetColorCopyProgram(g_Config.iMultisampleMode),VertexShaderCache::GetSimpleVertexShader(g_Config.iMultisampleMode)); } D3D::RefreshSamplerState(0, D3DSAMP_MINFILTER); @@ -1134,7 +1197,7 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons vp.MinZ = 0.0f; vp.MaxZ = 1.0f; D3D::dev->SetViewport(&vp); - if(s_bScreenshot) + if (s_bScreenshot) { s_criticalScreenshot.Enter(); HRESULT hr = D3D::dev->GetRenderTargetData(D3D::GetBackBufferSurface(),ScreenShootMEMSurface); @@ -1153,12 +1216,12 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons if (g_ActiveConfig.bDumpFrames) { HRESULT hr = D3D::dev->GetRenderTargetData(D3D::GetBackBufferSurface(),ScreenShootMEMSurface); - if (!s_LastFrameDumped) + if (!s_bLastFrameDumped) { s_recordWidth = dst_rect.GetWidth(); s_recordHeight = dst_rect.GetHeight(); - s_AVIDumping = AVIDump::Start(EmuWindow::GetParentWnd(), s_recordWidth, s_recordHeight); - if (!s_AVIDumping) + s_bAVIDumping = AVIDump::Start(EmuWindow::GetParentWnd(), s_recordWidth, s_recordHeight); + if (!s_bAVIDumping) { PanicAlert("Error dumping frames to AVI."); } @@ -1169,7 +1232,7 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons OSD::AddMessage(msg, 2000); } } - if (s_AVIDumping) + if (s_bAVIDumping) { D3DLOCKED_RECT rect; if (SUCCEEDED(ScreenShootMEMSurface->LockRect(&rect, dst_rect.AsRECT(), D3DLOCK_NO_DIRTY_UPDATE | D3DLOCK_NOSYSLOCK | D3DLOCK_READONLY))) @@ -1181,16 +1244,17 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons ScreenShootMEMSurface->UnlockRect(); } } - s_LastFrameDumped = true; + s_bLastFrameDumped = true; } else { - if (s_LastFrameDumped && s_AVIDumping) + if (s_bLastFrameDumped && s_bAVIDumping) { AVIDump::Stop(); - s_AVIDumping = false; + s_bAVIDumping = false; + OSD::AddMessage("Stop dumping frames to AVI", 2000); } - s_LastFrameDumped = false; + s_bLastFrameDumped = false; } // Finish up the current frame, print some stats @@ -1213,22 +1277,19 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons D3D::font.DrawTextScaled(0, 30, 20, 20, 0.0f, 0xFF00FFFF, st, false); } - OSD::DrawMessages(); - D3D::EndFrame(); - frameCount++; DLCache::ProgressiveCleanup(); TextureCache::Cleanup(); - // Make any new configuration settings active. + // Enable any configuration changes UpdateActiveConfig(); WindowResized = false; CheckForResize(); - + bool xfbchanged = false; - + if (s_XFB_width != fbWidth || s_XFB_height != fbHeight) { xfbchanged = true; @@ -1288,13 +1349,14 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons } else { - FBManager.Destroy(); - FBManager.Create(); + g_framebufferManager.Destroy(); + g_framebufferManager.Create(); } - D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); + D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); } + // Place messages on the picture, then copy it to the screen // --------------------------------------------------------------------- // Count FPS. // ------------- @@ -1311,20 +1373,26 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons // Begin new frame // Set default viewport and scissor, for the clear to work correctly + // New frame stats.ResetFrame(); // Flip/present backbuffer to frontbuffer here D3D::Present(); D3D::BeginFrame(); Renderer::RestoreAPIState(); - D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); + D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); UpdateViewport(); VertexShaderManager::SetViewportChanged(); + // For testing zbuffer targets. + // Renderer::SetZBufferRender(); + // SaveTexture("tex.tga", GL_TEXTURE_RECTANGLE_ARB, s_FakeZTarget, + // GetTargetWidth(), GetTargetHeight()); g_VideoInitialize.pCopiedToXFB(XFBWrited || g_ActiveConfig.bUseRealXFB); XFBWrited = false; } +// ALWAYS call RestoreAPIState for each ResetAPIState call you're doing void Renderer::ResetAPIState() { D3D::SetRenderState(D3DRS_SCISSORTESTENABLE, FALSE); @@ -1365,6 +1433,7 @@ void Renderer::SetDepthMode() } else { + // if the test is disabled write is disabled too D3D::SetRenderState(D3DRS_ZENABLE, FALSE); D3D::SetRenderState(D3DRS_ZWRITEENABLE, FALSE); // ?? } diff --git a/Source/Plugins/Plugin_VideoDX9/Src/TextureCache.cpp b/Source/Plugins/Plugin_VideoDX9/Src/TextureCache.cpp index a677380423..24add2eb2a 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/TextureCache.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/TextureCache.cpp @@ -79,6 +79,30 @@ void TextureCache::Invalidate(bool shutdown) HiresTextures::Shutdown(); } +void TextureCache::Shutdown() +{ + Invalidate(true); + FreeMemoryPages(temp, TEMP_SIZE); + temp = NULL; +} + +void TextureCache::Cleanup() +{ + TexCache::iterator iter = textures.begin(); + while (iter != textures.end()) + { + if (frameCount > TEXTURE_KILL_THRESHOLD + iter->second.frameCount) + { + iter->second.Destroy(false); + iter = textures.erase(iter); + } + else + { + ++iter; + } + } +} + void TextureCache::InvalidateRange(u32 start_address, u32 size) { TexCache::iterator iter = textures.begin(); @@ -90,9 +114,9 @@ void TextureCache::InvalidateRange(u32 start_address, u32 size) iter->second.Destroy(false); textures.erase(iter++); } - else + else { - ++iter; + ++iter; } } } @@ -120,53 +144,54 @@ int TextureCache::TCacheEntry::IntersectsMemoryRange(u32 range_address, u32 rang return 0; } -void TextureCache::Shutdown() -{ - Invalidate(true); - FreeMemoryPages(temp, TEMP_SIZE); - temp = NULL; -} - -void TextureCache::Cleanup() -{ - TexCache::iterator iter = textures.begin(); - while (iter != textures.end()) - { - if (frameCount > TEXTURE_KILL_THRESHOLD + iter->second.frameCount) - { - iter->second.Destroy(false); - textures.erase(iter++); - } - else - { - ++iter; - } - } -} - TextureCache::TCacheEntry *TextureCache::Load(int stage, u32 address, int width, int height, int tex_format, int tlutaddr, int tlutfmt,bool UseNativeMips, int maxlevel) { + // notes (about "UNsafe texture cache"): + // Have to be removed soon. + // But we keep it until the "safe" way became rock solid + // pros: it has an unique ID held by the texture data itself (@address) once cached. + // cons: it writes this unique ID in the gc RAM <- very dangerous (break MP1) and ugly + + // notes (about "safe texture cache"): + // Metroids text issue (character table): + // Same addr, same GX_TF_C4 texture data but different TLUT (hence different outputs). + // That's why we have to hash the TLUT too for TLUT tex_format dependent textures (ie. GX_TF_C4, GX_TF_C8, GX_TF_C14X2). + // And since the address and tex data don't change, the key index in the cacheEntry map can't be the address but + // have to be a real unique ID. + // DONE but not satifiying yet -> may break copyEFBToTexture sometimes. + + // Pokemon Colosseum text issue (plain text): + // Use a GX_TF_I4 512x512 text-flush-texture at a const address. + // The problem here was just the sparse hash on the texture. This texture is partly overwrited (what is needed only) + // so lot's of remaning old text. Thin white chars on black bg too. + + // TODO: - clean this up when ready to kill old "unsafe texture cache" + // - fix the key index situation with CopyRenderTargetToTexture. + // Could happen only for GX_TF_C4, GX_TF_C8 and GX_TF_C14X2 fmt. + // Wonder if we can't use tex width&height to know if EFB might be copied to it... + // raw idea: TOCHECK if addresses are aligned we have few bits left... + if (address == 0) return NULL; u8 *ptr = g_VideoInitialize.pGetMemoryPointer(address); - int bsw = TexDecoder_GetBlockWidthInTexels(tex_format) - 1; //TexelSizeInNibbles(format)*width*height/16; - int bsh = TexDecoder_GetBlockHeightInTexels(tex_format) - 1; //TexelSizeInNibbles(format)*width*height/16; + int bsw = TexDecoder_GetBlockWidthInTexels(tex_format) - 1; // TexelSizeInNibbles(format)*width*height/16; + int bsh = TexDecoder_GetBlockHeightInTexels(tex_format) - 1; // TexelSizeInNibbles(format)*width*height/16; int bsdepth = TexDecoder_GetTexelSizeInNibbles(tex_format); - int expandedWidth = (width + bsw) & (~bsw); + int expandedWidth = (width + bsw) & (~bsw); int expandedHeight = (height + bsh) & (~bsh); - u64 hash_value; + u64 hash_value = 0; u32 texID = address; - u64 texHash; + u64 texHash = 0; u32 FullFormat = tex_format; bool TextureisDynamic = false; if ((tex_format == GX_TF_C4) || (tex_format == GX_TF_C8) || (tex_format == GX_TF_C14X2)) - u32 FullFormat = (tex_format | (tlutfmt << 16)); + FullFormat = (tex_format | (tlutfmt << 16)); if (g_ActiveConfig.bSafeTextureCache || g_ActiveConfig.bHiresTextures || g_ActiveConfig.bDumpTextures) { - texHash = GetHash64(ptr,TexDecoder_GetTextureSizeInBytes(expandedWidth, expandedHeight, tex_format),g_ActiveConfig.iSafeTextureCache_ColorSamples); + texHash = GetHash64(ptr,TexDecoder_GetTextureSizeInBytes(expandedWidth, expandedHeight, tex_format),g_ActiveConfig.iSafeTextureCache_ColorSamples); if ((tex_format == GX_TF_C4) || (tex_format == GX_TF_C8) || (tex_format == GX_TF_C14X2)) { // WARNING! texID != address now => may break CopyRenderTargetToTexture (cf. TODO up) @@ -325,7 +350,7 @@ TextureCache::TCacheEntry *TextureCache::Load(int stage, u32 address, int width, bool isPow2 = !((width & (width - 1)) || (height & (height - 1))); entry.isNonPow2 = false; int TexLevels = (width > height)?width:height; - TexLevels = (isPow2 && UseNativeMips && (maxlevel > 0)) ? (int)(log((double)TexLevels)/log((double)2)) + 1 : ((isPow2)? 0 : 1); + TexLevels = (isPow2 && UseNativeMips && (maxlevel > 0)) ? (int)(log((double)TexLevels)/log((double)2)) + 1 : (isPow2? 0 : 1); if(TexLevels > (maxlevel + 1) && maxlevel > 0) TexLevels = (maxlevel + 1); entry.MipLevels = maxlevel; @@ -364,14 +389,14 @@ TextureCache::TCacheEntry *TextureCache::Load(int stage, u32 address, int width, entry.Scaledw = width; entry.Scaledh = height; entry.fmt = FullFormat; - + if (g_ActiveConfig.bDumpTextures) { // dump texture to file char szTemp[MAX_PATH]; char szDir[MAX_PATH]; const char* uniqueId = globals->unique_id; - bool bCheckedDumpDir = false; + static bool bCheckedDumpDir = false; sprintf(szDir, "%s%s", File::GetUserPath(D_DUMPTEXTURES_IDX), uniqueId); @@ -390,7 +415,7 @@ TextureCache::TCacheEntry *TextureCache::Load(int stage, u32 address, int width, } INCSTAT(stats.numTexturesCreated); - SETSTAT(stats.numTexturesAlive, (int)textures.size()); + SETSTAT(stats.numTexturesAlive, textures.size()); //Set the texture! D3D::SetTexture(stage, entry.texture); @@ -434,12 +459,12 @@ void TextureCache::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, boo textures.erase(iter); } } - if(TextureisDynamic) + if (TextureisDynamic) { Scaledtex_w = tex_w; Scaledtex_h = tex_h; } - if(!tex) + if (!tex) { TCacheEntry entry; entry.addr = address; @@ -459,7 +484,7 @@ void TextureCache::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, boo } // Make sure to resolve anything we need to read from. - LPDIRECT3DTEXTURE9 read_texture = bFromZBuffer ? FBManager.GetEFBDepthTexture(source_rect) : FBManager.GetEFBColorTexture(source_rect); + LPDIRECT3DTEXTURE9 read_texture = bFromZBuffer ? g_framebufferManager.GetEFBDepthTexture(source_rect) : g_framebufferManager.GetEFBColorTexture(source_rect); // We have to run a pixel shader, for color conversion. Renderer::ResetAPIState(); // reset any game specific settings @@ -625,7 +650,7 @@ void TextureCache::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, boo } - D3DFORMAT bformat = FBManager.GetEFBDepthRTSurfaceFormat(); + D3DFORMAT bformat = g_framebufferManager.GetEFBDepthRTSurfaceFormat(); int SSAAMode = g_ActiveConfig.iMultisampleMode; D3D::drawShadedTexQuad( read_texture, @@ -660,9 +685,7 @@ void TextureCache::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, boo D3D::RefreshSamplerState(0, D3DSAMP_MINFILTER); D3D::RefreshSamplerState(0, D3DSAMP_MAGFILTER); D3D::SetTexture(0,NULL); - D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); + D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); Renderer::RestoreAPIState(); - } - diff --git a/Source/Plugins/Plugin_VideoDX9/Src/TextureConverter.cpp b/Source/Plugins/Plugin_VideoDX9/Src/TextureConverter.cpp index ba04ae59be..be88040012 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/TextureConverter.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/TextureConverter.cpp @@ -156,7 +156,6 @@ void Init() } CreateRgbToYuyvProgram(); CreateYuyvToRgbProgram(); - } void Shutdown() @@ -242,7 +241,7 @@ void EncodeToRamUsingShader(LPDIRECT3DPIXELSHADER9 shader, LPDIRECT3DTEXTURE9 sr if (linearFilter) { - D3D::ChangeSamplerState(0, D3DSAMP_MINFILTER, D3DTEXF_LINEAR); + D3D::ChangeSamplerState(0, D3DSAMP_MINFILTER, D3DTEXF_LINEAR); } else { @@ -256,7 +255,7 @@ void EncodeToRamUsingShader(LPDIRECT3DPIXELSHADER9 shader, LPDIRECT3DTEXTURE9 sr vp.Height = dstHeight; vp.MinZ = 0.0f; vp.MaxZ = 1.0f; - hr = D3D::dev->SetViewport(&vp); + hr = D3D::dev->SetViewport(&vp); RECT SrcRect; SrcRect.top = sourceRc.top; SrcRect.left = sourceRc.left; @@ -277,40 +276,31 @@ void EncodeToRamUsingShader(LPDIRECT3DPIXELSHADER9 shader, LPDIRECT3DTEXTURE9 sr D3DLOCKED_RECT drect; - hr = D3D::dev->GetRenderTargetData(Rendersurf,s_texConvReadSurface); - if((hr = s_texConvReadSurface->LockRect(&drect, &DstRect, D3DLOCK_READONLY)) != D3D_OK) + hr = s_texConvReadSurface->LockRect(&drect, &DstRect, D3DLOCK_READONLY); + int writeStride = bpmem.copyMipMapStrideChannels * 32; + + if (writeStride != readStride && toTexture) { - PanicAlert("ERROR: %s", hr == D3DERR_WASSTILLDRAWING ? "Still drawing" : - hr == D3DERR_INVALIDCALL ? "Invalid call" : "w00t"); - + // writing to a texture of a different size + + int readHeight = readStride / dstWidth; + + int readStart = 0; + int readLoops = dstHeight / (readHeight/4); // 4 bytes per pixel + u8 *Source = (u8*)drect.pBits; + for (int i = 0; i < readLoops; i++) + { + int readDist = dstWidth*readHeight; + memcpy(destAddr,Source,readDist); + Source += readDist; + destAddr += writeStride; + } } else - { - int writeStride = bpmem.copyMipMapStrideChannels * 32; - - if (writeStride != readStride && toTexture) - { - // writing to a texture of a different size - - int readHeight = readStride / dstWidth; - - int readStart = 0; - int readLoops = dstHeight / (readHeight/4); // 4 bytes per pixel - u8 *Source = (u8*)drect.pBits; - for (int i = 0; i < readLoops; i++) - { - int readDist = dstWidth*readHeight; - memcpy(destAddr,Source,readDist); - Source += readDist; - destAddr += writeStride; - } - } - else - memcpy(destAddr,drect.pBits,dstWidth*dstHeight*4);// 4 bytes per pixel - - hr = s_texConvReadSurface->UnlockRect(); - } + memcpy(destAddr,drect.pBits,dstWidth*dstHeight*4);// 4 bytes per pixel + + hr = s_texConvReadSurface->UnlockRect(); } void EncodeToRam(u32 address, bool bFromZBuffer, bool bIsIntensityFmt, u32 copyfmt, int bScaleByHalf, const EFBRectangle& source) @@ -335,7 +325,7 @@ void EncodeToRam(u32 address, bool bFromZBuffer, bool bIsIntensityFmt, u32 copyf u8 *dest_ptr = Memory_GetPtr(address); - LPDIRECT3DTEXTURE9 source_texture = bFromZBuffer ? FBManager.GetEFBDepthTexture(source) : FBManager.GetEFBColorTexture(source); + LPDIRECT3DTEXTURE9 source_texture = bFromZBuffer ? g_framebufferManager.GetEFBDepthTexture(source) : g_framebufferManager.GetEFBColorTexture(source); int width = (source.right - source.left) >> bScaleByHalf; int height = (source.bottom - source.top) >> bScaleByHalf; @@ -343,7 +333,7 @@ void EncodeToRam(u32 address, bool bFromZBuffer, bool bIsIntensityFmt, u32 copyf // Invalidate any existing texture covering this memory range. // TODO - don't delete the texture if it already exists, just replace the contents. - TextureCache::InvalidateRange(address, size_in_bytes); + TextureCache::InvalidateRange(address, size_in_bytes); u16 blkW = TexDecoder_GetBlockWidthInTexels(format) - 1; u16 blkH = TexDecoder_GetBlockHeightInTexels(format) - 1; @@ -383,9 +373,9 @@ void EncodeToRam(u32 address, bool bFromZBuffer, bool bIsIntensityFmt, u32 copyf int readStride = (expandedWidth * cacheBytes) / TexDecoder_GetBlockWidthInTexels(format); Renderer::ResetAPIState(); - EncodeToRamUsingShader(texconv_shader, source_texture, scaledSource, dest_ptr, expandedWidth / samples, expandedHeight,readStride, true, bScaleByHalf > 0); - D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); + EncodeToRamUsingShader(texconv_shader, source_texture, scaledSource, dest_ptr, expandedWidth / samples, expandedHeight, readStride, true, bScaleByHalf > 0); + D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); Renderer::RestoreAPIState(); } @@ -454,8 +444,7 @@ u64 EncodeToRamFromTexture(u32 address,LPDIRECT3DTEXTURE9 source_texture,u32 Sou return Hashvalue; } - -void EncodeToRamYUYV(LPDIRECT3DTEXTURE9 srcTexture, const TargetRectangle& sourceRc,u8* destAddr, int dstWidth, int dstHeight) +void EncodeToRamYUYV(LPDIRECT3DTEXTURE9 srcTexture, const TargetRectangle& sourceRc, u8* destAddr, int dstWidth, int dstHeight) { TextureConversionShader::SetShaderParameters( (float)dstWidth, @@ -468,9 +457,9 @@ void EncodeToRamYUYV(LPDIRECT3DTEXTURE9 srcTexture, const TargetRectangle& sourc (float)Renderer::GetFullTargetHeight()); Renderer::ResetAPIState(); EncodeToRamUsingShader(s_rgbToYuyvProgram, srcTexture, sourceRc, destAddr, dstWidth / 2, dstHeight, 0, false, false); - D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); - Renderer::RestoreAPIState(); + D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); + Renderer::RestoreAPIState(); } @@ -491,7 +480,7 @@ void DecodeToTexture(u32 xfbAddr, int srcWidth, int srcHeight, LPDIRECT3DTEXTURE LPDIRECT3DSURFACE9 Rendersurf = NULL; destTexture->GetSurfaceLevel(0,&Rendersurf); D3D::dev->SetDepthStencilSurface(NULL); - D3D::dev->SetRenderTarget(0, Rendersurf); + D3D::dev->SetRenderTarget(0, Rendersurf); D3DVIEWPORT9 vp; @@ -535,17 +524,17 @@ void DecodeToTexture(u32 xfbAddr, int srcWidth, int srcHeight, LPDIRECT3DTEXTURE srcWidth, srcHeight, s_yuyvToRgbProgram, - VertexShaderCache::GetSimpleVertexShader(0)); + VertexShaderCache::GetSimpleVertexShader(0)); D3D::RefreshSamplerState(0, D3DSAMP_MINFILTER); D3D::RefreshSamplerState(0, D3DSAMP_MAGFILTER); D3D::SetTexture(0,NULL); - D3D::dev->SetRenderTarget(0, FBManager.GetEFBColorRTSurface()); - D3D::dev->SetDepthStencilSurface(FBManager.GetEFBDepthRTSurface()); + D3D::dev->SetRenderTarget(0, g_framebufferManager.GetEFBColorRTSurface()); + D3D::dev->SetDepthStencilSurface(g_framebufferManager.GetEFBDepthRTSurface()); Renderer::RestoreAPIState(); Rendersurf->Release(); - s_srcTexture->Release(); + s_srcTexture->Release(); } } // namespace diff --git a/Source/Plugins/Plugin_VideoDX9/Src/VertexManager.cpp b/Source/Plugins/Plugin_VideoDX9/Src/VertexManager.cpp index a5e33e0677..e6302ad2f4 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/VertexManager.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/VertexManager.cpp @@ -81,26 +81,24 @@ void Shutdown() delete [] LocalVBuffer; delete [] TIBuffer; delete [] LIBuffer; - delete [] PIBuffer; + delete [] PIBuffer; ResetBuffer(); } -void AddIndices(int _primitive, int _numVertices) +void AddIndices(int primitive, int numVertices) { - switch (_primitive) + switch (primitive) { - case GX_DRAW_QUADS: IndexGenerator::AddQuads(_numVertices); break; - case GX_DRAW_TRIANGLES: IndexGenerator::AddList(_numVertices); break; - case GX_DRAW_TRIANGLE_STRIP: IndexGenerator::AddStrip(_numVertices); break; - case GX_DRAW_TRIANGLE_FAN: IndexGenerator::AddFan(_numVertices); break; - case GX_DRAW_LINE_STRIP: IndexGenerator::AddLineStrip(_numVertices); break; - case GX_DRAW_LINES: IndexGenerator::AddLineList(_numVertices); break; - case GX_DRAW_POINTS: IndexGenerator::AddPoints(_numVertices); break; + case GX_DRAW_QUADS: IndexGenerator::AddQuads(numVertices); break; + case GX_DRAW_TRIANGLES: IndexGenerator::AddList(numVertices); break; + case GX_DRAW_TRIANGLE_STRIP: IndexGenerator::AddStrip(numVertices); break; + case GX_DRAW_TRIANGLE_FAN: IndexGenerator::AddFan(numVertices); break; + case GX_DRAW_LINE_STRIP: IndexGenerator::AddLineStrip(numVertices); break; + case GX_DRAW_LINES: IndexGenerator::AddLineList(numVertices); break; + case GX_DRAW_POINTS: IndexGenerator::AddPoints(numVertices); break; } } - - int GetRemainingSize() { return MAXVBUFFERSIZE - (int)(s_pCurBufferPointer - LocalVBuffer); @@ -110,53 +108,54 @@ int GetRemainingVertices(int primitive) { switch (primitive) { - case GX_DRAW_QUADS: - case GX_DRAW_TRIANGLES: - case GX_DRAW_TRIANGLE_STRIP: - case GX_DRAW_TRIANGLE_FAN: - return (MAXIBUFFERSIZE - IndexGenerator::GetTriangleindexLen())/3; - case GX_DRAW_LINE_STRIP: - case GX_DRAW_LINES: - return (MAXIBUFFERSIZE - IndexGenerator::GetLineindexLen())/2; - case GX_DRAW_POINTS: - return (MAXIBUFFERSIZE - IndexGenerator::GetPointindexLen()); - default: return 0; + case GX_DRAW_QUADS: + case GX_DRAW_TRIANGLES: + case GX_DRAW_TRIANGLE_STRIP: + case GX_DRAW_TRIANGLE_FAN: + return (MAXIBUFFERSIZE - IndexGenerator::GetTriangleindexLen())/3; + case GX_DRAW_LINE_STRIP: + case GX_DRAW_LINES: + return (MAXIBUFFERSIZE - IndexGenerator::GetLineindexLen())/2; + case GX_DRAW_POINTS: + return (MAXIBUFFERSIZE - IndexGenerator::GetPointindexLen()); + default: return 0; } } -void AddVertices(int _primitive, int _numVertices) +void AddVertices(int primitive, int numVertices) { - if (_numVertices <= 0) + if (numVertices <= 0) return; - switch (_primitive) + + switch (primitive) { - case GX_DRAW_QUADS: - case GX_DRAW_TRIANGLES: - case GX_DRAW_TRIANGLE_STRIP: - case GX_DRAW_TRIANGLE_FAN: - if(MAXIBUFFERSIZE - IndexGenerator::GetTriangleindexLen() < 3 * _numVertices) + case GX_DRAW_QUADS: + case GX_DRAW_TRIANGLES: + case GX_DRAW_TRIANGLE_STRIP: + case GX_DRAW_TRIANGLE_FAN: + if (MAXIBUFFERSIZE - IndexGenerator::GetTriangleindexLen() < 3 * numVertices) Flush(); - break; - case GX_DRAW_LINE_STRIP: - case GX_DRAW_LINES: - if(MAXIBUFFERSIZE - IndexGenerator::GetLineindexLen() < 2 * _numVertices) + break; + case GX_DRAW_LINE_STRIP: + case GX_DRAW_LINES: + if (MAXIBUFFERSIZE - IndexGenerator::GetLineindexLen() < 2 * numVertices) Flush(); - break; - case GX_DRAW_POINTS: - if(MAXIBUFFERSIZE - IndexGenerator::GetPointindexLen() < _numVertices) + break; + case GX_DRAW_POINTS: + if (MAXIBUFFERSIZE - IndexGenerator::GetPointindexLen() < numVertices) Flush(); - break; - default: return; + break; + default: return; } - if(Flushed) + if (Flushed) { IndexGenerator::Start(TIBuffer,LIBuffer,PIBuffer); Flushed=false; } - lastPrimitive = _primitive; - ADDSTAT(stats.thisFrame.numPrims, _numVertices); + lastPrimitive = primitive; + ADDSTAT(stats.thisFrame.numPrims, numVertices); INCSTAT(stats.thisFrame.numPrimitiveJoins); - AddIndices(_primitive, _numVertices); + AddIndices(primitive, numVertices); } inline void DumpBadShaders() @@ -179,7 +178,7 @@ inline void DumpBadShaders() inline void Draw(int stride) { - if(IndexGenerator::GetNumTriangles() > 0) + if (IndexGenerator::GetNumTriangles() > 0) { if (FAILED(D3D::dev->DrawIndexedPrimitiveUP( D3DPT_TRIANGLELIST, @@ -193,7 +192,7 @@ inline void Draw(int stride) } INCSTAT(stats.thisFrame.numIndexedDrawCalls); } - if(IndexGenerator::GetNumLines() > 0) + if (IndexGenerator::GetNumLines() > 0) { if (FAILED(D3D::dev->DrawIndexedPrimitiveUP( D3DPT_LINELIST, @@ -207,7 +206,7 @@ inline void Draw(int stride) } INCSTAT(stats.thisFrame.numIndexedDrawCalls); } - if(IndexGenerator::GetNumPoints() > 0) + if (IndexGenerator::GetNumPoints() > 0) { if (FAILED(D3D::dev->DrawIndexedPrimitiveUP( D3DPT_POINTLIST, @@ -226,47 +225,43 @@ inline void Draw(int stride) void Flush() { if (LocalVBuffer == s_pCurBufferPointer) return; - if(Flushed) return; + if (Flushed) return; Flushed=true; VideoFifo_CheckEFBAccess(); + DVSTARTPROFILE(); - + u32 usedtextures = 0; - for (u32 i = 0; i < (u32)bpmem.genMode.numtevstages + 1; ++i) { - if (bpmem.tevorders[i/2].getEnable(i & 1)) + for (u32 i = 0; i < (u32)bpmem.genMode.numtevstages + 1; ++i) + if (bpmem.tevorders[i / 2].getEnable(i & 1)) usedtextures |= 1 << bpmem.tevorders[i/2].getTexMap(i & 1); - } - if (bpmem.genMode.numindstages > 0) { - for (u32 i = 0; i < (u32)bpmem.genMode.numtevstages + 1; ++i) { - if (bpmem.tevind[i].IsActive() && bpmem.tevind[i].bt < bpmem.genMode.numindstages) { + if (bpmem.genMode.numindstages > 0) + for (unsigned int i = 0; i < bpmem.genMode.numtevstages + 1; ++i) + if (bpmem.tevind[i].IsActive() && bpmem.tevind[i].bt < bpmem.genMode.numindstages) usedtextures |= 1 << bpmem.tevindref.getTexMap(bpmem.tevind[i].bt); - } - } - } - for (int i = 0; i < 8; i++) + for (unsigned int i = 0; i < 8; i++) { - if (usedtextures & (1 << i)) { + if (usedtextures & (1 << i)) + { Renderer::SetSamplerState(i & 3, i >> 2); FourTexUnits &tex = bpmem.tex[i >> 2]; TextureCache::TCacheEntry* tentry = TextureCache::Load(i, - (tex.texImage3[i&3].image_base/* & 0x1FFFFF*/) << 5, - tex.texImage0[i&3].width + 1, tex.texImage0[i&3].height + 1, + (tex.texImage3[i&3].image_base/* & 0x1FFFFF*/) << 5, + tex.texImage0[i&3].width + 1, tex.texImage0[i&3].height + 1, tex.texImage0[i&3].format, tex.texTlut[i&3].tmem_offset<<9, tex.texTlut[i&3].tlut_format, - (tex.texMode0[i&3].min_filter & 3) && (tex.texMode0[i&3].min_filter != 8) && g_ActiveConfig.bUseNativeMips, + (tex.texMode0[i&3].min_filter & 3) && (tex.texMode0[i&3].min_filter != 8) && g_ActiveConfig.bUseNativeMips, (tex.texMode1[i&3].max_lod >> 4)); - if (tentry) { + if (tentry) + { + // 0s are probably for no manual wrapping needed. PixelShaderManager::SetTexDims(i, tentry->w, tentry->h, 0, 0); } else - { - DEBUGGER_PAUSE_LOG_AT(NEXT_ERROR,true,{printf("Fail to load texture\n");}); ERROR_LOG(VIDEO, "error loading texture"); - } - } } @@ -311,7 +306,5 @@ void Flush() shader_fail: ResetBuffer(); - } - } // namespace diff --git a/Source/Plugins/Plugin_VideoDX9/Src/VertexShaderCache.cpp b/Source/Plugins/Plugin_VideoDX9/Src/VertexShaderCache.cpp index 18598be900..e5ef24bc2b 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/VertexShaderCache.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/VertexShaderCache.cpp @@ -84,16 +84,19 @@ void SetMultiVSConstant4fv(unsigned int const_number, unsigned int count, const D3D::dev->SetVertexShaderConstantF(const_number, f, count); } +// this class will load the precompiled shaders into our cache class VertexShaderCacheInserter : public LinearDiskCacheReader { public: void Read(const u8 *key, int key_size, const u8 *value, int value_size) { VERTEXSHADERUID uid; - if (key_size != sizeof(uid)) { + if (key_size != sizeof(uid)) + { ERROR_LOG(VIDEO, "Wrong key size in vertex shader cache"); return; } memcpy(&uid, key, key_size); + VertexShaderCache::InsertByteCode(uid, value, value_size, false); } }; @@ -179,13 +182,12 @@ void VertexShaderCache::Init() char cache_filename[MAX_PATH]; sprintf(cache_filename, "%sdx9-%s-vs.cache", File::GetUserPath(D_SHADERCACHE_IDX), globals->unique_id); VertexShaderCacheInserter inserter; - int read_items = g_vs_disk_cache.OpenAndRead(cache_filename, &inserter); + g_vs_disk_cache.OpenAndRead(cache_filename, &inserter); } void VertexShaderCache::Clear() { - VSCache::iterator iter = vshaders.begin(); - for (; iter != vshaders.end(); ++iter) + for (VSCache::iterator iter = vshaders.begin(); iter != vshaders.end(); ++iter) iter->second.Destroy(); vshaders.clear(); @@ -217,16 +219,11 @@ bool VertexShaderCache::SetShader(u32 components) VERTEXSHADERUID uid; GetVertexShaderId(&uid, components); if (uid == last_vertex_shader_uid && vshaders[uid].frameCount == frameCount) - { - if (vshaders[uid].shader) - return true; - else - return false; - } + return (vshaders[uid].shader != NULL); + memcpy(&last_vertex_shader_uid, &uid, sizeof(VERTEXSHADERUID)); - VSCache::iterator iter; - iter = vshaders.find(uid); + VSCache::iterator iter = vshaders.find(uid); if (iter != vshaders.end()) { iter->second.frameCount = frameCount; diff --git a/Source/Plugins/Plugin_VideoDX9/Src/main.cpp b/Source/Plugins/Plugin_VideoDX9/Src/main.cpp index d4b21e4ecb..fdf8162d0b 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/main.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/main.cpp @@ -100,7 +100,7 @@ void *DllDebugger(void *_hParent, bool Show) return true; } }; - IMPLEMENT_APP_NO_MAIN(wxDLLApp) + IMPLEMENT_APP_NO_MAIN(wxDLLApp) WXDLLIMPEXP_BASE void wxSetInstance(HINSTANCE hInst); #endif @@ -148,18 +148,16 @@ void UpdateFPSDisplay(const char *text) SetWindowText(EmuWindow::GetWnd(), temp); } -void GetDllInfo (PLUGIN_INFO* _PluginInfo) +void GetDllInfo(PLUGIN_INFO* _PluginInfo) { _PluginInfo->Version = 0x0100; _PluginInfo->Type = PLUGIN_TYPE_VIDEO; #ifdef DEBUGFAST sprintf_s(_PluginInfo->Name, 100, "Dolphin Direct3D9 (DebugFast)"); -#else -#ifndef _DEBUG - sprintf_s(_PluginInfo->Name, 100, "Dolphin Direct3D9"); -#else +#elif defined _DEBUG sprintf_s(_PluginInfo->Name, 100, "Dolphin Direct3D9 (Debug)"); -#endif +#else + sprintf_s(_PluginInfo->Name, 100, "Dolphin Direct3D9"); #endif } @@ -197,14 +195,15 @@ void Initialize(void *init) { frameCount = 0; SVideoInitialize *_pVideoInitialize = (SVideoInitialize*)init; - g_VideoInitialize = *_pVideoInitialize; + // Create a shortcut to _pVideoInitialize that can also update it + g_VideoInitialize = *(_pVideoInitialize); InitXFBConvTables(); g_Config.Load((std::string(File::GetUserPath(D_CONFIG_IDX)) + "gfx_dx9.ini").c_str()); g_Config.GameIniLoad(globals->game_ini); UpdateProjectionHack(g_Config.iPhackvalue); // DX9 projection hack could be disabled by commenting out this line UpdateActiveConfig(); - + g_VideoInitialize.pWindowHandle = (void*)EmuWindow::Create((HWND)g_VideoInitialize.pWindowHandle, g_hInstance, _T("Loading - Please wait.")); if (g_VideoInitialize.pWindowHandle == NULL) { @@ -222,6 +221,8 @@ void Initialize(void *init) _pVideoInitialize->pPeekMessages = g_VideoInitialize.pPeekMessages; _pVideoInitialize->pUpdateFPSDisplay = g_VideoInitialize.pUpdateFPSDisplay; + + // Now the window handle is written _pVideoInitialize->pWindowHandle = g_VideoInitialize.pWindowHandle; OSD::AddMessage("Dolphin Direct3D9 Video Plugin.", 5000); @@ -234,10 +235,13 @@ void Video_Prepare() s_efbAccessRequested = FALSE; s_FifoShuttingDown = FALSE; s_swapRequested = FALSE; + + // internal interfaces Renderer::Init(); TextureCache::Init(); - BPInit(); VertexManager::Init(); + // VideoCommon + BPInit(); Fifo_Init(); VertexLoaderManager::Init(); OpcodeDecoder_Init(); @@ -246,36 +250,45 @@ void Video_Prepare() CommandProcessor::Init(); PixelEngine::Init(); DLCache::Init(); - // Tell the host the window is ready + + // Notify the core that the video plugin is ready g_VideoInitialize.pCoreMessage(WM_USER_CREATE); } void Shutdown() { + s_PluginInitialized = false; + s_efbAccessRequested = FALSE; s_FifoShuttingDown = FALSE; s_swapRequested = FALSE; + + // VideoCommon DLCache::Shutdown(); Fifo_Shutdown(); CommandProcessor::Shutdown(); - VertexManager::Shutdown(); - VertexLoaderManager::Shutdown(); - VertexShaderManager::Shutdown(); PixelShaderManager::Shutdown(); - TextureCache::Shutdown(); + VertexShaderManager::Shutdown(); OpcodeDecoder_Shutdown(); + VertexLoaderManager::Shutdown(); + + // internal interfaces + PixelShaderCache::Shutdown(); + VertexShaderCache::Shutdown(); + VertexManager::Shutdown(); + TextureCache::Shutdown(); Renderer::Shutdown(); D3D::Shutdown(); EmuWindow::Close(); - s_PluginInitialized = false; } -void DoState(unsigned char **ptr, int mode) { +void DoState(unsigned char **ptr, int mode) +{ // Clear texture cache because it might have written to RAM CommandProcessor::FifoCriticalEnter(); TextureCache::Invalidate(false); CommandProcessor::FifoCriticalLeave(); - // No need to clear shader caches. + // No need to clear shader caches PointerWrap p(ptr, mode); VideoCommon_DoState(p); } @@ -285,6 +298,7 @@ void EmuStateChange(PLUGIN_EMUSTATE newState) Fifo_RunLoop((newState == PLUGIN_EMUSTATE_PLAY) ? true : false); } +// Enter and exit the video loop void Video_EnterLoop() { Fifo_EnterLoop(g_VideoInitialize); @@ -293,11 +307,11 @@ void Video_EnterLoop() void Video_ExitLoop() { Fifo_ExitLoop(); - s_FifoShuttingDown = TRUE; } -void Video_SetRendering(bool bEnabled) { +void Video_SetRendering(bool bEnabled) +{ Fifo_SetRendering(bEnabled); } @@ -315,7 +329,7 @@ void VideoFifo_CheckSwapRequest() } } -inline bool addrRangesOverlap(u32 aLower, u32 aUpper, u32 bLower, u32 bUpper) +static inline bool addrRangesOverlap(u32 aLower, u32 aUpper, u32 bLower, u32 bUpper) { return !((aLower >= bUpper) || (bLower >= aUpper)); } @@ -335,14 +349,14 @@ void VideoFifo_CheckSwapRequestAt(u32 xfbAddr, u32 fbWidth, u32 fbHeight) if (addrRangesOverlap(aLower, aUpper, bLower, bUpper)) VideoFifo_CheckSwapRequest(); } - } + } } // Run from the CPU thread (from VideoInterface.cpp) void Video_BeginField(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight) { if (s_PluginInitialized && g_ActiveConfig.bUseXFB) - { + { if (g_VideoInitialize.bOnThread) { while (Common::AtomicLoadAcquire(s_swapRequested) && !s_FifoShuttingDown) @@ -350,7 +364,7 @@ void Video_BeginField(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight) Common::YieldCPU(); } else - VideoFifo_CheckSwapRequest(); + VideoFifo_CheckSwapRequest(); s_beginFieldArgs.xfbAddr = xfbAddr; s_beginFieldArgs.field = field; s_beginFieldArgs.fbWidth = fbWidth; @@ -360,30 +374,20 @@ void Video_BeginField(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight) } } +// Run from the CPU thread (from VideoInterface.cpp) void Video_EndField() { } void Video_AddMessage(const char* pstr, u32 milliseconds) { - OSD::AddMessage(pstr,milliseconds); -} - -HRESULT ScreenShot(const char *File) -{ - Renderer::SetScreenshot(File); - return S_OK; + OSD::AddMessage(pstr, milliseconds); } +// Screenshot void Video_Screenshot(const char *_szFilename) { - if (ScreenShot(_szFilename) != S_OK) - PanicAlert("Error while capturing screen"); - else { - std::string message = "Saved "; - message += _szFilename; - OSD::AddMessage(message.c_str(), 2000); - } + Renderer::SetScreenshot(_szFilename); } static struct @@ -406,7 +410,7 @@ void VideoFifo_CheckEFBAccess() } } -u32 Video_AccessEFB(EFBAccessType type, u32 x, u32 y,u32 InputData) +u32 Video_AccessEFB(EFBAccessType type, u32 x, u32 y, u32 InputData) { if (s_PluginInitialized) { diff --git a/Source/Plugins/Plugin_VideoDX9/Src/stdafx.cpp b/Source/Plugins/Plugin_VideoDX9/Src/stdafx.cpp index 31f734b17a..168ca738eb 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/stdafx.cpp +++ b/Source/Plugins/Plugin_VideoDX9/Src/stdafx.cpp @@ -15,4 +15,4 @@ // Official SVN repository and contact information can be found at // http://code.google.com/p/dolphin-emu/ -#include "stdafx.h" +#include "stdafx.h" \ No newline at end of file diff --git a/Source/Plugins/Plugin_VideoDX9/Src/stdafx.h b/Source/Plugins/Plugin_VideoDX9/Src/stdafx.h index b56c9ae5c4..8ade6faa40 100644 --- a/Source/Plugins/Plugin_VideoDX9/Src/stdafx.h +++ b/Source/Plugins/Plugin_VideoDX9/Src/stdafx.h @@ -23,4 +23,3 @@ #include #include - diff --git a/Source/Plugins/Plugin_VideoOGL/Plugin_VideoOGL.vcproj b/Source/Plugins/Plugin_VideoOGL/Plugin_VideoOGL.vcproj index df80ab23b8..3a31a30a27 100644 --- a/Source/Plugins/Plugin_VideoOGL/Plugin_VideoOGL.vcproj +++ b/Source/Plugins/Plugin_VideoOGL/Plugin_VideoOGL.vcproj @@ -766,11 +766,11 @@ > xfbAddr; s32 srcUpper = it->xfbAddr + 2 * it->xfbWidth * it->xfbHeight; @@ -311,13 +310,13 @@ void FramebufferManager::replaceVirtualXFB() if (dstLower >= srcLower && dstUpper <= srcUpper) { - // invalidate the data + // Invalidate the data it->xfbAddr = 0; it->xfbHeight = 0; it->xfbWidth = 0; } else if (addrRangesOverlap(srcLower, srcUpper, dstLower, dstUpper)) - { + { s32 upperOverlap = (srcUpper - dstLower) / lineSize; s32 lowerOverlap = (dstUpper - srcLower) / lineSize; @@ -338,14 +337,14 @@ void FramebufferManager::replaceVirtualXFB() void FramebufferManager::copyToRealXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight, const EFBRectangle& sourceRc) { - u8* pXFB = Memory_GetPtr(xfbAddr); - if (!pXFB) + u8* xfb_in_ram = Memory_GetPtr(xfbAddr); + if (!xfb_in_ram) { WARN_LOG(VIDEO, "Tried to copy to invalid XFB address"); return; } - XFB_Write(pXFB, sourceRc, fbWidth, fbHeight); + XFB_Write(xfb_in_ram, sourceRc, fbWidth, fbHeight); } void FramebufferManager::copyToVirtualXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight, const EFBRectangle& sourceRc) @@ -356,7 +355,7 @@ void FramebufferManager::copyToVirtualXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight if (it == m_virtualXFBList.end() && (int)m_virtualXFBList.size() >= MAX_VIRTUAL_XFB) { - // replace the last virtual XFB + // Replace the last virtual XFB --it; } @@ -432,7 +431,7 @@ void FramebufferManager::copyToVirtualXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight m_virtualXFBList.push_front(newVirt); } - // Copy EFB to XFB texture + // Copy EFB data to XFB and restore render target again #if 0 if (m_msaaSamples <= 1) diff --git a/Source/Plugins/Plugin_VideoOGL/Src/GUI/ConfigDlg.cpp b/Source/Plugins/Plugin_VideoOGL/Src/GUI/ConfigDlg.cpp index 166340168c..4a9e1ac685 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/GUI/ConfigDlg.cpp +++ b/Source/Plugins/Plugin_VideoOGL/Src/GUI/ConfigDlg.cpp @@ -25,7 +25,7 @@ #include "ConfigDlg.h" #include "../Globals.h" #include "VideoConfig.h" -#include "../TextureMngr.h" +#include "../TextureCache.h" #include "VertexShaderManager.h" #include "../PostProcessing.h" #include "Render.h" @@ -668,11 +668,11 @@ void GFXConfigDialogOGL::AdvancedSettingsChanged(wxCommandEvent& event) case ID_TEXFMTOVERLAY: g_Config.bTexFmtOverlayEnable = m_TexFmtOverlay->IsChecked(); m_TexFmtCenter->Enable(m_TexFmtOverlay->IsChecked()); - TextureMngr::Invalidate(false); + TextureCache::Invalidate(false); break; case ID_TEXFMTCENTER: g_Config.bTexFmtOverlayCenter = m_TexFmtCenter->IsChecked(); - TextureMngr::Invalidate(false); + TextureCache::Invalidate(false); break; case ID_SHOWEFBCOPYREGIONS: g_Config.bShowEFBCopyRegions = m_ShowEFBCopyRegions->IsChecked(); diff --git a/Source/Plugins/Plugin_VideoOGL/Src/Globals.h b/Source/Plugins/Plugin_VideoOGL/Src/Globals.h index e0d86e702a..161b29fddf 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/Globals.h +++ b/Source/Plugins/Plugin_VideoOGL/Src/Globals.h @@ -27,4 +27,4 @@ // A global plugin specification extern PLUGIN_GLOBALS* globals; -#endif // _GLOBALS_H_ +#endif // _GLOBALS_H_ \ No newline at end of file diff --git a/Source/Plugins/Plugin_VideoOGL/Src/PixelShaderCache.cpp b/Source/Plugins/Plugin_VideoOGL/Src/PixelShaderCache.cpp index 0ffa54c838..611ef6b9a7 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/PixelShaderCache.cpp +++ b/Source/Plugins/Plugin_VideoOGL/Src/PixelShaderCache.cpp @@ -43,6 +43,15 @@ bool PixelShaderCache::ShaderEnabled; static FRAGMENTSHADER* pShaderLast = NULL; +GLuint PixelShaderCache::GetDepthMatrixProgram() +{ + return s_DepthMatrixProgram; +} + +GLuint PixelShaderCache::GetColorMatrixProgram() +{ + return s_ColorMatrixProgram; +} void SetPSConstant4f(unsigned int const_number, float f1, float f2, float f3, float f4) { @@ -174,18 +183,7 @@ void PixelShaderCache::Shutdown() pshaders.clear(); } -GLuint PixelShaderCache::GetColorMatrixProgram() -{ - return s_ColorMatrixProgram; -} - -GLuint PixelShaderCache::GetDepthMatrixProgram() -{ - return s_DepthMatrixProgram; -} - - -FRAGMENTSHADER* PixelShaderCache::GetShader(bool dstAlphaEnable,u32 components) +FRAGMENTSHADER* PixelShaderCache::SetShader(bool dstAlphaEnable,u32 components) { DVSTARTPROFILE(); PIXELSHADERUID uid; diff --git a/Source/Plugins/Plugin_VideoOGL/Src/PixelShaderCache.h b/Source/Plugins/Plugin_VideoOGL/Src/PixelShaderCache.h index a99ff7b57a..d97d47dd7d 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/PixelShaderCache.h +++ b/Source/Plugins/Plugin_VideoOGL/Src/PixelShaderCache.h @@ -71,7 +71,7 @@ public: static void Init(); static void Shutdown(); - static FRAGMENTSHADER* GetShader(bool dstAlphaEnable,u32 components); + static FRAGMENTSHADER* SetShader(bool dstAlphaEnable,u32 components); static bool CompilePixelShader(FRAGMENTSHADER& ps, const char* pstrprogram); static GLuint GetColorMatrixProgram(); diff --git a/Source/Plugins/Plugin_VideoOGL/Src/Render.cpp b/Source/Plugins/Plugin_VideoOGL/Src/Render.cpp index ae47b8b33f..a1f6506598 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/Render.cpp +++ b/Source/Plugins/Plugin_VideoOGL/Src/Render.cpp @@ -39,7 +39,7 @@ #include "Render.h" #include "OpcodeDecoding.h" #include "BPStructs.h" -#include "TextureMngr.h" +#include "TextureCache.h" #include "RasterFont.h" #include "VertexShaderGen.h" #include "DLCache.h" @@ -106,11 +106,11 @@ int frameCount; // The custom resolution // TODO: Add functionality to reinit all the render targets when the window is resized. -static int m_CustomWidth; -static int m_CustomHeight; +static int s_backbuffer_width; +static int s_backbuffer_height; // The framebuffer size -static int m_FrameBufferWidth; -static int m_FrameBufferHeight; +static int s_target_width; +static int s_target_height; static unsigned int s_XFB_width; static unsigned int s_XFB_height; @@ -123,6 +123,8 @@ static float EFByScale; static bool s_skipSwap = false; +static bool XFBWrited = false; + int OSDChoice = 0 , OSDTime = 0, OSDInternalW = 0, OSDInternalH = 0; namespace @@ -305,6 +307,10 @@ bool Renderer::Init() if (!bSuccess) return false; + // Decide frambuffer size + s_backbuffer_width = (int)OpenGL_GetBackbufferWidth(); + s_backbuffer_height = (int)OpenGL_GetBackbufferHeight(); + // Handle VSync on/off #if defined USE_WX && USE_WX // TODO: FILL IN @@ -336,14 +342,11 @@ bool Renderer::Init() if (!GLEW_ARB_texture_non_power_of_two) WARN_LOG(VIDEO, "ARB_texture_non_power_of_two not supported."); - // Decide frambuffer size - int W = (int)OpenGL_GetBackbufferWidth(), H = (int)OpenGL_GetBackbufferHeight(); - s_XFB_width = MAX_XFB_WIDTH; s_XFB_height = MAX_XFB_HEIGHT; TargetRectangle dst_rect; - ComputeDrawRectangle(W, H, false, &dst_rect); + ComputeDrawRectangle(s_backbuffer_width, s_backbuffer_height, false, &dst_rect); xScale = 1.0f; yScale = 1.0f; @@ -365,12 +368,8 @@ bool Renderer::Init() EFBxScale = ceilf(xScale); EFByScale = ceilf(yScale); - m_FrameBufferWidth = EFB_WIDTH * EFBxScale; - m_FrameBufferHeight = EFB_HEIGHT * EFByScale; - - // Save the custom resolution - m_CustomWidth = W; - m_CustomHeight = H; + s_target_width = EFB_WIDTH * EFBxScale; + s_target_height = EFB_HEIGHT * EFByScale; // Because of the fixed framebuffer size we need to disable the resolution // options while running @@ -380,7 +379,7 @@ bool Renderer::Init() bSuccess = false; // Initialize the FramebufferManager - g_framebufferManager.Init(m_FrameBufferWidth, m_FrameBufferHeight, + g_framebufferManager.Init(s_target_width, s_target_height, s_MSAASamples, s_MSAACoverageSamples); glDrawBuffer(GL_COLOR_ATTACHMENT0_EXT); @@ -520,54 +519,26 @@ void Renderer::Shutdown(void) #endif } -// For the OSD menu's live resolution change -bool Renderer::Allow2x() +// Return the rendering target width and height +int Renderer::GetTargetWidth() { - if (GetFrameBufferWidth() >= 1280 && GetFrameBufferHeight() >= 960) - return true; - else - return false; + return s_target_width; } -bool Renderer::AllowCustom() +int Renderer::GetTargetHeight() { - if (GetCustomWidth() <= GetFrameBufferWidth() && GetCustomHeight() <= GetFrameBufferHeight()) - return true; - else - return false; -} - -// Return the framebuffer size -int Renderer::GetFrameBufferWidth() -{ - return m_FrameBufferWidth; -} - -int Renderer::GetFrameBufferHeight() -{ - return m_FrameBufferHeight; + return s_target_height; } // Return the custom resolution int Renderer::GetCustomWidth() { - return m_CustomWidth; + return s_backbuffer_width; } int Renderer::GetCustomHeight() { - return m_CustomHeight; -} - -// Return the rendering target width and height -int Renderer::GetTargetWidth() -{ - return m_FrameBufferWidth; -} - -int Renderer::GetTargetHeight() -{ - return m_FrameBufferHeight; + return s_backbuffer_height; } float Renderer::GetTargetScaleX() @@ -590,171 +561,207 @@ float Renderer::GetXFBScaleY() return yScale; } +// Return the framebuffer size +int Renderer::GetFrameBufferWidth() +{ + return s_target_width; +} + +int Renderer::GetFrameBufferHeight() +{ + return s_target_height; +} + +// Create On-Screen-Messages +void Renderer::DrawDebugText() +{ + // Reset viewport for drawing text + glViewport(0, 0, OpenGL_GetBackbufferWidth(), OpenGL_GetBackbufferHeight()); + // Draw various messages on the screen, like FPS, statistics, etc. + char debugtext_buffer[8192]; + char *p = debugtext_buffer; + p[0] = 0; + + if (g_ActiveConfig.bShowFPS) + p+=sprintf(p, "FPS: %d\n", s_fps); + + if (g_ActiveConfig.bShowEFBCopyRegions) + { + // Store Line Size + GLfloat lSize; + glGetFloatv(GL_LINE_WIDTH, &lSize); + + // Set Line Size + glLineWidth(3.0f); + + glBegin(GL_LINES); + + // Draw EFB copy regions rectangles + for (std::vector::const_iterator it = stats.efb_regions.begin(); + it != stats.efb_regions.end(); ++it) + { + GLfloat halfWidth = EFB_WIDTH / 2.0f; + GLfloat halfHeight = EFB_HEIGHT / 2.0f; + GLfloat x = (GLfloat) -1.0f + ((GLfloat)it->left / halfWidth); + GLfloat y = (GLfloat) 1.0f - ((GLfloat)it->top / halfHeight); + GLfloat x2 = (GLfloat) -1.0f + ((GLfloat)it->right / halfWidth); + GLfloat y2 = (GLfloat) 1.0f - ((GLfloat)it->bottom / halfHeight); + + // Draw shadow of rect + glColor3f(0.0f, 0.0f, 0.0f); + glVertex2f(x, y - 0.01); glVertex2f(x2, y - 0.01); + glVertex2f(x, y2 - 0.01); glVertex2f(x2, y2 - 0.01); + glVertex2f(x + 0.005, y); glVertex2f(x + 0.005, y2); + glVertex2f(x2 + 0.005, y); glVertex2f(x2 + 0.005, y2); + + // Draw rect + glColor3f(0.0f, 1.0f, 1.0f); + glVertex2f(x, y); glVertex2f(x2, y); + glVertex2f(x, y2); glVertex2f(x2, y2); + glVertex2f(x, y); glVertex2f(x, y2); + glVertex2f(x2, y); glVertex2f(x2, y2); + } + + glEnd(); + + // Restore Line Size + glLineWidth(lSize); + + // Clear stored regions + stats.efb_regions.clear(); + } + + if (g_ActiveConfig.bOverlayStats) + p = Statistics::ToString(p); + + if (g_ActiveConfig.bOverlayProjStats) + p = Statistics::ToStringProj(p); + + // Render a shadow, and then the text. + if (p != debugtext_buffer) + { + Renderer::RenderText(debugtext_buffer, 21, 21, 0xDD000000); + Renderer::RenderText(debugtext_buffer, 20, 20, 0xFF00FFFF); + } + + // OSD Menu messages + if (g_ActiveConfig.bOSDHotKey) + { + if (OSDChoice > 0) + { + OSDTime = Common::Timer::GetTimeMs() + 3000; + OSDChoice = -OSDChoice; + } + if ((u32)OSDTime > Common::Timer::GetTimeMs()) + { + std::string T1 = "", T2 = ""; + std::vector T0; + + int W, H; + W = OpenGL_GetBackbufferWidth(); + H = OpenGL_GetBackbufferHeight(); + + std::string OSDM1 = + g_ActiveConfig.bNativeResolution || g_ActiveConfig.b2xResolution ? + (g_ActiveConfig.bNativeResolution ? + StringFromFormat("%i x %i (native)", OSDInternalW, OSDInternalH) + : StringFromFormat("%i x %i (2x)", OSDInternalW, OSDInternalH)) + : StringFromFormat("%i x %i (custom)", W, H); + std::string OSDM21; + switch(g_ActiveConfig.iAspectRatio) + { + case ASPECT_AUTO: + OSDM21 = "Auto"; + break; + case ASPECT_FORCE_16_9: + OSDM21 = "16:9"; + break; + case ASPECT_FORCE_4_3: + OSDM21 = "4:3"; + break; + case ASPECT_STRETCH: + OSDM21 = "Stretch"; + break; + } + std::string OSDM22 = + g_ActiveConfig.bCrop ? " (crop)" : ""; + std::string OSDM3 = g_ActiveConfig.bEFBCopyDisable ? "Disabled" : + g_ActiveConfig.bCopyEFBToTexture ? "To Texture" : "To RAM"; + + // If there is more text than this we will have a collision + if (g_ActiveConfig.bShowFPS) + { + T1 += "\n\n"; + T2 += "\n\n"; + } + + // The rows + T0.push_back(StringFromFormat("3: Internal Resolution: %s\n", OSDM1.c_str())); + T0.push_back(StringFromFormat("4: Aspect Ratio: %s%s\n", OSDM21.c_str(), OSDM22.c_str())); + T0.push_back(StringFromFormat("5: Copy EFB: %s\n", OSDM3.c_str())); + T0.push_back(StringFromFormat("6: Fog: %s\n", g_ActiveConfig.bDisableFog ? "Disabled" : "Enabled")); + T0.push_back(StringFromFormat("7: Material Lighting: %s\n", g_ActiveConfig.bDisableLighting ? "Disabled" : "Enabled")); + + // The latest changed setting in yellow + T1 += (OSDChoice == -1) ? T0.at(0) : "\n"; + T1 += (OSDChoice == -2) ? T0.at(1) : "\n"; + T1 += (OSDChoice == -3) ? T0.at(2) : "\n"; + T1 += (OSDChoice == -4) ? T0.at(3) : "\n"; + T1 += (OSDChoice == -5) ? T0.at(4) : "\n"; + + // The other settings in cyan + T2 += (OSDChoice != -1) ? T0.at(0) : "\n"; + T2 += (OSDChoice != -2) ? T0.at(1) : "\n"; + T2 += (OSDChoice != -3) ? T0.at(2) : "\n"; + T2 += (OSDChoice != -4) ? T0.at(3) : "\n"; + T2 += (OSDChoice != -5) ? T0.at(4) : "\n"; + + // Render a shadow, and then the text + Renderer::RenderText(T1.c_str(), 21, 21, 0xDD000000); + Renderer::RenderText(T1.c_str(), 20, 20, 0xFFffff00); + Renderer::RenderText(T2.c_str(), 21, 21, 0xDD000000); + Renderer::RenderText(T2.c_str(), 20, 20, 0xFF00FFFF); + } + } +} + +void Renderer::RenderText(const char *text, int left, int top, u32 color) +{ + int nBackbufferWidth = (int)OpenGL_GetBackbufferWidth(); + int nBackbufferHeight = (int)OpenGL_GetBackbufferHeight(); + glColor4f(((color>>16) & 0xff)/255.0f, ((color>> 8) & 0xff)/255.0f, + ((color>> 0) & 0xff)/255.0f, ((color>>24) & 0xFF)/255.0f); + s_pfont->printMultilineText(text, + left * 2.0f / (float)nBackbufferWidth - 1, + 1 - top * 2.0f / (float)nBackbufferHeight, + 0, nBackbufferWidth, nBackbufferHeight); + GL_REPORT_ERRORD(); +} + TargetRectangle Renderer::ConvertEFBRectangle(const EFBRectangle& rc) { return g_framebufferManager.ConvertEFBRectangle(rc); } -void Renderer::ResetAPIState() +void Renderer::RenderToXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight, const EFBRectangle& sourceRc) { - // Gets us to a reasonably sane state where it's possible to do things like - // image copies with textured quads, etc. - VertexShaderCache::DisableShader(); - PixelShaderCache::DisableShader(); - glDisable(GL_SCISSOR_TEST); - glDisable(GL_DEPTH_TEST); - glDisable(GL_CULL_FACE); - glDisable(GL_BLEND); - glDepthMask(GL_FALSE); - glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE); -} - -void UpdateViewport(); - -void Renderer::RestoreAPIState() -{ - // Gets us back into a more game-like state. - - UpdateViewport(); - - if (bpmem.genMode.cullmode > 0) glEnable(GL_CULL_FACE); - if (bpmem.zmode.testenable) glEnable(GL_DEPTH_TEST); - if (bpmem.zmode.updateenable) glDepthMask(GL_TRUE); - - glEnable(GL_SCISSOR_TEST); - SetScissorRect(); - SetColorMask(); - SetBlendMode(true); - - VertexShaderCache::SetCurrentShader(0); - PixelShaderCache::SetCurrentShader(0); -} - -void Renderer::SetColorMask() -{ - GLenum ColorMask = (bpmem.blendmode.colorupdate) ? GL_TRUE : GL_FALSE; - GLenum AlphaMask = (bpmem.blendmode.alphaupdate) ? GL_TRUE : GL_FALSE; - glColorMask(ColorMask, ColorMask, ColorMask, AlphaMask); -} - -void Renderer::SetBlendMode(bool forceUpdate) -{ - // blend mode bit mask - // 0 - blend enable - // 2 - reverse subtract enable (else add) - // 3-5 - srcRGB function - // 6-8 - dstRGB function - - u32 newval = bpmem.blendmode.subtract << 2; - - if (bpmem.blendmode.subtract) - newval |= 0x0049; // enable blending src 1 dst 1 - else if (bpmem.blendmode.blendenable) + if (!fbWidth || !fbHeight) + return; + s_skipSwap = g_bSkipCurrentFrame; + VideoFifo_CheckEFBAccess(); + VideoFifo_CheckSwapRequestAt(xfbAddr, fbWidth, fbHeight); + XFBWrited = true; + // XXX: Without the VI, how would we know what kind of field this is? So + // just use progressive. + if (g_ActiveConfig.bUseXFB) { - newval |= 1; // enable blending - newval |= bpmem.blendmode.srcfactor << 3; - newval |= bpmem.blendmode.dstfactor << 6; + g_framebufferManager.CopyToXFB(xfbAddr, fbWidth, fbHeight, sourceRc); } - - u32 changes = forceUpdate ? 0xFFFFFFFF : newval ^ s_blendMode; - - 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); - - if (changes & 0x1F8) - // blend RGB change - glBlendFunc(glSrcFactors[(newval >> 3) & 7], glDestFactors[(newval >> 6) & 7]); - - s_blendMode = newval; -} - -u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) -{ - if(!g_ActiveConfig.bEFBAccessEnable) - return 0; - - // Get the rectangular target region covered by the EFB pixel. - EFBRectangle efbPixelRc; - efbPixelRc.left = x; - efbPixelRc.top = y; - efbPixelRc.right = x + 1; - efbPixelRc.bottom = y + 1; - - TargetRectangle targetPixelRc = Renderer::ConvertEFBRectangle(efbPixelRc); - - // TODO (FIX) : currently, AA path is broken/offset and doesn't return the correct pixel - switch (type) + else { - - case PEEK_Z: - { - if (s_MSAASamples > 1) - { - // Resolve our rectangle. - g_framebufferManager.GetEFBDepthTexture(efbPixelRc); - glBindFramebufferEXT(GL_READ_FRAMEBUFFER_EXT, g_framebufferManager.GetResolvedFramebuffer()); - } - - // Sample from the center of the target region. - int srcX = (targetPixelRc.left + targetPixelRc.right) / 2; - int srcY = (targetPixelRc.top + targetPixelRc.bottom) / 2; - - u32 z = 0; - glReadPixels(srcX, srcY, 1, 1, GL_DEPTH_COMPONENT, GL_UNSIGNED_INT, &z); - GL_REPORT_ERRORD(); - - // Scale the 32-bit value returned by glReadPixels to a 24-bit - // value (GC uses a 24-bit Z-buffer). - // TODO: in RE0 this value is often off by one, which causes lighting to disappear - return z >> 8; + Renderer::Swap(xfbAddr, FIELD_PROGRESSIVE, fbWidth, fbHeight,sourceRc); + Common::AtomicStoreRelease(s_swapRequested, FALSE); } - - case POKE_Z: - // TODO: Implement - break; - - case PEEK_COLOR: // GXPeekARGB - { - // Although it may sound strange, this really is A8R8G8B8 and not RGBA or 24-bit... - - // Tested in Killer 7, the first 8bits represent the alpha value which is used to - // determine if we're aiming at an enemy (0x80 / 0x88) or not (0x70) - // Wind Waker is also using it for the pictograph to determine the color of each pixel - - if (s_MSAASamples > 1) - { - // Resolve our rectangle. - g_framebufferManager.GetEFBColorTexture(efbPixelRc); - glBindFramebufferEXT(GL_READ_FRAMEBUFFER_EXT, g_framebufferManager.GetResolvedFramebuffer()); - } - - // Sample from the center of the target region. - int srcX = (targetPixelRc.left + targetPixelRc.right) / 2; - int srcY = (targetPixelRc.top + targetPixelRc.bottom) / 2; - - // Read back pixel in BGRA format, then byteswap to get GameCube's ARGB Format. - u32 color = 0; - glReadPixels(srcX, srcY, 1, 1, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, &color); - GL_REPORT_ERRORD(); - - return color; - } - - case POKE_COLOR: - // TODO: Implement. One way is to draw a tiny pixel-sized rectangle at - // the exact location. Note: EFB pokes are susceptible to Z-buffering - // and perhaps blending. - //WARN_LOG(VIDEOINTERFACE, "This is probably some kind of software rendering"); - break; - - } - - return 0; } // Function: This function handles the OpenGL glScissor() function @@ -819,8 +826,138 @@ bool Renderer::SetScissorRect() return false; } -void Renderer::ClearScreen(const EFBRectangle& rc, bool colorEnable, - bool alphaEnable, bool zEnable, u32 color, u32 z) +void Renderer::SetColorMask() +{ + GLenum ColorMask = (bpmem.blendmode.colorupdate) ? GL_TRUE : GL_FALSE; + GLenum AlphaMask = (bpmem.blendmode.alphaupdate) ? GL_TRUE : GL_FALSE; + glColorMask(ColorMask, ColorMask, ColorMask, AlphaMask); +} + +u32 Renderer::AccessEFB(EFBAccessType type, int x, int y) +{ + if(!g_ActiveConfig.bEFBAccessEnable) + return 0; + + // Get the rectangular target region covered by the EFB pixel + EFBRectangle efbPixelRc; + efbPixelRc.left = x; + efbPixelRc.top = y; + efbPixelRc.right = x + 1; + efbPixelRc.bottom = y + 1; + + TargetRectangle targetPixelRc = Renderer::ConvertEFBRectangle(efbPixelRc); + + // TODO (FIX) : currently, AA path is broken/offset and doesn't return the correct pixel + switch (type) + { + case PEEK_Z: + { + if (s_MSAASamples > 1) + { + // Resolve our rectangle. + g_framebufferManager.GetEFBDepthTexture(efbPixelRc); + glBindFramebufferEXT(GL_READ_FRAMEBUFFER_EXT, g_framebufferManager.GetResolvedFramebuffer()); + } + + // Sample from the center of the target region. + int srcX = (targetPixelRc.left + targetPixelRc.right) / 2; + int srcY = (targetPixelRc.top + targetPixelRc.bottom) / 2; + + u32 z = 0; + glReadPixels(srcX, srcY, 1, 1, GL_DEPTH_COMPONENT, GL_UNSIGNED_INT, &z); + GL_REPORT_ERRORD(); + + // Scale the 32-bit value returned by glReadPixels to a 24-bit + // value (GC uses a 24-bit Z-buffer). + // TODO: in RE0 this value is often off by one, which causes lighting to disappear + return z >> 8; + } + + case POKE_Z: + // TODO: Implement + break; + + case PEEK_COLOR: // GXPeekARGB + { + // Although it may sound strange, this really is A8R8G8B8 and not RGBA or 24-bit... + + // Tested in Killer 7, the first 8bits represent the alpha value which is used to + // determine if we're aiming at an enemy (0x80 / 0x88) or not (0x70) + // Wind Waker is also using it for the pictograph to determine the color of each pixel + + if (s_MSAASamples > 1) + { + // Resolve our rectangle. + g_framebufferManager.GetEFBColorTexture(efbPixelRc); + glBindFramebufferEXT(GL_READ_FRAMEBUFFER_EXT, g_framebufferManager.GetResolvedFramebuffer()); + } + + // Sample from the center of the target region. + int srcX = (targetPixelRc.left + targetPixelRc.right) / 2; + int srcY = (targetPixelRc.top + targetPixelRc.bottom) / 2; + + // Read back pixel in BGRA format, then byteswap to get GameCube's ARGB Format. + u32 color = 0; + glReadPixels(srcX, srcY, 1, 1, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, &color); + GL_REPORT_ERRORD(); + + return color; + } + + case POKE_COLOR: + // TODO: Implement. One way is to draw a tiny pixel-sized rectangle at + // the exact location. Note: EFB pokes are susceptible to Z-buffering + // and perhaps blending. + //WARN_LOG(VIDEOINTERFACE, "This is probably some kind of software rendering"); + break; + + // TODO: Implement POKE_Z and POKE_COLOR + default: + break; + } + + return 0; +} + +// Called from VertexShaderManager +void UpdateViewport() +{ + // reversed gxsetviewport(xorig, yorig, width, height, nearz, farz) + // [0] = width/2 + // [1] = height/2 + // [2] = 16777215 * (farz - nearz) + // [3] = xorig + width/2 + 342 + // [4] = yorig + height/2 + 342 + // [5] = 16777215 * farz + float scissorXOff = float(bpmem.scissorOffset.x) * 2.0f; // 342 + float scissorYOff = float(bpmem.scissorOffset.y) * 2.0f; // 342 + + // Stretch picture with increased internal resolution + int GLx = (int)ceil((xfregs.rawViewport[3] - xfregs.rawViewport[0] - scissorXOff) * + EFBxScale); + int GLy = (int)ceil( + (float(EFB_HEIGHT) - xfregs.rawViewport[4] + xfregs.rawViewport[1] + scissorYOff) * + EFByScale); + int GLWidth = (int)ceil(2.0f * xfregs.rawViewport[0] * EFBxScale); + int GLHeight = (int)ceil(-2.0f * xfregs.rawViewport[1] * EFByScale); + double GLNear = (xfregs.rawViewport[5] - xfregs.rawViewport[2]) / 16777216.0f; + double GLFar = xfregs.rawViewport[5] / 16777216.0f; + if(GLWidth < 0) + { + GLx += GLWidth; + GLWidth*=-1; + } + if(GLHeight < 0) + { + GLy += GLHeight; + GLHeight *= -1; + } + // Update the view port + glViewport(GLx, GLy, GLWidth, GLHeight); + glDepthRange(GLNear, GLFar); +} + +void Renderer::ClearScreen(const EFBRectangle& rc, bool colorEnable, bool alphaEnable, bool zEnable, u32 color, u32 z) { // Update the view port for clearing the picture TargetRectangle targetRc = Renderer::ConvertEFBRectangle(rc); @@ -853,41 +990,60 @@ void Renderer::ClearScreen(const EFBRectangle& rc, bool colorEnable, SetScissorRect(); } -static bool XFBWrited = false; -void Renderer::RenderToXFB(u32 xfbAddr, u32 fbWidth, u32 fbHeight, const EFBRectangle& sourceRc) +void Renderer::SetBlendMode(bool forceUpdate) { - if(!fbWidth || !fbHeight) - return; - s_skipSwap = g_bSkipCurrentFrame; - VideoFifo_CheckEFBAccess(); - VideoFifo_CheckSwapRequestAt(xfbAddr, fbWidth, fbHeight); - XFBWrited = true; - // XXX: Without the VI, how would we know what kind of field this is? So - // just use progressive. - if (g_ActiveConfig.bUseXFB) - g_framebufferManager.CopyToXFB(xfbAddr, fbWidth, fbHeight, sourceRc); - else + // blend mode bit mask + // 0 - blend enable + // 2 - reverse subtract enable (else add) + // 3-5 - srcRGB function + // 6-8 - dstRGB function + + u32 newval = bpmem.blendmode.subtract << 2; + + if (bpmem.blendmode.subtract) + newval |= 0x0049; // enable blending src 1 dst 1 + else if (bpmem.blendmode.blendenable) { - Renderer::Swap(xfbAddr, FIELD_PROGRESSIVE, fbWidth, fbHeight,sourceRc); - Common::AtomicStoreRelease(s_swapRequested, FALSE); + newval |= 1; // enable blending + newval |= bpmem.blendmode.srcfactor << 3; + newval |= bpmem.blendmode.dstfactor << 6; } + + u32 changes = forceUpdate ? 0xFFFFFFFF : newval ^ s_blendMode; + + 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); + + if (changes & 0x1F8) + // blend RGB change + glBlendFunc(glSrcFactors[(newval >> 3) & 7], glDestFactors[(newval >> 6) & 7]); + + s_blendMode = newval; } // This function has the final picture. We adjust the aspect ratio here. -void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,const EFBRectangle& Rc) +void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,const EFBRectangle& rc) { if (g_bSkipCurrentFrame || (!XFBWrited && !g_ActiveConfig.bUseRealXFB) || !fbWidth || !fbHeight) { g_VideoInitialize.pCopiedToXFB(false); return; } + // this function is called after the XFB field is changed, not after + // EFB is copied to XFB. In this way, flickering is reduced in games + // and seems to also give more FPS in ZTP + if (field == FIELD_LOWER) xfbAddr -= fbWidth * 2; u32 xfbCount = 0; const XFBSource** xfbSourceList = g_framebufferManager.GetXFBSource(xfbAddr, fbWidth, fbHeight, xfbCount); if ((!xfbSourceList || xfbCount == 0) && g_ActiveConfig.bUseXFB && !g_ActiveConfig.bUseRealXFB) { g_VideoInitialize.pCopiedToXFB(false); - WARN_LOG(VIDEO, "Failed to get video for this frame"); return; } @@ -895,7 +1051,7 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons ResetAPIState(); TargetRectangle back_rc; - ComputeDrawRectangle(m_CustomWidth, m_CustomHeight, true, &back_rc); + ComputeDrawRectangle(s_backbuffer_width, s_backbuffer_height, true, &back_rc); // Make sure that the wireframe setting doesn't screw up the screen copy. glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); @@ -904,7 +1060,7 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons // Disable all other stages for (int i = 1; i < 8; ++i) - TextureMngr::DisableStage(i); + TextureCache::DisableStage(i); // Update GLViewPort glViewport(back_rc.left, back_rc.bottom, back_rc.GetWidth(), back_rc.GetHeight()); @@ -996,38 +1152,38 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons if (applyShader) { glBegin(GL_QUADS); - glTexCoord2f(sourceRc.left, sourceRc.bottom); - glMultiTexCoord2fARB(GL_TEXTURE1, 0, 0); - glVertex2f(drawRc.left, drawRc.bottom); + glTexCoord2f(sourceRc.left, sourceRc.bottom); + glMultiTexCoord2fARB(GL_TEXTURE1, 0, 0); + glVertex2f(drawRc.left, drawRc.bottom); - glTexCoord2f(sourceRc.left, sourceRc.top); - glMultiTexCoord2fARB(GL_TEXTURE1, 0, 1); - glVertex2f(drawRc.left, drawRc.top); + glTexCoord2f(sourceRc.left, sourceRc.top); + glMultiTexCoord2fARB(GL_TEXTURE1, 0, 1); + glVertex2f(drawRc.left, drawRc.top); - glTexCoord2f(sourceRc.right, sourceRc.top); - glMultiTexCoord2fARB(GL_TEXTURE1, 1, 1); - glVertex2f(drawRc.right, drawRc.top); + glTexCoord2f(sourceRc.right, sourceRc.top); + glMultiTexCoord2fARB(GL_TEXTURE1, 1, 1); + glVertex2f(drawRc.right, drawRc.top); - glTexCoord2f(sourceRc.right, sourceRc.bottom); - glMultiTexCoord2fARB(GL_TEXTURE1, 1, 0); - glVertex2f(drawRc.right, drawRc.bottom); + glTexCoord2f(sourceRc.right, sourceRc.bottom); + glMultiTexCoord2fARB(GL_TEXTURE1, 1, 0); + glVertex2f(drawRc.right, drawRc.bottom); glEnd(); PixelShaderCache::DisableShader(); } else { glBegin(GL_QUADS); - glTexCoord2f(sourceRc.left, sourceRc.bottom); - glVertex2f(drawRc.left, drawRc.bottom); + glTexCoord2f(sourceRc.left, sourceRc.bottom); + glVertex2f(drawRc.left, drawRc.bottom); - glTexCoord2f(sourceRc.left, sourceRc.top); - glVertex2f(drawRc.left, drawRc.top); + glTexCoord2f(sourceRc.left, sourceRc.top); + glVertex2f(drawRc.left, drawRc.top); - glTexCoord2f(sourceRc.right, sourceRc.top); - glVertex2f(drawRc.right, drawRc.top); + glTexCoord2f(sourceRc.right, sourceRc.top); + glVertex2f(drawRc.right, drawRc.top); - glTexCoord2f(sourceRc.right, sourceRc.bottom); - glVertex2f(drawRc.right, drawRc.bottom); + glTexCoord2f(sourceRc.right, sourceRc.bottom); + glVertex2f(drawRc.right, drawRc.bottom); glEnd(); } @@ -1036,52 +1192,52 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons } else { - TargetRectangle targetRc = Renderer::ConvertEFBRectangle(Rc); - GLuint read_texture = g_framebufferManager.ResolveAndGetRenderTarget(Rc); + TargetRectangle targetRc = Renderer::ConvertEFBRectangle(rc); + GLuint read_texture = g_framebufferManager.ResolveAndGetRenderTarget(rc); // Render to the real buffer now. glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0); // switch to the window backbuffer glBindTexture(GL_TEXTURE_RECTANGLE_ARB, read_texture); if (applyShader) { glBegin(GL_QUADS); - glTexCoord2f(targetRc.left, targetRc.bottom); - glMultiTexCoord2fARB(GL_TEXTURE1, 0, 0); - glVertex2f(-1, -1); + glTexCoord2f(targetRc.left, targetRc.bottom); + glMultiTexCoord2fARB(GL_TEXTURE1, 0, 0); + glVertex2f(-1, -1); - glTexCoord2f(targetRc.left, targetRc.top); - glMultiTexCoord2fARB(GL_TEXTURE1, 0, 1); - glVertex2f(-1, 1); + glTexCoord2f(targetRc.left, targetRc.top); + glMultiTexCoord2fARB(GL_TEXTURE1, 0, 1); + glVertex2f(-1, 1); - glTexCoord2f(targetRc.right, targetRc.top); - glMultiTexCoord2fARB(GL_TEXTURE1, 1, 1); - glVertex2f( 1, 1); + glTexCoord2f(targetRc.right, targetRc.top); + glMultiTexCoord2fARB(GL_TEXTURE1, 1, 1); + glVertex2f( 1, 1); - glTexCoord2f(targetRc.right, targetRc.bottom); - glMultiTexCoord2fARB(GL_TEXTURE1, 1, 0); - glVertex2f( 1, -1); + glTexCoord2f(targetRc.right, targetRc.bottom); + glMultiTexCoord2fARB(GL_TEXTURE1, 1, 0); + glVertex2f( 1, -1); glEnd(); PixelShaderCache::DisableShader(); } else { glBegin(GL_QUADS); - glTexCoord2f(targetRc.left, targetRc.bottom); - glVertex2f(-1, -1); + glTexCoord2f(targetRc.left, targetRc.bottom); + glVertex2f(-1, -1); - glTexCoord2f(targetRc.left, targetRc.top); - glVertex2f(-1, 1); + glTexCoord2f(targetRc.left, targetRc.top); + glVertex2f(-1, 1); - glTexCoord2f(targetRc.right, targetRc.top); - glVertex2f( 1, 1); + glTexCoord2f(targetRc.right, targetRc.top); + glVertex2f( 1, 1); - glTexCoord2f(targetRc.right, targetRc.bottom); - glVertex2f( 1, -1); + glTexCoord2f(targetRc.right, targetRc.bottom); + glVertex2f( 1, -1); glEnd(); } } glBindTexture(GL_TEXTURE_RECTANGLE_ARB, 0); - TextureMngr::DisableStage(0); + TextureCache::DisableStage(0); if(g_ActiveConfig.bAnaglyphStereo) glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE); // Wireframe @@ -1137,7 +1293,7 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons } else { - if(s_bLastFrameDumped && s_bAVIDumping) + if (s_bLastFrameDumped && s_bAVIDumping) { AVIDump::Stop(); s_bAVIDumping = false; @@ -1192,33 +1348,34 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons s_bLastFrameDumped = false; } #endif - + // Finish up the current frame, print some stats OpenGL_Update(); // just updates the render window position and the backbuffer size bool xfbchanged = false; - if(s_XFB_width != fbWidth || s_XFB_height != fbHeight) + + if (s_XFB_width != fbWidth || s_XFB_height != fbHeight) { xfbchanged = true; s_XFB_width = fbWidth; s_XFB_height = fbHeight; - if(s_XFB_width < 1) s_XFB_width = MAX_XFB_WIDTH; - if(s_XFB_width > MAX_XFB_WIDTH) s_XFB_width = MAX_XFB_WIDTH; - if(s_XFB_height < 1) s_XFB_height = MAX_XFB_HEIGHT; - if(s_XFB_height > MAX_XFB_HEIGHT) s_XFB_height = MAX_XFB_HEIGHT; - + if (s_XFB_width < 1) s_XFB_width = MAX_XFB_WIDTH; + if (s_XFB_width > MAX_XFB_WIDTH) s_XFB_width = MAX_XFB_WIDTH; + if (s_XFB_height < 1) s_XFB_height = MAX_XFB_HEIGHT; + if (s_XFB_height > MAX_XFB_HEIGHT) s_XFB_height = MAX_XFB_HEIGHT; } + bool WindowResized = false; int W = (int)OpenGL_GetBackbufferWidth(), H = (int)OpenGL_GetBackbufferHeight(); - if (W != m_CustomWidth || H != m_CustomHeight) + if (W != s_backbuffer_width || H != s_backbuffer_height) { WindowResized = true; - m_CustomWidth = W; - m_CustomHeight = H; + s_backbuffer_width = W; + s_backbuffer_height = H; } if( xfbchanged || WindowResized) { TargetRectangle dst_rect; - ComputeDrawRectangle(m_CustomWidth, m_CustomHeight, false, &dst_rect); + ComputeDrawRectangle(s_backbuffer_width, s_backbuffer_height, false, &dst_rect); xScale = 1.0f; yScale = 1.0f; @@ -1242,18 +1399,17 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons int m_newFrameBufferWidth = EFB_WIDTH * EFBxScale; int m_newFrameBufferHeight = EFB_HEIGHT * EFByScale; - if(m_newFrameBufferWidth != m_FrameBufferWidth || - m_newFrameBufferHeight != m_FrameBufferHeight ) + if(m_newFrameBufferWidth != s_target_width || + m_newFrameBufferHeight != s_target_height ) { - m_FrameBufferWidth = m_newFrameBufferWidth; - m_FrameBufferHeight = m_newFrameBufferHeight; + s_target_width = m_newFrameBufferWidth; + s_target_height = m_newFrameBufferHeight; g_framebufferManager.Shutdown(); - g_framebufferManager.Init(m_FrameBufferWidth, m_FrameBufferHeight, - s_MSAASamples, s_MSAACoverageSamples); + g_framebufferManager.Init(s_target_width, s_target_height, + s_MSAASamples, s_MSAACoverageSamples); glDrawBuffer(GL_COLOR_ATTACHMENT0_EXT); } - } // Place messages on the picture, then copy it to the screen @@ -1268,7 +1424,8 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons s_fps = fpscount; fpscount = 0; } - ++fpscount; + if (XFBWrited) + ++fpscount; // --------------------------------------------------------------------- GL_REPORT_ERRORD(); @@ -1315,10 +1472,12 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons // Clean out old stuff from caches. It's not worth it to clean out the shader caches. DLCache::ProgressiveCleanup(); - TextureMngr::ProgressiveCleanup(); + TextureCache::Cleanup(); frameCount++; + // Begin new frame + // Set default viewport and scissor, for the clear to work correctly // New frame stats.ResetFrame(); @@ -1335,7 +1494,7 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons bool last_copy_efb_to_Texture = g_ActiveConfig.bCopyEFBToTexture; UpdateActiveConfig(); if (last_copy_efb_to_Texture != g_ActiveConfig.bCopyEFBToTexture) - TextureMngr::ClearRenderTargets(); + TextureCache::ClearRenderTargets(); // For testing zbuffer targets. // Renderer::SetZBufferRender(); @@ -1345,172 +1504,108 @@ void Renderer::Swap(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight,cons XFBWrited = false; } -// Create On-Screen-Messages -void Renderer::DrawDebugText() +// ALWAYS call RestoreAPIState for each ResetAPIState call you're doing +void Renderer::ResetAPIState() { - // Reset viewport for drawing text - glViewport(0, 0, OpenGL_GetBackbufferWidth(), OpenGL_GetBackbufferHeight()); - // Draw various messages on the screen, like FPS, statistics, etc. - char debugtext_buffer[8192]; - char *p = debugtext_buffer; - p[0] = 0; + // Gets us to a reasonably sane state where it's possible to do things like + // image copies with textured quads, etc. + VertexShaderCache::DisableShader(); + PixelShaderCache::DisableShader(); + glDisable(GL_SCISSOR_TEST); + glDisable(GL_DEPTH_TEST); + glDisable(GL_CULL_FACE); + glDisable(GL_BLEND); + glDepthMask(GL_FALSE); + glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE); +} - if (g_ActiveConfig.bShowFPS) - p+=sprintf(p, "FPS: %d\n", s_fps); +void Renderer::RestoreAPIState() +{ + // Gets us back into a more game-like state. - if (g_ActiveConfig.bShowEFBCopyRegions) + UpdateViewport(); + + if (bpmem.genMode.cullmode > 0) glEnable(GL_CULL_FACE); + if (bpmem.zmode.testenable) glEnable(GL_DEPTH_TEST); + if (bpmem.zmode.updateenable) glDepthMask(GL_TRUE); + + glEnable(GL_SCISSOR_TEST); + SetScissorRect(); + SetColorMask(); + SetBlendMode(true); + + VertexShaderCache::SetCurrentShader(0); + PixelShaderCache::SetCurrentShader(0); +} + +void Renderer::SetGenerationMode() +{ + // none, ccw, cw, ccw + if (bpmem.genMode.cullmode > 0) { - // Store Line Size - GLfloat lSize; - glGetFloatv(GL_LINE_WIDTH, &lSize); - - // Set Line Size - glLineWidth(3.0f); - - glBegin(GL_LINES); - - // Draw EFB copy regions rectangles - for (std::vector::const_iterator it = stats.efb_regions.begin(); - it != stats.efb_regions.end(); ++it) - { - GLfloat halfWidth = EFB_WIDTH / 2.0f; - GLfloat halfHeight = EFB_HEIGHT / 2.0f; - GLfloat x = (GLfloat) -1.0f + ((GLfloat)it->left / halfWidth); - GLfloat y = (GLfloat) 1.0f - ((GLfloat)it->top / halfHeight); - GLfloat x2 = (GLfloat) -1.0f + ((GLfloat)it->right / halfWidth); - GLfloat y2 = (GLfloat) 1.0f - ((GLfloat)it->bottom / halfHeight); - - // Draw shadow of rect - glColor3f(0.0f, 0.0f, 0.0f); - glVertex2f(x, y - 0.01); glVertex2f(x2, y - 0.01); - glVertex2f(x, y2 - 0.01); glVertex2f(x2, y2 - 0.01); - glVertex2f(x + 0.005, y); glVertex2f(x + 0.005, y2); - glVertex2f(x2 + 0.005, y); glVertex2f(x2 + 0.005, y2); - - // Draw rect - glColor3f(0.0f, 1.0f, 1.0f); - glVertex2f(x, y); glVertex2f(x2, y); - glVertex2f(x, y2); glVertex2f(x2, y2); - glVertex2f(x, y); glVertex2f(x, y2); - glVertex2f(x2, y); glVertex2f(x2, y2); - } - - glEnd(); - - // Restore Line Size - glLineWidth(lSize); - - // Clear stored regions - stats.efb_regions.clear(); + glEnable(GL_CULL_FACE); + glFrontFace(bpmem.genMode.cullmode == 2 ? GL_CCW : GL_CW); } + else + glDisable(GL_CULL_FACE); +} - if (g_ActiveConfig.bOverlayStats) - p = Statistics::ToString(p); - - if (g_ActiveConfig.bOverlayProjStats) - p = Statistics::ToStringProj(p); - - // Render a shadow, and then the text. - if (p != debugtext_buffer) +void Renderer::SetDepthMode() +{ + if (bpmem.zmode.testenable) { - Renderer::RenderText(debugtext_buffer, 21, 21, 0xDD000000); - Renderer::RenderText(debugtext_buffer, 20, 20, 0xFF00FFFF); + glEnable(GL_DEPTH_TEST); + glDepthMask(bpmem.zmode.updateenable ? GL_TRUE : GL_FALSE); + glDepthFunc(glCmpFuncs[bpmem.zmode.func]); } - - // OSD Menu messages - if (g_ActiveConfig.bOSDHotKey) + else { - if (OSDChoice > 0) - { - OSDTime = Common::Timer::GetTimeMs() + 3000; - OSDChoice = -OSDChoice; - } - if ((u32)OSDTime > Common::Timer::GetTimeMs()) - { - std::string T1 = "", T2 = ""; - std::vector T0; - - int W, H; - W = OpenGL_GetBackbufferWidth(); - H = OpenGL_GetBackbufferHeight(); - - std::string OSDM1 = - g_ActiveConfig.bNativeResolution || g_ActiveConfig.b2xResolution ? - (g_ActiveConfig.bNativeResolution ? - StringFromFormat("%i x %i (native)", OSDInternalW, OSDInternalH) - : StringFromFormat("%i x %i (2x)", OSDInternalW, OSDInternalH)) - : StringFromFormat("%i x %i (custom)", W, H); - std::string OSDM21; - switch(g_ActiveConfig.iAspectRatio) - { - case ASPECT_AUTO: - OSDM21 = "Auto"; - break; - case ASPECT_FORCE_16_9: - OSDM21 = "16:9"; - break; - case ASPECT_FORCE_4_3: - OSDM21 = "4:3"; - break; - case ASPECT_STRETCH: - OSDM21 = "Stretch"; - break; - } - std::string OSDM22 = - g_ActiveConfig.bCrop ? " (crop)" : ""; - std::string OSDM3 = g_ActiveConfig.bEFBCopyDisable ? "Disabled" : - g_ActiveConfig.bCopyEFBToTexture ? "To Texture" : "To RAM"; - - // If there is more text than this we will have a collission - if (g_ActiveConfig.bShowFPS) - { T1 += "\n\n"; T2 += "\n\n"; } - - // The rows - T0.push_back(StringFromFormat("3: Internal Resolution: %s\n", - OSDM1.c_str())); - T0.push_back(StringFromFormat("4: Aspect Ratio: %s%s\n", - OSDM21.c_str(), OSDM22.c_str())); - T0.push_back(StringFromFormat("5: Copy EFB: %s\n", - OSDM3.c_str())); - T0.push_back(StringFromFormat("6: Fog: %s\n", - g_ActiveConfig.bDisableFog ? "Disabled" : "Enabled")); - T0.push_back(StringFromFormat("7: Material Lighting: %s\n", - g_ActiveConfig.bDisableLighting ? "Disabled" : "Enabled")); - - // The latest changed setting in yellow - T1 += (OSDChoice == -1) ? T0.at(0) : "\n"; - T1 += (OSDChoice == -2) ? T0.at(1) : "\n"; - T1 += (OSDChoice == -3) ? T0.at(2) : "\n"; - T1 += (OSDChoice == -4) ? T0.at(3) : "\n"; - T1 += (OSDChoice == -5) ? T0.at(4) : "\n"; - - // The other settings in cyan - T2 += (OSDChoice != -1) ? T0.at(0) : "\n"; - T2 += (OSDChoice != -2) ? T0.at(1) : "\n"; - T2 += (OSDChoice != -3) ? T0.at(2) : "\n"; - T2 += (OSDChoice != -4) ? T0.at(3) : "\n"; - T2 += (OSDChoice != -5) ? T0.at(4) : "\n"; - - // Render a shadow, and then the text - Renderer::RenderText(T1.c_str(), 21, 21, 0xDD000000); - Renderer::RenderText(T1.c_str(), 20, 20, 0xFFffff00); - Renderer::RenderText(T2.c_str(), 21, 21, 0xDD000000); - Renderer::RenderText(T2.c_str(), 20, 20, 0xFF00FFFF); - } + // if the test is disabled write is disabled too + glDisable(GL_DEPTH_TEST); + glDepthMask(GL_FALSE); } } -void Renderer::RenderText(const char* pstr, int left, int top, u32 color) +void Renderer::SetLogicOpMode() { - int nBackbufferWidth = (int)OpenGL_GetBackbufferWidth(); - int nBackbufferHeight = (int)OpenGL_GetBackbufferHeight(); - glColor4f(((color>>16) & 0xff)/255.0f, ((color>> 8) & 0xff)/255.0f, - ((color>> 0) & 0xff)/255.0f, ((color>>24) & 0xFF)/255.0f); - s_pfont->printMultilineText(pstr, - left * 2.0f / (float)nBackbufferWidth - 1, - 1 - top * 2.0f / (float)nBackbufferHeight, - 0, nBackbufferWidth, nBackbufferHeight); - GL_REPORT_ERRORD(); + if (bpmem.blendmode.logicopenable && bpmem.blendmode.logicmode != 3) + { + glEnable(GL_COLOR_LOGIC_OP); + glLogicOp(glLogicOpCodes[bpmem.blendmode.logicmode]); + } + else + { + glDisable(GL_COLOR_LOGIC_OP); + } +} + +void Renderer::SetDitherMode() +{ + if (bpmem.blendmode.dither) + glEnable(GL_DITHER); + else + glDisable(GL_DITHER); +} + +void Renderer::SetLineWidth() +{ + float fratio = xfregs.rawViewport[0] != 0 ? + ((float)Renderer::GetTargetWidth() / EFB_WIDTH) : 1.0f; + if (bpmem.lineptwidth.linesize > 0) + // scale by ratio of widths + glLineWidth((float)bpmem.lineptwidth.linesize * fratio / 6.0f); + if (bpmem.lineptwidth.pointsize > 0) + glPointSize((float)bpmem.lineptwidth.pointsize * fratio / 6.0f); +} + +void Renderer::SetSamplerState(int stage, int texindex) +{ + // TODO +} + +void Renderer::SetInterlacingMode() +{ + // TODO } // Save screenshot @@ -1522,6 +1617,37 @@ void Renderer::SetScreenshot(const char *filename) s_criticalScreenshot.Leave(); } +// For the OSD menu's live resolution change +bool Renderer::Allow2x() +{ + if (GetFrameBufferWidth() >= 1280 && GetFrameBufferHeight() >= 960) + return true; + else + return false; +} + +bool Renderer::AllowCustom() +{ + if (GetCustomWidth() <= GetFrameBufferWidth() && GetCustomHeight() <= GetFrameBufferHeight()) + return true; + else + return false; +} + +void Renderer::FlipImageData(u8 *data, int w, int h) +{ + // Flip image upside down. Damn OpenGL. + for (int y = 0; y < h / 2; y++) + { + for(int x = 0; x < w; x++) + { + std::swap(data[(y * w + x) * 3], data[((h - 1 - y) * w + x) * 3]); + std::swap(data[(y * w + x) * 3 + 1], data[((h - 1 - y) * w + x) * 3 + 1]); + std::swap(data[(y * w + x) * 3 + 2], data[((h - 1 - y) * w + x) * 3 + 2]); + } + } +} + #if defined(HAVE_WX) && HAVE_WX THREAD_RETURN TakeScreenshot(void *pArgs) { @@ -1558,32 +1684,18 @@ THREAD_RETURN TakeScreenshot(void *pArgs) // Save the screenshot and finally kill the wxImage object // This is really expensive when saving to PNG, but not at all when using BMP threadStruct->img->SaveFile(wxString::FromAscii(threadStruct->filename.c_str()), - wxBITMAP_TYPE_PNG); + wxBITMAP_TYPE_PNG); threadStruct->img->Destroy(); // Show success messages OSD::AddMessage(StringFromFormat("Saved %i x %i %s", (int)FloatW, (int)FloatH, - threadStruct->filename.c_str()).c_str(), 2000); + threadStruct->filename.c_str()).c_str(), 2000); delete threadStruct; return 0; } #endif -void Renderer::FlipImageData(u8 *data, int w, int h) -{ - // Flip image upside down. Damn OpenGL. - for (int y = 0; y < h / 2; y++) - { - for(int x = 0; x < w; x++) - { - std::swap(data[(y * w + x) * 3], data[((h - 1 - y) * w + x) * 3]); - std::swap(data[(y * w + x) * 3 + 1], data[((h - 1 - y) * w + x) * 3 + 1]); - std::swap(data[(y * w + x) * 3 + 2], data[((h - 1 - y) * w + x) * 3 + 2]); - } - } -} - bool Renderer::SaveRenderTarget(const char *filename, TargetRectangle back_rc) { u32 W = back_rc.GetWidth(); @@ -1633,109 +1745,3 @@ bool Renderer::SaveRenderTarget(const char *filename, TargetRectangle back_rc) return result; } - -// Called from VertexShaderManager -void UpdateViewport() -{ - // reversed gxsetviewport(xorig, yorig, width, height, nearz, farz) - // [0] = width/2 - // [1] = height/2 - // [2] = 16777215 * (farz - nearz) - // [3] = xorig + width/2 + 342 - // [4] = yorig + height/2 + 342 - // [5] = 16777215 * farz - float scissorXOff = float(bpmem.scissorOffset.x) * 2.0f; // 342 - float scissorYOff = float(bpmem.scissorOffset.y) * 2.0f; // 342 - - // Stretch picture with increased internal resolution - int GLx = (int)ceil((xfregs.rawViewport[3] - xfregs.rawViewport[0] - scissorXOff) * - EFBxScale); - int GLy = (int)ceil( - (float(EFB_HEIGHT) - xfregs.rawViewport[4] + xfregs.rawViewport[1] + scissorYOff) * - EFByScale); - int GLWidth = (int)ceil(2.0f * xfregs.rawViewport[0] * EFBxScale); - int GLHeight = (int)ceil(-2.0f * xfregs.rawViewport[1] * EFByScale); - double GLNear = (xfregs.rawViewport[5] - xfregs.rawViewport[2]) / 16777216.0f; - double GLFar = xfregs.rawViewport[5] / 16777216.0f; - if(GLWidth < 0) - { - GLx += GLWidth; - GLWidth*=-1; - } - if(GLHeight < 0) - { - GLy += GLHeight; - GLHeight *= -1; - } - // Update the view port - glViewport(GLx, GLy, GLWidth, GLHeight); - glDepthRange(GLNear, GLFar); -} - -void Renderer::SetGenerationMode() -{ - // none, ccw, cw, ccw - if (bpmem.genMode.cullmode > 0) - { - glEnable(GL_CULL_FACE); - glFrontFace(bpmem.genMode.cullmode == 2 ? GL_CCW : GL_CW); - } - else - glDisable(GL_CULL_FACE); -} - -void Renderer::SetDepthMode() -{ - if (bpmem.zmode.testenable) - { - glEnable(GL_DEPTH_TEST); - glDepthMask(bpmem.zmode.updateenable ? GL_TRUE : GL_FALSE); - glDepthFunc(glCmpFuncs[bpmem.zmode.func]); - } - else - { - // if the test is disabled write is disabled too - glDisable(GL_DEPTH_TEST); - glDepthMask(GL_FALSE); - } -} - -void Renderer::SetLogicOpMode() -{ - if (bpmem.blendmode.logicopenable && bpmem.blendmode.logicmode != 3) - { - glEnable(GL_COLOR_LOGIC_OP); - glLogicOp(glLogicOpCodes[bpmem.blendmode.logicmode]); - } - else - glDisable(GL_COLOR_LOGIC_OP); -} - -void Renderer::SetDitherMode() -{ - if (bpmem.blendmode.dither) - glEnable(GL_DITHER); - else - glDisable(GL_DITHER); -} - -void Renderer::SetLineWidth() -{ - float fratio = xfregs.rawViewport[0] != 0 ? - ((float)Renderer::GetTargetWidth() / EFB_WIDTH) : 1.0f; - if (bpmem.lineptwidth.linesize > 0) - // scale by ratio of widths - glLineWidth((float)bpmem.lineptwidth.linesize * fratio / 6.0f); - if (bpmem.lineptwidth.pointsize > 0) - glPointSize((float)bpmem.lineptwidth.pointsize * fratio / 6.0f); -} - -void Renderer::SetSamplerState(int stage,int texindex) -{ - // TODO -} - -void Renderer::SetInterlacingMode() -{ - // TODO -} diff --git a/Source/Plugins/Plugin_VideoOGL/Src/SConscript b/Source/Plugins/Plugin_VideoOGL/Src/SConscript index 636a8ae390..e83b6a37c6 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/SConscript +++ b/Source/Plugins/Plugin_VideoOGL/Src/SConscript @@ -10,7 +10,7 @@ files = [ 'BPFunctions.cpp', 'RasterFont.cpp', 'Render.cpp', - 'TextureMngr.cpp', + 'TextureCache.cpp', 'NativeVertexFormat.cpp', 'PixelShaderCache.cpp', 'VertexShaderCache.cpp', diff --git a/Source/Plugins/Plugin_VideoOGL/Src/TextureMngr.cpp b/Source/Plugins/Plugin_VideoOGL/Src/TextureCache.cpp similarity index 84% rename from Source/Plugins/Plugin_VideoOGL/Src/TextureMngr.cpp rename to Source/Plugins/Plugin_VideoOGL/Src/TextureCache.cpp index c9ada9878c..7804e8e850 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/TextureMngr.cpp +++ b/Source/Plugins/Plugin_VideoOGL/Src/TextureCache.cpp @@ -18,9 +18,7 @@ #include #include -#include "Globals.h" -#include "CommonPaths.h" -#include "StringUtil.h" + #include #ifdef _WIN32 #define _interlockedbittestandset workaround_ms_header_bug_platform_sdk6_set @@ -34,28 +32,29 @@ #undef _interlockedbittestandreset64 #endif -#include "VideoConfig.h" -#include "Hash.h" -#include "Statistics.h" -#include "Profiler.h" -#include "ImageWrite.h" - -#include "Render.h" - -#include "MemoryUtil.h" #include "BPStructs.h" -#include "TextureDecoder.h" -#include "TextureMngr.h" +#include "CommonPaths.h" +#include "FileUtil.h" +#include "FramebufferManager.h" +#include "Globals.h" +#include "Hash.h" +#include "HiresTextures.h" +#include "ImageWrite.h" +#include "MemoryUtil.h" #include "PixelShaderCache.h" #include "PixelShaderManager.h" -#include "VertexShaderManager.h" -#include "FramebufferManager.h" -#include "FileUtil.h" -#include "HiresTextures.h" +#include "Profiler.h" +#include "Render.h" +#include "Statistics.h" +#include "StringUtil.h" +#include "TextureCache.h" #include "TextureConverter.h" +#include "TextureDecoder.h" +#include "VertexShaderManager.h" +#include "VideoConfig.h" -u8 *TextureMngr::temp = NULL; -TextureMngr::TexCache TextureMngr::textures; +u8 *TextureCache::temp = NULL; +TextureCache::TexCache TextureCache::textures; extern int frameCount; static u32 s_TempFramebuffer = 0; @@ -96,16 +95,7 @@ bool SaveTexture(const char* filename, u32 textarget, u32 tex, int width, int he return SaveTGA(filename, width, height, &data[0]); } -int TextureMngr::TCacheEntry::IntersectsMemoryRange(u32 range_address, u32 range_size) -{ - if (addr + size_in_bytes < range_address) - return -1; - if (addr >= range_address + range_size) - return 1; - return 0; -} - -void TextureMngr::TCacheEntry::SetTextureParameters(TexMode0 &newmode,TexMode1 &newmode1) +void TextureCache::TCacheEntry::SetTextureParameters(TexMode0 &newmode,TexMode1 &newmode1) { mode = newmode; mode1 = newmode1; @@ -134,48 +124,49 @@ void TextureMngr::TCacheEntry::SetTextureParameters(TexMode0 &newmode,TexMode1 & glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, (float)(1 << g_ActiveConfig.iMaxAnisotropy)); } -void TextureMngr::TCacheEntry::Destroy(bool shutdown) +void TextureCache::TCacheEntry::Destroy(bool shutdown) { - if (!texture) - return; - glDeleteTextures(1, &texture); - if (!isRenderTarget && !shutdown && !g_ActiveConfig.bSafeTextureCache) { - u32 *ptr = (u32*)g_VideoInitialize.pGetMemoryPointer(addr); - if (ptr && *ptr == hash) - *ptr = oldpixel; - } - texture = 0; -} + if (texture) + glDeleteTextures(1, &texture); + texture = 0; + if (!isRenderTarget && !shutdown && !g_ActiveConfig.bSafeTextureCache) + { + u32 *ptr = (u32*)g_VideoInitialize.pGetMemoryPointer(addr); + if (ptr && *ptr == hash) + *ptr = oldpixel; + } +} -void TextureMngr::Init() +void TextureCache::Init() { - temp = (u8*)AllocateMemoryPages(TEMP_SIZE); + temp = (u8*)AllocateMemoryPages(TEMP_SIZE); TexDecoder_SetTexFmtOverlayOptions(g_ActiveConfig.bTexFmtOverlayEnable, g_ActiveConfig.bTexFmtOverlayCenter); HiresTextures::Init(globals->unique_id); } -void TextureMngr::Invalidate(bool shutdown) +void TextureCache::Invalidate(bool shutdown) { - for (TexCache::iterator iter = textures.begin(); iter != textures.end(); ++iter) - iter->second.Destroy(shutdown); - textures.clear(); + for (TexCache::iterator iter = textures.begin(); iter != textures.end(); ++iter) + iter->second.Destroy(shutdown); + textures.clear(); HiresTextures::Shutdown(); } -void TextureMngr::Shutdown() +void TextureCache::Shutdown() { - Invalidate(true); + Invalidate(true); - if (s_TempFramebuffer) { - glDeleteFramebuffersEXT(1, (GLuint *)&s_TempFramebuffer); - s_TempFramebuffer = 0; - } + if (s_TempFramebuffer) + { + glDeleteFramebuffersEXT(1, (GLuint *)&s_TempFramebuffer); + s_TempFramebuffer = 0; + } - FreeMemoryPages(temp, TEMP_SIZE); - temp = NULL; + FreeMemoryPages(temp, TEMP_SIZE); + temp = NULL; } -void TextureMngr::ProgressiveCleanup() +void TextureCache::Cleanup() { TexCache::iterator iter = textures.begin(); while (iter != textures.end()) @@ -186,11 +177,13 @@ void TextureMngr::ProgressiveCleanup() textures.erase(iter++); } else + { ++iter; + } } } -void TextureMngr::InvalidateRange(u32 start_address, u32 size) +void TextureCache::InvalidateRange(u32 start_address, u32 size) { TexCache::iterator iter = textures.begin(); while (iter != textures.end()) @@ -201,14 +194,14 @@ void TextureMngr::InvalidateRange(u32 start_address, u32 size) iter->second.Destroy(false); textures.erase(iter++); } - else + else { - ++iter; + ++iter; } } } -void TextureMngr::MakeRangeDynamic(u32 start_address, u32 size) +void TextureCache::MakeRangeDynamic(u32 start_address, u32 size) { TexCache::iterator iter = textures.begin(); while (iter != textures.end()) @@ -222,8 +215,16 @@ void TextureMngr::MakeRangeDynamic(u32 start_address, u32 size) } } +int TextureCache::TCacheEntry::IntersectsMemoryRange(u32 range_address, u32 range_size) +{ + if (addr + size_in_bytes < range_address) + return -1; + if (addr >= range_address + range_size) + return 1; + return 0; +} -TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width, int height, u32 tex_format, int tlutaddr, int tlutfmt) +TextureCache::TCacheEntry* TextureCache::Load(int texstage, u32 address, int width, int height, u32 tex_format, int tlutaddr, int tlutfmt) { // notes (about "UNsafe texture cache"): // Have to be removed soon. @@ -250,31 +251,32 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width // Wonder if we can't use tex width&height to know if EFB might be copied to it... // raw idea: TOCHECK if addresses are aligned we have few bits left... - if (address == 0) - return NULL; + if (address == 0) + return NULL; TexMode0 &tm0 = bpmem.tex[texstage >> 2].texMode0[texstage & 3]; TexMode1 &tm1 = bpmem.tex[texstage >> 2].texMode1[texstage & 3]; int maxlevel = (tm1.max_lod >> 4); bool UseNativeMips = (tm0.min_filter & 3) && (tm0.min_filter != 8) && g_ActiveConfig.bUseNativeMips; - u8 *ptr = g_VideoInitialize.pGetMemoryPointer(address); - int bsw = TexDecoder_GetBlockWidthInTexels(tex_format) - 1; - int bsh = TexDecoder_GetBlockHeightInTexels(tex_format) - 1; + u8 *ptr = g_VideoInitialize.pGetMemoryPointer(address); + int bsw = TexDecoder_GetBlockWidthInTexels(tex_format) - 1; // TexelSizeInNibbles(format)*width*height/16; + int bsh = TexDecoder_GetBlockHeightInTexels(tex_format) - 1; // TexelSizeInNibbles(format)*width*height/16; int bsdepth = TexDecoder_GetTexelSizeInNibbles(tex_format); - int expandedWidth = (width + bsw) & (~bsw); + int expandedWidth = (width + bsw) & (~bsw); int expandedHeight = (height + bsh) & (~bsh); u64 hash_value = 0; - u32 texID = address; + u32 texID = address; u64 texHash = 0; u32 FullFormat = tex_format; bool TextureisDynamic = false; if ((tex_format == GX_TF_C4) || (tex_format == GX_TF_C8) || (tex_format == GX_TF_C14X2)) FullFormat = (tex_format | (tlutfmt << 16)); + if (g_ActiveConfig.bSafeTextureCache || g_ActiveConfig.bHiresTextures || g_ActiveConfig.bDumpTextures) { - texHash = GetHash64(ptr,TexDecoder_GetTextureSizeInBytes(expandedWidth, expandedHeight, tex_format),g_ActiveConfig.iSafeTextureCache_ColorSamples); + texHash = GetHash64(ptr,TexDecoder_GetTextureSizeInBytes(expandedWidth, expandedHeight, tex_format),g_ActiveConfig.iSafeTextureCache_ColorSamples); if ((tex_format == GX_TF_C4) || (tex_format == GX_TF_C8) || (tex_format == GX_TF_C14X2)) { // WARNING! texID != address now => may break CopyRenderTargetToTexture (cf. TODO up) @@ -300,7 +302,7 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width if (iter != textures.end()) { - TCacheEntry &entry = iter->second; + TCacheEntry &entry = iter->second; if (!g_ActiveConfig.bSafeTextureCache) { @@ -334,63 +336,62 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width } } } - - if (((entry.isRenderTarget || entry.isDynamic) && hash_value == entry.hash && address == entry.addr) + if (((entry.isRenderTarget || entry.isDynamic) && hash_value == entry.hash && address == entry.addr) || ((address == entry.addr) && (hash_value == entry.hash) && ((int) FullFormat == entry.fmt) && entry.MipLevels >= maxlevel)) { - entry.frameCount = frameCount; + entry.frameCount = frameCount; glEnable(GL_TEXTURE_2D); glBindTexture(GL_TEXTURE_2D, entry.texture); GL_REPORT_ERRORD(); entry.SetTextureParameters(tm0,tm1); entry.isDynamic = false; return &entry; - } - else - { - // Let's reload the new texture data into the same texture, + } + else + { + // Let's reload the new texture data into the same texture, // instead of destroying it and having to create a new one. // Might speed up movie playback very, very slightly. TextureisDynamic = (entry.isRenderTarget || entry.isDynamic) && !g_ActiveConfig.bCopyEFBToTexture; - if (((!(entry.isRenderTarget || entry.isDynamic) && width == entry.w && height == entry.h && (int)FullFormat == entry.fmt) || - ((entry.isRenderTarget || entry.isDynamic) && entry.w == width && entry.h == height && entry.Scaledw == width && entry.Scaledh == height))) + if (((!(entry.isRenderTarget || entry.isDynamic) && width == entry.w && height == entry.h && (int)FullFormat == entry.fmt) || + ((entry.isRenderTarget || entry.isDynamic) && entry.w == width && entry.h == height && entry.Scaledw == width && entry.Scaledh == height))) { glBindTexture(GL_TEXTURE_2D, entry.texture); GL_REPORT_ERRORD(); entry.SetTextureParameters(tm0,tm1); skip_texture_create = true; - } - else - { - entry.Destroy(false); - textures.erase(iter); - } - } - } + } + else + { + entry.Destroy(false); + textures.erase(iter); + } + } + } - //Make an entry in the table + // Make an entry in the table TCacheEntry& entry = textures[texID]; entry.isDynamic = TextureisDynamic; entry.isRenderTarget = false; - PC_TexFormat dfmt = PC_TEX_FMT_NONE; + PC_TexFormat pcfmt = PC_TEX_FMT_NONE; if (g_ActiveConfig.bHiresTextures) { - //Load Custom textures + // Load Custom textures char texPathTemp[MAX_PATH]; sprintf(texPathTemp, "%s_%08x_%i", globals->unique_id, (unsigned int) texHash, tex_format); - dfmt = HiresTextures::GetHiresTex(texPathTemp, &width, &height, tex_format, temp); + pcfmt = HiresTextures::GetHiresTex(texPathTemp, &width, &height, tex_format, temp); - if (dfmt != PC_TEX_FMT_NONE) + if (pcfmt != PC_TEX_FMT_NONE) { expandedWidth = width; expandedHeight = height; } } - if (dfmt == PC_TEX_FMT_NONE) - dfmt = TexDecoder_Decode(temp, ptr, expandedWidth, expandedHeight, tex_format, tlutaddr, tlutfmt); + if (pcfmt == PC_TEX_FMT_NONE) + pcfmt = TexDecoder_Decode(temp, ptr, expandedWidth, expandedHeight, tex_format, tlutaddr, tlutfmt); entry.oldpixel = ((u32 *)ptr)[0]; @@ -402,8 +403,8 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width ((u32 *)ptr)[0] = entry.hash; } - entry.addr = address; - entry.size_in_bytes = TexDecoder_GetTextureSizeInBytes(expandedWidth, expandedHeight, tex_format); + entry.addr = address; + entry.size_in_bytes = TexDecoder_GetTextureSizeInBytes(expandedWidth, expandedHeight, tex_format); GLenum target = GL_TEXTURE_2D; if (!skip_texture_create) { @@ -413,8 +414,8 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width bool isPow2 = !((width & (width - 1)) || (height & (height - 1))); int TexLevels = (width > height)?width:height; - TexLevels = (isPow2 && UseNativeMips && (maxlevel > 0)) ? (int)(log((double)TexLevels)/log((double)2))+ 1 : (isPow2? 0 : 1); - if(TexLevels > (maxlevel + 1) && maxlevel > 0) + TexLevels = (isPow2 && UseNativeMips && (maxlevel > 0)) ? (int)(log((double)TexLevels)/log((double)2)) + 1 : (isPow2? 0 : 1); + if(TexLevels > (maxlevel + 1) && maxlevel > 0) TexLevels = (maxlevel + 1); entry.MipLevels = maxlevel; bool GenerateMipmaps = TexLevels > 1 || TexLevels == 0; @@ -423,13 +424,13 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width int gl_iformat = 0; int gl_type = 0; GL_REPORT_ERRORD(); - if (dfmt != PC_TEX_FMT_DXT1) + if (pcfmt != PC_TEX_FMT_DXT1) { - switch (dfmt) + switch (pcfmt) { default: case PC_TEX_FMT_NONE: - PanicAlert("Invalid PC texture format %i", dfmt); + PanicAlert("Invalid PC texture format %i", pcfmt); case PC_TEX_FMT_BGRA32: gl_format = GL_BGRA; gl_iformat = 4; @@ -490,12 +491,12 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width } else { - glTexImage2D(target, 0, gl_iformat, width, height, 0, gl_format, gl_type, temp); + glTexImage2D(target, 0, gl_iformat, width, height, 0, gl_format, gl_type, temp); } } if (expandedWidth != width) // reset - glPixelStorei(GL_UNPACK_ROW_LENGTH, 0); + glPixelStorei(GL_UNPACK_ROW_LENGTH, 0); } else { @@ -511,7 +512,7 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width } } GL_REPORT_ERRORD(); - if(TexLevels > 1 && dfmt != PC_TEX_FMT_NONE) + if(TexLevels > 1 && pcfmt != PC_TEX_FMT_NONE) { int level = 1; int mipWidth = width >> 1; @@ -523,8 +524,8 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width u32 currentHeight = (mipHeight > 0)? mipHeight : 1; expandedWidth = (currentWidth + bsw) & (~bsw); expandedHeight = (currentHeight + bsh) & (~bsh); - TexDecoder_Decode(temp, ptr, expandedWidth, expandedHeight, tex_format, tlutaddr, tlutfmt); - if (dfmt != PC_TEX_FMT_DXT1) + TexDecoder_Decode(temp, ptr, expandedWidth, expandedHeight, tex_format, tlutaddr, tlutfmt); + if (pcfmt != PC_TEX_FMT_DXT1) { if (expandedWidth != (int)currentWidth) glPixelStorei(GL_UNPACK_ROW_LENGTH, expandedWidth); @@ -543,24 +544,25 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width mipHeight >>= 1; level++; } - } - entry.frameCount = frameCount; - entry.w = width; - entry.h = height; + } + entry.frameCount = frameCount; + entry.w = width; + entry.h = height; entry.Scaledw = width; entry.Scaledh = height; - entry.fmt = FullFormat; + entry.fmt = FullFormat; entry.SetTextureParameters(tm0,tm1); - if (g_ActiveConfig.bDumpTextures) // dump texture to file - { - char szTemp[MAX_PATH]; + if (g_ActiveConfig.bDumpTextures) + { + // dump texture to file + char szTemp[MAX_PATH]; char szDir[MAX_PATH]; const char* uniqueId = globals->unique_id; static bool bCheckedDumpDir = false; - sprintf(szDir,"%s%s", File::GetUserPath(D_DUMPTEXTURES_IDX), uniqueId); + sprintf(szDir, "%s%s", File::GetUserPath(D_DUMPTEXTURES_IDX), uniqueId); - if(!bCheckedDumpDir) + if (!bCheckedDumpDir) { if (!File::Exists(szDir) || !File::IsDirectory(szDir)) File::CreateDir(szDir); @@ -571,15 +573,14 @@ TextureMngr::TCacheEntry* TextureMngr::Load(int texstage, u32 address, int width sprintf(szTemp, "%s/%s_%08x_%i.tga", szDir, uniqueId, (unsigned int) texHash, tex_format); if (!File::Exists(szTemp)) SaveTexture(szTemp, target, entry.texture, entry.w, entry.h); - } + } - INCSTAT(stats.numTexturesCreated); - SETSTAT(stats.numTexturesAlive, textures.size()); - return &entry; + INCSTAT(stats.numTexturesCreated); + SETSTAT(stats.numTexturesAlive, textures.size()); + return &entry; } - -void TextureMngr::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, bool bIsIntensityFmt, u32 copyfmt, int bScaleByHalf, const EFBRectangle &source_rect) +void TextureCache::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, bool bIsIntensityFmt, u32 copyfmt, int bScaleByHalf, const EFBRectangle &source_rect) { DVSTARTPROFILE(); GL_REPORT_ERRORD(); @@ -601,7 +602,7 @@ void TextureMngr::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, bool { switch(copyfmt) { - case 0: // Z4 + case 0: // Z4 case 1: // Z8 colmat[2] = colmat[6] = colmat[10] = colmat[14] = 1; break; @@ -817,14 +818,14 @@ void TextureMngr::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, bool // Unbind texture from temporary framebuffer glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, 0, 0); } - + if(!g_ActiveConfig.bCopyEFBToTexture) { textures[address].hash = TextureConverter::EncodeToRamFromTexture( address, read_texture, xScale, - yScale, + yScale, bFromZBuffer, bIsIntensityFmt, copyfmt, @@ -836,7 +837,7 @@ void TextureMngr::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, bool g_framebufferManager.SetFramebuffer(0); Renderer::RestoreAPIState(); VertexShaderManager::SetViewportChanged(); - TextureMngr::DisableStage(0); + TextureCache::DisableStage(0); GL_REPORT_ERRORD(); @@ -847,14 +848,14 @@ void TextureMngr::CopyRenderTargetToTexture(u32 address, bool bFromZBuffer, bool } } -void TextureMngr::DisableStage(int stage) +void TextureCache::DisableStage(int stage) { glActiveTexture(GL_TEXTURE0 + stage); glDisable(GL_TEXTURE_2D); glDisable(GL_TEXTURE_RECTANGLE_ARB); } -void TextureMngr::ClearRenderTargets() +void TextureCache::ClearRenderTargets() { for (TexCache::iterator iter = textures.begin(); iter != textures.end(); ++iter) iter->second.isRenderTarget = false; diff --git a/Source/Plugins/Plugin_VideoOGL/Src/TextureMngr.h b/Source/Plugins/Plugin_VideoOGL/Src/TextureCache.h similarity index 98% rename from Source/Plugins/Plugin_VideoOGL/Src/TextureMngr.h rename to Source/Plugins/Plugin_VideoOGL/Src/TextureCache.h index f54d5d69ca..8a9987071f 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/TextureMngr.h +++ b/Source/Plugins/Plugin_VideoOGL/Src/TextureCache.h @@ -24,7 +24,7 @@ #include "GLUtil.h" #include "BPStructs.h" -class TextureMngr +class TextureCache { public: struct TCacheEntry @@ -66,7 +66,7 @@ private: public: static void Init(); - static void ProgressiveCleanup(); + static void Cleanup(); static void Shutdown(); static void Invalidate(bool shutdown); static void InvalidateRange(u32 start_address, u32 size); diff --git a/Source/Plugins/Plugin_VideoOGL/Src/TextureConverter.cpp b/Source/Plugins/Plugin_VideoOGL/Src/TextureConverter.cpp index 77a92a70b7..5b9b0f27c2 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/TextureConverter.cpp +++ b/Source/Plugins/Plugin_VideoOGL/Src/TextureConverter.cpp @@ -20,7 +20,7 @@ #include "TextureConverter.h" #include "TextureConversionShader.h" -#include "TextureMngr.h" +#include "TextureCache.h" #include "PixelShaderCache.h" #include "VertexShaderManager.h" #include "FramebufferManager.h" @@ -54,7 +54,7 @@ void CreateRgbToYuyvProgram() { // Output is BGRA because that is slightly faster than RGBA. const char *FProgram = - "uniform samplerRECT samp0 : register(s0);\n" + "uniform samplerRECT samp0 : register(s0);\n" "void main(\n" " out float4 ocol0 : COLOR0,\n" " in float2 uv0 : TEXCOORD0)\n" @@ -78,7 +78,7 @@ void CreateRgbToYuyvProgram() void CreateYuyvToRgbProgram() { const char *FProgram = - "uniform samplerRECT samp0 : register(s0);\n" + "uniform samplerRECT samp0 : register(s0);\n" "void main(\n" " out float4 ocol0 : COLOR0,\n" " in float2 uv0 : TEXCOORD0)\n" @@ -128,7 +128,6 @@ FRAGMENTSHADER &GetOrCreateEncodingShader(u32 format) ERROR_LOG(VIDEO, "Failed to create encoding fragment program"); } } - return s_encodingPrograms[format]; } @@ -180,7 +179,7 @@ void EncodeToRamUsingShader(FRAGMENTSHADER& shader, GLuint srcTexture, const Tar GL_REPORT_ERRORD(); for (int i = 1; i < 8; ++i) - TextureMngr::DisableStage(i); + TextureCache::DisableStage(i); // set source texture glActiveTexture(GL_TEXTURE0); @@ -216,27 +215,26 @@ void EncodeToRamUsingShader(FRAGMENTSHADER& shader, GLuint srcTexture, const Tar // .. and then readback the results. // TODO: make this less slow. - int writeStride = bpmem.copyMipMapStrideChannels * 32; + int writeStride = bpmem.copyMipMapStrideChannels * 32; - if (writeStride != readStride && toTexture) - { - // writing to a texture of a different size + if (writeStride != readStride && toTexture) + { + // writing to a texture of a different size - int readHeight = readStride / dstWidth; - readHeight /= 4; // 4 bytes per pixel + int readHeight = readStride / dstWidth; + readHeight /= 4; // 4 bytes per pixel - int readStart = 0; - int readLoops = dstHeight / readHeight; - for (int i = 0; i < readLoops; i++) - { - glReadPixels(0, readStart, (GLsizei)dstWidth, (GLsizei)readHeight, GL_BGRA, GL_UNSIGNED_BYTE, destAddr); - - readStart += readHeight; - destAddr += writeStride; - } - } - else - glReadPixels(0, 0, (GLsizei)dstWidth, (GLsizei)dstHeight, GL_BGRA, GL_UNSIGNED_BYTE, destAddr); + int readStart = 0; + int readLoops = dstHeight / readHeight; + for (int i = 0; i < readLoops; i++) + { + glReadPixels(0, readStart, (GLsizei)dstWidth, (GLsizei)readHeight, GL_BGRA, GL_UNSIGNED_BYTE, destAddr); + readStart += readHeight; + destAddr += writeStride; + } + } + else + glReadPixels(0, 0, (GLsizei)dstWidth, (GLsizei)dstHeight, GL_BGRA, GL_UNSIGNED_BYTE, destAddr); GL_REPORT_ERRORD(); @@ -273,7 +271,7 @@ void EncodeToRam(u32 address, bool bFromZBuffer, bool bIsIntensityFmt, u32 copyf // Invalidate any existing texture covering this memory range. // TODO - don't delete the texture if it already exists, just replace the contents. - TextureMngr::InvalidateRange(address, size_in_bytes); + TextureCache::InvalidateRange(address, size_in_bytes); u16 blkW = TexDecoder_GetBlockWidthInTexels(format) - 1; u16 blkH = TexDecoder_GetBlockHeightInTexels(format) - 1; @@ -303,9 +301,7 @@ void EncodeToRam(u32 address, bool bFromZBuffer, bool bIsIntensityFmt, u32 copyf scaledSource.bottom = expandedHeight; scaledSource.left = 0; scaledSource.right = expandedWidth / samples; - - - int cacheBytes = 32; + int cacheBytes = 32; if ((format & 0x0f) == 6) cacheBytes = 64; @@ -315,12 +311,11 @@ void EncodeToRam(u32 address, bool bFromZBuffer, bool bIsIntensityFmt, u32 copyf g_framebufferManager.SetFramebuffer(0); VertexShaderManager::SetViewportChanged(); glBindTexture(GL_TEXTURE_RECTANGLE_ARB, 0); - TextureMngr::DisableStage(0); + TextureCache::DisableStage(0); Renderer::RestoreAPIState(); GL_REPORT_ERRORD(); } - u64 EncodeToRamFromTexture(u32 address,GLuint source_texture,float MValueX,float MValueY,bool bFromZBuffer, bool bIsIntensityFmt, u32 copyfmt, int bScaleByHalf, const EFBRectangle& source) { u32 format = copyfmt; @@ -341,13 +336,13 @@ u64 EncodeToRamFromTexture(u32 address,GLuint source_texture,float MValueX,float if (texconv_shader.glprogid == 0) return 0; - u8 *dest_ptr = Memory_GetPtr(address); + u8 *dest_ptr = Memory_GetPtr(address); int width = (source.right - source.left) >> bScaleByHalf; int height = (source.bottom - source.top) >> bScaleByHalf; - int size_in_bytes = TexDecoder_GetTextureSizeInBytes(width, height, format); - + int size_in_bytes = TexDecoder_GetTextureSizeInBytes(width, height, format); + u16 blkW = TexDecoder_GetBlockWidthInTexels(format) - 1; u16 blkH = TexDecoder_GetBlockHeightInTexels(format) - 1; u16 samples = TextureConversionShader::GetEncodedSampleCount(format); @@ -371,28 +366,25 @@ u64 EncodeToRamFromTexture(u32 address,GLuint source_texture,float MValueX,float scaledSource.bottom = expandedHeight; scaledSource.left = 0; scaledSource.right = expandedWidth / samples; - - - int cacheBytes = 32; + int cacheBytes = 32; if ((format & 0x0f) == 6) cacheBytes = 64; int readStride = (expandedWidth * cacheBytes) / TexDecoder_GetBlockWidthInTexels(format); EncodeToRamUsingShader(texconv_shader, source_texture, scaledSource, dest_ptr, expandedWidth / samples, expandedHeight, readStride, true, bScaleByHalf > 0 && !bFromZBuffer); - TextureMngr::MakeRangeDynamic(address,size_in_bytes); + TextureCache::MakeRangeDynamic(address,size_in_bytes); return GetHash64(dest_ptr,size_in_bytes,g_ActiveConfig.iSafeTextureCache_ColorSamples); } -void EncodeToRamYUYV(GLuint srcTexture, const TargetRectangle& sourceRc, - u8* destAddr, int dstWidth, int dstHeight) +void EncodeToRamYUYV(GLuint srcTexture, const TargetRectangle& sourceRc, u8* destAddr, int dstWidth, int dstHeight) { Renderer::ResetAPIState(); EncodeToRamUsingShader(s_rgbToYuyvProgram, srcTexture, sourceRc, destAddr, dstWidth / 2, dstHeight, 0, false, false); g_framebufferManager.SetFramebuffer(0); - VertexShaderManager::SetViewportChanged(); + VertexShaderManager::SetViewportChanged(); glBindTexture(GL_TEXTURE_RECTANGLE_ARB, 0); - TextureMngr::DisableStage(0); + TextureCache::DisableStage(0); Renderer::RestoreAPIState(); GL_REPORT_ERRORD(); } @@ -421,7 +413,7 @@ void DecodeToTexture(u32 xfbAddr, int srcWidth, int srcHeight, GLuint destTextur GL_REPORT_FBO_ERROR(); for (int i = 1; i < 8; ++i) - TextureMngr::DisableStage(i); + TextureCache::DisableStage(i); // activate source texture // set srcAddr as data for source texture @@ -457,7 +449,7 @@ void DecodeToTexture(u32 xfbAddr, int srcWidth, int srcHeight, GLuint destTextur // reset state glBindTexture(GL_TEXTURE_RECTANGLE_ARB, 0); glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_RECTANGLE_ARB, 0, 0); - TextureMngr::DisableStage(0); + TextureCache::DisableStage(0); VertexShaderManager::SetViewportChanged(); diff --git a/Source/Plugins/Plugin_VideoOGL/Src/VertexManager.cpp b/Source/Plugins/Plugin_VideoOGL/Src/VertexManager.cpp index d3ca1ba131..12d054da59 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/VertexManager.cpp +++ b/Source/Plugins/Plugin_VideoOGL/Src/VertexManager.cpp @@ -29,7 +29,7 @@ #include "Render.h" #include "ImageWrite.h" #include "BPMemory.h" -#include "TextureMngr.h" +#include "TextureCache.h" #include "PixelShaderCache.h" #include "PixelShaderManager.h" #include "VertexShaderCache.h" @@ -90,6 +90,12 @@ bool Init() return true; } +void ResetBuffer() +{ + //s_nCurVBOIndex = (s_nCurVBOIndex + 1) % ARRAYSIZE(s_vboBuffers); + s_pCurBufferPointer = LocalVBuffer; +} + void Shutdown() { delete [] LocalVBuffer; @@ -100,73 +106,67 @@ void Shutdown() //s_nCurVBOIndex = 0; } -void ResetBuffer() -{ - //s_nCurVBOIndex = (s_nCurVBOIndex + 1) % ARRAYSIZE(s_vboBuffers); - s_pCurBufferPointer = LocalVBuffer; -} - void AddIndices(int primitive, int numVertices) { switch (primitive) { - case GX_DRAW_QUADS: IndexGenerator::AddQuads(numVertices);break; - case GX_DRAW_TRIANGLES: IndexGenerator::AddList(numVertices);break; - case GX_DRAW_TRIANGLE_STRIP: IndexGenerator::AddStrip(numVertices); break; - case GX_DRAW_TRIANGLE_FAN: IndexGenerator::AddFan(numVertices); break; - case GX_DRAW_LINE_STRIP: IndexGenerator::AddLineStrip(numVertices); break; - case GX_DRAW_LINES: IndexGenerator::AddLineList(numVertices);break; - case GX_DRAW_POINTS: IndexGenerator::AddPoints(numVertices); break; + case GX_DRAW_QUADS: IndexGenerator::AddQuads(numVertices); break; + case GX_DRAW_TRIANGLES: IndexGenerator::AddList(numVertices); break; + case GX_DRAW_TRIANGLE_STRIP: IndexGenerator::AddStrip(numVertices); break; + case GX_DRAW_TRIANGLE_FAN: IndexGenerator::AddFan(numVertices); break; + case GX_DRAW_LINE_STRIP: IndexGenerator::AddLineStrip(numVertices); break; + case GX_DRAW_LINES: IndexGenerator::AddLineList(numVertices); break; + case GX_DRAW_POINTS: IndexGenerator::AddPoints(numVertices); break; } } int GetRemainingSize() { - return MAXVBUFFERSIZE - (int)(s_pCurBufferPointer - LocalVBuffer); + return MAXVBUFFERSIZE - (int)(s_pCurBufferPointer - LocalVBuffer); } int GetRemainingVertices(int primitive) { switch (primitive) { - case GX_DRAW_QUADS: - case GX_DRAW_TRIANGLES: - case GX_DRAW_TRIANGLE_STRIP: - case GX_DRAW_TRIANGLE_FAN: - return (max_Index_size - IndexGenerator::GetTriangleindexLen())/3; - case GX_DRAW_LINE_STRIP: - case GX_DRAW_LINES: - return (max_Index_size - IndexGenerator::GetLineindexLen())/2; - case GX_DRAW_POINTS: - return (max_Index_size - IndexGenerator::GetPointindexLen()); - default: return 0; + case GX_DRAW_QUADS: + case GX_DRAW_TRIANGLES: + case GX_DRAW_TRIANGLE_STRIP: + case GX_DRAW_TRIANGLE_FAN: + return (max_Index_size - IndexGenerator::GetTriangleindexLen())/3; + case GX_DRAW_LINE_STRIP: + case GX_DRAW_LINES: + return (max_Index_size - IndexGenerator::GetLineindexLen())/2; + case GX_DRAW_POINTS: + return (max_Index_size - IndexGenerator::GetPointindexLen()); + default: return 0; } } -void AddVertices(int primitive, int numvertices) +void AddVertices(int primitive, int numVertices) { - if (numvertices <= 0) + if (numVertices <= 0) return; (void)GL_REPORT_ERROR(); switch (primitive) { - case GX_DRAW_QUADS: - case GX_DRAW_TRIANGLES: - case GX_DRAW_TRIANGLE_STRIP: - case GX_DRAW_TRIANGLE_FAN: - if(max_Index_size - IndexGenerator::GetTriangleindexLen() < 3 * numvertices) - Flush(); - break; - case GX_DRAW_LINE_STRIP: - case GX_DRAW_LINES: - if(max_Index_size - IndexGenerator::GetLineindexLen() < 2 * numvertices) - Flush(); - break; - case GX_DRAW_POINTS: - if(max_Index_size - IndexGenerator::GetPointindexLen() < numvertices) - Flush(); - break; - default: return; + case GX_DRAW_QUADS: + case GX_DRAW_TRIANGLES: + case GX_DRAW_TRIANGLE_STRIP: + case GX_DRAW_TRIANGLE_FAN: + if(max_Index_size - IndexGenerator::GetTriangleindexLen() < 3 * numVertices) + Flush(); + break; + case GX_DRAW_LINE_STRIP: + case GX_DRAW_LINES: + if(max_Index_size - IndexGenerator::GetLineindexLen() < 2 * numVertices) + Flush(); + break; + case GX_DRAW_POINTS: + if(max_Index_size - IndexGenerator::GetPointindexLen() < numVertices) + Flush(); + break; + default: return; } if(Flushed) { @@ -174,11 +174,9 @@ void AddVertices(int primitive, int numvertices) Flushed=false; } lastPrimitive = primitive; - ADDSTAT(stats.thisFrame.numPrims, numvertices); + ADDSTAT(stats.thisFrame.numPrims, numVertices); INCSTAT(stats.thisFrame.numPrimitiveJoins); - AddIndices(primitive, numvertices); - - + AddIndices(primitive, numVertices); } inline void Draw() @@ -203,7 +201,7 @@ inline void Draw() void Flush() { if (LocalVBuffer == s_pCurBufferPointer) return; - if(Flushed) return; + if (Flushed) return; Flushed=true; VideoFifo_CheckEFBAccess(); #if defined(_DEBUG) || defined(DEBUGFAST) @@ -257,7 +255,7 @@ void Flush() if (bpmem.genMode.numindstages > 0) for (u32 i = 0; i < (u32)bpmem.genMode.numtevstages + 1; ++i) - if (bpmem.tevind[i].IsActive() && bpmem.tevind[i].bt < bpmem.genMode.numindstages) + if (bpmem.tevind[i].IsActive() && bpmem.tevind[i].bt < bpmem.genMode.numindstages) usedtextures |= 1 << bpmem.tevindref.getTexMap(bpmem.tevind[i].bt); for (int i = 0; i < 8; i++) @@ -265,13 +263,14 @@ void Flush() if (usedtextures & (1 << i)) { glActiveTexture(GL_TEXTURE0 + i); - FourTexUnits &tex = bpmem.tex[i >> 2]; - TextureMngr::TCacheEntry* tentry = TextureMngr::Load(i, (tex.texImage3[i&3].image_base/* & 0x1FFFFF*/) << 5, + TextureCache::TCacheEntry* tentry = TextureCache::Load(i, + (tex.texImage3[i&3].image_base/* & 0x1FFFFF*/) << 5, tex.texImage0[i&3].width + 1, tex.texImage0[i&3].height + 1, - tex.texImage0[i&3].format, tex.texTlut[i&3].tmem_offset<<9, tex.texTlut[i&3].tlut_format); + tex.texImage0[i&3].format, tex.texTlut[i&3].tmem_offset<<9, + tex.texTlut[i&3].tlut_format); - if (tentry) + if (tentry) { // 0s are probably for no manual wrapping needed. PixelShaderManager::SetTexDims(i, tentry->w, tentry->h, 0, 0); @@ -285,12 +284,12 @@ void Flush() } } else - ERROR_LOG(VIDEO, "error loading tex\n"); + ERROR_LOG(VIDEO, "error loading texture"); } } - FRAGMENTSHADER* ps = PixelShaderCache::GetShader(false,g_nativeVertexFmt->m_components); - VERTEXSHADER* vs = VertexShaderCache::GetShader(g_nativeVertexFmt->m_components); + FRAGMENTSHADER* ps = PixelShaderCache::SetShader(false,g_nativeVertexFmt->m_components); + VERTEXSHADER* vs = VertexShaderCache::SetShader(g_nativeVertexFmt->m_components); // set global constants VertexShaderManager::SetConstants(); @@ -306,7 +305,7 @@ void Flush() // run through vertex groups again to set alpha if (!g_ActiveConfig.bDstAlphaPass && bpmem.dstalpha.enable && bpmem.blendmode.alphaupdate) { - ps = PixelShaderCache::GetShader(true,g_nativeVertexFmt->m_components); + ps = PixelShaderCache::SetShader(true,g_nativeVertexFmt->m_components); if (ps)PixelShaderCache::SetCurrentShader(ps->glprogid); @@ -357,4 +356,3 @@ void Flush() } } // namespace - diff --git a/Source/Plugins/Plugin_VideoOGL/Src/VertexShaderCache.cpp b/Source/Plugins/Plugin_VideoOGL/Src/VertexShaderCache.cpp index d7cb7fb669..71a516f2fc 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/VertexShaderCache.cpp +++ b/Source/Plugins/Plugin_VideoOGL/Src/VertexShaderCache.cpp @@ -93,27 +93,25 @@ void VertexShaderCache::Init() void VertexShaderCache::Shutdown() { - for (VSCache::iterator iter = vshaders.begin(); iter != vshaders.end(); iter++) + for (VSCache::iterator iter = vshaders.begin(); iter != vshaders.end(); ++iter) iter->second.Destroy(); vshaders.clear(); } -VERTEXSHADER* VertexShaderCache::GetShader(u32 components) +VERTEXSHADER* VertexShaderCache::SetShader(u32 components) { DVSTARTPROFILE(); + VERTEXSHADERUID uid; GetVertexShaderId(&uid, components); - if (uid == last_vertex_shader_uid && vshaders[uid].frameCount == frameCount) - { return pShaderLast; - } memcpy(&last_vertex_shader_uid, &uid, sizeof(VERTEXSHADERUID)); VSCache::iterator iter = vshaders.find(uid); - - if (iter != vshaders.end()) { + if (iter != vshaders.end()) + { iter->second.frameCount = frameCount; VSCacheEntry &entry = iter->second; if (&entry.shader != pShaderLast) { @@ -224,7 +222,7 @@ void VertexShaderCache::SetCurrentShader(GLuint Shader) if (!ShaderEnabled) { glEnable(GL_VERTEX_PROGRAM_ARB); - ShaderEnabled= true; + ShaderEnabled= true; } if (CurrentShader != Shader) { diff --git a/Source/Plugins/Plugin_VideoOGL/Src/VertexShaderCache.h b/Source/Plugins/Plugin_VideoOGL/Src/VertexShaderCache.h index 8befe6bd68..c024a9ee4f 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/VertexShaderCache.h +++ b/Source/Plugins/Plugin_VideoOGL/Src/VertexShaderCache.h @@ -61,7 +61,7 @@ public: static void Init(); static void Shutdown(); - static VERTEXSHADER* GetShader(u32 components); + static VERTEXSHADER* SetShader(u32 components); static bool CompileVertexShader(VERTEXSHADER& ps, const char* pstrprogram); static void SetCurrentShader(GLuint Shader); diff --git a/Source/Plugins/Plugin_VideoOGL/Src/main.cpp b/Source/Plugins/Plugin_VideoOGL/Src/main.cpp index ecba5f0a8f..ccc39bdd7b 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/main.cpp +++ b/Source/Plugins/Plugin_VideoOGL/Src/main.cpp @@ -73,7 +73,7 @@ GFXConfigDialogOGL *m_ConfigFrame = NULL; #include "GLUtil.h" #include "Fifo.h" #include "OpcodeDecoding.h" -#include "TextureMngr.h" +#include "TextureCache.h" #include "BPStructs.h" #include "VertexLoader.h" #include "VertexLoaderManager.h" @@ -109,6 +109,16 @@ static volatile u32 s_doStateRequested = FALSE; static u32 s_efbAccessRequested = FALSE; static volatile u32 s_FifoShuttingDown = FALSE; +static volatile struct +{ + u32 xfbAddr; + FieldType field; + u32 fbWidth; + u32 fbHeight; +} s_beginFieldArgs; + +static volatile EFBAccessType s_AccessEFBType; + bool IsD3D() { return false; @@ -191,7 +201,8 @@ void Initialize(void *init) // Now the window handle is written _pVideoInitialize->pWindowHandle = g_VideoInitialize.pWindowHandle; - OSD::AddMessage("Dolphin OpenGL Video Plugin", 5000); + OSD::AddMessage("Dolphin Direct3D9 Video Plugin.", 5000); + s_PluginInitialized = true; } static volatile struct @@ -207,7 +218,7 @@ static void check_DoState() { { #endif // Clear all caches that touch RAM - TextureMngr::Invalidate(false); + TextureCache::Invalidate(false); VertexLoaderManager::MarkAllDirty(); PointerWrap p(s_doStateArgs.ptr, s_doStateArgs.mode); @@ -259,14 +270,14 @@ void Video_Prepare(void) exit(1); } - s_swapRequested = FALSE; s_efbAccessRequested = FALSE; s_FifoShuttingDown = FALSE; + s_swapRequested = FALSE; CommandProcessor::Init(); PixelEngine::Init(); - TextureMngr::Init(); + TextureCache::Init(); BPInit(); VertexManager::Init(); @@ -289,14 +300,13 @@ void Video_Prepare(void) INFO_LOG(VIDEO, "Video plugin initialized."); } -void Shutdown(void) +void Shutdown() { - s_PluginInitialized = false; + s_PluginInitialized = false; s_efbAccessRequested = FALSE; - s_swapRequested = FALSE; s_FifoShuttingDown = FALSE; - + s_swapRequested = FALSE; DLCache::Shutdown(); Fifo_Shutdown(); PostProcessing::Shutdown(); @@ -310,7 +320,7 @@ void Shutdown(void) PixelShaderManager::Shutdown(); PixelShaderCache::Shutdown(); VertexManager::Shutdown(); - TextureMngr::Shutdown(); + TextureCache::Shutdown(); OpcodeDecoder_Shutdown(); Renderer::Shutdown(); OpenGL_Shutdown(); @@ -325,35 +335,14 @@ void Video_EnterLoop() void Video_ExitLoop() { Fifo_ExitLoop(); - s_FifoShuttingDown = TRUE; } -// Screenshot and screen message - -void Video_Screenshot(const char *_szFilename) -{ - Renderer::SetScreenshot(_szFilename); -} - -void Video_AddMessage(const char* pstr, u32 milliseconds) -{ - OSD::AddMessage(pstr, milliseconds); -} - void Video_SetRendering(bool bEnabled) { Fifo_SetRendering(bEnabled); } -static volatile struct -{ - u32 xfbAddr; - FieldType field; - u32 fbWidth; - u32 fbHeight; -} s_beginFieldArgs; - // Run from the graphics thread (from Fifo.cpp) void VideoFifo_CheckSwapRequest() { @@ -388,14 +377,14 @@ void VideoFifo_CheckSwapRequestAt(u32 xfbAddr, u32 fbWidth, u32 fbHeight) if (addrRangesOverlap(aLower, aUpper, bLower, bUpper)) VideoFifo_CheckSwapRequest(); } - } + } } // Run from the CPU thread (from VideoInterface.cpp) void Video_BeginField(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight) { if (s_PluginInitialized && g_ActiveConfig.bUseXFB) - { + { if (g_VideoInitialize.bOnThread) { while (Common::AtomicLoadAcquire(s_swapRequested) && !s_FifoShuttingDown) @@ -403,7 +392,7 @@ void Video_BeginField(u32 xfbAddr, FieldType field, u32 fbWidth, u32 fbHeight) Common::YieldCPU(); } else - VideoFifo_CheckSwapRequest(); + VideoFifo_CheckSwapRequest(); s_beginFieldArgs.xfbAddr = xfbAddr; s_beginFieldArgs.field = field; s_beginFieldArgs.fbWidth = fbWidth; @@ -418,6 +407,17 @@ void Video_EndField() { } +void Video_AddMessage(const char* pstr, u32 milliseconds) +{ + OSD::AddMessage(pstr, milliseconds); +} + +// Screenshot +void Video_Screenshot(const char *_szFilename) +{ + Renderer::SetScreenshot(_szFilename); +} + static struct { EFBAccessType type; @@ -446,6 +446,7 @@ u32 Video_AccessEFB(EFBAccessType type, u32 x, u32 y, u32 InputData) s_accessEFBArgs.x = x; s_accessEFBArgs.y = y; s_accessEFBArgs.Data = InputData; + Common::AtomicStoreRelease(s_efbAccessRequested, TRUE); if (g_VideoInitialize.bOnThread) @@ -496,7 +497,7 @@ void Video_PixelEngineWrite32(const u32 _Data, const u32 _Address) PixelEngine::Write32(_Data, _Address); } -void Video_GatherPipeBursted(void) +inline void Video_GatherPipeBursted(void) { CommandProcessor::GatherPipeBursted(); } diff --git a/Source/Plugins/Plugin_VideoOGL/Src/stdafx.cpp b/Source/Plugins/Plugin_VideoOGL/Src/stdafx.cpp index 31f734b17a..168ca738eb 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/stdafx.cpp +++ b/Source/Plugins/Plugin_VideoOGL/Src/stdafx.cpp @@ -15,4 +15,4 @@ // Official SVN repository and contact information can be found at // http://code.google.com/p/dolphin-emu/ -#include "stdafx.h" +#include "stdafx.h" \ No newline at end of file diff --git a/Source/Plugins/Plugin_VideoOGL/Src/stdafx.h b/Source/Plugins/Plugin_VideoOGL/Src/stdafx.h index fdeafc8ca1..8ade6faa40 100644 --- a/Source/Plugins/Plugin_VideoOGL/Src/stdafx.h +++ b/Source/Plugins/Plugin_VideoOGL/Src/stdafx.h @@ -1,4 +1,4 @@ -// Copyright (C) 2003 Dolphin Project.. +// Copyright (C) 2003 Dolphin Project. // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -23,4 +23,3 @@ #include #include -