diff --git a/src/core/gpu_hw_d3d11.cpp b/src/core/gpu_hw_d3d11.cpp index 87c44e8df..97eb39507 100644 --- a/src/core/gpu_hw_d3d11.cpp +++ b/src/core/gpu_hw_d3d11.cpp @@ -2,6 +2,7 @@ #include "common/assert.h" #include "common/d3d11/shader_compiler.h" #include "common/log.h" +#include "common/timer.h" #include "gpu_hw_shadergen.h" #include "host_display.h" #include "host_interface.h" @@ -332,7 +333,8 @@ bool GPU_HW_D3D11::CreateStateObjects() for (u8 transparency_mode = 0; transparency_mode < 5; transparency_mode++) { bl_desc = CD3D11_BLEND_DESC(CD3D11_DEFAULT()); - if (transparency_mode != static_cast(TransparencyMode::Disabled) || m_texture_filtering != GPUTextureFilter::Nearest) + if (transparency_mode != static_cast(TransparencyMode::Disabled) || + m_texture_filtering != GPUTextureFilter::Nearest) { bl_desc.RenderTarget[0].BlendEnable = TRUE; bl_desc.RenderTarget[0].SrcBlend = D3D11_BLEND_ONE; @@ -372,7 +374,19 @@ bool GPU_HW_D3D11::CompileShaders() GPU_HW_ShaderGen shadergen(m_host_display->GetRenderAPI(), m_resolution_scale, m_true_color, m_scaled_dithering, m_texture_filtering, m_using_uv_limits, m_supports_dual_source_blend); - g_host_interface->DisplayLoadingScreen("Compiling shaders..."); + Common::Timer compile_time; + const int progress_total = 1 + 1 + 2 + (4 * 9 * 2 * 2) + 7 + (2 * 3); + int progress_value = 0; +#define UPDATE_PROGRESS() \ + do \ + { \ + progress_value++; \ + if (compile_time.GetTimeSeconds() >= 1.0f) \ + { \ + compile_time.Reset(); \ + g_host_interface->DisplayLoadingScreen("Compiling Shaders", 0, progress_total, progress_value); \ + } \ + } while (0) // input layout { @@ -400,17 +414,23 @@ bool GPU_HW_D3D11::CompileShaders() } } + UPDATE_PROGRESS(); + m_screen_quad_vertex_shader = m_shader_cache.GetVertexShader(m_device.Get(), shadergen.GenerateScreenQuadVertexShader()); if (!m_screen_quad_vertex_shader) return false; + UPDATE_PROGRESS(); + for (u8 textured = 0; textured < 2; textured++) { const std::string vs = shadergen.GenerateBatchVertexShader(ConvertToBoolUnchecked(textured)); m_batch_vertex_shaders[textured] = m_shader_cache.GetVertexShader(m_device.Get(), vs); if (!m_batch_vertex_shaders[textured]) return false; + + UPDATE_PROGRESS(); } for (u8 render_mode = 0; render_mode < 4; render_mode++) @@ -429,6 +449,8 @@ bool GPU_HW_D3D11::CompileShaders() m_shader_cache.GetPixelShader(m_device.Get(), ps); if (!m_batch_pixel_shaders[render_mode][texture_mode][dithering][interlacing]) return false; + + UPDATE_PROGRESS(); } } } @@ -438,33 +460,47 @@ bool GPU_HW_D3D11::CompileShaders() if (!m_copy_pixel_shader) return false; + UPDATE_PROGRESS(); + m_vram_fill_pixel_shader = m_shader_cache.GetPixelShader(m_device.Get(), shadergen.GenerateFillFragmentShader()); if (!m_vram_fill_pixel_shader) return false; + UPDATE_PROGRESS(); + m_vram_interlaced_fill_pixel_shader = m_shader_cache.GetPixelShader(m_device.Get(), shadergen.GenerateInterlacedFillFragmentShader()); if (!m_vram_interlaced_fill_pixel_shader) return false; + UPDATE_PROGRESS(); + m_vram_read_pixel_shader = m_shader_cache.GetPixelShader(m_device.Get(), shadergen.GenerateVRAMReadFragmentShader()); if (!m_vram_read_pixel_shader) return false; + UPDATE_PROGRESS(); + m_vram_write_pixel_shader = m_shader_cache.GetPixelShader(m_device.Get(), shadergen.GenerateVRAMWriteFragmentShader(false)); if (!m_vram_write_pixel_shader) return false; + UPDATE_PROGRESS(); + m_vram_copy_pixel_shader = m_shader_cache.GetPixelShader(m_device.Get(), shadergen.GenerateVRAMCopyFragmentShader()); if (!m_vram_copy_pixel_shader) return false; + UPDATE_PROGRESS(); + m_vram_update_depth_pixel_shader = m_shader_cache.GetPixelShader(m_device.Get(), shadergen.GenerateVRAMUpdateDepthFragmentShader()); if (!m_vram_update_depth_pixel_shader) return false; + UPDATE_PROGRESS(); + for (u8 depth_24bit = 0; depth_24bit < 2; depth_24bit++) { for (u8 interlacing = 0; interlacing < 3; interlacing++) @@ -474,9 +510,15 @@ bool GPU_HW_D3D11::CompileShaders() m_display_pixel_shaders[depth_24bit][interlacing] = m_shader_cache.GetPixelShader(m_device.Get(), ps); if (!m_display_pixel_shaders[depth_24bit][interlacing]) return false; + + UPDATE_PROGRESS(); } } + UPDATE_PROGRESS(); + +#undef UPDATE_PROGRESS + return true; } diff --git a/src/core/gpu_hw_opengl.cpp b/src/core/gpu_hw_opengl.cpp index 97aca0306..cedc9144c 100644 --- a/src/core/gpu_hw_opengl.cpp +++ b/src/core/gpu_hw_opengl.cpp @@ -1,6 +1,7 @@ #include "gpu_hw_opengl.h" #include "common/assert.h" #include "common/log.h" +#include "common/timer.h" #include "gpu_hw_shadergen.h" #include "host_display.h" #include "system.h" @@ -358,7 +359,19 @@ bool GPU_HW_OpenGL::CompilePrograms() GPU_HW_ShaderGen shadergen(m_host_display->GetRenderAPI(), m_resolution_scale, m_true_color, m_scaled_dithering, m_texture_filtering, m_using_uv_limits, m_supports_dual_source_blend); - g_host_interface->DisplayLoadingScreen("Compiling Shaders..."); + Common::Timer compile_time; + const int progress_total = (4 * 9 * 2 * 2) + (2 * 3) + 5; + int progress_value = 0; +#define UPDATE_PROGRESS() \ + do \ + { \ + progress_value++; \ + if (compile_time.GetTimeSeconds() >= 1.0f) \ + { \ + compile_time.Reset(); \ + g_host_interface->DisplayLoadingScreen("Compiling Shaders", 0, progress_total, progress_value); \ + } \ + } while (0) for (u32 render_mode = 0; render_mode < 4; render_mode++) { @@ -416,6 +429,8 @@ bool GPU_HW_OpenGL::CompilePrograms() } m_render_programs[render_mode][texture_mode][dithering][interlacing] = std::move(*prog); + + UPDATE_PROGRESS(); } } } @@ -444,6 +459,7 @@ bool GPU_HW_OpenGL::CompilePrograms() prog->Uniform1i("samp0", 0); } m_display_programs[depth_24bit][interlaced] = std::move(*prog); + UPDATE_PROGRESS(); } } @@ -460,6 +476,7 @@ bool GPU_HW_OpenGL::CompilePrograms() prog->BindUniformBlock("UBOBlock", 1); m_vram_interlaced_fill_program = std::move(*prog); + UPDATE_PROGRESS(); prog = m_shader_cache.GetProgram(shadergen.GenerateScreenQuadVertexShader(), {}, shadergen.GenerateVRAMReadFragmentShader(), @@ -477,6 +494,7 @@ bool GPU_HW_OpenGL::CompilePrograms() prog->Uniform1i("samp0", 0); } m_vram_read_program = std::move(*prog); + UPDATE_PROGRESS(); prog = m_shader_cache.GetProgram(shadergen.GenerateScreenQuadVertexShader(), {}, shadergen.GenerateVRAMCopyFragmentShader(), @@ -494,6 +512,7 @@ bool GPU_HW_OpenGL::CompilePrograms() prog->Uniform1i("samp0", 0); } m_vram_copy_program = std::move(*prog); + UPDATE_PROGRESS(); prog = m_shader_cache.GetProgram(shadergen.GenerateScreenQuadVertexShader(), {}, shadergen.GenerateVRAMUpdateDepthFragmentShader()); @@ -503,6 +522,7 @@ bool GPU_HW_OpenGL::CompilePrograms() prog->Bind(); prog->Uniform1i("samp0", 0); m_vram_update_depth_program = std::move(*prog); + UPDATE_PROGRESS(); if (m_supports_texture_buffer || m_use_ssbo_for_vram_writes) { @@ -524,6 +544,9 @@ bool GPU_HW_OpenGL::CompilePrograms() m_vram_write_program = std::move(*prog); } + UPDATE_PROGRESS(); +#undef UPDATE_PROGRESS + return true; } diff --git a/src/core/gpu_hw_vulkan.cpp b/src/core/gpu_hw_vulkan.cpp index d1c266e96..d9d75b6a1 100644 --- a/src/core/gpu_hw_vulkan.cpp +++ b/src/core/gpu_hw_vulkan.cpp @@ -2,6 +2,7 @@ #include "common/assert.h" #include "common/log.h" #include "common/scope_guard.h" +#include "common/timer.h" #include "common/vulkan/builders.h" #include "common/vulkan/context.h" #include "common/vulkan/shader_cache.h" @@ -579,14 +580,26 @@ bool GPU_HW_Vulkan::CreateTextureBuffer() bool GPU_HW_Vulkan::CompilePipelines() { - g_host_interface->DisplayLoadingScreen("Compiling Shaders..."); - VkDevice device = g_vulkan_context->GetDevice(); VkPipelineCache pipeline_cache = g_vulkan_shader_cache->GetPipelineCache(); GPU_HW_ShaderGen shadergen(m_host_display->GetRenderAPI(), m_resolution_scale, m_true_color, m_scaled_dithering, m_texture_filtering, m_using_uv_limits, m_supports_dual_source_blend); + Common::Timer compile_time; + const int progress_total = 2 + (4 * 9 * 2 * 2) + (2 * 4 * 5 * 9 * 2 * 2) + 1 + 2 + 2 + 2 + 2 + (2 * 3); + int progress_value = 0; +#define UPDATE_PROGRESS() \ + do \ + { \ + progress_value++; \ + if (compile_time.GetTimeSeconds() >= 1.0f) \ + { \ + compile_time.Reset(); \ + g_host_interface->DisplayLoadingScreen("Compiling Shaders", 0, progress_total, progress_value); \ + } \ + } while (0) + // vertex shaders - [textured] // fragment shaders - [render_mode][texture_mode][dithering][interlacing] DimensionalArray batch_vertex_shaders{}; @@ -604,6 +617,7 @@ bool GPU_HW_Vulkan::CompilePipelines() return false; batch_vertex_shaders[textured] = shader; + UPDATE_PROGRESS(); } for (u8 render_mode = 0; render_mode < 4; render_mode++) @@ -623,6 +637,7 @@ bool GPU_HW_Vulkan::CompilePipelines() return false; batch_fragment_shaders[render_mode][texture_mode][dithering][interlacing] = shader; + UPDATE_PROGRESS(); } } } @@ -630,7 +645,7 @@ bool GPU_HW_Vulkan::CompilePipelines() Vulkan::GraphicsPipelineBuilder gpbuilder; - // [primitive][depth_test][render_mode][texture_mode][transparency_mode][dithering][interlacing] + // [depth_test][render_mode][texture_mode][transparency_mode][dithering][interlacing] for (u8 depth_test = 0; depth_test < 2; depth_test++) { for (u8 render_mode = 0; render_mode < 4; render_mode++) @@ -692,6 +707,7 @@ bool GPU_HW_Vulkan::CompilePipelines() m_batch_pipelines[depth_test][render_mode][texture_mode][transparency_mode][dithering][interlacing] = pipeline; + UPDATE_PROGRESS(); } } } @@ -706,6 +722,8 @@ bool GPU_HW_Vulkan::CompilePipelines() if (fullscreen_quad_vertex_shader == VK_NULL_HANDLE) return false; + UPDATE_PROGRESS(); + Common::ScopeGuard fullscreen_quad_vertex_shader_guard([&fullscreen_quad_vertex_shader]() { vkDestroyShaderModule(g_vulkan_context->GetDevice(), fullscreen_quad_vertex_shader, nullptr); }); @@ -736,6 +754,8 @@ bool GPU_HW_Vulkan::CompilePipelines() vkDestroyShaderModule(device, fs, nullptr); if (m_vram_fill_pipelines[interlaced] == VK_NULL_HANDLE) return false; + + UPDATE_PROGRESS(); } } @@ -758,6 +778,8 @@ bool GPU_HW_Vulkan::CompilePipelines() vkDestroyShaderModule(device, fs, nullptr); return false; } + + UPDATE_PROGRESS(); } vkDestroyShaderModule(device, fs, nullptr); @@ -782,6 +804,8 @@ bool GPU_HW_Vulkan::CompilePipelines() vkDestroyShaderModule(device, fs, nullptr); return false; } + + UPDATE_PROGRESS(); } vkDestroyShaderModule(device, fs, nullptr); @@ -804,6 +828,8 @@ bool GPU_HW_Vulkan::CompilePipelines() vkDestroyShaderModule(device, fs, nullptr); if (m_vram_update_depth_pipeline == VK_NULL_HANDLE) return false; + + UPDATE_PROGRESS(); } gpbuilder.Clear(); @@ -827,6 +853,8 @@ bool GPU_HW_Vulkan::CompilePipelines() vkDestroyShaderModule(device, fs, nullptr); if (m_vram_readback_pipeline == VK_NULL_HANDLE) return false; + + UPDATE_PROGRESS(); } gpbuilder.Clear(); @@ -856,10 +884,14 @@ bool GPU_HW_Vulkan::CompilePipelines() vkDestroyShaderModule(device, fs, nullptr); if (m_display_pipelines[depth_24][interlace_mode] == VK_NULL_HANDLE) return false; + + UPDATE_PROGRESS(); } } } +#undef UPDATE_PROGRESS + return true; }