From 5cffa342884df531d911555f7b3db9d2f6d1d1f0 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 3 May 2023 20:42:33 -0400 Subject: [PATCH 001/155] settings,video_core: Consolidate ASTC decoding options Just puts them all neatly into one place. --- src/common/settings.cpp | 2 - src/common/settings.h | 11 +++- src/core/telemetry_session.cpp | 15 +++++- .../renderer_opengl/gl_texture_cache.cpp | 8 +-- .../renderer_vulkan/vk_texture_cache.cpp | 19 ++++--- src/yuzu/configuration/config.cpp | 12 +++-- src/yuzu/configuration/config.h | 1 + src/yuzu/configuration/configure_graphics.cpp | 19 ++++--- src/yuzu/configuration/configure_graphics.ui | 51 ++++++++++++++++--- .../configure_graphics_advanced.cpp | 7 --- .../configure_graphics_advanced.ui | 10 ---- src/yuzu_cmd/config.cpp | 2 - 12 files changed, 105 insertions(+), 52 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 5972480e5..3f56afe94 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -82,7 +82,6 @@ void LogSettings() { values.use_asynchronous_gpu_emulation.GetValue()); log_setting("Renderer_NvdecEmulation", values.nvdec_emulation.GetValue()); log_setting("Renderer_AccelerateASTC", values.accelerate_astc.GetValue()); - log_setting("Renderer_AsyncASTC", values.async_astc.GetValue()); log_setting("Renderer_AstcRecompression", values.astc_recompression.GetValue()); log_setting("Renderer_UseVsync", values.vsync_mode.GetValue()); log_setting("Renderer_UseReactiveFlushing", values.use_reactive_flushing.GetValue()); @@ -246,7 +245,6 @@ void RestoreGlobalState(bool is_powered_on) { values.use_asynchronous_gpu_emulation.SetGlobal(true); values.nvdec_emulation.SetGlobal(true); values.accelerate_astc.SetGlobal(true); - values.async_astc.SetGlobal(true); values.astc_recompression.SetGlobal(true); values.use_reactive_flushing.SetGlobal(true); values.shader_backend.SetGlobal(true); diff --git a/src/common/settings.h b/src/common/settings.h index 59e96e74f..b8ab34f7f 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -16,6 +16,12 @@ namespace Settings { +enum class AstcDecodeMode : u32 { + CPU = 0, + GPU = 1, + CPUAsynchronous = 2, +}; + enum class VSyncMode : u32 { Immediate = 0, Mailbox = 1, @@ -467,8 +473,9 @@ struct Values { GPUAccuracy::Extreme, "gpu_accuracy"}; SwitchableSetting use_asynchronous_gpu_emulation{true, "use_asynchronous_gpu_emulation"}; SwitchableSetting nvdec_emulation{NvdecEmulation::GPU, "nvdec_emulation"}; - SwitchableSetting accelerate_astc{true, "accelerate_astc"}; - SwitchableSetting async_astc{false, "async_astc"}; + SwitchableSetting accelerate_astc{ + AstcDecodeMode::CPU, AstcDecodeMode::CPU, AstcDecodeMode::CPUAsynchronous, + "accelerate_astc"}; Setting vsync_mode{VSyncMode::FIFO, VSyncMode::Immediate, VSyncMode::FIFORelaxed, "use_vsync"}; SwitchableSetting use_reactive_flushing{true, "use_reactive_flushing"}; diff --git a/src/core/telemetry_session.cpp b/src/core/telemetry_session.cpp index 7a2f3c90a..665ffe3a2 100644 --- a/src/core/telemetry_session.cpp +++ b/src/core/telemetry_session.cpp @@ -99,6 +99,18 @@ static constexpr const char* TranslateVSyncMode(Settings::VSyncMode mode) { return "Unknown"; } +static constexpr const char* TranslateASTCDecodeMode(Settings::AstcDecodeMode mode) { + switch (mode) { + case Settings::AstcDecodeMode::CPU: + return "CPU"; + case Settings::AstcDecodeMode::GPU: + return "GPU"; + case Settings::AstcDecodeMode::CPUAsynchronous: + return "CPU Asynchronous"; + } + return "Unknown"; +} + u64 GetTelemetryId() { u64 telemetry_id{}; const auto filename = Common::FS::GetYuzuPath(Common::FS::YuzuPath::ConfigDir) / "telemetry_id"; @@ -254,7 +266,8 @@ void TelemetrySession::AddInitialInfo(Loader::AppLoader& app_loader, Settings::values.use_asynchronous_gpu_emulation.GetValue()); AddField(field_type, "Renderer_NvdecEmulation", TranslateNvdecEmulation(Settings::values.nvdec_emulation.GetValue())); - AddField(field_type, "Renderer_AccelerateASTC", Settings::values.accelerate_astc.GetValue()); + AddField(field_type, "Renderer_AccelerateASTC", + TranslateASTCDecodeMode(Settings::values.accelerate_astc.GetValue())); AddField(field_type, "Renderer_UseVsync", TranslateVSyncMode(Settings::values.vsync_mode.GetValue())); AddField(field_type, "Renderer_ShaderBackend", diff --git a/src/video_core/renderer_opengl/gl_texture_cache.cpp b/src/video_core/renderer_opengl/gl_texture_cache.cpp index 3b446be07..38ae12d8e 100644 --- a/src/video_core/renderer_opengl/gl_texture_cache.cpp +++ b/src/video_core/renderer_opengl/gl_texture_cache.cpp @@ -232,10 +232,9 @@ void ApplySwizzle(GLuint handle, PixelFormat format, std::arrayViewFormats(info.format))), aspect_mask(ImageAspectMask(info.format)) { if (IsPixelFormatASTC(info.format) && !runtime->device.IsOptimalAstcSupported()) { - if (Settings::values.async_astc.GetValue()) { + switch (Settings::values.accelerate_astc.GetValue()) { + case Settings::AstcDecodeMode::GPU: + if (Settings::values.astc_recompression.GetValue() == + Settings::AstcRecompression::Uncompressed && + info.size.depth == 1) { + flags |= VideoCommon::ImageFlagBits::AcceleratedUpload; + } + break; + case Settings::AstcDecodeMode::CPUAsynchronous: flags |= VideoCommon::ImageFlagBits::AsynchronousDecode; - } else if (Settings::values.astc_recompression.GetValue() == - Settings::AstcRecompression::Uncompressed && - Settings::values.accelerate_astc.GetValue() && info.size.depth == 1) { - flags |= VideoCommon::ImageFlagBits::AcceleratedUpload; + break; + default: + break; } flags |= VideoCommon::ImageFlagBits::Converted; flags |= VideoCommon::ImageFlagBits::CostlyLoad; diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 195d3556c..786c1222f 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -764,10 +764,8 @@ void Config::ReadRendererValues() { ReadGlobalSetting(Settings::values.use_asynchronous_gpu_emulation); ReadGlobalSetting(Settings::values.nvdec_emulation); ReadGlobalSetting(Settings::values.accelerate_astc); - ReadGlobalSetting(Settings::values.async_astc); ReadGlobalSetting(Settings::values.astc_recompression); ReadGlobalSetting(Settings::values.use_reactive_flushing); - ReadGlobalSetting(Settings::values.shader_backend); ReadGlobalSetting(Settings::values.use_asynchronous_shaders); ReadGlobalSetting(Settings::values.use_fast_gpu_time); ReadGlobalSetting(Settings::values.use_vulkan_driver_pipeline_cache); @@ -1428,13 +1426,19 @@ void Config::SaveRendererValues() { static_cast(Settings::values.nvdec_emulation.GetValue(global)), static_cast(Settings::values.nvdec_emulation.GetDefault()), Settings::values.nvdec_emulation.UsingGlobal()); - WriteGlobalSetting(Settings::values.accelerate_astc); - WriteGlobalSetting(Settings::values.async_astc); + WriteSetting(QString::fromStdString(Settings::values.accelerate_astc.GetLabel()), + static_cast(Settings::values.accelerate_astc.GetValue(global)), + static_cast(Settings::values.accelerate_astc.GetDefault()), + Settings::values.accelerate_astc.UsingGlobal()); WriteSetting(QString::fromStdString(Settings::values.astc_recompression.GetLabel()), static_cast(Settings::values.astc_recompression.GetValue(global)), static_cast(Settings::values.astc_recompression.GetDefault()), Settings::values.astc_recompression.UsingGlobal()); WriteGlobalSetting(Settings::values.use_reactive_flushing); + WriteSetting(QString::fromStdString(Settings::values.accelerate_astc.GetLabel()), + static_cast(Settings::values.accelerate_astc.GetValue(global)), + static_cast(Settings::values.accelerate_astc.GetDefault()), + Settings::values.shader_backend.UsingGlobal()); WriteSetting(QString::fromStdString(Settings::values.shader_backend.GetLabel()), static_cast(Settings::values.shader_backend.GetValue(global)), static_cast(Settings::values.shader_backend.GetDefault()), diff --git a/src/yuzu/configuration/config.h b/src/yuzu/configuration/config.h index 1211389d2..e066f7552 100644 --- a/src/yuzu/configuration/config.h +++ b/src/yuzu/configuration/config.h @@ -218,3 +218,4 @@ Q_DECLARE_METATYPE(Settings::AntiAliasing); Q_DECLARE_METATYPE(Settings::RendererBackend); Q_DECLARE_METATYPE(Settings::ShaderBackend); Q_DECLARE_METATYPE(Settings::AstcRecompression); +Q_DECLARE_METATYPE(Settings::AstcDecodeMode); diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index a4965524a..e70781357 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -194,14 +194,13 @@ void ConfigureGraphics::SetConfiguration() { ui->use_disk_shader_cache->setEnabled(runtime_lock); ui->nvdec_emulation_widget->setEnabled(runtime_lock); ui->resolution_combobox->setEnabled(runtime_lock); - ui->accelerate_astc->setEnabled(runtime_lock); + ui->astc_decode_mode_combobox->setEnabled(runtime_lock); ui->vsync_mode_layout->setEnabled(runtime_lock || Settings::values.renderer_backend.GetValue() == Settings::RendererBackend::Vulkan); ui->use_disk_shader_cache->setChecked(Settings::values.use_disk_shader_cache.GetValue()); ui->use_asynchronous_gpu_emulation->setChecked( Settings::values.use_asynchronous_gpu_emulation.GetValue()); - ui->accelerate_astc->setChecked(Settings::values.accelerate_astc.GetValue()); if (Settings::IsConfiguringGlobal()) { ui->api->setCurrentIndex(static_cast(Settings::values.renderer_backend.GetValue())); @@ -222,6 +221,11 @@ void ConfigureGraphics::SetConfiguration() { ConfigurationShared::SetHighlight(ui->api_widget, !Settings::values.renderer_backend.UsingGlobal()); + ConfigurationShared::SetPerGameSetting(ui->astc_decode_mode_combobox, + &Settings::values.accelerate_astc); + ConfigurationShared::SetHighlight(ui->astc_decode_mode_layout, + !Settings::values.accelerate_astc.UsingGlobal()); + ConfigurationShared::SetPerGameSetting(ui->nvdec_emulation, &Settings::values.nvdec_emulation); ConfigurationShared::SetHighlight(ui->nvdec_emulation_widget, @@ -337,8 +341,8 @@ void ConfigureGraphics::ApplyConfiguration() { ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_asynchronous_gpu_emulation, ui->use_asynchronous_gpu_emulation, use_asynchronous_gpu_emulation); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.accelerate_astc, ui->accelerate_astc, - accelerate_astc); + ConfigurationShared::ApplyPerGameSetting(&Settings::values.accelerate_astc, + ui->astc_decode_mode_combobox); if (Settings::IsConfiguringGlobal()) { // Guard if during game and set to game-specific value @@ -555,7 +559,7 @@ void ConfigureGraphics::SetupPerGameUI() { ui->use_asynchronous_gpu_emulation->setEnabled( Settings::values.use_asynchronous_gpu_emulation.UsingGlobal()); ui->nvdec_emulation->setEnabled(Settings::values.nvdec_emulation.UsingGlobal()); - ui->accelerate_astc->setEnabled(Settings::values.accelerate_astc.UsingGlobal()); + ui->astc_decode_mode_combobox->setEnabled(Settings::values.accelerate_astc.UsingGlobal()); ui->use_disk_shader_cache->setEnabled(Settings::values.use_disk_shader_cache.UsingGlobal()); ui->bg_button->setEnabled(Settings::values.bg_red.UsingGlobal()); ui->fsr_slider_layout->setEnabled(Settings::values.fsr_sharpening_slider.UsingGlobal()); @@ -577,8 +581,6 @@ void ConfigureGraphics::SetupPerGameUI() { ConfigurationShared::SetColoredTristate( ui->use_disk_shader_cache, Settings::values.use_disk_shader_cache, use_disk_shader_cache); - ConfigurationShared::SetColoredTristate(ui->accelerate_astc, Settings::values.accelerate_astc, - accelerate_astc); ConfigurationShared::SetColoredTristate(ui->use_asynchronous_gpu_emulation, Settings::values.use_asynchronous_gpu_emulation, use_asynchronous_gpu_emulation); @@ -597,6 +599,9 @@ void ConfigureGraphics::SetupPerGameUI() { ConfigurationShared::SetColoredComboBox( ui->anti_aliasing_combobox, ui->anti_aliasing_label, static_cast(Settings::values.anti_aliasing.GetValue(true))); + ConfigurationShared::SetColoredComboBox( + ui->astc_decode_mode_combobox, ui->astc_decode_mode_label, + static_cast(Settings::values.accelerate_astc.GetValue(true))); ConfigurationShared::InsertGlobalItem( ui->api, static_cast(Settings::values.renderer_backend.GetValue(true))); ConfigurationShared::InsertGlobalItem( diff --git a/src/yuzu/configuration/configure_graphics.ui b/src/yuzu/configuration/configure_graphics.ui index 39f70e406..91b09625b 100644 --- a/src/yuzu/configuration/configure_graphics.ui +++ b/src/yuzu/configuration/configure_graphics.ui @@ -181,13 +181,6 @@ - - - - Accelerate ASTC texture decoding - - - @@ -226,6 +219,50 @@ Immediate (no synchronization) just presents whatever is available and can exhib + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + ASTC Texture Decoding Method: + + + + + + + + CPU + + + + + GPU Compute + + + + + CPU Asynchronous (Hack) + + + + + + + diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index c0a044767..e5c99f742 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -26,7 +26,6 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { ui->use_reactive_flushing->setEnabled(runtime_lock); ui->async_present->setEnabled(runtime_lock); ui->renderer_force_max_clock->setEnabled(runtime_lock); - ui->async_astc->setEnabled(runtime_lock); ui->astc_recompression_combobox->setEnabled(runtime_lock); ui->use_asynchronous_shaders->setEnabled(runtime_lock); ui->anisotropic_filtering_combobox->setEnabled(runtime_lock); @@ -35,7 +34,6 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { ui->async_present->setChecked(Settings::values.async_presentation.GetValue()); ui->renderer_force_max_clock->setChecked(Settings::values.renderer_force_max_clock.GetValue()); ui->use_reactive_flushing->setChecked(Settings::values.use_reactive_flushing.GetValue()); - ui->async_astc->setChecked(Settings::values.async_astc.GetValue()); ui->use_asynchronous_shaders->setChecked(Settings::values.use_asynchronous_shaders.GetValue()); ui->use_fast_gpu_time->setChecked(Settings::values.use_fast_gpu_time.GetValue()); ui->use_vulkan_driver_pipeline_cache->setChecked( @@ -79,8 +77,6 @@ void ConfigureGraphicsAdvanced::ApplyConfiguration() { ui->anisotropic_filtering_combobox); ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_reactive_flushing, ui->use_reactive_flushing, use_reactive_flushing); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.async_astc, ui->async_astc, - async_astc); ConfigurationShared::ApplyPerGameSetting(&Settings::values.astc_recompression, ui->astc_recompression_combobox); ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_asynchronous_shaders, @@ -121,7 +117,6 @@ void ConfigureGraphicsAdvanced::SetupPerGameUI() { ui->renderer_force_max_clock->setEnabled( Settings::values.renderer_force_max_clock.UsingGlobal()); ui->use_reactive_flushing->setEnabled(Settings::values.use_reactive_flushing.UsingGlobal()); - ui->async_astc->setEnabled(Settings::values.async_astc.UsingGlobal()); ui->astc_recompression_combobox->setEnabled( Settings::values.astc_recompression.UsingGlobal()); ui->use_asynchronous_shaders->setEnabled( @@ -148,8 +143,6 @@ void ConfigureGraphicsAdvanced::SetupPerGameUI() { renderer_force_max_clock); ConfigurationShared::SetColoredTristate( ui->use_reactive_flushing, Settings::values.use_reactive_flushing, use_reactive_flushing); - ConfigurationShared::SetColoredTristate(ui->async_astc, Settings::values.async_astc, - async_astc); ConfigurationShared::SetColoredTristate(ui->use_asynchronous_shaders, Settings::values.use_asynchronous_shaders, use_asynchronous_shaders); diff --git a/src/yuzu/configuration/configure_graphics_advanced.ui b/src/yuzu/configuration/configure_graphics_advanced.ui index d527a6f38..859ab9366 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.ui +++ b/src/yuzu/configuration/configure_graphics_advanced.ui @@ -130,16 +130,6 @@ - - - - Enables asynchronous ASTC texture decoding, which may reduce load time stutter. This feature is experimental. - - - Decode ASTC textures asynchronously (Hack) - - - diff --git a/src/yuzu_cmd/config.cpp b/src/yuzu_cmd/config.cpp index c5bc472ca..b2049ae57 100644 --- a/src/yuzu_cmd/config.cpp +++ b/src/yuzu_cmd/config.cpp @@ -317,9 +317,7 @@ void Config::ReadValues() { ReadSetting("Renderer", Settings::values.use_asynchronous_shaders); ReadSetting("Renderer", Settings::values.nvdec_emulation); ReadSetting("Renderer", Settings::values.accelerate_astc); - ReadSetting("Renderer", Settings::values.async_astc); ReadSetting("Renderer", Settings::values.astc_recompression); - ReadSetting("Renderer", Settings::values.use_fast_gpu_time); ReadSetting("Renderer", Settings::values.use_vulkan_driver_pipeline_cache); ReadSetting("Renderer", Settings::values.bg_red); From 5ccfaf0517ed365e64458783b30f521d3ed21c78 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 4 May 2023 03:44:53 -0400 Subject: [PATCH 002/155] settings: Pool SetGlobal functions --- src/common/settings.cpp | 63 +++-------------------------------------- src/common/settings.h | 12 ++++++-- 2 files changed, 14 insertions(+), 61 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 3f56afe94..e3f30f7e3 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -7,6 +7,7 @@ #include #include #endif +#include #include #include "common/assert.h" @@ -210,65 +211,9 @@ void RestoreGlobalState(bool is_powered_on) { return; } - // Audio - values.volume.SetGlobal(true); - - // Core - values.use_multi_core.SetGlobal(true); - values.use_unsafe_extended_memory_layout.SetGlobal(true); - - // CPU - values.cpu_accuracy.SetGlobal(true); - values.cpuopt_unsafe_unfuse_fma.SetGlobal(true); - values.cpuopt_unsafe_reduce_fp_error.SetGlobal(true); - values.cpuopt_unsafe_ignore_standard_fpcr.SetGlobal(true); - values.cpuopt_unsafe_inaccurate_nan.SetGlobal(true); - values.cpuopt_unsafe_fastmem_check.SetGlobal(true); - values.cpuopt_unsafe_ignore_global_monitor.SetGlobal(true); - - // Renderer - values.fsr_sharpening_slider.SetGlobal(true); - values.renderer_backend.SetGlobal(true); - values.async_presentation.SetGlobal(true); - values.renderer_force_max_clock.SetGlobal(true); - values.vulkan_device.SetGlobal(true); - values.fullscreen_mode.SetGlobal(true); - values.aspect_ratio.SetGlobal(true); - values.resolution_setup.SetGlobal(true); - values.scaling_filter.SetGlobal(true); - values.anti_aliasing.SetGlobal(true); - values.max_anisotropy.SetGlobal(true); - values.use_speed_limit.SetGlobal(true); - values.speed_limit.SetGlobal(true); - values.use_disk_shader_cache.SetGlobal(true); - values.gpu_accuracy.SetGlobal(true); - values.use_asynchronous_gpu_emulation.SetGlobal(true); - values.nvdec_emulation.SetGlobal(true); - values.accelerate_astc.SetGlobal(true); - values.astc_recompression.SetGlobal(true); - values.use_reactive_flushing.SetGlobal(true); - values.shader_backend.SetGlobal(true); - values.use_asynchronous_shaders.SetGlobal(true); - values.use_fast_gpu_time.SetGlobal(true); - values.use_vulkan_driver_pipeline_cache.SetGlobal(true); - values.bg_red.SetGlobal(true); - values.bg_green.SetGlobal(true); - values.bg_blue.SetGlobal(true); - values.enable_compute_pipelines.SetGlobal(true); - values.use_video_framerate.SetGlobal(true); - - // System - values.language_index.SetGlobal(true); - values.region_index.SetGlobal(true); - values.time_zone_index.SetGlobal(true); - values.rng_seed.SetGlobal(true); - values.sound_index.SetGlobal(true); - - // Controls - values.players.SetGlobal(true); - values.use_docked_mode.SetGlobal(true); - values.vibration_enabled.SetGlobal(true); - values.motion_enabled.SetGlobal(true); + for (const auto& reset : global_reset_registry) { + reset(); + } } } // namespace Settings diff --git a/src/common/settings.h b/src/common/settings.h index b8ab34f7f..61d15467d 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -5,6 +5,8 @@ #include #include +#include +#include #include #include #include @@ -125,6 +127,8 @@ struct ResolutionScalingInfo { } }; +static std::forward_list> global_reset_registry; + /** The Setting class is a simple resource manager. It defines a label and default value alongside * the actual value of the setting for simpler and less-error prone use with frontend * configurations. Specifying a default value and label is required. A minimum and maximum range can @@ -255,7 +259,9 @@ public: */ explicit SwitchableSetting(const Type& default_val, const std::string& name) requires(!ranged) - : Setting{default_val, name} {} + : Setting{default_val, name} { + global_reset_registry.push_front([this]() { this->SetGlobal(true); }); + } virtual ~SwitchableSetting() = default; /** @@ -269,7 +275,9 @@ public: explicit SwitchableSetting(const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name) requires(ranged) - : Setting{default_val, min_val, max_val, name} {} + : Setting{default_val, min_val, max_val, name} { + global_reset_registry.push_front([this]() { this->SetGlobal(true); }); + } /** * Tells this setting to represent either the global or custom setting when other member From 413316560784348b8ea2684d272b974fd0428267 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 5 Jun 2023 20:41:50 -0400 Subject: [PATCH 003/155] settings,core,config_sys: Remove optional type from custom_rtc, rng_seed core: Fix MSVC errors --- src/common/settings.cpp | 3 +- src/common/settings.h | 6 ++-- src/core/core.cpp | 4 ++- src/core/hle/kernel/k_process.cpp | 3 +- src/core/hle/service/spl/spl_module.cpp | 3 +- src/yuzu/configuration/configure_system.cpp | 38 ++++++++++----------- 6 files changed, 32 insertions(+), 25 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index e3f30f7e3..696929479 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -62,7 +62,8 @@ void LogSettings() { LOG_INFO(Config, "yuzu Configuration:"); log_setting("Controls_UseDockedMode", values.use_docked_mode.GetValue()); - log_setting("System_RngSeed", values.rng_seed.GetValue().value_or(0)); + log_setting("System_RngSeedEnabled", values.rng_seed_enabled.GetValue()); + log_setting("System_RngSeed", values.rng_seed.GetValue()); log_setting("System_DeviceName", values.device_name.GetValue()); log_setting("System_CurrentUser", values.current_user.GetValue()); log_setting("System_LanguageIndex", values.language_index.GetValue()); diff --git a/src/common/settings.h b/src/common/settings.h index 61d15467d..999f8b5be 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -505,10 +505,12 @@ struct Values { SwitchableSetting bg_blue{0, "bg_blue"}; // System - SwitchableSetting> rng_seed{std::optional(), "rng_seed"}; + SwitchableSetting rng_seed_enabled{false, "rng_seed_enabled"}; + SwitchableSetting rng_seed{0, "rng_seed"}; Setting device_name{"Yuzu", "device_name"}; // Measured in seconds since epoch - std::optional custom_rtc; + SwitchableSetting custom_rtc_enabled{false, "custom_rtc_enabled"}; + SwitchableSetting custom_rtc{0, "custom_rtc"}; // Set on game boot, reset on stop. Seconds difference between current time and `custom_rtc` s64 custom_rtc_differential; diff --git a/src/core/core.cpp b/src/core/core.cpp index 9e3eb3795..da1baa892 100644 --- a/src/core/core.cpp +++ b/src/core/core.cpp @@ -149,7 +149,9 @@ struct System::Impl { const auto current_time = std::chrono::duration_cast(posix_time).count(); Settings::values.custom_rtc_differential = - Settings::values.custom_rtc.value_or(current_time) - current_time; + (Settings::values.custom_rtc_enabled ? Settings::values.custom_rtc.GetValue() + : current_time) - + current_time; // Create a default fs if one doesn't already exist. if (virtual_filesystem == nullptr) { diff --git a/src/core/hle/kernel/k_process.cpp b/src/core/hle/kernel/k_process.cpp index efe86ad27..ae064ee04 100644 --- a/src/core/hle/kernel/k_process.cpp +++ b/src/core/hle/kernel/k_process.cpp @@ -81,7 +81,8 @@ Result KProcess::Initialize(KProcess* process, Core::System& system, std::string process->m_capabilities.InitializeForMetadatalessProcess(); process->m_is_initialized = true; - std::mt19937 rng(Settings::values.rng_seed.GetValue().value_or(std::time(nullptr))); + std::mt19937 rng(Settings::values.rng_seed_enabled ? Settings::values.rng_seed.GetValue() + : static_cast(std::time(nullptr))); std::uniform_int_distribution distribution; std::generate(process->m_random_entropy.begin(), process->m_random_entropy.end(), [&] { return distribution(rng); }); diff --git a/src/core/hle/service/spl/spl_module.cpp b/src/core/hle/service/spl/spl_module.cpp index 0227d4393..cd631b2ea 100644 --- a/src/core/hle/service/spl/spl_module.cpp +++ b/src/core/hle/service/spl/spl_module.cpp @@ -19,7 +19,8 @@ namespace Service::SPL { Module::Interface::Interface(Core::System& system_, std::shared_ptr module_, const char* name) : ServiceFramework{system_, name}, module{std::move(module_)}, - rng(Settings::values.rng_seed.GetValue().value_or(std::time(nullptr))) {} + rng(Settings::values.rng_seed_enabled ? Settings::values.rng_seed.GetValue() + : static_cast(std::time(nullptr))) {} Module::Interface::~Interface() = default; diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index f1ae312c6..c892635b8 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -95,19 +95,20 @@ void ConfigureSystem::RetranslateUI() { void ConfigureSystem::SetConfiguration() { enabled = !system.IsPoweredOn(); - const auto rng_seed = - QStringLiteral("%1") - .arg(Settings::values.rng_seed.GetValue().value_or(0), 8, 16, QLatin1Char{'0'}) - .toUpper(); - const auto rtc_time = Settings::values.custom_rtc.value_or(QDateTime::currentSecsSinceEpoch()); + const auto rng_seed = QStringLiteral("%1") + .arg(Settings::values.rng_seed.GetValue(), 8, 16, QLatin1Char{'0'}) + .toUpper(); + const auto rtc_time = Settings::values.custom_rtc_enabled + ? Settings::values.custom_rtc.GetValue() + : QDateTime::currentSecsSinceEpoch(); - ui->rng_seed_checkbox->setChecked(Settings::values.rng_seed.GetValue().has_value()); - ui->rng_seed_edit->setEnabled(Settings::values.rng_seed.GetValue().has_value() && + ui->rng_seed_checkbox->setChecked(Settings::values.rng_seed_enabled.GetValue()); + ui->rng_seed_edit->setEnabled(Settings::values.rng_seed_enabled.GetValue() && Settings::values.rng_seed.UsingGlobal()); ui->rng_seed_edit->setText(rng_seed); - ui->custom_rtc_checkbox->setChecked(Settings::values.custom_rtc.has_value()); - ui->custom_rtc_edit->setEnabled(Settings::values.custom_rtc.has_value()); + ui->custom_rtc_checkbox->setChecked(Settings::values.custom_rtc_enabled.GetValue()); + ui->custom_rtc_edit->setEnabled(Settings::values.custom_rtc_enabled.GetValue()); ui->custom_rtc_edit->setDateTime(QDateTime::fromSecsSinceEpoch(rtc_time)); ui->device_name_edit->setText( QString::fromUtf8(Settings::values.device_name.GetValue().c_str())); @@ -142,13 +143,15 @@ void ConfigureSystem::ApplyConfiguration() { // to allow in-game time to be fast forwarded if (Settings::IsConfiguringGlobal()) { if (ui->custom_rtc_checkbox->isChecked()) { + Settings::values.custom_rtc_enabled = true; Settings::values.custom_rtc = ui->custom_rtc_edit->dateTime().toSecsSinceEpoch(); if (system.IsPoweredOn()) { - const s64 posix_time{*Settings::values.custom_rtc}; + const s64 posix_time{Settings::values.custom_rtc.GetValue() + + Service::Time::TimeManager::GetExternalTimeZoneOffset()}; system.GetTimeManager().UpdateLocalSystemClockTime(posix_time); } } else { - Settings::values.custom_rtc = std::nullopt; + Settings::values.custom_rtc_enabled = false; } } @@ -169,26 +172,23 @@ void ConfigureSystem::ApplyConfiguration() { if (Settings::IsConfiguringGlobal()) { // Guard if during game and set to game-specific value if (Settings::values.rng_seed.UsingGlobal()) { + Settings::values.rng_seed_enabled = ui->rng_seed_checkbox->isChecked(); if (ui->rng_seed_checkbox->isChecked()) { Settings::values.rng_seed.SetValue(ui->rng_seed_edit->text().toUInt(nullptr, 16)); - } else { - Settings::values.rng_seed.SetValue(std::nullopt); } } } else { switch (use_rng_seed) { case ConfigurationShared::CheckState::On: case ConfigurationShared::CheckState::Off: + Settings::values.rng_seed_enabled.SetGlobal(false); Settings::values.rng_seed.SetGlobal(false); if (ui->rng_seed_checkbox->isChecked()) { Settings::values.rng_seed.SetValue(ui->rng_seed_edit->text().toUInt(nullptr, 16)); - } else { - Settings::values.rng_seed.SetValue(std::nullopt); } break; case ConfigurationShared::CheckState::Global: - Settings::values.rng_seed.SetGlobal(false); - Settings::values.rng_seed.SetValue(std::nullopt); + Settings::values.rng_seed_enabled.SetGlobal(true); Settings::values.rng_seed.SetGlobal(true); break; case ConfigurationShared::CheckState::Count: @@ -217,8 +217,8 @@ void ConfigureSystem::SetupPerGameUI() { ConfigurationShared::SetColoredTristate( ui->rng_seed_checkbox, Settings::values.rng_seed.UsingGlobal(), - Settings::values.rng_seed.GetValue().has_value(), - Settings::values.rng_seed.GetValue(true).has_value(), use_rng_seed); + Settings::values.rng_seed_enabled.GetValue(), + Settings::values.rng_seed_enabled.GetValue(true), use_rng_seed); ConfigurationShared::SetColoredTristate(ui->use_unsafe_extended_memory_layout, Settings::values.use_unsafe_extended_memory_layout, From e7543e8b84c5520e09d5703bc8b191a1a76195b7 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 5 Jun 2023 20:45:33 -0400 Subject: [PATCH 004/155] uisettings: Fix typings --- src/yuzu/multiplayer/direct_connect.cpp | 9 +-- src/yuzu/multiplayer/host_room.cpp | 16 +++-- src/yuzu/multiplayer/lobby.cpp | 7 ++- src/yuzu/uisettings.h | 84 ++++++++++++------------- 4 files changed, 61 insertions(+), 55 deletions(-) diff --git a/src/yuzu/multiplayer/direct_connect.cpp b/src/yuzu/multiplayer/direct_connect.cpp index d71cc23a7..a415a953f 100644 --- a/src/yuzu/multiplayer/direct_connect.cpp +++ b/src/yuzu/multiplayer/direct_connect.cpp @@ -34,13 +34,14 @@ DirectConnectWindow::DirectConnectWindow(Core::System& system_, QWidget* parent) connect(watcher, &QFutureWatcher::finished, this, &DirectConnectWindow::OnConnection); ui->nickname->setValidator(validation.GetNickname()); - ui->nickname->setText(UISettings::values.multiplayer_nickname.GetValue()); + ui->nickname->setText( + QString::fromStdString(UISettings::values.multiplayer_nickname.GetValue())); if (ui->nickname->text().isEmpty() && !Settings::values.yuzu_username.GetValue().empty()) { // Use yuzu Web Service user name as nickname by default ui->nickname->setText(QString::fromStdString(Settings::values.yuzu_username.GetValue())); } ui->ip->setValidator(validation.GetIP()); - ui->ip->setText(UISettings::values.multiplayer_ip.GetValue()); + ui->ip->setText(QString::fromStdString(UISettings::values.multiplayer_ip.GetValue())); ui->port->setValidator(validation.GetPort()); ui->port->setText(QString::number(UISettings::values.multiplayer_port.GetValue())); @@ -91,8 +92,8 @@ void DirectConnectWindow::Connect() { } // Store settings - UISettings::values.multiplayer_nickname = ui->nickname->text(); - UISettings::values.multiplayer_ip = ui->ip->text(); + UISettings::values.multiplayer_nickname = ui->nickname->text().toStdString(); + UISettings::values.multiplayer_ip = ui->ip->text().toStdString(); if (ui->port->isModified() && !ui->port->text().isEmpty()) { UISettings::values.multiplayer_port = ui->port->text().toInt(); } else { diff --git a/src/yuzu/multiplayer/host_room.cpp b/src/yuzu/multiplayer/host_room.cpp index a8faa5b24..ef364ee43 100644 --- a/src/yuzu/multiplayer/host_room.cpp +++ b/src/yuzu/multiplayer/host_room.cpp @@ -55,12 +55,14 @@ HostRoomWindow::HostRoomWindow(QWidget* parent, QStandardItemModel* list, connect(ui->host, &QPushButton::clicked, this, &HostRoomWindow::Host); // Restore the settings: - ui->username->setText(UISettings::values.multiplayer_room_nickname.GetValue()); + ui->username->setText( + QString::fromStdString(UISettings::values.multiplayer_room_nickname.GetValue())); if (ui->username->text().isEmpty() && !Settings::values.yuzu_username.GetValue().empty()) { // Use yuzu Web Service user name as nickname by default ui->username->setText(QString::fromStdString(Settings::values.yuzu_username.GetValue())); } - ui->room_name->setText(UISettings::values.multiplayer_room_name.GetValue()); + ui->room_name->setText( + QString::fromStdString(UISettings::values.multiplayer_room_name.GetValue())); ui->port->setText(QString::number(UISettings::values.multiplayer_room_port.GetValue())); ui->max_player->setValue(UISettings::values.multiplayer_max_player.GetValue()); int index = UISettings::values.multiplayer_host_type.GetValue(); @@ -72,7 +74,8 @@ HostRoomWindow::HostRoomWindow(QWidget* parent, QStandardItemModel* list, if (index != -1) { ui->game_list->setCurrentIndex(index); } - ui->room_description->setText(UISettings::values.multiplayer_room_description.GetValue()); + ui->room_description->setText( + QString::fromStdString(UISettings::values.multiplayer_room_description.GetValue())); } HostRoomWindow::~HostRoomWindow() = default; @@ -218,8 +221,8 @@ void HostRoomWindow::Host() { Network::NoPreferredIP, password, token); // Store settings - UISettings::values.multiplayer_room_nickname = ui->username->text(); - UISettings::values.multiplayer_room_name = ui->room_name->text(); + UISettings::values.multiplayer_room_nickname = ui->username->text().toStdString(); + UISettings::values.multiplayer_room_name = ui->room_name->text().toStdString(); UISettings::values.multiplayer_game_id = ui->game_list->currentData(GameListItemPath::ProgramIdRole).toLongLong(); UISettings::values.multiplayer_max_player = ui->max_player->value(); @@ -230,7 +233,8 @@ void HostRoomWindow::Host() { } else { UISettings::values.multiplayer_room_port = Network::DefaultRoomPort; } - UISettings::values.multiplayer_room_description = ui->room_description->toPlainText(); + UISettings::values.multiplayer_room_description = + ui->room_description->toPlainText().toStdString(); ui->host->setEnabled(true); emit SaveConfig(); close(); diff --git a/src/yuzu/multiplayer/lobby.cpp b/src/yuzu/multiplayer/lobby.cpp index 387f6f7c9..603e9ae3d 100644 --- a/src/yuzu/multiplayer/lobby.cpp +++ b/src/yuzu/multiplayer/lobby.cpp @@ -60,7 +60,8 @@ Lobby::Lobby(QWidget* parent, QStandardItemModel* list, ui->room_list->setContextMenuPolicy(Qt::CustomContextMenu); ui->nickname->setValidator(validation.GetNickname()); - ui->nickname->setText(UISettings::values.multiplayer_nickname.GetValue()); + ui->nickname->setText( + QString::fromStdString(UISettings::values.multiplayer_nickname.GetValue())); // Try find the best nickname by default if (ui->nickname->text().isEmpty() || ui->nickname->text() == QStringLiteral("yuzu")) { @@ -202,9 +203,9 @@ void Lobby::OnJoinRoom(const QModelIndex& source) { // TODO(jroweboy): disable widgets and display a connecting while we wait // Save settings - UISettings::values.multiplayer_nickname = ui->nickname->text(); + UISettings::values.multiplayer_nickname = ui->nickname->text().toStdString(); UISettings::values.multiplayer_ip = - proxy->data(connection_index, LobbyItemHost::HostIPRole).toString(); + proxy->data(connection_index, LobbyItemHost::HostIPRole).value().toStdString(); UISettings::values.multiplayer_port = proxy->data(connection_index, LobbyItemHost::HostPortRole).toInt(); emit SaveConfig(); diff --git a/src/yuzu/uisettings.h b/src/yuzu/uisettings.h index 20a517d34..0be8ee369 100644 --- a/src/yuzu/uisettings.h +++ b/src/yuzu/uisettings.h @@ -14,6 +14,8 @@ #include "common/common_types.h" #include "common/settings.h" +using Settings::Setting; + namespace UISettings { bool IsDarkTheme(); @@ -64,30 +66,33 @@ struct Values { QByteArray gamelist_header_state; QByteArray microprofile_geometry; - Settings::Setting microprofile_visible{false, "microProfileDialogVisible"}; + Setting microprofile_visible{false, "microProfileDialogVisible"}; - Settings::Setting single_window_mode{true, "singleWindowMode"}; - Settings::Setting fullscreen{false, "fullscreen"}; - Settings::Setting display_titlebar{true, "displayTitleBars"}; - Settings::Setting show_filter_bar{true, "showFilterBar"}; - Settings::Setting show_status_bar{true, "showStatusBar"}; - - Settings::Setting confirm_before_closing{true, "confirmClose"}; - Settings::Setting first_start{true, "firstStart"}; - Settings::Setting pause_when_in_background{false, "pauseWhenInBackground"}; - Settings::Setting mute_when_in_background{false, "muteWhenInBackground"}; - Settings::Setting hide_mouse{true, "hideInactiveMouse"}; - Settings::Setting controller_applet_disabled{false, "disableControllerApplet"}; + Setting single_window_mode{true, "singleWindowMode"}; + Setting fullscreen{false, "fullscreen"}; + Setting display_titlebar{true, "displayTitleBars"}; + Setting show_filter_bar{true, "showFilterBar"}; + Setting show_status_bar{true, "showStatusBar"}; + Setting confirm_before_closing{true, "confirmClose"}; + Setting first_start{true, "firstStart"}; + Setting pause_when_in_background{false, "pauseWhenInBackground"}; + Setting mute_when_in_background{false, "muteWhenInBackground"}; + Setting hide_mouse{true, "hideInactiveMouse"}; + Setting controller_applet_disabled{false, "disableControllerApplet"}; // Set when Vulkan is known to crash the application bool has_broken_vulkan = false; - Settings::Setting select_user_on_boot{false, "select_user_on_boot"}; + Setting select_user_on_boot{false, "select_user_on_boot"}; + Setting disable_web_applet{true, "disable_web_applet"}; // Discord RPC - Settings::Setting enable_discord_presence{true, "enable_discord_presence"}; + Setting enable_discord_presence{true, "enable_discord_presence"}; - Settings::Setting enable_screenshot_save_as{true, "enable_screenshot_save_as"}; + // logging + Setting show_console{false, "showConsole"}; + + Setting enable_screenshot_save_as{true, "enable_screenshot_save_as"}; QString roms_path; QString symbols_path; @@ -102,47 +107,42 @@ struct Values { // Shortcut name std::vector shortcuts; - Settings::Setting callout_flags{0, "calloutFlags"}; + Setting callout_flags{0, "calloutFlags"}; // multiplayer settings - Settings::Setting multiplayer_nickname{{}, "nickname"}; - Settings::Setting multiplayer_ip{{}, "ip"}; - Settings::SwitchableSetting multiplayer_port{24872, 0, UINT16_MAX, "port"}; - Settings::Setting multiplayer_room_nickname{{}, "room_nickname"}; - Settings::Setting multiplayer_room_name{{}, "room_name"}; - Settings::SwitchableSetting multiplayer_max_player{8, 0, 8, "max_player"}; - Settings::SwitchableSetting multiplayer_room_port{24872, 0, UINT16_MAX, - "room_port"}; - Settings::SwitchableSetting multiplayer_host_type{0, 0, 1, "host_type"}; - Settings::Setting multiplayer_game_id{{}, "game_id"}; - Settings::Setting multiplayer_room_description{{}, "room_description"}; + Setting multiplayer_nickname{{}, "nickname"}; + Setting multiplayer_ip{{}, "ip"}; + Setting multiplayer_port{24872, 0, UINT16_MAX, "port"}; + Setting multiplayer_room_nickname{{}, "room_nickname"}; + Setting multiplayer_room_name{{}, "room_name"}; + Setting multiplayer_max_player{8, 0, 8, "max_player"}; + Setting multiplayer_room_port{24872, 0, UINT16_MAX, "room_port"}; + Setting multiplayer_host_type{0, 0, 1, "host_type"}; + Setting multiplayer_game_id{{}, "game_id"}; + Setting multiplayer_room_description{{}, "room_description"}; std::pair, std::vector> multiplayer_ban_list; - // logging - Settings::Setting show_console{false, "showConsole"}; - // Game List - Settings::Setting show_add_ons{true, "show_add_ons"}; - Settings::Setting game_icon_size{64, "game_icon_size"}; - Settings::Setting folder_icon_size{48, "folder_icon_size"}; - Settings::Setting row_1_text_id{3, "row_1_text_id"}; - Settings::Setting row_2_text_id{2, "row_2_text_id"}; + Setting show_add_ons{true, "show_add_ons"}; + Setting game_icon_size{64, "game_icon_size"}; + Setting folder_icon_size{48, "folder_icon_size"}; + Setting row_1_text_id{3, "row_1_text_id"}; + Setting row_2_text_id{2, "row_2_text_id"}; std::atomic_bool is_game_list_reload_pending{false}; - Settings::Setting cache_game_list{true, "cache_game_list"}; - Settings::Setting favorites_expanded{true, "favorites_expanded"}; + Setting cache_game_list{true, "cache_game_list"}; + Setting favorites_expanded{true, "favorites_expanded"}; QVector favorited_ids; // Compatibility List - Settings::Setting show_compat{false, "show_compat"}; + Setting show_compat{false, "show_compat"}; // Size & File Types Column - Settings::Setting show_size{true, "show_size"}; - Settings::Setting show_types{true, "show_types"}; + Setting show_size{true, "show_size"}; + Setting show_types{true, "show_types"}; bool configuration_applied; bool reset_to_defaults; bool shortcut_already_warned{false}; - Settings::Setting disable_web_applet{true, "disable_web_applet"}; }; extern Values values; From 60773194a039fced8cf2da308e1b8220d08a1636 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 5 Jun 2023 21:05:22 -0400 Subject: [PATCH 005/155] settings: Add a registry of settings LoadString: Sanitize input settings: Handle empty string, remove redundant category settings: Rename Input to Controls, FS to DataStorage settings: Fix Controls groups information settings: Move use_docked_mode to System (again) settings: Document settings: Add type identification function settings: Move registry into values settings: Move global_reset_registry into values settings: Separate AdvGraphics from Renderer settings: More document squash settings: Use linkage object uisettings: Move registry into settings Probably wont build without uisettings: Use settings linkage object config: Load settings with a map Uses the new all_settings vector to load settings. qt-config: Rename settings category qt config: Rename to read category config: Read/write contols category with for_each This is extremely limited due to the complexity of the Controls group, but this handles the the settings that use the interface. qt-config: Use new settings registry qt-config: Read/write advgrphics qt-config: Use settings linkage object yuzu_cmd: Load setting off of vector cmd-config: Finish settings rename config: Read controls settings group with for_each cmd/config: Move registry into values cmd: Read adv graphics cmd-config: Use settings linkage object --- src/common/settings.cpp | 52 +- src/common/settings.h | 600 +++++++++++++----- src/yuzu/configuration/config.cpp | 586 ++++------------- src/yuzu/configuration/config.h | 13 +- .../configuration/configuration_shared.cpp | 19 - src/yuzu/configuration/configuration_shared.h | 22 +- src/yuzu/uisettings.h | 86 +-- src/yuzu_cmd/config.cpp | 167 +---- src/yuzu_cmd/config.h | 1 + 9 files changed, 688 insertions(+), 858 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 696929479..59934803e 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -144,6 +144,56 @@ float Volume() { return values.volume.GetValue() / static_cast(values.volume.GetDefault()); } +const char* TranslateCategory(Category category) { + switch (category) { + case Category::Audio: + return "Audio"; + case Category::Core: + return "Core"; + case Category::Cpu: + return "Cpu"; + case Category::Renderer: + return "Renderer"; + case Category::System: + return "System"; + case Category::DataStorage: + return "Data Storage"; + case Category::Debugging: + return "Debugging"; + case Category::Miscellaneous: + return "Miscellaneous"; + case Category::Network: + return "Network"; + case Category::WebService: + return "WebService"; + case Category::AddOns: + return "DisabledAddOns"; + case Category::Controls: + return "Controls"; + case Category::Ui: + return "UI"; + case Category::UiLayout: + return "UiLayout"; + case Category::UiGameList: + return "UiGameList"; + case Category::Screenshots: + return "Screenshots"; + case Category::Shortcuts: + return "Shortcuts"; + case Category::Multiplayer: + return "Multiplayer"; + case Category::Services: + return "Services"; + case Category::Paths: + return "Paths"; + case Category::MaxEnum: + break; + case Category::AdvancedGraphics: + return "Renderer"; + } + return "Miscellaneous"; +} + void UpdateRescalingInfo() { const auto setup = values.resolution_setup.GetValue(); auto& info = values.resolution_info; @@ -212,7 +262,7 @@ void RestoreGlobalState(bool is_powered_on) { return; } - for (const auto& reset : global_reset_registry) { + for (const auto& reset : values.linkage.restore_functions) { reset(); } } diff --git a/src/common/settings.h b/src/common/settings.h index 999f8b5be..df4bcb053 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -9,7 +9,9 @@ #include #include #include +#include #include +#include #include #include @@ -104,6 +106,33 @@ enum class AstcRecompression : u32 { Bc3 = 2, }; +enum class Category : u32 { + Audio, + Core, + Cpu, + Renderer, + AdvancedGraphics, + System, + DataStorage, + Debugging, + Miscellaneous, + Network, + WebService, + AddOns, + Controls, + Ui, + UiLayout, + UiGameList, + Screenshots, + Shortcuts, + Multiplayer, + Services, + Paths, + MaxEnum, +}; + +const char* TranslateCategory(Settings::Category category); + struct ResolutionScalingInfo { u32 up_scale{1}; u32 down_shift{0}; @@ -127,15 +156,40 @@ struct ResolutionScalingInfo { } }; -static std::forward_list> global_reset_registry; +class BasicSetting { +protected: + explicit BasicSetting() = default; -/** The Setting class is a simple resource manager. It defines a label and default value alongside - * the actual value of the setting for simpler and less-error prone use with frontend - * configurations. Specifying a default value and label is required. A minimum and maximum range can - * be specified for sanitization. +public: + virtual ~BasicSetting() = default; + + virtual Category Category() const = 0; + virtual constexpr bool Switchable() const = 0; + virtual std::string ToString() const = 0; + virtual void LoadString(const std::string& load) = 0; + virtual const std::string& GetLabel() const = 0; + virtual std::string DefaultToString() const = 0; + virtual bool Save() const = 0; + virtual std::type_index TypeId() const = 0; + virtual void SetGlobal(bool global) {} + virtual bool UsingGlobal() const { + return false; + } +}; + +class Linkage { +public: + std::map> by_category; + std::vector> restore_functions; +}; + +/** The Setting class is a simple resource manager. It defines a label and default value + * alongside the actual value of the setting for simpler and less-error prone use with frontend + * configurations. Specifying a default value and label is required. A minimum and maximum range + * can be specified for sanitization. */ -template -class Setting { +template +class Setting : public BasicSetting { protected: Setting() = default; @@ -151,27 +205,36 @@ public: /** * Sets a default value, label, and setting value. * + * @param linkage Setting registry * @param default_val Initial value of the setting, and default value of the setting * @param name Label for the setting + * @param category_ Category of the setting AKA INI group */ - explicit Setting(const Type& default_val, const std::string& name) + explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, + enum Category category_) requires(!ranged) - : value{default_val}, default_value{default_val}, label{name} {} + : value{default_val}, default_value{default_val}, label{name}, category{category_} { + linkage.by_category[category].push_front(this); + } virtual ~Setting() = default; /** * Sets a default value, minimum value, maximum value, and label. * + * @param linkage Setting registry * @param default_val Initial value of the setting, and default value of the setting * @param min_val Sets the minimum allowed value of the setting * @param max_val Sets the maximum allowed value of the setting * @param name Label for the setting + * @param category_ Category of the setting AKA INI group */ - explicit Setting(const Type& default_val, const Type& min_val, const Type& max_val, - const std::string& name) + explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, + const Type& max_val, const std::string& name, enum Category category_) requires(ranged) - : value{default_val}, - default_value{default_val}, maximum{max_val}, minimum{min_val}, label{name} {} + : value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val}, + label{name}, category{category_} { + linkage.by_category[category].push_front(this); + } /** * Returns a reference to the setting's value. @@ -206,10 +269,61 @@ public: * * @returns A reference to the label */ - [[nodiscard]] const std::string& GetLabel() const { + [[nodiscard]] const std::string& GetLabel() const override { return label; } + /** + * Returns the setting's category AKA INI group. + * + * @returns The setting's category + */ + [[nodiscard]] enum Category Category() const override { + return category; + } + + /** + * Returns whether the current setting is Switchable. + * + * @returns If the setting is a SwitchableSetting + */ + [[nodiscard]] virtual constexpr bool Switchable() const override { + return false; + } + +private: + std::string ToString(const Type& value_) const { + if constexpr (std::is_same()) { + return value_; + } else if constexpr (std::is_same>()) { + return value_.has_value() ? std::to_string(*value_) : "0"; + } else if constexpr (std::is_same()) { + return value_ ? "true" : "false"; + } else { + return std::to_string(static_cast(value_)); + } + } + +public: + /** + * Converts the value of the setting to a std::string. Respects the global state if the setting + * has one. + * + * @returns The current setting as a std::string + */ + std::string ToString() const override { + return ToString(this->GetValue()); + } + + /** + * Returns the default value of the setting as a std::string. + * + * @returns The default value as a string. + */ + std::string DefaultToString() const override { + return ToString(default_value); + } + /** * Assigns a value to the setting. * @@ -232,12 +346,58 @@ public: return value; } + /** + * Converts the given value to the Setting's type of value. Uses SetValue to enter the setting, + * thus respecting its constraints. + * + * @param input The desired value + */ + void LoadString(const std::string& input) override { + if (input.empty()) { + this->SetValue(this->GetDefault()); + return; + } + try { + if constexpr (std::is_same()) { + this->SetValue(input); + } else if constexpr (std::is_same>()) { + this->SetValue(static_cast(std::stoll(input))); + } else if constexpr (std::is_same()) { + this->SetValue(input == "true"); + } else { + this->SetValue(static_cast(std::stoll(input))); + } + } catch (std::invalid_argument) { + this->SetValue(this->GetDefault()); + } + } + + /** + * Returns the save preference of the setting i.e. when saving or reading the setting from a + * frontend, whether this setting should be skipped. + * + * @returns The save preference + */ + virtual bool Save() const override { + return save; + } + + /** + * Gives us another way to identify the setting without having to go through a string. + * + * @returns the type_index of the setting's type + */ + virtual std::type_index TypeId() const override { + return std::type_index(typeid(Type)); + } + protected: - Type value{}; ///< The setting - const Type default_value{}; ///< The default value - const Type maximum{}; ///< Maximum allowed value of the setting - const Type minimum{}; ///< Minimum allowed value of the setting - const std::string label{}; ///< The setting's label + Type value{}; ///< The setting + const Type default_value{}; ///< The default value + const Type maximum{}; ///< Maximum allowed value of the setting + const Type minimum{}; ///< Minimum allowed value of the setting + const std::string label{}; ///< The setting's label + const enum Category category; ///< The setting's category AKA INI group }; /** @@ -248,35 +408,40 @@ protected: * * By default, the global setting is used. */ -template -class SwitchableSetting : virtual public Setting { +template +class SwitchableSetting : virtual public Setting { public: /** * Sets a default value, label, and setting value. * + * @param linkage Setting registry * @param default_val Initial value of the setting, and default value of the setting * @param name Label for the setting + * @param category_ Category of the setting AKA INI group */ - explicit SwitchableSetting(const Type& default_val, const std::string& name) + explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, + Category category) requires(!ranged) - : Setting{default_val, name} { - global_reset_registry.push_front([this]() { this->SetGlobal(true); }); + : Setting{linkage, default_val, name, category} { + linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } virtual ~SwitchableSetting() = default; /** * Sets a default value, minimum value, maximum value, and label. * + * @param linkage Setting registry * @param default_val Initial value of the setting, and default value of the setting * @param min_val Sets the minimum allowed value of the setting * @param max_val Sets the maximum allowed value of the setting * @param name Label for the setting + * @param category_ Category of the setting AKA INI group */ - explicit SwitchableSetting(const Type& default_val, const Type& min_val, const Type& max_val, - const std::string& name) + explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, + const Type& max_val, const std::string& name, Category category) requires(ranged) - : Setting{default_val, min_val, max_val, name} { - global_reset_registry.push_front([this]() { this->SetGlobal(true); }); + : Setting{linkage, default_val, min_val, max_val, name, category} { + linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } /** @@ -285,7 +450,7 @@ public: * * @param to_global Whether to use the global or custom setting. */ - void SetGlobal(bool to_global) { + void SetGlobal(bool to_global) override { use_global = to_global; } @@ -294,7 +459,7 @@ public: * * @returns The global state */ - [[nodiscard]] bool UsingGlobal() const { + [[nodiscard]] bool UsingGlobal() const override { return use_global; } @@ -333,6 +498,10 @@ public: } } + [[nodiscard]] virtual constexpr bool Switchable() const override { + return true; + } + /** * Assigns the current setting value depending on the global state. * @@ -405,211 +574,290 @@ struct TouchFromButtonMap { }; struct Values { + Linkage linkage{}; + // Audio - Setting sink_id{"auto", "output_engine"}; - Setting audio_output_device_id{"auto", "output_device"}; - Setting audio_input_device_id{"auto", "input_device"}; - Setting audio_muted{false, "audio_muted"}; - SwitchableSetting volume{100, 0, 200, "volume"}; - Setting dump_audio_commands{false, "dump_audio_commands"}; + Setting sink_id{linkage, "auto", "output_engine", Category::Audio}; + Setting audio_output_device_id{linkage, "auto", "output_device", Category::Audio}; + Setting audio_input_device_id{linkage, "auto", "input_device", Category::Audio}; + Setting audio_muted{linkage, false, "audio_muted", Category::Audio}; + SwitchableSetting volume{linkage, 100, 0, 200, "volume", Category::Audio}; + Setting dump_audio_commands{linkage, false, "dump_audio_commands", + Category::Audio}; // Core - SwitchableSetting use_multi_core{true, "use_multi_core"}; - SwitchableSetting use_unsafe_extended_memory_layout{false, - "use_unsafe_extended_memory_layout"}; + SwitchableSetting use_multi_core{linkage, true, "use_multi_core", Category::Core}; + SwitchableSetting use_unsafe_extended_memory_layout{ + linkage, false, "use_unsafe_extended_memory_layout", Category::Core}; // Cpu - SwitchableSetting cpu_accuracy{CPUAccuracy::Auto, CPUAccuracy::Auto, - CPUAccuracy::Paranoid, "cpu_accuracy"}; + SwitchableSetting cpu_accuracy{linkage, CPUAccuracy::Auto, + CPUAccuracy::Auto, CPUAccuracy::Paranoid, + "cpu_accuracy", Category::Cpu}; // TODO: remove cpu_accuracy_first_time, migration setting added 8 July 2021 - Setting cpu_accuracy_first_time{true, "cpu_accuracy_first_time"}; - Setting cpu_debug_mode{false, "cpu_debug_mode"}; + Setting cpu_accuracy_first_time{linkage, true, "cpu_accuracy_first_time", Category::Cpu}; + Setting cpu_debug_mode{linkage, false, "cpu_debug_mode", Category::Cpu}; - Setting cpuopt_page_tables{true, "cpuopt_page_tables"}; - Setting cpuopt_block_linking{true, "cpuopt_block_linking"}; - Setting cpuopt_return_stack_buffer{true, "cpuopt_return_stack_buffer"}; - Setting cpuopt_fast_dispatcher{true, "cpuopt_fast_dispatcher"}; - Setting cpuopt_context_elimination{true, "cpuopt_context_elimination"}; - Setting cpuopt_const_prop{true, "cpuopt_const_prop"}; - Setting cpuopt_misc_ir{true, "cpuopt_misc_ir"}; - Setting cpuopt_reduce_misalign_checks{true, "cpuopt_reduce_misalign_checks"}; - Setting cpuopt_fastmem{true, "cpuopt_fastmem"}; - Setting cpuopt_fastmem_exclusives{true, "cpuopt_fastmem_exclusives"}; - Setting cpuopt_recompile_exclusives{true, "cpuopt_recompile_exclusives"}; - Setting cpuopt_ignore_memory_aborts{true, "cpuopt_ignore_memory_aborts"}; + Setting cpuopt_page_tables{linkage, true, "cpuopt_page_tables", Category::Cpu}; + Setting cpuopt_block_linking{linkage, true, "cpuopt_block_linking", Category::Cpu}; + Setting cpuopt_return_stack_buffer{linkage, true, "cpuopt_return_stack_buffer", + Category::Cpu}; + Setting cpuopt_fast_dispatcher{linkage, true, "cpuopt_fast_dispatcher", Category::Cpu}; + Setting cpuopt_context_elimination{linkage, true, "cpuopt_context_elimination", + Category::Cpu}; + Setting cpuopt_const_prop{linkage, true, "cpuopt_const_prop", Category::Cpu}; + Setting cpuopt_misc_ir{linkage, true, "cpuopt_misc_ir", Category::Cpu}; + Setting cpuopt_reduce_misalign_checks{linkage, true, "cpuopt_reduce_misalign_checks", + Category::Cpu}; + Setting cpuopt_fastmem{linkage, true, "cpuopt_fastmem", Category::Cpu}; + Setting cpuopt_fastmem_exclusives{linkage, true, "cpuopt_fastmem_exclusives", + Category::Cpu}; + Setting cpuopt_recompile_exclusives{linkage, true, "cpuopt_recompile_exclusives", + Category::Cpu}; + Setting cpuopt_ignore_memory_aborts{linkage, true, "cpuopt_ignore_memory_aborts", + Category::Cpu}; - SwitchableSetting cpuopt_unsafe_unfuse_fma{true, "cpuopt_unsafe_unfuse_fma"}; - SwitchableSetting cpuopt_unsafe_reduce_fp_error{true, "cpuopt_unsafe_reduce_fp_error"}; + SwitchableSetting cpuopt_unsafe_unfuse_fma{linkage, true, "cpuopt_unsafe_unfuse_fma", + Category::Cpu}; + SwitchableSetting cpuopt_unsafe_reduce_fp_error{ + linkage, true, "cpuopt_unsafe_reduce_fp_error", Category::Cpu}; SwitchableSetting cpuopt_unsafe_ignore_standard_fpcr{ - true, "cpuopt_unsafe_ignore_standard_fpcr"}; - SwitchableSetting cpuopt_unsafe_inaccurate_nan{true, "cpuopt_unsafe_inaccurate_nan"}; - SwitchableSetting cpuopt_unsafe_fastmem_check{true, "cpuopt_unsafe_fastmem_check"}; + linkage, true, "cpuopt_unsafe_ignore_standard_fpcr", Category::Cpu}; + SwitchableSetting cpuopt_unsafe_inaccurate_nan{ + linkage, true, "cpuopt_unsafe_inaccurate_nan", Category::Cpu}; + SwitchableSetting cpuopt_unsafe_fastmem_check{ + linkage, true, "cpuopt_unsafe_fastmem_check", Category::Cpu}; SwitchableSetting cpuopt_unsafe_ignore_global_monitor{ - true, "cpuopt_unsafe_ignore_global_monitor"}; + linkage, true, "cpuopt_unsafe_ignore_global_monitor", Category::Cpu}; // Renderer SwitchableSetting renderer_backend{ - RendererBackend::Vulkan, RendererBackend::OpenGL, RendererBackend::Null, "backend"}; - SwitchableSetting async_presentation{false, "async_presentation"}; - SwitchableSetting renderer_force_max_clock{false, "force_max_clock"}; - Setting renderer_debug{false, "debug"}; - Setting renderer_shader_feedback{false, "shader_feedback"}; - Setting enable_nsight_aftermath{false, "nsight_aftermath"}; - Setting disable_shader_loop_safety_checks{false, "disable_shader_loop_safety_checks"}; - SwitchableSetting vulkan_device{0, "vulkan_device"}; + linkage, RendererBackend::Vulkan, RendererBackend::OpenGL, RendererBackend::Null, + "backend", Category::Renderer}; + SwitchableSetting async_presentation{linkage, false, "async_presentation", + Category::AdvancedGraphics}; + SwitchableSetting renderer_force_max_clock{linkage, false, "force_max_clock", + Category::AdvancedGraphics}; + Setting renderer_debug{linkage, false, "debug", Category::Renderer}; + Setting renderer_shader_feedback{linkage, false, "shader_feedback", Category::Renderer}; + Setting enable_nsight_aftermath{linkage, false, "nsight_aftermath", Category::Renderer}; + Setting disable_shader_loop_safety_checks{ + linkage, false, "disable_shader_loop_safety_checks", Category::Renderer}; + SwitchableSetting vulkan_device{linkage, 0, "vulkan_device", Category::Renderer}; ResolutionScalingInfo resolution_info{}; - SwitchableSetting resolution_setup{ResolutionSetup::Res1X, "resolution_setup"}; - SwitchableSetting scaling_filter{ScalingFilter::Bilinear, "scaling_filter"}; - SwitchableSetting fsr_sharpening_slider{25, 0, 200, "fsr_sharpening_slider"}; - SwitchableSetting anti_aliasing{AntiAliasing::None, "anti_aliasing"}; + SwitchableSetting resolution_setup{linkage, ResolutionSetup::Res1X, + "resolution_setup", Category::Renderer}; + SwitchableSetting scaling_filter{linkage, ScalingFilter::Bilinear, + "scaling_filter", Category::Renderer}; + SwitchableSetting fsr_sharpening_slider{ + linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer}; + SwitchableSetting anti_aliasing{linkage, AntiAliasing::None, "anti_aliasing", + Category::Renderer}; // *nix platforms may have issues with the borderless windowed fullscreen mode. // Default to exclusive fullscreen on these platforms for now. - SwitchableSetting fullscreen_mode{ + SwitchableSetting fullscreen_mode{linkage, #ifdef _WIN32 - FullscreenMode::Borderless, + FullscreenMode::Borderless, #else - FullscreenMode::Exclusive, + FullscreenMode::Exclusive, #endif - FullscreenMode::Borderless, FullscreenMode::Exclusive, "fullscreen_mode"}; - SwitchableSetting aspect_ratio{0, 0, 4, "aspect_ratio"}; - SwitchableSetting max_anisotropy{0, 0, 5, "max_anisotropy"}; - SwitchableSetting use_speed_limit{true, "use_speed_limit"}; - SwitchableSetting speed_limit{100, 0, 9999, "speed_limit"}; - SwitchableSetting use_disk_shader_cache{true, "use_disk_shader_cache"}; - SwitchableSetting gpu_accuracy{GPUAccuracy::High, GPUAccuracy::Normal, - GPUAccuracy::Extreme, "gpu_accuracy"}; - SwitchableSetting use_asynchronous_gpu_emulation{true, "use_asynchronous_gpu_emulation"}; - SwitchableSetting nvdec_emulation{NvdecEmulation::GPU, "nvdec_emulation"}; - SwitchableSetting accelerate_astc{ - AstcDecodeMode::CPU, AstcDecodeMode::CPU, AstcDecodeMode::CPUAsynchronous, - "accelerate_astc"}; - Setting vsync_mode{VSyncMode::FIFO, VSyncMode::Immediate, - VSyncMode::FIFORelaxed, "use_vsync"}; - SwitchableSetting use_reactive_flushing{true, "use_reactive_flushing"}; - SwitchableSetting shader_backend{ShaderBackend::GLSL, ShaderBackend::GLSL, - ShaderBackend::SPIRV, "shader_backend"}; - SwitchableSetting use_asynchronous_shaders{false, "use_asynchronous_shaders"}; - SwitchableSetting use_fast_gpu_time{true, "use_fast_gpu_time"}; - SwitchableSetting use_vulkan_driver_pipeline_cache{true, - "use_vulkan_driver_pipeline_cache"}; - SwitchableSetting enable_compute_pipelines{false, "enable_compute_pipelines"}; - SwitchableSetting astc_recompression{ - AstcRecompression::Uncompressed, AstcRecompression::Uncompressed, AstcRecompression::Bc3, - "astc_recompression"}; - SwitchableSetting use_video_framerate{false, "use_video_framerate"}; - SwitchableSetting barrier_feedback_loops{true, "barrier_feedback_loops"}; + FullscreenMode::Borderless, + FullscreenMode::Exclusive, + "fullscreen_mode", + Category::Renderer}; + SwitchableSetting aspect_ratio{linkage, 0, 0, 4, "aspect_ratio", Category::Renderer}; + SwitchableSetting max_anisotropy{ + linkage, 0, 0, 5, "max_anisotropy", Category::AdvancedGraphics}; + SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", + Category::Renderer}; + SwitchableSetting speed_limit{linkage, 100, 0, + 9999, "speed_limit", Category::Renderer}; + SwitchableSetting use_disk_shader_cache{linkage, true, "use_disk_shader_cache", + Category::Renderer}; + SwitchableSetting gpu_accuracy{ + linkage, GPUAccuracy::High, GPUAccuracy::Normal, GPUAccuracy::Extreme, + "gpu_accuracy", Category::AdvancedGraphics}; + SwitchableSetting use_asynchronous_gpu_emulation{ + linkage, true, "use_asynchronous_gpu_emulation", Category::Renderer}; + SwitchableSetting nvdec_emulation{linkage, NvdecEmulation::GPU, + "nvdec_emulation", Category::Renderer}; + SwitchableSetting accelerate_astc{linkage, + AstcDecodeMode::CPU, + AstcDecodeMode::CPU, + AstcDecodeMode::CPUAsynchronous, + "accelerate_astc", + Category::Renderer}; + Setting vsync_mode{ + linkage, VSyncMode::FIFO, VSyncMode::Immediate, VSyncMode::FIFORelaxed, + "use_vsync", Category::Renderer}; + SwitchableSetting use_reactive_flushing{linkage, true, "use_reactive_flushing", + Category::Renderer}; + SwitchableSetting shader_backend{ + linkage, ShaderBackend::GLSL, ShaderBackend::GLSL, ShaderBackend::SPIRV, + "shader_backend", Category::Renderer}; + SwitchableSetting use_asynchronous_shaders{linkage, false, "use_asynchronous_shaders", + Category::Renderer}; + SwitchableSetting use_fast_gpu_time{linkage, true, "use_fast_gpu_time", + Category::AdvancedGraphics}; + SwitchableSetting use_vulkan_driver_pipeline_cache{ + linkage, true, "use_vulkan_driver_pipeline_cache", Category::AdvancedGraphics}; + SwitchableSetting enable_compute_pipelines{linkage, false, "enable_compute_pipelines", + Category::AdvancedGraphics}; + SwitchableSetting astc_recompression{linkage, + AstcRecompression::Uncompressed, + AstcRecompression::Uncompressed, + AstcRecompression::Bc3, + "astc_recompression", + Category::AdvancedGraphics}; + SwitchableSetting use_video_framerate{linkage, false, "use_video_framerate", + Category::AdvancedGraphics}; + SwitchableSetting barrier_feedback_loops{linkage, true, "barrier_feedback_loops", + Category::AdvancedGraphics}; - SwitchableSetting bg_red{0, "bg_red"}; - SwitchableSetting bg_green{0, "bg_green"}; - SwitchableSetting bg_blue{0, "bg_blue"}; + SwitchableSetting bg_red{linkage, 0, "bg_red", Category::Renderer}; + SwitchableSetting bg_green{linkage, 0, "bg_green", Category::Renderer}; + SwitchableSetting bg_blue{linkage, 0, "bg_blue", Category::Renderer}; // System - SwitchableSetting rng_seed_enabled{false, "rng_seed_enabled"}; - SwitchableSetting rng_seed{0, "rng_seed"}; - Setting device_name{"Yuzu", "device_name"}; + SwitchableSetting rng_seed_enabled{linkage, false, "rng_seed_enabled", Category::System}; + SwitchableSetting rng_seed{linkage, 0, "rng_seed", Category::System}; + Setting device_name{linkage, "Yuzu", "device_name", Category::System}; // Measured in seconds since epoch - SwitchableSetting custom_rtc_enabled{false, "custom_rtc_enabled"}; - SwitchableSetting custom_rtc{0, "custom_rtc"}; + Setting custom_rtc_enabled{linkage, false, "custom_rtc_enabled", Category::System}; + Setting custom_rtc{linkage, 0, "custom_rtc", Category::System}; // Set on game boot, reset on stop. Seconds difference between current time and `custom_rtc` s64 custom_rtc_differential; - Setting current_user{0, "current_user"}; - SwitchableSetting language_index{1, 0, 17, "language_index"}; - SwitchableSetting region_index{1, 0, 6, "region_index"}; - SwitchableSetting time_zone_index{0, 0, 45, "time_zone_index"}; - SwitchableSetting sound_index{1, 0, 2, "sound_index"}; + Setting current_user{linkage, 0, "current_user", Category::System}; + SwitchableSetting language_index{linkage, 1, 0, 17, "language_index", + Category::System}; + SwitchableSetting region_index{linkage, 1, 0, 6, "region_index", Category::System}; + SwitchableSetting time_zone_index{linkage, 0, 0, 45, "time_zone_index", + Category::System}; + SwitchableSetting sound_index{linkage, 1, 0, 2, "sound_index", Category::System}; + + SwitchableSetting use_docked_mode{linkage, true, "use_docked_mode", Category::System}; // Controls InputSetting> players; - SwitchableSetting use_docked_mode{true, "use_docked_mode"}; + Setting + enable_raw_input{linkage, false, "enable_raw_input", Category::Controls}; + Setting controller_navigation{linkage, true, "controller_navigation", Category::Controls}; + Setting enable_joycon_driver{linkage, true, "enable_joycon_driver", Category::Controls}; + Setting enable_procon_driver{linkage, false, "enable_procon_driver", Category::Controls}; - Setting enable_raw_input{false, "enable_raw_input"}; - Setting controller_navigation{true, "controller_navigation"}; - Setting enable_joycon_driver{true, "enable_joycon_driver"}; - Setting enable_procon_driver{false, "enable_procon_driver"}; + SwitchableSetting vibration_enabled{linkage, true, "vibration_enabled", + Category::Controls}; + SwitchableSetting enable_accurate_vibrations{linkage, false, "enable_accurate_vibrations", + Category::Controls}; - SwitchableSetting vibration_enabled{true, "vibration_enabled"}; - SwitchableSetting enable_accurate_vibrations{false, "enable_accurate_vibrations"}; + SwitchableSetting motion_enabled{linkage, true, "motion_enabled", Category::Controls}; + Setting udp_input_servers{linkage, "127.0.0.1:26760", "udp_input_servers", + Category::Controls}; + Setting enable_udp_controller{linkage, false, "enable_udp_controller", + Category::Controls}; - SwitchableSetting motion_enabled{true, "motion_enabled"}; - Setting udp_input_servers{"127.0.0.1:26760", "udp_input_servers"}; - Setting enable_udp_controller{false, "enable_udp_controller"}; + Setting pause_tas_on_load{linkage, true, "pause_tas_on_load", Category::Controls}; + Setting tas_enable{linkage, false, "tas_enable", Category::Controls}; + Setting tas_loop{linkage, false, "tas_loop", Category::Controls}; - Setting pause_tas_on_load{true, "pause_tas_on_load"}; - Setting tas_enable{false, "tas_enable"}; - Setting tas_loop{false, "tas_loop"}; + Setting mouse_panning{linkage, false, "mouse_panning", Category::Controls}; + Setting mouse_panning_sensitivity{ + linkage, 50, 1, 100, "mouse_panning_sensitivity", Category::Controls}; + Setting mouse_enabled{linkage, false, "mouse_enabled", Category::Controls}; - Setting mouse_panning{false, "mouse_panning"}; - Setting mouse_panning_x_sensitivity{50, 1, 100, "mouse_panning_x_sensitivity"}; - Setting mouse_panning_y_sensitivity{50, 1, 100, "mouse_panning_y_sensitivity"}; - Setting mouse_panning_deadzone_counterweight{20, 0, 100, - "mouse_panning_deadzone_counterweight"}; - Setting mouse_panning_decay_strength{18, 0, 100, "mouse_panning_decay_strength"}; - Setting mouse_panning_min_decay{6, 0, 100, "mouse_panning_min_decay"}; + Setting mouse_panning_x_sensitivity{ + linkage, 50, 1, 100, "mouse_panning_x_sensitivity", Category::Controls}; + Setting mouse_panning_y_sensitivity{ + linkage, 50, 1, 100, "mouse_panning_y_sensitivity", Category::Controls}; + Setting mouse_panning_deadzone_counterweight{ + linkage, 20, 0, 100, "mouse_panning_deadzone_counterweight", Category::Controls}; + Setting mouse_panning_decay_strength{ + linkage, 18, 0, 100, "mouse_panning_decay_strength", Category::Controls}; + Setting mouse_panning_min_decay{ + linkage, 6, 0, 100, "mouse_panning_min_decay", Category::Controls}; - Setting mouse_enabled{false, "mouse_enabled"}; - Setting emulate_analog_keyboard{false, "emulate_analog_keyboard"}; - Setting keyboard_enabled{false, "keyboard_enabled"}; + Setting emulate_analog_keyboard{linkage, false, "emulate_analog_keyboard", + Category::Controls}; + Setting keyboard_enabled{linkage, false, "keyboard_enabled", Category::Controls}; - Setting debug_pad_enabled{false, "debug_pad_enabled"}; + Setting debug_pad_enabled{linkage, false, "debug_pad_enabled", Category::Controls}; ButtonsRaw debug_pad_buttons; AnalogsRaw debug_pad_analogs; TouchscreenInput touchscreen; - Setting touch_device{"min_x:100,min_y:50,max_x:1800,max_y:850", "touch_device"}; - Setting touch_from_button_map_index{0, "touch_from_button_map"}; + Setting touch_device{linkage, "min_x:100,min_y:50,max_x:1800,max_y:850", + "touch_device", Category::Controls}; + Setting touch_from_button_map_index{linkage, 0, "touch_from_button_map", + Category::Controls}; std::vector touch_from_button_maps; - Setting enable_ring_controller{true, "enable_ring_controller"}; + Setting enable_ring_controller{linkage, true, "enable_ring_controller", + Category::Controls}; RingconRaw ringcon_analogs; - Setting enable_ir_sensor{false, "enable_ir_sensor"}; - Setting ir_sensor_device{"auto", "ir_sensor_device"}; + Setting enable_ir_sensor{linkage, false, "enable_ir_sensor", Category::Controls}; + Setting ir_sensor_device{linkage, "auto", "ir_sensor_device", Category::Controls}; - Setting random_amiibo_id{false, "random_amiibo_id"}; + Setting random_amiibo_id{linkage, false, "random_amiibo_id", Category::Controls}; // Data Storage - Setting use_virtual_sd{true, "use_virtual_sd"}; - Setting gamecard_inserted{false, "gamecard_inserted"}; - Setting gamecard_current_game{false, "gamecard_current_game"}; - Setting gamecard_path{std::string(), "gamecard_path"}; + Setting use_virtual_sd{linkage, true, "use_virtual_sd", Category::DataStorage}; + Setting gamecard_inserted{linkage, false, "gamecard_inserted", Category::DataStorage}; + Setting gamecard_current_game{linkage, false, "gamecard_current_game", + Category::DataStorage}; + Setting gamecard_path{linkage, std::string(), "gamecard_path", + Category::DataStorage}; // Debugging bool record_frame_times; - Setting use_gdbstub{false, "use_gdbstub"}; - Setting gdbstub_port{6543, "gdbstub_port"}; - Setting program_args{std::string(), "program_args"}; - Setting dump_exefs{false, "dump_exefs"}; - Setting dump_nso{false, "dump_nso"}; - Setting dump_shaders{false, "dump_shaders"}; - Setting dump_macros{false, "dump_macros"}; - Setting enable_fs_access_log{false, "enable_fs_access_log"}; - Setting reporting_services{false, "reporting_services"}; - Setting quest_flag{false, "quest_flag"}; - Setting disable_macro_jit{false, "disable_macro_jit"}; - Setting disable_macro_hle{false, "disable_macro_hle"}; - Setting extended_logging{false, "extended_logging"}; - Setting use_debug_asserts{false, "use_debug_asserts"}; - Setting use_auto_stub{false, "use_auto_stub"}; - Setting enable_all_controllers{false, "enable_all_controllers"}; - Setting create_crash_dumps{false, "create_crash_dumps"}; - Setting perform_vulkan_check{true, "perform_vulkan_check"}; + Setting use_gdbstub{linkage, false, "use_gdbstub", Category::Debugging}; + Setting gdbstub_port{linkage, 6543, "gdbstub_port", Category::Debugging}; + Setting program_args{linkage, std::string(), "program_args", Category::Debugging}; + Setting dump_exefs{linkage, false, "dump_exefs", Category::Debugging}; + Setting dump_nso{linkage, false, "dump_nso", Category::Debugging}; + Setting dump_shaders{linkage, false, "dump_shaders", Category::Debugging}; + Setting dump_macros{linkage, false, "dump_macros", Category::Debugging}; + Setting enable_fs_access_log{linkage, false, "enable_fs_access_log", Category::Debugging}; + Setting reporting_services{linkage, false, "reporting_services", + Category::Debugging}; + Setting quest_flag{linkage, false, "quest_flag", Category::Debugging}; + Setting disable_macro_jit{linkage, false, "disable_macro_jit", Category::Debugging}; + Setting disable_macro_hle{linkage, false, "disable_macro_hle", Category::Debugging}; + Setting extended_logging{linkage, false, "extended_logging", + Category::Debugging}; + Setting use_debug_asserts{linkage, false, "use_debug_asserts", Category::Debugging}; + Setting use_auto_stub{linkage, false, "use_auto_stub", Category::Debugging}; + Setting enable_all_controllers{linkage, false, "enable_all_controllers", + Category::Debugging}; + Setting create_crash_dumps{linkage, false, "create_crash_dumps", Category::Debugging}; + Setting perform_vulkan_check{linkage, true, "perform_vulkan_check", Category::Debugging}; // Miscellaneous - Setting log_filter{"*:Info", "log_filter"}; - Setting use_dev_keys{false, "use_dev_keys"}; + Setting log_filter{linkage, "*:Info", "log_filter", Category::Miscellaneous}; + Setting use_dev_keys{linkage, false, "use_dev_keys", Category::Miscellaneous}; // Network - Setting network_interface{std::string(), "network_interface"}; + Setting network_interface{linkage, std::string(), "network_interface", + Category::Network}; // WebService - Setting enable_telemetry{true, "enable_telemetry"}; - Setting web_api_url{"https://api.yuzu-emu.org", "web_api_url"}; - Setting yuzu_username{std::string(), "yuzu_username"}; - Setting yuzu_token{std::string(), "yuzu_token"}; + Setting enable_telemetry{linkage, true, "enable_telemetry", Category::WebService}; + Setting web_api_url{linkage, "https://api.yuzu-emu.org", "web_api_url", + Category::WebService}; + Setting yuzu_username{linkage, std::string(), "yuzu_username", + Category::WebService}; + Setting yuzu_token{linkage, std::string(), "yuzu_token", Category::WebService}; // Add-Ons std::map> disabled_addons; diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 786c1222f..f274fe4ea 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -1,6 +1,7 @@ // SPDX-FileCopyrightText: 2014 Citra Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#include #include #include #include @@ -16,8 +17,11 @@ namespace FS = Common::FS; -Config::Config(const std::string& config_name, ConfigType config_type) : type(config_type) { - global = config_type == ConfigType::GlobalConfig; +Config::Config(const std::string& config_name, ConfigType config_type) + : type(config_type), global{config_type == ConfigType::GlobalConfig} { + + settings_map = Settings::values.linkage.by_category; + settings_map.merge(UISettings::values.linkage.by_category); Initialize(config_name); } @@ -351,15 +355,9 @@ void Config::ReadPlayerValue(std::size_t player_index) { player_motions = default_param; } } - - if (player_index == 0) { - ReadMousePanningValues(); - } } void Config::ReadDebugValues() { - ReadBasicSetting(Settings::values.debug_pad_enabled); - for (int i = 0; i < Settings::NativeButton::NumButtons; ++i) { const std::string default_param = InputCommon::GenerateKeyboardParam(default_buttons[i]); auto& debug_pad_buttons = Settings::values.debug_pad_buttons[i]; @@ -393,14 +391,6 @@ void Config::ReadDebugValues() { } } -void Config::ReadKeyboardValues() { - ReadBasicSetting(Settings::values.keyboard_enabled); -} - -void Config::ReadMouseValues() { - ReadBasicSetting(Settings::values.mouse_enabled); -} - void Config::ReadTouchscreenValues() { Settings::values.touchscreen.enabled = ReadSetting(QStringLiteral("touchscreen_enabled"), true).toBool(); @@ -414,9 +404,6 @@ void Config::ReadTouchscreenValues() { } void Config::ReadHidbusValues() { - Settings::values.enable_ring_controller = - ReadSetting(QStringLiteral("enable_ring_controller"), true).toBool(); - const std::string default_param = InputCommon::GenerateAnalogParamFromKeys( 0, 0, default_ringcon_analogs[0], default_ringcon_analogs[1], 0, 0.05f); auto& ringcon_analogs = Settings::values.ringcon_analogs; @@ -430,20 +417,10 @@ void Config::ReadHidbusValues() { } } -void Config::ReadIrCameraValues() { - ReadBasicSetting(Settings::values.enable_ir_sensor); - ReadBasicSetting(Settings::values.ir_sensor_device); -} - void Config::ReadAudioValues() { qt_config->beginGroup(QStringLiteral("Audio")); - if (global) { - ReadBasicSetting(Settings::values.sink_id); - ReadBasicSetting(Settings::values.audio_output_device_id); - ReadBasicSetting(Settings::values.audio_input_device_id); - } - ReadGlobalSetting(Settings::values.volume); + ReadCategory(Settings::Category::Audio); qt_config->endGroup(); } @@ -451,11 +428,12 @@ void Config::ReadAudioValues() { void Config::ReadControlValues() { qt_config->beginGroup(QStringLiteral("Controls")); + ReadCategory(Settings::Category::Controls); + Settings::values.players.SetGlobal(!IsCustomConfig()); for (std::size_t p = 0; p < Settings::values.players.GetValue().size(); ++p) { ReadPlayerValue(p); } - ReadGlobalSetting(Settings::values.use_docked_mode); // Disable docked mode if handheld is selected const auto controller_type = Settings::values.players.GetValue()[0].controller_type; @@ -464,50 +442,18 @@ void Config::ReadControlValues() { Settings::values.use_docked_mode.SetValue(false); } - ReadGlobalSetting(Settings::values.vibration_enabled); - ReadGlobalSetting(Settings::values.enable_accurate_vibrations); - ReadGlobalSetting(Settings::values.motion_enabled); if (IsCustomConfig()) { qt_config->endGroup(); return; } ReadDebugValues(); - ReadKeyboardValues(); - ReadMouseValues(); ReadTouchscreenValues(); - ReadMousePanningValues(); ReadMotionTouchValues(); ReadHidbusValues(); - ReadIrCameraValues(); - -#ifdef _WIN32 - ReadBasicSetting(Settings::values.enable_raw_input); -#else - Settings::values.enable_raw_input = false; -#endif - ReadBasicSetting(Settings::values.emulate_analog_keyboard); - ReadBasicSetting(Settings::values.enable_joycon_driver); - ReadBasicSetting(Settings::values.enable_procon_driver); - ReadBasicSetting(Settings::values.random_amiibo_id); - - ReadBasicSetting(Settings::values.tas_enable); - ReadBasicSetting(Settings::values.tas_loop); - ReadBasicSetting(Settings::values.pause_tas_on_load); - - ReadBasicSetting(Settings::values.controller_navigation); qt_config->endGroup(); } -void Config::ReadMousePanningValues() { - ReadBasicSetting(Settings::values.mouse_panning); - ReadBasicSetting(Settings::values.mouse_panning_x_sensitivity); - ReadBasicSetting(Settings::values.mouse_panning_y_sensitivity); - ReadBasicSetting(Settings::values.mouse_panning_deadzone_counterweight); - ReadBasicSetting(Settings::values.mouse_panning_decay_strength); - ReadBasicSetting(Settings::values.mouse_panning_min_decay); -} - void Config::ReadMotionTouchValues() { int num_touch_from_button_maps = qt_config->beginReadArray(QStringLiteral("touch_from_button_maps")); @@ -541,19 +487,14 @@ void Config::ReadMotionTouchValues() { } qt_config->endArray(); - ReadBasicSetting(Settings::values.touch_device); - ReadBasicSetting(Settings::values.touch_from_button_map_index); Settings::values.touch_from_button_map_index = std::clamp( Settings::values.touch_from_button_map_index.GetValue(), 0, num_touch_from_button_maps - 1); - ReadBasicSetting(Settings::values.udp_input_servers); - ReadBasicSetting(Settings::values.enable_udp_controller); } void Config::ReadCoreValues() { qt_config->beginGroup(QStringLiteral("Core")); - ReadGlobalSetting(Settings::values.use_multi_core); - ReadGlobalSetting(Settings::values.use_unsafe_extended_memory_layout); + ReadCategory(Settings::Category::Core); qt_config->endGroup(); } @@ -561,7 +502,6 @@ void Config::ReadCoreValues() { void Config::ReadDataStorageValues() { qt_config->beginGroup(QStringLiteral("Data Storage")); - ReadBasicSetting(Settings::values.use_virtual_sd); FS::SetYuzuPath( FS::YuzuPath::NANDDir, qt_config @@ -597,9 +537,7 @@ void Config::ReadDataStorageValues() { .toString() .toStdString()); - ReadBasicSetting(Settings::values.gamecard_inserted); - ReadBasicSetting(Settings::values.gamecard_current_game); - ReadBasicSetting(Settings::values.gamecard_path); + ReadCategory(Settings::Category::DataStorage); qt_config->endGroup(); } @@ -611,29 +549,16 @@ void Config::ReadDebuggingValues() { Settings::values.record_frame_times = qt_config->value(QStringLiteral("record_frame_times"), false).toBool(); - ReadBasicSetting(Settings::values.use_gdbstub); - ReadBasicSetting(Settings::values.gdbstub_port); - ReadBasicSetting(Settings::values.program_args); - ReadBasicSetting(Settings::values.dump_exefs); - ReadBasicSetting(Settings::values.dump_nso); - ReadBasicSetting(Settings::values.enable_fs_access_log); - ReadBasicSetting(Settings::values.reporting_services); - ReadBasicSetting(Settings::values.quest_flag); - ReadBasicSetting(Settings::values.disable_macro_jit); - ReadBasicSetting(Settings::values.disable_macro_hle); - ReadBasicSetting(Settings::values.extended_logging); - ReadBasicSetting(Settings::values.use_debug_asserts); - ReadBasicSetting(Settings::values.use_auto_stub); - ReadBasicSetting(Settings::values.enable_all_controllers); - ReadBasicSetting(Settings::values.create_crash_dumps); - ReadBasicSetting(Settings::values.perform_vulkan_check); + ReadCategory(Settings::Category::Debugging); qt_config->endGroup(); } void Config::ReadServiceValues() { qt_config->beginGroup(QStringLiteral("Services")); - ReadBasicSetting(Settings::values.network_interface); + + ReadCategory(Settings::Category::Services); + qt_config->endGroup(); } @@ -659,8 +584,7 @@ void Config::ReadDisabledAddOnValues() { void Config::ReadMiscellaneousValues() { qt_config->beginGroup(QStringLiteral("Miscellaneous")); - ReadBasicSetting(Settings::values.log_filter); - ReadBasicSetting(Settings::values.use_dev_keys); + ReadCategory(Settings::Category::Miscellaneous); qt_config->endGroup(); } @@ -710,35 +634,11 @@ void Config::ReadPathValues() { void Config::ReadCpuValues() { qt_config->beginGroup(QStringLiteral("Cpu")); - ReadBasicSetting(Settings::values.cpu_accuracy_first_time); + ReadCategory(Settings::Category::Cpu); + if (Settings::values.cpu_accuracy_first_time) { Settings::values.cpu_accuracy.SetValue(Settings::values.cpu_accuracy.GetDefault()); Settings::values.cpu_accuracy_first_time.SetValue(false); - } else { - ReadGlobalSetting(Settings::values.cpu_accuracy); - } - - ReadGlobalSetting(Settings::values.cpuopt_unsafe_unfuse_fma); - ReadGlobalSetting(Settings::values.cpuopt_unsafe_reduce_fp_error); - ReadGlobalSetting(Settings::values.cpuopt_unsafe_ignore_standard_fpcr); - ReadGlobalSetting(Settings::values.cpuopt_unsafe_inaccurate_nan); - ReadGlobalSetting(Settings::values.cpuopt_unsafe_fastmem_check); - ReadGlobalSetting(Settings::values.cpuopt_unsafe_ignore_global_monitor); - - if (global) { - ReadBasicSetting(Settings::values.cpu_debug_mode); - ReadBasicSetting(Settings::values.cpuopt_page_tables); - ReadBasicSetting(Settings::values.cpuopt_block_linking); - ReadBasicSetting(Settings::values.cpuopt_return_stack_buffer); - ReadBasicSetting(Settings::values.cpuopt_fast_dispatcher); - ReadBasicSetting(Settings::values.cpuopt_context_elimination); - ReadBasicSetting(Settings::values.cpuopt_const_prop); - ReadBasicSetting(Settings::values.cpuopt_misc_ir); - ReadBasicSetting(Settings::values.cpuopt_reduce_misalign_checks); - ReadBasicSetting(Settings::values.cpuopt_fastmem); - ReadBasicSetting(Settings::values.cpuopt_fastmem_exclusives); - ReadBasicSetting(Settings::values.cpuopt_recompile_exclusives); - ReadBasicSetting(Settings::values.cpuopt_ignore_memory_aborts); } qt_config->endGroup(); @@ -747,45 +647,8 @@ void Config::ReadCpuValues() { void Config::ReadRendererValues() { qt_config->beginGroup(QStringLiteral("Renderer")); - ReadGlobalSetting(Settings::values.renderer_backend); - ReadGlobalSetting(Settings::values.async_presentation); - ReadGlobalSetting(Settings::values.renderer_force_max_clock); - ReadGlobalSetting(Settings::values.vulkan_device); - ReadGlobalSetting(Settings::values.fullscreen_mode); - ReadGlobalSetting(Settings::values.aspect_ratio); - ReadGlobalSetting(Settings::values.resolution_setup); - ReadGlobalSetting(Settings::values.scaling_filter); - ReadGlobalSetting(Settings::values.fsr_sharpening_slider); - ReadGlobalSetting(Settings::values.anti_aliasing); - ReadGlobalSetting(Settings::values.max_anisotropy); - ReadGlobalSetting(Settings::values.speed_limit); - ReadGlobalSetting(Settings::values.use_disk_shader_cache); - ReadGlobalSetting(Settings::values.gpu_accuracy); - ReadGlobalSetting(Settings::values.use_asynchronous_gpu_emulation); - ReadGlobalSetting(Settings::values.nvdec_emulation); - ReadGlobalSetting(Settings::values.accelerate_astc); - ReadGlobalSetting(Settings::values.astc_recompression); - ReadGlobalSetting(Settings::values.use_reactive_flushing); - ReadGlobalSetting(Settings::values.use_asynchronous_shaders); - ReadGlobalSetting(Settings::values.use_fast_gpu_time); - ReadGlobalSetting(Settings::values.use_vulkan_driver_pipeline_cache); - ReadGlobalSetting(Settings::values.enable_compute_pipelines); - ReadGlobalSetting(Settings::values.use_video_framerate); - ReadGlobalSetting(Settings::values.barrier_feedback_loops); - ReadGlobalSetting(Settings::values.bg_red); - ReadGlobalSetting(Settings::values.bg_green); - ReadGlobalSetting(Settings::values.bg_blue); - - if (global) { - Settings::values.vsync_mode.SetValue(static_cast( - ReadSetting(QString::fromStdString(Settings::values.vsync_mode.GetLabel()), - static_cast(Settings::values.vsync_mode.GetDefault())) - .value())); - ReadBasicSetting(Settings::values.renderer_debug); - ReadBasicSetting(Settings::values.renderer_shader_feedback); - ReadBasicSetting(Settings::values.enable_nsight_aftermath); - ReadBasicSetting(Settings::values.disable_shader_loop_safety_checks); - } + ReadCategory(Settings::Category::Renderer); + ReadCategory(Settings::Category::AdvancedGraphics); qt_config->endGroup(); } @@ -832,41 +695,7 @@ void Config::ReadShortcutValues() { void Config::ReadSystemValues() { qt_config->beginGroup(QStringLiteral("System")); - ReadGlobalSetting(Settings::values.language_index); - - ReadGlobalSetting(Settings::values.region_index); - - ReadGlobalSetting(Settings::values.time_zone_index); - - bool rng_seed_enabled; - ReadSettingGlobal(rng_seed_enabled, QStringLiteral("rng_seed_enabled"), false); - bool rng_seed_global = - global || qt_config->value(QStringLiteral("rng_seed/use_global"), true).toBool(); - Settings::values.rng_seed.SetGlobal(rng_seed_global); - if (global || !rng_seed_global) { - if (rng_seed_enabled) { - Settings::values.rng_seed.SetValue(ReadSetting(QStringLiteral("rng_seed"), 0).toUInt()); - } else { - Settings::values.rng_seed.SetValue(std::nullopt); - } - } - - if (global) { - ReadBasicSetting(Settings::values.current_user); - Settings::values.current_user = std::clamp(Settings::values.current_user.GetValue(), 0, - Service::Account::MAX_USERS - 1); - - const auto custom_rtc_enabled = - ReadSetting(QStringLiteral("custom_rtc_enabled"), false).toBool(); - if (custom_rtc_enabled) { - Settings::values.custom_rtc = ReadSetting(QStringLiteral("custom_rtc"), 0).toLongLong(); - } else { - Settings::values.custom_rtc = std::nullopt; - } - ReadBasicSetting(Settings::values.device_name); - } - - ReadGlobalSetting(Settings::values.sound_index); + ReadCategory(Settings::Category::System); qt_config->endGroup(); } @@ -879,8 +708,6 @@ void Config::ReadUIValues() { QStringLiteral("theme"), QString::fromUtf8(UISettings::themes[static_cast(default_theme)].second)) .toString(); - ReadBasicSetting(UISettings::values.enable_discord_presence); - ReadBasicSetting(UISettings::values.select_user_on_boot); ReadUIGamelistValues(); ReadUILayoutValues(); @@ -889,20 +716,7 @@ void Config::ReadUIValues() { ReadShortcutValues(); ReadMultiplayerValues(); - ReadBasicSetting(UISettings::values.single_window_mode); - ReadBasicSetting(UISettings::values.fullscreen); - ReadBasicSetting(UISettings::values.display_titlebar); - ReadBasicSetting(UISettings::values.show_filter_bar); - ReadBasicSetting(UISettings::values.show_status_bar); - ReadBasicSetting(UISettings::values.confirm_before_closing); - ReadBasicSetting(UISettings::values.first_start); - ReadBasicSetting(UISettings::values.callout_flags); - ReadBasicSetting(UISettings::values.show_console); - ReadBasicSetting(UISettings::values.pause_when_in_background); - ReadBasicSetting(UISettings::values.mute_when_in_background); - ReadBasicSetting(UISettings::values.hide_mouse); - ReadBasicSetting(UISettings::values.controller_applet_disabled); - ReadBasicSetting(UISettings::values.disable_web_applet); + ReadCategory(Settings::Category::Ui); qt_config->endGroup(); } @@ -910,16 +724,8 @@ void Config::ReadUIValues() { void Config::ReadUIGamelistValues() { qt_config->beginGroup(QStringLiteral("UIGameList")); - ReadBasicSetting(UISettings::values.show_add_ons); - ReadBasicSetting(UISettings::values.show_compat); - ReadBasicSetting(UISettings::values.show_size); - ReadBasicSetting(UISettings::values.show_types); - ReadBasicSetting(UISettings::values.game_icon_size); - ReadBasicSetting(UISettings::values.folder_icon_size); - ReadBasicSetting(UISettings::values.row_1_text_id); - ReadBasicSetting(UISettings::values.row_2_text_id); - ReadBasicSetting(UISettings::values.cache_game_list); - ReadBasicSetting(UISettings::values.favorites_expanded); + ReadCategory(Settings::Category::UiGameList); + const int favorites_size = qt_config->beginReadArray(QStringLiteral("favorites")); for (int i = 0; i < favorites_size; i++) { qt_config->setArrayIndex(i); @@ -942,7 +748,8 @@ void Config::ReadUILayoutValues() { ReadSetting(QStringLiteral("gameListHeaderState")).toByteArray(); UISettings::values.microprofile_geometry = ReadSetting(QStringLiteral("microProfileDialogGeometry")).toByteArray(); - ReadBasicSetting(UISettings::values.microprofile_visible); + + ReadCategory(Settings::Category::UiLayout); qt_config->endGroup(); } @@ -950,10 +757,7 @@ void Config::ReadUILayoutValues() { void Config::ReadWebServiceValues() { qt_config->beginGroup(QStringLiteral("WebService")); - ReadBasicSetting(Settings::values.enable_telemetry); - ReadBasicSetting(Settings::values.web_api_url); - ReadBasicSetting(Settings::values.yuzu_username); - ReadBasicSetting(Settings::values.yuzu_token); + ReadCategory(Settings::Category::WebService); qt_config->endGroup(); } @@ -961,17 +765,7 @@ void Config::ReadWebServiceValues() { void Config::ReadMultiplayerValues() { qt_config->beginGroup(QStringLiteral("Multiplayer")); - ReadBasicSetting(UISettings::values.multiplayer_nickname); - ReadBasicSetting(UISettings::values.multiplayer_ip); - ReadBasicSetting(UISettings::values.multiplayer_port); - ReadBasicSetting(UISettings::values.multiplayer_room_nickname); - ReadBasicSetting(UISettings::values.multiplayer_room_name); - ReadBasicSetting(UISettings::values.multiplayer_room_port); - ReadBasicSetting(UISettings::values.multiplayer_host_type); - ReadBasicSetting(UISettings::values.multiplayer_port); - ReadBasicSetting(UISettings::values.multiplayer_max_player); - ReadBasicSetting(UISettings::values.multiplayer_game_id); - ReadBasicSetting(UISettings::values.multiplayer_room_description); + ReadCategory(Settings::Category::Multiplayer); // Read ban list back int size = qt_config->beginReadArray(QStringLiteral("username_ban_list")); @@ -1075,14 +869,9 @@ void Config::SavePlayerValue(std::size_t player_index) { QString::fromStdString(player.motions[i]), QString::fromStdString(default_param)); } - - if (player_index == 0) { - SaveMousePanningValues(); - } } void Config::SaveDebugValues() { - WriteBasicSetting(Settings::values.debug_pad_enabled); for (int i = 0; i < Settings::NativeButton::NumButtons; ++i) { const std::string default_param = InputCommon::GenerateKeyboardParam(default_buttons[i]); WriteSetting(QStringLiteral("debug_pad_") + @@ -1101,10 +890,6 @@ void Config::SaveDebugValues() { } } -void Config::SaveMouseValues() { - WriteBasicSetting(Settings::values.mouse_enabled); -} - void Config::SaveTouchscreenValues() { const auto& touchscreen = Settings::values.touchscreen; @@ -1115,21 +900,7 @@ void Config::SaveTouchscreenValues() { WriteSetting(QStringLiteral("touchscreen_diameter_y"), touchscreen.diameter_y, 15); } -void Config::SaveMousePanningValues() { - // Don't overwrite values.mouse_panning - WriteBasicSetting(Settings::values.mouse_panning_x_sensitivity); - WriteBasicSetting(Settings::values.mouse_panning_y_sensitivity); - WriteBasicSetting(Settings::values.mouse_panning_deadzone_counterweight); - WriteBasicSetting(Settings::values.mouse_panning_decay_strength); - WriteBasicSetting(Settings::values.mouse_panning_min_decay); -} - void Config::SaveMotionTouchValues() { - WriteBasicSetting(Settings::values.touch_device); - WriteBasicSetting(Settings::values.touch_from_button_map_index); - WriteBasicSetting(Settings::values.udp_input_servers); - WriteBasicSetting(Settings::values.enable_udp_controller); - qt_config->beginWriteArray(QStringLiteral("touch_from_button_maps")); for (std::size_t p = 0; p < Settings::values.touch_from_button_maps.size(); ++p) { qt_config->setArrayIndex(static_cast(p)); @@ -1150,8 +921,6 @@ void Config::SaveMotionTouchValues() { } void Config::SaveHidbusValues() { - WriteBasicSetting(Settings::values.enable_ring_controller); - const std::string default_param = InputCommon::GenerateAnalogParamFromKeys( 0, 0, default_ringcon_analogs[0], default_ringcon_analogs[1], 0, 0.05f); WriteSetting(QStringLiteral("ring_controller"), @@ -1159,11 +928,6 @@ void Config::SaveHidbusValues() { QString::fromStdString(default_param)); } -void Config::SaveIrCameraValues() { - WriteBasicSetting(Settings::values.enable_ir_sensor); - WriteBasicSetting(Settings::values.ir_sensor_device); -} - void Config::SaveValues() { if (global) { SaveDataStorageValues(); @@ -1180,18 +944,14 @@ void Config::SaveValues() { SaveRendererValues(); SaveAudioValues(); SaveSystemValues(); + qt_config->sync(); } void Config::SaveAudioValues() { qt_config->beginGroup(QStringLiteral("Audio")); - if (global) { - WriteBasicSetting(Settings::values.sink_id); - WriteBasicSetting(Settings::values.audio_output_device_id); - WriteBasicSetting(Settings::values.audio_input_device_id); - } - WriteGlobalSetting(Settings::values.volume); + WriteCategory(Settings::Category::Audio); qt_config->endGroup(); } @@ -1199,6 +959,8 @@ void Config::SaveAudioValues() { void Config::SaveControlValues() { qt_config->beginGroup(QStringLiteral("Controls")); + WriteCategory(Settings::Category::Controls); + Settings::values.players.SetGlobal(!IsCustomConfig()); for (std::size_t p = 0; p < Settings::values.players.GetValue().size(); ++p) { SavePlayerValue(p); @@ -1208,28 +970,9 @@ void Config::SaveControlValues() { return; } SaveDebugValues(); - SaveMouseValues(); SaveTouchscreenValues(); - SaveMousePanningValues(); SaveMotionTouchValues(); SaveHidbusValues(); - SaveIrCameraValues(); - - WriteGlobalSetting(Settings::values.use_docked_mode); - WriteGlobalSetting(Settings::values.vibration_enabled); - WriteGlobalSetting(Settings::values.enable_accurate_vibrations); - WriteGlobalSetting(Settings::values.motion_enabled); - WriteBasicSetting(Settings::values.enable_raw_input); - WriteBasicSetting(Settings::values.enable_joycon_driver); - WriteBasicSetting(Settings::values.enable_procon_driver); - WriteBasicSetting(Settings::values.random_amiibo_id); - WriteBasicSetting(Settings::values.keyboard_enabled); - WriteBasicSetting(Settings::values.emulate_analog_keyboard); - WriteBasicSetting(Settings::values.controller_navigation); - - WriteBasicSetting(Settings::values.tas_enable); - WriteBasicSetting(Settings::values.tas_loop); - WriteBasicSetting(Settings::values.pause_tas_on_load); qt_config->endGroup(); } @@ -1237,8 +980,7 @@ void Config::SaveControlValues() { void Config::SaveCoreValues() { qt_config->beginGroup(QStringLiteral("Core")); - WriteGlobalSetting(Settings::values.use_multi_core); - WriteGlobalSetting(Settings::values.use_unsafe_extended_memory_layout); + WriteCategory(Settings::Category::Core); qt_config->endGroup(); } @@ -1246,7 +988,6 @@ void Config::SaveCoreValues() { void Config::SaveDataStorageValues() { qt_config->beginGroup(QStringLiteral("Data Storage")); - WriteBasicSetting(Settings::values.use_virtual_sd); WriteSetting(QStringLiteral("nand_directory"), QString::fromStdString(FS::GetYuzuPathString(FS::YuzuPath::NANDDir)), QString::fromStdString(FS::GetYuzuPathString(FS::YuzuPath::NANDDir))); @@ -1263,9 +1004,7 @@ void Config::SaveDataStorageValues() { QString::fromStdString(FS::GetYuzuPathString(FS::YuzuPath::TASDir)), QString::fromStdString(FS::GetYuzuPathString(FS::YuzuPath::TASDir))); - WriteBasicSetting(Settings::values.gamecard_inserted); - WriteBasicSetting(Settings::values.gamecard_current_game); - WriteBasicSetting(Settings::values.gamecard_path); + WriteCategory(Settings::Category::DataStorage); qt_config->endGroup(); } @@ -1275,19 +1014,8 @@ void Config::SaveDebuggingValues() { // Intentionally not using the QT default setting as this is intended to be changed in the ini qt_config->setValue(QStringLiteral("record_frame_times"), Settings::values.record_frame_times); - WriteBasicSetting(Settings::values.use_gdbstub); - WriteBasicSetting(Settings::values.gdbstub_port); - WriteBasicSetting(Settings::values.program_args); - WriteBasicSetting(Settings::values.dump_exefs); - WriteBasicSetting(Settings::values.dump_nso); - WriteBasicSetting(Settings::values.enable_fs_access_log); - WriteBasicSetting(Settings::values.quest_flag); - WriteBasicSetting(Settings::values.use_debug_asserts); - WriteBasicSetting(Settings::values.disable_macro_jit); - WriteBasicSetting(Settings::values.disable_macro_hle); - WriteBasicSetting(Settings::values.enable_all_controllers); - WriteBasicSetting(Settings::values.create_crash_dumps); - WriteBasicSetting(Settings::values.perform_vulkan_check); + + WriteCategory(Settings::Category::Debugging); qt_config->endGroup(); } @@ -1295,7 +1023,7 @@ void Config::SaveDebuggingValues() { void Config::SaveNetworkValues() { qt_config->beginGroup(QStringLiteral("Services")); - WriteBasicSetting(Settings::values.network_interface); + WriteCategory(Settings::Category::Network); qt_config->endGroup(); } @@ -1322,8 +1050,7 @@ void Config::SaveDisabledAddOnValues() { void Config::SaveMiscellaneousValues() { qt_config->beginGroup(QStringLiteral("Miscellaneous")); - WriteBasicSetting(Settings::values.log_filter); - WriteBasicSetting(Settings::values.use_dev_keys); + WriteCategory(Settings::Category::Miscellaneous); qt_config->endGroup(); } @@ -1351,34 +1078,7 @@ void Config::SavePathValues() { void Config::SaveCpuValues() { qt_config->beginGroup(QStringLiteral("Cpu")); - WriteBasicSetting(Settings::values.cpu_accuracy_first_time); - WriteSetting(QStringLiteral("cpu_accuracy"), - static_cast(Settings::values.cpu_accuracy.GetValue(global)), - static_cast(Settings::values.cpu_accuracy.GetDefault()), - Settings::values.cpu_accuracy.UsingGlobal()); - - WriteGlobalSetting(Settings::values.cpuopt_unsafe_unfuse_fma); - WriteGlobalSetting(Settings::values.cpuopt_unsafe_reduce_fp_error); - WriteGlobalSetting(Settings::values.cpuopt_unsafe_ignore_standard_fpcr); - WriteGlobalSetting(Settings::values.cpuopt_unsafe_inaccurate_nan); - WriteGlobalSetting(Settings::values.cpuopt_unsafe_fastmem_check); - WriteGlobalSetting(Settings::values.cpuopt_unsafe_ignore_global_monitor); - - if (global) { - WriteBasicSetting(Settings::values.cpu_debug_mode); - WriteBasicSetting(Settings::values.cpuopt_page_tables); - WriteBasicSetting(Settings::values.cpuopt_block_linking); - WriteBasicSetting(Settings::values.cpuopt_return_stack_buffer); - WriteBasicSetting(Settings::values.cpuopt_fast_dispatcher); - WriteBasicSetting(Settings::values.cpuopt_context_elimination); - WriteBasicSetting(Settings::values.cpuopt_const_prop); - WriteBasicSetting(Settings::values.cpuopt_misc_ir); - WriteBasicSetting(Settings::values.cpuopt_reduce_misalign_checks); - WriteBasicSetting(Settings::values.cpuopt_fastmem); - WriteBasicSetting(Settings::values.cpuopt_fastmem_exclusives); - WriteBasicSetting(Settings::values.cpuopt_recompile_exclusives); - WriteBasicSetting(Settings::values.cpuopt_ignore_memory_aborts); - } + WriteCategory(Settings::Category::Cpu); qt_config->endGroup(); } @@ -1386,82 +1086,8 @@ void Config::SaveCpuValues() { void Config::SaveRendererValues() { qt_config->beginGroup(QStringLiteral("Renderer")); - WriteSetting(QString::fromStdString(Settings::values.renderer_backend.GetLabel()), - static_cast(Settings::values.renderer_backend.GetValue(global)), - static_cast(Settings::values.renderer_backend.GetDefault()), - Settings::values.renderer_backend.UsingGlobal()); - WriteGlobalSetting(Settings::values.async_presentation); - WriteGlobalSetting(Settings::values.renderer_force_max_clock); - WriteGlobalSetting(Settings::values.vulkan_device); - WriteSetting(QString::fromStdString(Settings::values.fullscreen_mode.GetLabel()), - static_cast(Settings::values.fullscreen_mode.GetValue(global)), - static_cast(Settings::values.fullscreen_mode.GetDefault()), - Settings::values.fullscreen_mode.UsingGlobal()); - WriteGlobalSetting(Settings::values.aspect_ratio); - WriteSetting(QString::fromStdString(Settings::values.resolution_setup.GetLabel()), - static_cast(Settings::values.resolution_setup.GetValue(global)), - static_cast(Settings::values.resolution_setup.GetDefault()), - Settings::values.resolution_setup.UsingGlobal()); - WriteSetting(QString::fromStdString(Settings::values.scaling_filter.GetLabel()), - static_cast(Settings::values.scaling_filter.GetValue(global)), - static_cast(Settings::values.scaling_filter.GetDefault()), - Settings::values.scaling_filter.UsingGlobal()); - WriteSetting(QString::fromStdString(Settings::values.fsr_sharpening_slider.GetLabel()), - static_cast(Settings::values.fsr_sharpening_slider.GetValue(global)), - static_cast(Settings::values.fsr_sharpening_slider.GetDefault()), - Settings::values.fsr_sharpening_slider.UsingGlobal()); - WriteSetting(QString::fromStdString(Settings::values.anti_aliasing.GetLabel()), - static_cast(Settings::values.anti_aliasing.GetValue(global)), - static_cast(Settings::values.anti_aliasing.GetDefault()), - Settings::values.anti_aliasing.UsingGlobal()); - WriteGlobalSetting(Settings::values.max_anisotropy); - WriteGlobalSetting(Settings::values.speed_limit); - WriteGlobalSetting(Settings::values.use_disk_shader_cache); - WriteSetting(QString::fromStdString(Settings::values.gpu_accuracy.GetLabel()), - static_cast(Settings::values.gpu_accuracy.GetValue(global)), - static_cast(Settings::values.gpu_accuracy.GetDefault()), - Settings::values.gpu_accuracy.UsingGlobal()); - WriteGlobalSetting(Settings::values.use_asynchronous_gpu_emulation); - WriteSetting(QString::fromStdString(Settings::values.nvdec_emulation.GetLabel()), - static_cast(Settings::values.nvdec_emulation.GetValue(global)), - static_cast(Settings::values.nvdec_emulation.GetDefault()), - Settings::values.nvdec_emulation.UsingGlobal()); - WriteSetting(QString::fromStdString(Settings::values.accelerate_astc.GetLabel()), - static_cast(Settings::values.accelerate_astc.GetValue(global)), - static_cast(Settings::values.accelerate_astc.GetDefault()), - Settings::values.accelerate_astc.UsingGlobal()); - WriteSetting(QString::fromStdString(Settings::values.astc_recompression.GetLabel()), - static_cast(Settings::values.astc_recompression.GetValue(global)), - static_cast(Settings::values.astc_recompression.GetDefault()), - Settings::values.astc_recompression.UsingGlobal()); - WriteGlobalSetting(Settings::values.use_reactive_flushing); - WriteSetting(QString::fromStdString(Settings::values.accelerate_astc.GetLabel()), - static_cast(Settings::values.accelerate_astc.GetValue(global)), - static_cast(Settings::values.accelerate_astc.GetDefault()), - Settings::values.shader_backend.UsingGlobal()); - WriteSetting(QString::fromStdString(Settings::values.shader_backend.GetLabel()), - static_cast(Settings::values.shader_backend.GetValue(global)), - static_cast(Settings::values.shader_backend.GetDefault()), - Settings::values.shader_backend.UsingGlobal()); - WriteGlobalSetting(Settings::values.use_asynchronous_shaders); - WriteGlobalSetting(Settings::values.use_fast_gpu_time); - WriteGlobalSetting(Settings::values.use_vulkan_driver_pipeline_cache); - WriteGlobalSetting(Settings::values.enable_compute_pipelines); - WriteGlobalSetting(Settings::values.use_video_framerate); - WriteGlobalSetting(Settings::values.barrier_feedback_loops); - WriteGlobalSetting(Settings::values.bg_red); - WriteGlobalSetting(Settings::values.bg_green); - WriteGlobalSetting(Settings::values.bg_blue); - - if (global) { - WriteSetting(QString::fromStdString(Settings::values.vsync_mode.GetLabel()), - static_cast(Settings::values.vsync_mode.GetValue()), - static_cast(Settings::values.vsync_mode.GetDefault())); - WriteBasicSetting(Settings::values.renderer_debug); - WriteBasicSetting(Settings::values.renderer_shader_feedback); - WriteBasicSetting(Settings::values.enable_nsight_aftermath); - WriteBasicSetting(Settings::values.disable_shader_loop_safety_checks); - } + WriteCategory(Settings::Category::AdvancedGraphics); + WriteCategory(Settings::Category::Renderer); qt_config->endGroup(); } @@ -1469,9 +1095,9 @@ void Config::SaveRendererValues() { void Config::SaveScreenshotValues() { qt_config->beginGroup(QStringLiteral("Screenshots")); - WriteBasicSetting(UISettings::values.enable_screenshot_save_as); WriteSetting(QStringLiteral("screenshot_path"), QString::fromStdString(FS::GetYuzuPathString(FS::YuzuPath::ScreenshotsDir))); + WriteCategory(Settings::Category::Screenshots); qt_config->endGroup(); } @@ -1502,27 +1128,7 @@ void Config::SaveShortcutValues() { void Config::SaveSystemValues() { qt_config->beginGroup(QStringLiteral("System")); - WriteGlobalSetting(Settings::values.language_index); - WriteGlobalSetting(Settings::values.region_index); - WriteGlobalSetting(Settings::values.time_zone_index); - - WriteSetting(QStringLiteral("rng_seed_enabled"), - Settings::values.rng_seed.GetValue(global).has_value(), false, - Settings::values.rng_seed.UsingGlobal()); - WriteSetting(QStringLiteral("rng_seed"), Settings::values.rng_seed.GetValue(global).value_or(0), - 0, Settings::values.rng_seed.UsingGlobal()); - - if (global) { - WriteBasicSetting(Settings::values.current_user); - - WriteSetting(QStringLiteral("custom_rtc_enabled"), Settings::values.custom_rtc.has_value(), - false); - WriteSetting(QStringLiteral("custom_rtc"), - QVariant::fromValue(Settings::values.custom_rtc.value_or(0)), 0); - WriteBasicSetting(Settings::values.device_name); - } - - WriteGlobalSetting(Settings::values.sound_index); + WriteCategory(Settings::Category::System); qt_config->endGroup(); } @@ -1530,10 +1136,10 @@ void Config::SaveSystemValues() { void Config::SaveUIValues() { qt_config->beginGroup(QStringLiteral("UI")); + WriteCategory(Settings::Category::Ui); + WriteSetting(QStringLiteral("theme"), UISettings::values.theme, QString::fromUtf8(UISettings::themes[static_cast(default_theme)].second)); - WriteBasicSetting(UISettings::values.enable_discord_presence); - WriteBasicSetting(UISettings::values.select_user_on_boot); SaveUIGamelistValues(); SaveUILayoutValues(); @@ -1542,37 +1148,14 @@ void Config::SaveUIValues() { SaveShortcutValues(); SaveMultiplayerValues(); - WriteBasicSetting(UISettings::values.single_window_mode); - WriteBasicSetting(UISettings::values.fullscreen); - WriteBasicSetting(UISettings::values.display_titlebar); - WriteBasicSetting(UISettings::values.show_filter_bar); - WriteBasicSetting(UISettings::values.show_status_bar); - WriteBasicSetting(UISettings::values.confirm_before_closing); - WriteBasicSetting(UISettings::values.first_start); - WriteBasicSetting(UISettings::values.callout_flags); - WriteBasicSetting(UISettings::values.show_console); - WriteBasicSetting(UISettings::values.pause_when_in_background); - WriteBasicSetting(UISettings::values.mute_when_in_background); - WriteBasicSetting(UISettings::values.hide_mouse); - WriteBasicSetting(UISettings::values.controller_applet_disabled); - WriteBasicSetting(UISettings::values.disable_web_applet); - qt_config->endGroup(); } void Config::SaveUIGamelistValues() { qt_config->beginGroup(QStringLiteral("UIGameList")); - WriteBasicSetting(UISettings::values.show_add_ons); - WriteBasicSetting(UISettings::values.show_compat); - WriteBasicSetting(UISettings::values.show_size); - WriteBasicSetting(UISettings::values.show_types); - WriteBasicSetting(UISettings::values.game_icon_size); - WriteBasicSetting(UISettings::values.folder_icon_size); - WriteBasicSetting(UISettings::values.row_1_text_id); - WriteBasicSetting(UISettings::values.row_2_text_id); - WriteBasicSetting(UISettings::values.cache_game_list); - WriteBasicSetting(UISettings::values.favorites_expanded); + WriteCategory(Settings::Category::UiGameList); + qt_config->beginWriteArray(QStringLiteral("favorites")); for (int i = 0; i < UISettings::values.favorited_ids.size(); i++) { qt_config->setArrayIndex(i); @@ -1593,7 +1176,8 @@ void Config::SaveUILayoutValues() { WriteSetting(QStringLiteral("gameListHeaderState"), UISettings::values.gamelist_header_state); WriteSetting(QStringLiteral("microProfileDialogGeometry"), UISettings::values.microprofile_geometry); - WriteBasicSetting(UISettings::values.microprofile_visible); + + WriteCategory(Settings::Category::UiLayout); qt_config->endGroup(); } @@ -1601,10 +1185,7 @@ void Config::SaveUILayoutValues() { void Config::SaveWebServiceValues() { qt_config->beginGroup(QStringLiteral("WebService")); - WriteBasicSetting(Settings::values.enable_telemetry); - WriteBasicSetting(Settings::values.web_api_url); - WriteBasicSetting(Settings::values.yuzu_username); - WriteBasicSetting(Settings::values.yuzu_token); + WriteCategory(Settings::Category::WebService); qt_config->endGroup(); } @@ -1612,17 +1193,7 @@ void Config::SaveWebServiceValues() { void Config::SaveMultiplayerValues() { qt_config->beginGroup(QStringLiteral("Multiplayer")); - WriteBasicSetting(UISettings::values.multiplayer_nickname); - WriteBasicSetting(UISettings::values.multiplayer_ip); - WriteBasicSetting(UISettings::values.multiplayer_port); - WriteBasicSetting(UISettings::values.multiplayer_room_nickname); - WriteBasicSetting(UISettings::values.multiplayer_room_name); - WriteBasicSetting(UISettings::values.multiplayer_room_port); - WriteBasicSetting(UISettings::values.multiplayer_host_type); - WriteBasicSetting(UISettings::values.multiplayer_port); - WriteBasicSetting(UISettings::values.multiplayer_max_player); - WriteBasicSetting(UISettings::values.multiplayer_game_id); - WriteBasicSetting(UISettings::values.multiplayer_room_description); + WriteCategory(Settings::Category::Multiplayer); // Write ban list qt_config->beginWriteArray(QStringLiteral("username_ban_list")); @@ -1731,3 +1302,58 @@ void Config::ClearControlPlayerValues() { const std::string& Config::GetConfigFilePath() const { return qt_config_loc; } + +void Config::ReadCategory(Settings::Category category) { + const auto& settings = settings_map[category]; + std::for_each(settings.begin(), settings.end(), + [&](const auto& setting) { ReadSettingGeneric(setting); }); +} + +void Config::WriteCategory(Settings::Category category) { + const auto& settings = settings_map[category]; + std::for_each(settings.begin(), settings.end(), + [&](const auto& setting) { WriteSettingGeneric(setting); }); +} + +void Config::ReadSettingGeneric(Settings::BasicSetting* const setting) { + if (!setting->Save()) { + return; + } + const QString name = QString::fromStdString(setting->GetLabel()); + const auto default_value = + QVariant::fromValue(QString::fromStdString(setting->DefaultToString())); + + if (setting->Switchable()) { + const bool use_global = + qt_config->value(name + QStringLiteral("/use_global"), true).value(); + setting->SetGlobal(use_global); + + if (global || !use_global) { + setting->LoadString(ReadSetting(name, default_value).value().toStdString()); + } + } else if (global) { + setting->LoadString(ReadSetting(name, default_value).value().toStdString()); + } +} + +void Config::WriteSettingGeneric(Settings::BasicSetting* const setting) const { + if (!setting->Save()) { + return; + } + const QVariant value = QVariant::fromValue(QString::fromStdString(setting->ToString())); + const QVariant default_value = + QVariant::fromValue(QString::fromStdString(setting->DefaultToString())); + const QString label = QString::fromStdString(setting->GetLabel()); + if (setting->Switchable()) { + if (!global) { + qt_config->setValue(label + QStringLiteral("/use_global"), setting->UsingGlobal()); + } + if (global || !setting->UsingGlobal()) { + qt_config->setValue(label + QStringLiteral("/default"), value == default_value); + qt_config->setValue(label, value); + } + } else if (global) { + qt_config->setValue(label + QStringLiteral("/default"), value == default_value); + qt_config->setValue(label, value); + } +} diff --git a/src/yuzu/configuration/config.h b/src/yuzu/configuration/config.h index e066f7552..ec748bf0c 100644 --- a/src/yuzu/configuration/config.h +++ b/src/yuzu/configuration/config.h @@ -74,7 +74,6 @@ private: void ReadKeyboardValues(); void ReadMouseValues(); void ReadTouchscreenValues(); - void ReadMousePanningValues(); void ReadMotionTouchValues(); void ReadHidbusValues(); void ReadIrCameraValues(); @@ -105,7 +104,6 @@ private: void SaveDebugValues(); void SaveMouseValues(); void SaveTouchscreenValues(); - void SaveMousePanningValues(); void SaveMotionTouchValues(); void SaveHidbusValues(); void SaveIrCameraValues(); @@ -201,10 +199,17 @@ private: template void WriteBasicSetting(const Settings::Setting& setting); - ConfigType type; + void ReadCategory(Settings::Category category); + void WriteCategory(Settings::Category category); + void ReadSettingGeneric(Settings::BasicSetting* const setting); + void WriteSettingGeneric(Settings::BasicSetting* const setting) const; + + std::map> settings_map; + + const ConfigType type; std::unique_ptr qt_config; std::string qt_config_loc; - bool global; + const bool global; }; // These metatype declarations cannot be in common/settings.h because core is devoid of QT diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index ac42cc7fc..8fd12c9e8 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -43,25 +43,6 @@ void ConfigurationShared::SetHighlight(QWidget* widget, bool highlighted) { widget->show(); } -void ConfigurationShared::SetColoredTristate(QCheckBox* checkbox, - const Settings::SwitchableSetting& setting, - CheckState& tracker) { - if (setting.UsingGlobal()) { - tracker = CheckState::Global; - } else { - tracker = (setting.GetValue() == setting.GetValue(true)) ? CheckState::On : CheckState::Off; - } - SetHighlight(checkbox, tracker != CheckState::Global); - QObject::connect(checkbox, &QCheckBox::clicked, checkbox, [checkbox, setting, &tracker] { - tracker = static_cast((static_cast(tracker) + 1) % - static_cast(CheckState::Count)); - if (tracker == CheckState::Global) { - checkbox->setChecked(setting.GetValue(true)); - } - SetHighlight(checkbox, tracker != CheckState::Global); - }); -} - void ConfigurationShared::SetColoredTristate(QCheckBox* checkbox, bool global, bool state, bool global_state, CheckState& tracker) { if (global) { diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 04c88758c..1e61bcbeb 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -57,8 +57,26 @@ void SetPerGameSetting(QComboBox* combobox, void SetHighlight(QWidget* widget, bool highlighted); // Sets up a QCheckBox like a tristate one, given a Setting -void SetColoredTristate(QCheckBox* checkbox, const Settings::SwitchableSetting& setting, - CheckState& tracker); +template +void SetColoredTristate(QCheckBox* checkbox, + const Settings::SwitchableSetting& setting, + CheckState& tracker) { + if (setting.UsingGlobal()) { + tracker = CheckState::Global; + } else { + tracker = (setting.GetValue() == setting.GetValue(true)) ? CheckState::On : CheckState::Off; + } + SetHighlight(checkbox, tracker != CheckState::Global); + QObject::connect(checkbox, &QCheckBox::clicked, checkbox, [checkbox, setting, &tracker] { + tracker = static_cast((static_cast(tracker) + 1) % + static_cast(CheckState::Count)); + if (tracker == CheckState::Global) { + checkbox->setChecked(setting.GetValue(true)); + } + SetHighlight(checkbox, tracker != CheckState::Global); + }); +} + void SetColoredTristate(QCheckBox* checkbox, bool global, bool state, bool global_state, CheckState& tracker); diff --git a/src/yuzu/uisettings.h b/src/yuzu/uisettings.h index 0be8ee369..53cdd7fcb 100644 --- a/src/yuzu/uisettings.h +++ b/src/yuzu/uisettings.h @@ -14,6 +14,7 @@ #include "common/common_types.h" #include "common/settings.h" +using Settings::Category; using Settings::Setting; namespace UISettings { @@ -58,6 +59,8 @@ struct GameDir { }; struct Values { + Settings::Linkage linkage{}; + QByteArray geometry; QByteArray state; @@ -66,33 +69,36 @@ struct Values { QByteArray gamelist_header_state; QByteArray microprofile_geometry; - Setting microprofile_visible{false, "microProfileDialogVisible"}; + Setting microprofile_visible{linkage, false, "microProfileDialogVisible", + Category::UiLayout}; - Setting single_window_mode{true, "singleWindowMode"}; - Setting fullscreen{false, "fullscreen"}; - Setting display_titlebar{true, "displayTitleBars"}; - Setting show_filter_bar{true, "showFilterBar"}; - Setting show_status_bar{true, "showStatusBar"}; + Setting single_window_mode{linkage, true, "singleWindowMode", Category::Ui}; + Setting fullscreen{linkage, false, "fullscreen", Category::Ui}; + Setting display_titlebar{linkage, true, "displayTitleBars", Category::Ui}; + Setting show_filter_bar{linkage, true, "showFilterBar", Category::Ui}; + Setting show_status_bar{linkage, true, "showStatusBar", Category::Ui}; - Setting confirm_before_closing{true, "confirmClose"}; - Setting first_start{true, "firstStart"}; - Setting pause_when_in_background{false, "pauseWhenInBackground"}; - Setting mute_when_in_background{false, "muteWhenInBackground"}; - Setting hide_mouse{true, "hideInactiveMouse"}; - Setting controller_applet_disabled{false, "disableControllerApplet"}; + Setting confirm_before_closing{linkage, true, "confirmClose", Category::Ui}; + Setting first_start{linkage, true, "firstStart", Category::Ui}; + Setting pause_when_in_background{linkage, false, "pauseWhenInBackground", Category::Ui}; + Setting mute_when_in_background{linkage, false, "muteWhenInBackground", Category::Ui}; + Setting hide_mouse{linkage, true, "hideInactiveMouse", Category::Ui}; + Setting controller_applet_disabled{linkage, false, "disableControllerApplet", + Category::Ui}; // Set when Vulkan is known to crash the application bool has_broken_vulkan = false; - Setting select_user_on_boot{false, "select_user_on_boot"}; - Setting disable_web_applet{true, "disable_web_applet"}; + Setting select_user_on_boot{linkage, false, "select_user_on_boot", Category::Ui}; + Setting disable_web_applet{linkage, true, "disable_web_applet", Category::Ui}; // Discord RPC - Setting enable_discord_presence{true, "enable_discord_presence"}; + Setting enable_discord_presence{linkage, true, "enable_discord_presence", Category::Ui}; // logging - Setting show_console{false, "showConsole"}; + Setting show_console{linkage, false, "showConsole", Category::Ui}; - Setting enable_screenshot_save_as{true, "enable_screenshot_save_as"}; + Setting enable_screenshot_save_as{linkage, true, "enable_screenshot_save_as", + Category::Screenshots}; QString roms_path; QString symbols_path; @@ -107,38 +113,42 @@ struct Values { // Shortcut name std::vector shortcuts; - Setting callout_flags{0, "calloutFlags"}; + Setting callout_flags{linkage, 0, "calloutFlags", Category::Ui}; // multiplayer settings - Setting multiplayer_nickname{{}, "nickname"}; - Setting multiplayer_ip{{}, "ip"}; - Setting multiplayer_port{24872, 0, UINT16_MAX, "port"}; - Setting multiplayer_room_nickname{{}, "room_nickname"}; - Setting multiplayer_room_name{{}, "room_name"}; - Setting multiplayer_max_player{8, 0, 8, "max_player"}; - Setting multiplayer_room_port{24872, 0, UINT16_MAX, "room_port"}; - Setting multiplayer_host_type{0, 0, 1, "host_type"}; - Setting multiplayer_game_id{{}, "game_id"}; - Setting multiplayer_room_description{{}, "room_description"}; + Setting multiplayer_nickname{linkage, {}, "nickname", Category::Multiplayer}; + Setting multiplayer_ip{linkage, {}, "ip", Category::Multiplayer}; + Setting multiplayer_port{linkage, 24872, 0, + UINT16_MAX, "port", Category::Multiplayer}; + Setting multiplayer_room_nickname{ + linkage, {}, "room_nickname", Category::Multiplayer}; + Setting multiplayer_room_name{linkage, {}, "room_name", Category::Multiplayer}; + Setting multiplayer_max_player{linkage, 8, 0, 8, "max_player", Category::Multiplayer}; + Setting multiplayer_room_port{linkage, 24872, 0, + UINT16_MAX, "room_port", Category::Multiplayer}; + Setting multiplayer_host_type{linkage, 0, 0, 1, "host_type", Category::Multiplayer}; + Setting multiplayer_game_id{linkage, {}, "game_id", Category::Multiplayer}; + Setting multiplayer_room_description{ + linkage, {}, "room_description", Category::Multiplayer}; std::pair, std::vector> multiplayer_ban_list; // Game List - Setting show_add_ons{true, "show_add_ons"}; - Setting game_icon_size{64, "game_icon_size"}; - Setting folder_icon_size{48, "folder_icon_size"}; - Setting row_1_text_id{3, "row_1_text_id"}; - Setting row_2_text_id{2, "row_2_text_id"}; + Setting show_add_ons{linkage, true, "show_add_ons", Category::UiGameList}; + Setting game_icon_size{linkage, 64, "game_icon_size", Category::UiGameList}; + Setting folder_icon_size{linkage, 48, "folder_icon_size", Category::UiGameList}; + Setting row_1_text_id{linkage, 3, "row_1_text_id", Category::UiGameList}; + Setting row_2_text_id{linkage, 2, "row_2_text_id", Category::UiGameList}; std::atomic_bool is_game_list_reload_pending{false}; - Setting cache_game_list{true, "cache_game_list"}; - Setting favorites_expanded{true, "favorites_expanded"}; + Setting cache_game_list{linkage, true, "cache_game_list", Category::UiGameList}; + Setting favorites_expanded{linkage, true, "favorites_expanded", Category::UiGameList}; QVector favorited_ids; // Compatibility List - Setting show_compat{false, "show_compat"}; + Setting show_compat{linkage, false, "show_compat", Category::UiGameList}; // Size & File Types Column - Setting show_size{true, "show_size"}; - Setting show_types{true, "show_types"}; + Setting show_size{linkage, true, "show_size", Category::UiGameList}; + Setting show_types{linkage, true, "show_types", Category::UiGameList}; bool configuration_applied; bool reset_to_defaults; diff --git a/src/yuzu_cmd/config.cpp b/src/yuzu_cmd/config.cpp index b2049ae57..cfc1a5d81 100644 --- a/src/yuzu_cmd/config.cpp +++ b/src/yuzu_cmd/config.cpp @@ -98,8 +98,26 @@ void Config::ReadSetting(const std::string& group, Settings::Setting(setting.GetDefault()))); } +void Config::ReadCategory(Settings::Category category) { + for (const auto setting : Settings::values.linkage.by_category[category]) { + const char* category_name = [&]() { + if (category == Settings::Category::Controls) { + // For compatibility with older configs + return "ControlsGeneral"; + } else { + return Settings::TranslateCategory(category); + } + }(); + std::string setting_value = + sdl2_config->Get(category_name, setting->GetLabel(), setting->DefaultToString()); + setting->LoadString(setting_value); + } +} + void Config::ReadValues() { // Controls + ReadCategory(Settings::Category::Controls); + for (std::size_t p = 0; p < Settings::values.players.GetValue().size(); ++p) { auto& player = Settings::values.players.GetValue()[p]; @@ -139,13 +157,6 @@ void Config::ReadValues() { player.connected = sdl2_config->GetBoolean(group, "connected", false); } - ReadSetting("ControlsGeneral", Settings::values.mouse_enabled); - - ReadSetting("ControlsGeneral", Settings::values.touch_device); - - ReadSetting("ControlsGeneral", Settings::values.keyboard_enabled); - - ReadSetting("ControlsGeneral", Settings::values.debug_pad_enabled); for (int i = 0; i < Settings::NativeButton::NumButtons; ++i) { std::string default_param = InputCommon::GenerateKeyboardParam(default_buttons[i]); Settings::values.debug_pad_buttons[i] = sdl2_config->Get( @@ -166,14 +177,6 @@ void Config::ReadValues() { Settings::values.debug_pad_analogs[i] = default_param; } - ReadSetting("ControlsGeneral", Settings::values.enable_raw_input); - ReadSetting("ControlsGeneral", Settings::values.enable_joycon_driver); - ReadSetting("ControlsGeneral", Settings::values.enable_procon_driver); - ReadSetting("ControlsGeneral", Settings::values.random_amiibo_id); - ReadSetting("ControlsGeneral", Settings::values.emulate_analog_keyboard); - ReadSetting("ControlsGeneral", Settings::values.vibration_enabled); - ReadSetting("ControlsGeneral", Settings::values.enable_accurate_vibrations); - ReadSetting("ControlsGeneral", Settings::values.motion_enabled); Settings::values.touchscreen.enabled = sdl2_config->GetBoolean("ControlsGeneral", "touch_enabled", true); Settings::values.touchscreen.rotation_angle = @@ -217,10 +220,19 @@ void Config::ReadValues() { Settings::values.touch_from_button_map_index = std::clamp( Settings::values.touch_from_button_map_index.GetValue(), 0, num_touch_from_button_maps - 1); - ReadSetting("ControlsGeneral", Settings::values.udp_input_servers); + ReadCategory(Settings::Category::Audio); + ReadCategory(Settings::Category::Core); + ReadCategory(Settings::Category::Cpu); + ReadCategory(Settings::Category::Renderer); + ReadCategory(Settings::Category::AdvancedGraphics); + ReadCategory(Settings::Category::System); + ReadCategory(Settings::Category::DataStorage); + ReadCategory(Settings::Category::Debugging); + ReadCategory(Settings::Category::Miscellaneous); + ReadCategory(Settings::Category::Network); + ReadCategory(Settings::Category::WebService); // Data Storage - ReadSetting("Data Storage", Settings::values.use_virtual_sd); FS::SetYuzuPath(FS::YuzuPath::NANDDir, sdl2_config->Get("Data Storage", "nand_directory", FS::GetYuzuPathString(FS::YuzuPath::NANDDir))); @@ -233,122 +245,10 @@ void Config::ReadValues() { FS::SetYuzuPath(FS::YuzuPath::DumpDir, sdl2_config->Get("Data Storage", "dump_directory", FS::GetYuzuPathString(FS::YuzuPath::DumpDir))); - ReadSetting("Data Storage", Settings::values.gamecard_inserted); - ReadSetting("Data Storage", Settings::values.gamecard_current_game); - ReadSetting("Data Storage", Settings::values.gamecard_path); - - // System - ReadSetting("System", Settings::values.use_docked_mode); - - ReadSetting("System", Settings::values.current_user); - Settings::values.current_user = std::clamp(Settings::values.current_user.GetValue(), 0, - Service::Account::MAX_USERS - 1); - - const auto rng_seed_enabled = sdl2_config->GetBoolean("System", "rng_seed_enabled", false); - if (rng_seed_enabled) { - Settings::values.rng_seed.SetValue(sdl2_config->GetInteger("System", "rng_seed", 0)); - } else { - Settings::values.rng_seed.SetValue(std::nullopt); - } - - const auto custom_rtc_enabled = sdl2_config->GetBoolean("System", "custom_rtc_enabled", false); - if (custom_rtc_enabled) { - Settings::values.custom_rtc = sdl2_config->GetInteger("System", "custom_rtc", 0); - } else { - Settings::values.custom_rtc = std::nullopt; - } - - ReadSetting("System", Settings::values.language_index); - ReadSetting("System", Settings::values.region_index); - ReadSetting("System", Settings::values.time_zone_index); - ReadSetting("System", Settings::values.sound_index); - - // Core - ReadSetting("Core", Settings::values.use_multi_core); - ReadSetting("Core", Settings::values.use_unsafe_extended_memory_layout); - - // Cpu - ReadSetting("Cpu", Settings::values.cpu_accuracy); - ReadSetting("Cpu", Settings::values.cpu_debug_mode); - ReadSetting("Cpu", Settings::values.cpuopt_page_tables); - ReadSetting("Cpu", Settings::values.cpuopt_block_linking); - ReadSetting("Cpu", Settings::values.cpuopt_return_stack_buffer); - ReadSetting("Cpu", Settings::values.cpuopt_fast_dispatcher); - ReadSetting("Cpu", Settings::values.cpuopt_context_elimination); - ReadSetting("Cpu", Settings::values.cpuopt_const_prop); - ReadSetting("Cpu", Settings::values.cpuopt_misc_ir); - ReadSetting("Cpu", Settings::values.cpuopt_reduce_misalign_checks); - ReadSetting("Cpu", Settings::values.cpuopt_fastmem); - ReadSetting("Cpu", Settings::values.cpuopt_fastmem_exclusives); - ReadSetting("Cpu", Settings::values.cpuopt_recompile_exclusives); - ReadSetting("Cpu", Settings::values.cpuopt_ignore_memory_aborts); - ReadSetting("Cpu", Settings::values.cpuopt_unsafe_unfuse_fma); - ReadSetting("Cpu", Settings::values.cpuopt_unsafe_reduce_fp_error); - ReadSetting("Cpu", Settings::values.cpuopt_unsafe_ignore_standard_fpcr); - ReadSetting("Cpu", Settings::values.cpuopt_unsafe_inaccurate_nan); - ReadSetting("Cpu", Settings::values.cpuopt_unsafe_fastmem_check); - ReadSetting("Cpu", Settings::values.cpuopt_unsafe_ignore_global_monitor); - - // Renderer - ReadSetting("Renderer", Settings::values.renderer_backend); - ReadSetting("Renderer", Settings::values.async_presentation); - ReadSetting("Renderer", Settings::values.renderer_force_max_clock); - ReadSetting("Renderer", Settings::values.renderer_debug); - ReadSetting("Renderer", Settings::values.renderer_shader_feedback); - ReadSetting("Renderer", Settings::values.enable_nsight_aftermath); - ReadSetting("Renderer", Settings::values.disable_shader_loop_safety_checks); - ReadSetting("Renderer", Settings::values.vulkan_device); - - ReadSetting("Renderer", Settings::values.resolution_setup); - ReadSetting("Renderer", Settings::values.scaling_filter); - ReadSetting("Renderer", Settings::values.fsr_sharpening_slider); - ReadSetting("Renderer", Settings::values.anti_aliasing); - ReadSetting("Renderer", Settings::values.fullscreen_mode); - ReadSetting("Renderer", Settings::values.aspect_ratio); - ReadSetting("Renderer", Settings::values.max_anisotropy); - ReadSetting("Renderer", Settings::values.use_speed_limit); - ReadSetting("Renderer", Settings::values.speed_limit); - ReadSetting("Renderer", Settings::values.use_disk_shader_cache); - ReadSetting("Renderer", Settings::values.gpu_accuracy); - ReadSetting("Renderer", Settings::values.use_asynchronous_gpu_emulation); - ReadSetting("Renderer", Settings::values.vsync_mode); - ReadSetting("Renderer", Settings::values.shader_backend); - ReadSetting("Renderer", Settings::values.use_reactive_flushing); - ReadSetting("Renderer", Settings::values.use_asynchronous_shaders); - ReadSetting("Renderer", Settings::values.nvdec_emulation); - ReadSetting("Renderer", Settings::values.accelerate_astc); - ReadSetting("Renderer", Settings::values.astc_recompression); - ReadSetting("Renderer", Settings::values.use_vulkan_driver_pipeline_cache); - - ReadSetting("Renderer", Settings::values.bg_red); - ReadSetting("Renderer", Settings::values.bg_green); - ReadSetting("Renderer", Settings::values.bg_blue); - - // Audio - ReadSetting("Audio", Settings::values.sink_id); - ReadSetting("Audio", Settings::values.audio_output_device_id); - ReadSetting("Audio", Settings::values.volume); - - // Miscellaneous - // log_filter has a different default here than from common - Settings::values.log_filter = - sdl2_config->Get("Miscellaneous", Settings::values.log_filter.GetLabel(), "*:Trace"); - ReadSetting("Miscellaneous", Settings::values.use_dev_keys); // Debugging Settings::values.record_frame_times = sdl2_config->GetBoolean("Debugging", "record_frame_times", false); - ReadSetting("Debugging", Settings::values.dump_exefs); - ReadSetting("Debugging", Settings::values.dump_nso); - ReadSetting("Debugging", Settings::values.enable_fs_access_log); - ReadSetting("Debugging", Settings::values.reporting_services); - ReadSetting("Debugging", Settings::values.quest_flag); - ReadSetting("Debugging", Settings::values.use_debug_asserts); - ReadSetting("Debugging", Settings::values.use_auto_stub); - ReadSetting("Debugging", Settings::values.disable_macro_jit); - ReadSetting("Debugging", Settings::values.disable_macro_hle); - ReadSetting("Debugging", Settings::values.use_gdbstub); - ReadSetting("Debugging", Settings::values.gdbstub_port); const auto title_list = sdl2_config->Get("AddOns", "title_ids", ""); std::stringstream ss(title_list); @@ -366,15 +266,6 @@ void Config::ReadValues() { Settings::values.disabled_addons.insert_or_assign(title_id, out); } - - // Web Service - ReadSetting("WebService", Settings::values.enable_telemetry); - ReadSetting("WebService", Settings::values.web_api_url); - ReadSetting("WebService", Settings::values.yuzu_username); - ReadSetting("WebService", Settings::values.yuzu_token); - - // Network - ReadSetting("Network", Settings::values.network_interface); } void Config::Reload() { diff --git a/src/yuzu_cmd/config.h b/src/yuzu_cmd/config.h index 021438b17..512591a39 100644 --- a/src/yuzu_cmd/config.h +++ b/src/yuzu_cmd/config.h @@ -34,4 +34,5 @@ private: */ template void ReadSetting(const std::string& group, Settings::Setting& setting); + void ReadCategory(Settings::Category category); }; From e5b981e1e45be66c66c5592019b85928a34efbd7 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 5 May 2023 19:49:51 -0400 Subject: [PATCH 006/155] configuration_shared: Create Tab base class --- src/yuzu/configuration/configuration_shared.cpp | 9 +++++++++ src/yuzu/configuration/configuration_shared.h | 13 +++++++++++++ 2 files changed, 22 insertions(+) diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 8fd12c9e8..ce12f55a2 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -4,10 +4,19 @@ #include #include #include +#include #include "common/settings.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_per_game.h" +namespace ConfigurationShared { + +Tab::Tab(QWidget* parent) : QWidget(parent) {} + +Tab::~Tab() {} + +} // namespace ConfigurationShared + void ConfigurationShared::ApplyPerGameSetting(Settings::SwitchableSetting* setting, const QCheckBox* checkbox, const CheckState& tracker) { diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 1e61bcbeb..ea8b18755 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -5,10 +5,23 @@ #include #include +#include +#include #include "common/settings.h" namespace ConfigurationShared { +class Tab : public QWidget { + Q_OBJECT + +public: + explicit Tab(QWidget* parent = nullptr); + ~Tab(); + + virtual void ApplyConfiguration() = 0; + virtual void SetConfiguration() = 0; +}; + constexpr int USE_GLOBAL_INDEX = 0; constexpr int USE_GLOBAL_SEPARATOR_INDEX = 1; constexpr int USE_GLOBAL_OFFSET = 2; From d3b94d64d492407dcd43acf79cd1e94d57630109 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 5 May 2023 23:30:59 -0400 Subject: [PATCH 007/155] configuration: Add base class to tabs Tabs that largely configure SwitchableSetting's are now Tabs and grouped together. --- .../configuration/configuration_shared.cpp | 10 +++++-- src/yuzu/configuration/configuration_shared.h | 8 +++++- src/yuzu/configuration/configure_audio.cpp | 6 +++-- src/yuzu/configuration/configure_audio.h | 17 +++++------- src/yuzu/configuration/configure_cpu.cpp | 8 ++++-- src/yuzu/configuration/configure_cpu.h | 17 +++++------- src/yuzu/configuration/configure_dialog.cpp | 14 +++++----- src/yuzu/configuration/configure_dialog.h | 3 +++ src/yuzu/configuration/configure_general.cpp | 6 +++-- src/yuzu/configuration/configure_general.h | 18 +++++-------- src/yuzu/configuration/configure_graphics.cpp | 12 ++++----- src/yuzu/configuration/configure_graphics.h | 14 ++++------ .../configure_graphics_advanced.cpp | 6 +++-- .../configure_graphics_advanced.h | 18 ++++++------- src/yuzu/configuration/configure_per_game.cpp | 27 +++++++++---------- src/yuzu/configuration/configure_per_game.h | 4 ++- src/yuzu/configuration/configure_system.cpp | 6 +++-- src/yuzu/configuration/configure_system.h | 17 +++++------- 18 files changed, 110 insertions(+), 101 deletions(-) diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index ce12f55a2..72b7957e0 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -1,6 +1,7 @@ // SPDX-FileCopyrightText: 2016 Citra Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#include #include #include #include @@ -11,9 +12,14 @@ namespace ConfigurationShared { -Tab::Tab(QWidget* parent) : QWidget(parent) {} +Tab::Tab(std::shared_ptr> group_, QWidget* parent) + : QWidget(parent), group{group_} { + if (group != nullptr) { + group->push_front(this); + } +} -Tab::~Tab() {} +Tab::~Tab() = default; } // namespace ConfigurationShared diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index ea8b18755..1a3a2a985 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -3,6 +3,9 @@ #pragma once +#include +#include +#include #include #include #include @@ -15,11 +18,14 @@ class Tab : public QWidget { Q_OBJECT public: - explicit Tab(QWidget* parent = nullptr); + explicit Tab(std::shared_ptr> group_, QWidget* parent = nullptr); ~Tab(); virtual void ApplyConfiguration() = 0; virtual void SetConfiguration() = 0; + +private: + std::shared_ptr> group; }; constexpr int USE_GLOBAL_INDEX = 0; diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index fcd6d61a0..335662144 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -12,8 +12,10 @@ #include "yuzu/configuration/configure_audio.h" #include "yuzu/uisettings.h" -ConfigureAudio::ConfigureAudio(const Core::System& system_, QWidget* parent) - : QWidget(parent), ui(std::make_unique()), system{system_} { +ConfigureAudio::ConfigureAudio(const Core::System& system_, + std::shared_ptr> group, + QWidget* parent) + : Tab(group, parent), ui(std::make_unique()), system{system_} { ui->setupUi(this); InitializeAudioSinkComboBox(); diff --git a/src/yuzu/configuration/configure_audio.h b/src/yuzu/configuration/configure_audio.h index 0d03aae1d..d134ac957 100644 --- a/src/yuzu/configuration/configure_audio.h +++ b/src/yuzu/configuration/configure_audio.h @@ -5,28 +5,25 @@ #include #include +#include "yuzu/configuration/configuration_shared.h" namespace Core { class System; } -namespace ConfigurationShared { -enum class CheckState; -} - namespace Ui { class ConfigureAudio; } -class ConfigureAudio : public QWidget { - Q_OBJECT - +class ConfigureAudio : public ConfigurationShared::Tab { public: - explicit ConfigureAudio(const Core::System& system_, QWidget* parent = nullptr); + explicit ConfigureAudio(const Core::System& system_, + std::shared_ptr> group, + QWidget* parent = nullptr); ~ConfigureAudio() override; - void ApplyConfiguration(); - void SetConfiguration(); + void ApplyConfiguration() override; + void SetConfiguration() override; private: void changeEvent(QEvent* event) override; diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 3d69fb03f..ecaeb1a6b 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -1,6 +1,8 @@ // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#include +#include #include "common/common_types.h" #include "common/settings.h" #include "core/core.h" @@ -8,8 +10,10 @@ #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_cpu.h" -ConfigureCpu::ConfigureCpu(const Core::System& system_, QWidget* parent) - : QWidget(parent), ui{std::make_unique()}, system{system_} { +ConfigureCpu::ConfigureCpu(const Core::System& system_, + std::shared_ptr> group, + QWidget* parent) + : Tab(group, parent), ui{std::make_unique()}, system{system_} { ui->setupUi(this); SetupPerGameUI(); diff --git a/src/yuzu/configuration/configure_cpu.h b/src/yuzu/configuration/configure_cpu.h index 86d928ca3..187d080b6 100644 --- a/src/yuzu/configuration/configure_cpu.h +++ b/src/yuzu/configuration/configure_cpu.h @@ -5,28 +5,25 @@ #include #include +#include "yuzu/configuration/configuration_shared.h" namespace Core { class System; } -namespace ConfigurationShared { -enum class CheckState; -} - namespace Ui { class ConfigureCpu; } -class ConfigureCpu : public QWidget { - Q_OBJECT - +class ConfigureCpu : public ConfigurationShared::Tab { public: - explicit ConfigureCpu(const Core::System& system_, QWidget* parent = nullptr); + explicit ConfigureCpu(const Core::System& system_, + std::shared_ptr> group, + QWidget* parent = nullptr); ~ConfigureCpu() override; - void ApplyConfiguration(); - void SetConfiguration(); + void ApplyConfiguration() override; + void SetConfiguration() override; private: void changeEvent(QEvent* event) override; diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index bdf83ebfe..2cc9f3621 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -32,21 +32,21 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, std::vector& vk_device_records, Core::System& system_, bool enable_web_config) : QDialog(parent), ui{std::make_unique()}, - registry(registry_), system{system_}, audio_tab{std::make_unique(system_, - this)}, - cpu_tab{std::make_unique(system_, this)}, + registry(registry_), system{system_}, audio_tab{std::make_unique( + system_, nullptr, this)}, + cpu_tab{std::make_unique(system_, nullptr, this)}, debug_tab_tab{std::make_unique(system_, this)}, filesystem_tab{std::make_unique(this)}, - general_tab{std::make_unique(system_, this)}, - graphics_advanced_tab{std::make_unique(system_, this)}, + general_tab{std::make_unique(system_, nullptr, this)}, + graphics_advanced_tab{std::make_unique(system_, nullptr, this)}, graphics_tab{std::make_unique( system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, - this)}, + nullptr, this)}, hotkeys_tab{std::make_unique(system_.HIDCore(), this)}, input_tab{std::make_unique(system_, this)}, network_tab{std::make_unique(system_, this)}, profile_tab{std::make_unique(system_, this)}, - system_tab{std::make_unique(system_, this)}, + system_tab{std::make_unique(system_, nullptr, this)}, ui_tab{std::make_unique(system_, this)}, web_tab{std::make_unique( this)} { Settings::SetConfiguringGlobal(true); diff --git a/src/yuzu/configuration/configure_dialog.h b/src/yuzu/configuration/configure_dialog.h index 2a08b7fee..8ee89a192 100644 --- a/src/yuzu/configuration/configure_dialog.h +++ b/src/yuzu/configuration/configure_dialog.h @@ -3,9 +3,11 @@ #pragma once +#include #include #include #include +#include "configuration/configuration_shared.h" #include "yuzu/vk_device_info.h" namespace Core { @@ -69,6 +71,7 @@ private: HotkeyRegistry& registry; Core::System& system; + std::forward_list tab_group; std::unique_ptr audio_tab; std::unique_ptr cpu_tab; diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index 2f55159f5..03261992a 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -11,8 +11,10 @@ #include "yuzu/configuration/configure_general.h" #include "yuzu/uisettings.h" -ConfigureGeneral::ConfigureGeneral(const Core::System& system_, QWidget* parent) - : QWidget(parent), ui{std::make_unique()}, system{system_} { +ConfigureGeneral::ConfigureGeneral( + const Core::System& system_, + std::shared_ptr> group, QWidget* parent) + : Tab(group, parent), ui{std::make_unique()}, system{system_} { ui->setupUi(this); SetupPerGameUI(); diff --git a/src/yuzu/configuration/configure_general.h b/src/yuzu/configuration/configure_general.h index 7ff63f425..0aad69f0a 100644 --- a/src/yuzu/configuration/configure_general.h +++ b/src/yuzu/configuration/configure_general.h @@ -6,34 +6,30 @@ #include #include #include +#include "yuzu/configuration/configuration_shared.h" namespace Core { class System; } class ConfigureDialog; - -namespace ConfigurationShared { -enum class CheckState; -} - class HotkeyRegistry; namespace Ui { class ConfigureGeneral; } -class ConfigureGeneral : public QWidget { - Q_OBJECT - +class ConfigureGeneral : public ConfigurationShared::Tab { public: - explicit ConfigureGeneral(const Core::System& system_, QWidget* parent = nullptr); + explicit ConfigureGeneral(const Core::System& system_, + std::shared_ptr> group, + QWidget* parent = nullptr); ~ConfigureGeneral() override; void SetResetCallback(std::function callback); void ResetDefaults(); - void ApplyConfiguration(); - void SetConfiguration(); + void ApplyConfiguration() override; + void SetConfiguration() override; private: void changeEvent(QEvent* event) override; diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index e70781357..a8c5b1d9f 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -70,12 +70,12 @@ static constexpr Settings::VSyncMode PresentModeToSetting(VkPresentModeKHR mode) } } -ConfigureGraphics::ConfigureGraphics(const Core::System& system_, - std::vector& records_, - const std::function& expose_compute_option_, - QWidget* parent) - : QWidget(parent), ui{std::make_unique()}, records{records_}, - expose_compute_option{expose_compute_option_}, system{system_} { +ConfigureGraphics::ConfigureGraphics( + const Core::System& system_, std::vector& records_, + const std::function& expose_compute_option_, + std::shared_ptr> group, QWidget* parent) + : ConfigurationShared::Tab(group, parent), ui{std::make_unique()}, + records{records_}, expose_compute_option{expose_compute_option_}, system{system_} { vulkan_device = Settings::values.vulkan_device.GetValue(); RetrieveVulkanDevices(); diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index be9310b74..adc3faffa 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -13,6 +13,7 @@ #include #include "common/common_types.h" #include "vk_device_info.h" +#include "yuzu/configuration/configuration_shared.h" class QEvent; class QObject; @@ -27,26 +28,21 @@ namespace Core { class System; } -namespace ConfigurationShared { -enum class CheckState; -} - namespace Ui { class ConfigureGraphics; } -class ConfigureGraphics : public QWidget { - Q_OBJECT - +class ConfigureGraphics : public ConfigurationShared::Tab { public: explicit ConfigureGraphics(const Core::System& system_, std::vector& records, const std::function& expose_compute_option_, + std::shared_ptr> group, QWidget* parent = nullptr); ~ConfigureGraphics() override; - void ApplyConfiguration(); - void SetConfiguration(); + void ApplyConfiguration() override; + void SetConfiguration() override; private: void changeEvent(QEvent* event) override; diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index e5c99f742..d332c9b7b 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -7,8 +7,10 @@ #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_graphics_advanced.h" -ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced(const Core::System& system_, QWidget* parent) - : QWidget(parent), ui{std::make_unique()}, system{system_} { +ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced( + const Core::System& system_, + std::shared_ptr> group, QWidget* parent) + : Tab(group, parent), ui{std::make_unique()}, system{system_} { ui->setupUi(this); diff --git a/src/yuzu/configuration/configure_graphics_advanced.h b/src/yuzu/configuration/configure_graphics_advanced.h index 369a7c83e..585b9cb50 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.h +++ b/src/yuzu/configuration/configure_graphics_advanced.h @@ -5,28 +5,26 @@ #include #include +#include "yuzu/configuration/configuration_shared.h" namespace Core { class System; } -namespace ConfigurationShared { -enum class CheckState; -} - namespace Ui { class ConfigureGraphicsAdvanced; } -class ConfigureGraphicsAdvanced : public QWidget { - Q_OBJECT - +class ConfigureGraphicsAdvanced : public ConfigurationShared::Tab { public: - explicit ConfigureGraphicsAdvanced(const Core::System& system_, QWidget* parent = nullptr); + explicit ConfigureGraphicsAdvanced( + const Core::System& system_, + std::shared_ptr> group, + QWidget* parent = nullptr); ~ConfigureGraphicsAdvanced() override; - void ApplyConfiguration(); - void SetConfiguration(); + void ApplyConfiguration() override; + void SetConfiguration() override; void ExposeComputeOption(); diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index eb96e6068..c54d7e76f 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -24,6 +24,7 @@ #include "core/loader/loader.h" #include "ui_configure_per_game.h" #include "yuzu/configuration/config.h" +#include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_audio.h" #include "yuzu/configuration/configure_cpu.h" #include "yuzu/configuration/configure_general.h" @@ -40,22 +41,23 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::string& file_name, std::vector& vk_device_records, Core::System& system_) - : QDialog(parent), - ui(std::make_unique()), title_id{title_id_}, system{system_} { + : QDialog(parent), ui(std::make_unique()), title_id{title_id_}, + system{system_}, group{std::make_shared>()} { const auto file_path = std::filesystem::path(Common::FS::ToU8String(file_name)); const auto config_file_name = title_id == 0 ? Common::FS::PathToUTF8String(file_path.filename()) : fmt::format("{:016X}", title_id); game_config = std::make_unique(config_file_name, Config::ConfigType::PerGameConfig); addons_tab = std::make_unique(system_, this); - audio_tab = std::make_unique(system_, this); - cpu_tab = std::make_unique(system_, this); - general_tab = std::make_unique(system_, this); - graphics_advanced_tab = std::make_unique(system_, this); + audio_tab = std::make_unique(system_, group, this); + cpu_tab = std::make_unique(system_, group, this); + general_tab = std::make_unique(system_, group, this); + graphics_advanced_tab = std::make_unique(system_, group, this); graphics_tab = std::make_unique( - system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, this); + system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, group, + this); input_tab = std::make_unique(system_, game_config.get(), this); - system_tab = std::make_unique(system_, this); + system_tab = std::make_unique(system_, group, this); ui->setupUi(this); @@ -88,13 +90,10 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st ConfigurePerGame::~ConfigurePerGame() = default; void ConfigurePerGame::ApplyConfiguration() { + for (const auto tab : *group) { + tab->ApplyConfiguration(); + } addons_tab->ApplyConfiguration(); - general_tab->ApplyConfiguration(); - cpu_tab->ApplyConfiguration(); - system_tab->ApplyConfiguration(); - graphics_tab->ApplyConfiguration(); - graphics_advanced_tab->ApplyConfiguration(); - audio_tab->ApplyConfiguration(); input_tab->ApplyConfiguration(); system.ApplySettings(); diff --git a/src/yuzu/configuration/configure_per_game.h b/src/yuzu/configuration/configure_per_game.h index 7ec1ded06..5326e70e6 100644 --- a/src/yuzu/configuration/configure_per_game.h +++ b/src/yuzu/configuration/configure_per_game.h @@ -3,6 +3,7 @@ #pragma once +#include #include #include #include @@ -13,6 +14,7 @@ #include "core/file_sys/vfs_types.h" #include "vk_device_info.h" #include "yuzu/configuration/config.h" +#include "yuzu/configuration/configuration_shared.h" namespace Core { class System; @@ -73,7 +75,7 @@ private: std::unique_ptr game_config; Core::System& system; - + std::shared_ptr> group; std::unique_ptr addons_tab; std::unique_ptr audio_tab; std::unique_ptr cpu_tab; diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index c892635b8..4872a475b 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -37,8 +37,10 @@ static bool IsValidLocale(u32 region_index, u32 language_index) { return ((LOCALE_BLOCKLIST.at(region_index) >> language_index) & 1) == 0; } -ConfigureSystem::ConfigureSystem(Core::System& system_, QWidget* parent) - : QWidget(parent), ui{std::make_unique()}, system{system_} { +ConfigureSystem::ConfigureSystem( + Core::System& system_, std::shared_ptr> group, + QWidget* parent) + : Tab(group, parent), ui{std::make_unique()}, system{system_} { ui->setupUi(this); connect(ui->rng_seed_checkbox, &QCheckBox::stateChanged, this, [this](int state) { diff --git a/src/yuzu/configuration/configure_system.h b/src/yuzu/configuration/configure_system.h index ce1a91601..6064b5b40 100644 --- a/src/yuzu/configuration/configure_system.h +++ b/src/yuzu/configuration/configure_system.h @@ -6,28 +6,25 @@ #include #include +#include "yuzu/configuration/configuration_shared.h" namespace Core { class System; } -namespace ConfigurationShared { -enum class CheckState; -} - namespace Ui { class ConfigureSystem; } -class ConfigureSystem : public QWidget { - Q_OBJECT - +class ConfigureSystem : public ConfigurationShared::Tab { public: - explicit ConfigureSystem(Core::System& system_, QWidget* parent = nullptr); + explicit ConfigureSystem(Core::System& system_, + std::shared_ptr> group, + QWidget* parent = nullptr); ~ConfigureSystem() override; - void ApplyConfiguration(); - void SetConfiguration(); + void ApplyConfiguration() override; + void SetConfiguration() override; private: void changeEvent(QEvent* event) override; From b11b4be7cb764bc0c1aa6c563ccf41a3d1b335dd Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 5 May 2023 23:31:24 -0400 Subject: [PATCH 008/155] configure_per_game: Rename group to tab_group --- src/yuzu/configuration/configure_per_game.cpp | 18 +++++++++--------- src/yuzu/configuration/configure_per_game.h | 3 ++- 2 files changed, 11 insertions(+), 10 deletions(-) diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index c54d7e76f..7ec0bf9d3 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -42,22 +42,22 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st std::vector& vk_device_records, Core::System& system_) : QDialog(parent), ui(std::make_unique()), title_id{title_id_}, - system{system_}, group{std::make_shared>()} { + system{system_}, tab_group{std::make_shared>()} { const auto file_path = std::filesystem::path(Common::FS::ToU8String(file_name)); const auto config_file_name = title_id == 0 ? Common::FS::PathToUTF8String(file_path.filename()) : fmt::format("{:016X}", title_id); game_config = std::make_unique(config_file_name, Config::ConfigType::PerGameConfig); addons_tab = std::make_unique(system_, this); - audio_tab = std::make_unique(system_, group, this); - cpu_tab = std::make_unique(system_, group, this); - general_tab = std::make_unique(system_, group, this); - graphics_advanced_tab = std::make_unique(system_, group, this); + audio_tab = std::make_unique(system_, tab_group, this); + cpu_tab = std::make_unique(system_, tab_group, this); + general_tab = std::make_unique(system_, tab_group, this); + graphics_advanced_tab = std::make_unique(system_, tab_group, this); graphics_tab = std::make_unique( - system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, group, - this); + system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, + tab_group, this); input_tab = std::make_unique(system_, game_config.get(), this); - system_tab = std::make_unique(system_, group, this); + system_tab = std::make_unique(system_, tab_group, this); ui->setupUi(this); @@ -90,7 +90,7 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st ConfigurePerGame::~ConfigurePerGame() = default; void ConfigurePerGame::ApplyConfiguration() { - for (const auto tab : *group) { + for (const auto tab : *tab_group) { tab->ApplyConfiguration(); } addons_tab->ApplyConfiguration(); diff --git a/src/yuzu/configuration/configure_per_game.h b/src/yuzu/configuration/configure_per_game.h index 5326e70e6..9fceff414 100644 --- a/src/yuzu/configuration/configure_per_game.h +++ b/src/yuzu/configuration/configure_per_game.h @@ -75,7 +75,8 @@ private: std::unique_ptr game_config; Core::System& system; - std::shared_ptr> group; + std::shared_ptr> tab_group; + std::unique_ptr addons_tab; std::unique_ptr audio_tab; std::unique_ptr cpu_tab; From a007ac6b9ccc23861f5a5c6967d535220ed794b0 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 7 May 2023 09:48:26 -0400 Subject: [PATCH 009/155] configure_graphics_advance: Generate UI at runtime We can iterate through the AdvancedGraphics settings and generate the UI during runtime. This doesn't help runtime efficiency, but it helps a ton in reducing the amount of work a developer needs in order to add a new setting. --- src/common/settings.h | 53 +++- src/core/telemetry_session.cpp | 2 + src/video_core/textures/texture.cpp | 4 +- src/yuzu/CMakeLists.txt | 2 + .../configuration/configuration_shared.cpp | 153 ++++++++++++ src/yuzu/configuration/configuration_shared.h | 6 + src/yuzu/configuration/configure_dialog.cpp | 8 +- src/yuzu/configuration/configure_dialog.h | 1 + .../configure_graphics_advanced.cpp | 168 +++---------- .../configure_graphics_advanced.h | 20 +- .../configure_graphics_advanced.ui | 234 +----------------- src/yuzu/configuration/configure_per_game.cpp | 9 +- src/yuzu/configuration/configure_per_game.h | 1 + src/yuzu/configuration/shared_translation.cpp | 170 +++++++++++++ src/yuzu/configuration/shared_translation.h | 18 ++ 15 files changed, 449 insertions(+), 400 deletions(-) create mode 100644 src/yuzu/configuration/shared_translation.cpp create mode 100644 src/yuzu/configuration/shared_translation.h diff --git a/src/common/settings.h b/src/common/settings.h index df4bcb053..48f86d0aa 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -20,6 +20,15 @@ namespace Settings { +enum class AnisotropyMode : u32 { + Automatic = 0, + Default = 1, + X2 = 2, + X4 = 3, + X8 = 4, + X16 = 5, +}; + enum class AstcDecodeMode : u32 { CPU = 0, GPU = 1, @@ -49,6 +58,7 @@ enum class GPUAccuracy : u32 { Normal = 0, High = 1, Extreme = 2, + MaxEnum = 3, }; enum class CPUAccuracy : u32 { @@ -166,11 +176,16 @@ public: virtual Category Category() const = 0; virtual constexpr bool Switchable() const = 0; virtual std::string ToString() const = 0; + virtual std::string ToStringGlobal() const { + return {}; + } virtual void LoadString(const std::string& load) = 0; virtual const std::string& GetLabel() const = 0; virtual std::string DefaultToString() const = 0; virtual bool Save() const = 0; virtual std::type_index TypeId() const = 0; + virtual bool IsEnum() const = 0; + virtual bool RuntimeModfiable() const = 0; virtual void SetGlobal(bool global) {} virtual bool UsingGlobal() const { return false; @@ -188,7 +203,7 @@ public: * configurations. Specifying a default value and label is required. A minimum and maximum range * can be specified for sanitization. */ -template +template class Setting : public BasicSetting { protected: Setting() = default; @@ -282,6 +297,14 @@ public: return category; } + [[nodiscard]] bool RuntimeModfiable() const override { + return runtime_modifiable; + } + + [[nodiscard]] bool IsEnum() const override { + return std::is_enum::value; + } + /** * Returns whether the current setting is Switchable. * @@ -291,7 +314,7 @@ public: return false; } -private: +protected: std::string ToString(const Type& value_) const { if constexpr (std::is_same()) { return value_; @@ -408,8 +431,8 @@ protected: * * By default, the global setting is used. */ -template -class SwitchableSetting : virtual public Setting { +template +class SwitchableSetting : virtual public Setting { public: /** * Sets a default value, label, and setting value. @@ -422,7 +445,7 @@ public: explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, Category category) requires(!ranged) - : Setting{linkage, default_val, name, category} { + : Setting{linkage, default_val, name, category} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } virtual ~SwitchableSetting() = default; @@ -440,7 +463,8 @@ public: explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, Category category) requires(ranged) - : Setting{linkage, default_val, min_val, max_val, name, category} { + : Setting{linkage, default_val, min_val, + max_val, name, category} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } @@ -502,6 +526,10 @@ public: return true; } + [[nodiscard]] virtual std::string ToStringGlobal() const override { + return this->ToString(this->value); + } + /** * Assigns the current setting value depending on the global state. * @@ -667,15 +695,16 @@ struct Values { "fullscreen_mode", Category::Renderer}; SwitchableSetting aspect_ratio{linkage, 0, 0, 4, "aspect_ratio", Category::Renderer}; - SwitchableSetting max_anisotropy{ - linkage, 0, 0, 5, "max_anisotropy", Category::AdvancedGraphics}; + SwitchableSetting max_anisotropy{ + linkage, AnisotropyMode::Automatic, AnisotropyMode::Automatic, AnisotropyMode::X16, + "max_anisotropy", Category::AdvancedGraphics}; SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", Category::Renderer}; SwitchableSetting speed_limit{linkage, 100, 0, 9999, "speed_limit", Category::Renderer}; SwitchableSetting use_disk_shader_cache{linkage, true, "use_disk_shader_cache", Category::Renderer}; - SwitchableSetting gpu_accuracy{ + SwitchableSetting gpu_accuracy{ linkage, GPUAccuracy::High, GPUAccuracy::Normal, GPUAccuracy::Extreme, "gpu_accuracy", Category::AdvancedGraphics}; SwitchableSetting use_asynchronous_gpu_emulation{ @@ -698,9 +727,9 @@ struct Values { "shader_backend", Category::Renderer}; SwitchableSetting use_asynchronous_shaders{linkage, false, "use_asynchronous_shaders", Category::Renderer}; - SwitchableSetting use_fast_gpu_time{linkage, true, "use_fast_gpu_time", - Category::AdvancedGraphics}; - SwitchableSetting use_vulkan_driver_pipeline_cache{ + SwitchableSetting use_fast_gpu_time{linkage, true, "use_fast_gpu_time", + Category::AdvancedGraphics}; + SwitchableSetting use_vulkan_driver_pipeline_cache{ linkage, true, "use_vulkan_driver_pipeline_cache", Category::AdvancedGraphics}; SwitchableSetting enable_compute_pipelines{linkage, false, "enable_compute_pipelines", Category::AdvancedGraphics}; diff --git a/src/core/telemetry_session.cpp b/src/core/telemetry_session.cpp index 665ffe3a2..a3505a505 100644 --- a/src/core/telemetry_session.cpp +++ b/src/core/telemetry_session.cpp @@ -69,6 +69,8 @@ static const char* TranslateGPUAccuracyLevel(Settings::GPUAccuracy backend) { return "High"; case Settings::GPUAccuracy::Extreme: return "Extreme"; + case Settings::GPUAccuracy::MaxEnum: + break; } return "Unknown"; } diff --git a/src/video_core/textures/texture.cpp b/src/video_core/textures/texture.cpp index d8b88d9bc..39c08b5ae 100644 --- a/src/video_core/textures/texture.cpp +++ b/src/video_core/textures/texture.cpp @@ -72,12 +72,12 @@ float TSCEntry::MaxAnisotropy() const noexcept { } const auto anisotropic_settings = Settings::values.max_anisotropy.GetValue(); s32 added_anisotropic{}; - if (anisotropic_settings == 0) { + if (anisotropic_settings == Settings::AnisotropyMode::Automatic) { added_anisotropic = Settings::values.resolution_info.up_scale >> Settings::values.resolution_info.down_shift; added_anisotropic = std::max(added_anisotropic - 1, 0); } else { - added_anisotropic = Settings::values.max_anisotropy.GetValue() - 1U; + added_anisotropic = static_cast(Settings::values.max_anisotropy.GetValue()) - 1U; } return static_cast(1U << (max_anisotropy + added_anisotropic)); } diff --git a/src/yuzu/CMakeLists.txt b/src/yuzu/CMakeLists.txt index fe98e3605..8b54e1268 100644 --- a/src/yuzu/CMakeLists.txt +++ b/src/yuzu/CMakeLists.txt @@ -143,6 +143,8 @@ add_executable(yuzu configuration/configure_web.ui configuration/input_profiles.cpp configuration/input_profiles.h + configuration/shared_translation.cpp + configuration/shared_translation.h debugger/console.cpp debugger/console.h debugger/controller.cpp diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 72b7957e0..44222718c 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -3,14 +3,167 @@ #include #include +#include +#include #include #include #include +#include #include "common/settings.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_per_game.h" +#include "yuzu/configuration/shared_translation.h" namespace ConfigurationShared { +static std::pair> CreateCheckBox(Settings::BasicSetting* setting, + const QString& label, + QWidget* parent, + std::list& trackers) { + QCheckBox* checkbox = new QCheckBox(label, parent); + checkbox->setObjectName(QString::fromStdString(setting->GetLabel())); + checkbox->setCheckState(setting->ToString() == "true" ? Qt::CheckState::Checked + : Qt::CheckState::Unchecked); + + CheckState* tracker{}; + + // Per-game config highlight + if (setting->Switchable() && !Settings::IsConfiguringGlobal()) { + bool global_state = setting->ToStringGlobal() == "true"; + bool state = setting->ToString() == "true"; + bool global = setting->UsingGlobal(); + tracker = &trackers.emplace_front(CheckState{}); + SetColoredTristate(checkbox, global, state, global_state, *tracker); + } + + auto load_func = [checkbox, setting, tracker]() { + if (Settings::IsConfiguringGlobal()) { + setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + } + + if (Settings::IsConfiguringGlobal() || !setting->Switchable()) { + return; + } + + if (*tracker != CheckState::Global) { + setting->SetGlobal(false); + setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + } else { + setting->SetGlobal(true); + } + }; + + return {checkbox, load_func}; +} + +static std::pair> CreateCombobox(Settings::BasicSetting* setting, + const QString& label, + QWidget* parent) { + const auto type = setting->TypeId(); + + QWidget* group = new QWidget(parent); + group->setObjectName(QString::fromStdString(setting->GetLabel())); + QLayout* combobox_layout = new QHBoxLayout(group); + + QLabel* qt_label = new QLabel(label, parent); + QComboBox* combobox = new QComboBox(parent); + + std::forward_list combobox_enumerations = ComboboxEnumeration(type, parent); + for (const auto& item : combobox_enumerations) { + combobox->addItem(item); + } + + combobox_layout->addWidget(qt_label); + combobox_layout->addWidget(combobox); + + combobox_layout->setSpacing(6); + combobox_layout->setContentsMargins(0, 0, 0, 0); + + if (setting->Switchable() && !Settings::IsConfiguringGlobal()) { + int current = std::stoi(setting->ToString()); + int global_value = std::stoi(setting->ToStringGlobal()); + SetColoredComboBox(combobox, group, global_value); + if (setting->UsingGlobal()) { + combobox->setCurrentIndex(USE_GLOBAL_INDEX); + } else { + SetHighlight(group, true); + combobox->setCurrentIndex(current + USE_GLOBAL_OFFSET); + } + } else { + combobox->setCurrentIndex(std::stoi(setting->ToString())); + } + + const auto load_func = [combobox, setting]() { + if (Settings::IsConfiguringGlobal()) { + setting->LoadString(std::to_string(combobox->currentIndex())); + } + + if (Settings::IsConfiguringGlobal() || !setting->Switchable()) { + return; + } + + bool using_global = combobox->currentIndex() == USE_GLOBAL_INDEX; + int index = combobox->currentIndex() - USE_GLOBAL_OFFSET; + + setting->SetGlobal(using_global); + if (!using_global) { + setting->LoadString(std::to_string(index)); + } + }; + + return {group, load_func}; +} + +QWidget* CreateWidget(Settings::BasicSetting* setting, const TranslationMap& translations, + QWidget* parent, bool runtime_lock, + std::forward_list>& apply_funcs, + std::list& trackers) { + const auto type = setting->TypeId(); + QWidget* widget{nullptr}; + + std::function load_func; + + const auto [label, tooltip] = [&]() { + const auto& setting_label = setting->GetLabel(); + if (translations.contains(setting_label)) { + return std::pair{translations.at(setting_label).first, + translations.at(setting_label).second}; + } + LOG_ERROR(Frontend, "Translation map lacks entry for \"{}\"", setting_label); + return std::pair{QString::fromStdString(setting_label), QStringLiteral("")}; + }(); + + if (type == typeid(bool)) { + auto pair = CreateCheckBox(setting, label, parent, trackers); + widget = pair.first; + load_func = pair.second; + } else if (setting->IsEnum()) { + auto pair = CreateCombobox(setting, label, parent); + widget = pair.first; + load_func = pair.second; + } + + if (widget == nullptr) { + LOG_ERROR(Frontend, "No widget was created for \"{}\"", setting->GetLabel()); + return widget; + } + + apply_funcs.push_front([load_func, setting](bool powered_on) { + if (setting->RuntimeModfiable() || !powered_on) { + load_func(); + } + }); + + bool enable = runtime_lock || setting->RuntimeModfiable(); + enable &= + setting->Switchable() && !(Settings::IsConfiguringGlobal() && !setting->UsingGlobal()); + + widget->setEnabled(enable); + widget->setVisible(Settings::IsConfiguringGlobal() || setting->Switchable()); + + widget->setToolTip(tooltip); + + return widget; +} Tab::Tab(std::shared_ptr> group_, QWidget* parent) : QWidget(parent), group{group_} { diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 1a3a2a985..7040673ea 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -11,6 +11,7 @@ #include #include #include "common/settings.h" +#include "yuzu/configuration/shared_translation.h" namespace ConfigurationShared { @@ -40,6 +41,11 @@ enum class CheckState { Count, // Simply the number of states, not a valid checkbox state }; +QWidget* CreateWidget(Settings::BasicSetting* setting, const TranslationMap& translations, + QWidget* parent, bool runtime_lock, + std::forward_list>& apply_funcs, + std::list& trackers); + // Global-aware apply and set functions // ApplyPerGameSetting, given a Settings::Setting and a Qt UI element, properly applies a Setting diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index 2cc9f3621..b3f4764c7 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -32,13 +32,15 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, std::vector& vk_device_records, Core::System& system_, bool enable_web_config) : QDialog(parent), ui{std::make_unique()}, - registry(registry_), system{system_}, audio_tab{std::make_unique( - system_, nullptr, this)}, + registry(registry_), system{system_}, + translations{ConfigurationShared::InitializeTranslations(this)}, + audio_tab{std::make_unique(system_, nullptr, this)}, cpu_tab{std::make_unique(system_, nullptr, this)}, debug_tab_tab{std::make_unique(system_, this)}, filesystem_tab{std::make_unique(this)}, general_tab{std::make_unique(system_, nullptr, this)}, - graphics_advanced_tab{std::make_unique(system_, nullptr, this)}, + graphics_advanced_tab{ + std::make_unique(system_, nullptr, *translations, this)}, graphics_tab{std::make_unique( system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, nullptr, this)}, diff --git a/src/yuzu/configuration/configure_dialog.h b/src/yuzu/configuration/configure_dialog.h index 8ee89a192..0416b01d9 100644 --- a/src/yuzu/configuration/configure_dialog.h +++ b/src/yuzu/configuration/configure_dialog.h @@ -71,6 +71,7 @@ private: HotkeyRegistry& registry; Core::System& system; + std::unique_ptr translations; std::forward_list tab_group; std::unique_ptr audio_tab; diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index d332c9b7b..6d387b5c3 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -1,6 +1,8 @@ // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#include +#include #include "common/settings.h" #include "core/core.h" #include "ui_configure_graphics_advanced.h" @@ -9,94 +11,54 @@ ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced( const Core::System& system_, - std::shared_ptr> group, QWidget* parent) - : Tab(group, parent), ui{std::make_unique()}, system{system_} { + std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, QWidget* parent) + : Tab(group, parent), ui{std::make_unique()}, system{system_}, + translations{translations_} { ui->setupUi(this); - SetupPerGameUI(); - SetConfiguration(); - ui->enable_compute_pipelines_checkbox->setVisible(false); + checkbox_enable_compute_pipelines->setVisible(false); } ConfigureGraphicsAdvanced::~ConfigureGraphicsAdvanced() = default; void ConfigureGraphicsAdvanced::SetConfiguration() { const bool runtime_lock = !system.IsPoweredOn(); - ui->use_reactive_flushing->setEnabled(runtime_lock); - ui->async_present->setEnabled(runtime_lock); - ui->renderer_force_max_clock->setEnabled(runtime_lock); - ui->astc_recompression_combobox->setEnabled(runtime_lock); - ui->use_asynchronous_shaders->setEnabled(runtime_lock); - ui->anisotropic_filtering_combobox->setEnabled(runtime_lock); - ui->enable_compute_pipelines_checkbox->setEnabled(runtime_lock); + auto& layout = *ui->populate_target->layout(); + std::map hold{}; // A map will sort the data for us - ui->async_present->setChecked(Settings::values.async_presentation.GetValue()); - ui->renderer_force_max_clock->setChecked(Settings::values.renderer_force_max_clock.GetValue()); - ui->use_reactive_flushing->setChecked(Settings::values.use_reactive_flushing.GetValue()); - ui->use_asynchronous_shaders->setChecked(Settings::values.use_asynchronous_shaders.GetValue()); - ui->use_fast_gpu_time->setChecked(Settings::values.use_fast_gpu_time.GetValue()); - ui->use_vulkan_driver_pipeline_cache->setChecked( - Settings::values.use_vulkan_driver_pipeline_cache.GetValue()); - ui->enable_compute_pipelines_checkbox->setChecked( - Settings::values.enable_compute_pipelines.GetValue()); - ui->use_video_framerate_checkbox->setChecked(Settings::values.use_video_framerate.GetValue()); - ui->barrier_feedback_loops_checkbox->setChecked( - Settings::values.barrier_feedback_loops.GetValue()); + for (auto setting : + Settings::values.linkage.by_category[Settings::Category::AdvancedGraphics]) { + QWidget* widget = ConfigurationShared::CreateWidget(setting, translations, this, + runtime_lock, apply_funcs, trackers); - if (Settings::IsConfiguringGlobal()) { - ui->gpu_accuracy->setCurrentIndex( - static_cast(Settings::values.gpu_accuracy.GetValue())); - ui->anisotropic_filtering_combobox->setCurrentIndex( - Settings::values.max_anisotropy.GetValue()); - ui->astc_recompression_combobox->setCurrentIndex( - static_cast(Settings::values.astc_recompression.GetValue())); - } else { - ConfigurationShared::SetPerGameSetting(ui->gpu_accuracy, &Settings::values.gpu_accuracy); - ConfigurationShared::SetPerGameSetting(ui->anisotropic_filtering_combobox, - &Settings::values.max_anisotropy); - ConfigurationShared::SetPerGameSetting(ui->astc_recompression_combobox, - &Settings::values.astc_recompression); - ConfigurationShared::SetHighlight(ui->label_gpu_accuracy, - !Settings::values.gpu_accuracy.UsingGlobal()); - ConfigurationShared::SetHighlight(ui->af_label, - !Settings::values.max_anisotropy.UsingGlobal()); - ConfigurationShared::SetHighlight(ui->label_astc_recompression, - !Settings::values.astc_recompression.UsingGlobal()); + if (widget == nullptr) { + continue; + } + + if (!setting->IsEnum()) { + hold.emplace(setting->GetLabel(), widget); + } else { + layout.addWidget(widget); + } + + if (setting->GetLabel() == "enable_compute_pipelines") { + checkbox_enable_compute_pipelines = widget; + } + } + for (const auto& [label, widget] : hold) { + layout.addWidget(widget); } } void ConfigureGraphicsAdvanced::ApplyConfiguration() { - ConfigurationShared::ApplyPerGameSetting(&Settings::values.gpu_accuracy, ui->gpu_accuracy); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.async_presentation, - ui->async_present, async_present); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.renderer_force_max_clock, - ui->renderer_force_max_clock, - renderer_force_max_clock); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.max_anisotropy, - ui->anisotropic_filtering_combobox); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_reactive_flushing, - ui->use_reactive_flushing, use_reactive_flushing); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.astc_recompression, - ui->astc_recompression_combobox); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_asynchronous_shaders, - ui->use_asynchronous_shaders, - use_asynchronous_shaders); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_fast_gpu_time, - ui->use_fast_gpu_time, use_fast_gpu_time); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_vulkan_driver_pipeline_cache, - ui->use_vulkan_driver_pipeline_cache, - use_vulkan_driver_pipeline_cache); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.enable_compute_pipelines, - ui->enable_compute_pipelines_checkbox, - enable_compute_pipelines); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_video_framerate, - ui->use_video_framerate_checkbox, use_video_framerate); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.barrier_feedback_loops, - ui->barrier_feedback_loops_checkbox, - barrier_feedback_loops); + const bool is_powered_on = system.IsPoweredOn(); + for (const auto& func : apply_funcs) { + func(is_powered_on); + } } void ConfigureGraphicsAdvanced::changeEvent(QEvent* event) { @@ -111,68 +73,6 @@ void ConfigureGraphicsAdvanced::RetranslateUI() { ui->retranslateUi(this); } -void ConfigureGraphicsAdvanced::SetupPerGameUI() { - // Disable if not global (only happens during game) - if (Settings::IsConfiguringGlobal()) { - ui->gpu_accuracy->setEnabled(Settings::values.gpu_accuracy.UsingGlobal()); - ui->async_present->setEnabled(Settings::values.async_presentation.UsingGlobal()); - ui->renderer_force_max_clock->setEnabled( - Settings::values.renderer_force_max_clock.UsingGlobal()); - ui->use_reactive_flushing->setEnabled(Settings::values.use_reactive_flushing.UsingGlobal()); - ui->astc_recompression_combobox->setEnabled( - Settings::values.astc_recompression.UsingGlobal()); - ui->use_asynchronous_shaders->setEnabled( - Settings::values.use_asynchronous_shaders.UsingGlobal()); - ui->use_fast_gpu_time->setEnabled(Settings::values.use_fast_gpu_time.UsingGlobal()); - ui->use_vulkan_driver_pipeline_cache->setEnabled( - Settings::values.use_vulkan_driver_pipeline_cache.UsingGlobal()); - ui->anisotropic_filtering_combobox->setEnabled( - Settings::values.max_anisotropy.UsingGlobal()); - ui->enable_compute_pipelines_checkbox->setEnabled( - Settings::values.enable_compute_pipelines.UsingGlobal()); - ui->use_video_framerate_checkbox->setEnabled( - Settings::values.use_video_framerate.UsingGlobal()); - ui->barrier_feedback_loops_checkbox->setEnabled( - Settings::values.barrier_feedback_loops.UsingGlobal()); - - return; - } - - ConfigurationShared::SetColoredTristate(ui->async_present, Settings::values.async_presentation, - async_present); - ConfigurationShared::SetColoredTristate(ui->renderer_force_max_clock, - Settings::values.renderer_force_max_clock, - renderer_force_max_clock); - ConfigurationShared::SetColoredTristate( - ui->use_reactive_flushing, Settings::values.use_reactive_flushing, use_reactive_flushing); - ConfigurationShared::SetColoredTristate(ui->use_asynchronous_shaders, - Settings::values.use_asynchronous_shaders, - use_asynchronous_shaders); - ConfigurationShared::SetColoredTristate(ui->use_fast_gpu_time, - Settings::values.use_fast_gpu_time, use_fast_gpu_time); - ConfigurationShared::SetColoredTristate(ui->use_vulkan_driver_pipeline_cache, - Settings::values.use_vulkan_driver_pipeline_cache, - use_vulkan_driver_pipeline_cache); - ConfigurationShared::SetColoredTristate(ui->enable_compute_pipelines_checkbox, - Settings::values.enable_compute_pipelines, - enable_compute_pipelines); - ConfigurationShared::SetColoredTristate(ui->use_video_framerate_checkbox, - Settings::values.use_video_framerate, - use_video_framerate); - ConfigurationShared::SetColoredTristate(ui->barrier_feedback_loops_checkbox, - Settings::values.barrier_feedback_loops, - barrier_feedback_loops); - ConfigurationShared::SetColoredComboBox( - ui->gpu_accuracy, ui->label_gpu_accuracy, - static_cast(Settings::values.gpu_accuracy.GetValue(true))); - ConfigurationShared::SetColoredComboBox( - ui->anisotropic_filtering_combobox, ui->af_label, - static_cast(Settings::values.max_anisotropy.GetValue(true))); - ConfigurationShared::SetColoredComboBox( - ui->astc_recompression_combobox, ui->label_astc_recompression, - static_cast(Settings::values.astc_recompression.GetValue(true))); -} - void ConfigureGraphicsAdvanced::ExposeComputeOption() { - ui->enable_compute_pipelines_checkbox->setVisible(true); + checkbox_enable_compute_pipelines->setVisible(true); } diff --git a/src/yuzu/configuration/configure_graphics_advanced.h b/src/yuzu/configuration/configure_graphics_advanced.h index 585b9cb50..3ac6b4bce 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.h +++ b/src/yuzu/configuration/configure_graphics_advanced.h @@ -20,7 +20,7 @@ public: explicit ConfigureGraphicsAdvanced( const Core::System& system_, std::shared_ptr> group, - QWidget* parent = nullptr); + const ConfigurationShared::TranslationMap& translations_, QWidget* parent = nullptr); ~ConfigureGraphicsAdvanced() override; void ApplyConfiguration() override; @@ -32,21 +32,13 @@ private: void changeEvent(QEvent* event) override; void RetranslateUI(); - void SetupPerGameUI(); - std::unique_ptr ui; - ConfigurationShared::CheckState async_present; - ConfigurationShared::CheckState renderer_force_max_clock; - ConfigurationShared::CheckState use_vsync; - ConfigurationShared::CheckState async_astc; - ConfigurationShared::CheckState use_reactive_flushing; - ConfigurationShared::CheckState use_asynchronous_shaders; - ConfigurationShared::CheckState use_fast_gpu_time; - ConfigurationShared::CheckState use_vulkan_driver_pipeline_cache; - ConfigurationShared::CheckState enable_compute_pipelines; - ConfigurationShared::CheckState use_video_framerate; - ConfigurationShared::CheckState barrier_feedback_loops; + std::list trackers{}; const Core::System& system; + const ConfigurationShared::TranslationMap& translations; + std::forward_list> apply_funcs; + + QWidget* checkbox_enable_compute_pipelines{}; }; diff --git a/src/yuzu/configuration/configure_graphics_advanced.ui b/src/yuzu/configuration/configure_graphics_advanced.ui index 859ab9366..113fbc010 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.ui +++ b/src/yuzu/configuration/configure_graphics_advanced.ui @@ -26,238 +26,8 @@ - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Accuracy Level: - - - - - - - - Normal - - - - - High - - - - - Extreme(very slow) - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - ASTC recompression: - - - - - - - - Uncompressed (Best quality) - - - - - BC1 (Low quality) - - - - - BC3 (Medium quality) - - - - - - - - - - - Enable asynchronous presentation (Vulkan only) - - - - - - - Runs work in the background while waiting for graphics commands to keep the GPU from lowering its clock speed. - - - Force maximum clocks (Vulkan only) - - - - - - - Uses reactive flushing instead of predictive flushing. Allowing a more accurate syncing of memory. - - - Enable Reactive Flushing - - - - - - - Enables asynchronous shader compilation, which may reduce shader stutter. This feature is experimental. - - - Use asynchronous shader building (Hack) - - - - - - - Enables Fast GPU Time. This option will force most games to run at their highest native resolution. - - - Use Fast GPU Time (Hack) - - - - - - - Enables GPU vendor-specific pipeline cache. This option can improve shader loading time significantly in cases where the Vulkan driver does not store pipeline cache files internally. - - - Use Vulkan pipeline cache - - - - - - - Enable compute pipelines, required by some games. This setting only exists for Intel proprietary drivers, and may crash if enabled. -Compute pipelines are always enabled on all other drivers. - - - Enable Compute Pipelines (Intel Vulkan only) - - - - - - - Run the game at normal speed during video playback, even when the framerate is unlocked. - - - Sync to framerate of video playback - - - - - - - Improves rendering of transparency effects in specific games. - - - Barrier feedback loops - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Anisotropic Filtering: - - - - - - - - Automatic - - - - - Default - - - - - 2x - - - - - 4x - - - - - 8x - - - - - 16x - - - - - + + diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index 7ec0bf9d3..339768017 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -41,8 +41,10 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::string& file_name, std::vector& vk_device_records, Core::System& system_) - : QDialog(parent), ui(std::make_unique()), title_id{title_id_}, - system{system_}, tab_group{std::make_shared>()} { + : QDialog(parent), + ui(std::make_unique()), title_id{title_id_}, system{system_}, + translations{ConfigurationShared::InitializeTranslations(this)}, + tab_group{std::make_shared>()} { const auto file_path = std::filesystem::path(Common::FS::ToU8String(file_name)); const auto config_file_name = title_id == 0 ? Common::FS::PathToUTF8String(file_path.filename()) : fmt::format("{:016X}", title_id); @@ -52,7 +54,8 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st audio_tab = std::make_unique(system_, tab_group, this); cpu_tab = std::make_unique(system_, tab_group, this); general_tab = std::make_unique(system_, tab_group, this); - graphics_advanced_tab = std::make_unique(system_, tab_group, this); + graphics_advanced_tab = + std::make_unique(system_, tab_group, *translations, this); graphics_tab = std::make_unique( system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, tab_group, this); diff --git a/src/yuzu/configuration/configure_per_game.h b/src/yuzu/configuration/configure_per_game.h index 9fceff414..1e222c2f9 100644 --- a/src/yuzu/configuration/configure_per_game.h +++ b/src/yuzu/configuration/configure_per_game.h @@ -75,6 +75,7 @@ private: std::unique_ptr game_config; Core::System& system; + std::unique_ptr translations; std::shared_ptr> tab_group; std::unique_ptr addons_tab; diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp new file mode 100644 index 000000000..974203f75 --- /dev/null +++ b/src/yuzu/configuration/shared_translation.cpp @@ -0,0 +1,170 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include "common/settings.h" +#include "yuzu/configuration/shared_translation.h" + +namespace ConfigurationShared { + +std::unique_ptr InitializeTranslations(QWidget* parent) { + std::unique_ptr translations = std::make_unique(); + const auto& tr = [parent](const char* text) -> QString { return parent->tr(text); }; + +#define INSERT(LABEL, NAME, TOOLTIP) \ + translations->insert(std::pair{(LABEL), std::pair{tr((NAME)), tr((TOOLTIP))}}) + + // Audio + INSERT("output_engine", "Output Engine:", ""); + INSERT("output_device", "Output Device:", ""); + INSERT("input_device", "Input Device:", ""); + INSERT("audio_muted", "Mute audio when in background", ""); + INSERT("volume", "Volume:", ""); + + // Core + INSERT("use_multi_core", "Multicore CPU Emulation", ""); + INSERT("use_unsafe_extended_memory_layout", "Unsafe extended memory layout (8GB DRAM)", ""); + + // Cpu + INSERT("cpu_accuracy", "Accuracy:", ""); + INSERT("cpu_debug_mode", "Enable CPU Debugging", ""); + INSERT("cpuopt_page_tables", "Enable inline page tables", ""); + INSERT("cpuopt_block_linking", "Enable block linking", ""); + INSERT("cpuopt_return_stack_buffer", "Enable return stack buffer", ""); + INSERT("cpuopt_fast_dispatcher", "Enable fast dispatcher", ""); + INSERT("cpuopt_context_elimination", "Enable context elimination", ""); + INSERT("cpuopt_const_prop", "Enable constant propagation", ""); + INSERT("cpuopt_misc_ir", "Enable miscellaneous optimizations", ""); + INSERT("cpuopt_reduce_misalign_checks", "Enable misalignment check reduction", ""); + INSERT("cpuopt_fastmem", "Enable Host MMU Emulation (general memory instructions)", ""); + INSERT("cpuopt_fastmem_exclusives", "Enable Host MMU Emulation (exclusive memory instructions)", + ""); + INSERT("cpuopt_recompile_exclusives", "Enable recompilation of exlucsive memory instructions", + ""); + INSERT("cpuopt_ignore_memory_aborts", "Enable fallbacks for invalid memory accesses", ""); + + INSERT("cpuopt_unsafe_unfuse_fma", "Unfuse FMA (improve performance on CPUs without FMA)", ""); + INSERT("cpuopt_unsafe_reduce_fp_error", "Faster FRSQRTE and FRECPE", ""); + INSERT("cpuopt_unsafe_ignore_standard_fpcr", "Faster ASIMD instructions (32 bits only)", ""); + INSERT("cpuopt_unsafe_inaccurate_nan", "Inaccurate NaN handling", ""); + INSERT("cpuopt_unsafe_fastmem_check", "Disable address space checks", ""); + INSERT("cpuopt_unsafe_ignore_global_monitor", "Ignore global monitor", ""); + + // Renderer + INSERT("backend", "API:", ""); + INSERT("vulkan_device", "Device:", ""); + INSERT("shader_backend", "Shader Backend:", ""); + INSERT("resolution_setup", "Resolution:", ""); + INSERT("scaling_filter", "Window Adapting Filter:", ""); + INSERT("fsr_sharpening_slider", "AMD FidelityFX™ Super Resolution Sharpness:", ""); + INSERT("anti_aliasing", "Anti-Aliasing Method:", ""); + INSERT("fullscreen_mode", "Fullscreen Mode:", ""); + INSERT("aspect_ratio", "Aspect Ratio:", ""); + INSERT("use_disk_shader_cache", "Use disk pipeline cache", ""); + INSERT("use_asynchronous_gpu_emulation", "Use asynchronous GPU emulation", ""); + INSERT("nvdec_emulation", "NVDEC emulation:", ""); + INSERT("acclerate_astc", "ASTC Decoding Method:", ""); + INSERT( + "use_vsync", "VSync Mode:", + "FIFO (VSync) does not drop frames or exhibit tearing but is limited by the screen refresh " + "rate. FIFO Relaxed is similar to FIFO but allows tearing as it recovers from a slow down. " + "Mailbox can have lower latency than FIFO and does not tear but may drop frames. Immediate " + "(no synchronization) just presents whatever is available and can exhibit tearing."); + + // Renderer (Advanced Graphics) + INSERT("async_presentation", "Enable asynchronous presentation (Vulkan only)", ""); + INSERT("force_max_clock", "Force maximum clocks (Vulkan only)", + "Runs work in the background while waiting for graphics commands to keep the GPU from " + "lowering its clock speed."); + INSERT("max_anisotropy", "Anisotropic Filtering:", ""); + INSERT("gpu_accuracy", "Accuracy Level:", ""); + INSERT("use_asynchronous_shaders", "Use asynchronous shader building (Hack)", + "Enables asynchronous shader compilation, which may reduce shader stutter. This feature " + "is experimental."); + INSERT("use_fast_gpu_time", "Use Fast GPU Time (Hack)", + "Enables Fast GPU Time. This option will force most games to run at their highest " + "native resolution."); + INSERT("use_vulkan_driver_pipeline_cache", "Use Vulkan pipeline cache", + "Enables GPU vendor-specific pipeline cache. This option can improve shader loading " + "time significantly in cases where the Vulkan driver does not store pipeline cache " + "files internally."); + INSERT("enable_compute_pipelines", "Enable Compute Pipelines (Intel Vulkan Only)", + "Enable compute pipelines, required by some games.\nThis setting only exists for Intel " + "proprietary drivers, and may crash if enabled.\nCompute pipelines are always enabled " + "on all other drivers."); + INSERT("bg_red", "Background Color:", ""); + INSERT("bg_green", "Background Color:", ""); + INSERT("bg_blue", "Background Color:", ""); + + // Renderer (Debug) + INSERT("debug", "Enable Graphics Debugging", + "When checked, the graphics API enters a slower debugging mode"); + INSERT("shader_feedback", "Enable Shader Feedback", + "When checked, yuzu will log statistics about the compiled pipeline cache"); + INSERT("nsight_aftermath", "Enable Nsight Aftermath", + "When checked, it enables Nsight Aftermath crash dumps"); + INSERT("disable_shader_loop_safety_checks", "Disable Loop safety checks", + "When checked, it executes shaders without loop logic changes"); + + // Renderer (General) + INSERT("use_speed_limit", "Limit Speed Percent", ""); + INSERT("speed_limit", "Limit Speed Percent", ""); + + // System + INSERT("rng_seed_enabled", "RNG Seed", ""); + INSERT("rng_seed", "RNG Seed", ""); + INSERT("device_name", "Device Name", ""); + INSERT("custom_rtc_enabled", "Custom RTC", ""); + INSERT("custom_rtc", "Custom RTC", ""); + INSERT("language_index", "Language:", ""); + INSERT("region_index", "Region:", ""); + INSERT("time_zone_index", "Time Zone:", ""); + INSERT("sound_index", "Sound Output Mode:", ""); + INSERT("use_docked_mode", "Docked", ""); + +#undef INSERT + + return translations; +} + +std::forward_list ComboboxEnumeration(std::type_index type, QWidget* parent) { + const auto& tr = [&](const char* text) { return parent->tr(text); }; + + if (type == typeid(Settings::AstcDecodeMode)) { + return { + tr("CPU"), + tr("GPU"), + tr("CPU Asynchronous"), + }; + } else if (type == typeid(Settings::RendererBackend)) { + return { + tr("OpenGL"), + tr("Vulkan"), + tr("Null"), + }; + } else if (type == typeid(Settings::ShaderBackend)) { + return { + tr("GLSL"), + tr("GLASM (Assembly Shaders, NVIDIA Only)"), + tr("SPIR-V (Experimental, Mesa Only)"), + }; + } else if (type == typeid(Settings::GPUAccuracy)) { + return { + tr("Normal"), + tr("High"), + tr("Extreme"), + }; + } else if (type == typeid(Settings::AnisotropyMode)) { + return { + tr("Automatic"), tr("Default"), tr("2x"), tr("4x"), tr("8x"), tr("16x"), + }; + } + + return {}; +} + +} // namespace ConfigurationShared diff --git a/src/yuzu/configuration/shared_translation.h b/src/yuzu/configuration/shared_translation.h new file mode 100644 index 000000000..a81ae9c87 --- /dev/null +++ b/src/yuzu/configuration/shared_translation.h @@ -0,0 +1,18 @@ +#include +#include +#include +#include +#include +#include +#include + +class QWidget; + +namespace ConfigurationShared { +using TranslationMap = std::map>; + +std::unique_ptr InitializeTranslations(QWidget* parent); + +std::forward_list ComboboxEnumeration(std::type_index type, QWidget* parent); + +} // namespace ConfigurationShared From 4f545e3024920643c6c4326072829c0a39d1396e Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 7 May 2023 09:49:47 -0400 Subject: [PATCH 010/155] shared_translation: Add copyright and license --- src/yuzu/configuration/shared_translation.cpp | 3 +++ src/yuzu/configuration/shared_translation.h | 3 +++ 2 files changed, 6 insertions(+) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 974203f75..f82074d7d 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -1,3 +1,6 @@ +// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + #include #include #include diff --git a/src/yuzu/configuration/shared_translation.h b/src/yuzu/configuration/shared_translation.h index a81ae9c87..79cd08a6a 100644 --- a/src/yuzu/configuration/shared_translation.h +++ b/src/yuzu/configuration/shared_translation.h @@ -1,3 +1,6 @@ +// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + #include #include #include From 4a825268d60a53c6bff429cd4202e3e60f5c8842 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 7 May 2023 10:34:39 -0400 Subject: [PATCH 011/155] shared_translation: Add the rest of the settings --- src/yuzu/configuration/shared_translation.cpp | 81 ++++++++++++++++++- 1 file changed, 80 insertions(+), 1 deletion(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index f82074d7d..ddc7569f1 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -21,6 +21,8 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { #define INSERT(LABEL, NAME, TOOLTIP) \ translations->insert(std::pair{(LABEL), std::pair{tr((NAME)), tr((TOOLTIP))}}) + // A setting can be ignored by giving it a blank name + // Audio INSERT("output_engine", "Output Engine:", ""); INSERT("output_device", "Output Device:", ""); @@ -34,6 +36,8 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { // Cpu INSERT("cpu_accuracy", "Accuracy:", ""); + + // Cpu Debug INSERT("cpu_debug_mode", "Enable CPU Debugging", ""); INSERT("cpuopt_page_tables", "Enable inline page tables", ""); INSERT("cpuopt_block_linking", "Enable block linking", ""); @@ -50,6 +54,7 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { ""); INSERT("cpuopt_ignore_memory_aborts", "Enable fallbacks for invalid memory accesses", ""); + // Cpu Unsafe INSERT("cpuopt_unsafe_unfuse_fma", "Unfuse FMA (improve performance on CPUs without FMA)", ""); INSERT("cpuopt_unsafe_reduce_fp_error", "Faster FRSQRTE and FRECPE", ""); INSERT("cpuopt_unsafe_ignore_standard_fpcr", "Faster ASIMD instructions (32 bits only)", ""); @@ -127,7 +132,81 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT("region_index", "Region:", ""); INSERT("time_zone_index", "Time Zone:", ""); INSERT("sound_index", "Sound Output Mode:", ""); - INSERT("use_docked_mode", "Docked", ""); + INSERT("use_docked_mode", "", ""); + + // Controls + INSERT("enable_raw_input", "", ""); + INSERT("controller_navigation", "", ""); + INSERT("enable_joycon_driver", "", ""); + INSERT("enable_procon_driver", "", ""); + INSERT("vibration_enabled", "", ""); + INSERT("enable_accurate_vibrations", "", ""); + INSERT("motion_enabled", "", ""); + INSERT("udp_input_servers", "", ""); + INSERT("enable_udp_controller", "", ""); + INSERT("pause_tas_on_load", "", ""); + INSERT("tas_enable", "", ""); + INSERT("tas_loop", "", ""); + INSERT("mouse_panning", "", ""); + INSERT("mouse_panning_sensitivity", "", ""); + INSERT("mouse_enabled", "", ""); + INSERT("emulate_analog_keyboard", "", ""); + INSERT("keyboard_enabled", "", ""); + INSERT("debug_pad_enabled", "", ""); + INSERT("touch_device", "", ""); + INSERT("touch_from_button_map", "", ""); + INSERT("enable_ring_controller", "", ""); + INSERT("enable_ir_sensor", "", ""); + INSERT("ir_sensor_device", "", ""); + + // Data Storage + INSERT("use_virtual_sd", "", ""); + INSERT("gamecard_inserted", "Inserted", ""); + INSERT("gamecard_current_game", "Current Game", ""); + INSERT("gamecard_path", "Path", ""); + + // Debugging + INSERT("use_gdbstub", "Enable GDB Stub", ""); + INSERT("gdbstub_port", "Port:", ""); + INSERT("program_args", "Arguments String", ""); + INSERT("dump_exefs", "Dump ExeFS", ""); + INSERT("dump_nso", "Dump Decompressed NSOs", ""); + INSERT("enable_fs_access_log", "Enable FS Access Log", ""); + INSERT("reporting_services", "Enable Verbose Repoting Services**", ""); + INSERT("quest_flag", "Kiosk (Quest) Mode", ""); + INSERT("extended_logging", "Enable Extended Logging**", + "When checked, the max size of the log increases from 100 MB to 1 GB"); + INSERT("use_debug_asserts", "Enable Debug Asserts", ""); + INSERT("use_auto_stub", "Enable Auto-Stub**", ""); + INSERT("enable_all_controllers", "Enable All Controller Types", ""); + INSERT("create_crash_dumps", "Create Minidump After Crash", ""); + INSERT("perform_vulkan_check", "Perform Startup Vulkan Check", + "Enables yuzu to check for a working Vulkan environment when the program starts up. " + "Disable this if this is causing issues with external programs seeing yuzu."); + INSERT("log_filter", "Global Log Filter", ""); + INSERT("use_dev_keys", "", ""); + + // Debugging Graphics + INSERT("dump_shaders", "Dump Game Shaders", + "When checked, it will dump all the original assembler shaders from the disk shader " + "cache or game as found"); + INSERT("disable_macro_jit", "Disable Macro JIT", + "When checked, it disables the macro Just In Time compiler. Enabling this makes games " + "run slower"); + INSERT( + "disable_macro_hle", "Disable Macro HLE", + "When checked, it disables the macro HLE functions. Enabling this makes games run slower"); + INSERT("dump_macros", "Dump Maxwell Macros", + "When checked, it will dump all the macro programs of the GPU"); + + // Network + INSERT("network_interface", "Network Interface", ""); + + // Web Service + INSERT("enable_telemetry", "Share anonymous usage data with the yuzu team", ""); + INSERT("web_api_url", "", ""); + INSERT("yuzu_username", "", ""); + INSERT("yuzu_token", "Token:", ""); #undef INSERT From 75d7e40113c03ec6a2a83fb8cfa736a17c6862a3 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 7 May 2023 10:35:28 -0400 Subject: [PATCH 012/155] settings: Recategorize a bit Will help with generating config UI later. --- src/common/settings.cpp | 7 +- src/common/settings.h | 87 +++++++++++-------- src/yuzu/configuration/config.cpp | 12 ++- .../configuration/configuration_shared.cpp | 8 +- .../configure_graphics_advanced.cpp | 2 +- src/yuzu_cmd/config.cpp | 6 +- 6 files changed, 77 insertions(+), 45 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 59934803e..38a82f6f7 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -151,14 +151,19 @@ const char* TranslateCategory(Category category) { case Category::Core: return "Core"; case Category::Cpu: + case Category::CpuDebug: + case Category::CpuUnsafe: return "Cpu"; case Category::Renderer: + case Category::RendererAdvanced: + case Category::RendererDebug: return "Renderer"; case Category::System: return "System"; case Category::DataStorage: return "Data Storage"; case Category::Debugging: + case Category::DebuggingGraphics: return "Debugging"; case Category::Miscellaneous: return "Miscellaneous"; @@ -188,8 +193,6 @@ const char* TranslateCategory(Category category) { return "Paths"; case Category::MaxEnum: break; - case Category::AdvancedGraphics: - return "Renderer"; } return "Miscellaneous"; } diff --git a/src/common/settings.h b/src/common/settings.h index 48f86d0aa..70ab8d584 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -120,11 +120,15 @@ enum class Category : u32 { Audio, Core, Cpu, + CpuDebug, + CpuUnsafe, Renderer, - AdvancedGraphics, + RendererAdvanced, + RendererDebug, System, DataStorage, Debugging, + DebuggingGraphics, Miscellaneous, Network, WebService, @@ -624,53 +628,56 @@ struct Values { "cpu_accuracy", Category::Cpu}; // TODO: remove cpu_accuracy_first_time, migration setting added 8 July 2021 Setting cpu_accuracy_first_time{linkage, true, "cpu_accuracy_first_time", Category::Cpu}; - Setting cpu_debug_mode{linkage, false, "cpu_debug_mode", Category::Cpu}; + Setting cpu_debug_mode{linkage, false, "cpu_debug_mode", Category::CpuDebug}; - Setting cpuopt_page_tables{linkage, true, "cpuopt_page_tables", Category::Cpu}; - Setting cpuopt_block_linking{linkage, true, "cpuopt_block_linking", Category::Cpu}; + Setting cpuopt_page_tables{linkage, true, "cpuopt_page_tables", Category::CpuDebug}; + Setting cpuopt_block_linking{linkage, true, "cpuopt_block_linking", Category::CpuDebug}; Setting cpuopt_return_stack_buffer{linkage, true, "cpuopt_return_stack_buffer", - Category::Cpu}; - Setting cpuopt_fast_dispatcher{linkage, true, "cpuopt_fast_dispatcher", Category::Cpu}; + Category::CpuDebug}; + Setting cpuopt_fast_dispatcher{linkage, true, "cpuopt_fast_dispatcher", + Category::CpuDebug}; Setting cpuopt_context_elimination{linkage, true, "cpuopt_context_elimination", - Category::Cpu}; - Setting cpuopt_const_prop{linkage, true, "cpuopt_const_prop", Category::Cpu}; - Setting cpuopt_misc_ir{linkage, true, "cpuopt_misc_ir", Category::Cpu}; + Category::CpuDebug}; + Setting cpuopt_const_prop{linkage, true, "cpuopt_const_prop", Category::CpuDebug}; + Setting cpuopt_misc_ir{linkage, true, "cpuopt_misc_ir", Category::CpuDebug}; Setting cpuopt_reduce_misalign_checks{linkage, true, "cpuopt_reduce_misalign_checks", - Category::Cpu}; - Setting cpuopt_fastmem{linkage, true, "cpuopt_fastmem", Category::Cpu}; + Category::CpuDebug}; + Setting cpuopt_fastmem{linkage, true, "cpuopt_fastmem", Category::CpuDebug}; Setting cpuopt_fastmem_exclusives{linkage, true, "cpuopt_fastmem_exclusives", - Category::Cpu}; + Category::CpuDebug}; Setting cpuopt_recompile_exclusives{linkage, true, "cpuopt_recompile_exclusives", - Category::Cpu}; + Category::CpuDebug}; Setting cpuopt_ignore_memory_aborts{linkage, true, "cpuopt_ignore_memory_aborts", - Category::Cpu}; + Category::CpuDebug}; SwitchableSetting cpuopt_unsafe_unfuse_fma{linkage, true, "cpuopt_unsafe_unfuse_fma", - Category::Cpu}; + Category::CpuUnsafe}; SwitchableSetting cpuopt_unsafe_reduce_fp_error{ - linkage, true, "cpuopt_unsafe_reduce_fp_error", Category::Cpu}; + linkage, true, "cpuopt_unsafe_reduce_fp_error", Category::CpuUnsafe}; SwitchableSetting cpuopt_unsafe_ignore_standard_fpcr{ - linkage, true, "cpuopt_unsafe_ignore_standard_fpcr", Category::Cpu}; + linkage, true, "cpuopt_unsafe_ignore_standard_fpcr", Category::CpuUnsafe}; SwitchableSetting cpuopt_unsafe_inaccurate_nan{ - linkage, true, "cpuopt_unsafe_inaccurate_nan", Category::Cpu}; + linkage, true, "cpuopt_unsafe_inaccurate_nan", Category::CpuUnsafe}; SwitchableSetting cpuopt_unsafe_fastmem_check{ - linkage, true, "cpuopt_unsafe_fastmem_check", Category::Cpu}; + linkage, true, "cpuopt_unsafe_fastmem_check", Category::CpuUnsafe}; SwitchableSetting cpuopt_unsafe_ignore_global_monitor{ - linkage, true, "cpuopt_unsafe_ignore_global_monitor", Category::Cpu}; + linkage, true, "cpuopt_unsafe_ignore_global_monitor", Category::CpuUnsafe}; // Renderer SwitchableSetting renderer_backend{ linkage, RendererBackend::Vulkan, RendererBackend::OpenGL, RendererBackend::Null, "backend", Category::Renderer}; SwitchableSetting async_presentation{linkage, false, "async_presentation", - Category::AdvancedGraphics}; + Category::RendererAdvanced}; SwitchableSetting renderer_force_max_clock{linkage, false, "force_max_clock", - Category::AdvancedGraphics}; - Setting renderer_debug{linkage, false, "debug", Category::Renderer}; - Setting renderer_shader_feedback{linkage, false, "shader_feedback", Category::Renderer}; - Setting enable_nsight_aftermath{linkage, false, "nsight_aftermath", Category::Renderer}; + Category::RendererAdvanced}; + Setting renderer_debug{linkage, false, "debug", Category::RendererDebug}; + Setting renderer_shader_feedback{linkage, false, "shader_feedback", + Category::RendererDebug}; + Setting enable_nsight_aftermath{linkage, false, "nsight_aftermath", + Category::RendererDebug}; Setting disable_shader_loop_safety_checks{ - linkage, false, "disable_shader_loop_safety_checks", Category::Renderer}; + linkage, false, "disable_shader_loop_safety_checks", Category::RendererDebug}; SwitchableSetting vulkan_device{linkage, 0, "vulkan_device", Category::Renderer}; ResolutionScalingInfo resolution_info{}; @@ -697,7 +704,7 @@ struct Values { SwitchableSetting aspect_ratio{linkage, 0, 0, 4, "aspect_ratio", Category::Renderer}; SwitchableSetting max_anisotropy{ linkage, AnisotropyMode::Automatic, AnisotropyMode::Automatic, AnisotropyMode::X16, - "max_anisotropy", Category::AdvancedGraphics}; + "max_anisotropy", Category::RendererAdvanced}; SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", Category::Renderer}; SwitchableSetting speed_limit{linkage, 100, 0, @@ -706,7 +713,7 @@ struct Values { Category::Renderer}; SwitchableSetting gpu_accuracy{ linkage, GPUAccuracy::High, GPUAccuracy::Normal, GPUAccuracy::Extreme, - "gpu_accuracy", Category::AdvancedGraphics}; + "gpu_accuracy", Category::RendererAdvanced}; SwitchableSetting use_asynchronous_gpu_emulation{ linkage, true, "use_asynchronous_gpu_emulation", Category::Renderer}; SwitchableSetting nvdec_emulation{linkage, NvdecEmulation::GPU, @@ -728,21 +735,21 @@ struct Values { SwitchableSetting use_asynchronous_shaders{linkage, false, "use_asynchronous_shaders", Category::Renderer}; SwitchableSetting use_fast_gpu_time{linkage, true, "use_fast_gpu_time", - Category::AdvancedGraphics}; + Category::RendererAdvanced}; SwitchableSetting use_vulkan_driver_pipeline_cache{ - linkage, true, "use_vulkan_driver_pipeline_cache", Category::AdvancedGraphics}; + linkage, true, "use_vulkan_driver_pipeline_cache", Category::RendererAdvanced}; SwitchableSetting enable_compute_pipelines{linkage, false, "enable_compute_pipelines", - Category::AdvancedGraphics}; + Category::RendererAdvanced}; SwitchableSetting astc_recompression{linkage, AstcRecompression::Uncompressed, AstcRecompression::Uncompressed, AstcRecompression::Bc3, "astc_recompression", - Category::AdvancedGraphics}; + Category::RendererAdvanced}; SwitchableSetting use_video_framerate{linkage, false, "use_video_framerate", - Category::AdvancedGraphics}; + Category::RendererAdvanced}; SwitchableSetting barrier_feedback_loops{linkage, true, "barrier_feedback_loops", - Category::AdvancedGraphics}; + Category::RendererAdvanced}; SwitchableSetting bg_red{linkage, 0, "bg_red", Category::Renderer}; SwitchableSetting bg_green{linkage, 0, "bg_green", Category::Renderer}; @@ -855,14 +862,18 @@ struct Values { Setting program_args{linkage, std::string(), "program_args", Category::Debugging}; Setting dump_exefs{linkage, false, "dump_exefs", Category::Debugging}; Setting dump_nso{linkage, false, "dump_nso", Category::Debugging}; - Setting dump_shaders{linkage, false, "dump_shaders", Category::Debugging}; - Setting dump_macros{linkage, false, "dump_macros", Category::Debugging}; + Setting dump_shaders{linkage, false, "dump_shaders", + Category::DebuggingGraphics}; + Setting dump_macros{linkage, false, "dump_macros", + Category::DebuggingGraphics}; Setting enable_fs_access_log{linkage, false, "enable_fs_access_log", Category::Debugging}; Setting reporting_services{linkage, false, "reporting_services", Category::Debugging}; Setting quest_flag{linkage, false, "quest_flag", Category::Debugging}; - Setting disable_macro_jit{linkage, false, "disable_macro_jit", Category::Debugging}; - Setting disable_macro_hle{linkage, false, "disable_macro_hle", Category::Debugging}; + Setting disable_macro_jit{linkage, false, "disable_macro_jit", + Category::DebuggingGraphics}; + Setting disable_macro_hle{linkage, false, "disable_macro_hle", + Category::DebuggingGraphics}; Setting extended_logging{linkage, false, "extended_logging", Category::Debugging}; Setting use_debug_asserts{linkage, false, "use_debug_asserts", Category::Debugging}; diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index f274fe4ea..c6a34e787 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -550,6 +550,7 @@ void Config::ReadDebuggingValues() { qt_config->value(QStringLiteral("record_frame_times"), false).toBool(); ReadCategory(Settings::Category::Debugging); + ReadCategory(Settings::Category::DebuggingGraphics); qt_config->endGroup(); } @@ -635,6 +636,8 @@ void Config::ReadCpuValues() { qt_config->beginGroup(QStringLiteral("Cpu")); ReadCategory(Settings::Category::Cpu); + ReadCategory(Settings::Category::CpuDebug); + ReadCategory(Settings::Category::CpuUnsafe); if (Settings::values.cpu_accuracy_first_time) { Settings::values.cpu_accuracy.SetValue(Settings::values.cpu_accuracy.GetDefault()); @@ -648,7 +651,8 @@ void Config::ReadRendererValues() { qt_config->beginGroup(QStringLiteral("Renderer")); ReadCategory(Settings::Category::Renderer); - ReadCategory(Settings::Category::AdvancedGraphics); + ReadCategory(Settings::Category::RendererAdvanced); + ReadCategory(Settings::Category::RendererDebug); qt_config->endGroup(); } @@ -1016,6 +1020,7 @@ void Config::SaveDebuggingValues() { qt_config->setValue(QStringLiteral("record_frame_times"), Settings::values.record_frame_times); WriteCategory(Settings::Category::Debugging); + WriteCategory(Settings::Category::DebuggingGraphics); qt_config->endGroup(); } @@ -1079,6 +1084,8 @@ void Config::SaveCpuValues() { qt_config->beginGroup(QStringLiteral("Cpu")); WriteCategory(Settings::Category::Cpu); + WriteCategory(Settings::Category::CpuDebug); + WriteCategory(Settings::Category::CpuUnsafe); qt_config->endGroup(); } @@ -1086,8 +1093,9 @@ void Config::SaveCpuValues() { void Config::SaveRendererValues() { qt_config->beginGroup(QStringLiteral("Renderer")); - WriteCategory(Settings::Category::AdvancedGraphics); WriteCategory(Settings::Category::Renderer); + WriteCategory(Settings::Category::RendererAdvanced); + WriteCategory(Settings::Category::RendererDebug); qt_config->endGroup(); } diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 44222718c..dc11a318a 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -128,10 +128,16 @@ QWidget* CreateWidget(Settings::BasicSetting* setting, const TranslationMap& tra return std::pair{translations.at(setting_label).first, translations.at(setting_label).second}; } - LOG_ERROR(Frontend, "Translation map lacks entry for \"{}\"", setting_label); + LOG_ERROR(Frontend, "Translation table lacks entry for \"{}\"", setting_label); return std::pair{QString::fromStdString(setting_label), QStringLiteral("")}; }(); + if (label == QStringLiteral("")) { + LOG_DEBUG(Frontend, "Translation table has emtpy entry for \"{}\", skipping...", + setting->GetLabel()); + return widget; + } + if (type == typeid(bool)) { auto pair = CreateCheckBox(setting, label, parent, trackers); widget = pair.first; diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 6d387b5c3..7d79044d4 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -31,7 +31,7 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { std::map hold{}; // A map will sort the data for us for (auto setting : - Settings::values.linkage.by_category[Settings::Category::AdvancedGraphics]) { + Settings::values.linkage.by_category[Settings::Category::RendererAdvanced]) { QWidget* widget = ConfigurationShared::CreateWidget(setting, translations, this, runtime_lock, apply_funcs, trackers); diff --git a/src/yuzu_cmd/config.cpp b/src/yuzu_cmd/config.cpp index cfc1a5d81..f8cbf8034 100644 --- a/src/yuzu_cmd/config.cpp +++ b/src/yuzu_cmd/config.cpp @@ -223,11 +223,15 @@ void Config::ReadValues() { ReadCategory(Settings::Category::Audio); ReadCategory(Settings::Category::Core); ReadCategory(Settings::Category::Cpu); + ReadCategory(Settings::Category::CpuDebug); + ReadCategory(Settings::Category::CpuUnsafe); ReadCategory(Settings::Category::Renderer); - ReadCategory(Settings::Category::AdvancedGraphics); + ReadCategory(Settings::Category::RendererAdvanced); + ReadCategory(Settings::Category::RendererDebug); ReadCategory(Settings::Category::System); ReadCategory(Settings::Category::DataStorage); ReadCategory(Settings::Category::Debugging); + ReadCategory(Settings::Category::DebuggingGraphics); ReadCategory(Settings::Category::Miscellaneous); ReadCategory(Settings::Category::Network); ReadCategory(Settings::Category::WebService); From f8435d676f0073dee4d2ea87c84767a53911fbe6 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 7 May 2023 12:03:40 -0400 Subject: [PATCH 013/155] configure_graphics: Partial runtime implementation --- src/common/settings.h | 2 +- .../configuration/configuration_shared.cpp | 72 +- src/yuzu/configuration/configuration_shared.h | 18 +- src/yuzu/configuration/configure_dialog.cpp | 2 +- src/yuzu/configuration/configure_graphics.cpp | 755 ++++++++++-------- src/yuzu/configuration/configure_graphics.h | 16 +- src/yuzu/configuration/configure_graphics.ui | 751 +---------------- .../configure_graphics_advanced.cpp | 4 +- src/yuzu/configuration/configure_per_game.cpp | 2 +- src/yuzu/configuration/shared_translation.cpp | 9 +- 10 files changed, 498 insertions(+), 1133 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 70ab8d584..8f02fa9af 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -733,7 +733,7 @@ struct Values { linkage, ShaderBackend::GLSL, ShaderBackend::GLSL, ShaderBackend::SPIRV, "shader_backend", Category::Renderer}; SwitchableSetting use_asynchronous_shaders{linkage, false, "use_asynchronous_shaders", - Category::Renderer}; + Category::RendererAdvanced}; SwitchableSetting use_fast_gpu_time{linkage, true, "use_fast_gpu_time", Category::RendererAdvanced}; SwitchableSetting use_vulkan_driver_pipeline_cache{ diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index dc11a318a..575d239eb 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -5,6 +5,7 @@ #include #include #include +#include #include #include #include @@ -55,9 +56,8 @@ static std::pair> CreateCheckBox(Settings::Basic return {checkbox, load_func}; } -static std::pair> CreateCombobox(Settings::BasicSetting* setting, - const QString& label, - QWidget* parent) { +static std::tuple> CreateCombobox( + Settings::BasicSetting* setting, const QString& label, QWidget* parent) { const auto type = setting->TypeId(); QWidget* group = new QWidget(parent); @@ -110,15 +110,34 @@ static std::pair> CreateCombobox(Settings::Basic } }; - return {group, load_func}; + return {group, combobox, load_func}; } -QWidget* CreateWidget(Settings::BasicSetting* setting, const TranslationMap& translations, - QWidget* parent, bool runtime_lock, - std::forward_list>& apply_funcs, - std::list& trackers) { +static std::tuple> CreateLineEdit( + Settings::BasicSetting* setting, const QString& label, QWidget* parent) { + QWidget* widget = new QWidget(parent); + QHBoxLayout* layout = new QHBoxLayout(widget); + + QLabel* q_label = new QLabel(label, widget); + QLineEdit* line_edit = new QLineEdit(widget); + + layout->addWidget(q_label); + layout->addStretch(); + layout->addWidget(line_edit); + + layout->setContentsMargins(0, 0, 0, 0); + + return {widget, line_edit, []() {}}; +} + +std::pair CreateWidget(Settings::BasicSetting* setting, + const TranslationMap& translations, QWidget* parent, + bool runtime_lock, + std::forward_list>& apply_funcs, + std::list& trackers, RequestType request) { const auto type = setting->TypeId(); QWidget* widget{nullptr}; + void* extra{nullptr}; std::function load_func; @@ -135,7 +154,7 @@ QWidget* CreateWidget(Settings::BasicSetting* setting, const TranslationMap& tra if (label == QStringLiteral("")) { LOG_DEBUG(Frontend, "Translation table has emtpy entry for \"{}\", skipping...", setting->GetLabel()); - return widget; + return {nullptr, nullptr}; } if (type == typeid(bool)) { @@ -143,14 +162,36 @@ QWidget* CreateWidget(Settings::BasicSetting* setting, const TranslationMap& tra widget = pair.first; load_func = pair.second; } else if (setting->IsEnum()) { - auto pair = CreateCombobox(setting, label, parent); - widget = pair.first; - load_func = pair.second; + auto tuple = CreateCombobox(setting, label, parent); + widget = std::get<0>(tuple); + extra = std::get<1>(tuple); + load_func = std::get<2>(tuple); + } else if (type == typeid(u32) || type == typeid(int)) { + switch (request) { + case RequestType::Default: { + auto tuple = CreateLineEdit(setting, label, parent); + widget = std::get<0>(tuple); + extra = std::get<1>(tuple); + load_func = std::get<2>(tuple); + break; + } + case RequestType::ComboBox: { + auto tuple = CreateCombobox(setting, label, parent); + widget = std::get<0>(tuple); + extra = std::get<1>(tuple); + load_func = std::get<2>(tuple); + break; + } + case RequestType::SpinBox: + case RequestType::Slider: + case RequestType::MaxEnum: + break; + } } if (widget == nullptr) { LOG_ERROR(Frontend, "No widget was created for \"{}\"", setting->GetLabel()); - return widget; + return {nullptr, nullptr}; } apply_funcs.push_front([load_func, setting](bool powered_on) { @@ -162,13 +203,14 @@ QWidget* CreateWidget(Settings::BasicSetting* setting, const TranslationMap& tra bool enable = runtime_lock || setting->RuntimeModfiable(); enable &= setting->Switchable() && !(Settings::IsConfiguringGlobal() && !setting->UsingGlobal()); - + enable |= !setting->Switchable() && Settings::IsConfiguringGlobal() && runtime_lock; widget->setEnabled(enable); + widget->setVisible(Settings::IsConfiguringGlobal() || setting->Switchable()); widget->setToolTip(tooltip); - return widget; + return {widget, extra}; } Tab::Tab(std::shared_ptr> group_, QWidget* parent) diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 7040673ea..d0fe6ea38 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -41,10 +41,20 @@ enum class CheckState { Count, // Simply the number of states, not a valid checkbox state }; -QWidget* CreateWidget(Settings::BasicSetting* setting, const TranslationMap& translations, - QWidget* parent, bool runtime_lock, - std::forward_list>& apply_funcs, - std::list& trackers); +enum class RequestType { + Default, + ComboBox, + SpinBox, + Slider, + MaxEnum, +}; + +std::pair CreateWidget(Settings::BasicSetting* setting, + const TranslationMap& translations, QWidget* parent, + bool runtime_lock, + std::forward_list>& apply_funcs, + std::list& trackers, + RequestType request = RequestType::Default); // Global-aware apply and set functions diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index b3f4764c7..5b356a074 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -43,7 +43,7 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, std::make_unique(system_, nullptr, *translations, this)}, graphics_tab{std::make_unique( system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, - nullptr, this)}, + nullptr, *translations, this)}, hotkeys_tab{std::make_unique(system_.HIDCore(), this)}, input_tab{std::make_unique(system_, this)}, network_tab{std::make_unique(system_, this)}, diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index a8c5b1d9f..8128a4047 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -55,100 +55,123 @@ static constexpr VkPresentModeKHR VSyncSettingToMode(Settings::VSyncMode mode) { } } -static constexpr Settings::VSyncMode PresentModeToSetting(VkPresentModeKHR mode) { - switch (mode) { - case VK_PRESENT_MODE_IMMEDIATE_KHR: - return Settings::VSyncMode::Immediate; - case VK_PRESENT_MODE_MAILBOX_KHR: - return Settings::VSyncMode::Mailbox; - case VK_PRESENT_MODE_FIFO_KHR: - return Settings::VSyncMode::FIFO; - case VK_PRESENT_MODE_FIFO_RELAXED_KHR: - return Settings::VSyncMode::FIFORelaxed; - default: - return Settings::VSyncMode::FIFO; - } -} +// static constexpr Settings::VSyncMode PresentModeToSetting(VkPresentModeKHR mode) { +// switch (mode) { +// case VK_PRESENT_MODE_IMMEDIATE_KHR: +// return Settings::VSyncMode::Immediate; +// case VK_PRESENT_MODE_MAILBOX_KHR: +// return Settings::VSyncMode::Mailbox; +// case VK_PRESENT_MODE_FIFO_KHR: +// return Settings::VSyncMode::FIFO; +// case VK_PRESENT_MODE_FIFO_RELAXED_KHR: +// return Settings::VSyncMode::FIFORelaxed; +// default: +// return Settings::VSyncMode::FIFO; +// } +// } ConfigureGraphics::ConfigureGraphics( const Core::System& system_, std::vector& records_, const std::function& expose_compute_option_, - std::shared_ptr> group, QWidget* parent) + std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, QWidget* parent) : ConfigurationShared::Tab(group, parent), ui{std::make_unique()}, - records{records_}, expose_compute_option{expose_compute_option_}, system{system_} { + records{records_}, expose_compute_option{expose_compute_option_}, system{system_}, + translations{translations_} { vulkan_device = Settings::values.vulkan_device.GetValue(); RetrieveVulkanDevices(); ui->setupUi(this); + SetConfiguration(); + for (const auto& device : vulkan_devices) { - ui->device->addItem(device); + vulkan_device_combobox->addItem(device); } - ui->backend->addItem(QStringLiteral("GLSL")); - ui->backend->addItem(tr("GLASM (Assembly Shaders, NVIDIA Only)")); - ui->backend->addItem(tr("SPIR-V (Experimental, Mesa Only)")); + UpdateBackgroundColorButton(QColor::fromRgb(Settings::values.bg_red.GetValue(), + Settings::values.bg_green.GetValue(), + Settings::values.bg_blue.GetValue())); + UpdateAPILayout(); + PopulateVSyncModeSelection(); //< must happen after UpdateAPILayout + // SetFSRIndicatorText(ui->fsr_sharpening_slider->sliderPosition()); + + // VSync setting needs to be determined after populating the VSync combobox + if (Settings::IsConfiguringGlobal()) { + const auto vsync_mode_setting = Settings::values.vsync_mode.GetValue(); + const auto vsync_mode = VSyncSettingToMode(vsync_mode_setting); + int index{}; + for (const auto mode : vsync_mode_combobox_enum_map) { + if (mode == vsync_mode) { + break; + } + index++; + } + if (static_cast(index) < vsync_mode_combobox_enum_map.size()) { + vsync_mode_combobox->setCurrentIndex(index); + } + } SetupPerGameUI(); - SetConfiguration(); - - connect(ui->api, qOverload(&QComboBox::currentIndexChanged), this, [this] { + connect(api_combobox, qOverload(&QComboBox::currentIndexChanged), this, [this] { UpdateAPILayout(); PopulateVSyncModeSelection(); if (!Settings::IsConfiguringGlobal()) { - ConfigurationShared::SetHighlight( - ui->api_widget, ui->api->currentIndex() != ConfigurationShared::USE_GLOBAL_INDEX); + ConfigurationShared::SetHighlight(ui->api_widget, + api_combobox->currentIndex() != + ConfigurationShared::USE_GLOBAL_INDEX); } }); - connect(ui->device, qOverload(&QComboBox::activated), this, [this](int device) { - UpdateDeviceSelection(device); - PopulateVSyncModeSelection(); - }); - connect(ui->backend, qOverload(&QComboBox::activated), this, + connect(vulkan_device_combobox, qOverload(&QComboBox::activated), this, + [this](int device) { + UpdateDeviceSelection(device); + PopulateVSyncModeSelection(); + }); + connect(shader_backend_combobox, qOverload(&QComboBox::activated), this, [this](int backend) { UpdateShaderBackendSelection(backend); }); - connect(ui->bg_button, &QPushButton::clicked, this, [this] { - const QColor new_bg_color = QColorDialog::getColor(bg_color); - if (!new_bg_color.isValid()) { - return; - } - UpdateBackgroundColorButton(new_bg_color); - }); + // connect(ui->bg_button, &QPushButton::clicked, this, [this] { + // const QColor new_bg_color = QColorDialog::getColor(bg_color); + // if (!new_bg_color.isValid()) { + // return; + // } + // UpdateBackgroundColorButton(new_bg_color); + // }); - ui->api->setEnabled(!UISettings::values.has_broken_vulkan && ui->api->isEnabled()); + api_combobox->setEnabled(!UISettings::values.has_broken_vulkan && api_combobox->isEnabled()); ui->api_widget->setEnabled( (!UISettings::values.has_broken_vulkan || Settings::IsConfiguringGlobal()) && ui->api_widget->isEnabled()); - ui->bg_label->setVisible(Settings::IsConfiguringGlobal()); - ui->bg_combobox->setVisible(!Settings::IsConfiguringGlobal()); + // ui->bg_label->setVisible(Settings::IsConfiguringGlobal()); + // ui->bg_combobox->setVisible(!Settings::IsConfiguringGlobal()); - connect(ui->fsr_sharpening_slider, &QSlider::valueChanged, this, - &ConfigureGraphics::SetFSRIndicatorText); - ui->fsr_sharpening_combobox->setVisible(!Settings::IsConfiguringGlobal()); - ui->fsr_sharpening_label->setVisible(Settings::IsConfiguringGlobal()); + // connect(ui->fsr_sharpening_slider, &QSlider::valueChanged, this, + // &ConfigureGraphics::SetFSRIndicatorText); + // ui->fsr_sharpening_combobox->setVisible(!Settings::IsConfiguringGlobal()); + // ui->fsr_sharpening_label->setVisible(Settings::IsConfiguringGlobal()); } void ConfigureGraphics::PopulateVSyncModeSelection() { const Settings::RendererBackend backend{GetCurrentGraphicsBackend()}; if (backend == Settings::RendererBackend::Null) { - ui->vsync_mode_combobox->setEnabled(false); + vsync_mode_combobox->setEnabled(false); return; } - ui->vsync_mode_combobox->setEnabled(true); + vsync_mode_combobox->setEnabled(true); const int current_index = //< current selected vsync mode from combobox - ui->vsync_mode_combobox->currentIndex(); + vsync_mode_combobox->currentIndex(); const auto current_mode = //< current selected vsync mode as a VkPresentModeKHR current_index == -1 ? VSyncSettingToMode(Settings::values.vsync_mode.GetValue()) : vsync_mode_combobox_enum_map[current_index]; int index{}; - const int device{ui->device->currentIndex()}; //< current selected Vulkan device + const int device{vulkan_device_combobox->currentIndex()}; //< current selected Vulkan device const auto& present_modes = //< relevant vector of present modes for the selected device or API backend == Settings::RendererBackend::Vulkan ? device_present_modes[device] : default_present_modes; - ui->vsync_mode_combobox->clear(); + vsync_mode_combobox->clear(); vsync_mode_combobox_enum_map.clear(); vsync_mode_combobox_enum_map.reserve(present_modes.size()); for (const auto present_mode : present_modes) { @@ -157,10 +180,10 @@ void ConfigureGraphics::PopulateVSyncModeSelection() { continue; } - ui->vsync_mode_combobox->insertItem(index, mode_name); + vsync_mode_combobox->insertItem(index, mode_name); vsync_mode_combobox_enum_map.push_back(present_mode); if (present_mode == current_mode) { - ui->vsync_mode_combobox->setCurrentIndex(index); + vsync_mode_combobox->setCurrentIndex(index); } index++; } @@ -188,114 +211,137 @@ ConfigureGraphics::~ConfigureGraphics() = default; void ConfigureGraphics::SetConfiguration() { const bool runtime_lock = !system.IsPoweredOn(); + QLayout& api_layout = *ui->api_widget->layout(); + QLayout& graphics_layout = *ui->graphics_widget->layout(); - ui->api_widget->setEnabled(runtime_lock); - ui->use_asynchronous_gpu_emulation->setEnabled(runtime_lock); - ui->use_disk_shader_cache->setEnabled(runtime_lock); - ui->nvdec_emulation_widget->setEnabled(runtime_lock); - ui->resolution_combobox->setEnabled(runtime_lock); - ui->astc_decode_mode_combobox->setEnabled(runtime_lock); - ui->vsync_mode_layout->setEnabled(runtime_lock || - Settings::values.renderer_backend.GetValue() == - Settings::RendererBackend::Vulkan); - ui->use_disk_shader_cache->setChecked(Settings::values.use_disk_shader_cache.GetValue()); - ui->use_asynchronous_gpu_emulation->setChecked( - Settings::values.use_asynchronous_gpu_emulation.GetValue()); + std::map hold_graphics; - if (Settings::IsConfiguringGlobal()) { - ui->api->setCurrentIndex(static_cast(Settings::values.renderer_backend.GetValue())); - ui->fullscreen_mode_combobox->setCurrentIndex( - static_cast(Settings::values.fullscreen_mode.GetValue())); - ui->nvdec_emulation->setCurrentIndex( - static_cast(Settings::values.nvdec_emulation.GetValue())); - ui->aspect_ratio_combobox->setCurrentIndex(Settings::values.aspect_ratio.GetValue()); - ui->resolution_combobox->setCurrentIndex( - static_cast(Settings::values.resolution_setup.GetValue())); - ui->scaling_filter_combobox->setCurrentIndex( - static_cast(Settings::values.scaling_filter.GetValue())); - ui->fsr_sharpening_slider->setValue(Settings::values.fsr_sharpening_slider.GetValue()); - ui->anti_aliasing_combobox->setCurrentIndex( - static_cast(Settings::values.anti_aliasing.GetValue())); - } else { - ConfigurationShared::SetPerGameSetting(ui->api, &Settings::values.renderer_backend); - ConfigurationShared::SetHighlight(ui->api_widget, - !Settings::values.renderer_backend.UsingGlobal()); + for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { + const auto& setting_label = setting->GetLabel(); - ConfigurationShared::SetPerGameSetting(ui->astc_decode_mode_combobox, - &Settings::values.accelerate_astc); - ConfigurationShared::SetHighlight(ui->astc_decode_mode_layout, - !Settings::values.accelerate_astc.UsingGlobal()); - - ConfigurationShared::SetPerGameSetting(ui->nvdec_emulation, - &Settings::values.nvdec_emulation); - ConfigurationShared::SetHighlight(ui->nvdec_emulation_widget, - !Settings::values.nvdec_emulation.UsingGlobal()); - - ConfigurationShared::SetPerGameSetting(ui->fullscreen_mode_combobox, - &Settings::values.fullscreen_mode); - ConfigurationShared::SetHighlight(ui->fullscreen_mode_label, - !Settings::values.fullscreen_mode.UsingGlobal()); - - ConfigurationShared::SetPerGameSetting(ui->aspect_ratio_combobox, - &Settings::values.aspect_ratio); - ConfigurationShared::SetHighlight(ui->ar_label, - !Settings::values.aspect_ratio.UsingGlobal()); - - ConfigurationShared::SetPerGameSetting(ui->resolution_combobox, - &Settings::values.resolution_setup); - ConfigurationShared::SetHighlight(ui->resolution_label, - !Settings::values.resolution_setup.UsingGlobal()); - - ConfigurationShared::SetPerGameSetting(ui->scaling_filter_combobox, - &Settings::values.scaling_filter); - ConfigurationShared::SetHighlight(ui->scaling_filter_label, - !Settings::values.scaling_filter.UsingGlobal()); - - ConfigurationShared::SetPerGameSetting(ui->anti_aliasing_combobox, - &Settings::values.anti_aliasing); - ConfigurationShared::SetHighlight(ui->anti_aliasing_label, - !Settings::values.anti_aliasing.UsingGlobal()); - - ui->fsr_sharpening_combobox->setCurrentIndex( - Settings::values.fsr_sharpening_slider.UsingGlobal() ? 0 : 1); - ui->fsr_sharpening_slider->setEnabled( - !Settings::values.fsr_sharpening_slider.UsingGlobal()); - ui->fsr_sharpening_value->setEnabled(!Settings::values.fsr_sharpening_slider.UsingGlobal()); - ConfigurationShared::SetHighlight(ui->fsr_sharpening_layout, - !Settings::values.fsr_sharpening_slider.UsingGlobal()); - ui->fsr_sharpening_slider->setValue(Settings::values.fsr_sharpening_slider.GetValue()); - - ui->bg_combobox->setCurrentIndex(Settings::values.bg_red.UsingGlobal() ? 0 : 1); - ui->bg_button->setEnabled(!Settings::values.bg_red.UsingGlobal()); - ConfigurationShared::SetHighlight(ui->bg_layout, !Settings::values.bg_red.UsingGlobal()); - } - UpdateBackgroundColorButton(QColor::fromRgb(Settings::values.bg_red.GetValue(), - Settings::values.bg_green.GetValue(), - Settings::values.bg_blue.GetValue())); - UpdateAPILayout(); - PopulateVSyncModeSelection(); //< must happen after UpdateAPILayout - SetFSRIndicatorText(ui->fsr_sharpening_slider->sliderPosition()); - - // VSync setting needs to be determined after populating the VSync combobox - if (Settings::IsConfiguringGlobal()) { - const auto vsync_mode_setting = Settings::values.vsync_mode.GetValue(); - const auto vsync_mode = VSyncSettingToMode(vsync_mode_setting); - int index{}; - for (const auto mode : vsync_mode_combobox_enum_map) { - if (mode == vsync_mode) { - break; + auto [widget, extra] = [&]() { + if (setting_label == "vulkan_device") { + return ConfigurationShared::CreateWidget( + setting, translations, this, runtime_lock, apply_funcs, trackers, + ConfigurationShared::RequestType::ComboBox); } - index++; + return ConfigurationShared::CreateWidget(setting, translations, this, runtime_lock, + apply_funcs, trackers); + }(); + + if (widget == nullptr) { + continue; } - if (static_cast(index) < vsync_mode_combobox_enum_map.size()) { - ui->vsync_mode_combobox->setCurrentIndex(index); + + if (setting_label == "backend") { + api_layout.addWidget(widget); + api_combobox = reinterpret_cast(extra); + } else if (setting_label == "vulkan_device") { + api_layout.addWidget(widget); + vulkan_device_combobox = reinterpret_cast(extra); + vulkan_device_widget = widget; + } else if (setting_label == "shader_backend") { + api_layout.addWidget(widget); + shader_backend_combobox = reinterpret_cast(extra); + shader_backend_widget = widget; + } else { + hold_graphics.insert(std::pair(setting_label, widget)); + } + + if (setting_label == "use_vsync") { + vsync_mode_combobox = reinterpret_cast(extra); } } + + for (const auto& [label, widget] : hold_graphics) { + graphics_layout.addWidget(widget); + } + + // ui->api_widget->setEnabled(runtime_lock); + // ui->use_asynchronous_gpu_emulation->setEnabled(runtime_lock); + // ui->use_disk_shader_cache->setEnabled(runtime_lock); + // ui->nvdec_emulation_widget->setEnabled(runtime_lock); + // ui->resolution_combobox->setEnabled(runtime_lock); + // ui->astc_decode_mode_combobox->setEnabled(runtime_lock); + // ui->vsync_mode_layout->setEnabled(runtime_lock || + // Settings::values.renderer_backend.GetValue() == + // Settings::RendererBackend::Vulkan); + // ui->use_disk_shader_cache->setChecked(Settings::values.use_disk_shader_cache.GetValue()); + // ui->use_asynchronous_gpu_emulation->setChecked( + // Settings::values.use_asynchronous_gpu_emulation.GetValue()); + + // if (Settings::IsConfiguringGlobal()) { + // api_combobox->setCurrentIndex(static_cast(Settings::values.renderer_backend.GetValue())); + // ui->fullscreen_mode_combobox->setCurrentIndex( + // static_cast(Settings::values.fullscreen_mode.GetValue())); + // ui->nvdec_emulation->setCurrentIndex( + // static_cast(Settings::values.nvdec_emulation.GetValue())); + // ui->aspect_ratio_combobox->setCurrentIndex(Settings::values.aspect_ratio.GetValue()); + // ui->resolution_combobox->setCurrentIndex( + // static_cast(Settings::values.resolution_setup.GetValue())); + // ui->scaling_filter_combobox->setCurrentIndex( + // static_cast(Settings::values.scaling_filter.GetValue())); + // ui->fsr_sharpening_slider->setValue(Settings::values.fsr_sharpening_slider.GetValue()); + // ui->anti_aliasing_combobox->setCurrentIndex( + // static_cast(Settings::values.anti_aliasing.GetValue())); + // } else { + // ConfigurationShared::SetPerGameSetting(api_combobox, &Settings::values.renderer_backend); + // ConfigurationShared::SetHighlight(ui->api_widget, + // !Settings::values.renderer_backend.UsingGlobal()); + + // ConfigurationShared::SetPerGameSetting(ui->astc_decode_mode_combobox, + // &Settings::values.accelerate_astc); + // ConfigurationShared::SetHighlight(ui->astc_decode_mode_layout, + // !Settings::values.accelerate_astc.UsingGlobal()); + + // ConfigurationShared::SetPerGameSetting(ui->nvdec_emulation, + // &Settings::values.nvdec_emulation); + // ConfigurationShared::SetHighlight(ui->nvdec_emulation_widget, + // !Settings::values.nvdec_emulation.UsingGlobal()); + + // ConfigurationShared::SetPerGameSetting(ui->fullscreen_mode_combobox, + // &Settings::values.fullscreen_mode); + // ConfigurationShared::SetHighlight(ui->fullscreen_mode_label, + // !Settings::values.fullscreen_mode.UsingGlobal()); + + // ConfigurationShared::SetPerGameSetting(ui->aspect_ratio_combobox, + // &Settings::values.aspect_ratio); + // ConfigurationShared::SetHighlight(ui->ar_label, + // !Settings::values.aspect_ratio.UsingGlobal()); + + // ConfigurationShared::SetPerGameSetting(ui->resolution_combobox, + // &Settings::values.resolution_setup); + // ConfigurationShared::SetHighlight(ui->resolution_label, + // !Settings::values.resolution_setup.UsingGlobal()); + + // ConfigurationShared::SetPerGameSetting(ui->scaling_filter_combobox, + // &Settings::values.scaling_filter); + // ConfigurationShared::SetHighlight(ui->scaling_filter_label, + // !Settings::values.scaling_filter.UsingGlobal()); + + // ConfigurationShared::SetPerGameSetting(ui->anti_aliasing_combobox, + // &Settings::values.anti_aliasing); + // ConfigurationShared::SetHighlight(ui->anti_aliasing_label, + // !Settings::values.anti_aliasing.UsingGlobal()); + + // ui->fsr_sharpening_combobox->setCurrentIndex( + // Settings::values.fsr_sharpening_slider.UsingGlobal() ? 0 : 1); + // ui->fsr_sharpening_slider->setEnabled( + // !Settings::values.fsr_sharpening_slider.UsingGlobal()); + // ui->fsr_sharpening_value->setEnabled(!Settings::values.fsr_sharpening_slider.UsingGlobal()); + // ConfigurationShared::SetHighlight(ui->fsr_sharpening_layout, + // !Settings::values.fsr_sharpening_slider.UsingGlobal()); + // ui->fsr_sharpening_slider->setValue(Settings::values.fsr_sharpening_slider.GetValue()); + + // ui->bg_combobox->setCurrentIndex(Settings::values.bg_red.UsingGlobal() ? 0 : 1); + // ui->bg_button->setEnabled(!Settings::values.bg_red.UsingGlobal()); + // ConfigurationShared::SetHighlight(ui->bg_layout, !Settings::values.bg_red.UsingGlobal()); + // } } void ConfigureGraphics::SetFSRIndicatorText(int percentage) { - ui->fsr_sharpening_value->setText( - tr("%1%", "FSR sharpening percentage (e.g. 50%)").arg(100 - (percentage / 2))); + // ui->fsr_sharpening_value->setText( + // tr("%1%", "FSR sharpening percentage (e.g. 50%)").arg(100 - (percentage / 2))); } const QString ConfigureGraphics::TranslateVSyncMode(VkPresentModeKHR mode, @@ -320,131 +366,134 @@ const QString ConfigureGraphics::TranslateVSyncMode(VkPresentModeKHR mode, } void ConfigureGraphics::ApplyConfiguration() { - const auto resolution_setup = static_cast( - ui->resolution_combobox->currentIndex() - - ((Settings::IsConfiguringGlobal()) ? 0 : ConfigurationShared::USE_GLOBAL_OFFSET)); + // const auto resolution_setup = static_cast( + // ui->resolution_combobox->currentIndex() - + // ((Settings::IsConfiguringGlobal()) ? 0 : ConfigurationShared::USE_GLOBAL_OFFSET)); - const auto scaling_filter = static_cast( - ui->scaling_filter_combobox->currentIndex() - - ((Settings::IsConfiguringGlobal()) ? 0 : ConfigurationShared::USE_GLOBAL_OFFSET)); + // const auto scaling_filter = static_cast( + // ui->scaling_filter_combobox->currentIndex() - + // ((Settings::IsConfiguringGlobal()) ? 0 : ConfigurationShared::USE_GLOBAL_OFFSET)); - const auto anti_aliasing = static_cast( - ui->anti_aliasing_combobox->currentIndex() - - ((Settings::IsConfiguringGlobal()) ? 0 : ConfigurationShared::USE_GLOBAL_OFFSET)); + // const auto anti_aliasing = static_cast( + // ui->anti_aliasing_combobox->currentIndex() - + // ((Settings::IsConfiguringGlobal()) ? 0 : ConfigurationShared::USE_GLOBAL_OFFSET)); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.fullscreen_mode, - ui->fullscreen_mode_combobox); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.aspect_ratio, - ui->aspect_ratio_combobox); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_disk_shader_cache, - ui->use_disk_shader_cache, use_disk_shader_cache); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_asynchronous_gpu_emulation, - ui->use_asynchronous_gpu_emulation, - use_asynchronous_gpu_emulation); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.accelerate_astc, - ui->astc_decode_mode_combobox); + // ConfigurationShared::ApplyPerGameSetting(&Settings::values.fullscreen_mode, + // ui->fullscreen_mode_combobox); + // ConfigurationShared::ApplyPerGameSetting(&Settings::values.aspect_ratio, + // ui->aspect_ratio_combobox); + // ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_disk_shader_cache, + // ui->use_disk_shader_cache, use_disk_shader_cache); + // ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_asynchronous_gpu_emulation, + // ui->use_asynchronous_gpu_emulation, + // use_asynchronous_gpu_emulation); + // ConfigurationShared::ApplyPerGameSetting(&Settings::values.accelerate_astc, + // ui->astc_decode_mode_combobox); - if (Settings::IsConfiguringGlobal()) { - // Guard if during game and set to game-specific value - if (Settings::values.renderer_backend.UsingGlobal()) { - Settings::values.renderer_backend.SetValue(GetCurrentGraphicsBackend()); - } - if (Settings::values.nvdec_emulation.UsingGlobal()) { - Settings::values.nvdec_emulation.SetValue(GetCurrentNvdecEmulation()); - } - if (Settings::values.shader_backend.UsingGlobal()) { - Settings::values.shader_backend.SetValue(shader_backend); - } - if (Settings::values.vulkan_device.UsingGlobal()) { - Settings::values.vulkan_device.SetValue(vulkan_device); - } - if (Settings::values.bg_red.UsingGlobal()) { - Settings::values.bg_red.SetValue(static_cast(bg_color.red())); - Settings::values.bg_green.SetValue(static_cast(bg_color.green())); - Settings::values.bg_blue.SetValue(static_cast(bg_color.blue())); - } - if (Settings::values.resolution_setup.UsingGlobal()) { - Settings::values.resolution_setup.SetValue(resolution_setup); - } - if (Settings::values.scaling_filter.UsingGlobal()) { - Settings::values.scaling_filter.SetValue(scaling_filter); - } - if (Settings::values.anti_aliasing.UsingGlobal()) { - Settings::values.anti_aliasing.SetValue(anti_aliasing); - } - Settings::values.fsr_sharpening_slider.SetValue(ui->fsr_sharpening_slider->value()); + // if (Settings::IsConfiguringGlobal()) { + // // Guard if during game and set to game-specific value + // if (Settings::values.renderer_backend.UsingGlobal()) { + // Settings::values.renderer_backend.SetValue(GetCurrentGraphicsBackend()); + // } + // if (Settings::values.nvdec_emulation.UsingGlobal()) { + // Settings::values.nvdec_emulation.SetValue(GetCurrentNvdecEmulation()); + // } + // if (Settings::values.shader_backend.UsingGlobal()) { + // Settings::values.shader_backend.SetValue(shader_backend); + // } + // if (Settings::values.vulkan_device.UsingGlobal()) { + // Settings::values.vulkan_device.SetValue(vulkan_device); + // } + // if (Settings::values.bg_red.UsingGlobal()) { + // Settings::values.bg_red.SetValue(static_cast(bg_color.red())); + // Settings::values.bg_green.SetValue(static_cast(bg_color.green())); + // Settings::values.bg_blue.SetValue(static_cast(bg_color.blue())); + // } + // if (Settings::values.resolution_setup.UsingGlobal()) { + // Settings::values.resolution_setup.SetValue(resolution_setup); + // } + // if (Settings::values.scaling_filter.UsingGlobal()) { + // Settings::values.scaling_filter.SetValue(scaling_filter); + // } + // if (Settings::values.anti_aliasing.UsingGlobal()) { + // Settings::values.anti_aliasing.SetValue(anti_aliasing); + // } + // Settings::values.fsr_sharpening_slider.SetValue(ui->fsr_sharpening_slider->value()); - const auto mode = vsync_mode_combobox_enum_map[ui->vsync_mode_combobox->currentIndex()]; - const auto vsync_mode = PresentModeToSetting(mode); - Settings::values.vsync_mode.SetValue(vsync_mode); - } else { - if (ui->resolution_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - Settings::values.resolution_setup.SetGlobal(true); - } else { - Settings::values.resolution_setup.SetGlobal(false); - Settings::values.resolution_setup.SetValue(resolution_setup); - } - if (ui->scaling_filter_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - Settings::values.scaling_filter.SetGlobal(true); - } else { - Settings::values.scaling_filter.SetGlobal(false); - Settings::values.scaling_filter.SetValue(scaling_filter); - } - if (ui->anti_aliasing_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - Settings::values.anti_aliasing.SetGlobal(true); - } else { - Settings::values.anti_aliasing.SetGlobal(false); - Settings::values.anti_aliasing.SetValue(anti_aliasing); - } - if (ui->api->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - Settings::values.renderer_backend.SetGlobal(true); - Settings::values.shader_backend.SetGlobal(true); - Settings::values.vulkan_device.SetGlobal(true); - } else { - Settings::values.renderer_backend.SetGlobal(false); - Settings::values.renderer_backend.SetValue(GetCurrentGraphicsBackend()); - switch (GetCurrentGraphicsBackend()) { - case Settings::RendererBackend::OpenGL: - case Settings::RendererBackend::Null: - Settings::values.shader_backend.SetGlobal(false); - Settings::values.vulkan_device.SetGlobal(true); - Settings::values.shader_backend.SetValue(shader_backend); - break; - case Settings::RendererBackend::Vulkan: - Settings::values.shader_backend.SetGlobal(true); - Settings::values.vulkan_device.SetGlobal(false); - Settings::values.vulkan_device.SetValue(vulkan_device); - break; - } - } + // const auto mode = vsync_mode_combobox_enum_map[vsync_mode_combobox->currentIndex()]; + // const auto vsync_mode = PresentModeToSetting(mode); + // Settings::values.vsync_mode.SetValue(vsync_mode); + // } else { + // if (ui->resolution_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { + // Settings::values.resolution_setup.SetGlobal(true); + // } else { + // Settings::values.resolution_setup.SetGlobal(false); + // Settings::values.resolution_setup.SetValue(resolution_setup); + // } + // if (ui->scaling_filter_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) + // { + // Settings::values.scaling_filter.SetGlobal(true); + // } else { + // Settings::values.scaling_filter.SetGlobal(false); + // Settings::values.scaling_filter.SetValue(scaling_filter); + // } + // if (ui->anti_aliasing_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) + // { + // Settings::values.anti_aliasing.SetGlobal(true); + // } else { + // Settings::values.anti_aliasing.SetGlobal(false); + // Settings::values.anti_aliasing.SetValue(anti_aliasing); + // } + // if (api_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { + // Settings::values.renderer_backend.SetGlobal(true); + // Settings::values.shader_backend.SetGlobal(true); + // Settings::values.vulkan_device.SetGlobal(true); + // } else { + // Settings::values.renderer_backend.SetGlobal(false); + // Settings::values.renderer_backend.SetValue(GetCurrentGraphicsBackend()); + // switch (GetCurrentGraphicsBackend()) { + // case Settings::RendererBackend::OpenGL: + // case Settings::RendererBackend::Null: + // Settings::values.shader_backend.SetGlobal(false); + // Settings::values.vulkan_device.SetGlobal(true); + // Settings::values.shader_backend.SetValue(shader_backend); + // break; + // case Settings::RendererBackend::Vulkan: + // Settings::values.shader_backend.SetGlobal(true); + // Settings::values.vulkan_device.SetGlobal(false); + // Settings::values.vulkan_device.SetValue(vulkan_device); + // break; + // } + // } - if (ui->nvdec_emulation->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - Settings::values.nvdec_emulation.SetGlobal(true); - } else { - Settings::values.nvdec_emulation.SetGlobal(false); - Settings::values.nvdec_emulation.SetValue(GetCurrentNvdecEmulation()); - } + // if (ui->nvdec_emulation->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { + // Settings::values.nvdec_emulation.SetGlobal(true); + // } else { + // Settings::values.nvdec_emulation.SetGlobal(false); + // Settings::values.nvdec_emulation.SetValue(GetCurrentNvdecEmulation()); + // } - if (ui->bg_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - Settings::values.bg_red.SetGlobal(true); - Settings::values.bg_green.SetGlobal(true); - Settings::values.bg_blue.SetGlobal(true); - } else { - Settings::values.bg_red.SetGlobal(false); - Settings::values.bg_green.SetGlobal(false); - Settings::values.bg_blue.SetGlobal(false); - Settings::values.bg_red.SetValue(static_cast(bg_color.red())); - Settings::values.bg_green.SetValue(static_cast(bg_color.green())); - Settings::values.bg_blue.SetValue(static_cast(bg_color.blue())); - } + // if (ui->bg_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { + // Settings::values.bg_red.SetGlobal(true); + // Settings::values.bg_green.SetGlobal(true); + // Settings::values.bg_blue.SetGlobal(true); + // } else { + // Settings::values.bg_red.SetGlobal(false); + // Settings::values.bg_green.SetGlobal(false); + // Settings::values.bg_blue.SetGlobal(false); + // Settings::values.bg_red.SetValue(static_cast(bg_color.red())); + // Settings::values.bg_green.SetValue(static_cast(bg_color.green())); + // Settings::values.bg_blue.SetValue(static_cast(bg_color.blue())); + // } - if (ui->fsr_sharpening_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - Settings::values.fsr_sharpening_slider.SetGlobal(true); - } else { - Settings::values.fsr_sharpening_slider.SetGlobal(false); - Settings::values.fsr_sharpening_slider.SetValue(ui->fsr_sharpening_slider->value()); - } - } + // if (ui->fsr_sharpening_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) + // { + // Settings::values.fsr_sharpening_slider.SetGlobal(true); + // } else { + // Settings::values.fsr_sharpening_slider.SetGlobal(false); + // Settings::values.fsr_sharpening_slider.SetValue(ui->fsr_sharpening_slider->value()); + // } + // } } void ConfigureGraphics::changeEvent(QEvent* event) { @@ -462,43 +511,43 @@ void ConfigureGraphics::RetranslateUI() { void ConfigureGraphics::UpdateBackgroundColorButton(QColor color) { bg_color = color; - QPixmap pixmap(ui->bg_button->size()); - pixmap.fill(bg_color); + // QPixmap pixmap(ui->bg_button->size()); + // pixmap.fill(bg_color); - const QIcon color_icon(pixmap); - ui->bg_button->setIcon(color_icon); + // const QIcon color_icon(pixmap); + // ui->bg_button->setIcon(color_icon); } void ConfigureGraphics::UpdateAPILayout() { if (!Settings::IsConfiguringGlobal() && - ui->api->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { + api_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { vulkan_device = Settings::values.vulkan_device.GetValue(true); shader_backend = Settings::values.shader_backend.GetValue(true); - ui->device_widget->setEnabled(false); - ui->backend_widget->setEnabled(false); + vulkan_device_widget->setEnabled(false); + shader_backend_widget->setEnabled(false); } else { vulkan_device = Settings::values.vulkan_device.GetValue(); shader_backend = Settings::values.shader_backend.GetValue(); - ui->device_widget->setEnabled(true); - ui->backend_widget->setEnabled(true); + vulkan_device_widget->setEnabled(true); + shader_backend_widget->setEnabled(true); } switch (GetCurrentGraphicsBackend()) { case Settings::RendererBackend::OpenGL: - ui->backend->setCurrentIndex(static_cast(shader_backend)); - ui->device_widget->setVisible(false); - ui->backend_widget->setVisible(true); + shader_backend_combobox->setCurrentIndex(static_cast(shader_backend)); + vulkan_device_widget->setVisible(false); + shader_backend_widget->setVisible(true); break; case Settings::RendererBackend::Vulkan: - if (static_cast(vulkan_device) < ui->device->count()) { - ui->device->setCurrentIndex(vulkan_device); + if (static_cast(vulkan_device) < vulkan_device_combobox->count()) { + vulkan_device_combobox->setCurrentIndex(vulkan_device); } - ui->device_widget->setVisible(true); - ui->backend_widget->setVisible(false); + vulkan_device_widget->setVisible(true); + shader_backend_widget->setVisible(false); break; case Settings::RendererBackend::Null: - ui->device_widget->setVisible(false); - ui->backend_widget->setVisible(false); + vulkan_device_widget->setVisible(false); + shader_backend_widget->setVisible(false); break; } } @@ -520,92 +569,94 @@ void ConfigureGraphics::RetrieveVulkanDevices() { Settings::RendererBackend ConfigureGraphics::GetCurrentGraphicsBackend() const { if (Settings::IsConfiguringGlobal()) { - return static_cast(ui->api->currentIndex()); + return static_cast(api_combobox->currentIndex()); } - if (ui->api->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { + if (api_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { Settings::values.renderer_backend.SetGlobal(true); return Settings::values.renderer_backend.GetValue(); } Settings::values.renderer_backend.SetGlobal(false); - return static_cast(ui->api->currentIndex() - + return static_cast(api_combobox->currentIndex() - ConfigurationShared::USE_GLOBAL_OFFSET); } Settings::NvdecEmulation ConfigureGraphics::GetCurrentNvdecEmulation() const { - if (Settings::IsConfiguringGlobal()) { - return static_cast(ui->nvdec_emulation->currentIndex()); - } + return Settings::NvdecEmulation::CPU; + // if (Settings::IsConfiguringGlobal()) { + // return static_cast(ui->nvdec_emulation->currentIndex()); + // } - if (ui->nvdec_emulation->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - Settings::values.nvdec_emulation.SetGlobal(true); - return Settings::values.nvdec_emulation.GetValue(); - } - Settings::values.nvdec_emulation.SetGlobal(false); - return static_cast(ui->nvdec_emulation->currentIndex() - - ConfigurationShared::USE_GLOBAL_OFFSET); + // if (ui->nvdec_emulation->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { + // Settings::values.nvdec_emulation.SetGlobal(true); + // return Settings::values.nvdec_emulation.GetValue(); + // } + // Settings::values.nvdec_emulation.SetGlobal(false); + // return static_cast(ui->nvdec_emulation->currentIndex() - + // ConfigurationShared::USE_GLOBAL_OFFSET); } void ConfigureGraphics::SetupPerGameUI() { - if (Settings::IsConfiguringGlobal()) { - ui->api->setEnabled(Settings::values.renderer_backend.UsingGlobal()); - ui->device->setEnabled(Settings::values.renderer_backend.UsingGlobal()); - ui->fullscreen_mode_combobox->setEnabled(Settings::values.fullscreen_mode.UsingGlobal()); - ui->aspect_ratio_combobox->setEnabled(Settings::values.aspect_ratio.UsingGlobal()); - ui->resolution_combobox->setEnabled(Settings::values.resolution_setup.UsingGlobal()); - ui->scaling_filter_combobox->setEnabled(Settings::values.scaling_filter.UsingGlobal()); - ui->fsr_sharpening_slider->setEnabled(Settings::values.fsr_sharpening_slider.UsingGlobal()); - ui->anti_aliasing_combobox->setEnabled(Settings::values.anti_aliasing.UsingGlobal()); - ui->use_asynchronous_gpu_emulation->setEnabled( - Settings::values.use_asynchronous_gpu_emulation.UsingGlobal()); - ui->nvdec_emulation->setEnabled(Settings::values.nvdec_emulation.UsingGlobal()); - ui->astc_decode_mode_combobox->setEnabled(Settings::values.accelerate_astc.UsingGlobal()); - ui->use_disk_shader_cache->setEnabled(Settings::values.use_disk_shader_cache.UsingGlobal()); - ui->bg_button->setEnabled(Settings::values.bg_red.UsingGlobal()); - ui->fsr_slider_layout->setEnabled(Settings::values.fsr_sharpening_slider.UsingGlobal()); + // if (Settings::IsConfiguringGlobal()) { + // api_combobox->setEnabled(Settings::values.renderer_backend.UsingGlobal()); + // vulkan_device_combobox->setEnabled(Settings::values.renderer_backend.UsingGlobal()); + // ui->fullscreen_mode_combobox->setEnabled(Settings::values.fullscreen_mode.UsingGlobal()); + // ui->aspect_ratio_combobox->setEnabled(Settings::values.aspect_ratio.UsingGlobal()); + // ui->resolution_combobox->setEnabled(Settings::values.resolution_setup.UsingGlobal()); + // ui->scaling_filter_combobox->setEnabled(Settings::values.scaling_filter.UsingGlobal()); + // ui->fsr_sharpening_slider->setEnabled(Settings::values.fsr_sharpening_slider.UsingGlobal()); + // ui->anti_aliasing_combobox->setEnabled(Settings::values.anti_aliasing.UsingGlobal()); + // ui->use_asynchronous_gpu_emulation->setEnabled( + // Settings::values.use_asynchronous_gpu_emulation.UsingGlobal()); + // ui->nvdec_emulation->setEnabled(Settings::values.nvdec_emulation.UsingGlobal()); + // ui->astc_decode_mode_combobox->setEnabled(Settings::values.accelerate_astc.UsingGlobal()); + // ui->use_disk_shader_cache->setEnabled(Settings::values.use_disk_shader_cache.UsingGlobal()); + // ui->bg_button->setEnabled(Settings::values.bg_red.UsingGlobal()); + // ui->fsr_slider_layout->setEnabled(Settings::values.fsr_sharpening_slider.UsingGlobal()); - return; - } + // return; + // } - connect(ui->bg_combobox, qOverload(&QComboBox::activated), this, [this](int index) { - ui->bg_button->setEnabled(index == 1); - ConfigurationShared::SetHighlight(ui->bg_layout, index == 1); - }); + // connect(ui->bg_combobox, qOverload(&QComboBox::activated), this, [this](int index) { + // ui->bg_button->setEnabled(index == 1); + // ConfigurationShared::SetHighlight(ui->bg_layout, index == 1); + // }); - connect(ui->fsr_sharpening_combobox, qOverload(&QComboBox::activated), this, - [this](int index) { - ui->fsr_sharpening_slider->setEnabled(index == 1); - ui->fsr_sharpening_value->setEnabled(index == 1); - ConfigurationShared::SetHighlight(ui->fsr_sharpening_layout, index == 1); - }); + // connect(ui->fsr_sharpening_combobox, qOverload(&QComboBox::activated), this, + // [this](int index) { + // ui->fsr_sharpening_slider->setEnabled(index == 1); + // ui->fsr_sharpening_value->setEnabled(index == 1); + // ConfigurationShared::SetHighlight(ui->fsr_sharpening_layout, index == 1); + // }); - ConfigurationShared::SetColoredTristate( - ui->use_disk_shader_cache, Settings::values.use_disk_shader_cache, use_disk_shader_cache); - ConfigurationShared::SetColoredTristate(ui->use_asynchronous_gpu_emulation, - Settings::values.use_asynchronous_gpu_emulation, - use_asynchronous_gpu_emulation); + // ConfigurationShared::SetColoredTristate( + // ui->use_disk_shader_cache, Settings::values.use_disk_shader_cache, + // use_disk_shader_cache); + // ConfigurationShared::SetColoredTristate(ui->use_asynchronous_gpu_emulation, + // Settings::values.use_asynchronous_gpu_emulation, + // use_asynchronous_gpu_emulation); - ConfigurationShared::SetColoredComboBox(ui->aspect_ratio_combobox, ui->ar_label, - Settings::values.aspect_ratio.GetValue(true)); - ConfigurationShared::SetColoredComboBox( - ui->fullscreen_mode_combobox, ui->fullscreen_mode_label, - static_cast(Settings::values.fullscreen_mode.GetValue(true))); - ConfigurationShared::SetColoredComboBox( - ui->resolution_combobox, ui->resolution_label, - static_cast(Settings::values.resolution_setup.GetValue(true))); - ConfigurationShared::SetColoredComboBox( - ui->scaling_filter_combobox, ui->scaling_filter_label, - static_cast(Settings::values.scaling_filter.GetValue(true))); - ConfigurationShared::SetColoredComboBox( - ui->anti_aliasing_combobox, ui->anti_aliasing_label, - static_cast(Settings::values.anti_aliasing.GetValue(true))); - ConfigurationShared::SetColoredComboBox( - ui->astc_decode_mode_combobox, ui->astc_decode_mode_label, - static_cast(Settings::values.accelerate_astc.GetValue(true))); - ConfigurationShared::InsertGlobalItem( - ui->api, static_cast(Settings::values.renderer_backend.GetValue(true))); - ConfigurationShared::InsertGlobalItem( - ui->nvdec_emulation, static_cast(Settings::values.nvdec_emulation.GetValue(true))); + // ConfigurationShared::SetColoredComboBox(ui->aspect_ratio_combobox, ui->ar_label, + // Settings::values.aspect_ratio.GetValue(true)); + // ConfigurationShared::SetColoredComboBox( + // ui->fullscreen_mode_combobox, ui->fullscreen_mode_label, + // static_cast(Settings::values.fullscreen_mode.GetValue(true))); + // ConfigurationShared::SetColoredComboBox( + // ui->resolution_combobox, ui->resolution_label, + // static_cast(Settings::values.resolution_setup.GetValue(true))); + // ConfigurationShared::SetColoredComboBox( + // ui->scaling_filter_combobox, ui->scaling_filter_label, + // static_cast(Settings::values.scaling_filter.GetValue(true))); + // ConfigurationShared::SetColoredComboBox( + // ui->anti_aliasing_combobox, ui->anti_aliasing_label, + // static_cast(Settings::values.anti_aliasing.GetValue(true))); + // ConfigurationShared::SetColoredComboBox( + // ui->astc_decode_mode_combobox, ui->astc_decode_mode_label, + // static_cast(Settings::values.accelerate_astc.GetValue(true))); + // ConfigurationShared::InsertGlobalItem( + // api_combobox, static_cast(Settings::values.renderer_backend.GetValue(true))); + // ConfigurationShared::InsertGlobalItem( + // ui->nvdec_emulation, static_cast(Settings::values.nvdec_emulation.GetValue(true))); - ui->vsync_mode_layout->setVisible(false); + // ui->vsync_mode_layout->setVisible(false); } diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index adc3faffa..30dfb6163 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -17,6 +17,7 @@ class QEvent; class QObject; +class QComboBox; namespace Settings { enum class NvdecEmulation : u32; @@ -38,6 +39,7 @@ public: std::vector& records, const std::function& expose_compute_option_, std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, QWidget* parent = nullptr); ~ConfigureGraphics() override; @@ -70,10 +72,8 @@ private: std::unique_ptr ui; QColor bg_color; - ConfigurationShared::CheckState use_nvdec_emulation; - ConfigurationShared::CheckState accelerate_astc; - ConfigurationShared::CheckState use_disk_shader_cache; - ConfigurationShared::CheckState use_asynchronous_gpu_emulation; + std::list trackers{}; + std::forward_list> apply_funcs{}; std::vector& records; std::vector vulkan_devices; @@ -86,4 +86,12 @@ private: const std::function& expose_compute_option; const Core::System& system; + const ConfigurationShared::TranslationMap& translations; + + QComboBox* vulkan_device_combobox; + QComboBox* api_combobox; + QComboBox* shader_backend_combobox; + QComboBox* vsync_mode_combobox; + QWidget* vulkan_device_widget; + QWidget* shader_backend_widget; }; diff --git a/src/yuzu/configuration/configure_graphics.ui b/src/yuzu/configuration/configure_graphics.ui index 91b09625b..565429c98 100644 --- a/src/yuzu/configuration/configure_graphics.ui +++ b/src/yuzu/configuration/configure_graphics.ui @@ -43,112 +43,6 @@ 6 - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Shader Backend: - - - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Device: - - - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - API: - - - - - - - - 0 - 0 - - - - - OpenGL - - - - - Vulkan - - - - - None - - - - - - - @@ -168,649 +62,8 @@ - - - Use disk pipeline cache - - - - - - - Use asynchronous GPU emulation - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - VSync Mode: - - - - - - - FIFO (VSync) does not drop frames or exhibit tearing but is limited by the screen refresh rate. -FIFO Relaxed is similar to FIFO but allows tearing as it recovers from a slow down. -Mailbox can have lower latency than FIFO and does not tear but may drop frames. -Immediate (no synchronization) just presents whatever is available and can exhibit tearing. - - - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - ASTC Texture Decoding Method: - - - - - - - - CPU - - - - - GPU Compute - - - - - CPU Asynchronous (Hack) - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - NVDEC emulation: - - - - - - - - No Video Output - - - - - CPU Video Decoding - - - - - GPU Video Decoding (Default) - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Fullscreen Mode: - - - - - - - - Borderless Windowed - - - - - Exclusive Fullscreen - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Aspect Ratio: - - - - - - - - Default (16:9) - - - - - Force 4:3 - - - - - Force 21:9 - - - - - Force 16:10 - - - - - Stretch to Window - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Resolution: - - - - - - - - 0.5X (360p/540p) [EXPERIMENTAL] - - - - - 0.75X (540p/810p) [EXPERIMENTAL] - - - - - 1X (720p/1080p) - - - - - 1.5X (1080p/1620p) [EXPERIMENTAL] - - - - - 2X (1440p/2160p) - - - - - 3X (2160p/3240p) - - - - - 4X (2880p/4320p) - - - - - 5X (3600p/5400p) - - - - - 6X (4320p/6480p) - - - - - 7X (5040p/7560p) - - - - - 8X (5760p/8640p) - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Window Adapting Filter: - - - - - - - - Nearest Neighbor - - - - - Bilinear - - - - - Bicubic - - - - - Gaussian - - - - - ScaleForce - - - - - AMD FidelityFX™️ Super Resolution - - - - - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Anti-Aliasing Method: - - - - - - - - None - - - - - FXAA - - - - - SMAA - - - - - - - - - - - true - - - - 0 - 0 - - - - - 6 - - - QLayout::SetDefaultConstraint - - - 0 - - - 0 - - - 0 - - - 0 - - - - - 0 - - - 0 - - - - - - 0 - 0 - - - - - Use global FSR Sharpness - - - - - Set FSR Sharpness - - - - - - - - - 0 - 0 - - - - FSR Sharpness: - - - - - - - Qt::Horizontal - - - - 40 - 20 - - - - - - - - - - 6 - - - - - - 0 - 0 - - - - - 0 - 0 - - - - 200 - - - 25 - - - Qt::Horizontal - - - true - - - - - - - - 0 - 0 - - - - - 32 - 0 - - - - 100% - - - Qt::AlignCenter - - - - - - - - - - - - - 0 - 0 - - - - - 6 - - - 0 - - - 0 - - - 0 - - - 0 - - - - - Use global background color - - - 0 - - - 10 - - - - Use global background color - - - - - Set background color: - - - - - - - - Background Color: - - - - - - - Qt::Horizontal - - - - 40 - 20 - - - - - - - - - 40 - 16777215 - - - - - + + diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 7d79044d4..8a9495109 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -32,8 +32,8 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { for (auto setting : Settings::values.linkage.by_category[Settings::Category::RendererAdvanced]) { - QWidget* widget = ConfigurationShared::CreateWidget(setting, translations, this, - runtime_lock, apply_funcs, trackers); + auto [widget, extra] = ConfigurationShared::CreateWidget( + setting, translations, this, runtime_lock, apply_funcs, trackers); if (widget == nullptr) { continue; diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index 339768017..9e229977d 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -58,7 +58,7 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st std::make_unique(system_, tab_group, *translations, this); graphics_tab = std::make_unique( system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, - tab_group, this); + tab_group, *translations, this); input_tab = std::make_unique(system_, game_config.get(), this); system_tab = std::make_unique(system_, tab_group, this); diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index ddc7569f1..73c3086ae 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -36,6 +36,7 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { // Cpu INSERT("cpu_accuracy", "Accuracy:", ""); + INSERT("cpu_accuracy_first_time", "", ""); // Cpu Debug INSERT("cpu_debug_mode", "Enable CPU Debugging", ""); @@ -75,13 +76,16 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT("use_disk_shader_cache", "Use disk pipeline cache", ""); INSERT("use_asynchronous_gpu_emulation", "Use asynchronous GPU emulation", ""); INSERT("nvdec_emulation", "NVDEC emulation:", ""); - INSERT("acclerate_astc", "ASTC Decoding Method:", ""); + INSERT("accelerate_astc", "ASTC Decoding Method:", ""); INSERT( "use_vsync", "VSync Mode:", "FIFO (VSync) does not drop frames or exhibit tearing but is limited by the screen refresh " "rate. FIFO Relaxed is similar to FIFO but allows tearing as it recovers from a slow down. " "Mailbox can have lower latency than FIFO and does not tear but may drop frames. Immediate " "(no synchronization) just presents whatever is available and can exhibit tearing."); + INSERT("bg_red", "", ""); + INSERT("bg_green", "", ""); + INSERT("bg_blue", "", ""); // Renderer (Advanced Graphics) INSERT("async_presentation", "Enable asynchronous presentation (Vulkan only)", ""); @@ -104,9 +108,6 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { "Enable compute pipelines, required by some games.\nThis setting only exists for Intel " "proprietary drivers, and may crash if enabled.\nCompute pipelines are always enabled " "on all other drivers."); - INSERT("bg_red", "Background Color:", ""); - INSERT("bg_green", "Background Color:", ""); - INSERT("bg_blue", "Background Color:", ""); // Renderer (Debug) INSERT("debug", "Enable Graphics Debugging", From bafd569b4768d3888798db8b8e71359b4b844579 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 7 May 2023 12:51:12 -0400 Subject: [PATCH 014/155] settings,uisettings: Add IDs to settings --- src/common/settings.h | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 8f02fa9af..69777421e 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -191,6 +191,7 @@ public: virtual bool IsEnum() const = 0; virtual bool RuntimeModfiable() const = 0; virtual void SetGlobal(bool global) {} + virtual u32 Id() const = 0; virtual bool UsingGlobal() const { return false; } @@ -200,6 +201,7 @@ class Linkage { public: std::map> by_category; std::vector> restore_functions; + u32 count; }; /** The Setting class is a simple resource manager. It defines a label and default value @@ -232,8 +234,10 @@ public: explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, enum Category category_) requires(!ranged) - : value{default_val}, default_value{default_val}, label{name}, category{category_} { + : value{default_val}, + default_value{default_val}, label{name}, category{category_}, id{linkage.count} { linkage.by_category[category].push_front(this); + linkage.count++; } virtual ~Setting() = default; @@ -251,8 +255,9 @@ public: const Type& max_val, const std::string& name, enum Category category_) requires(ranged) : value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val}, - label{name}, category{category_} { + label{name}, category{category_}, id{linkage.count} { linkage.by_category[category].push_front(this); + linkage.count++; } /** @@ -418,6 +423,10 @@ public: return std::type_index(typeid(Type)); } + virtual u32 Id() const override { + return id; + } + protected: Type value{}; ///< The setting const Type default_value{}; ///< The default value @@ -425,6 +434,7 @@ protected: const Type minimum{}; ///< Minimum allowed value of the setting const std::string label{}; ///< The setting's label const enum Category category; ///< The setting's category AKA INI group + const u32 id; }; /** @@ -728,7 +738,7 @@ struct Values { linkage, VSyncMode::FIFO, VSyncMode::Immediate, VSyncMode::FIFORelaxed, "use_vsync", Category::Renderer}; SwitchableSetting use_reactive_flushing{linkage, true, "use_reactive_flushing", - Category::Renderer}; + Category::RendererAdvanced}; SwitchableSetting shader_backend{ linkage, ShaderBackend::GLSL, ShaderBackend::GLSL, ShaderBackend::SPIRV, "shader_backend", Category::Renderer}; From cfb63c68dbdc2c8add45cddb2cedf371059af6c4 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 7 May 2023 13:28:52 -0400 Subject: [PATCH 015/155] shared_translation: Finish using int ids --- src/common/settings.h | 4 +- .../configuration/configuration_shared.cpp | 6 +- src/yuzu/configuration/configure_graphics.cpp | 25 +- .../configure_graphics_advanced.cpp | 2 +- src/yuzu/configuration/shared_translation.cpp | 236 +++++++----------- src/yuzu/configuration/shared_translation.h | 2 +- 6 files changed, 117 insertions(+), 158 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 69777421e..a90fc87a7 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -191,7 +191,7 @@ public: virtual bool IsEnum() const = 0; virtual bool RuntimeModfiable() const = 0; virtual void SetGlobal(bool global) {} - virtual u32 Id() const = 0; + virtual constexpr u32 Id() const = 0; virtual bool UsingGlobal() const { return false; } @@ -423,7 +423,7 @@ public: return std::type_index(typeid(Type)); } - virtual u32 Id() const override { + virtual constexpr u32 Id() const override { return id; } diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 575d239eb..54fbce53a 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -136,6 +136,7 @@ std::pair CreateWidget(Settings::BasicSetting* setting, std::forward_list>& apply_funcs, std::list& trackers, RequestType request) { const auto type = setting->TypeId(); + const int id = setting->Id(); QWidget* widget{nullptr}; void* extra{nullptr}; @@ -143,9 +144,8 @@ std::pair CreateWidget(Settings::BasicSetting* setting, const auto [label, tooltip] = [&]() { const auto& setting_label = setting->GetLabel(); - if (translations.contains(setting_label)) { - return std::pair{translations.at(setting_label).first, - translations.at(setting_label).second}; + if (translations.contains(id)) { + return std::pair{translations.at(id).first, translations.at(id).second}; } LOG_ERROR(Frontend, "Translation table lacks entry for \"{}\"", setting_label); return std::pair{QString::fromStdString(setting_label), QStringLiteral("")}; diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 8128a4047..d8e95b9b1 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -214,13 +214,13 @@ void ConfigureGraphics::SetConfiguration() { QLayout& api_layout = *ui->api_widget->layout(); QLayout& graphics_layout = *ui->graphics_widget->layout(); - std::map hold_graphics; + std::map> hold_graphics; for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { const auto& setting_label = setting->GetLabel(); auto [widget, extra] = [&]() { - if (setting_label == "vulkan_device") { + if (setting->Id() == Settings::values.vulkan_device.Id()) { return ConfigurationShared::CreateWidget( setting, translations, this, runtime_lock, apply_funcs, trackers, ConfigurationShared::RequestType::ComboBox); @@ -233,28 +233,29 @@ void ConfigureGraphics::SetConfiguration() { continue; } - if (setting_label == "backend") { + if (setting->Id() == Settings::values.vulkan_device.Id()) { api_layout.addWidget(widget); api_combobox = reinterpret_cast(extra); - } else if (setting_label == "vulkan_device") { + } else if (setting->Id() == Settings::values.vulkan_device.Id()) { api_layout.addWidget(widget); vulkan_device_combobox = reinterpret_cast(extra); vulkan_device_widget = widget; - } else if (setting_label == "shader_backend") { + } else if (setting->Id() == Settings::values.shader_backend.Id()) { api_layout.addWidget(widget); shader_backend_combobox = reinterpret_cast(extra); shader_backend_widget = widget; - } else { - hold_graphics.insert(std::pair(setting_label, widget)); - } - - if (setting_label == "use_vsync") { + } else if (setting->Id() == Settings::values.vsync_mode.Id()) { vsync_mode_combobox = reinterpret_cast(extra); + hold_graphics[setting->IsEnum()][setting_label] = widget; + } else { + hold_graphics[setting->IsEnum()][setting_label] = widget; } } - for (const auto& [label, widget] : hold_graphics) { - graphics_layout.addWidget(widget); + for (const auto& [_, settings] : hold_graphics) { + for (const auto& [label, widget] : settings) { + graphics_layout.addWidget(widget); + } } // ui->api_widget->setEnabled(runtime_lock); diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 8a9495109..3a207e2cd 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -45,7 +45,7 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { layout.addWidget(widget); } - if (setting->GetLabel() == "enable_compute_pipelines") { + if (setting->Id() == Settings::values.enable_compute_pipelines.Id()) { checkbox_enable_compute_pipelines = widget; } } diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 73c3086ae..181dd7cf0 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -18,196 +18,111 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { std::unique_ptr translations = std::make_unique(); const auto& tr = [parent](const char* text) -> QString { return parent->tr(text); }; -#define INSERT(LABEL, NAME, TOOLTIP) \ - translations->insert(std::pair{(LABEL), std::pair{tr((NAME)), tr((TOOLTIP))}}) +#define INSERT(ID, NAME, TOOLTIP) \ + translations->insert(std::pair{Settings::values.ID.Id(), std::pair{tr((NAME)), tr((TOOLTIP))}}) // A setting can be ignored by giving it a blank name // Audio - INSERT("output_engine", "Output Engine:", ""); - INSERT("output_device", "Output Device:", ""); - INSERT("input_device", "Input Device:", ""); - INSERT("audio_muted", "Mute audio when in background", ""); - INSERT("volume", "Volume:", ""); + INSERT(sink_id, "Output Engine:", ""); + INSERT(audio_output_device_id, "Output Device:", ""); + INSERT(audio_input_device_id, "Input Device:", ""); + INSERT(audio_muted, "Mute audio when in background", ""); + INSERT(volume, "Volume:", ""); // Core - INSERT("use_multi_core", "Multicore CPU Emulation", ""); - INSERT("use_unsafe_extended_memory_layout", "Unsafe extended memory layout (8GB DRAM)", ""); + INSERT(use_multi_core, "Multicore CPU Emulation", ""); + INSERT(use_unsafe_extended_memory_layout, "Unsafe extended memory layout (8GB DRAM)", ""); // Cpu - INSERT("cpu_accuracy", "Accuracy:", ""); - INSERT("cpu_accuracy_first_time", "", ""); + INSERT(cpu_accuracy, "Accuracy:", ""); + INSERT(cpu_accuracy_first_time, "", ""); // Cpu Debug - INSERT("cpu_debug_mode", "Enable CPU Debugging", ""); - INSERT("cpuopt_page_tables", "Enable inline page tables", ""); - INSERT("cpuopt_block_linking", "Enable block linking", ""); - INSERT("cpuopt_return_stack_buffer", "Enable return stack buffer", ""); - INSERT("cpuopt_fast_dispatcher", "Enable fast dispatcher", ""); - INSERT("cpuopt_context_elimination", "Enable context elimination", ""); - INSERT("cpuopt_const_prop", "Enable constant propagation", ""); - INSERT("cpuopt_misc_ir", "Enable miscellaneous optimizations", ""); - INSERT("cpuopt_reduce_misalign_checks", "Enable misalignment check reduction", ""); - INSERT("cpuopt_fastmem", "Enable Host MMU Emulation (general memory instructions)", ""); - INSERT("cpuopt_fastmem_exclusives", "Enable Host MMU Emulation (exclusive memory instructions)", - ""); - INSERT("cpuopt_recompile_exclusives", "Enable recompilation of exlucsive memory instructions", - ""); - INSERT("cpuopt_ignore_memory_aborts", "Enable fallbacks for invalid memory accesses", ""); // Cpu Unsafe - INSERT("cpuopt_unsafe_unfuse_fma", "Unfuse FMA (improve performance on CPUs without FMA)", ""); - INSERT("cpuopt_unsafe_reduce_fp_error", "Faster FRSQRTE and FRECPE", ""); - INSERT("cpuopt_unsafe_ignore_standard_fpcr", "Faster ASIMD instructions (32 bits only)", ""); - INSERT("cpuopt_unsafe_inaccurate_nan", "Inaccurate NaN handling", ""); - INSERT("cpuopt_unsafe_fastmem_check", "Disable address space checks", ""); - INSERT("cpuopt_unsafe_ignore_global_monitor", "Ignore global monitor", ""); + INSERT(cpuopt_unsafe_unfuse_fma, "Unfuse FMA (improve performance on CPUs without FMA)", ""); + INSERT(cpuopt_unsafe_reduce_fp_error, "Faster FRSQRTE and FRECPE", ""); + INSERT(cpuopt_unsafe_ignore_standard_fpcr, "Faster ASIMD instructions (32 bits only)", ""); + INSERT(cpuopt_unsafe_inaccurate_nan, "Inaccurate NaN handling", ""); + INSERT(cpuopt_unsafe_fastmem_check, "Disable address space checks", ""); + INSERT(cpuopt_unsafe_ignore_global_monitor, "Ignore global monitor", ""); // Renderer - INSERT("backend", "API:", ""); - INSERT("vulkan_device", "Device:", ""); - INSERT("shader_backend", "Shader Backend:", ""); - INSERT("resolution_setup", "Resolution:", ""); - INSERT("scaling_filter", "Window Adapting Filter:", ""); - INSERT("fsr_sharpening_slider", "AMD FidelityFX™ Super Resolution Sharpness:", ""); - INSERT("anti_aliasing", "Anti-Aliasing Method:", ""); - INSERT("fullscreen_mode", "Fullscreen Mode:", ""); - INSERT("aspect_ratio", "Aspect Ratio:", ""); - INSERT("use_disk_shader_cache", "Use disk pipeline cache", ""); - INSERT("use_asynchronous_gpu_emulation", "Use asynchronous GPU emulation", ""); - INSERT("nvdec_emulation", "NVDEC emulation:", ""); - INSERT("accelerate_astc", "ASTC Decoding Method:", ""); + INSERT(renderer_backend, "API:", ""); + INSERT(vulkan_device, "Device:", ""); + INSERT(shader_backend, "Shader Backend:", ""); + INSERT(resolution_setup, "Resolution:", ""); + INSERT(scaling_filter, "Window Adapting Filter:", ""); + INSERT(fsr_sharpening_slider, "AMD FidelityFX™ Super Resolution Sharpness:", ""); + INSERT(anti_aliasing, "Anti-Aliasing Method:", ""); + INSERT(fullscreen_mode, "Fullscreen Mode:", ""); + INSERT(aspect_ratio, "Aspect Ratio:", ""); + INSERT(use_disk_shader_cache, "Use disk pipeline cache", ""); + INSERT(use_asynchronous_gpu_emulation, "Use asynchronous GPU emulation", ""); + INSERT(nvdec_emulation, "NVDEC emulation:", ""); + INSERT(accelerate_astc, "ASTC Decoding Method:", ""); INSERT( - "use_vsync", "VSync Mode:", + vsync_mode, "VSync Mode:", "FIFO (VSync) does not drop frames or exhibit tearing but is limited by the screen refresh " "rate. FIFO Relaxed is similar to FIFO but allows tearing as it recovers from a slow down. " "Mailbox can have lower latency than FIFO and does not tear but may drop frames. Immediate " "(no synchronization) just presents whatever is available and can exhibit tearing."); - INSERT("bg_red", "", ""); - INSERT("bg_green", "", ""); - INSERT("bg_blue", "", ""); + INSERT(bg_red, "", ""); + INSERT(bg_green, "", ""); + INSERT(bg_blue, "", ""); // Renderer (Advanced Graphics) - INSERT("async_presentation", "Enable asynchronous presentation (Vulkan only)", ""); - INSERT("force_max_clock", "Force maximum clocks (Vulkan only)", + INSERT(async_presentation, "Enable asynchronous presentation (Vulkan only)", ""); + INSERT(renderer_force_max_clock, "Force maximum clocks (Vulkan only)", "Runs work in the background while waiting for graphics commands to keep the GPU from " "lowering its clock speed."); - INSERT("max_anisotropy", "Anisotropic Filtering:", ""); - INSERT("gpu_accuracy", "Accuracy Level:", ""); - INSERT("use_asynchronous_shaders", "Use asynchronous shader building (Hack)", + INSERT(max_anisotropy, "Anisotropic Filtering:", ""); + INSERT(gpu_accuracy, "Accuracy Level:", ""); + INSERT(use_asynchronous_shaders, "Use asynchronous shader building (Hack)", "Enables asynchronous shader compilation, which may reduce shader stutter. This feature " "is experimental."); - INSERT("use_fast_gpu_time", "Use Fast GPU Time (Hack)", + INSERT(use_fast_gpu_time, "Use Fast GPU Time (Hack)", "Enables Fast GPU Time. This option will force most games to run at their highest " "native resolution."); - INSERT("use_vulkan_driver_pipeline_cache", "Use Vulkan pipeline cache", + INSERT(use_vulkan_driver_pipeline_cache, "Use Vulkan pipeline cache", "Enables GPU vendor-specific pipeline cache. This option can improve shader loading " "time significantly in cases where the Vulkan driver does not store pipeline cache " "files internally."); - INSERT("enable_compute_pipelines", "Enable Compute Pipelines (Intel Vulkan Only)", + INSERT(enable_compute_pipelines, "Enable Compute Pipelines (Intel Vulkan Only)", "Enable compute pipelines, required by some games.\nThis setting only exists for Intel " "proprietary drivers, and may crash if enabled.\nCompute pipelines are always enabled " "on all other drivers."); // Renderer (Debug) - INSERT("debug", "Enable Graphics Debugging", - "When checked, the graphics API enters a slower debugging mode"); - INSERT("shader_feedback", "Enable Shader Feedback", - "When checked, yuzu will log statistics about the compiled pipeline cache"); - INSERT("nsight_aftermath", "Enable Nsight Aftermath", - "When checked, it enables Nsight Aftermath crash dumps"); - INSERT("disable_shader_loop_safety_checks", "Disable Loop safety checks", - "When checked, it executes shaders without loop logic changes"); // Renderer (General) - INSERT("use_speed_limit", "Limit Speed Percent", ""); - INSERT("speed_limit", "Limit Speed Percent", ""); + INSERT(use_speed_limit, "Limit Speed Percent", ""); + INSERT(speed_limit, "Limit Speed Percent", ""); // System - INSERT("rng_seed_enabled", "RNG Seed", ""); - INSERT("rng_seed", "RNG Seed", ""); - INSERT("device_name", "Device Name", ""); - INSERT("custom_rtc_enabled", "Custom RTC", ""); - INSERT("custom_rtc", "Custom RTC", ""); - INSERT("language_index", "Language:", ""); - INSERT("region_index", "Region:", ""); - INSERT("time_zone_index", "Time Zone:", ""); - INSERT("sound_index", "Sound Output Mode:", ""); - INSERT("use_docked_mode", "", ""); + INSERT(rng_seed_enabled, "RNG Seed", ""); + INSERT(rng_seed, "RNG Seed", ""); + INSERT(device_name, "Device Name", ""); + INSERT(custom_rtc_enabled, "Custom RTC", ""); + INSERT(custom_rtc, "Custom RTC", ""); + INSERT(language_index, "Language:", ""); + INSERT(region_index, "Region:", ""); + INSERT(time_zone_index, "Time Zone:", ""); + INSERT(sound_index, "Sound Output Mode:", ""); + INSERT(use_docked_mode, "", ""); // Controls - INSERT("enable_raw_input", "", ""); - INSERT("controller_navigation", "", ""); - INSERT("enable_joycon_driver", "", ""); - INSERT("enable_procon_driver", "", ""); - INSERT("vibration_enabled", "", ""); - INSERT("enable_accurate_vibrations", "", ""); - INSERT("motion_enabled", "", ""); - INSERT("udp_input_servers", "", ""); - INSERT("enable_udp_controller", "", ""); - INSERT("pause_tas_on_load", "", ""); - INSERT("tas_enable", "", ""); - INSERT("tas_loop", "", ""); - INSERT("mouse_panning", "", ""); - INSERT("mouse_panning_sensitivity", "", ""); - INSERT("mouse_enabled", "", ""); - INSERT("emulate_analog_keyboard", "", ""); - INSERT("keyboard_enabled", "", ""); - INSERT("debug_pad_enabled", "", ""); - INSERT("touch_device", "", ""); - INSERT("touch_from_button_map", "", ""); - INSERT("enable_ring_controller", "", ""); - INSERT("enable_ir_sensor", "", ""); - INSERT("ir_sensor_device", "", ""); // Data Storage - INSERT("use_virtual_sd", "", ""); - INSERT("gamecard_inserted", "Inserted", ""); - INSERT("gamecard_current_game", "Current Game", ""); - INSERT("gamecard_path", "Path", ""); // Debugging - INSERT("use_gdbstub", "Enable GDB Stub", ""); - INSERT("gdbstub_port", "Port:", ""); - INSERT("program_args", "Arguments String", ""); - INSERT("dump_exefs", "Dump ExeFS", ""); - INSERT("dump_nso", "Dump Decompressed NSOs", ""); - INSERT("enable_fs_access_log", "Enable FS Access Log", ""); - INSERT("reporting_services", "Enable Verbose Repoting Services**", ""); - INSERT("quest_flag", "Kiosk (Quest) Mode", ""); - INSERT("extended_logging", "Enable Extended Logging**", - "When checked, the max size of the log increases from 100 MB to 1 GB"); - INSERT("use_debug_asserts", "Enable Debug Asserts", ""); - INSERT("use_auto_stub", "Enable Auto-Stub**", ""); - INSERT("enable_all_controllers", "Enable All Controller Types", ""); - INSERT("create_crash_dumps", "Create Minidump After Crash", ""); - INSERT("perform_vulkan_check", "Perform Startup Vulkan Check", - "Enables yuzu to check for a working Vulkan environment when the program starts up. " - "Disable this if this is causing issues with external programs seeing yuzu."); - INSERT("log_filter", "Global Log Filter", ""); - INSERT("use_dev_keys", "", ""); // Debugging Graphics - INSERT("dump_shaders", "Dump Game Shaders", - "When checked, it will dump all the original assembler shaders from the disk shader " - "cache or game as found"); - INSERT("disable_macro_jit", "Disable Macro JIT", - "When checked, it disables the macro Just In Time compiler. Enabling this makes games " - "run slower"); - INSERT( - "disable_macro_hle", "Disable Macro HLE", - "When checked, it disables the macro HLE functions. Enabling this makes games run slower"); - INSERT("dump_macros", "Dump Maxwell Macros", - "When checked, it will dump all the macro programs of the GPU"); // Network - INSERT("network_interface", "Network Interface", ""); // Web Service - INSERT("enable_telemetry", "Share anonymous usage data with the yuzu team", ""); - INSERT("web_api_url", "", ""); - INSERT("yuzu_username", "", ""); - INSERT("yuzu_token", "Token:", ""); #undef INSERT @@ -241,6 +156,49 @@ std::forward_list ComboboxEnumeration(std::type_index type, QWidget* pa tr("High"), tr("Extreme"), }; + } else if (type == typeid(Settings::CPUAccuracy)) { + return { + tr("Auto"), + tr("Accurate"), + tr("Unsafe"), + tr("Paranoid (disables most optimizations)"), + }; + } else if (type == typeid(Settings::FullscreenMode)) { + return { + tr("Borderless Windowed"), + tr("Exclusive Fullscreen"), + }; + } else if (type == typeid(Settings::NvdecEmulation)) { + return { + tr("No Video Output"), + tr("CPU Video Decoding"), + tr("GPU Video Decoding (Default)"), + }; + } else if (type == typeid(Settings::ResolutionSetup)) { + return { + tr("0.5X (360p/540p) [EXPERIMENTAL]"), + tr("0.75X (540p/810p) [EXPERIMENTAL]"), + tr("1X (720p/1080p)"), + tr("1.5X (1080p/1620p) [EXPERIMENTAL]"), + tr("2X (1440p/2160p)"), + tr("3X (2160p/3240p)"), + tr("4X (2880p/4320p)"), + tr("5X (3600p/5400p)"), + tr("6X (4320p/6480p)"), + tr("7X (5040p/7560p)"), + tr("8X (5760p/8640p)"), + }; + } else if (type == typeid(Settings::ScalingFilter)) { + return { + tr("Nearest Neighbor"), tr("Bilinear"), tr("Bicubic"), + tr("Gaussian"), tr("ScaleForce"), tr("AMD FidelityFX™️ Super Resolution"), + }; + } else if (type == typeid(Settings::AntiAliasing)) { + return { + tr("None"), + tr("FXAA"), + tr("SMAA"), + }; } else if (type == typeid(Settings::AnisotropyMode)) { return { tr("Automatic"), tr("Default"), tr("2x"), tr("4x"), tr("8x"), tr("16x"), diff --git a/src/yuzu/configuration/shared_translation.h b/src/yuzu/configuration/shared_translation.h index 79cd08a6a..fcf638ea5 100644 --- a/src/yuzu/configuration/shared_translation.h +++ b/src/yuzu/configuration/shared_translation.h @@ -12,7 +12,7 @@ class QWidget; namespace ConfigurationShared { -using TranslationMap = std::map>; +using TranslationMap = std::map>; std::unique_ptr InitializeTranslations(QWidget* parent); From a4de202cbd5abdf46c48663874e34bdd028b6df5 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 7 May 2023 17:41:30 -0400 Subject: [PATCH 016/155] settings: Add anisotropy mode enum --- src/common/settings.h | 8 ++++++++ src/yuzu/configuration/shared_translation.cpp | 7 +++++++ 2 files changed, 15 insertions(+) diff --git a/src/common/settings.h b/src/common/settings.h index a90fc87a7..1c26081c9 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -116,6 +116,14 @@ enum class AstcRecompression : u32 { Bc3 = 2, }; +enum class AspectRatio : u32 { + R16_9, + R4_3, + R21_9, + R16_10, + Stretch, +}; + enum class Category : u32 { Audio, Core, diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 181dd7cf0..c20a3ebd9 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -132,6 +132,8 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { std::forward_list ComboboxEnumeration(std::type_index type, QWidget* parent) { const auto& tr = [&](const char* text) { return parent->tr(text); }; + // Intentionally skipping VSyncMode to let the UI fill that one out + if (type == typeid(Settings::AstcDecodeMode)) { return { tr("CPU"), @@ -199,6 +201,11 @@ std::forward_list ComboboxEnumeration(std::type_index type, QWidget* pa tr("FXAA"), tr("SMAA"), }; + } else if (type == typeid(Settings::AspectRatio)) { + return { + tr("Default (16:9)"), tr("Force 4:3"), tr("Force 21:9"), + tr("Force 16:10"), tr("Stretch to Window"), + }; } else if (type == typeid(Settings::AnisotropyMode)) { return { tr("Automatic"), tr("Default"), tr("2x"), tr("4x"), tr("8x"), tr("16x"), From 05c26411a399d415793fcc1c729ea00f87416b46 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 8 May 2023 09:33:23 -0400 Subject: [PATCH 017/155] configuration_shared: Fix blank state hiding check box --- src/yuzu/configuration/configuration_shared.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 54fbce53a..80637f3a2 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -253,8 +253,7 @@ void ConfigurationShared::SetHighlight(QWidget* widget, bool highlighted) { widget->setStyleSheet(QStringLiteral("QWidget#%1 { background-color:rgba(0,203,255,0.5) }") .arg(widget->objectName())); } else { - widget->setStyleSheet(QStringLiteral("QWidget#%1 { background-color:rgba(0,0,0,0) }") - .arg(widget->objectName())); + widget->setStyleSheet(QStringLiteral("")); } widget->show(); } From 3a7a5edceaec30b0c34c492724068a8dc20eb181 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 8 May 2023 10:03:40 -0400 Subject: [PATCH 018/155] settings: Define base renderer runtime modifiable settings --- src/common/settings.h | 43 ++++++++++--------- src/yuzu/configuration/configuration_shared.h | 9 ++-- 2 files changed, 27 insertions(+), 25 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 1c26081c9..2879237cc 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -701,32 +701,33 @@ struct Values { ResolutionScalingInfo resolution_info{}; SwitchableSetting resolution_setup{linkage, ResolutionSetup::Res1X, "resolution_setup", Category::Renderer}; - SwitchableSetting scaling_filter{linkage, ScalingFilter::Bilinear, - "scaling_filter", Category::Renderer}; - SwitchableSetting fsr_sharpening_slider{ + SwitchableSetting scaling_filter{ + linkage, ScalingFilter::Bilinear, "scaling_filter", Category::Renderer}; + SwitchableSetting fsr_sharpening_slider{ linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer}; - SwitchableSetting anti_aliasing{linkage, AntiAliasing::None, "anti_aliasing", - Category::Renderer}; + SwitchableSetting anti_aliasing{ + linkage, AntiAliasing::None, "anti_aliasing", Category::Renderer}; // *nix platforms may have issues with the borderless windowed fullscreen mode. // Default to exclusive fullscreen on these platforms for now. - SwitchableSetting fullscreen_mode{linkage, + SwitchableSetting fullscreen_mode{linkage, #ifdef _WIN32 - FullscreenMode::Borderless, + FullscreenMode::Borderless, #else - FullscreenMode::Exclusive, + FullscreenMode::Exclusive, #endif - FullscreenMode::Borderless, - FullscreenMode::Exclusive, - "fullscreen_mode", - Category::Renderer}; - SwitchableSetting aspect_ratio{linkage, 0, 0, 4, "aspect_ratio", Category::Renderer}; + FullscreenMode::Borderless, + FullscreenMode::Exclusive, + "fullscreen_mode", + Category::Renderer}; + SwitchableSetting aspect_ratio{ + linkage, 0, 0, 4, "aspect_ratio", Category::Renderer}; SwitchableSetting max_anisotropy{ linkage, AnisotropyMode::Automatic, AnisotropyMode::Automatic, AnisotropyMode::X16, "max_anisotropy", Category::RendererAdvanced}; - SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", - Category::Renderer}; - SwitchableSetting speed_limit{linkage, 100, 0, - 9999, "speed_limit", Category::Renderer}; + SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", + Category::Renderer}; + SwitchableSetting speed_limit{ + linkage, 100, 0, 9999, "speed_limit", Category::Renderer}; SwitchableSetting use_disk_shader_cache{linkage, true, "use_disk_shader_cache", Category::Renderer}; SwitchableSetting gpu_accuracy{ @@ -742,7 +743,7 @@ struct Values { AstcDecodeMode::CPUAsynchronous, "accelerate_astc", Category::Renderer}; - Setting vsync_mode{ + Setting vsync_mode{ linkage, VSyncMode::FIFO, VSyncMode::Immediate, VSyncMode::FIFORelaxed, "use_vsync", Category::Renderer}; SwitchableSetting use_reactive_flushing{linkage, true, "use_reactive_flushing", @@ -769,9 +770,9 @@ struct Values { SwitchableSetting barrier_feedback_loops{linkage, true, "barrier_feedback_loops", Category::RendererAdvanced}; - SwitchableSetting bg_red{linkage, 0, "bg_red", Category::Renderer}; - SwitchableSetting bg_green{linkage, 0, "bg_green", Category::Renderer}; - SwitchableSetting bg_blue{linkage, 0, "bg_blue", Category::Renderer}; + SwitchableSetting bg_red{linkage, 0, "bg_red", Category::Renderer}; + SwitchableSetting bg_green{linkage, 0, "bg_green", Category::Renderer}; + SwitchableSetting bg_blue{linkage, 0, "bg_blue", Category::Renderer}; // System SwitchableSetting rng_seed_enabled{linkage, false, "rng_seed_enabled", Category::System}; diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index d0fe6ea38..d70828935 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -92,10 +92,11 @@ void SetPerGameSetting(QComboBox* combobox, void SetHighlight(QWidget* widget, bool highlighted); // Sets up a QCheckBox like a tristate one, given a Setting -template -void SetColoredTristate(QCheckBox* checkbox, - const Settings::SwitchableSetting& setting, - CheckState& tracker) { +template +void SetColoredTristate( + QCheckBox* checkbox, + const Settings::SwitchableSetting& setting, + CheckState& tracker) { if (setting.UsingGlobal()) { tracker = CheckState::Global; } else { From 9a844bbf0cb14c9de33225ded27a78852e044df6 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 8 May 2023 10:04:44 -0400 Subject: [PATCH 019/155] configure_graphics: More complete reimplementation --- .../configuration/configuration_shared.cpp | 101 +++-- src/yuzu/configuration/configuration_shared.h | 3 +- src/yuzu/configuration/configure_graphics.cpp | 350 ++---------------- src/yuzu/configuration/configure_graphics.h | 4 +- 4 files changed, 113 insertions(+), 345 deletions(-) diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 80637f3a2..8d5ab8b4c 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -9,6 +9,7 @@ #include #include #include +#include #include #include "common/settings.h" #include "yuzu/configuration/configuration_shared.h" @@ -57,7 +58,7 @@ static std::pair> CreateCheckBox(Settings::Basic } static std::tuple> CreateCombobox( - Settings::BasicSetting* setting, const QString& label, QWidget* parent) { + Settings::BasicSetting* setting, const QString& label, QWidget* parent, bool managed) { const auto type = setting->TypeId(); QWidget* group = new QWidget(parent); @@ -78,7 +79,7 @@ static std::tuple> CreateCombobox( combobox_layout->setSpacing(6); combobox_layout->setContentsMargins(0, 0, 0, 0); - if (setting->Switchable() && !Settings::IsConfiguringGlobal()) { + if (setting->Switchable() && !Settings::IsConfiguringGlobal() && managed) { int current = std::stoi(setting->ToString()); int global_value = std::stoi(setting->ToStringGlobal()); SetColoredComboBox(combobox, group, global_value); @@ -92,23 +93,26 @@ static std::tuple> CreateCombobox( combobox->setCurrentIndex(std::stoi(setting->ToString())); } - const auto load_func = [combobox, setting]() { - if (Settings::IsConfiguringGlobal()) { - setting->LoadString(std::to_string(combobox->currentIndex())); - } + std::function load_func = []() {}; + if (managed) { + load_func = [combobox, setting]() { + if (Settings::IsConfiguringGlobal()) { + setting->LoadString(std::to_string(combobox->currentIndex())); + } - if (Settings::IsConfiguringGlobal() || !setting->Switchable()) { - return; - } + if (Settings::IsConfiguringGlobal() || !setting->Switchable()) { + return; + } - bool using_global = combobox->currentIndex() == USE_GLOBAL_INDEX; - int index = combobox->currentIndex() - USE_GLOBAL_OFFSET; + bool using_global = combobox->currentIndex() == USE_GLOBAL_INDEX; + int index = combobox->currentIndex() - USE_GLOBAL_OFFSET; - setting->SetGlobal(using_global); - if (!using_global) { - setting->LoadString(std::to_string(index)); - } - }; + setting->SetGlobal(using_global); + if (!using_global) { + setting->LoadString(std::to_string(index)); + } + }; + } return {group, combobox, load_func}; } @@ -116,25 +120,68 @@ static std::tuple> CreateCombobox( static std::tuple> CreateLineEdit( Settings::BasicSetting* setting, const QString& label, QWidget* parent) { QWidget* widget = new QWidget(parent); + widget->setObjectName(label); + QHBoxLayout* layout = new QHBoxLayout(widget); + QLineEdit* line_edit = new QLineEdit(parent); - QLabel* q_label = new QLabel(label, widget); - QLineEdit* line_edit = new QLineEdit(widget); + const QString text = QString::fromStdString(setting->ToString()); + line_edit->setText(text); + + std::function load_func; + + // setSizePolicy lets widget expand and take an equal part of the space as the line edit + if (Settings::IsConfiguringGlobal()) { + QLabel* q_label = new QLabel(label, widget); + q_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + layout->addWidget(q_label); + + load_func = [&]() { + std::string load_text = line_edit->text().toStdString(); + setting->LoadString(load_text); + }; + } else { + QCheckBox* checkbox = new QCheckBox(label, parent); + checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + layout->addWidget(checkbox); + + const auto highlight_func = [widget, line_edit](int state) { + bool using_global = state != Qt::Checked; + SetHighlight(widget, !using_global); + line_edit->setEnabled(!using_global); + }; + + QObject::connect(checkbox, qOverload(&QCheckBox::stateChanged), widget, + highlight_func); + + checkbox->setCheckState(setting->UsingGlobal() ? Qt::Unchecked : Qt::Checked); + highlight_func(checkbox->checkState()); + + load_func = [&]() { + if (checkbox->checkState() == Qt::Checked) { + setting->SetGlobal(false); + + std::string load_text = line_edit->text().toStdString(); + setting->LoadString(load_text); + } else { + setting->SetGlobal(true); + } + }; + } - layout->addWidget(q_label); - layout->addStretch(); layout->addWidget(line_edit); layout->setContentsMargins(0, 0, 0, 0); - return {widget, line_edit, []() {}}; + return {widget, line_edit, load_func}; } std::pair CreateWidget(Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, bool runtime_lock, std::forward_list>& apply_funcs, - std::list& trackers, RequestType request) { + std::list& trackers, RequestType request, + bool managed) { const auto type = setting->TypeId(); const int id = setting->Id(); QWidget* widget{nullptr}; @@ -162,7 +209,7 @@ std::pair CreateWidget(Settings::BasicSetting* setting, widget = pair.first; load_func = pair.second; } else if (setting->IsEnum()) { - auto tuple = CreateCombobox(setting, label, parent); + auto tuple = CreateCombobox(setting, label, parent, managed); widget = std::get<0>(tuple); extra = std::get<1>(tuple); load_func = std::get<2>(tuple); @@ -176,7 +223,7 @@ std::pair CreateWidget(Settings::BasicSetting* setting, break; } case RequestType::ComboBox: { - auto tuple = CreateCombobox(setting, label, parent); + auto tuple = CreateCombobox(setting, label, parent, managed); widget = std::get<0>(tuple); extra = std::get<1>(tuple); load_func = std::get<2>(tuple); @@ -201,9 +248,9 @@ std::pair CreateWidget(Settings::BasicSetting* setting, }); bool enable = runtime_lock || setting->RuntimeModfiable(); - enable &= - setting->Switchable() && !(Settings::IsConfiguringGlobal() && !setting->UsingGlobal()); - enable |= !setting->Switchable() && Settings::IsConfiguringGlobal() && runtime_lock; + if (setting->Switchable() && Settings::IsConfiguringGlobal() && !runtime_lock) { + enable &= !setting->UsingGlobal(); + } widget->setEnabled(enable); widget->setVisible(Settings::IsConfiguringGlobal() || setting->Switchable()); diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index d70828935..942af0215 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -54,7 +54,8 @@ std::pair CreateWidget(Settings::BasicSetting* setting, bool runtime_lock, std::forward_list>& apply_funcs, std::list& trackers, - RequestType request = RequestType::Default); + RequestType request = RequestType::Default, + bool managed = true); // Global-aware apply and set functions diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index d8e95b9b1..37a10ac87 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -55,20 +55,20 @@ static constexpr VkPresentModeKHR VSyncSettingToMode(Settings::VSyncMode mode) { } } -// static constexpr Settings::VSyncMode PresentModeToSetting(VkPresentModeKHR mode) { -// switch (mode) { -// case VK_PRESENT_MODE_IMMEDIATE_KHR: -// return Settings::VSyncMode::Immediate; -// case VK_PRESENT_MODE_MAILBOX_KHR: -// return Settings::VSyncMode::Mailbox; -// case VK_PRESENT_MODE_FIFO_KHR: -// return Settings::VSyncMode::FIFO; -// case VK_PRESENT_MODE_FIFO_RELAXED_KHR: -// return Settings::VSyncMode::FIFORelaxed; -// default: -// return Settings::VSyncMode::FIFO; -// } -// } +static constexpr Settings::VSyncMode PresentModeToSetting(VkPresentModeKHR mode) { + switch (mode) { + case VK_PRESENT_MODE_IMMEDIATE_KHR: + return Settings::VSyncMode::Immediate; + case VK_PRESENT_MODE_MAILBOX_KHR: + return Settings::VSyncMode::Mailbox; + case VK_PRESENT_MODE_FIFO_KHR: + return Settings::VSyncMode::FIFO; + case VK_PRESENT_MODE_FIFO_RELAXED_KHR: + return Settings::VSyncMode::FIFORelaxed; + default: + return Settings::VSyncMode::FIFO; + } +} ConfigureGraphics::ConfigureGraphics( const Core::System& system_, std::vector& records_, @@ -112,16 +112,9 @@ ConfigureGraphics::ConfigureGraphics( } } - SetupPerGameUI(); - connect(api_combobox, qOverload(&QComboBox::currentIndexChanged), this, [this] { UpdateAPILayout(); PopulateVSyncModeSelection(); - if (!Settings::IsConfiguringGlobal()) { - ConfigurationShared::SetHighlight(ui->api_widget, - api_combobox->currentIndex() != - ConfigurationShared::USE_GLOBAL_INDEX); - } }); connect(vulkan_device_combobox, qOverload(&QComboBox::activated), this, [this](int device) { @@ -215,18 +208,22 @@ void ConfigureGraphics::SetConfiguration() { QLayout& graphics_layout = *ui->graphics_widget->layout(); std::map> hold_graphics; + std::forward_list hold_api; for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { const auto& setting_label = setting->GetLabel(); auto [widget, extra] = [&]() { - if (setting->Id() == Settings::values.vulkan_device.Id()) { + if (setting->Id() == Settings::values.vulkan_device.Id() || + setting->Id() == Settings::values.shader_backend.Id() || + setting->Id() == Settings::values.vsync_mode.Id()) { return ConfigurationShared::CreateWidget( setting, translations, this, runtime_lock, apply_funcs, trackers, - ConfigurationShared::RequestType::ComboBox); + ConfigurationShared::RequestType::ComboBox, false); + } else { + return ConfigurationShared::CreateWidget(setting, translations, this, runtime_lock, + apply_funcs, trackers); } - return ConfigurationShared::CreateWidget(setting, translations, this, runtime_lock, - apply_funcs, trackers); }(); if (widget == nullptr) { @@ -237,11 +234,11 @@ void ConfigureGraphics::SetConfiguration() { api_layout.addWidget(widget); api_combobox = reinterpret_cast(extra); } else if (setting->Id() == Settings::values.vulkan_device.Id()) { - api_layout.addWidget(widget); + hold_api.push_front(widget); vulkan_device_combobox = reinterpret_cast(extra); vulkan_device_widget = widget; } else if (setting->Id() == Settings::values.shader_backend.Id()) { - api_layout.addWidget(widget); + hold_api.push_front(widget); shader_backend_combobox = reinterpret_cast(extra); shader_backend_widget = widget; } else if (setting->Id() == Settings::values.vsync_mode.Id()) { @@ -258,86 +255,9 @@ void ConfigureGraphics::SetConfiguration() { } } - // ui->api_widget->setEnabled(runtime_lock); - // ui->use_asynchronous_gpu_emulation->setEnabled(runtime_lock); - // ui->use_disk_shader_cache->setEnabled(runtime_lock); - // ui->nvdec_emulation_widget->setEnabled(runtime_lock); - // ui->resolution_combobox->setEnabled(runtime_lock); - // ui->astc_decode_mode_combobox->setEnabled(runtime_lock); - // ui->vsync_mode_layout->setEnabled(runtime_lock || - // Settings::values.renderer_backend.GetValue() == - // Settings::RendererBackend::Vulkan); - // ui->use_disk_shader_cache->setChecked(Settings::values.use_disk_shader_cache.GetValue()); - // ui->use_asynchronous_gpu_emulation->setChecked( - // Settings::values.use_asynchronous_gpu_emulation.GetValue()); - - // if (Settings::IsConfiguringGlobal()) { - // api_combobox->setCurrentIndex(static_cast(Settings::values.renderer_backend.GetValue())); - // ui->fullscreen_mode_combobox->setCurrentIndex( - // static_cast(Settings::values.fullscreen_mode.GetValue())); - // ui->nvdec_emulation->setCurrentIndex( - // static_cast(Settings::values.nvdec_emulation.GetValue())); - // ui->aspect_ratio_combobox->setCurrentIndex(Settings::values.aspect_ratio.GetValue()); - // ui->resolution_combobox->setCurrentIndex( - // static_cast(Settings::values.resolution_setup.GetValue())); - // ui->scaling_filter_combobox->setCurrentIndex( - // static_cast(Settings::values.scaling_filter.GetValue())); - // ui->fsr_sharpening_slider->setValue(Settings::values.fsr_sharpening_slider.GetValue()); - // ui->anti_aliasing_combobox->setCurrentIndex( - // static_cast(Settings::values.anti_aliasing.GetValue())); - // } else { - // ConfigurationShared::SetPerGameSetting(api_combobox, &Settings::values.renderer_backend); - // ConfigurationShared::SetHighlight(ui->api_widget, - // !Settings::values.renderer_backend.UsingGlobal()); - - // ConfigurationShared::SetPerGameSetting(ui->astc_decode_mode_combobox, - // &Settings::values.accelerate_astc); - // ConfigurationShared::SetHighlight(ui->astc_decode_mode_layout, - // !Settings::values.accelerate_astc.UsingGlobal()); - - // ConfigurationShared::SetPerGameSetting(ui->nvdec_emulation, - // &Settings::values.nvdec_emulation); - // ConfigurationShared::SetHighlight(ui->nvdec_emulation_widget, - // !Settings::values.nvdec_emulation.UsingGlobal()); - - // ConfigurationShared::SetPerGameSetting(ui->fullscreen_mode_combobox, - // &Settings::values.fullscreen_mode); - // ConfigurationShared::SetHighlight(ui->fullscreen_mode_label, - // !Settings::values.fullscreen_mode.UsingGlobal()); - - // ConfigurationShared::SetPerGameSetting(ui->aspect_ratio_combobox, - // &Settings::values.aspect_ratio); - // ConfigurationShared::SetHighlight(ui->ar_label, - // !Settings::values.aspect_ratio.UsingGlobal()); - - // ConfigurationShared::SetPerGameSetting(ui->resolution_combobox, - // &Settings::values.resolution_setup); - // ConfigurationShared::SetHighlight(ui->resolution_label, - // !Settings::values.resolution_setup.UsingGlobal()); - - // ConfigurationShared::SetPerGameSetting(ui->scaling_filter_combobox, - // &Settings::values.scaling_filter); - // ConfigurationShared::SetHighlight(ui->scaling_filter_label, - // !Settings::values.scaling_filter.UsingGlobal()); - - // ConfigurationShared::SetPerGameSetting(ui->anti_aliasing_combobox, - // &Settings::values.anti_aliasing); - // ConfigurationShared::SetHighlight(ui->anti_aliasing_label, - // !Settings::values.anti_aliasing.UsingGlobal()); - - // ui->fsr_sharpening_combobox->setCurrentIndex( - // Settings::values.fsr_sharpening_slider.UsingGlobal() ? 0 : 1); - // ui->fsr_sharpening_slider->setEnabled( - // !Settings::values.fsr_sharpening_slider.UsingGlobal()); - // ui->fsr_sharpening_value->setEnabled(!Settings::values.fsr_sharpening_slider.UsingGlobal()); - // ConfigurationShared::SetHighlight(ui->fsr_sharpening_layout, - // !Settings::values.fsr_sharpening_slider.UsingGlobal()); - // ui->fsr_sharpening_slider->setValue(Settings::values.fsr_sharpening_slider.GetValue()); - - // ui->bg_combobox->setCurrentIndex(Settings::values.bg_red.UsingGlobal() ? 0 : 1); - // ui->bg_button->setEnabled(!Settings::values.bg_red.UsingGlobal()); - // ConfigurationShared::SetHighlight(ui->bg_layout, !Settings::values.bg_red.UsingGlobal()); - // } + for (auto widget : hold_api) { + api_layout.addWidget(widget); + } } void ConfigureGraphics::SetFSRIndicatorText(int percentage) { @@ -367,134 +287,16 @@ const QString ConfigureGraphics::TranslateVSyncMode(VkPresentModeKHR mode, } void ConfigureGraphics::ApplyConfiguration() { - // const auto resolution_setup = static_cast( - // ui->resolution_combobox->currentIndex() - - // ((Settings::IsConfiguringGlobal()) ? 0 : ConfigurationShared::USE_GLOBAL_OFFSET)); + const bool powered_on = system.IsPoweredOn(); + for (const auto& func : apply_funcs) { + func(powered_on); + } - // const auto scaling_filter = static_cast( - // ui->scaling_filter_combobox->currentIndex() - - // ((Settings::IsConfiguringGlobal()) ? 0 : ConfigurationShared::USE_GLOBAL_OFFSET)); - - // const auto anti_aliasing = static_cast( - // ui->anti_aliasing_combobox->currentIndex() - - // ((Settings::IsConfiguringGlobal()) ? 0 : ConfigurationShared::USE_GLOBAL_OFFSET)); - - // ConfigurationShared::ApplyPerGameSetting(&Settings::values.fullscreen_mode, - // ui->fullscreen_mode_combobox); - // ConfigurationShared::ApplyPerGameSetting(&Settings::values.aspect_ratio, - // ui->aspect_ratio_combobox); - // ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_disk_shader_cache, - // ui->use_disk_shader_cache, use_disk_shader_cache); - // ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_asynchronous_gpu_emulation, - // ui->use_asynchronous_gpu_emulation, - // use_asynchronous_gpu_emulation); - // ConfigurationShared::ApplyPerGameSetting(&Settings::values.accelerate_astc, - // ui->astc_decode_mode_combobox); - - // if (Settings::IsConfiguringGlobal()) { - // // Guard if during game and set to game-specific value - // if (Settings::values.renderer_backend.UsingGlobal()) { - // Settings::values.renderer_backend.SetValue(GetCurrentGraphicsBackend()); - // } - // if (Settings::values.nvdec_emulation.UsingGlobal()) { - // Settings::values.nvdec_emulation.SetValue(GetCurrentNvdecEmulation()); - // } - // if (Settings::values.shader_backend.UsingGlobal()) { - // Settings::values.shader_backend.SetValue(shader_backend); - // } - // if (Settings::values.vulkan_device.UsingGlobal()) { - // Settings::values.vulkan_device.SetValue(vulkan_device); - // } - // if (Settings::values.bg_red.UsingGlobal()) { - // Settings::values.bg_red.SetValue(static_cast(bg_color.red())); - // Settings::values.bg_green.SetValue(static_cast(bg_color.green())); - // Settings::values.bg_blue.SetValue(static_cast(bg_color.blue())); - // } - // if (Settings::values.resolution_setup.UsingGlobal()) { - // Settings::values.resolution_setup.SetValue(resolution_setup); - // } - // if (Settings::values.scaling_filter.UsingGlobal()) { - // Settings::values.scaling_filter.SetValue(scaling_filter); - // } - // if (Settings::values.anti_aliasing.UsingGlobal()) { - // Settings::values.anti_aliasing.SetValue(anti_aliasing); - // } - // Settings::values.fsr_sharpening_slider.SetValue(ui->fsr_sharpening_slider->value()); - - // const auto mode = vsync_mode_combobox_enum_map[vsync_mode_combobox->currentIndex()]; - // const auto vsync_mode = PresentModeToSetting(mode); - // Settings::values.vsync_mode.SetValue(vsync_mode); - // } else { - // if (ui->resolution_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - // Settings::values.resolution_setup.SetGlobal(true); - // } else { - // Settings::values.resolution_setup.SetGlobal(false); - // Settings::values.resolution_setup.SetValue(resolution_setup); - // } - // if (ui->scaling_filter_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) - // { - // Settings::values.scaling_filter.SetGlobal(true); - // } else { - // Settings::values.scaling_filter.SetGlobal(false); - // Settings::values.scaling_filter.SetValue(scaling_filter); - // } - // if (ui->anti_aliasing_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) - // { - // Settings::values.anti_aliasing.SetGlobal(true); - // } else { - // Settings::values.anti_aliasing.SetGlobal(false); - // Settings::values.anti_aliasing.SetValue(anti_aliasing); - // } - // if (api_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - // Settings::values.renderer_backend.SetGlobal(true); - // Settings::values.shader_backend.SetGlobal(true); - // Settings::values.vulkan_device.SetGlobal(true); - // } else { - // Settings::values.renderer_backend.SetGlobal(false); - // Settings::values.renderer_backend.SetValue(GetCurrentGraphicsBackend()); - // switch (GetCurrentGraphicsBackend()) { - // case Settings::RendererBackend::OpenGL: - // case Settings::RendererBackend::Null: - // Settings::values.shader_backend.SetGlobal(false); - // Settings::values.vulkan_device.SetGlobal(true); - // Settings::values.shader_backend.SetValue(shader_backend); - // break; - // case Settings::RendererBackend::Vulkan: - // Settings::values.shader_backend.SetGlobal(true); - // Settings::values.vulkan_device.SetGlobal(false); - // Settings::values.vulkan_device.SetValue(vulkan_device); - // break; - // } - // } - - // if (ui->nvdec_emulation->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - // Settings::values.nvdec_emulation.SetGlobal(true); - // } else { - // Settings::values.nvdec_emulation.SetGlobal(false); - // Settings::values.nvdec_emulation.SetValue(GetCurrentNvdecEmulation()); - // } - - // if (ui->bg_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - // Settings::values.bg_red.SetGlobal(true); - // Settings::values.bg_green.SetGlobal(true); - // Settings::values.bg_blue.SetGlobal(true); - // } else { - // Settings::values.bg_red.SetGlobal(false); - // Settings::values.bg_green.SetGlobal(false); - // Settings::values.bg_blue.SetGlobal(false); - // Settings::values.bg_red.SetValue(static_cast(bg_color.red())); - // Settings::values.bg_green.SetValue(static_cast(bg_color.green())); - // Settings::values.bg_blue.SetValue(static_cast(bg_color.blue())); - // } - - // if (ui->fsr_sharpening_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) - // { - // Settings::values.fsr_sharpening_slider.SetGlobal(true); - // } else { - // Settings::values.fsr_sharpening_slider.SetGlobal(false); - // Settings::values.fsr_sharpening_slider.SetValue(ui->fsr_sharpening_slider->value()); - // } - // } + if (Settings::IsConfiguringGlobal()) { + const auto mode = vsync_mode_combobox_enum_map[vsync_mode_combobox->currentIndex()]; + const auto vsync_mode = PresentModeToSetting(mode); + Settings::values.vsync_mode.SetValue(vsync_mode); + } } void ConfigureGraphics::changeEvent(QEvent* event) { @@ -581,83 +383,3 @@ Settings::RendererBackend ConfigureGraphics::GetCurrentGraphicsBackend() const { return static_cast(api_combobox->currentIndex() - ConfigurationShared::USE_GLOBAL_OFFSET); } - -Settings::NvdecEmulation ConfigureGraphics::GetCurrentNvdecEmulation() const { - return Settings::NvdecEmulation::CPU; - // if (Settings::IsConfiguringGlobal()) { - // return static_cast(ui->nvdec_emulation->currentIndex()); - // } - - // if (ui->nvdec_emulation->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - // Settings::values.nvdec_emulation.SetGlobal(true); - // return Settings::values.nvdec_emulation.GetValue(); - // } - // Settings::values.nvdec_emulation.SetGlobal(false); - // return static_cast(ui->nvdec_emulation->currentIndex() - - // ConfigurationShared::USE_GLOBAL_OFFSET); -} - -void ConfigureGraphics::SetupPerGameUI() { - // if (Settings::IsConfiguringGlobal()) { - // api_combobox->setEnabled(Settings::values.renderer_backend.UsingGlobal()); - // vulkan_device_combobox->setEnabled(Settings::values.renderer_backend.UsingGlobal()); - // ui->fullscreen_mode_combobox->setEnabled(Settings::values.fullscreen_mode.UsingGlobal()); - // ui->aspect_ratio_combobox->setEnabled(Settings::values.aspect_ratio.UsingGlobal()); - // ui->resolution_combobox->setEnabled(Settings::values.resolution_setup.UsingGlobal()); - // ui->scaling_filter_combobox->setEnabled(Settings::values.scaling_filter.UsingGlobal()); - // ui->fsr_sharpening_slider->setEnabled(Settings::values.fsr_sharpening_slider.UsingGlobal()); - // ui->anti_aliasing_combobox->setEnabled(Settings::values.anti_aliasing.UsingGlobal()); - // ui->use_asynchronous_gpu_emulation->setEnabled( - // Settings::values.use_asynchronous_gpu_emulation.UsingGlobal()); - // ui->nvdec_emulation->setEnabled(Settings::values.nvdec_emulation.UsingGlobal()); - // ui->astc_decode_mode_combobox->setEnabled(Settings::values.accelerate_astc.UsingGlobal()); - // ui->use_disk_shader_cache->setEnabled(Settings::values.use_disk_shader_cache.UsingGlobal()); - // ui->bg_button->setEnabled(Settings::values.bg_red.UsingGlobal()); - // ui->fsr_slider_layout->setEnabled(Settings::values.fsr_sharpening_slider.UsingGlobal()); - - // return; - // } - - // connect(ui->bg_combobox, qOverload(&QComboBox::activated), this, [this](int index) { - // ui->bg_button->setEnabled(index == 1); - // ConfigurationShared::SetHighlight(ui->bg_layout, index == 1); - // }); - - // connect(ui->fsr_sharpening_combobox, qOverload(&QComboBox::activated), this, - // [this](int index) { - // ui->fsr_sharpening_slider->setEnabled(index == 1); - // ui->fsr_sharpening_value->setEnabled(index == 1); - // ConfigurationShared::SetHighlight(ui->fsr_sharpening_layout, index == 1); - // }); - - // ConfigurationShared::SetColoredTristate( - // ui->use_disk_shader_cache, Settings::values.use_disk_shader_cache, - // use_disk_shader_cache); - // ConfigurationShared::SetColoredTristate(ui->use_asynchronous_gpu_emulation, - // Settings::values.use_asynchronous_gpu_emulation, - // use_asynchronous_gpu_emulation); - - // ConfigurationShared::SetColoredComboBox(ui->aspect_ratio_combobox, ui->ar_label, - // Settings::values.aspect_ratio.GetValue(true)); - // ConfigurationShared::SetColoredComboBox( - // ui->fullscreen_mode_combobox, ui->fullscreen_mode_label, - // static_cast(Settings::values.fullscreen_mode.GetValue(true))); - // ConfigurationShared::SetColoredComboBox( - // ui->resolution_combobox, ui->resolution_label, - // static_cast(Settings::values.resolution_setup.GetValue(true))); - // ConfigurationShared::SetColoredComboBox( - // ui->scaling_filter_combobox, ui->scaling_filter_label, - // static_cast(Settings::values.scaling_filter.GetValue(true))); - // ConfigurationShared::SetColoredComboBox( - // ui->anti_aliasing_combobox, ui->anti_aliasing_label, - // static_cast(Settings::values.anti_aliasing.GetValue(true))); - // ConfigurationShared::SetColoredComboBox( - // ui->astc_decode_mode_combobox, ui->astc_decode_mode_label, - // static_cast(Settings::values.accelerate_astc.GetValue(true))); - // ConfigurationShared::InsertGlobalItem( - // api_combobox, static_cast(Settings::values.renderer_backend.GetValue(true))); - // ConfigurationShared::InsertGlobalItem( - // ui->nvdec_emulation, static_cast(Settings::values.nvdec_emulation.GetValue(true))); - - // ui->vsync_mode_layout->setVisible(false); -} diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index 30dfb6163..c226e825b 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -64,10 +64,7 @@ private: const QString TranslateVSyncMode(VkPresentModeKHR mode, Settings::RendererBackend backend) const; - void SetupPerGameUI(); - Settings::RendererBackend GetCurrentGraphicsBackend() const; - Settings::NvdecEmulation GetCurrentNvdecEmulation() const; std::unique_ptr ui; QColor bg_color; @@ -93,5 +90,6 @@ private: QComboBox* shader_backend_combobox; QComboBox* vsync_mode_combobox; QWidget* vulkan_device_widget; + QWidget* api_widget; QWidget* shader_backend_widget; }; From d72ff0172661c0e10308d7000c4fef57cdb94d90 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 8 May 2023 10:05:37 -0400 Subject: [PATCH 020/155] shared_translations: Re flow strings --- src/yuzu/configuration/shared_translation.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index c20a3ebd9..5a2071781 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -62,12 +62,12 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(use_asynchronous_gpu_emulation, "Use asynchronous GPU emulation", ""); INSERT(nvdec_emulation, "NVDEC emulation:", ""); INSERT(accelerate_astc, "ASTC Decoding Method:", ""); - INSERT( - vsync_mode, "VSync Mode:", - "FIFO (VSync) does not drop frames or exhibit tearing but is limited by the screen refresh " - "rate. FIFO Relaxed is similar to FIFO but allows tearing as it recovers from a slow down. " - "Mailbox can have lower latency than FIFO and does not tear but may drop frames. Immediate " - "(no synchronization) just presents whatever is available and can exhibit tearing."); + INSERT(vsync_mode, "VSync Mode:", + "FIFO (VSync) does not drop frames or exhibit tearing but is limited by the screen " + "refresh rate.\nFIFO Relaxed is similar to FIFO but allows tearing as it recovers from " + "a slow down.\nMailbox can have lower latency than FIFO and does not tear but may drop " + "frames.\nImmediate (no synchronization) just presents whatever is available and can " + "exhibit tearing."); INSERT(bg_red, "", ""); INSERT(bg_green, "", ""); INSERT(bg_blue, "", ""); From 39a1ffbb91a026fd3842f55ebca222db50afea41 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 8 May 2023 14:11:45 -0400 Subject: [PATCH 021/155] configuration: Use buttons instead of highlights Only for updated configs at the moment --- .../configuration/configuration_shared.cpp | 177 +++++++++++------- src/yuzu/configuration/configuration_shared.h | 14 +- src/yuzu/configuration/configure_general.cpp | 4 +- src/yuzu/configuration/configure_graphics.cpp | 71 +++++-- src/yuzu/configuration/configure_graphics.h | 1 + src/yuzu/configuration/configure_graphics.ui | 20 +- .../configure_graphics_advanced.cpp | 2 +- .../configure_graphics_advanced.ui | 15 +- src/yuzu/configuration/shared_translation.cpp | 3 + 9 files changed, 204 insertions(+), 103 deletions(-) diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 8d5ab8b4c..45165c2e9 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -2,119 +2,151 @@ // SPDX-License-Identifier: GPL-2.0-or-later #include +#include #include #include #include #include #include +#include #include +#include #include +#include #include +#include #include +#include #include "common/settings.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_per_game.h" #include "yuzu/configuration/shared_translation.h" namespace ConfigurationShared { + +static QPushButton* CreateClearGlobalButton(QWidget* parent, Settings::BasicSetting* setting) { + QStyle* style = parent->style(); + QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_DialogResetButton)); + QPushButton* button = new QPushButton(*icon, QStringLiteral(""), parent); + button->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Expanding); + + QSizePolicy sp_retain = button->sizePolicy(); + sp_retain.setRetainSizeWhenHidden(true); + button->setSizePolicy(sp_retain); + + button->setEnabled(!setting->UsingGlobal()); + button->setVisible(!setting->UsingGlobal()); + + return button; +} + static std::pair> CreateCheckBox(Settings::BasicSetting* setting, const QString& label, QWidget* parent, std::list& trackers) { + QWidget* widget = new QWidget(parent); + QHBoxLayout* layout = new QHBoxLayout(widget); + QCheckBox* checkbox = new QCheckBox(label, parent); checkbox->setObjectName(QString::fromStdString(setting->GetLabel())); checkbox->setCheckState(setting->ToString() == "true" ? Qt::CheckState::Checked : Qt::CheckState::Unchecked); - CheckState* tracker{}; + std::function load_func; - // Per-game config highlight - if (setting->Switchable() && !Settings::IsConfiguringGlobal()) { - bool global_state = setting->ToStringGlobal() == "true"; - bool state = setting->ToString() == "true"; - bool global = setting->UsingGlobal(); - tracker = &trackers.emplace_front(CheckState{}); - SetColoredTristate(checkbox, global, state, global_state, *tracker); + layout->addWidget(checkbox); + if (Settings::IsConfiguringGlobal()) { + load_func = [setting, checkbox]() { + setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + }; + } else { + auto* button = CreateClearGlobalButton(parent, setting); + layout->addWidget(button); + + QObject::connect(checkbox, &QCheckBox::stateChanged, [button](int) { + button->setVisible(true); + button->setEnabled(true); + }); + + QObject::connect(button, &QAbstractButton::clicked, [checkbox, setting, button](bool) { + checkbox->setCheckState(setting->ToStringGlobal() == "true" ? Qt::Checked + : Qt::Unchecked); + button->setEnabled(false); + button->setVisible(false); + }); + + load_func = [setting, checkbox, button]() { + bool using_global = !button->isEnabled(); + setting->SetGlobal(using_global); + if (!using_global) { + setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + } + }; } - auto load_func = [checkbox, setting, tracker]() { - if (Settings::IsConfiguringGlobal()) { - setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); - } + layout->setContentsMargins(0, 0, 0, 0); - if (Settings::IsConfiguringGlobal() || !setting->Switchable()) { - return; - } - - if (*tracker != CheckState::Global) { - setting->SetGlobal(false); - setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); - } else { - setting->SetGlobal(true); - } - }; - - return {checkbox, load_func}; + return {widget, load_func}; } -static std::tuple> CreateCombobox( +static std::tuple> CreateCombobox( Settings::BasicSetting* setting, const QString& label, QWidget* parent, bool managed) { const auto type = setting->TypeId(); QWidget* group = new QWidget(parent); group->setObjectName(QString::fromStdString(setting->GetLabel())); - QLayout* combobox_layout = new QHBoxLayout(group); + QLayout* layout = new QHBoxLayout(group); QLabel* qt_label = new QLabel(label, parent); QComboBox* combobox = new QComboBox(parent); + QPushButton* button{nullptr}; + std::forward_list combobox_enumerations = ComboboxEnumeration(type, parent); for (const auto& item : combobox_enumerations) { combobox->addItem(item); } - combobox_layout->addWidget(qt_label); - combobox_layout->addWidget(combobox); + layout->addWidget(qt_label); + layout->addWidget(combobox); - combobox_layout->setSpacing(6); - combobox_layout->setContentsMargins(0, 0, 0, 0); + layout->setSpacing(6); + layout->setContentsMargins(0, 0, 0, 0); - if (setting->Switchable() && !Settings::IsConfiguringGlobal() && managed) { - int current = std::stoi(setting->ToString()); - int global_value = std::stoi(setting->ToStringGlobal()); - SetColoredComboBox(combobox, group, global_value); - if (setting->UsingGlobal()) { - combobox->setCurrentIndex(USE_GLOBAL_INDEX); - } else { - SetHighlight(group, true); - combobox->setCurrentIndex(current + USE_GLOBAL_OFFSET); - } - } else { - combobox->setCurrentIndex(std::stoi(setting->ToString())); - } + combobox->setCurrentIndex(std::stoi(setting->ToString())); std::function load_func = []() {}; - if (managed) { - load_func = [combobox, setting]() { - if (Settings::IsConfiguringGlobal()) { - setting->LoadString(std::to_string(combobox->currentIndex())); - } - if (Settings::IsConfiguringGlobal() || !setting->Switchable()) { - return; - } + if (Settings::IsConfiguringGlobal() && managed) { + load_func = [setting, combobox]() { + setting->LoadString(std::to_string(combobox->currentIndex())); + }; + } else if (managed) { + button = CreateClearGlobalButton(parent, setting); + layout->addWidget(button); - bool using_global = combobox->currentIndex() == USE_GLOBAL_INDEX; - int index = combobox->currentIndex() - USE_GLOBAL_OFFSET; + QObject::connect(button, &QAbstractButton::clicked, [button, combobox, setting](bool) { + button->setEnabled(false); + button->setVisible(false); + combobox->setCurrentIndex(std::stoi(setting->ToStringGlobal())); + }); + + QObject::connect(combobox, QOverload::of(&QComboBox::activated), [=](int) { + button->setEnabled(true); + button->setVisible(true); + }); + + load_func = [setting, combobox, button]() { + bool using_global = !button->isEnabled(); setting->SetGlobal(using_global); if (!using_global) { - setting->LoadString(std::to_string(index)); + setting->LoadString(std::to_string(combobox->currentIndex())); } }; } - return {group, combobox, load_func}; + return {group, combobox, button, load_func}; } static std::tuple> CreateLineEdit( @@ -136,7 +168,7 @@ static std::tuple> CreateLineEdit( q_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->addWidget(q_label); - load_func = [&]() { + load_func = [line_edit, setting]() { std::string load_text = line_edit->text().toStdString(); setting->LoadString(load_text); }; @@ -157,7 +189,7 @@ static std::tuple> CreateLineEdit( checkbox->setCheckState(setting->UsingGlobal() ? Qt::Unchecked : Qt::Checked); highlight_func(checkbox->checkState()); - load_func = [&]() { + load_func = [checkbox, setting, line_edit]() { if (checkbox->checkState() == Qt::Checked) { setting->SetGlobal(false); @@ -176,12 +208,15 @@ static std::tuple> CreateLineEdit( return {widget, line_edit, load_func}; } -std::pair CreateWidget(Settings::BasicSetting* setting, - const TranslationMap& translations, QWidget* parent, - bool runtime_lock, - std::forward_list>& apply_funcs, - std::list& trackers, RequestType request, - bool managed) { +std::tuple CreateWidget( + Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, + bool runtime_lock, std::forward_list>& apply_funcs, + std::list& trackers, RequestType request, bool managed) { + if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { + LOG_DEBUG(Frontend, "\"{}\" is not switchable, skipping...", setting->GetLabel()); + return {nullptr, nullptr, nullptr}; + } + const auto type = setting->TypeId(); const int id = setting->Id(); QWidget* widget{nullptr}; @@ -201,9 +236,11 @@ std::pair CreateWidget(Settings::BasicSetting* setting, if (label == QStringLiteral("")) { LOG_DEBUG(Frontend, "Translation table has emtpy entry for \"{}\", skipping...", setting->GetLabel()); - return {nullptr, nullptr}; + return {nullptr, nullptr, nullptr}; } + QPushButton* button; + if (type == typeid(bool)) { auto pair = CreateCheckBox(setting, label, parent, trackers); widget = pair.first; @@ -212,7 +249,8 @@ std::pair CreateWidget(Settings::BasicSetting* setting, auto tuple = CreateCombobox(setting, label, parent, managed); widget = std::get<0>(tuple); extra = std::get<1>(tuple); - load_func = std::get<2>(tuple); + button = std::get<2>(tuple); + load_func = std::get<3>(tuple); } else if (type == typeid(u32) || type == typeid(int)) { switch (request) { case RequestType::Default: { @@ -226,7 +264,8 @@ std::pair CreateWidget(Settings::BasicSetting* setting, auto tuple = CreateCombobox(setting, label, parent, managed); widget = std::get<0>(tuple); extra = std::get<1>(tuple); - load_func = std::get<2>(tuple); + button = std::get<2>(tuple); + load_func = std::get<3>(tuple); break; } case RequestType::SpinBox: @@ -238,7 +277,7 @@ std::pair CreateWidget(Settings::BasicSetting* setting, if (widget == nullptr) { LOG_ERROR(Frontend, "No widget was created for \"{}\"", setting->GetLabel()); - return {nullptr, nullptr}; + return {nullptr, nullptr, nullptr}; } apply_funcs.push_front([load_func, setting](bool powered_on) { @@ -257,7 +296,7 @@ std::pair CreateWidget(Settings::BasicSetting* setting, widget->setToolTip(tooltip); - return {widget, extra}; + return {widget, extra, button}; } Tab::Tab(std::shared_ptr> group_, QWidget* parent) diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 942af0215..63df11d26 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -13,6 +13,8 @@ #include "common/settings.h" #include "yuzu/configuration/shared_translation.h" +class QPushButton; + namespace ConfigurationShared { class Tab : public QWidget { @@ -49,13 +51,11 @@ enum class RequestType { MaxEnum, }; -std::pair CreateWidget(Settings::BasicSetting* setting, - const TranslationMap& translations, QWidget* parent, - bool runtime_lock, - std::forward_list>& apply_funcs, - std::list& trackers, - RequestType request = RequestType::Default, - bool managed = true); +std::tuple CreateWidget( + Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, + bool runtime_lock, std::forward_list>& apply_funcs, + std::list& trackers, RequestType request = RequestType::Default, + bool managed = true); // Global-aware apply and set functions diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index 03261992a..8c6fee2a5 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -139,8 +139,8 @@ void ConfigureGeneral::SetupPerGameUI() { ui->button_reset_defaults->setVisible(false); - ConfigurationShared::SetColoredTristate(ui->toggle_speed_limit, - Settings::values.use_speed_limit, use_speed_limit); + // ConfigurationShared::SetColoredTristate(ui->toggle_speed_limit, + // Settings::values.use_speed_limit, use_speed_limit); ConfigurationShared::SetColoredTristate(ui->use_multi_core, Settings::values.use_multi_core, use_multi_core); diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 37a10ac87..1145b6c43 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -20,8 +20,11 @@ #include #include #include +#include +#include #include #include +#include #include #include "common/common_types.h" @@ -112,7 +115,7 @@ ConfigureGraphics::ConfigureGraphics( } } - connect(api_combobox, qOverload(&QComboBox::currentIndexChanged), this, [this] { + connect(api_combobox, qOverload(&QComboBox::activated), this, [this] { UpdateAPILayout(); PopulateVSyncModeSelection(); }); @@ -146,6 +149,10 @@ ConfigureGraphics::ConfigureGraphics( } void ConfigureGraphics::PopulateVSyncModeSelection() { + if (!Settings::IsConfiguringGlobal()) { + return; + } + const Settings::RendererBackend backend{GetCurrentGraphicsBackend()}; if (backend == Settings::RendererBackend::Null) { vsync_mode_combobox->setEnabled(false); @@ -204,7 +211,12 @@ ConfigureGraphics::~ConfigureGraphics() = default; void ConfigureGraphics::SetConfiguration() { const bool runtime_lock = !system.IsPoweredOn(); - QLayout& api_layout = *ui->api_widget->layout(); + QLayout* api_layout = ui->api_widget->layout(); + QWidget* api_grid_widget = new QWidget(this); + QVBoxLayout* api_grid_layout = new QVBoxLayout(api_grid_widget); + api_grid_layout->setContentsMargins(0, 0, 0, 0); + api_layout->addWidget(api_grid_widget); + QLayout& graphics_layout = *ui->graphics_widget->layout(); std::map> hold_graphics; @@ -213,7 +225,7 @@ void ConfigureGraphics::SetConfiguration() { for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { const auto& setting_label = setting->GetLabel(); - auto [widget, extra] = [&]() { + auto [widget, extra, button] = [&]() { if (setting->Id() == Settings::values.vulkan_device.Id() || setting->Id() == Settings::values.shader_backend.Id() || setting->Id() == Settings::values.vsync_mode.Id()) { @@ -230,8 +242,20 @@ void ConfigureGraphics::SetConfiguration() { continue; } - if (setting->Id() == Settings::values.vulkan_device.Id()) { - api_layout.addWidget(widget); + if (setting->Id() == Settings::values.renderer_backend.Id()) { + api_grid_layout->addWidget(widget); + api_combobox = reinterpret_cast(extra); + api_restore_global_button = button; + + if (!Settings::IsConfiguringGlobal()) { + QObject::connect(api_restore_global_button, &QAbstractButton::clicked, + [=](bool) { UpdateAPILayout(); }); + + widget->layout()->removeWidget(api_restore_global_button); + api_layout->addWidget(api_restore_global_button); + } + } else if (setting->Id() == Settings::values.vulkan_device.Id()) { + api_layout->addWidget(widget); api_combobox = reinterpret_cast(extra); } else if (setting->Id() == Settings::values.vulkan_device.Id()) { hold_api.push_front(widget); @@ -256,7 +280,7 @@ void ConfigureGraphics::SetConfiguration() { } for (auto widget : hold_api) { - api_layout.addWidget(widget); + api_grid_layout->addWidget(widget); } } @@ -297,6 +321,25 @@ void ConfigureGraphics::ApplyConfiguration() { const auto vsync_mode = PresentModeToSetting(mode); Settings::values.vsync_mode.SetValue(vsync_mode); } + + Settings::values.shader_backend.SetGlobal(true); + Settings::values.vulkan_device.SetGlobal(true); + if (!Settings::IsConfiguringGlobal() && api_restore_global_button->isEnabled()) { + auto backend = static_cast(api_combobox->currentIndex()); + switch (backend) { + case Settings::RendererBackend::OpenGL: + Settings::values.shader_backend.SetGlobal(false); + Settings::values.shader_backend.SetValue( + static_cast(shader_backend_combobox->currentIndex())); + break; + case Settings::RendererBackend::Vulkan: + Settings::values.vulkan_device.SetGlobal(false); + Settings::values.vulkan_device.SetValue(vulkan_device_combobox->currentIndex()); + break; + case Settings::RendererBackend::Null: + break; + } + } } void ConfigureGraphics::changeEvent(QEvent* event) { @@ -322,8 +365,7 @@ void ConfigureGraphics::UpdateBackgroundColorButton(QColor color) { } void ConfigureGraphics::UpdateAPILayout() { - if (!Settings::IsConfiguringGlobal() && - api_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { + if (!Settings::IsConfiguringGlobal() && !api_restore_global_button->isEnabled()) { vulkan_device = Settings::values.vulkan_device.GetValue(true); shader_backend = Settings::values.shader_backend.GetValue(true); vulkan_device_widget->setEnabled(false); @@ -371,15 +413,8 @@ void ConfigureGraphics::RetrieveVulkanDevices() { } Settings::RendererBackend ConfigureGraphics::GetCurrentGraphicsBackend() const { - if (Settings::IsConfiguringGlobal()) { - return static_cast(api_combobox->currentIndex()); + if (!Settings::IsConfiguringGlobal() && !api_restore_global_button->isEnabled()) { + return Settings::values.renderer_backend.GetValue(true); } - - if (api_combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - Settings::values.renderer_backend.SetGlobal(true); - return Settings::values.renderer_backend.GetValue(); - } - Settings::values.renderer_backend.SetGlobal(false); - return static_cast(api_combobox->currentIndex() - - ConfigurationShared::USE_GLOBAL_OFFSET); + return static_cast(api_combobox->currentIndex()); } diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index c226e825b..12a588127 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -85,6 +85,7 @@ private: const Core::System& system; const ConfigurationShared::TranslationMap& translations; + QPushButton* api_restore_global_button; QComboBox* vulkan_device_combobox; QComboBox* api_combobox; QComboBox* shader_backend_combobox; diff --git a/src/yuzu/configuration/configure_graphics.ui b/src/yuzu/configuration/configure_graphics.ui index 565429c98..1f6ffea1a 100644 --- a/src/yuzu/configuration/configure_graphics.ui +++ b/src/yuzu/configuration/configure_graphics.ui @@ -27,7 +27,7 @@ - + 0 @@ -40,9 +40,6 @@ 0 - - 6 - @@ -63,7 +60,20 @@ - + + + 0 + + + 0 + + + 0 + + + 0 + + diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 3a207e2cd..8a53ad111 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -32,7 +32,7 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { for (auto setting : Settings::values.linkage.by_category[Settings::Category::RendererAdvanced]) { - auto [widget, extra] = ConfigurationShared::CreateWidget( + auto [widget, extra, button] = ConfigurationShared::CreateWidget( setting, translations, this, runtime_lock, apply_funcs, trackers); if (widget == nullptr) { diff --git a/src/yuzu/configuration/configure_graphics_advanced.ui b/src/yuzu/configuration/configure_graphics_advanced.ui index 113fbc010..37a854ca3 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.ui +++ b/src/yuzu/configuration/configure_graphics_advanced.ui @@ -27,7 +27,20 @@ - + + + 0 + + + 0 + + + 0 + + + 0 + + diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 5a2071781..a13636af6 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -93,6 +93,9 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { "Enable compute pipelines, required by some games.\nThis setting only exists for Intel " "proprietary drivers, and may crash if enabled.\nCompute pipelines are always enabled " "on all other drivers."); + INSERT(use_reactive_flushing, "Enable Reactive Flushing", + "Uses reactive flushing instead of predictive flushing, allowing more accurate memory " + "syncing."); // Renderer (Debug) From d35577d3ed0bfc56ddf85a2e8b163d9d02bec809 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 8 May 2023 17:33:10 -0400 Subject: [PATCH 022/155] configuration: Implement slider --- src/common/settings.h | 13 +- .../configuration/configuration_shared.cpp | 203 ++++++++++++++---- src/yuzu/configuration/configuration_shared.h | 6 +- src/yuzu/configuration/configure_graphics.cpp | 31 ++- src/yuzu/configuration/configure_graphics.h | 2 - .../configure_graphics_advanced.cpp | 2 +- .../configure_graphics_advanced.h | 2 - 7 files changed, 188 insertions(+), 71 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 2879237cc..4ca8299b3 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -200,6 +200,8 @@ public: virtual bool RuntimeModfiable() const = 0; virtual void SetGlobal(bool global) {} virtual constexpr u32 Id() const = 0; + virtual std::string MinVal() const = 0; + virtual std::string MaxVal() const = 0; virtual bool UsingGlobal() const { return false; } @@ -336,7 +338,7 @@ protected: if constexpr (std::is_same()) { return value_; } else if constexpr (std::is_same>()) { - return value_.has_value() ? std::to_string(*value_) : "0"; + return value_.has_value() ? std::to_string(*value_) : "none"; } else if constexpr (std::is_same()) { return value_ ? "true" : "false"; } else { @@ -401,7 +403,7 @@ public: if constexpr (std::is_same()) { this->SetValue(input); } else if constexpr (std::is_same>()) { - this->SetValue(static_cast(std::stoll(input))); + this->SetValue(static_cast(std::stoul(input))); } else if constexpr (std::is_same()) { this->SetValue(input == "true"); } else { @@ -435,6 +437,13 @@ public: return id; } + virtual std::string MinVal() const override { + return this->ToString(minimum); + } + virtual std::string MaxVal() const override { + return this->ToString(maximum); + } + protected: Type value{}; ///< The setting const Type default_value{}; ///< The default value diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 45165c2e9..076d9cc0d 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -13,10 +13,14 @@ #include #include #include +#include +#include #include #include #include +#include #include +#include #include "common/settings.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_per_game.h" @@ -24,7 +28,7 @@ namespace ConfigurationShared { -static QPushButton* CreateClearGlobalButton(QWidget* parent, Settings::BasicSetting* setting) { +static QPushButton* CreateRestoreGlobalButton(QWidget* parent, Settings::BasicSetting* setting) { QStyle* style = parent->style(); QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_DialogResetButton)); QPushButton* button = new QPushButton(*icon, QStringLiteral(""), parent); @@ -40,10 +44,8 @@ static QPushButton* CreateClearGlobalButton(QWidget* parent, Settings::BasicSett return button; } -static std::pair> CreateCheckBox(Settings::BasicSetting* setting, - const QString& label, - QWidget* parent, - std::list& trackers) { +static std::tuple> CreateCheckBox( + Settings::BasicSetting* setting, const QString& label, QWidget* parent) { QWidget* widget = new QWidget(parent); QHBoxLayout* layout = new QHBoxLayout(widget); @@ -54,13 +56,15 @@ static std::pair> CreateCheckBox(Settings::Basic std::function load_func; + QPushButton* button{nullptr}; + layout->addWidget(checkbox); if (Settings::IsConfiguringGlobal()) { load_func = [setting, checkbox]() { setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); }; } else { - auto* button = CreateClearGlobalButton(parent, setting); + button = CreateRestoreGlobalButton(parent, setting); layout->addWidget(button); QObject::connect(checkbox, &QCheckBox::stateChanged, [button](int) { @@ -86,7 +90,7 @@ static std::pair> CreateCheckBox(Settings::Basic layout->setContentsMargins(0, 0, 0, 0); - return {widget, load_func}; + return {widget, checkbox, button, load_func}; } static std::tuple> CreateCombobox( @@ -122,7 +126,7 @@ static std::tuple> Cre setting->LoadString(std::to_string(combobox->currentIndex())); }; } else if (managed) { - button = CreateClearGlobalButton(parent, setting); + button = CreateRestoreGlobalButton(parent, setting); layout->addWidget(button); QObject::connect(button, &QAbstractButton::clicked, [button, combobox, setting](bool) { @@ -149,8 +153,8 @@ static std::tuple> Cre return {group, combobox, button, load_func}; } -static std::tuple> CreateLineEdit( - Settings::BasicSetting* setting, const QString& label, QWidget* parent) { +static std::tuple> CreateLineEdit( + Settings::BasicSetting* setting, const QString& label, QWidget* parent, bool managed = true) { QWidget* widget = new QWidget(parent); widget->setObjectName(label); @@ -160,58 +164,140 @@ static std::tuple> CreateLineEdit( const QString text = QString::fromStdString(setting->ToString()); line_edit->setText(text); - std::function load_func; + std::function load_func = []() {}; + QLabel* q_label = new QLabel(label, widget); // setSizePolicy lets widget expand and take an equal part of the space as the line edit - if (Settings::IsConfiguringGlobal()) { - QLabel* q_label = new QLabel(label, widget); - q_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - layout->addWidget(q_label); + q_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + layout->addWidget(q_label); + layout->addWidget(line_edit); + + QPushButton* button{nullptr}; + + if (Settings::IsConfiguringGlobal() && !managed) { load_func = [line_edit, setting]() { std::string load_text = line_edit->text().toStdString(); setting->LoadString(load_text); }; - } else { - QCheckBox* checkbox = new QCheckBox(label, parent); - checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - layout->addWidget(checkbox); + } else if (!managed) { + button = CreateRestoreGlobalButton(parent, setting); + layout->addWidget(button); - const auto highlight_func = [widget, line_edit](int state) { - bool using_global = state != Qt::Checked; - SetHighlight(widget, !using_global); - line_edit->setEnabled(!using_global); - }; + QObject::connect(button, &QAbstractButton::clicked, [=](bool) { + button->setEnabled(false); + button->setVisible(false); - QObject::connect(checkbox, qOverload(&QCheckBox::stateChanged), widget, - highlight_func); + line_edit->setText(QString::fromStdString(setting->ToStringGlobal())); + }); - checkbox->setCheckState(setting->UsingGlobal() ? Qt::Unchecked : Qt::Checked); - highlight_func(checkbox->checkState()); + QObject::connect(line_edit, &QLineEdit::textChanged, [=](QString) { + button->setEnabled(true); + button->setVisible(true); + }); - load_func = [checkbox, setting, line_edit]() { - if (checkbox->checkState() == Qt::Checked) { - setting->SetGlobal(false); - - std::string load_text = line_edit->text().toStdString(); - setting->LoadString(load_text); - } else { - setting->SetGlobal(true); + load_func = [=]() { + bool using_global = !button->isEnabled(); + setting->SetGlobal(using_global); + if (!using_global) { + setting->LoadString(line_edit->text().toStdString()); } }; } - layout->addWidget(line_edit); + layout->setContentsMargins(0, 0, 0, 0); + + return {widget, line_edit, button, load_func}; +} + +static std::tuple> CreateSlider( + Settings::BasicSetting* setting, const QString& name, QWidget* parent, bool reversed, + float multiplier) { + QWidget* widget = new QWidget(parent); + QHBoxLayout* layout = new QHBoxLayout(widget); + QSlider* slider = new QSlider(Qt::Horizontal, widget); + QLabel* label = new QLabel(name, widget); + QPushButton* button{nullptr}; + QLabel* feedback = new QLabel(widget); + + layout->addWidget(label); + layout->addWidget(slider); + layout->addWidget(feedback); + + label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->setContentsMargins(0, 0, 0, 0); - return {widget, line_edit, load_func}; + int max_val = std::stoi(setting->MaxVal()); + + QObject::connect(slider, &QAbstractSlider::valueChanged, [=](int value) { + int present = (reversed ? max_val - value : value) * multiplier; + feedback->setText( + QStringLiteral("%1%").arg(QString::fromStdString(std::to_string(present)))); + }); + + slider->setValue(std::stoi(setting->ToString())); + slider->setMinimum(std::stoi(setting->MinVal())); + slider->setMaximum(max_val); + + if (reversed) { + slider->setInvertedAppearance(true); + } + + std::function load_func; + + if (Settings::IsConfiguringGlobal()) { + load_func = [=]() { setting->LoadString(std::to_string(slider->value())); }; + } else { + button = CreateRestoreGlobalButton(parent, setting); + layout->addWidget(button); + + QObject::connect(button, &QAbstractButton::clicked, [=](bool) { + slider->setValue(std::stoi(setting->ToStringGlobal())); + + button->setEnabled(false); + button->setVisible(false); + }); + + QObject::connect(slider, &QAbstractSlider::sliderMoved, [=](int) { + button->setEnabled(true); + button->setVisible(true); + }); + + load_func = [=]() { + bool using_global = !button->isEnabled(); + setting->SetGlobal(using_global); + if (!using_global) { + setting->LoadString(std::to_string(slider->value())); + } + }; + } + + return {widget, slider, button, []() {}}; +} + +static std::tuple> +CreateCheckBoxWithLineEdit(Settings::BasicSetting* setting, const QString& label, QWidget* parent) { + auto tuple = CreateCheckBox(setting, label, parent); + auto* widget = std::get<0>(tuple); + auto* checkbox = std::get<1>(tuple); + auto* button = std::get<2>(tuple); + auto load_func = std::get<3>(tuple); + QHBoxLayout* layout = dynamic_cast(widget->layout()); + + auto line_edit_tuple = CreateLineEdit(setting, label, parent, false); + auto* line_edit_widget = std::get<0>(line_edit_tuple); + auto* line_edit = std::get<1>(line_edit_tuple); + + layout->insertWidget(1, line_edit_widget); + + return {widget, checkbox, line_edit, button, load_func}; } std::tuple CreateWidget( Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, bool runtime_lock, std::forward_list>& apply_funcs, - std::list& trackers, RequestType request, bool managed) { + RequestType request, bool managed, float multiplier, const std::string& text_box_default) { if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { LOG_DEBUG(Frontend, "\"{}\" is not switchable, skipping...", setting->GetLabel()); return {nullptr, nullptr, nullptr}; @@ -242,9 +328,27 @@ std::tuple CreateWidget( QPushButton* button; if (type == typeid(bool)) { - auto pair = CreateCheckBox(setting, label, parent, trackers); - widget = pair.first; - load_func = pair.second; + switch (request) { + case RequestType::Default: { + auto tuple = CreateCheckBox(setting, label, parent); + widget = std::get<0>(tuple); + extra = std::get<1>(tuple); + button = std::get<2>(tuple); + load_func = std::get<3>(tuple); + break; + } + case RequestType::LineEdit: { + auto tuple = CreateCheckBoxWithLineEdit(setting, label, parent); + widget = std::get<0>(tuple); + break; + } + case RequestType::ComboBox: + case RequestType::SpinBox: + case RequestType::Slider: + case RequestType::ReverseSlider: + case RequestType::MaxEnum: + break; + } } else if (setting->IsEnum()) { auto tuple = CreateCombobox(setting, label, parent, managed); widget = std::get<0>(tuple); @@ -253,11 +357,13 @@ std::tuple CreateWidget( load_func = std::get<3>(tuple); } else if (type == typeid(u32) || type == typeid(int)) { switch (request) { + case RequestType::LineEdit: case RequestType::Default: { auto tuple = CreateLineEdit(setting, label, parent); widget = std::get<0>(tuple); extra = std::get<1>(tuple); - load_func = std::get<2>(tuple); + button = std::get<2>(tuple); + load_func = std::get<3>(tuple); break; } case RequestType::ComboBox: { @@ -268,8 +374,17 @@ std::tuple CreateWidget( load_func = std::get<3>(tuple); break; } - case RequestType::SpinBox: case RequestType::Slider: + case RequestType::ReverseSlider: { + auto tuple = CreateSlider(setting, label, parent, request == RequestType::ReverseSlider, + multiplier); + widget = std::get<0>(tuple); + extra = std::get<1>(tuple); + button = std::get<2>(tuple); + load_func = std::get<3>(tuple); + break; + } + case RequestType::SpinBox: case RequestType::MaxEnum: break; } diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 63df11d26..ef3b7c9a9 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -48,14 +48,16 @@ enum class RequestType { ComboBox, SpinBox, Slider, + ReverseSlider, + LineEdit, MaxEnum, }; std::tuple CreateWidget( Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, bool runtime_lock, std::forward_list>& apply_funcs, - std::list& trackers, RequestType request = RequestType::Default, - bool managed = true); + RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, + const std::string& text_box_default = ""); // Global-aware apply and set functions diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 1145b6c43..d3ca7e8cc 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -97,7 +97,6 @@ ConfigureGraphics::ConfigureGraphics( Settings::values.bg_blue.GetValue())); UpdateAPILayout(); PopulateVSyncModeSelection(); //< must happen after UpdateAPILayout - // SetFSRIndicatorText(ui->fsr_sharpening_slider->sliderPosition()); // VSync setting needs to be determined after populating the VSync combobox if (Settings::IsConfiguringGlobal()) { @@ -134,18 +133,13 @@ ConfigureGraphics::ConfigureGraphics( // } // UpdateBackgroundColorButton(new_bg_color); // }); + // ui->bg_label->setVisible(Settings::IsConfiguringGlobal()); + // ui->bg_combobox->setVisible(!Settings::IsConfiguringGlobal()); api_combobox->setEnabled(!UISettings::values.has_broken_vulkan && api_combobox->isEnabled()); ui->api_widget->setEnabled( (!UISettings::values.has_broken_vulkan || Settings::IsConfiguringGlobal()) && ui->api_widget->isEnabled()); - // ui->bg_label->setVisible(Settings::IsConfiguringGlobal()); - // ui->bg_combobox->setVisible(!Settings::IsConfiguringGlobal()); - - // connect(ui->fsr_sharpening_slider, &QSlider::valueChanged, this, - // &ConfigureGraphics::SetFSRIndicatorText); - // ui->fsr_sharpening_combobox->setVisible(!Settings::IsConfiguringGlobal()); - // ui->fsr_sharpening_label->setVisible(Settings::IsConfiguringGlobal()); } void ConfigureGraphics::PopulateVSyncModeSelection() { @@ -230,11 +224,19 @@ void ConfigureGraphics::SetConfiguration() { setting->Id() == Settings::values.shader_backend.Id() || setting->Id() == Settings::values.vsync_mode.Id()) { return ConfigurationShared::CreateWidget( - setting, translations, this, runtime_lock, apply_funcs, trackers, + setting, translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ComboBox, false); + } else if (setting->Id() == Settings::values.fsr_sharpening_slider.Id()) { + return ConfigurationShared::CreateWidget( + setting, translations, this, runtime_lock, apply_funcs, + ConfigurationShared::RequestType::ReverseSlider, true, 0.5f); + } else if (setting->Id() == Settings::values.use_speed_limit.Id()) { + return ConfigurationShared::CreateWidget( + setting, translations, this, runtime_lock, apply_funcs, + ConfigurationShared::RequestType::LineEdit, true, 1.0f, setting->ToString()); } else { return ConfigurationShared::CreateWidget(setting, translations, this, runtime_lock, - apply_funcs, trackers); + apply_funcs); } }(); @@ -251,12 +253,10 @@ void ConfigureGraphics::SetConfiguration() { QObject::connect(api_restore_global_button, &QAbstractButton::clicked, [=](bool) { UpdateAPILayout(); }); + // Detach API's restore button and place it where we want widget->layout()->removeWidget(api_restore_global_button); api_layout->addWidget(api_restore_global_button); } - } else if (setting->Id() == Settings::values.vulkan_device.Id()) { - api_layout->addWidget(widget); - api_combobox = reinterpret_cast(extra); } else if (setting->Id() == Settings::values.vulkan_device.Id()) { hold_api.push_front(widget); vulkan_device_combobox = reinterpret_cast(extra); @@ -284,11 +284,6 @@ void ConfigureGraphics::SetConfiguration() { } } -void ConfigureGraphics::SetFSRIndicatorText(int percentage) { - // ui->fsr_sharpening_value->setText( - // tr("%1%", "FSR sharpening percentage (e.g. 50%)").arg(100 - (percentage / 2))); -} - const QString ConfigureGraphics::TranslateVSyncMode(VkPresentModeKHR mode, Settings::RendererBackend backend) const { switch (mode) { diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index 12a588127..a049458a8 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -58,7 +58,6 @@ private: void RetrieveVulkanDevices(); - void SetFSRIndicatorText(int percentage); /* Turns a Vulkan present mode into a textual string for a UI * (and eventually for a human to read) */ const QString TranslateVSyncMode(VkPresentModeKHR mode, @@ -69,7 +68,6 @@ private: std::unique_ptr ui; QColor bg_color; - std::list trackers{}; std::forward_list> apply_funcs{}; std::vector& records; diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 8a53ad111..4a3868693 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -33,7 +33,7 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { for (auto setting : Settings::values.linkage.by_category[Settings::Category::RendererAdvanced]) { auto [widget, extra, button] = ConfigurationShared::CreateWidget( - setting, translations, this, runtime_lock, apply_funcs, trackers); + setting, translations, this, runtime_lock, apply_funcs); if (widget == nullptr) { continue; diff --git a/src/yuzu/configuration/configure_graphics_advanced.h b/src/yuzu/configuration/configure_graphics_advanced.h index 3ac6b4bce..327134ee6 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.h +++ b/src/yuzu/configuration/configure_graphics_advanced.h @@ -34,8 +34,6 @@ private: std::unique_ptr ui; - std::list trackers{}; - const Core::System& system; const ConfigurationShared::TranslationMap& translations; std::forward_list> apply_funcs; From f66d617107e45f8213643f2bbaa5f58878c3d3a6 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 8 May 2023 22:37:03 -0400 Subject: [PATCH 023/155] configuration: Move CreateWidget to a class We were passing so many objects between the function and the caller that it needed to be redesigned. --- src/yuzu/CMakeLists.txt | 2 + src/yuzu/configuration/config.cpp | 3 + .../configuration/configuration_shared.cpp | 386 ------------------ src/yuzu/configuration/configuration_shared.h | 18 - src/yuzu/configuration/configure_general.cpp | 63 +-- src/yuzu/configuration/configure_graphics.cpp | 55 ++- src/yuzu/configuration/configure_graphics.h | 1 + .../configure_graphics_advanced.cpp | 8 +- src/yuzu/configuration/shared_widget.cpp | 360 ++++++++++++++++ src/yuzu/configuration/shared_widget.h | 64 +++ 10 files changed, 507 insertions(+), 453 deletions(-) create mode 100644 src/yuzu/configuration/shared_widget.cpp create mode 100644 src/yuzu/configuration/shared_widget.h diff --git a/src/yuzu/CMakeLists.txt b/src/yuzu/CMakeLists.txt index 8b54e1268..899b75871 100644 --- a/src/yuzu/CMakeLists.txt +++ b/src/yuzu/CMakeLists.txt @@ -145,6 +145,8 @@ add_executable(yuzu configuration/input_profiles.h configuration/shared_translation.cpp configuration/shared_translation.h + configuration/shared_widget.cpp + configuration/shared_widget.h debugger/console.cpp debugger/console.h debugger/controller.cpp diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index c6a34e787..08aa20859 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -1346,8 +1346,11 @@ void Config::ReadSettingGeneric(Settings::BasicSetting* const setting) { void Config::WriteSettingGeneric(Settings::BasicSetting* const setting) const { if (!setting->Save()) { + LOG_DEBUG(Frontend, "Skipping \"{}\" marked for not saving", setting->GetLabel()); return; } + LOG_DEBUG(Frontend, "Saving {} setting \"{}\"...", global ? "global" : "custom", + setting->GetLabel()); const QVariant value = QVariant::fromValue(QString::fromStdString(setting->ToString())); const QVariant default_value = QVariant::fromValue(QString::fromStdString(setting->DefaultToString())); diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 076d9cc0d..dff70f04b 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -28,392 +28,6 @@ namespace ConfigurationShared { -static QPushButton* CreateRestoreGlobalButton(QWidget* parent, Settings::BasicSetting* setting) { - QStyle* style = parent->style(); - QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_DialogResetButton)); - QPushButton* button = new QPushButton(*icon, QStringLiteral(""), parent); - button->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Expanding); - - QSizePolicy sp_retain = button->sizePolicy(); - sp_retain.setRetainSizeWhenHidden(true); - button->setSizePolicy(sp_retain); - - button->setEnabled(!setting->UsingGlobal()); - button->setVisible(!setting->UsingGlobal()); - - return button; -} - -static std::tuple> CreateCheckBox( - Settings::BasicSetting* setting, const QString& label, QWidget* parent) { - QWidget* widget = new QWidget(parent); - QHBoxLayout* layout = new QHBoxLayout(widget); - - QCheckBox* checkbox = new QCheckBox(label, parent); - checkbox->setObjectName(QString::fromStdString(setting->GetLabel())); - checkbox->setCheckState(setting->ToString() == "true" ? Qt::CheckState::Checked - : Qt::CheckState::Unchecked); - - std::function load_func; - - QPushButton* button{nullptr}; - - layout->addWidget(checkbox); - if (Settings::IsConfiguringGlobal()) { - load_func = [setting, checkbox]() { - setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); - }; - } else { - button = CreateRestoreGlobalButton(parent, setting); - layout->addWidget(button); - - QObject::connect(checkbox, &QCheckBox::stateChanged, [button](int) { - button->setVisible(true); - button->setEnabled(true); - }); - - QObject::connect(button, &QAbstractButton::clicked, [checkbox, setting, button](bool) { - checkbox->setCheckState(setting->ToStringGlobal() == "true" ? Qt::Checked - : Qt::Unchecked); - button->setEnabled(false); - button->setVisible(false); - }); - - load_func = [setting, checkbox, button]() { - bool using_global = !button->isEnabled(); - setting->SetGlobal(using_global); - if (!using_global) { - setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); - } - }; - } - - layout->setContentsMargins(0, 0, 0, 0); - - return {widget, checkbox, button, load_func}; -} - -static std::tuple> CreateCombobox( - Settings::BasicSetting* setting, const QString& label, QWidget* parent, bool managed) { - const auto type = setting->TypeId(); - - QWidget* group = new QWidget(parent); - group->setObjectName(QString::fromStdString(setting->GetLabel())); - QLayout* layout = new QHBoxLayout(group); - - QLabel* qt_label = new QLabel(label, parent); - QComboBox* combobox = new QComboBox(parent); - - QPushButton* button{nullptr}; - - std::forward_list combobox_enumerations = ComboboxEnumeration(type, parent); - for (const auto& item : combobox_enumerations) { - combobox->addItem(item); - } - - layout->addWidget(qt_label); - layout->addWidget(combobox); - - layout->setSpacing(6); - layout->setContentsMargins(0, 0, 0, 0); - - combobox->setCurrentIndex(std::stoi(setting->ToString())); - - std::function load_func = []() {}; - - if (Settings::IsConfiguringGlobal() && managed) { - load_func = [setting, combobox]() { - setting->LoadString(std::to_string(combobox->currentIndex())); - }; - } else if (managed) { - button = CreateRestoreGlobalButton(parent, setting); - layout->addWidget(button); - - QObject::connect(button, &QAbstractButton::clicked, [button, combobox, setting](bool) { - button->setEnabled(false); - button->setVisible(false); - - combobox->setCurrentIndex(std::stoi(setting->ToStringGlobal())); - }); - - QObject::connect(combobox, QOverload::of(&QComboBox::activated), [=](int) { - button->setEnabled(true); - button->setVisible(true); - }); - - load_func = [setting, combobox, button]() { - bool using_global = !button->isEnabled(); - setting->SetGlobal(using_global); - if (!using_global) { - setting->LoadString(std::to_string(combobox->currentIndex())); - } - }; - } - - return {group, combobox, button, load_func}; -} - -static std::tuple> CreateLineEdit( - Settings::BasicSetting* setting, const QString& label, QWidget* parent, bool managed = true) { - QWidget* widget = new QWidget(parent); - widget->setObjectName(label); - - QHBoxLayout* layout = new QHBoxLayout(widget); - QLineEdit* line_edit = new QLineEdit(parent); - - const QString text = QString::fromStdString(setting->ToString()); - line_edit->setText(text); - - std::function load_func = []() {}; - - QLabel* q_label = new QLabel(label, widget); - // setSizePolicy lets widget expand and take an equal part of the space as the line edit - q_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - layout->addWidget(q_label); - - layout->addWidget(line_edit); - - QPushButton* button{nullptr}; - - if (Settings::IsConfiguringGlobal() && !managed) { - load_func = [line_edit, setting]() { - std::string load_text = line_edit->text().toStdString(); - setting->LoadString(load_text); - }; - } else if (!managed) { - button = CreateRestoreGlobalButton(parent, setting); - layout->addWidget(button); - - QObject::connect(button, &QAbstractButton::clicked, [=](bool) { - button->setEnabled(false); - button->setVisible(false); - - line_edit->setText(QString::fromStdString(setting->ToStringGlobal())); - }); - - QObject::connect(line_edit, &QLineEdit::textChanged, [=](QString) { - button->setEnabled(true); - button->setVisible(true); - }); - - load_func = [=]() { - bool using_global = !button->isEnabled(); - setting->SetGlobal(using_global); - if (!using_global) { - setting->LoadString(line_edit->text().toStdString()); - } - }; - } - - layout->setContentsMargins(0, 0, 0, 0); - - return {widget, line_edit, button, load_func}; -} - -static std::tuple> CreateSlider( - Settings::BasicSetting* setting, const QString& name, QWidget* parent, bool reversed, - float multiplier) { - QWidget* widget = new QWidget(parent); - QHBoxLayout* layout = new QHBoxLayout(widget); - QSlider* slider = new QSlider(Qt::Horizontal, widget); - QLabel* label = new QLabel(name, widget); - QPushButton* button{nullptr}; - QLabel* feedback = new QLabel(widget); - - layout->addWidget(label); - layout->addWidget(slider); - layout->addWidget(feedback); - - label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - - layout->setContentsMargins(0, 0, 0, 0); - - int max_val = std::stoi(setting->MaxVal()); - - QObject::connect(slider, &QAbstractSlider::valueChanged, [=](int value) { - int present = (reversed ? max_val - value : value) * multiplier; - feedback->setText( - QStringLiteral("%1%").arg(QString::fromStdString(std::to_string(present)))); - }); - - slider->setValue(std::stoi(setting->ToString())); - slider->setMinimum(std::stoi(setting->MinVal())); - slider->setMaximum(max_val); - - if (reversed) { - slider->setInvertedAppearance(true); - } - - std::function load_func; - - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { setting->LoadString(std::to_string(slider->value())); }; - } else { - button = CreateRestoreGlobalButton(parent, setting); - layout->addWidget(button); - - QObject::connect(button, &QAbstractButton::clicked, [=](bool) { - slider->setValue(std::stoi(setting->ToStringGlobal())); - - button->setEnabled(false); - button->setVisible(false); - }); - - QObject::connect(slider, &QAbstractSlider::sliderMoved, [=](int) { - button->setEnabled(true); - button->setVisible(true); - }); - - load_func = [=]() { - bool using_global = !button->isEnabled(); - setting->SetGlobal(using_global); - if (!using_global) { - setting->LoadString(std::to_string(slider->value())); - } - }; - } - - return {widget, slider, button, []() {}}; -} - -static std::tuple> -CreateCheckBoxWithLineEdit(Settings::BasicSetting* setting, const QString& label, QWidget* parent) { - auto tuple = CreateCheckBox(setting, label, parent); - auto* widget = std::get<0>(tuple); - auto* checkbox = std::get<1>(tuple); - auto* button = std::get<2>(tuple); - auto load_func = std::get<3>(tuple); - QHBoxLayout* layout = dynamic_cast(widget->layout()); - - auto line_edit_tuple = CreateLineEdit(setting, label, parent, false); - auto* line_edit_widget = std::get<0>(line_edit_tuple); - auto* line_edit = std::get<1>(line_edit_tuple); - - layout->insertWidget(1, line_edit_widget); - - return {widget, checkbox, line_edit, button, load_func}; -} - -std::tuple CreateWidget( - Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, - bool runtime_lock, std::forward_list>& apply_funcs, - RequestType request, bool managed, float multiplier, const std::string& text_box_default) { - if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { - LOG_DEBUG(Frontend, "\"{}\" is not switchable, skipping...", setting->GetLabel()); - return {nullptr, nullptr, nullptr}; - } - - const auto type = setting->TypeId(); - const int id = setting->Id(); - QWidget* widget{nullptr}; - void* extra{nullptr}; - - std::function load_func; - - const auto [label, tooltip] = [&]() { - const auto& setting_label = setting->GetLabel(); - if (translations.contains(id)) { - return std::pair{translations.at(id).first, translations.at(id).second}; - } - LOG_ERROR(Frontend, "Translation table lacks entry for \"{}\"", setting_label); - return std::pair{QString::fromStdString(setting_label), QStringLiteral("")}; - }(); - - if (label == QStringLiteral("")) { - LOG_DEBUG(Frontend, "Translation table has emtpy entry for \"{}\", skipping...", - setting->GetLabel()); - return {nullptr, nullptr, nullptr}; - } - - QPushButton* button; - - if (type == typeid(bool)) { - switch (request) { - case RequestType::Default: { - auto tuple = CreateCheckBox(setting, label, parent); - widget = std::get<0>(tuple); - extra = std::get<1>(tuple); - button = std::get<2>(tuple); - load_func = std::get<3>(tuple); - break; - } - case RequestType::LineEdit: { - auto tuple = CreateCheckBoxWithLineEdit(setting, label, parent); - widget = std::get<0>(tuple); - break; - } - case RequestType::ComboBox: - case RequestType::SpinBox: - case RequestType::Slider: - case RequestType::ReverseSlider: - case RequestType::MaxEnum: - break; - } - } else if (setting->IsEnum()) { - auto tuple = CreateCombobox(setting, label, parent, managed); - widget = std::get<0>(tuple); - extra = std::get<1>(tuple); - button = std::get<2>(tuple); - load_func = std::get<3>(tuple); - } else if (type == typeid(u32) || type == typeid(int)) { - switch (request) { - case RequestType::LineEdit: - case RequestType::Default: { - auto tuple = CreateLineEdit(setting, label, parent); - widget = std::get<0>(tuple); - extra = std::get<1>(tuple); - button = std::get<2>(tuple); - load_func = std::get<3>(tuple); - break; - } - case RequestType::ComboBox: { - auto tuple = CreateCombobox(setting, label, parent, managed); - widget = std::get<0>(tuple); - extra = std::get<1>(tuple); - button = std::get<2>(tuple); - load_func = std::get<3>(tuple); - break; - } - case RequestType::Slider: - case RequestType::ReverseSlider: { - auto tuple = CreateSlider(setting, label, parent, request == RequestType::ReverseSlider, - multiplier); - widget = std::get<0>(tuple); - extra = std::get<1>(tuple); - button = std::get<2>(tuple); - load_func = std::get<3>(tuple); - break; - } - case RequestType::SpinBox: - case RequestType::MaxEnum: - break; - } - } - - if (widget == nullptr) { - LOG_ERROR(Frontend, "No widget was created for \"{}\"", setting->GetLabel()); - return {nullptr, nullptr, nullptr}; - } - - apply_funcs.push_front([load_func, setting](bool powered_on) { - if (setting->RuntimeModfiable() || !powered_on) { - load_func(); - } - }); - - bool enable = runtime_lock || setting->RuntimeModfiable(); - if (setting->Switchable() && Settings::IsConfiguringGlobal() && !runtime_lock) { - enable &= !setting->UsingGlobal(); - } - widget->setEnabled(enable); - - widget->setVisible(Settings::IsConfiguringGlobal() || setting->Switchable()); - - widget->setToolTip(tooltip); - - return {widget, extra, button}; -} - Tab::Tab(std::shared_ptr> group_, QWidget* parent) : QWidget(parent), group{group_} { if (group != nullptr) { diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index ef3b7c9a9..0a0a92ae5 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -13,8 +13,6 @@ #include "common/settings.h" #include "yuzu/configuration/shared_translation.h" -class QPushButton; - namespace ConfigurationShared { class Tab : public QWidget { @@ -43,22 +41,6 @@ enum class CheckState { Count, // Simply the number of states, not a valid checkbox state }; -enum class RequestType { - Default, - ComboBox, - SpinBox, - Slider, - ReverseSlider, - LineEdit, - MaxEnum, -}; - -std::tuple CreateWidget( - Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, - bool runtime_lock, std::forward_list>& apply_funcs, - RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, - const std::string& text_box_default = ""); - // Global-aware apply and set functions // ApplyPerGameSetting, given a Settings::Setting and a Qt UI element, properly applies a Setting diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index 8c6fee2a5..764ff68b3 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -21,10 +21,10 @@ ConfigureGeneral::ConfigureGeneral( SetConfiguration(); - if (Settings::IsConfiguringGlobal()) { - connect(ui->toggle_speed_limit, &QCheckBox::clicked, ui->speed_limit, - [this]() { ui->speed_limit->setEnabled(ui->toggle_speed_limit->isChecked()); }); - } + // if (Settings::IsConfiguringGlobal()) { + // connect(ui->toggle_speed_limit, &QCheckBox::clicked, ui->speed_limit, + // [this]() { ui->speed_limit->setEnabled(ui->toggle_speed_limit->isChecked()); }); + // } connect(ui->button_reset_defaults, &QPushButton::clicked, this, &ConfigureGeneral::ResetDefaults); @@ -46,17 +46,17 @@ void ConfigureGeneral::SetConfiguration() { ui->toggle_controller_applet_disabled->setChecked( UISettings::values.controller_applet_disabled.GetValue()); - ui->toggle_speed_limit->setChecked(Settings::values.use_speed_limit.GetValue()); - ui->speed_limit->setValue(Settings::values.speed_limit.GetValue()); + // ui->toggle_speed_limit->setChecked(Settings::values.use_speed_limit.GetValue()); + // ui->speed_limit->setValue(Settings::values.speed_limit.GetValue()); ui->button_reset_defaults->setEnabled(runtime_lock); - if (Settings::IsConfiguringGlobal()) { - ui->speed_limit->setEnabled(Settings::values.use_speed_limit.GetValue()); - } else { - ui->speed_limit->setEnabled(Settings::values.use_speed_limit.GetValue() && - use_speed_limit != ConfigurationShared::CheckState::Global); - } + // if (Settings::IsConfiguringGlobal()) { + // ui->speed_limit->setEnabled(Settings::values.use_speed_limit.GetValue()); + // } else { + // ui->speed_limit->setEnabled(Settings::values.use_speed_limit.GetValue() && + // use_speed_limit != ConfigurationShared::CheckState::Global); + // } } // Called to set the callback when resetting settings to defaults @@ -91,20 +91,20 @@ void ConfigureGeneral::ApplyConfiguration() { ui->toggle_controller_applet_disabled->isChecked(); // Guard if during game and set to game-specific value - if (Settings::values.use_speed_limit.UsingGlobal()) { - Settings::values.use_speed_limit.SetValue(ui->toggle_speed_limit->checkState() == - Qt::Checked); - Settings::values.speed_limit.SetValue(ui->speed_limit->value()); - } + // if (Settings::values.use_speed_limit.UsingGlobal()) { + // Settings::values.use_speed_limit.SetValue(ui->toggle_speed_limit->checkState() == + // Qt::Checked); + // Settings::values.speed_limit.SetValue(ui->speed_limit->value()); + // } } else { - bool global_speed_limit = use_speed_limit == ConfigurationShared::CheckState::Global; - Settings::values.use_speed_limit.SetGlobal(global_speed_limit); - Settings::values.speed_limit.SetGlobal(global_speed_limit); - if (!global_speed_limit) { - Settings::values.use_speed_limit.SetValue(ui->toggle_speed_limit->checkState() == - Qt::Checked); - Settings::values.speed_limit.SetValue(ui->speed_limit->value()); - } + // bool global_speed_limit = use_speed_limit == ConfigurationShared::CheckState::Global; + // Settings::values.use_speed_limit.SetGlobal(global_speed_limit); + // Settings::values.speed_limit.SetGlobal(global_speed_limit); + // if (!global_speed_limit) { + // Settings::values.use_speed_limit.SetValue(ui->toggle_speed_limit->checkState() == + // Qt::Checked); + // Settings::values.speed_limit.SetValue(ui->speed_limit->value()); + // } } } @@ -125,8 +125,8 @@ void ConfigureGeneral::SetupPerGameUI() { // Disables each setting if: // - A game is running (thus settings in use), and // - A non-global setting is applied. - ui->toggle_speed_limit->setEnabled(Settings::values.use_speed_limit.UsingGlobal()); - ui->speed_limit->setEnabled(Settings::values.speed_limit.UsingGlobal()); + // ui->toggle_speed_limit->setEnabled(Settings::values.use_speed_limit.UsingGlobal()); + // ui->speed_limit->setEnabled(Settings::values.speed_limit.UsingGlobal()); return; } @@ -144,8 +144,9 @@ void ConfigureGeneral::SetupPerGameUI() { ConfigurationShared::SetColoredTristate(ui->use_multi_core, Settings::values.use_multi_core, use_multi_core); - connect(ui->toggle_speed_limit, &QCheckBox::clicked, ui->speed_limit, [this]() { - ui->speed_limit->setEnabled(ui->toggle_speed_limit->isChecked() && - (use_speed_limit != ConfigurationShared::CheckState::Global)); - }); + // connect(ui->toggle_speed_limit, &QCheckBox::clicked, ui->speed_limit, [this]() { + // ui->speed_limit->setEnabled(ui->toggle_speed_limit->isChecked() && + // (use_speed_limit != + // ConfigurationShared::CheckState::Global)); + // }); } diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index d3ca7e8cc..093e33625 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -15,6 +15,7 @@ #include #include #include +#include #include #include #include @@ -35,6 +36,7 @@ #include "ui_configure_graphics.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_graphics.h" +#include "yuzu/configuration/shared_widget.h" #include "yuzu/qt_common.h" #include "yuzu/uisettings.h" #include "yuzu/vk_device_info.h" @@ -219,35 +221,38 @@ void ConfigureGraphics::SetConfiguration() { for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { const auto& setting_label = setting->GetLabel(); - auto [widget, extra, button] = [&]() { + ConfigurationShared::Widget* widget = [&]() { if (setting->Id() == Settings::values.vulkan_device.Id() || setting->Id() == Settings::values.shader_backend.Id() || setting->Id() == Settings::values.vsync_mode.Id()) { - return ConfigurationShared::CreateWidget( + return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ComboBox, false); } else if (setting->Id() == Settings::values.fsr_sharpening_slider.Id()) { - return ConfigurationShared::CreateWidget( + return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ReverseSlider, true, 0.5f); } else if (setting->Id() == Settings::values.use_speed_limit.Id()) { - return ConfigurationShared::CreateWidget( + return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::LineEdit, true, 1.0f, setting->ToString()); + ConfigurationShared::RequestType::LineEdit, true, 1.0f, + Settings::values.speed_limit.ToString()); } else { - return ConfigurationShared::CreateWidget(setting, translations, this, runtime_lock, - apply_funcs); + return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, + apply_funcs); } }(); - if (widget == nullptr) { + if (!widget->Valid()) { + LOG_DEBUG(Frontend, "Deleted widget for \"{}\"", setting->GetLabel()); + delete widget; continue; } if (setting->Id() == Settings::values.renderer_backend.Id()) { api_grid_layout->addWidget(widget); - api_combobox = reinterpret_cast(extra); - api_restore_global_button = button; + api_combobox = widget->combobox; + api_restore_global_button = widget->restore_button; if (!Settings::IsConfiguringGlobal()) { QObject::connect(api_restore_global_button, &QAbstractButton::clicked, @@ -259,14 +264,33 @@ void ConfigureGraphics::SetConfiguration() { } } else if (setting->Id() == Settings::values.vulkan_device.Id()) { hold_api.push_front(widget); - vulkan_device_combobox = reinterpret_cast(extra); + vulkan_device_combobox = widget->combobox; vulkan_device_widget = widget; } else if (setting->Id() == Settings::values.shader_backend.Id()) { hold_api.push_front(widget); - shader_backend_combobox = reinterpret_cast(extra); + shader_backend_combobox = widget->combobox; shader_backend_widget = widget; + } else if (setting->Id() == Settings::values.use_speed_limit.Id()) { + apply_funcs.push_front([setting, widget](bool powered_on) { + if (!setting->RuntimeModfiable() && powered_on) { + return; + } + + u16 value = QVariant(widget->line_edit->text()).value(); + auto& speed_limit = Settings::values.speed_limit; + if (Settings::IsConfiguringGlobal()) { + speed_limit.SetValue(value); + } else { + bool using_global = !widget->restore_button->isVisible(); + speed_limit.SetGlobal(using_global); + if (!using_global) { + speed_limit.SetValue(value); + } + } + }); + hold_graphics[setting->IsEnum()][setting_label] = widget; } else if (setting->Id() == Settings::values.vsync_mode.Id()) { - vsync_mode_combobox = reinterpret_cast(extra); + vsync_mode_combobox = widget->combobox; hold_graphics[setting->IsEnum()][setting_label] = widget; } else { hold_graphics[setting->IsEnum()][setting_label] = widget; @@ -360,6 +384,7 @@ void ConfigureGraphics::UpdateBackgroundColorButton(QColor color) { } void ConfigureGraphics::UpdateAPILayout() { + bool runtime_lock = !system.IsPoweredOn(); if (!Settings::IsConfiguringGlobal() && !api_restore_global_button->isEnabled()) { vulkan_device = Settings::values.vulkan_device.GetValue(true); shader_backend = Settings::values.shader_backend.GetValue(true); @@ -368,8 +393,8 @@ void ConfigureGraphics::UpdateAPILayout() { } else { vulkan_device = Settings::values.vulkan_device.GetValue(); shader_backend = Settings::values.shader_backend.GetValue(); - vulkan_device_widget->setEnabled(true); - shader_backend_widget->setEnabled(true); + vulkan_device_widget->setEnabled(runtime_lock); + shader_backend_widget->setEnabled(runtime_lock); } switch (GetCurrentGraphicsBackend()) { diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index a049458a8..4ef551341 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -15,6 +15,7 @@ #include "vk_device_info.h" #include "yuzu/configuration/configuration_shared.h" +class QPushButton; class QEvent; class QObject; class QComboBox; diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 4a3868693..4f57a7ae6 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -8,6 +8,7 @@ #include "ui_configure_graphics_advanced.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_graphics_advanced.h" +#include "yuzu/configuration/shared_widget.h" ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced( const Core::System& system_, @@ -32,10 +33,11 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { for (auto setting : Settings::values.linkage.by_category[Settings::Category::RendererAdvanced]) { - auto [widget, extra, button] = ConfigurationShared::CreateWidget( - setting, translations, this, runtime_lock, apply_funcs); + ConfigurationShared::Widget* widget = + new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); - if (widget == nullptr) { + if (!widget->Valid()) { + delete widget; continue; } diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp new file mode 100644 index 000000000..0676973a9 --- /dev/null +++ b/src/yuzu/configuration/shared_widget.cpp @@ -0,0 +1,360 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include "common/settings.h" +#include "yuzu/configuration/shared_translation.h" +#include "yuzu/configuration/shared_widget.h" + +namespace ConfigurationShared { + +void Widget::CreateRestoreGlobalButton() { + QStyle* style = this->style(); + QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_DialogResetButton)); + restore_button = new QPushButton(*icon, QStringLiteral(""), this); + restore_button->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Expanding); + + QSizePolicy sp_retain = restore_button->sizePolicy(); + sp_retain.setRetainSizeWhenHidden(true); + restore_button->setSizePolicy(sp_retain); + + restore_button->setEnabled(!setting.UsingGlobal()); + restore_button->setVisible(!setting.UsingGlobal()); +} + +void Widget::CreateCheckBox(const QString& label, std::function& load_func) { + created = true; + + QHBoxLayout* layout = new QHBoxLayout(this); + + checkbox = new QCheckBox(label, this); + checkbox->setObjectName(QString::fromStdString(setting.GetLabel())); + checkbox->setCheckState(setting.ToString() == "true" ? Qt::CheckState::Checked + : Qt::CheckState::Unchecked); + + layout->addWidget(checkbox); + if (Settings::IsConfiguringGlobal()) { + load_func = [=]() { + setting.LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + }; + } else { + CreateRestoreGlobalButton(); + layout->addWidget(restore_button); + + QObject::connect(checkbox, &QCheckBox::stateChanged, [&](int) { + restore_button->setVisible(true); + restore_button->setEnabled(true); + }); + + QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { + checkbox->setCheckState(setting.ToStringGlobal() == "true" ? Qt::Checked + : Qt::Unchecked); + restore_button->setEnabled(false); + restore_button->setVisible(false); + }); + + load_func = [=]() { + bool using_global = !restore_button->isEnabled(); + setting.SetGlobal(using_global); + if (!using_global) { + setting.LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + } + }; + } + + layout->setContentsMargins(0, 0, 0, 0); +} + +void Widget::CreateCombobox(const QString& label, bool managed, std::function& load_func) { + created = true; + + const auto type = setting.TypeId(); + + QLayout* layout = new QHBoxLayout(this); + + QLabel* qt_label = new QLabel(label, this); + combobox = new QComboBox(this); + + std::forward_list combobox_enumerations = ComboboxEnumeration(type, this); + for (const auto& item : combobox_enumerations) { + combobox->addItem(item); + } + + layout->addWidget(qt_label); + layout->addWidget(combobox); + + layout->setSpacing(6); + layout->setContentsMargins(0, 0, 0, 0); + + combobox->setCurrentIndex(std::stoi(setting.ToString())); + + if (Settings::IsConfiguringGlobal() && managed) { + load_func = [=]() { setting.LoadString(std::to_string(combobox->currentIndex())); }; + } else if (managed) { + CreateRestoreGlobalButton(); + layout->addWidget(restore_button); + + QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { + restore_button->setEnabled(false); + restore_button->setVisible(false); + + combobox->setCurrentIndex(std::stoi(setting.ToStringGlobal())); + }); + + QObject::connect(combobox, QOverload::of(&QComboBox::activated), [=](int) { + restore_button->setEnabled(true); + restore_button->setVisible(true); + }); + + load_func = [=]() { + bool using_global = !restore_button->isEnabled(); + setting.SetGlobal(using_global); + if (!using_global) { + setting.LoadString(std::to_string(combobox->currentIndex())); + } + }; + } +} + +void Widget::CreateLineEdit(const QString& label, bool managed, std::function& load_func) { + created = true; + + QHBoxLayout* layout = new QHBoxLayout(this); + line_edit = new QLineEdit(this); + + const QString text = QString::fromStdString(setting.ToString()); + line_edit->setText(text); + + QLabel* q_label = new QLabel(label, this); + // setSizePolicy lets widget expand and take an equal part of the space as the line edit + q_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + layout->addWidget(q_label); + + layout->addWidget(line_edit); + + if (Settings::IsConfiguringGlobal() && !managed) { + load_func = [=]() { + std::string load_text = line_edit->text().toStdString(); + setting.LoadString(load_text); + }; + } else if (!managed) { + CreateRestoreGlobalButton(); + layout->addWidget(restore_button); + + QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { + restore_button->setEnabled(false); + restore_button->setVisible(false); + + line_edit->setText(QString::fromStdString(setting.ToStringGlobal())); + }); + + QObject::connect(line_edit, &QLineEdit::textChanged, [&](QString) { + restore_button->setEnabled(true); + restore_button->setVisible(true); + }); + + load_func = [=]() { + bool using_global = !restore_button->isEnabled(); + setting.SetGlobal(using_global); + if (!using_global) { + setting.LoadString(line_edit->text().toStdString()); + } + }; + } + + layout->setContentsMargins(0, 0, 0, 0); +} + +void Widget::CreateSlider(const QString& name, bool reversed, float multiplier, + std::function& load_func) { + created = true; + + QHBoxLayout* layout = new QHBoxLayout(this); + slider = new QSlider(Qt::Horizontal, this); + QLabel* label = new QLabel(name, this); + QLabel* feedback = new QLabel(this); + + layout->addWidget(label); + layout->addWidget(slider); + layout->addWidget(feedback); + + label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + + layout->setContentsMargins(0, 0, 0, 0); + + int max_val = std::stoi(setting.MaxVal()); + + QObject::connect(slider, &QAbstractSlider::valueChanged, [=](int value) { + int present = (reversed ? max_val - value : value) * multiplier; + feedback->setText( + QStringLiteral("%1%").arg(QString::fromStdString(std::to_string(present)))); + }); + + slider->setValue(std::stoi(setting.ToString())); + slider->setMinimum(std::stoi(setting.MinVal())); + slider->setMaximum(max_val); + + if (reversed) { + slider->setInvertedAppearance(true); + } + + if (Settings::IsConfiguringGlobal()) { + load_func = [=]() { setting.LoadString(std::to_string(slider->value())); }; + } else { + CreateRestoreGlobalButton(); + layout->addWidget(restore_button); + + QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { + slider->setValue(std::stoi(setting.ToStringGlobal())); + + restore_button->setEnabled(false); + restore_button->setVisible(false); + }); + + QObject::connect(slider, &QAbstractSlider::sliderMoved, [=](int) { + restore_button->setEnabled(true); + restore_button->setVisible(true); + }); + + load_func = [=]() { + bool using_global = !restore_button->isEnabled(); + setting.SetGlobal(using_global); + if (!using_global) { + setting.LoadString(std::to_string(slider->value())); + } + }; + } +} + +void Widget::CreateCheckBoxWithLineEdit(const QString& label, const std::string& text_box_default, + std::function& load_func) { + created = true; + + CreateCheckBox(label, load_func); + + QHBoxLayout* layout = reinterpret_cast(this->layout()); + + line_edit = new QLineEdit(this); + line_edit->setText(QString::fromStdString(text_box_default)); + + checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + + layout->insertWidget(1, line_edit); + + QObject::connect(line_edit, &QLineEdit::textEdited, + [=](const QString&) { checkbox->setCheckState(Qt::Checked); }); + + if (!Settings::IsConfiguringGlobal()) { + QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { + line_edit->setText(QString::fromStdString(text_box_default)); + }); + + QObject::connect(line_edit, &QLineEdit::textEdited, [=](const QString&) { + restore_button->setEnabled(true); + restore_button->setVisible(true); + }); + } +} + +bool Widget::Valid() { + return created; +} + +Widget::~Widget() = default; + +Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, + QWidget* parent_, bool runtime_lock, + std::forward_list>& apply_funcs, RequestType request, + bool managed, float multiplier, const std::string& text_box_default) + : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_} { + if (!Settings::IsConfiguringGlobal() && !setting.Switchable()) { + LOG_DEBUG(Frontend, "\"{}\" is not switchable, skipping...", setting.GetLabel()); + return; + } + + const auto type = setting.TypeId(); + const int id = setting.Id(); + + const auto [label, tooltip] = [&]() { + const auto& setting_label = setting.GetLabel(); + if (translations.contains(id)) { + return std::pair{translations.at(id).first, translations.at(id).second}; + } + LOG_WARNING(Frontend, "Translation table lacks entry for \"{}\"", setting_label); + return std::pair{QString::fromStdString(setting_label), QStringLiteral("")}; + }(); + + if (label == QStringLiteral("")) { + LOG_DEBUG(Frontend, "Translation table has emtpy entry for \"{}\", skipping...", + setting.GetLabel()); + return; + } + + std::function load_func = []() {}; + + if (type == typeid(bool)) { + switch (request) { + case RequestType::Default: + CreateCheckBox(label, load_func); + break; + case RequestType::LineEdit: + case RequestType::SpinBox: + CreateCheckBoxWithLineEdit(label, text_box_default, load_func); + break; + case RequestType::ComboBox: + case RequestType::Slider: + case RequestType::ReverseSlider: + case RequestType::MaxEnum: + break; + } + } else if (setting.IsEnum()) { + CreateCombobox(label, managed, load_func); + } else if (type == typeid(u32) || type == typeid(int)) { + switch (request) { + case RequestType::Slider: + case RequestType::ReverseSlider: + CreateSlider(label, request == RequestType::ReverseSlider, multiplier, load_func); + break; + case RequestType::LineEdit: + case RequestType::Default: + CreateLineEdit(label, managed, load_func); + break; + case RequestType::ComboBox: + CreateCombobox(label, managed, load_func); + break; + case RequestType::SpinBox: + case RequestType::MaxEnum: + break; + } + } + + if (!created) { + LOG_ERROR(Frontend, "No widget was created for \"{}\"", setting.GetLabel()); + return; + } + + apply_funcs.push_front([load_func, setting_](bool powered_on) { + LOG_DEBUG(Frontend, "{}", setting_->GetLabel()); + if (setting_->RuntimeModfiable() || !powered_on) { + load_func(); + } + }); + + bool enable = runtime_lock || setting.RuntimeModfiable(); + if (setting.Switchable() && Settings::IsConfiguringGlobal() && !runtime_lock) { + enable &= setting.UsingGlobal(); + } + this->setEnabled(enable); + + this->setVisible(Settings::IsConfiguringGlobal() || setting.Switchable()); + + this->setToolTip(tooltip); +} + +} // namespace ConfigurationShared diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h new file mode 100644 index 000000000..559a27b41 --- /dev/null +++ b/src/yuzu/configuration/shared_widget.h @@ -0,0 +1,64 @@ +#include "yuzu/configuration/configuration_shared.h" +#include "yuzu/configuration/shared_translation.h" + +class QPushButton; +class QComboBox; +class QLineEdit; +class QSlider; +class QCheckBox; + +namespace Settings { +class BasicSetting; +} + +namespace ConfigurationShared { + +enum class RequestType { + Default, + ComboBox, + SpinBox, + Slider, + ReverseSlider, + LineEdit, + MaxEnum, +}; + +class Widget : public QWidget { + Q_OBJECT + +public: + Widget(Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, + bool runtime_lock, std::forward_list>& apply_funcs, + RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, + const std::string& text_box_default = ""); + virtual ~Widget(); + + bool Valid(); + + QPushButton* restore_button{}; + QLineEdit* line_edit{}; + QCheckBox* checkbox{}; + QSlider* slider{}; + QComboBox* combobox{}; + +private: + void CreateCheckBox(const QString& label, std::function& load_func); + void CreateCheckBoxWithLineEdit(const QString& label, const std::string& text_box_default, + std::function& load_func); + void CreateCheckBoxWithSpinBox(const QString& label, const std::string& text_box_default, + std::function& load_func); + void CreateCombobox(const QString& label, bool managed, std::function& load_func); + void CreateLineEdit(const QString& label, bool managed, std::function& load_func); + void CreateSlider(const QString& label, bool reversed, float multiplier, + std::function& load_func); + + void CreateRestoreGlobalButton(); + + QWidget* parent; + const TranslationMap& translations; + Settings::BasicSetting& setting; + + bool created{false}; +}; + +} // namespace ConfigurationShared From 640e7db60e768da34c11c14afd0821e4f43e86de Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 8 May 2023 23:55:34 -0400 Subject: [PATCH 024/155] configure_graphics: Remove redundant log --- src/yuzu/configuration/configure_graphics.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 093e33625..0b21f80f5 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -244,7 +244,6 @@ void ConfigureGraphics::SetConfiguration() { }(); if (!widget->Valid()) { - LOG_DEBUG(Frontend, "Deleted widget for \"{}\"", setting->GetLabel()); delete widget; continue; } From ea4afbfc54319b6fb4d0f4546da048bf68bdad3b Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 01:29:08 -0400 Subject: [PATCH 025/155] config: Don't merge the maps Me shooting myself in the foot 3 days in advance. --- src/yuzu/configuration/config.cpp | 19 ++++++++++--------- src/yuzu/configuration/config.h | 2 -- 2 files changed, 10 insertions(+), 11 deletions(-) diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 08aa20859..28c606f5e 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -19,10 +19,6 @@ namespace FS = Common::FS; Config::Config(const std::string& config_name, ConfigType config_type) : type(config_type), global{config_type == ConfigType::GlobalConfig} { - - settings_map = Settings::values.linkage.by_category; - settings_map.merge(UISettings::values.linkage.by_category); - Initialize(config_name); } @@ -1311,14 +1307,22 @@ const std::string& Config::GetConfigFilePath() const { return qt_config_loc; } +static auto FindRelevantList(Settings::Category category) { + auto& map = Settings::values.linkage.by_category; + if (map.contains(category)) { + return Settings::values.linkage.by_category[category]; + } + return UISettings::values.linkage.by_category[category]; +} + void Config::ReadCategory(Settings::Category category) { - const auto& settings = settings_map[category]; + const auto& settings = FindRelevantList(category); std::for_each(settings.begin(), settings.end(), [&](const auto& setting) { ReadSettingGeneric(setting); }); } void Config::WriteCategory(Settings::Category category) { - const auto& settings = settings_map[category]; + const auto& settings = FindRelevantList(category); std::for_each(settings.begin(), settings.end(), [&](const auto& setting) { WriteSettingGeneric(setting); }); } @@ -1346,11 +1350,8 @@ void Config::ReadSettingGeneric(Settings::BasicSetting* const setting) { void Config::WriteSettingGeneric(Settings::BasicSetting* const setting) const { if (!setting->Save()) { - LOG_DEBUG(Frontend, "Skipping \"{}\" marked for not saving", setting->GetLabel()); return; } - LOG_DEBUG(Frontend, "Saving {} setting \"{}\"...", global ? "global" : "custom", - setting->GetLabel()); const QVariant value = QVariant::fromValue(QString::fromStdString(setting->ToString())); const QVariant default_value = QVariant::fromValue(QString::fromStdString(setting->DefaultToString())); diff --git a/src/yuzu/configuration/config.h b/src/yuzu/configuration/config.h index ec748bf0c..553a82295 100644 --- a/src/yuzu/configuration/config.h +++ b/src/yuzu/configuration/config.h @@ -204,8 +204,6 @@ private: void ReadSettingGeneric(Settings::BasicSetting* const setting); void WriteSettingGeneric(Settings::BasicSetting* const setting) const; - std::map> settings_map; - const ConfigType type; std::unique_ptr qt_config; std::string qt_config_loc; From 464aad52cd644bdc32ca4eb35b0ce669c3b30c4f Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 01:35:25 -0400 Subject: [PATCH 026/155] settings: Add UiGeneral class --- src/common/settings.cpp | 4 ++++ src/common/settings.h | 7 +++++-- src/yuzu/configuration/config.cpp | 1 + src/yuzu/uisettings.h | 11 ++++++----- 4 files changed, 16 insertions(+), 7 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 38a82f6f7..b7a0c063f 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -144,6 +144,9 @@ float Volume() { return values.volume.GetValue() / static_cast(values.volume.GetDefault()); } +Linkage::Linkage() = default; +Linkage::~Linkage() = default; + const char* TranslateCategory(Category category) { switch (category) { case Category::Audio: @@ -176,6 +179,7 @@ const char* TranslateCategory(Category category) { case Category::Controls: return "Controls"; case Category::Ui: + case Category::UiGeneral: return "UI"; case Category::UiLayout: return "UiLayout"; diff --git a/src/common/settings.h b/src/common/settings.h index 4ca8299b3..e60105059 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -143,6 +143,7 @@ enum class Category : u32 { AddOns, Controls, Ui, + UiGeneral, UiLayout, UiGameList, Screenshots, @@ -209,8 +210,10 @@ public: class Linkage { public: - std::map> by_category; - std::vector> restore_functions; + explicit Linkage(); + ~Linkage(); + std::map> by_category{}; + std::vector> restore_functions{}; u32 count; }; diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 28c606f5e..3181a9528 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -717,6 +717,7 @@ void Config::ReadUIValues() { ReadMultiplayerValues(); ReadCategory(Settings::Category::Ui); + ReadCategory(Settings::Category::UiGeneral); qt_config->endGroup(); } diff --git a/src/yuzu/uisettings.h b/src/yuzu/uisettings.h index 53cdd7fcb..9e2cea4d6 100644 --- a/src/yuzu/uisettings.h +++ b/src/yuzu/uisettings.h @@ -78,17 +78,18 @@ struct Values { Setting show_filter_bar{linkage, true, "showFilterBar", Category::Ui}; Setting show_status_bar{linkage, true, "showStatusBar", Category::Ui}; - Setting confirm_before_closing{linkage, true, "confirmClose", Category::Ui}; + Setting confirm_before_closing{linkage, true, "confirmClose", Category::UiGeneral}; Setting first_start{linkage, true, "firstStart", Category::Ui}; - Setting pause_when_in_background{linkage, false, "pauseWhenInBackground", Category::Ui}; + Setting pause_when_in_background{linkage, false, "pauseWhenInBackground", + Category::UiGeneral}; Setting mute_when_in_background{linkage, false, "muteWhenInBackground", Category::Ui}; - Setting hide_mouse{linkage, true, "hideInactiveMouse", Category::Ui}; + Setting hide_mouse{linkage, true, "hideInactiveMouse", Category::UiGeneral}; Setting controller_applet_disabled{linkage, false, "disableControllerApplet", - Category::Ui}; + Category::UiGeneral}; // Set when Vulkan is known to crash the application bool has_broken_vulkan = false; - Setting select_user_on_boot{linkage, false, "select_user_on_boot", Category::Ui}; + Setting select_user_on_boot{linkage, false, "select_user_on_boot", Category::UiGeneral}; Setting disable_web_applet{linkage, true, "disable_web_applet", Category::Ui}; // Discord RPC From d3d9c3568e9b234d3f4c6679651189c3bae68dbc Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 01:36:05 -0400 Subject: [PATCH 027/155] shared_widget: Fix header --- src/yuzu/configuration/shared_widget.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 559a27b41..3d96805ed 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -1,3 +1,5 @@ +#pragma once + #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/shared_translation.h" From c530532de7f532eb39278b25d9810ced2e61872a Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 01:36:17 -0400 Subject: [PATCH 028/155] shared_translation: Add UI widget translations --- src/yuzu/configuration/shared_translation.cpp | 128 ++++++++++-------- 1 file changed, 73 insertions(+), 55 deletions(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index a13636af6..d38815e77 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -11,6 +11,7 @@ #include #include "common/settings.h" #include "yuzu/configuration/shared_translation.h" +#include "yuzu/uisettings.h" namespace ConfigurationShared { @@ -18,102 +19,105 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { std::unique_ptr translations = std::make_unique(); const auto& tr = [parent](const char* text) -> QString { return parent->tr(text); }; -#define INSERT(ID, NAME, TOOLTIP) \ - translations->insert(std::pair{Settings::values.ID.Id(), std::pair{tr((NAME)), tr((TOOLTIP))}}) +#define INSERT(SETTINGS, ID, NAME, TOOLTIP) \ + translations->insert(std::pair{SETTINGS::values.ID.Id(), std::pair{tr((NAME)), tr((TOOLTIP))}}) // A setting can be ignored by giving it a blank name // Audio - INSERT(sink_id, "Output Engine:", ""); - INSERT(audio_output_device_id, "Output Device:", ""); - INSERT(audio_input_device_id, "Input Device:", ""); - INSERT(audio_muted, "Mute audio when in background", ""); - INSERT(volume, "Volume:", ""); + INSERT(Settings, sink_id, "Output Engine:", ""); + INSERT(Settings, audio_output_device_id, "Output Device:", ""); + INSERT(Settings, audio_input_device_id, "Input Device:", ""); + INSERT(Settings, audio_muted, "Mute audio when in background", ""); + INSERT(Settings, volume, "Volume:", ""); // Core - INSERT(use_multi_core, "Multicore CPU Emulation", ""); - INSERT(use_unsafe_extended_memory_layout, "Unsafe extended memory layout (8GB DRAM)", ""); + INSERT(Settings, use_multi_core, "Multicore CPU Emulation", ""); + INSERT(Settings, use_unsafe_extended_memory_layout, "Unsafe extended memory layout (8GB DRAM)", + ""); // Cpu - INSERT(cpu_accuracy, "Accuracy:", ""); - INSERT(cpu_accuracy_first_time, "", ""); + INSERT(Settings, cpu_accuracy, "Accuracy:", ""); + INSERT(Settings, cpu_accuracy_first_time, "", ""); // Cpu Debug // Cpu Unsafe - INSERT(cpuopt_unsafe_unfuse_fma, "Unfuse FMA (improve performance on CPUs without FMA)", ""); - INSERT(cpuopt_unsafe_reduce_fp_error, "Faster FRSQRTE and FRECPE", ""); - INSERT(cpuopt_unsafe_ignore_standard_fpcr, "Faster ASIMD instructions (32 bits only)", ""); - INSERT(cpuopt_unsafe_inaccurate_nan, "Inaccurate NaN handling", ""); - INSERT(cpuopt_unsafe_fastmem_check, "Disable address space checks", ""); - INSERT(cpuopt_unsafe_ignore_global_monitor, "Ignore global monitor", ""); + INSERT(Settings, cpuopt_unsafe_unfuse_fma, + "Unfuse FMA (improve performance on CPUs without FMA)", ""); + INSERT(Settings, cpuopt_unsafe_reduce_fp_error, "Faster FRSQRTE and FRECPE", ""); + INSERT(Settings, cpuopt_unsafe_ignore_standard_fpcr, "Faster ASIMD instructions (32 bits only)", + ""); + INSERT(Settings, cpuopt_unsafe_inaccurate_nan, "Inaccurate NaN handling", ""); + INSERT(Settings, cpuopt_unsafe_fastmem_check, "Disable address space checks", ""); + INSERT(Settings, cpuopt_unsafe_ignore_global_monitor, "Ignore global monitor", ""); // Renderer - INSERT(renderer_backend, "API:", ""); - INSERT(vulkan_device, "Device:", ""); - INSERT(shader_backend, "Shader Backend:", ""); - INSERT(resolution_setup, "Resolution:", ""); - INSERT(scaling_filter, "Window Adapting Filter:", ""); - INSERT(fsr_sharpening_slider, "AMD FidelityFX™ Super Resolution Sharpness:", ""); - INSERT(anti_aliasing, "Anti-Aliasing Method:", ""); - INSERT(fullscreen_mode, "Fullscreen Mode:", ""); - INSERT(aspect_ratio, "Aspect Ratio:", ""); - INSERT(use_disk_shader_cache, "Use disk pipeline cache", ""); - INSERT(use_asynchronous_gpu_emulation, "Use asynchronous GPU emulation", ""); - INSERT(nvdec_emulation, "NVDEC emulation:", ""); - INSERT(accelerate_astc, "ASTC Decoding Method:", ""); - INSERT(vsync_mode, "VSync Mode:", + INSERT(Settings, renderer_backend, "API:", ""); + INSERT(Settings, vulkan_device, "Device:", ""); + INSERT(Settings, shader_backend, "Shader Backend:", ""); + INSERT(Settings, resolution_setup, "Resolution:", ""); + INSERT(Settings, scaling_filter, "Window Adapting Filter:", ""); + INSERT(Settings, fsr_sharpening_slider, "AMD FidelityFX™ Super Resolution Sharpness:", ""); + INSERT(Settings, anti_aliasing, "Anti-Aliasing Method:", ""); + INSERT(Settings, fullscreen_mode, "Fullscreen Mode:", ""); + INSERT(Settings, aspect_ratio, "Aspect Ratio:", ""); + INSERT(Settings, use_disk_shader_cache, "Use disk pipeline cache", ""); + INSERT(Settings, use_asynchronous_gpu_emulation, "Use asynchronous GPU emulation", ""); + INSERT(Settings, nvdec_emulation, "NVDEC emulation:", ""); + INSERT(Settings, accelerate_astc, "ASTC Decoding Method:", ""); + INSERT(Settings, vsync_mode, "VSync Mode:", "FIFO (VSync) does not drop frames or exhibit tearing but is limited by the screen " "refresh rate.\nFIFO Relaxed is similar to FIFO but allows tearing as it recovers from " "a slow down.\nMailbox can have lower latency than FIFO and does not tear but may drop " "frames.\nImmediate (no synchronization) just presents whatever is available and can " "exhibit tearing."); - INSERT(bg_red, "", ""); - INSERT(bg_green, "", ""); - INSERT(bg_blue, "", ""); + INSERT(Settings, bg_red, "", ""); + INSERT(Settings, bg_green, "", ""); + INSERT(Settings, bg_blue, "", ""); // Renderer (Advanced Graphics) - INSERT(async_presentation, "Enable asynchronous presentation (Vulkan only)", ""); - INSERT(renderer_force_max_clock, "Force maximum clocks (Vulkan only)", + INSERT(Settings, async_presentation, "Enable asynchronous presentation (Vulkan only)", ""); + INSERT(Settings, renderer_force_max_clock, "Force maximum clocks (Vulkan only)", "Runs work in the background while waiting for graphics commands to keep the GPU from " "lowering its clock speed."); - INSERT(max_anisotropy, "Anisotropic Filtering:", ""); - INSERT(gpu_accuracy, "Accuracy Level:", ""); - INSERT(use_asynchronous_shaders, "Use asynchronous shader building (Hack)", + INSERT(Settings, max_anisotropy, "Anisotropic Filtering:", ""); + INSERT(Settings, gpu_accuracy, "Accuracy Level:", ""); + INSERT(Settings, use_asynchronous_shaders, "Use asynchronous shader building (Hack)", "Enables asynchronous shader compilation, which may reduce shader stutter. This feature " "is experimental."); - INSERT(use_fast_gpu_time, "Use Fast GPU Time (Hack)", + INSERT(Settings, use_fast_gpu_time, "Use Fast GPU Time (Hack)", "Enables Fast GPU Time. This option will force most games to run at their highest " "native resolution."); - INSERT(use_vulkan_driver_pipeline_cache, "Use Vulkan pipeline cache", + INSERT(Settings, use_vulkan_driver_pipeline_cache, "Use Vulkan pipeline cache", "Enables GPU vendor-specific pipeline cache. This option can improve shader loading " "time significantly in cases where the Vulkan driver does not store pipeline cache " "files internally."); - INSERT(enable_compute_pipelines, "Enable Compute Pipelines (Intel Vulkan Only)", + INSERT(Settings, enable_compute_pipelines, "Enable Compute Pipelines (Intel Vulkan Only)", "Enable compute pipelines, required by some games.\nThis setting only exists for Intel " "proprietary drivers, and may crash if enabled.\nCompute pipelines are always enabled " "on all other drivers."); - INSERT(use_reactive_flushing, "Enable Reactive Flushing", + INSERT(Settings, use_reactive_flushing, "Enable Reactive Flushing", "Uses reactive flushing instead of predictive flushing, allowing more accurate memory " "syncing."); // Renderer (Debug) // Renderer (General) - INSERT(use_speed_limit, "Limit Speed Percent", ""); - INSERT(speed_limit, "Limit Speed Percent", ""); + INSERT(Settings, use_speed_limit, "", ""); + INSERT(Settings, speed_limit, "Limit Speed Percent", ""); // System - INSERT(rng_seed_enabled, "RNG Seed", ""); - INSERT(rng_seed, "RNG Seed", ""); - INSERT(device_name, "Device Name", ""); - INSERT(custom_rtc_enabled, "Custom RTC", ""); - INSERT(custom_rtc, "Custom RTC", ""); - INSERT(language_index, "Language:", ""); - INSERT(region_index, "Region:", ""); - INSERT(time_zone_index, "Time Zone:", ""); - INSERT(sound_index, "Sound Output Mode:", ""); - INSERT(use_docked_mode, "", ""); + INSERT(Settings, rng_seed_enabled, "RNG Seed", ""); + INSERT(Settings, rng_seed, "RNG Seed", ""); + INSERT(Settings, device_name, "Device Name", ""); + INSERT(Settings, custom_rtc_enabled, "Custom RTC", ""); + INSERT(Settings, custom_rtc, "Custom RTC", ""); + INSERT(Settings, language_index, "Language:", ""); + INSERT(Settings, region_index, "Region:", ""); + INSERT(Settings, time_zone_index, "Time Zone:", ""); + INSERT(Settings, sound_index, "Sound Output Mode:", ""); + INSERT(Settings, use_docked_mode, "", ""); // Controls @@ -127,6 +131,20 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { // Web Service + // Ui + + // Ui General + INSERT(UISettings, select_user_on_boot, "Prompt for user on game boot", ""); + INSERT(UISettings, pause_when_in_background, "Pause emulation when in background", ""); + INSERT(UISettings, confirm_before_closing, "Confirm exit while emulation is running", ""); + INSERT(UISettings, hide_mouse, "Hide mouse on inactivity", ""); + + // Ui Debugging + + // Ui Multiplayer + + // Ui Games list + #undef INSERT return translations; From 827082c5ac30ff488016d168e3ca93021eb612e4 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 01:38:01 -0400 Subject: [PATCH 029/155] configure_general: Generate UI using containers This leaves per-game config's General tab empty? --- src/yuzu/configuration/configure_dialog.cpp | 2 +- src/yuzu/configuration/configure_general.cpp | 105 ++++-------------- src/yuzu/configuration/configure_general.h | 8 +- src/yuzu/configuration/configure_general.ui | 87 +++------------ src/yuzu/configuration/configure_per_game.cpp | 2 +- 5 files changed, 41 insertions(+), 163 deletions(-) diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index 5b356a074..8baa8de1e 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -38,7 +38,7 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, cpu_tab{std::make_unique(system_, nullptr, this)}, debug_tab_tab{std::make_unique(system_, this)}, filesystem_tab{std::make_unique(this)}, - general_tab{std::make_unique(system_, nullptr, this)}, + general_tab{std::make_unique(system_, nullptr, *translations, this)}, graphics_advanced_tab{ std::make_unique(system_, nullptr, *translations, this)}, graphics_tab{std::make_unique( diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index 764ff68b3..743ea824c 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -9,23 +9,19 @@ #include "ui_configure_general.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_general.h" +#include "yuzu/configuration/shared_widget.h" #include "yuzu/uisettings.h" ConfigureGeneral::ConfigureGeneral( const Core::System& system_, - std::shared_ptr> group, QWidget* parent) - : Tab(group, parent), ui{std::make_unique()}, system{system_} { + std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, QWidget* parent) + : Tab(group, parent), ui{std::make_unique()}, system{system_}, + translations{translations_} { ui->setupUi(this); - SetupPerGameUI(); - SetConfiguration(); - // if (Settings::IsConfiguringGlobal()) { - // connect(ui->toggle_speed_limit, &QCheckBox::clicked, ui->speed_limit, - // [this]() { ui->speed_limit->setEnabled(ui->toggle_speed_limit->isChecked()); }); - // } - connect(ui->button_reset_defaults, &QPushButton::clicked, this, &ConfigureGeneral::ResetDefaults); } @@ -34,29 +30,20 @@ ConfigureGeneral::~ConfigureGeneral() = default; void ConfigureGeneral::SetConfiguration() { const bool runtime_lock = !system.IsPoweredOn(); + QLayout& layout = *ui->general_widget->layout(); - ui->use_multi_core->setEnabled(runtime_lock); - ui->use_multi_core->setChecked(Settings::values.use_multi_core.GetValue()); + for (const auto setting : + UISettings::values.linkage.by_category[Settings::Category::UiGeneral]) { + ConfigurationShared::Widget* widget = + new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); - ui->toggle_check_exit->setChecked(UISettings::values.confirm_before_closing.GetValue()); - ui->toggle_user_on_boot->setChecked(UISettings::values.select_user_on_boot.GetValue()); - ui->toggle_background_pause->setChecked(UISettings::values.pause_when_in_background.GetValue()); - ui->toggle_hide_mouse->setChecked(UISettings::values.hide_mouse.GetValue()); - ui->toggle_controller_applet_disabled->setEnabled(runtime_lock); - ui->toggle_controller_applet_disabled->setChecked( - UISettings::values.controller_applet_disabled.GetValue()); + if (!widget->Valid()) { + delete widget; + continue; + } - // ui->toggle_speed_limit->setChecked(Settings::values.use_speed_limit.GetValue()); - // ui->speed_limit->setValue(Settings::values.speed_limit.GetValue()); - - ui->button_reset_defaults->setEnabled(runtime_lock); - - // if (Settings::IsConfiguringGlobal()) { - // ui->speed_limit->setEnabled(Settings::values.use_speed_limit.GetValue()); - // } else { - // ui->speed_limit->setEnabled(Settings::values.use_speed_limit.GetValue() && - // use_speed_limit != ConfigurationShared::CheckState::Global); - // } + layout.addWidget(widget); + } } // Called to set the callback when resetting settings to defaults @@ -79,32 +66,9 @@ void ConfigureGeneral::ResetDefaults() { } void ConfigureGeneral::ApplyConfiguration() { - ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_multi_core, ui->use_multi_core, - use_multi_core); - - if (Settings::IsConfiguringGlobal()) { - UISettings::values.confirm_before_closing = ui->toggle_check_exit->isChecked(); - UISettings::values.select_user_on_boot = ui->toggle_user_on_boot->isChecked(); - UISettings::values.pause_when_in_background = ui->toggle_background_pause->isChecked(); - UISettings::values.hide_mouse = ui->toggle_hide_mouse->isChecked(); - UISettings::values.controller_applet_disabled = - ui->toggle_controller_applet_disabled->isChecked(); - - // Guard if during game and set to game-specific value - // if (Settings::values.use_speed_limit.UsingGlobal()) { - // Settings::values.use_speed_limit.SetValue(ui->toggle_speed_limit->checkState() == - // Qt::Checked); - // Settings::values.speed_limit.SetValue(ui->speed_limit->value()); - // } - } else { - // bool global_speed_limit = use_speed_limit == ConfigurationShared::CheckState::Global; - // Settings::values.use_speed_limit.SetGlobal(global_speed_limit); - // Settings::values.speed_limit.SetGlobal(global_speed_limit); - // if (!global_speed_limit) { - // Settings::values.use_speed_limit.SetValue(ui->toggle_speed_limit->checkState() == - // Qt::Checked); - // Settings::values.speed_limit.SetValue(ui->speed_limit->value()); - // } + bool powered_on = system.IsPoweredOn(); + for (const auto& func : apply_funcs) { + func(powered_on); } } @@ -119,34 +83,3 @@ void ConfigureGeneral::changeEvent(QEvent* event) { void ConfigureGeneral::RetranslateUI() { ui->retranslateUi(this); } - -void ConfigureGeneral::SetupPerGameUI() { - if (Settings::IsConfiguringGlobal()) { - // Disables each setting if: - // - A game is running (thus settings in use), and - // - A non-global setting is applied. - // ui->toggle_speed_limit->setEnabled(Settings::values.use_speed_limit.UsingGlobal()); - // ui->speed_limit->setEnabled(Settings::values.speed_limit.UsingGlobal()); - - return; - } - - ui->toggle_check_exit->setVisible(false); - ui->toggle_user_on_boot->setVisible(false); - ui->toggle_background_pause->setVisible(false); - ui->toggle_hide_mouse->setVisible(false); - ui->toggle_controller_applet_disabled->setVisible(false); - - ui->button_reset_defaults->setVisible(false); - - // ConfigurationShared::SetColoredTristate(ui->toggle_speed_limit, - // Settings::values.use_speed_limit, use_speed_limit); - ConfigurationShared::SetColoredTristate(ui->use_multi_core, Settings::values.use_multi_core, - use_multi_core); - - // connect(ui->toggle_speed_limit, &QCheckBox::clicked, ui->speed_limit, [this]() { - // ui->speed_limit->setEnabled(ui->toggle_speed_limit->isChecked() && - // (use_speed_limit != - // ConfigurationShared::CheckState::Global)); - // }); -} diff --git a/src/yuzu/configuration/configure_general.h b/src/yuzu/configuration/configure_general.h index 0aad69f0a..7692c16da 100644 --- a/src/yuzu/configuration/configure_general.h +++ b/src/yuzu/configuration/configure_general.h @@ -7,6 +7,7 @@ #include #include #include "yuzu/configuration/configuration_shared.h" +#include "yuzu/configuration/shared_widget.h" namespace Core { class System; @@ -23,6 +24,7 @@ class ConfigureGeneral : public ConfigurationShared::Tab { public: explicit ConfigureGeneral(const Core::System& system_, std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, QWidget* parent = nullptr); ~ConfigureGeneral() override; @@ -35,14 +37,12 @@ private: void changeEvent(QEvent* event) override; void RetranslateUI(); - void SetupPerGameUI(); - std::function reset_callback; std::unique_ptr ui; - ConfigurationShared::CheckState use_speed_limit; - ConfigurationShared::CheckState use_multi_core; + std::forward_list> apply_funcs{}; const Core::System& system; + const ConfigurationShared::TranslationMap& translations; }; diff --git a/src/yuzu/configuration/configure_general.ui b/src/yuzu/configuration/configure_general.ui index fe757d011..a10e7d3a5 100644 --- a/src/yuzu/configuration/configure_general.ui +++ b/src/yuzu/configuration/configure_general.ui @@ -26,77 +26,22 @@ - - - - - - - Limit Speed Percent - - - - - - - % - - - 1 - - - 9999 - - - 100 - - - - - - - - - Multicore CPU Emulation - - - - - - - Confirm exit while emulation is running - - - - - - - Prompt for user on game boot - - - - - - - Pause emulation when in background - - - - - - - Hide mouse on inactivity - - - - - - - Disable controller applet - - - - + + + + 0 + + + 0 + + + 0 + + + 0 + + + diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index 9e229977d..05da9bda0 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -53,7 +53,7 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st addons_tab = std::make_unique(system_, this); audio_tab = std::make_unique(system_, tab_group, this); cpu_tab = std::make_unique(system_, tab_group, this); - general_tab = std::make_unique(system_, tab_group, this); + general_tab = std::make_unique(system_, tab_group, *translations, this); graphics_advanced_tab = std::make_unique(system_, tab_group, *translations, this); graphics_tab = std::make_unique( From e2de48f14b421f810b26d83c3fabd3b46c3fcc9d Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 14:11:40 -0400 Subject: [PATCH 030/155] configure_general: Sort data --- src/yuzu/configuration/configure_general.cpp | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index 743ea824c..a7f26023d 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -32,9 +32,11 @@ void ConfigureGeneral::SetConfiguration() { const bool runtime_lock = !system.IsPoweredOn(); QLayout& layout = *ui->general_widget->layout(); + std::map hold{}; + for (const auto setting : UISettings::values.linkage.by_category[Settings::Category::UiGeneral]) { - ConfigurationShared::Widget* widget = + auto* widget = new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); if (!widget->Valid()) { @@ -42,6 +44,10 @@ void ConfigureGeneral::SetConfiguration() { continue; } + hold.insert({setting->GetLabel(), widget}); + } + + for (const auto& [label, widget] : hold) { layout.addWidget(widget); } } From 8c03ae793eaca063f161695dae0921bf7d04a817 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 14:13:59 -0400 Subject: [PATCH 031/155] configure_general: Hide reset button in custom configs --- src/yuzu/configuration/configure_general.cpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index a7f26023d..7eb6cb9ec 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -24,6 +24,10 @@ ConfigureGeneral::ConfigureGeneral( connect(ui->button_reset_defaults, &QPushButton::clicked, this, &ConfigureGeneral::ResetDefaults); + + if (!Settings::IsConfiguringGlobal()) { + ui->button_reset_defaults->setVisible(false); + } } ConfigureGeneral::~ConfigureGeneral() = default; From c1748b229a81390c3ee81a1b951455839204c572 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 14:26:03 -0400 Subject: [PATCH 032/155] shared_widget: Make button creation static --- src/yuzu/configuration/shared_widget.cpp | 17 +++++++++-------- src/yuzu/configuration/shared_widget.h | 5 +++-- 2 files changed, 12 insertions(+), 10 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 0676973a9..ba44d1973 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -14,10 +14,10 @@ namespace ConfigurationShared { -void Widget::CreateRestoreGlobalButton() { - QStyle* style = this->style(); +QPushButton* Widget::CreateRestoreGlobalButton(Settings::BasicSetting& setting, QWidget* parent) { + QStyle* style = parent->style(); QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_DialogResetButton)); - restore_button = new QPushButton(*icon, QStringLiteral(""), this); + QPushButton* restore_button = new QPushButton(*icon, QStringLiteral(""), parent); restore_button->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Expanding); QSizePolicy sp_retain = restore_button->sizePolicy(); @@ -26,6 +26,8 @@ void Widget::CreateRestoreGlobalButton() { restore_button->setEnabled(!setting.UsingGlobal()); restore_button->setVisible(!setting.UsingGlobal()); + + return restore_button; } void Widget::CreateCheckBox(const QString& label, std::function& load_func) { @@ -44,7 +46,7 @@ void Widget::CreateCheckBox(const QString& label, std::function& load_fu setting.LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); }; } else { - CreateRestoreGlobalButton(); + restore_button = CreateRestoreGlobalButton(setting, this); layout->addWidget(restore_button); QObject::connect(checkbox, &QCheckBox::stateChanged, [&](int) { @@ -97,7 +99,7 @@ void Widget::CreateCombobox(const QString& label, bool managed, std::functioncurrentIndex())); }; } else if (managed) { - CreateRestoreGlobalButton(); + restore_button = CreateRestoreGlobalButton(setting, this); layout->addWidget(restore_button); QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { @@ -144,7 +146,7 @@ void Widget::CreateLineEdit(const QString& label, bool managed, std::functionaddWidget(restore_button); QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { @@ -207,7 +209,7 @@ void Widget::CreateSlider(const QString& name, bool reversed, float multiplier, if (Settings::IsConfiguringGlobal()) { load_func = [=]() { setting.LoadString(std::to_string(slider->value())); }; } else { - CreateRestoreGlobalButton(); + restore_button = CreateRestoreGlobalButton(setting, this); layout->addWidget(restore_button); QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { @@ -340,7 +342,6 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati } apply_funcs.push_front([load_func, setting_](bool powered_on) { - LOG_DEBUG(Frontend, "{}", setting_->GetLabel()); if (setting_->RuntimeModfiable() || !powered_on) { load_func(); } diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 3d96805ed..8d2d7f269 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -37,6 +37,9 @@ public: bool Valid(); + [[nodiscard]] static QPushButton* CreateRestoreGlobalButton(Settings::BasicSetting& setting, + QWidget* parent); + QPushButton* restore_button{}; QLineEdit* line_edit{}; QCheckBox* checkbox{}; @@ -54,8 +57,6 @@ private: void CreateSlider(const QString& label, bool reversed, float multiplier, std::function& load_func); - void CreateRestoreGlobalButton(); - QWidget* parent; const TranslationMap& translations; Settings::BasicSetting& setting; From 23f874ae60eebae5451722cd89101e76e1e14065 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 15:10:22 -0400 Subject: [PATCH 033/155] configure_graphics: Reimplement bg_color To specialized a setting to be worth adding to the shared_widget imo, so add it roughly like before. --- src/yuzu/configuration/configure_graphics.cpp | 74 +++++++++++++++---- src/yuzu/configuration/configure_graphics.h | 2 + src/yuzu/configuration/configure_graphics.ui | 50 +++++++++++++ 3 files changed, 111 insertions(+), 15 deletions(-) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 0b21f80f5..4c6d69703 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -88,7 +88,7 @@ ConfigureGraphics::ConfigureGraphics( ui->setupUi(this); - SetConfiguration(); + Setup(); for (const auto& device : vulkan_devices) { vulkan_device_combobox->addItem(device); @@ -128,20 +128,22 @@ ConfigureGraphics::ConfigureGraphics( connect(shader_backend_combobox, qOverload(&QComboBox::activated), this, [this](int backend) { UpdateShaderBackendSelection(backend); }); - // connect(ui->bg_button, &QPushButton::clicked, this, [this] { - // const QColor new_bg_color = QColorDialog::getColor(bg_color); - // if (!new_bg_color.isValid()) { - // return; - // } - // UpdateBackgroundColorButton(new_bg_color); - // }); - // ui->bg_label->setVisible(Settings::IsConfiguringGlobal()); - // ui->bg_combobox->setVisible(!Settings::IsConfiguringGlobal()); + connect(ui->bg_button, &QPushButton::clicked, this, [this] { + const QColor new_bg_color = QColorDialog::getColor(bg_color); + if (!new_bg_color.isValid()) { + return; + } + UpdateBackgroundColorButton(new_bg_color); + }); api_combobox->setEnabled(!UISettings::values.has_broken_vulkan && api_combobox->isEnabled()); ui->api_widget->setEnabled( (!UISettings::values.has_broken_vulkan || Settings::IsConfiguringGlobal()) && ui->api_widget->isEnabled()); + + if (Settings::IsConfiguringGlobal()) { + ui->bg_widget->setEnabled(Settings::values.bg_red.UsingGlobal()); + } } void ConfigureGraphics::PopulateVSyncModeSelection() { @@ -205,7 +207,9 @@ void ConfigureGraphics::UpdateShaderBackendSelection(int backend) { ConfigureGraphics::~ConfigureGraphics() = default; -void ConfigureGraphics::SetConfiguration() { +void ConfigureGraphics::SetConfiguration() {} + +void ConfigureGraphics::Setup() { const bool runtime_lock = !system.IsPoweredOn(); QLayout* api_layout = ui->api_widget->layout(); QWidget* api_grid_widget = new QWidget(this); @@ -305,6 +309,46 @@ void ConfigureGraphics::SetConfiguration() { for (auto widget : hold_api) { api_grid_layout->addWidget(widget); } + + if (Settings::IsConfiguringGlobal()) { + apply_funcs.push_front([this](bool powered_on) { + Settings::values.bg_red.SetValue(static_cast(bg_color.red())); + Settings::values.bg_green.SetValue(static_cast(bg_color.green())); + Settings::values.bg_blue.SetValue(static_cast(bg_color.blue())); + }); + } else { + QPushButton* bg_restore_button = ConfigurationShared::Widget::CreateRestoreGlobalButton( + Settings::values.bg_red, ui->bg_widget); + ui->bg_widget->layout()->addWidget(bg_restore_button); + + QObject::connect(bg_restore_button, &QAbstractButton::clicked, + [bg_restore_button, this](bool) { + const int r = Settings::values.bg_red.GetValue(true); + const int g = Settings::values.bg_green.GetValue(true); + const int b = Settings::values.bg_blue.GetValue(true); + UpdateBackgroundColorButton(QColor::fromRgb(r, g, b)); + + bg_restore_button->setVisible(false); + bg_restore_button->setEnabled(false); + }); + + QObject::connect(ui->bg_button, &QAbstractButton::clicked, [bg_restore_button](bool) { + bg_restore_button->setVisible(true); + bg_restore_button->setEnabled(true); + }); + + apply_funcs.push_front([bg_restore_button, this](bool powered_on) { + const bool using_global = !bg_restore_button->isEnabled(); + Settings::values.bg_red.SetGlobal(using_global); + Settings::values.bg_green.SetGlobal(using_global); + Settings::values.bg_blue.SetGlobal(using_global); + if (!using_global) { + Settings::values.bg_red.SetValue(static_cast(bg_color.red())); + Settings::values.bg_green.SetValue(static_cast(bg_color.green())); + Settings::values.bg_blue.SetValue(static_cast(bg_color.blue())); + } + }); + } } const QString ConfigureGraphics::TranslateVSyncMode(VkPresentModeKHR mode, @@ -375,11 +419,11 @@ void ConfigureGraphics::RetranslateUI() { void ConfigureGraphics::UpdateBackgroundColorButton(QColor color) { bg_color = color; - // QPixmap pixmap(ui->bg_button->size()); - // pixmap.fill(bg_color); + QPixmap pixmap(ui->bg_button->size()); + pixmap.fill(bg_color); - // const QIcon color_icon(pixmap); - // ui->bg_button->setIcon(color_icon); + const QIcon color_icon(pixmap); + ui->bg_button->setIcon(color_icon); } void ConfigureGraphics::UpdateAPILayout() { diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index 4ef551341..61eb2f2fc 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -51,6 +51,8 @@ private: void changeEvent(QEvent* event) override; void RetranslateUI(); + void Setup(); + void PopulateVSyncModeSelection(); void UpdateBackgroundColorButton(QColor color); void UpdateAPILayout(); diff --git a/src/yuzu/configuration/configure_graphics.ui b/src/yuzu/configuration/configure_graphics.ui index 1f6ffea1a..d09415d70 100644 --- a/src/yuzu/configuration/configure_graphics.ui +++ b/src/yuzu/configuration/configure_graphics.ui @@ -76,6 +76,56 @@ + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + 0 + + + + Background Color: + + + + + + + + 0 + 0 + + + + + 40 + 16777215 + + + + + + + + + + From def00e8c55796cc89abf745df2160873cf1c5f80 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 15:45:42 -0400 Subject: [PATCH 034/155] configure_debug: Reorganize --- src/yuzu/configuration/configure_debug.ui | 852 +++++++++++++--------- 1 file changed, 519 insertions(+), 333 deletions(-) diff --git a/src/yuzu/configuration/configure_debug.ui b/src/yuzu/configuration/configure_debug.ui index 15acefe33..97c7d9022 100644 --- a/src/yuzu/configuration/configure_debug.ui +++ b/src/yuzu/configuration/configure_debug.ui @@ -2,360 +2,549 @@ ConfigureDebug + + + 0 + 0 + 831 + 760 + + true - - - - - - - - Debugger - - - - - - - - Enable GDB Stub - - - - - - - Qt::Horizontal - - - - 40 - 20 - - - - - - - - Port: - - - - - - - 1024 - - - 65535 - - - - - - - - - - - - - - Logging - - - - - - - - Global Log Filter - - - - - - - - - - - - Show Log in Console - - - - - - - Open Log Location - - - - - - - true - - - When checked, the max size of the log increases from 100 MB to 1 GB - - - Enable Extended Logging** - - - - - - - - - - Homebrew - - + + + + 0 + 0 + 829 + 758 + + + + + + + 0 + - - - - - Arguments String - - - - - - - - - - - - - - - Graphics - - - - - - true + + + + 0 + 0 + - - When checked, the graphics API enters a slower debugging mode + + Debugger - - Enable Graphics Debugging + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop + + false + + + false + + + + + + + 0 + 0 + + + + + QLayout::SetDefaultConstraint + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + 0 + + + + Enable GDB Stub + + + + + + + + 0 + 0 + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + 0 + + + + Port: + + + + + + + + 0 + 0 + + + + 1024 + + + 65535 + + + + + + + + + + - - - - When checked, it enables Nsight Aftermath crash dumps + + + + + 0 + 0 + - - Enable Nsight Aftermath - - - - - - - true - - - When checked, it will dump all the original assembler shaders from the disk shader cache or game as found - - - Dump Game Shaders - - - - - - - true - - - When checked, it will dump all the macro programs of the GPU - - - Dump Maxwell Macros - - - - - - - true - - - When checked, it disables the macro Just In Time compiler. Enabling this makes games run slower - - - Disable Macro JIT - - - - - - - true - - - When checked, it disables the macro HLE functions. Enabling this makes games run slower - - - Disable Macro HLE - - - - - - - When checked, yuzu will log statistics about the compiled pipeline cache - - - Enable Shader Feedback - - - - - - - When checked, it executes shaders without loop logic changes - - - Disable Loop safety checks + + Logging + + + + + Open Log Location + + + + + + + + 0 + 0 + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + 0 + + + + Global Log Filter + + + + + + + + + + + + + true + + + When checked, the max size of the log increases from 100 MB to 1 GB + + + Enable Extended Logging** + + + + + + + Show Log in Console + + + + - - - - - - Debugging - - - - - - Enable Verbose Reporting Services** + + + + + Homebrew + + + + + + + + Arguments String + + + + + + + + + + + + + + + + + Graphics + + + + + When checked, it executes shaders without loop logic changes + + + Disable Loop safety checks + + + + + + + true + + + When checked, it will dump all the original assembler shaders from the disk shader cache or game as found + + + Dump Game Shaders + + + + + + + true + + + When checked, it disables the macro HLE functions. Enabling this makes games run slower + + + Disable Macro HLE + + + + + + + true + + + When checked, it disables the macro Just In Time compiler. Enabling this makes games run slower + + + Disable Macro JIT + + + + + + + true + + + When checked, the graphics API enters a slower debugging mode + + + Enable Graphics Debugging + + + + + + + true + + + When checked, it will dump all the macro programs of the GPU + + + Dump Maxwell Macros + + + + + + + When checked, yuzu will log statistics about the compiled pipeline cache + + + Enable Shader Feedback + + + + + + + When checked, it enables Nsight Aftermath crash dumps + + + Enable Nsight Aftermath + + + + + + + Qt::Vertical + + + QSizePolicy::Preferred + + + + 20 + 0 + + + + + - - - - Enable FS Access Log + + + + Advanced + + + + + Enables yuzu to check for a working Vulkan environment when the program starts up. Disable this if this is causing issues with external programs seeing yuzu. + + + Perform Startup Vulkan Check + + + + + + + Disable Web Applet + + + + + + + Enable All Controller Types + + + + + + + Enable Auto-Stub** + + + + + + + Kiosk (Quest) Mode + + + + + + + Enable CPU Debugging + + + + + + + Enable Debug Asserts + + + + + + + Qt::Vertical + + + QSizePolicy::Expanding + + + + 20 + 0 + + + + + - - - - Enable this to output the latest generated audio command list to the console. Only affects games using the audio renderer. - - - Dump Audio Commands To Console** - - - - - - - Create Minidump After Crash + + + + Debugging + + + + + Enable FS Access Log + + + + + + + Create Minidump After Crash + + + + + + + Enable this to output the latest generated audio command list to the console. Only affects games using the audio renderer. + + + Dump Audio Commands To Console** + + + + + + + Enable Verbose Reporting Services** + + + + + + + Qt::Vertical + + + QSizePolicy::Expanding + + + + 20 + 0 + + + + + - - - - - - Advanced - - - - - - Kiosk (Quest) Mode - - - - - - - Enable CPU Debugging - - - - - - - Enable Debug Asserts - - - - - - - Enable Auto-Stub** - - - - - - - Enable All Controller Types - - - - - - - Disable Web Applet - - - - - - - Enables yuzu to check for a working Vulkan environment when the program starts up. Disable this if this is causing issues with external programs seeing yuzu. - - - Perform Startup Vulkan Check - - - - - - - - - - - true - - - - **This will be reset automatically when yuzu closes. - - - 20 - - - - - + + + + + Qt::Vertical + + + + 20 + 0 + + + + + + + + + 0 + 0 + + + + + true + + + + **This will be reset automatically when yuzu closes. + + + 20 + + + + + log_filter_edit @@ -366,14 +555,11 @@ enable_graphics_debugging enable_shader_feedback enable_nsight_aftermath - disable_macro_jit - disable_loop_safety_checks fs_access_log reporting_services quest_flag enable_cpu_debugging use_debug_asserts - use_auto_stub From 97674bc88821b202aa7309208b71f2ab042fc5aa Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 15:46:07 -0400 Subject: [PATCH 035/155] shared_widget: Support checkbox + spinbox --- src/yuzu/configuration/configure_graphics.cpp | 2 +- src/yuzu/configuration/shared_widget.cpp | 50 +++++++++++++++++-- src/yuzu/configuration/shared_widget.h | 13 +++-- 3 files changed, 55 insertions(+), 10 deletions(-) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 4c6d69703..5132c4796 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -240,7 +240,7 @@ void ConfigureGraphics::Setup() { return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::LineEdit, true, 1.0f, - Settings::values.speed_limit.ToString()); + &Settings::values.speed_limit, QString::fromStdString("%")); } else { return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index ba44d1973..841524b9c 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -6,6 +6,7 @@ #include #include #include +#include #include #include #include "common/settings.h" @@ -234,7 +235,8 @@ void Widget::CreateSlider(const QString& name, bool reversed, float multiplier, } } -void Widget::CreateCheckBoxWithLineEdit(const QString& label, const std::string& text_box_default, +void Widget::CreateCheckBoxWithLineEdit(const QString& label, + const Settings::BasicSetting* other_setting, std::function& load_func) { created = true; @@ -243,7 +245,7 @@ void Widget::CreateCheckBoxWithLineEdit(const QString& label, const std::string& QHBoxLayout* layout = reinterpret_cast(this->layout()); line_edit = new QLineEdit(this); - line_edit->setText(QString::fromStdString(text_box_default)); + line_edit->setText(QString::fromStdString(other_setting->ToString())); checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); @@ -254,7 +256,7 @@ void Widget::CreateCheckBoxWithLineEdit(const QString& label, const std::string& if (!Settings::IsConfiguringGlobal()) { QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { - line_edit->setText(QString::fromStdString(text_box_default)); + line_edit->setText(QString::fromStdString(other_setting->ToString())); }); QObject::connect(line_edit, &QLineEdit::textEdited, [=](const QString&) { @@ -264,6 +266,41 @@ void Widget::CreateCheckBoxWithLineEdit(const QString& label, const std::string& } } +void Widget::CreateCheckBoxWithSpinBox(const QString& label, + const Settings::BasicSetting* other_setting, + std::function& load_func, const QString& suffix) { + created = true; + + CreateCheckBox(label, load_func); + checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + + QHBoxLayout* layout = reinterpret_cast(this->layout()); + + spinbox = new QSpinBox(this); + const int min_val = std::stoi(other_setting->MinVal()); + const int max_val = std::stoi(other_setting->MaxVal()); + spinbox->setRange(min_val, max_val); + spinbox->setValue(std::stoi(other_setting->ToString())); + spinbox->setSuffix(suffix); + spinbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + + layout->insertWidget(1, spinbox); + + QObject::connect(spinbox, QOverload::of(&QSpinBox::valueChanged), + [this](int) { checkbox->setCheckState(Qt::Checked); }); + + if (!Settings::IsConfiguringGlobal()) { + QObject::connect(restore_button, &QAbstractButton::clicked, [this, other_setting](bool) { + spinbox->setValue(std::stoi(other_setting->ToString())); + }); + + QObject::connect(spinbox, QOverload::of(&QSpinBox::valueChanged), [this](int) { + restore_button->setEnabled(true); + restore_button->setVisible(true); + }); + } +} + bool Widget::Valid() { return created; } @@ -273,7 +310,8 @@ Widget::~Widget() = default; Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, QWidget* parent_, bool runtime_lock, std::forward_list>& apply_funcs, RequestType request, - bool managed, float multiplier, const std::string& text_box_default) + bool managed, float multiplier, const Settings::BasicSetting* other_setting, + const QString& format) : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_} { if (!Settings::IsConfiguringGlobal() && !setting.Switchable()) { LOG_DEBUG(Frontend, "\"{}\" is not switchable, skipping...", setting.GetLabel()); @@ -306,8 +344,10 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati CreateCheckBox(label, load_func); break; case RequestType::LineEdit: + CreateCheckBoxWithLineEdit(label, other_setting, load_func); + break; case RequestType::SpinBox: - CreateCheckBoxWithLineEdit(label, text_box_default, load_func); + CreateCheckBoxWithSpinBox(label, other_setting, load_func, format); break; case RequestType::ComboBox: case RequestType::Slider: diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 8d2d7f269..c25d819f0 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -4,6 +4,7 @@ #include "yuzu/configuration/shared_translation.h" class QPushButton; +class QSpinBox; class QComboBox; class QLineEdit; class QSlider; @@ -32,7 +33,8 @@ public: Widget(Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, bool runtime_lock, std::forward_list>& apply_funcs, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, - const std::string& text_box_default = ""); + const Settings::BasicSetting* other_setting = nullptr, + const QString& format = QStringLiteral("")); virtual ~Widget(); bool Valid(); @@ -42,16 +44,19 @@ public: QPushButton* restore_button{}; QLineEdit* line_edit{}; + QSpinBox* spinbox{}; QCheckBox* checkbox{}; QSlider* slider{}; QComboBox* combobox{}; private: void CreateCheckBox(const QString& label, std::function& load_func); - void CreateCheckBoxWithLineEdit(const QString& label, const std::string& text_box_default, + void CreateCheckBoxWithLineEdit(const QString& label, + const Settings::BasicSetting* other_setting, std::function& load_func); - void CreateCheckBoxWithSpinBox(const QString& label, const std::string& text_box_default, - std::function& load_func); + void CreateCheckBoxWithSpinBox(const QString& label, + const Settings::BasicSetting* other_setting, + std::function& load_func, const QString& suffix); void CreateCombobox(const QString& label, bool managed, std::function& load_func); void CreateLineEdit(const QString& label, bool managed, std::function& load_func); void CreateSlider(const QString& label, bool reversed, float multiplier, From df2bd251faa39b9f368110f0fb7f92f7eea4d8d2 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 15:46:23 -0400 Subject: [PATCH 036/155] graphics: Set speed limit to spinbox --- src/yuzu/configuration/configure_graphics.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 5132c4796..d1ec2bae3 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -239,8 +239,8 @@ void ConfigureGraphics::Setup() { } else if (setting->Id() == Settings::values.use_speed_limit.Id()) { return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::LineEdit, true, 1.0f, - &Settings::values.speed_limit, QString::fromStdString("%")); + ConfigurationShared::RequestType::SpinBox, true, 1.0f, + &Settings::values.speed_limit, QStringLiteral("%")); } else { return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); From cdb5dea26959001f9cf7448fcdb612475045a313 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 16:21:24 -0400 Subject: [PATCH 037/155] settings: Move runtime and save to parameters These don't need to be whole new types. --- src/common/settings.h | 148 ++++++++++-------- src/yuzu/configuration/configuration_shared.h | 9 +- 2 files changed, 89 insertions(+), 68 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index e60105059..fdadb06a1 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -222,7 +222,7 @@ public: * configurations. Specifying a default value and label is required. A minimum and maximum range * can be specified for sanitization. */ -template +template class Setting : public BasicSetting { protected: Setting() = default; @@ -245,10 +245,10 @@ public: * @param category_ Category of the setting AKA INI group */ explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, - enum Category category_) + enum Category category_, bool save_ = true, bool runtime_modifiable_ = false) requires(!ranged) - : value{default_val}, - default_value{default_val}, label{name}, category{category_}, id{linkage.count} { + : value{default_val}, default_value{default_val}, label{name}, category{category_}, + id{linkage.count}, save{save_}, runtime_modifiable{runtime_modifiable_} { linkage.by_category[category].push_front(this); linkage.count++; } @@ -265,10 +265,12 @@ public: * @param category_ Category of the setting AKA INI group */ explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, - const Type& max_val, const std::string& name, enum Category category_) + const Type& max_val, const std::string& name, enum Category category_, + bool save_ = true, bool runtime_modifiable_ = false) requires(ranged) : value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val}, - label{name}, category{category_}, id{linkage.count} { + label{name}, category{category_}, id{linkage.count}, save{save_}, + runtime_modifiable{runtime_modifiable_} { linkage.by_category[category].push_front(this); linkage.count++; } @@ -455,6 +457,8 @@ protected: const std::string label{}; ///< The setting's label const enum Category category; ///< The setting's category AKA INI group const u32 id; + bool save; + bool runtime_modifiable; }; /** @@ -465,8 +469,8 @@ protected: * * By default, the global setting is used. */ -template -class SwitchableSetting : virtual public Setting { +template +class SwitchableSetting : virtual public Setting { public: /** * Sets a default value, label, and setting value. @@ -477,9 +481,9 @@ public: * @param category_ Category of the setting AKA INI group */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, - Category category) + Category category, bool save = true, bool runtime_modifiable = false) requires(!ranged) - : Setting{linkage, default_val, name, category} { + : Setting{linkage, default_val, name, category, save, runtime_modifiable} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } virtual ~SwitchableSetting() = default; @@ -495,10 +499,11 @@ public: * @param category_ Category of the setting AKA INI group */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, - const Type& max_val, const std::string& name, Category category) + const Type& max_val, const std::string& name, Category category, + bool save = true, bool runtime_modifiable = false) requires(ranged) - : Setting{linkage, default_val, min_val, - max_val, name, category} { + : Setting{linkage, default_val, min_val, max_val, + name, category, save, runtime_modifiable} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } @@ -642,10 +647,10 @@ struct Values { Setting sink_id{linkage, "auto", "output_engine", Category::Audio}; Setting audio_output_device_id{linkage, "auto", "output_device", Category::Audio}; Setting audio_input_device_id{linkage, "auto", "input_device", Category::Audio}; - Setting audio_muted{linkage, false, "audio_muted", Category::Audio}; + Setting audio_muted{linkage, false, "audio_muted", Category::Audio, false}; SwitchableSetting volume{linkage, 100, 0, 200, "volume", Category::Audio}; - Setting dump_audio_commands{linkage, false, "dump_audio_commands", - Category::Audio}; + Setting dump_audio_commands{linkage, false, "dump_audio_commands", Category::Audio, + false}; // Core SwitchableSetting use_multi_core{linkage, true, "use_multi_core", Category::Core}; @@ -713,38 +718,51 @@ struct Values { ResolutionScalingInfo resolution_info{}; SwitchableSetting resolution_setup{linkage, ResolutionSetup::Res1X, "resolution_setup", Category::Renderer}; - SwitchableSetting scaling_filter{ - linkage, ScalingFilter::Bilinear, "scaling_filter", Category::Renderer}; - SwitchableSetting fsr_sharpening_slider{ - linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer}; - SwitchableSetting anti_aliasing{ - linkage, AntiAliasing::None, "anti_aliasing", Category::Renderer}; + SwitchableSetting scaling_filter{ + linkage, ScalingFilter::Bilinear, "scaling_filter", Category::Renderer, true, true}; + SwitchableSetting fsr_sharpening_slider{ + linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer, true, true}; + SwitchableSetting anti_aliasing{ + linkage, AntiAliasing::None, "anti_aliasing", Category::Renderer, true, true}; // *nix platforms may have issues with the borderless windowed fullscreen mode. // Default to exclusive fullscreen on these platforms for now. - SwitchableSetting fullscreen_mode{linkage, + SwitchableSetting fullscreen_mode{linkage, #ifdef _WIN32 - FullscreenMode::Borderless, + FullscreenMode::Borderless, #else - FullscreenMode::Exclusive, + FullscreenMode::Exclusive, #endif - FullscreenMode::Borderless, - FullscreenMode::Exclusive, - "fullscreen_mode", - Category::Renderer}; - SwitchableSetting aspect_ratio{ - linkage, 0, 0, 4, "aspect_ratio", Category::Renderer}; + FullscreenMode::Borderless, + FullscreenMode::Exclusive, + "fullscreen_mode", + Category::Renderer, + true, + true}; + SwitchableSetting aspect_ratio{linkage, + AspectRatio::R16_9, + AspectRatio::R16_9, + AspectRatio::Stretch, + "aspect_ratio", + Category::Renderer, + true, + true}; SwitchableSetting max_anisotropy{ linkage, AnisotropyMode::Automatic, AnisotropyMode::Automatic, AnisotropyMode::X16, "max_anisotropy", Category::RendererAdvanced}; - SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", - Category::Renderer}; - SwitchableSetting speed_limit{ - linkage, 100, 0, 9999, "speed_limit", Category::Renderer}; + SwitchableSetting use_speed_limit{ + linkage, true, "use_speed_limit", Category::Renderer, false, true}; + SwitchableSetting speed_limit{ + linkage, 100, 0, 9999, "speed_limit", Category::Renderer, true, true}; SwitchableSetting use_disk_shader_cache{linkage, true, "use_disk_shader_cache", Category::Renderer}; - SwitchableSetting gpu_accuracy{ - linkage, GPUAccuracy::High, GPUAccuracy::Normal, GPUAccuracy::Extreme, - "gpu_accuracy", Category::RendererAdvanced}; + SwitchableSetting gpu_accuracy{linkage, + GPUAccuracy::High, + GPUAccuracy::Normal, + GPUAccuracy::Extreme, + "gpu_accuracy", + Category::RendererAdvanced, + true, + true}; SwitchableSetting use_asynchronous_gpu_emulation{ linkage, true, "use_asynchronous_gpu_emulation", Category::Renderer}; SwitchableSetting nvdec_emulation{linkage, NvdecEmulation::GPU, @@ -755,9 +773,14 @@ struct Values { AstcDecodeMode::CPUAsynchronous, "accelerate_astc", Category::Renderer}; - Setting vsync_mode{ - linkage, VSyncMode::FIFO, VSyncMode::Immediate, VSyncMode::FIFORelaxed, - "use_vsync", Category::Renderer}; + Setting vsync_mode{linkage, + VSyncMode::FIFO, + VSyncMode::Immediate, + VSyncMode::FIFORelaxed, + "use_vsync", + Category::Renderer, + true, + true}; SwitchableSetting use_reactive_flushing{linkage, true, "use_reactive_flushing", Category::RendererAdvanced}; SwitchableSetting shader_backend{ @@ -765,10 +788,10 @@ struct Values { "shader_backend", Category::Renderer}; SwitchableSetting use_asynchronous_shaders{linkage, false, "use_asynchronous_shaders", Category::RendererAdvanced}; - SwitchableSetting use_fast_gpu_time{linkage, true, "use_fast_gpu_time", - Category::RendererAdvanced}; - SwitchableSetting use_vulkan_driver_pipeline_cache{ - linkage, true, "use_vulkan_driver_pipeline_cache", Category::RendererAdvanced}; + SwitchableSetting use_fast_gpu_time{ + linkage, true, "use_fast_gpu_time", Category::RendererAdvanced, true, true}; + SwitchableSetting use_vulkan_driver_pipeline_cache{ + linkage, true, "use_vulkan_driver_pipeline_cache", Category::RendererAdvanced, true, true}; SwitchableSetting enable_compute_pipelines{linkage, false, "enable_compute_pipelines", Category::RendererAdvanced}; SwitchableSetting astc_recompression{linkage, @@ -782,9 +805,9 @@ struct Values { SwitchableSetting barrier_feedback_loops{linkage, true, "barrier_feedback_loops", Category::RendererAdvanced}; - SwitchableSetting bg_red{linkage, 0, "bg_red", Category::Renderer}; - SwitchableSetting bg_green{linkage, 0, "bg_green", Category::Renderer}; - SwitchableSetting bg_blue{linkage, 0, "bg_blue", Category::Renderer}; + SwitchableSetting bg_red{linkage, 0, "bg_red", Category::Renderer, true, true}; + SwitchableSetting bg_green{linkage, 0, "bg_green", Category::Renderer, true, true}; + SwitchableSetting bg_blue{linkage, 0, "bg_blue", Category::Renderer, true, true}; // System SwitchableSetting rng_seed_enabled{linkage, false, "rng_seed_enabled", Category::System}; @@ -809,15 +832,14 @@ struct Values { // Controls InputSetting> players; - Setting enable_raw_input{linkage, false, "enable_raw_input", Category::Controls, // Only read/write enable_raw_input on Windows platforms #ifdef _WIN32 - true + true #else - false + false #endif - > - enable_raw_input{linkage, false, "enable_raw_input", Category::Controls}; + }; Setting controller_navigation{linkage, true, "controller_navigation", Category::Controls}; Setting enable_joycon_driver{linkage, true, "enable_joycon_driver", Category::Controls}; Setting enable_procon_driver{linkage, false, "enable_procon_driver", Category::Controls}; @@ -837,7 +859,7 @@ struct Values { Setting tas_enable{linkage, false, "tas_enable", Category::Controls}; Setting tas_loop{linkage, false, "tas_loop", Category::Controls}; - Setting mouse_panning{linkage, false, "mouse_panning", Category::Controls}; + Setting mouse_panning{linkage, false, "mouse_panning", Category::Controls, false}; Setting mouse_panning_sensitivity{ linkage, 50, 1, 100, "mouse_panning_sensitivity", Category::Controls}; Setting mouse_enabled{linkage, false, "mouse_enabled", Category::Controls}; @@ -893,22 +915,22 @@ struct Values { Setting program_args{linkage, std::string(), "program_args", Category::Debugging}; Setting dump_exefs{linkage, false, "dump_exefs", Category::Debugging}; Setting dump_nso{linkage, false, "dump_nso", Category::Debugging}; - Setting dump_shaders{linkage, false, "dump_shaders", - Category::DebuggingGraphics}; - Setting dump_macros{linkage, false, "dump_macros", - Category::DebuggingGraphics}; + Setting dump_shaders{linkage, false, "dump_shaders", Category::DebuggingGraphics, + false}; + Setting dump_macros{linkage, false, "dump_macros", Category::DebuggingGraphics, + false}; Setting enable_fs_access_log{linkage, false, "enable_fs_access_log", Category::Debugging}; - Setting reporting_services{linkage, false, "reporting_services", - Category::Debugging}; + Setting reporting_services{linkage, false, "reporting_services", + Category::Debugging, false}; Setting quest_flag{linkage, false, "quest_flag", Category::Debugging}; Setting disable_macro_jit{linkage, false, "disable_macro_jit", Category::DebuggingGraphics}; Setting disable_macro_hle{linkage, false, "disable_macro_hle", Category::DebuggingGraphics}; - Setting extended_logging{linkage, false, "extended_logging", - Category::Debugging}; + Setting extended_logging{linkage, false, "extended_logging", Category::Debugging, + false}; Setting use_debug_asserts{linkage, false, "use_debug_asserts", Category::Debugging}; - Setting use_auto_stub{linkage, false, "use_auto_stub", Category::Debugging}; + Setting use_auto_stub{linkage, false, "use_auto_stub", Category::Debugging, false}; Setting enable_all_controllers{linkage, false, "enable_all_controllers", Category::Debugging}; Setting create_crash_dumps{linkage, false, "create_crash_dumps", Category::Debugging}; diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 0a0a92ae5..83a0dd574 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -77,11 +77,10 @@ void SetPerGameSetting(QComboBox* combobox, void SetHighlight(QWidget* widget, bool highlighted); // Sets up a QCheckBox like a tristate one, given a Setting -template -void SetColoredTristate( - QCheckBox* checkbox, - const Settings::SwitchableSetting& setting, - CheckState& tracker) { +template +void SetColoredTristate(QCheckBox* checkbox, + const Settings::SwitchableSetting& setting, + CheckState& tracker) { if (setting.UsingGlobal()) { tracker = CheckState::Global; } else { From b11a2a206fa2945c954f0b432937bfd468c43fea Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 16:36:09 -0400 Subject: [PATCH 038/155] shared_widget: Internalize extra setting configuration --- src/yuzu/configuration/configure_graphics.cpp | 19 ---- src/yuzu/configuration/shared_widget.cpp | 87 ++++++++++++++----- src/yuzu/configuration/shared_widget.h | 8 +- 3 files changed, 66 insertions(+), 48 deletions(-) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index d1ec2bae3..ae3cf269f 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -273,25 +273,6 @@ void ConfigureGraphics::Setup() { hold_api.push_front(widget); shader_backend_combobox = widget->combobox; shader_backend_widget = widget; - } else if (setting->Id() == Settings::values.use_speed_limit.Id()) { - apply_funcs.push_front([setting, widget](bool powered_on) { - if (!setting->RuntimeModfiable() && powered_on) { - return; - } - - u16 value = QVariant(widget->line_edit->text()).value(); - auto& speed_limit = Settings::values.speed_limit; - if (Settings::IsConfiguringGlobal()) { - speed_limit.SetValue(value); - } else { - bool using_global = !widget->restore_button->isVisible(); - speed_limit.SetGlobal(using_global); - if (!using_global) { - speed_limit.SetValue(value); - } - } - }); - hold_graphics[setting->IsEnum()][setting_label] = widget; } else if (setting->Id() == Settings::values.vsync_mode.Id()) { vsync_mode_combobox = widget->combobox; hold_graphics[setting->IsEnum()][setting_label] = widget; diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 841524b9c..d1113f793 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -9,12 +9,18 @@ #include #include #include +#include "common/common_types.h" #include "common/settings.h" +#include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/shared_translation.h" #include "yuzu/configuration/shared_widget.h" namespace ConfigurationShared { +static bool IsInt(const std::type_index& type) { + return type == typeid(u32) || type == typeid(s32) || type == typeid(u16) || type == typeid(s16); +} + QPushButton* Widget::CreateRestoreGlobalButton(Settings::BasicSetting& setting, QWidget* parent) { QStyle* style = parent->style(); QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_DialogResetButton)); @@ -235,43 +241,63 @@ void Widget::CreateSlider(const QString& name, bool reversed, float multiplier, } } -void Widget::CreateCheckBoxWithLineEdit(const QString& label, - const Settings::BasicSetting* other_setting, +void Widget::CreateCheckBoxWithLineEdit(const QString& label, Settings::BasicSetting* other_setting, std::function& load_func) { + if (other_setting == nullptr) { + LOG_WARNING(Frontend, "Extra setting is null or not an integer"); + return; + } created = true; - CreateCheckBox(label, load_func); + std::function checkbox_load_func; + CreateCheckBox(label, checkbox_load_func); QHBoxLayout* layout = reinterpret_cast(this->layout()); + const QString default_val = QString::fromStdString(other_setting->ToString()); line_edit = new QLineEdit(this); - line_edit->setText(QString::fromStdString(other_setting->ToString())); + line_edit->setText(default_val); checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->insertWidget(1, line_edit); - QObject::connect(line_edit, &QLineEdit::textEdited, - [=](const QString&) { checkbox->setCheckState(Qt::Checked); }); - - if (!Settings::IsConfiguringGlobal()) { - QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { - line_edit->setText(QString::fromStdString(other_setting->ToString())); - }); + if (Settings::IsConfiguringGlobal()) { + load_func = [=]() { + checkbox_load_func(); + other_setting->LoadString(line_edit->text().toStdString()); + }; + } else { + QObject::connect(restore_button, &QAbstractButton::clicked, + [=](bool) { line_edit->setText(default_val); }); QObject::connect(line_edit, &QLineEdit::textEdited, [=](const QString&) { restore_button->setEnabled(true); restore_button->setVisible(true); }); + + load_func = [=]() { + checkbox_load_func(); + + const bool using_global = !restore_button->isVisible(); + other_setting->SetGlobal(using_global); + if (!using_global) { + other_setting->LoadString(line_edit->text().toStdString()); + } + }; } } -void Widget::CreateCheckBoxWithSpinBox(const QString& label, - const Settings::BasicSetting* other_setting, +void Widget::CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSetting* other_setting, std::function& load_func, const QString& suffix) { + if (other_setting == nullptr && IsInt(other_setting->TypeId())) { + LOG_WARNING(Frontend, "Extra setting is null or not an integer"); + return; + } created = true; - CreateCheckBox(label, load_func); + std::function checkbox_load_func; + CreateCheckBox(label, checkbox_load_func); checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); QHBoxLayout* layout = reinterpret_cast(this->layout()); @@ -279,17 +305,20 @@ void Widget::CreateCheckBoxWithSpinBox(const QString& label, spinbox = new QSpinBox(this); const int min_val = std::stoi(other_setting->MinVal()); const int max_val = std::stoi(other_setting->MaxVal()); + const int default_val = std::stoi(other_setting->ToString()); spinbox->setRange(min_val, max_val); - spinbox->setValue(std::stoi(other_setting->ToString())); + spinbox->setValue(default_val); spinbox->setSuffix(suffix); spinbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->insertWidget(1, spinbox); - QObject::connect(spinbox, QOverload::of(&QSpinBox::valueChanged), - [this](int) { checkbox->setCheckState(Qt::Checked); }); - - if (!Settings::IsConfiguringGlobal()) { + if (Settings::IsConfiguringGlobal()) { + load_func = [=]() { + checkbox_load_func(); + other_setting->LoadString(std::to_string(spinbox->value())); + }; + } else { QObject::connect(restore_button, &QAbstractButton::clicked, [this, other_setting](bool) { spinbox->setValue(std::stoi(other_setting->ToString())); }); @@ -298,6 +327,16 @@ void Widget::CreateCheckBoxWithSpinBox(const QString& label, restore_button->setEnabled(true); restore_button->setVisible(true); }); + + load_func = [=]() { + checkbox_load_func(); + + const bool using_global = !restore_button->isVisible(); + other_setting->SetGlobal(using_global); + if (!using_global) { + other_setting->LoadString(std::to_string(spinbox->value())); + } + }; } } @@ -310,7 +349,7 @@ Widget::~Widget() = default; Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, QWidget* parent_, bool runtime_lock, std::forward_list>& apply_funcs, RequestType request, - bool managed, float multiplier, const Settings::BasicSetting* other_setting, + bool managed, float multiplier, Settings::BasicSetting* other_setting, const QString& format) : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_} { if (!Settings::IsConfiguringGlobal() && !setting.Switchable()) { @@ -340,15 +379,15 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati if (type == typeid(bool)) { switch (request) { + case RequestType::SpinBox: + CreateCheckBoxWithSpinBox(label, other_setting, load_func, format); + break; case RequestType::Default: CreateCheckBox(label, load_func); break; case RequestType::LineEdit: CreateCheckBoxWithLineEdit(label, other_setting, load_func); break; - case RequestType::SpinBox: - CreateCheckBoxWithSpinBox(label, other_setting, load_func, format); - break; case RequestType::ComboBox: case RequestType::Slider: case RequestType::ReverseSlider: @@ -377,7 +416,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati } if (!created) { - LOG_ERROR(Frontend, "No widget was created for \"{}\"", setting.GetLabel()); + LOG_WARNING(Frontend, "No widget was created for \"{}\"", setting.GetLabel()); return; } diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index c25d819f0..88a864b42 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -33,7 +33,7 @@ public: Widget(Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, bool runtime_lock, std::forward_list>& apply_funcs, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, - const Settings::BasicSetting* other_setting = nullptr, + Settings::BasicSetting* other_setting = nullptr, const QString& format = QStringLiteral("")); virtual ~Widget(); @@ -51,11 +51,9 @@ public: private: void CreateCheckBox(const QString& label, std::function& load_func); - void CreateCheckBoxWithLineEdit(const QString& label, - const Settings::BasicSetting* other_setting, + void CreateCheckBoxWithLineEdit(const QString& label, Settings::BasicSetting* other_setting, std::function& load_func); - void CreateCheckBoxWithSpinBox(const QString& label, - const Settings::BasicSetting* other_setting, + void CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSetting* other_setting, std::function& load_func, const QString& suffix); void CreateCombobox(const QString& label, bool managed, std::function& load_func); void CreateLineEdit(const QString& label, bool managed, std::function& load_func); From 56960bf9f8ff6987fe265d98fe60852d9b7b05b4 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 9 May 2023 17:05:08 -0400 Subject: [PATCH 039/155] per_game: Remove general tab It's empty. --- src/yuzu/configuration/configure_per_game.cpp | 3 --- src/yuzu/configuration/configure_per_game.h | 2 -- 2 files changed, 5 deletions(-) diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index 05da9bda0..5548fc2ba 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -27,7 +27,6 @@ #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_audio.h" #include "yuzu/configuration/configure_cpu.h" -#include "yuzu/configuration/configure_general.h" #include "yuzu/configuration/configure_graphics.h" #include "yuzu/configuration/configure_graphics_advanced.h" #include "yuzu/configuration/configure_input_per_game.h" @@ -53,7 +52,6 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st addons_tab = std::make_unique(system_, this); audio_tab = std::make_unique(system_, tab_group, this); cpu_tab = std::make_unique(system_, tab_group, this); - general_tab = std::make_unique(system_, tab_group, *translations, this); graphics_advanced_tab = std::make_unique(system_, tab_group, *translations, this); graphics_tab = std::make_unique( @@ -65,7 +63,6 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st ui->setupUi(this); ui->tabWidget->addTab(addons_tab.get(), tr("Add-Ons")); - ui->tabWidget->addTab(general_tab.get(), tr("General")); ui->tabWidget->addTab(system_tab.get(), tr("System")); ui->tabWidget->addTab(cpu_tab.get(), tr("CPU")); ui->tabWidget->addTab(graphics_tab.get(), tr("Graphics")); diff --git a/src/yuzu/configuration/configure_per_game.h b/src/yuzu/configuration/configure_per_game.h index 1e222c2f9..32217c1f1 100644 --- a/src/yuzu/configuration/configure_per_game.h +++ b/src/yuzu/configuration/configure_per_game.h @@ -27,7 +27,6 @@ class InputSubsystem; class ConfigurePerGameAddons; class ConfigureAudio; class ConfigureCpu; -class ConfigureGeneral; class ConfigureGraphics; class ConfigureGraphicsAdvanced; class ConfigureInputPerGame; @@ -81,7 +80,6 @@ private: std::unique_ptr addons_tab; std::unique_ptr audio_tab; std::unique_ptr cpu_tab; - std::unique_ptr general_tab; std::unique_ptr graphics_advanced_tab; std::unique_ptr graphics_tab; std::unique_ptr input_tab; From 8e151460265f04c7bf4a981b5f97f252a0444c27 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 10 May 2023 17:57:25 -0400 Subject: [PATCH 040/155] configure_system: Implement with for loop --- src/common/settings.cpp | 1 + src/common/settings.h | 114 +++- src/core/core.cpp | 20 +- src/core/file_sys/control_metadata.cpp | 3 +- src/core/file_sys/patch_manager.cpp | 4 +- src/core/hle/service/ns/ns.cpp | 2 +- src/core/hle/service/set/set.cpp | 10 +- src/yuzu/configuration/config.cpp | 2 + src/yuzu/configuration/configure_dialog.cpp | 2 +- src/yuzu/configuration/configure_graphics.cpp | 2 +- src/yuzu/configuration/configure_per_game.cpp | 2 +- src/yuzu/configuration/configure_system.cpp | 244 ++++----- src/yuzu/configuration/configure_system.h | 17 +- src/yuzu/configuration/configure_system.ui | 509 ++---------------- src/yuzu/configuration/shared_translation.cpp | 43 +- src/yuzu/configuration/shared_widget.cpp | 179 +++++- src/yuzu/configuration/shared_widget.h | 13 +- src/yuzu_cmd/config.cpp | 1 + 18 files changed, 514 insertions(+), 654 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index b7a0c063f..605fe7f86 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -162,6 +162,7 @@ const char* TranslateCategory(Category category) { case Category::RendererDebug: return "Renderer"; case Category::System: + case Category::SystemAudio: return "System"; case Category::DataStorage: return "Data Storage"; diff --git a/src/common/settings.h b/src/common/settings.h index fdadb06a1..1f95bd7d5 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -20,6 +20,86 @@ namespace Settings { +enum class Language : u32 { + Japanese, + EnglishAmerican, + French, + German, + Italian, + Spanish, + Chinese, + Korean, + Dutch, + Portuguese, + Russian, + Taiwanese, + EnglishBritish, + FrenchCanadian, + SpanishLatin, + ChineseSimplified, + ChineseTraditional, + PortugueseBrazilian, +}; + +enum class Region : u32 { + Japan, + USA, + Europe, + Australia, + China, + Korea, + Taiwan, +}; + +enum class TimeZone : u32 { + Auto, + Default, + CET, + CST6CDT, + Cuba, + EET, + Egypt, + Eire, + EST, + EST5EDT, + GB, + GBEire, + GMT, + GMTPlusZero, + GMTMinusZero, + GMTZero, + Greenwich, + Hongkong, + HST, + Iceland, + Iran, + Israel, + Jamaica, + Japan, + Kwajalein, + Libya, + MET, + MST, + MST7MDT, + Navajo, + NZ, + NZCHAT, + Poland, + Portugal, + PRC, + PST8PDT, + ROC, + ROK, + Singapore, + Turkey, + UCT, + Universal, + UTC, + W_SU, + WET, + Zulu, +}; + enum class AnisotropyMode : u32 { Automatic = 0, Default = 1, @@ -134,6 +214,7 @@ enum class Category : u32 { RendererAdvanced, RendererDebug, System, + SystemAudio, DataStorage, Debugging, DebuggingGraphics, @@ -810,22 +891,31 @@ struct Values { SwitchableSetting bg_blue{linkage, 0, "bg_blue", Category::Renderer, true, true}; // System - SwitchableSetting rng_seed_enabled{linkage, false, "rng_seed_enabled", Category::System}; - SwitchableSetting rng_seed{linkage, 0, "rng_seed", Category::System}; - Setting device_name{linkage, "Yuzu", "device_name", Category::System}; + SwitchableSetting rng_seed_enabled{linkage, false, "rng_seed_enabled", + Category::System, true, true}; + SwitchableSetting rng_seed{linkage, 0, "rng_seed", Category::System, true, true}; + Setting device_name{linkage, "Yuzu", "device_name", Category::System, true, true}; // Measured in seconds since epoch - Setting custom_rtc_enabled{linkage, false, "custom_rtc_enabled", Category::System}; - Setting custom_rtc{linkage, 0, "custom_rtc", Category::System}; + SwitchableSetting custom_rtc_enabled{linkage, false, "custom_rtc_enabled", + Category::System, true, true}; + SwitchableSetting custom_rtc{linkage, 0, "custom_rtc", Category::System, true, true}; // Set on game boot, reset on stop. Seconds difference between current time and `custom_rtc` s64 custom_rtc_differential; Setting current_user{linkage, 0, "current_user", Category::System}; - SwitchableSetting language_index{linkage, 1, 0, 17, "language_index", - Category::System}; - SwitchableSetting region_index{linkage, 1, 0, 6, "region_index", Category::System}; - SwitchableSetting time_zone_index{linkage, 0, 0, 45, "time_zone_index", - Category::System}; - SwitchableSetting sound_index{linkage, 1, 0, 2, "sound_index", Category::System}; + SwitchableSetting language_index{linkage, + Language::EnglishAmerican, + Language::Japanese, + Language::PortugueseBrazilian, + "language_index", + Category::System}; + SwitchableSetting region_index{linkage, Region::USA, Region::Japan, + Region::Taiwan, "region_index", Category::System}; + SwitchableSetting time_zone_index{linkage, TimeZone::Auto, + TimeZone::Auto, TimeZone::Zulu, + "time_zone_index", Category::System}; + SwitchableSetting sound_index{ + linkage, 1, 0, 2, "sound_index", Category::SystemAudio}; SwitchableSetting use_docked_mode{linkage, true, "use_docked_mode", Category::System}; @@ -837,7 +927,7 @@ struct Values { #ifdef _WIN32 true #else - false + false #endif }; Setting controller_navigation{linkage, true, "controller_navigation", Category::Controls}; diff --git a/src/core/core.cpp b/src/core/core.cpp index da1baa892..e2902a91f 100644 --- a/src/core/core.cpp +++ b/src/core/core.cpp @@ -145,13 +145,7 @@ struct System::Impl { core_timing.SetMulticore(is_multicore); core_timing.Initialize([&system]() { system.RegisterHostThread(); }); - const auto posix_time = std::chrono::system_clock::now().time_since_epoch(); - const auto current_time = - std::chrono::duration_cast(posix_time).count(); - Settings::values.custom_rtc_differential = - (Settings::values.custom_rtc_enabled ? Settings::values.custom_rtc.GetValue() - : current_time) - - current_time; + RefreshTime(); // Create a default fs if one doesn't already exist. if (virtual_filesystem == nullptr) { @@ -188,6 +182,16 @@ struct System::Impl { Initialize(system); } + void RefreshTime() { + const auto posix_time = std::chrono::system_clock::now().time_since_epoch(); + const auto current_time = + std::chrono::duration_cast(posix_time).count(); + Settings::values.custom_rtc_differential = + (Settings::values.custom_rtc_enabled ? Settings::values.custom_rtc.GetValue() + : current_time) - + current_time; + } + void Run() { std::unique_lock lk(suspend_guard); @@ -1022,6 +1026,8 @@ void System::Exit() { } void System::ApplySettings() { + impl->RefreshTime(); + if (IsPoweredOn()) { Renderer().RefreshBaseSettings(); } diff --git a/src/core/file_sys/control_metadata.cpp b/src/core/file_sys/control_metadata.cpp index cd9ac2e75..0697c29ae 100644 --- a/src/core/file_sys/control_metadata.cpp +++ b/src/core/file_sys/control_metadata.cpp @@ -68,7 +68,8 @@ NACP::NACP(VirtualFile file) { NACP::~NACP() = default; const LanguageEntry& NACP::GetLanguageEntry() const { - Language language = language_to_codes[Settings::values.language_index.GetValue()]; + Language language = + language_to_codes[static_cast(Settings::values.language_index.GetValue())]; { const auto& language_entry = raw.language_entries.at(static_cast(language)); diff --git a/src/core/file_sys/patch_manager.cpp b/src/core/file_sys/patch_manager.cpp index d3286b352..2ba1b34a4 100644 --- a/src/core/file_sys/patch_manager.cpp +++ b/src/core/file_sys/patch_manager.cpp @@ -626,8 +626,8 @@ PatchManager::Metadata PatchManager::ParseControlNCA(const NCA& nca) const { auto nacp = nacp_file == nullptr ? nullptr : std::make_unique(nacp_file); // Get language code from settings - const auto language_code = - Service::Set::GetLanguageCodeFromIndex(Settings::values.language_index.GetValue()); + const auto language_code = Service::Set::GetLanguageCodeFromIndex( + static_cast(Settings::values.language_index.GetValue())); // Convert to application language and get priority list const auto application_language = diff --git a/src/core/hle/service/ns/ns.cpp b/src/core/hle/service/ns/ns.cpp index 376067a95..91c5a2182 100644 --- a/src/core/hle/service/ns/ns.cpp +++ b/src/core/hle/service/ns/ns.cpp @@ -409,7 +409,7 @@ ResultVal IApplicationManagerInterface::GetApplicationDesiredLanguage( // Get language code from settings const auto language_code = - Set::GetLanguageCodeFromIndex(Settings::values.language_index.GetValue()); + Set::GetLanguageCodeFromIndex(static_cast(Settings::values.language_index.GetValue())); // Convert to application language, get priority list const auto application_language = ConvertToApplicationLanguage(language_code); diff --git a/src/core/hle/service/set/set.cpp b/src/core/hle/service/set/set.cpp index f5788b481..83f888c54 100644 --- a/src/core/hle/service/set/set.cpp +++ b/src/core/hle/service/set/set.cpp @@ -93,7 +93,8 @@ void GetAvailableLanguageCodesImpl(HLERequestContext& ctx, std::size_t max_entri } void GetKeyCodeMapImpl(HLERequestContext& ctx) { - const auto language_code = available_language_codes[Settings::values.language_index.GetValue()]; + const auto language_code = + available_language_codes[static_cast(Settings::values.language_index.GetValue())]; const auto key_code = std::find_if(language_to_layout.cbegin(), language_to_layout.cend(), [=](const auto& element) { return element.first == language_code; }); @@ -162,7 +163,7 @@ void SET::GetQuestFlag(HLERequestContext& ctx) { IPC::ResponseBuilder rb{ctx, 3}; rb.Push(ResultSuccess); - rb.Push(static_cast(Settings::values.quest_flag.GetValue())); + rb.Push(static_cast(Settings::values.quest_flag.GetValue())); } void SET::GetLanguageCode(HLERequestContext& ctx) { @@ -170,7 +171,8 @@ void SET::GetLanguageCode(HLERequestContext& ctx) { IPC::ResponseBuilder rb{ctx, 4}; rb.Push(ResultSuccess); - rb.PushEnum(available_language_codes[Settings::values.language_index.GetValue()]); + rb.PushEnum( + available_language_codes[static_cast(Settings::values.language_index.GetValue())]); } void SET::GetRegionCode(HLERequestContext& ctx) { @@ -178,7 +180,7 @@ void SET::GetRegionCode(HLERequestContext& ctx) { IPC::ResponseBuilder rb{ctx, 3}; rb.Push(ResultSuccess); - rb.Push(Settings::values.region_index.GetValue()); + rb.Push(static_cast(Settings::values.region_index.GetValue())); } void SET::GetKeyCodeMap(HLERequestContext& ctx) { diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 3181a9528..28ee5d492 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -696,6 +696,7 @@ void Config::ReadSystemValues() { qt_config->beginGroup(QStringLiteral("System")); ReadCategory(Settings::Category::System); + ReadCategory(Settings::Category::SystemAudio); qt_config->endGroup(); } @@ -1134,6 +1135,7 @@ void Config::SaveSystemValues() { qt_config->beginGroup(QStringLiteral("System")); WriteCategory(Settings::Category::System); + WriteCategory(Settings::Category::SystemAudio); qt_config->endGroup(); } diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index 8baa8de1e..3a94fee9e 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -48,7 +48,7 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, input_tab{std::make_unique(system_, this)}, network_tab{std::make_unique(system_, this)}, profile_tab{std::make_unique(system_, this)}, - system_tab{std::make_unique(system_, nullptr, this)}, + system_tab{std::make_unique(system_, nullptr, *translations, this)}, ui_tab{std::make_unique(system_, this)}, web_tab{std::make_unique( this)} { Settings::SetConfiguringGlobal(true); diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index ae3cf269f..977aed42d 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -240,7 +240,7 @@ void ConfigureGraphics::Setup() { return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::SpinBox, true, 1.0f, - &Settings::values.speed_limit, QStringLiteral("%")); + &Settings::values.speed_limit, "%"); } else { return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index 5548fc2ba..c39855334 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -58,7 +58,7 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, tab_group, *translations, this); input_tab = std::make_unique(system_, game_config.get(), this); - system_tab = std::make_unique(system_, tab_group, this); + system_tab = std::make_unique(system_, tab_group, *translations, this); ui->setupUi(this); diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 4872a475b..dedbad57f 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -2,17 +2,22 @@ // SPDX-License-Identifier: GPL-2.0-or-later #include +#include #include +#include #include #include +#include #include #include "common/settings.h" #include "core/core.h" #include "core/hle/service/time/time_manager.h" #include "ui_configure_system.h" +#include "yuzu/configuration/config.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_system.h" +#include "yuzu/configuration/shared_widget.h" constexpr std::array LOCALE_BLOCKLIST{ // pzzefezrpnkzeidfej @@ -39,44 +44,42 @@ static bool IsValidLocale(u32 region_index, u32 language_index) { ConfigureSystem::ConfigureSystem( Core::System& system_, std::shared_ptr> group, - QWidget* parent) - : Tab(group, parent), ui{std::make_unique()}, system{system_} { + ConfigurationShared::TranslationMap& translations_, QWidget* parent) + : Tab(group, parent), ui{std::make_unique()}, system{system_}, + translations{translations_} { ui->setupUi(this); - connect(ui->rng_seed_checkbox, &QCheckBox::stateChanged, this, [this](int state) { - ui->rng_seed_edit->setEnabled(state == Qt::Checked); + Setup(); + + connect(rng_seed_checkbox, &QCheckBox::stateChanged, this, [this](int state) { + rng_seed_edit->setEnabled(state == Qt::Checked); if (state != Qt::Checked) { - ui->rng_seed_edit->setText(QStringLiteral("00000000")); + rng_seed_edit->setText(QStringLiteral("00000000")); } }); - connect(ui->custom_rtc_checkbox, &QCheckBox::stateChanged, this, [this](int state) { - ui->custom_rtc_edit->setEnabled(state == Qt::Checked); + connect(custom_rtc_checkbox, &QCheckBox::stateChanged, this, [this](int state) { + custom_rtc_edit->setEnabled(state == Qt::Checked); if (state != Qt::Checked) { - ui->custom_rtc_edit->setDateTime(QDateTime::currentDateTime()); + custom_rtc_edit->setDateTime(QDateTime::currentDateTime()); } }); const auto locale_check = [this](int index) { - const auto region_index = ConfigurationShared::GetComboboxIndex( - Settings::values.region_index.GetValue(true), ui->combo_region); - const auto language_index = ConfigurationShared::GetComboboxIndex( - Settings::values.language_index.GetValue(true), ui->combo_language); + const auto region_index = combo_region->currentIndex(); + const auto language_index = combo_language->currentIndex(); const bool valid_locale = IsValidLocale(region_index, language_index); ui->label_warn_invalid_locale->setVisible(!valid_locale); if (!valid_locale) { ui->label_warn_invalid_locale->setText( tr("Warning: \"%1\" is not a valid language for region \"%2\"") - .arg(ui->combo_language->currentText()) - .arg(ui->combo_region->currentText())); + .arg(combo_language->currentText()) + .arg(combo_region->currentText())); } }; - connect(ui->combo_language, qOverload(&QComboBox::currentIndexChanged), this, - locale_check); - connect(ui->combo_region, qOverload(&QComboBox::currentIndexChanged), this, locale_check); - - SetupPerGameUI(); + connect(combo_language, qOverload(&QComboBox::currentIndexChanged), this, locale_check); + connect(combo_region, qOverload(&QComboBox::currentIndexChanged), this, locale_check); SetConfiguration(); } @@ -95,137 +98,94 @@ void ConfigureSystem::RetranslateUI() { ui->retranslateUi(this); } -void ConfigureSystem::SetConfiguration() { - enabled = !system.IsPoweredOn(); - const auto rng_seed = QStringLiteral("%1") - .arg(Settings::values.rng_seed.GetValue(), 8, 16, QLatin1Char{'0'}) - .toUpper(); - const auto rtc_time = Settings::values.custom_rtc_enabled - ? Settings::values.custom_rtc.GetValue() - : QDateTime::currentSecsSinceEpoch(); +void ConfigureSystem::Setup() { + const bool runtime_lock = !system.IsPoweredOn(); + auto& core_layout = *ui->core_widget->layout(); + auto& system_layout = *ui->system_widget->layout(); - ui->rng_seed_checkbox->setChecked(Settings::values.rng_seed_enabled.GetValue()); - ui->rng_seed_edit->setEnabled(Settings::values.rng_seed_enabled.GetValue() && - Settings::values.rng_seed.UsingGlobal()); - ui->rng_seed_edit->setText(rng_seed); + std::map core_hold{}; + std::map> system_hold{}; - ui->custom_rtc_checkbox->setChecked(Settings::values.custom_rtc_enabled.GetValue()); - ui->custom_rtc_edit->setEnabled(Settings::values.custom_rtc_enabled.GetValue()); - ui->custom_rtc_edit->setDateTime(QDateTime::fromSecsSinceEpoch(rtc_time)); - ui->device_name_edit->setText( - QString::fromUtf8(Settings::values.device_name.GetValue().c_str())); - ui->use_unsafe_extended_memory_layout->setEnabled(enabled); - ui->use_unsafe_extended_memory_layout->setChecked( - Settings::values.use_unsafe_extended_memory_layout.GetValue()); + std::forward_list settings; + auto push = [&settings](std::forward_list& list) { + for (auto setting : list) { + settings.push_front(setting); + } + }; - if (Settings::IsConfiguringGlobal()) { - ui->combo_language->setCurrentIndex(Settings::values.language_index.GetValue()); - ui->combo_region->setCurrentIndex(Settings::values.region_index.GetValue()); - ui->combo_time_zone->setCurrentIndex(Settings::values.time_zone_index.GetValue()); - } else { - ConfigurationShared::SetPerGameSetting(ui->combo_language, - &Settings::values.language_index); - ConfigurationShared::SetPerGameSetting(ui->combo_region, &Settings::values.region_index); - ConfigurationShared::SetPerGameSetting(ui->combo_time_zone, - &Settings::values.time_zone_index); + push(Settings::values.linkage.by_category[Settings::Category::Core]); + push(Settings::values.linkage.by_category[Settings::Category::System]); - ConfigurationShared::SetHighlight(ui->label_language, - !Settings::values.language_index.UsingGlobal()); - ConfigurationShared::SetHighlight(ui->label_region, - !Settings::values.region_index.UsingGlobal()); - ConfigurationShared::SetHighlight(ui->label_timezone, - !Settings::values.time_zone_index.UsingGlobal()); + for (auto setting : settings) { + ConfigurationShared::Widget* widget = [=]() { + if (setting->Id() == Settings::values.custom_rtc_enabled.Id()) { + return new ConfigurationShared::Widget( + setting, translations, this, runtime_lock, apply_funcs, + ConfigurationShared::RequestType::DateTimeEdit, true, 1.0f, + &Settings::values.custom_rtc); + } else if (setting->Id() == Settings::values.rng_seed_enabled.Id()) { + return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, + apply_funcs, + ConfigurationShared::RequestType::HexEdit, + true, 1.0f, &Settings::values.rng_seed); + } else { + return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, + + apply_funcs); + } + }(); + + if (!widget->Valid()) { + delete widget; + continue; + } + + if (setting->Id() == Settings::values.rng_seed_enabled.Id()) { + rng_seed_checkbox = widget->checkbox; + rng_seed_edit = widget->line_edit; + + if (!Settings::values.rng_seed_enabled.GetValue()) { + rng_seed_edit->setEnabled(false); + } + } else if (setting->Id() == Settings::values.custom_rtc_enabled.Id()) { + custom_rtc_checkbox = widget->checkbox; + custom_rtc_edit = widget->date_time_edit; + + custom_rtc_edit->setEnabled(Settings::values.custom_rtc_enabled.GetValue()); + } else if (setting->Id() == Settings::values.region_index.Id()) { + + combo_region = widget->combobox; + } else if (setting->Id() == Settings::values.language_index.Id()) { + combo_language = widget->combobox; + } + + switch (setting->Category()) { + case Settings::Category::Core: + core_hold[setting->GetLabel()] = widget; + break; + case Settings::Category::System: + system_hold[setting->IsEnum()].insert(std::pair{setting->GetLabel(), widget}); + break; + default: + delete widget; + } + } + for (const auto& [label, widget] : core_hold) { + core_layout.addWidget(widget); + } + for (const auto& [label, widget] : system_hold[true]) { + system_layout.addWidget(widget); + } + for (const auto& [label, widget] : system_hold[false]) { + system_layout.addWidget(widget); } } -void ConfigureSystem::ReadSystemSettings() {} +void ConfigureSystem::SetConfiguration() {} void ConfigureSystem::ApplyConfiguration() { - // Allow setting custom RTC even if system is powered on, - // to allow in-game time to be fast forwarded - if (Settings::IsConfiguringGlobal()) { - if (ui->custom_rtc_checkbox->isChecked()) { - Settings::values.custom_rtc_enabled = true; - Settings::values.custom_rtc = ui->custom_rtc_edit->dateTime().toSecsSinceEpoch(); - if (system.IsPoweredOn()) { - const s64 posix_time{Settings::values.custom_rtc.GetValue() + - Service::Time::TimeManager::GetExternalTimeZoneOffset()}; - system.GetTimeManager().UpdateLocalSystemClockTime(posix_time); - } - } else { - Settings::values.custom_rtc_enabled = false; - } - } - - Settings::values.device_name = ui->device_name_edit->text().toStdString(); - - if (!enabled) { - return; - } - - ConfigurationShared::ApplyPerGameSetting(&Settings::values.language_index, ui->combo_language); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.region_index, ui->combo_region); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.time_zone_index, - ui->combo_time_zone); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_unsafe_extended_memory_layout, - ui->use_unsafe_extended_memory_layout, - use_unsafe_extended_memory_layout); - - if (Settings::IsConfiguringGlobal()) { - // Guard if during game and set to game-specific value - if (Settings::values.rng_seed.UsingGlobal()) { - Settings::values.rng_seed_enabled = ui->rng_seed_checkbox->isChecked(); - if (ui->rng_seed_checkbox->isChecked()) { - Settings::values.rng_seed.SetValue(ui->rng_seed_edit->text().toUInt(nullptr, 16)); - } - } - } else { - switch (use_rng_seed) { - case ConfigurationShared::CheckState::On: - case ConfigurationShared::CheckState::Off: - Settings::values.rng_seed_enabled.SetGlobal(false); - Settings::values.rng_seed.SetGlobal(false); - if (ui->rng_seed_checkbox->isChecked()) { - Settings::values.rng_seed.SetValue(ui->rng_seed_edit->text().toUInt(nullptr, 16)); - } - break; - case ConfigurationShared::CheckState::Global: - Settings::values.rng_seed_enabled.SetGlobal(true); - Settings::values.rng_seed.SetGlobal(true); - break; - case ConfigurationShared::CheckState::Count: - break; - } + const bool powered_on = system.IsPoweredOn(); + for (const auto& func : apply_funcs) { + func(powered_on); } } - -void ConfigureSystem::SetupPerGameUI() { - if (Settings::IsConfiguringGlobal()) { - ui->combo_language->setEnabled(Settings::values.language_index.UsingGlobal()); - ui->combo_region->setEnabled(Settings::values.region_index.UsingGlobal()); - ui->combo_time_zone->setEnabled(Settings::values.time_zone_index.UsingGlobal()); - ui->rng_seed_checkbox->setEnabled(Settings::values.rng_seed.UsingGlobal()); - ui->rng_seed_edit->setEnabled(Settings::values.rng_seed.UsingGlobal()); - - return; - } - - ConfigurationShared::SetColoredComboBox(ui->combo_language, ui->label_language, - Settings::values.language_index.GetValue(true)); - ConfigurationShared::SetColoredComboBox(ui->combo_region, ui->label_region, - Settings::values.region_index.GetValue(true)); - ConfigurationShared::SetColoredComboBox(ui->combo_time_zone, ui->label_timezone, - Settings::values.time_zone_index.GetValue(true)); - - ConfigurationShared::SetColoredTristate( - ui->rng_seed_checkbox, Settings::values.rng_seed.UsingGlobal(), - Settings::values.rng_seed_enabled.GetValue(), - Settings::values.rng_seed_enabled.GetValue(true), use_rng_seed); - - ConfigurationShared::SetColoredTristate(ui->use_unsafe_extended_memory_layout, - Settings::values.use_unsafe_extended_memory_layout, - use_unsafe_extended_memory_layout); - - ui->custom_rtc_checkbox->setVisible(false); - ui->custom_rtc_edit->setVisible(false); -} diff --git a/src/yuzu/configuration/configure_system.h b/src/yuzu/configuration/configure_system.h index 6064b5b40..87b575060 100644 --- a/src/yuzu/configuration/configure_system.h +++ b/src/yuzu/configuration/configure_system.h @@ -3,11 +3,15 @@ #pragma once +#include +#include #include #include #include "yuzu/configuration/configuration_shared.h" +class QDateTimeEdit; + namespace Core { class System; } @@ -20,6 +24,7 @@ class ConfigureSystem : public ConfigurationShared::Tab { public: explicit ConfigureSystem(Core::System& system_, std::shared_ptr> group, + ConfigurationShared::TranslationMap& translations, QWidget* parent = nullptr); ~ConfigureSystem() override; @@ -30,9 +35,9 @@ private: void changeEvent(QEvent* event) override; void RetranslateUI(); - void ReadSystemSettings(); + void Setup(); - void SetupPerGameUI(); + std::forward_list> apply_funcs{}; std::unique_ptr ui; bool enabled = false; @@ -41,4 +46,12 @@ private: ConfigurationShared::CheckState use_unsafe_extended_memory_layout; Core::System& system; + ConfigurationShared::TranslationMap& translations; + + QCheckBox* rng_seed_checkbox; + QLineEdit* rng_seed_edit; + QCheckBox* custom_rtc_checkbox; + QDateTimeEdit* custom_rtc_edit; + QComboBox* combo_region; + QComboBox* combo_language; }; diff --git a/src/yuzu/configuration/configure_system.ui b/src/yuzu/configuration/configure_system.ui index e0caecd5e..a5a3e2dc3 100644 --- a/src/yuzu/configuration/configure_system.ui +++ b/src/yuzu/configuration/configure_system.ui @@ -6,7 +6,7 @@ 0 0 - 366 + 605 483 @@ -22,470 +22,53 @@ - System Settings + System - - - - - Region: - - - - - - - - Auto - - - - - Default - - - - - CET - - - - - CST6CDT - - - - - Cuba - - - - - EET - - - - - Egypt - - - - - Eire - - - - - EST - - - - - EST5EDT - - - - - GB - - - - - GB-Eire - - - - - GMT - - - - - GMT+0 - - - - - GMT-0 - - - - - GMT0 - - - - - Greenwich - - - - - Hongkong - - - - - HST - - - - - Iceland - - - - - Iran - - - - - Israel - - - - - Jamaica - - - - - Japan - - - - - Kwajalein - - - - - Libya - - - - - MET - - - - - MST - - - - - MST7MDT - - - - - Navajo - - - - - NZ - - - - - NZ-CHAT - - - - - Poland - - - - - Portugal - - - - - PRC - - - - - PST8PDT - - - - - ROC - - - - - ROK - - - - - Singapore - - - - - Turkey - - - - - UCT - - - - - Universal - - - - - UTC - - - - - W-SU - - - - - WET - - - - - Zulu - - - - - - - - - Japan - - - - - USA - - - - - Europe - - - - - Australia - - - - - China - - - - - Korea - - - - - Taiwan - - - - - - - - Time Zone: - - - - - - - Note: this can be overridden when region setting is auto-select - - - - Japanese (日本語) - - - - - American English - - - - - French (français) - - - - - German (Deutsch) - - - - - Italian (italiano) - - - - - Spanish (español) - - - - - Chinese - - - - - Korean (한국어) - - - - - Dutch (Nederlands) - - - - - Portuguese (português) - - - - - Russian (Русский) - - - - - Taiwanese - - - - - British English - - - - - Canadian French - - - - - Latin American Spanish - - - - - Simplified Chinese - - - - - Traditional Chinese (正體中文) - - - - - Brazilian Portuguese (português do Brasil) - - - - - - - - Custom RTC - - - - - - - Language - - - - - - - RNG Seed - - - - - - - Device Name - - - - - - - - 1970 - 1 - 1 - - - - - - - - 128 - - - - - - - - 0 - 0 - - - - - Lucida Console - - - - HHHHHHHH - - - 8 - - - - - - - Unsafe extended memory layout (8GB DRAM) - - - - + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + + + + + + Core + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + @@ -506,7 +89,7 @@ - + true diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index d38815e77..dc9f15cdd 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -109,15 +109,16 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { // System INSERT(Settings, rng_seed_enabled, "RNG Seed", ""); - INSERT(Settings, rng_seed, "RNG Seed", ""); + INSERT(Settings, rng_seed, "", ""); INSERT(Settings, device_name, "Device Name", ""); INSERT(Settings, custom_rtc_enabled, "Custom RTC", ""); - INSERT(Settings, custom_rtc, "Custom RTC", ""); + INSERT(Settings, custom_rtc, "", ""); INSERT(Settings, language_index, "Language:", ""); INSERT(Settings, region_index, "Region:", ""); INSERT(Settings, time_zone_index, "Time Zone:", ""); INSERT(Settings, sound_index, "Sound Output Mode:", ""); INSERT(Settings, use_docked_mode, "", ""); + INSERT(Settings, current_user, "", ""); // Controls @@ -231,6 +232,44 @@ std::forward_list ComboboxEnumeration(std::type_index type, QWidget* pa return { tr("Automatic"), tr("Default"), tr("2x"), tr("4x"), tr("8x"), tr("16x"), }; + } else if (type == typeid(Settings::Language)) { + return { + tr("Japanese (日本語)"), + tr("American English"), + tr("French (français)"), + tr("German (Deutsch)"), + tr("Italian (italiano)"), + tr("Spanish (español)"), + tr("Chinese"), + tr("Korean (한국어)"), + tr("Dutch (Nederlands)"), + tr("Portuguese (português)"), + tr("Russian (Русский)"), + tr("Taiwanese"), + tr("British English"), + tr("Canadian French"), + tr("Latin American Spanish"), + tr("Simplified Chinese"), + tr("Traditional Chinese (正體中文)"), + tr("Brazilian Portuguese (português do Brasil)"), + }; + } else if (type == typeid(Settings::Region)) { + return { + tr("Japan"), tr("USA"), tr("Europe"), tr("Australia"), + tr("China"), tr("Korea"), tr("Taiwan"), + }; + } else if (type == typeid(Settings::TimeZone)) { + return { + tr("Auto"), tr("Default"), tr("CET"), tr("CST6CDT"), tr("Cuba"), + tr("EET"), tr("Egypt"), tr("Eire"), tr("EST"), tr("EST5EDT"), + tr("GB"), tr("GB-Eire"), tr("GMT"), tr("GMT+0"), tr("GMT-0"), + tr("GMT0"), tr("Greenwich"), tr("Hongkong"), tr("HST"), tr("Iceland"), + tr("Iran"), tr("Israel"), tr("Jamaica"), tr("Kwajalein"), tr("Libya"), + tr("MET"), tr("MST"), tr("MST7MDT"), tr("Navajo"), tr("NZ"), + tr("NZ-CHAT"), tr("Poland"), tr("Portugal"), tr("PRC"), tr("PST8PDT"), + tr("ROC"), tr("ROK"), tr("Singapore"), tr("Turkey"), tr("UCT"), + tr("W-SU"), tr("WET"), tr("Zulu"), + }; } return {}; diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index d1113f793..0d553c67f 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -1,5 +1,7 @@ #include +#include #include +#include #include #include #include @@ -9,6 +11,9 @@ #include #include #include +#include +#include +#include #include "common/common_types.h" #include "common/settings.h" #include "yuzu/configuration/configuration_shared.h" @@ -25,7 +30,7 @@ QPushButton* Widget::CreateRestoreGlobalButton(Settings::BasicSetting& setting, QStyle* style = parent->style(); QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_DialogResetButton)); QPushButton* restore_button = new QPushButton(*icon, QStringLiteral(""), parent); - restore_button->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Expanding); + restore_button->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred); QSizePolicy sp_retain = restore_button->sizePolicy(); sp_retain.setRetainSizeWhenHidden(true); @@ -241,6 +246,67 @@ void Widget::CreateSlider(const QString& name, bool reversed, float multiplier, } } +void Widget::CreateCheckBoxWithHexEdit(const QString& label, Settings::BasicSetting* other_setting, + std::function& load_func) { + if (other_setting == nullptr) { + LOG_WARNING(Frontend, "Extra setting is null or not an integer"); + return; + } + created = true; + + std::function checkbox_load_func; + CreateCheckBox(label, checkbox_load_func); + + auto to_hex = [=](const std::string& input) { + return QString::fromStdString(fmt::format("{:08x}", std::stoi(input))); + }; + + QHBoxLayout* layout = reinterpret_cast(this->layout()); + const QString default_val = to_hex(other_setting->ToString()); + + line_edit = new QLineEdit(this); + line_edit->setText(default_val); + + checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + + layout->insertWidget(1, line_edit); + + line_edit->setMaxLength(8); + QRegExpValidator* regex = + new QRegExpValidator{QRegExp{QStringLiteral("^[0-9a-fA-F]{0,8}$")}, line_edit}; + line_edit->setValidator(regex); + + auto hex_to_dec = [=]() -> std::string { + return std::to_string(std::stoul(line_edit->text().toStdString(), nullptr, 16)); + }; + + if (Settings::IsConfiguringGlobal()) { + load_func = [=]() { + checkbox_load_func(); + other_setting->LoadString(hex_to_dec()); + }; + } else { + QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { + line_edit->setText(to_hex(other_setting->ToStringGlobal())); + }); + + QObject::connect(line_edit, &QLineEdit::textEdited, [=](const QString&) { + restore_button->setEnabled(true); + restore_button->setVisible(true); + }); + + load_func = [=]() { + checkbox_load_func(); + + const bool using_global = !restore_button->isEnabled(); + other_setting->SetGlobal(using_global); + if (!using_global) { + other_setting->LoadString(hex_to_dec()); + } + }; + } +} + void Widget::CreateCheckBoxWithLineEdit(const QString& label, Settings::BasicSetting* other_setting, std::function& load_func) { if (other_setting == nullptr) { @@ -268,8 +334,9 @@ void Widget::CreateCheckBoxWithLineEdit(const QString& label, Settings::BasicSet other_setting->LoadString(line_edit->text().toStdString()); }; } else { - QObject::connect(restore_button, &QAbstractButton::clicked, - [=](bool) { line_edit->setText(default_val); }); + QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { + line_edit->setText(QString::fromStdString(other_setting->ToStringGlobal())); + }); QObject::connect(line_edit, &QLineEdit::textEdited, [=](const QString&) { restore_button->setEnabled(true); @@ -279,7 +346,7 @@ void Widget::CreateCheckBoxWithLineEdit(const QString& label, Settings::BasicSet load_func = [=]() { checkbox_load_func(); - const bool using_global = !restore_button->isVisible(); + const bool using_global = !restore_button->isEnabled(); other_setting->SetGlobal(using_global); if (!using_global) { other_setting->LoadString(line_edit->text().toStdString()); @@ -289,7 +356,8 @@ void Widget::CreateCheckBoxWithLineEdit(const QString& label, Settings::BasicSet } void Widget::CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSetting* other_setting, - std::function& load_func, const QString& suffix) { + std::function& load_func, + const std::string& suffix) { if (other_setting == nullptr && IsInt(other_setting->TypeId())) { LOG_WARNING(Frontend, "Extra setting is null or not an integer"); return; @@ -308,7 +376,7 @@ void Widget::CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSett const int default_val = std::stoi(other_setting->ToString()); spinbox->setRange(min_val, max_val); spinbox->setValue(default_val); - spinbox->setSuffix(suffix); + spinbox->setSuffix(QString::fromStdString(suffix)); spinbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->insertWidget(1, spinbox); @@ -320,7 +388,7 @@ void Widget::CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSett }; } else { QObject::connect(restore_button, &QAbstractButton::clicked, [this, other_setting](bool) { - spinbox->setValue(std::stoi(other_setting->ToString())); + spinbox->setValue(std::stoi(other_setting->ToStringGlobal())); }); QObject::connect(spinbox, QOverload::of(&QSpinBox::valueChanged), [this](int) { @@ -331,7 +399,7 @@ void Widget::CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSett load_func = [=]() { checkbox_load_func(); - const bool using_global = !restore_button->isVisible(); + const bool using_global = !restore_button->isEnabled(); other_setting->SetGlobal(using_global); if (!using_global) { other_setting->LoadString(std::to_string(spinbox->value())); @@ -340,6 +408,81 @@ void Widget::CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSett } } +// Currently tailored to custom_rtc +void Widget::CreateCheckBoxWithDateTimeEdit(const QString& label, + Settings::BasicSetting* other_setting, + std::function& load_func) { + if (other_setting == nullptr) { + LOG_WARNING(Frontend, "Extra setting is null or not an integer"); + return; + } + created = true; + + std::function checkbox_load_func; + CreateCheckBox(label, checkbox_load_func); + + QHBoxLayout* layout = reinterpret_cast(this->layout()); + const bool disabled = setting.ToString() != "true"; + const long long current_time = QDateTime::currentSecsSinceEpoch(); + const s64 the_time = disabled ? current_time : std::stoll(other_setting->ToString()); + const auto default_val = QDateTime::fromSecsSinceEpoch(the_time); + + date_time_edit = new QDateTimeEdit(this); + date_time_edit->setDateTime(default_val); + + date_time_edit->setMinimumDateTime(QDateTime::fromSecsSinceEpoch(0)); + + date_time_edit->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + + layout->insertWidget(1, date_time_edit); + + if (Settings::IsConfiguringGlobal()) { + load_func = [=]() { + checkbox_load_func(); + if (checkbox->checkState() == Qt::Unchecked) { + return; + } + + other_setting->LoadString( + std::to_string(date_time_edit->dateTime().toSecsSinceEpoch())); + }; + } else { + auto get_clear_val = [=]() { + return QDateTime::fromSecsSinceEpoch([=]() { + if (checkbox->checkState() == Qt::Checked) { + return std::stoll(other_setting->ToStringGlobal()); + } + return current_time; + }()); + }; + + QObject::connect(restore_button, &QAbstractButton::clicked, + [=](bool) { date_time_edit->setDateTime(get_clear_val()); }); + + QObject::connect(date_time_edit, &QDateTimeEdit::editingFinished, [=]() { + if (date_time_edit->dateTime() != get_clear_val()) { + restore_button->setEnabled(true); + restore_button->setVisible(true); + } + }); + + load_func = [=]() { + checkbox_load_func(); + if (checkbox->checkState() == Qt::Unchecked) { + return; + } + + const bool using_global = !restore_button->isEnabled(); + other_setting->SetGlobal(using_global); + if (!using_global) { + other_setting->LoadString( + std::to_string(date_time_edit->dateTime().toSecsSinceEpoch())); + } + }; + } +} + bool Widget::Valid() { return created; } @@ -350,7 +493,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati QWidget* parent_, bool runtime_lock, std::forward_list>& apply_funcs, RequestType request, bool managed, float multiplier, Settings::BasicSetting* other_setting, - const QString& format) + const std::string& string) : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_} { if (!Settings::IsConfiguringGlobal() && !setting.Switchable()) { LOG_DEBUG(Frontend, "\"{}\" is not switchable, skipping...", setting.GetLabel()); @@ -379,19 +522,26 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati if (type == typeid(bool)) { switch (request) { - case RequestType::SpinBox: - CreateCheckBoxWithSpinBox(label, other_setting, load_func, format); - break; case RequestType::Default: CreateCheckBox(label, load_func); break; + case RequestType::SpinBox: + CreateCheckBoxWithSpinBox(label, other_setting, load_func, string); + break; + case RequestType::HexEdit: + CreateCheckBoxWithHexEdit(label, other_setting, load_func); + break; case RequestType::LineEdit: CreateCheckBoxWithLineEdit(label, other_setting, load_func); break; + case RequestType::DateTimeEdit: + CreateCheckBoxWithDateTimeEdit(label, other_setting, load_func); + break; case RequestType::ComboBox: case RequestType::Slider: case RequestType::ReverseSlider: case RequestType::MaxEnum: + LOG_DEBUG(Frontend, "Requested widget is unimplemented."); break; } } else if (setting.IsEnum()) { @@ -409,10 +559,15 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati case RequestType::ComboBox: CreateCombobox(label, managed, load_func); break; + case RequestType::DateTimeEdit: case RequestType::SpinBox: + case RequestType::HexEdit: case RequestType::MaxEnum: + LOG_DEBUG(Frontend, "Requested widget is unimplemented."); break; } + } else if (type == typeid(std::string)) { + CreateLineEdit(label, managed, load_func); } if (!created) { diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 88a864b42..9923aa2ea 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -9,6 +9,7 @@ class QComboBox; class QLineEdit; class QSlider; class QCheckBox; +class QDateTimeEdit; namespace Settings { class BasicSetting; @@ -23,6 +24,8 @@ enum class RequestType { Slider, ReverseSlider, LineEdit, + HexEdit, + DateTimeEdit, MaxEnum, }; @@ -33,8 +36,7 @@ public: Widget(Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, bool runtime_lock, std::forward_list>& apply_funcs, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, - Settings::BasicSetting* other_setting = nullptr, - const QString& format = QStringLiteral("")); + Settings::BasicSetting* other_setting = nullptr, const std::string& format = ""); virtual ~Widget(); bool Valid(); @@ -48,13 +50,18 @@ public: QCheckBox* checkbox{}; QSlider* slider{}; QComboBox* combobox{}; + QDateTimeEdit* date_time_edit{}; private: void CreateCheckBox(const QString& label, std::function& load_func); void CreateCheckBoxWithLineEdit(const QString& label, Settings::BasicSetting* other_setting, std::function& load_func); + void CreateCheckBoxWithHexEdit(const QString& label, Settings::BasicSetting* other_setting, + std::function& load_func); void CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSetting* other_setting, - std::function& load_func, const QString& suffix); + std::function& load_func, const std::string& suffix); + void CreateCheckBoxWithDateTimeEdit(const QString& label, Settings::BasicSetting* other_setting, + std::function& load_func); void CreateCombobox(const QString& label, bool managed, std::function& load_func); void CreateLineEdit(const QString& label, bool managed, std::function& load_func); void CreateSlider(const QString& label, bool reversed, float multiplier, diff --git a/src/yuzu_cmd/config.cpp b/src/yuzu_cmd/config.cpp index f8cbf8034..c42d98709 100644 --- a/src/yuzu_cmd/config.cpp +++ b/src/yuzu_cmd/config.cpp @@ -229,6 +229,7 @@ void Config::ReadValues() { ReadCategory(Settings::Category::RendererAdvanced); ReadCategory(Settings::Category::RendererDebug); ReadCategory(Settings::Category::System); + ReadCategory(Settings::Category::SystemAudio); ReadCategory(Settings::Category::DataStorage); ReadCategory(Settings::Category::Debugging); ReadCategory(Settings::Category::DebuggingGraphics); From 4c4bc134a90a248435786b1dff4f514d1c9c4464 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 9 Jun 2023 16:53:01 -0400 Subject: [PATCH 041/155] settings, uisettings: Initialize linkage counter --- src/common/settings.cpp | 2 +- src/common/settings.h | 2 +- src/yuzu/uisettings.h | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 605fe7f86..c8651925e 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -144,7 +144,7 @@ float Volume() { return values.volume.GetValue() / static_cast(values.volume.GetDefault()); } -Linkage::Linkage() = default; +Linkage::Linkage(u32 initial_count) : count{initial_count} {} Linkage::~Linkage() = default; const char* TranslateCategory(Category category) { diff --git a/src/common/settings.h b/src/common/settings.h index 1f95bd7d5..51708706b 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -291,7 +291,7 @@ public: class Linkage { public: - explicit Linkage(); + explicit Linkage(u32 initial_count = 0); ~Linkage(); std::map> by_category{}; std::vector> restore_functions{}; diff --git a/src/yuzu/uisettings.h b/src/yuzu/uisettings.h index 9e2cea4d6..a734513ea 100644 --- a/src/yuzu/uisettings.h +++ b/src/yuzu/uisettings.h @@ -59,7 +59,7 @@ struct GameDir { }; struct Values { - Settings::Linkage linkage{}; + Settings::Linkage linkage{1000}; QByteArray geometry; QByteArray state; From 4ff8255e4a985e69046e453a9bd38adf80346548 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 9 Jun 2023 16:53:26 -0400 Subject: [PATCH 042/155] shared_widget: Refactor helpers Makes checkbox creation an option as opposed to a label. --- src/yuzu/configuration/configure_graphics.cpp | 9 +- src/yuzu/configuration/configure_graphics.h | 4 +- src/yuzu/configuration/configure_system.cpp | 23 +- src/yuzu/configuration/shared_translation.cpp | 8 +- src/yuzu/configuration/shared_widget.cpp | 441 +++++++++--------- src/yuzu/configuration/shared_widget.h | 35 +- 6 files changed, 277 insertions(+), 243 deletions(-) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 977aed42d..2354323b8 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -165,6 +165,11 @@ void ConfigureGraphics::PopulateVSyncModeSelection() { : vsync_mode_combobox_enum_map[current_index]; int index{}; const int device{vulkan_device_combobox->currentIndex()}; //< current selected Vulkan device + if (device == -1) { + // Invalid device + return; + } + const auto& present_modes = //< relevant vector of present modes for the selected device or API backend == Settings::RendererBackend::Vulkan ? device_present_modes[device] : default_present_modes; @@ -236,11 +241,11 @@ void ConfigureGraphics::Setup() { return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ReverseSlider, true, 0.5f); - } else if (setting->Id() == Settings::values.use_speed_limit.Id()) { + } else if (setting->Id() == Settings::values.speed_limit.Id()) { return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::SpinBox, true, 1.0f, - &Settings::values.speed_limit, "%"); + &Settings::values.use_speed_limit, "%"); } else { return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index 61eb2f2fc..f36495ed3 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -77,8 +77,8 @@ private: std::vector vulkan_devices; std::vector> device_present_modes; std::vector - vsync_mode_combobox_enum_map; //< Keeps track of which present mode corresponds to which - // selection in the combobox + vsync_mode_combobox_enum_map{}; //< Keeps track of which present mode corresponds to which + // selection in the combobox u32 vulkan_device{}; Settings::ShaderBackend shader_backend{}; const std::function& expose_compute_option; diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index dedbad57f..128860800 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -117,17 +117,18 @@ void ConfigureSystem::Setup() { push(Settings::values.linkage.by_category[Settings::Category::System]); for (auto setting : settings) { + [[maybe_unused]] std::string label = setting->GetLabel(); ConfigurationShared::Widget* widget = [=]() { - if (setting->Id() == Settings::values.custom_rtc_enabled.Id()) { + if (setting->Id() == Settings::values.custom_rtc.Id()) { return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::DateTimeEdit, true, 1.0f, - &Settings::values.custom_rtc); - } else if (setting->Id() == Settings::values.rng_seed_enabled.Id()) { - return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, - apply_funcs, - ConfigurationShared::RequestType::HexEdit, - true, 1.0f, &Settings::values.rng_seed); + &Settings::values.custom_rtc_enabled); + } else if (setting->Id() == Settings::values.rng_seed.Id()) { + return new ConfigurationShared::Widget( + setting, translations, this, runtime_lock, apply_funcs, + ConfigurationShared::RequestType::HexEdit, true, 1.0f, + &Settings::values.rng_seed_enabled); } else { return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, @@ -140,14 +141,12 @@ void ConfigureSystem::Setup() { continue; } - if (setting->Id() == Settings::values.rng_seed_enabled.Id()) { + if (setting->Id() == Settings::values.rng_seed.Id()) { rng_seed_checkbox = widget->checkbox; rng_seed_edit = widget->line_edit; - if (!Settings::values.rng_seed_enabled.GetValue()) { - rng_seed_edit->setEnabled(false); - } - } else if (setting->Id() == Settings::values.custom_rtc_enabled.Id()) { + rng_seed_edit->setEnabled(Settings::values.rng_seed_enabled.GetValue()); + } else if (setting->Id() == Settings::values.custom_rtc.Id()) { custom_rtc_checkbox = widget->checkbox; custom_rtc_edit = widget->date_time_edit; diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index dc9f15cdd..6038e8c25 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -108,11 +108,11 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(Settings, speed_limit, "Limit Speed Percent", ""); // System - INSERT(Settings, rng_seed_enabled, "RNG Seed", ""); - INSERT(Settings, rng_seed, "", ""); + INSERT(Settings, rng_seed, "RNG Seed", ""); + INSERT(Settings, rng_seed_enabled, "", ""); INSERT(Settings, device_name, "Device Name", ""); - INSERT(Settings, custom_rtc_enabled, "Custom RTC", ""); - INSERT(Settings, custom_rtc, "", ""); + INSERT(Settings, custom_rtc, "Custom RTC", ""); + INSERT(Settings, custom_rtc_enabled, "", ""); INSERT(Settings, language_index, "Language:", ""); INSERT(Settings, region_index, "Region:", ""); INSERT(Settings, time_zone_index, "Time Zone:", ""); diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 0d553c67f..3ef2c25c6 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -12,7 +12,9 @@ #include #include #include +#include #include +#include #include #include "common/common_types.h" #include "common/settings.h" @@ -22,10 +24,6 @@ namespace ConfigurationShared { -static bool IsInt(const std::type_index& type) { - return type == typeid(u32) || type == typeid(s32) || type == typeid(u16) || type == typeid(s16); -} - QPushButton* Widget::CreateRestoreGlobalButton(Settings::BasicSetting& setting, QWidget* parent) { QStyle* style = parent->style(); QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_DialogResetButton)); @@ -42,50 +40,65 @@ QPushButton* Widget::CreateRestoreGlobalButton(Settings::BasicSetting& setting, return restore_button; } -void Widget::CreateCheckBox(const QString& label, std::function& load_func) { +QLabel* Widget::CreateLabel(const QString& text) { + QLabel* qt_label = new QLabel(text, this->parent); + qt_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + return qt_label; +} + +QHBoxLayout* Widget::CreateCheckBox(Settings::BasicSetting* bool_setting, const QString& label, + std::function& load_func, bool managed) { created = true; QHBoxLayout* layout = new QHBoxLayout(this); checkbox = new QCheckBox(label, this); - checkbox->setObjectName(QString::fromStdString(setting.GetLabel())); - checkbox->setCheckState(setting.ToString() == "true" ? Qt::CheckState::Checked - : Qt::CheckState::Unchecked); + checkbox->setCheckState(bool_setting->ToString() == "true" ? Qt::CheckState::Checked + : Qt::CheckState::Unchecked); + checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->addWidget(checkbox); + + layout->setContentsMargins(0, 0, 0, 0); + + if (!managed) { + return layout; + } + if (Settings::IsConfiguringGlobal()) { load_func = [=]() { - setting.LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + bool_setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); }; } else { - restore_button = CreateRestoreGlobalButton(setting, this); + restore_button = CreateRestoreGlobalButton(*bool_setting, this); layout->addWidget(restore_button); - QObject::connect(checkbox, &QCheckBox::stateChanged, [&](int) { + QObject::connect(checkbox, &QCheckBox::stateChanged, [=](int) { restore_button->setVisible(true); restore_button->setEnabled(true); }); - QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { - checkbox->setCheckState(setting.ToStringGlobal() == "true" ? Qt::Checked - : Qt::Unchecked); + QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { + checkbox->setCheckState(bool_setting->ToStringGlobal() == "true" ? Qt::Checked + : Qt::Unchecked); restore_button->setEnabled(false); restore_button->setVisible(false); }); load_func = [=]() { bool using_global = !restore_button->isEnabled(); - setting.SetGlobal(using_global); + bool_setting->SetGlobal(using_global); if (!using_global) { - setting.LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + bool_setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); } }; } - layout->setContentsMargins(0, 0, 0, 0); + return layout; } -void Widget::CreateCombobox(const QString& label, bool managed, std::function& load_func) { +void Widget::CreateCombobox(const QString& label, std::function& load_func, bool managed, + Settings::BasicSetting* const other_setting) { created = true; const auto type = setting.TypeId(); @@ -108,9 +121,13 @@ void Widget::CreateCombobox(const QString& label, bool managed, std::functionsetCurrentIndex(std::stoi(setting.ToString())); - if (Settings::IsConfiguringGlobal() && managed) { + if (!managed) { + return; + } + + if (Settings::IsConfiguringGlobal()) { load_func = [=]() { setting.LoadString(std::to_string(combobox->currentIndex())); }; - } else if (managed) { + } else { restore_button = CreateRestoreGlobalButton(setting, this); layout->addWidget(restore_button); @@ -136,30 +153,50 @@ void Widget::CreateCombobox(const QString& label, bool managed, std::function& load_func) { +void Widget::CreateLineEdit(const QString& label, std::function& load_func, bool managed, + Settings::BasicSetting* other_setting) { + const bool has_checkbox = other_setting != nullptr; + if (has_checkbox && other_setting->TypeId() != typeid(bool)) { + LOG_WARNING(Frontend, "Extra setting requested but setting is not boolean"); + return; + } + created = true; - QHBoxLayout* layout = new QHBoxLayout(this); - line_edit = new QLineEdit(this); + QHBoxLayout* layout{nullptr}; + std::function checkbox_load_func = []() {}; + + if (has_checkbox) { + layout = CreateCheckBox(other_setting, label, checkbox_load_func, managed); + } else { + layout = new QHBoxLayout(this); + layout->setContentsMargins(0, 0, 0, 0); + QLabel* q_label = CreateLabel(label); + layout->addWidget(q_label); + } const QString text = QString::fromStdString(setting.ToString()); + line_edit = new QLineEdit(this); line_edit->setText(text); - QLabel* q_label = new QLabel(label, this); - // setSizePolicy lets widget expand and take an equal part of the space as the line edit - q_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - layout->addWidget(q_label); - layout->addWidget(line_edit); - if (Settings::IsConfiguringGlobal() && !managed) { + if (!managed) { + return; + } + + if (Settings::IsConfiguringGlobal()) { load_func = [=]() { + checkbox_load_func(); + std::string load_text = line_edit->text().toStdString(); setting.LoadString(load_text); }; - } else if (!managed) { - restore_button = CreateRestoreGlobalButton(setting, this); - layout->addWidget(restore_button); + } else { + if (!has_checkbox) { + restore_button = CreateRestoreGlobalButton(setting, this); + layout->addWidget(restore_button); + } QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { restore_button->setEnabled(false); @@ -174,6 +211,8 @@ void Widget::CreateLineEdit(const QString& label, bool managed, std::functionisEnabled(); setting.SetGlobal(using_global); if (!using_global) { @@ -181,24 +220,23 @@ void Widget::CreateLineEdit(const QString& label, bool managed, std::functionsetContentsMargins(0, 0, 0, 0); } -void Widget::CreateSlider(const QString& name, bool reversed, float multiplier, - std::function& load_func) { +void Widget::CreateSlider(const QString& label, bool reversed, float multiplier, + std::function& load_func, bool managed, + Settings::BasicSetting* const other_setting) { created = true; QHBoxLayout* layout = new QHBoxLayout(this); slider = new QSlider(Qt::Horizontal, this); - QLabel* label = new QLabel(name, this); + QLabel* qt_label = new QLabel(label, this); QLabel* feedback = new QLabel(this); - layout->addWidget(label); + layout->addWidget(qt_label); layout->addWidget(slider); layout->addWidget(feedback); - label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + qt_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->setContentsMargins(0, 0, 0, 0); @@ -214,8 +252,10 @@ void Widget::CreateSlider(const QString& name, bool reversed, float multiplier, slider->setMinimum(std::stoi(setting.MinVal())); slider->setMaximum(max_val); - if (reversed) { - slider->setInvertedAppearance(true); + slider->setInvertedAppearance(reversed); + + if (!managed) { + return; } if (Settings::IsConfiguringGlobal()) { @@ -246,134 +286,33 @@ void Widget::CreateSlider(const QString& name, bool reversed, float multiplier, } } -void Widget::CreateCheckBoxWithHexEdit(const QString& label, Settings::BasicSetting* other_setting, - std::function& load_func) { - if (other_setting == nullptr) { - LOG_WARNING(Frontend, "Extra setting is null or not an integer"); +void Widget::CreateSpinBox(const QString& label, std::function& load_func, bool managed, + const std::string& suffix, Settings::BasicSetting* other_setting) { + const bool has_checkbox = other_setting != nullptr; + if (has_checkbox && other_setting->TypeId() != typeid(bool)) { + LOG_WARNING(Frontend, "Extra setting requested but setting is not boolean"); return; } created = true; - std::function checkbox_load_func; - CreateCheckBox(label, checkbox_load_func); + QHBoxLayout* layout{nullptr}; + std::function checkbox_load_func = []() {}; + QLabel* q_label{nullptr}; - auto to_hex = [=](const std::string& input) { - return QString::fromStdString(fmt::format("{:08x}", std::stoi(input))); - }; - - QHBoxLayout* layout = reinterpret_cast(this->layout()); - const QString default_val = to_hex(other_setting->ToString()); - - line_edit = new QLineEdit(this); - line_edit->setText(default_val); - - checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - - layout->insertWidget(1, line_edit); - - line_edit->setMaxLength(8); - QRegExpValidator* regex = - new QRegExpValidator{QRegExp{QStringLiteral("^[0-9a-fA-F]{0,8}$")}, line_edit}; - line_edit->setValidator(regex); - - auto hex_to_dec = [=]() -> std::string { - return std::to_string(std::stoul(line_edit->text().toStdString(), nullptr, 16)); - }; - - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { - checkbox_load_func(); - other_setting->LoadString(hex_to_dec()); - }; + if (has_checkbox) { + layout = CreateCheckBox(other_setting, label, checkbox_load_func, managed); } else { - QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { - line_edit->setText(to_hex(other_setting->ToStringGlobal())); - }); - - QObject::connect(line_edit, &QLineEdit::textEdited, [=](const QString&) { - restore_button->setEnabled(true); - restore_button->setVisible(true); - }); - - load_func = [=]() { - checkbox_load_func(); - - const bool using_global = !restore_button->isEnabled(); - other_setting->SetGlobal(using_global); - if (!using_global) { - other_setting->LoadString(hex_to_dec()); - } - }; + layout = new QHBoxLayout(this); + layout->setContentsMargins(0, 0, 0, 0); + q_label = CreateLabel(label); + layout->addWidget(q_label); } -} -void Widget::CreateCheckBoxWithLineEdit(const QString& label, Settings::BasicSetting* other_setting, - std::function& load_func) { - if (other_setting == nullptr) { - LOG_WARNING(Frontend, "Extra setting is null or not an integer"); - return; - } - created = true; - - std::function checkbox_load_func; - CreateCheckBox(label, checkbox_load_func); - - QHBoxLayout* layout = reinterpret_cast(this->layout()); - const QString default_val = QString::fromStdString(other_setting->ToString()); - - line_edit = new QLineEdit(this); - line_edit->setText(default_val); - - checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - - layout->insertWidget(1, line_edit); - - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { - checkbox_load_func(); - other_setting->LoadString(line_edit->text().toStdString()); - }; - } else { - QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { - line_edit->setText(QString::fromStdString(other_setting->ToStringGlobal())); - }); - - QObject::connect(line_edit, &QLineEdit::textEdited, [=](const QString&) { - restore_button->setEnabled(true); - restore_button->setVisible(true); - }); - - load_func = [=]() { - checkbox_load_func(); - - const bool using_global = !restore_button->isEnabled(); - other_setting->SetGlobal(using_global); - if (!using_global) { - other_setting->LoadString(line_edit->text().toStdString()); - } - }; - } -} - -void Widget::CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSetting* other_setting, - std::function& load_func, - const std::string& suffix) { - if (other_setting == nullptr && IsInt(other_setting->TypeId())) { - LOG_WARNING(Frontend, "Extra setting is null or not an integer"); - return; - } - created = true; - - std::function checkbox_load_func; - CreateCheckBox(label, checkbox_load_func); - checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - - QHBoxLayout* layout = reinterpret_cast(this->layout()); + const int min_val = std::stoi(setting.MinVal()); + const int max_val = std::stoi(setting.MaxVal()); + const int default_val = std::stoi(setting.ToString()); spinbox = new QSpinBox(this); - const int min_val = std::stoi(other_setting->MinVal()); - const int max_val = std::stoi(other_setting->MaxVal()); - const int default_val = std::stoi(other_setting->ToString()); spinbox->setRange(min_val, max_val); spinbox->setValue(default_val); spinbox->setSuffix(QString::fromStdString(suffix)); @@ -384,12 +323,15 @@ void Widget::CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSett if (Settings::IsConfiguringGlobal()) { load_func = [=]() { checkbox_load_func(); - other_setting->LoadString(std::to_string(spinbox->value())); + setting.LoadString(std::to_string(spinbox->value())); }; } else { - QObject::connect(restore_button, &QAbstractButton::clicked, [this, other_setting](bool) { - spinbox->setValue(std::stoi(other_setting->ToStringGlobal())); - }); + if (!has_checkbox) { + restore_button = CreateRestoreGlobalButton(setting, this); + } + + QObject::connect(restore_button, &QAbstractButton::clicked, + [this](bool) { spinbox->setValue(std::stoi(setting.ToStringGlobal())); }); QObject::connect(spinbox, QOverload::of(&QSpinBox::valueChanged), [this](int) { restore_button->setEnabled(true); @@ -400,47 +342,122 @@ void Widget::CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSett checkbox_load_func(); const bool using_global = !restore_button->isEnabled(); - other_setting->SetGlobal(using_global); + setting.SetGlobal(using_global); if (!using_global) { - other_setting->LoadString(std::to_string(spinbox->value())); + setting.LoadString(std::to_string(spinbox->value())); } }; } } -// Currently tailored to custom_rtc -void Widget::CreateCheckBoxWithDateTimeEdit(const QString& label, - Settings::BasicSetting* other_setting, - std::function& load_func) { - if (other_setting == nullptr) { - LOG_WARNING(Frontend, "Extra setting is null or not an integer"); +void Widget::CreateHexEdit(const QString& label, std::function& load_func, bool managed, + Settings::BasicSetting* const other_setting) { + CreateLineEdit(label, load_func, false, other_setting); + if (!created || !managed) { + return; + } + + QLayout* layout = this->layout(); + + auto to_hex = [=](const std::string& input) { + return QString::fromStdString(fmt::format("{:08x}", std::stoi(input))); + }; + + QRegExpValidator* regex = + new QRegExpValidator{QRegExp{QStringLiteral("^[0-9a-fA-F]{0,8}$")}, line_edit}; + + const QString default_val = to_hex(setting.ToString()); + + line_edit->setText(default_val); + line_edit->setMaxLength(8); + line_edit->setValidator(regex); + + auto hex_to_dec = [=]() -> std::string { + return std::to_string(std::stoul(line_edit->text().toStdString(), nullptr, 16)); + }; + + if (Settings::IsConfiguringGlobal()) { + load_func = [=]() { + other_setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + setting.LoadString(hex_to_dec()); + }; + } else { + restore_button = CreateRestoreGlobalButton(setting, this); + layout->addWidget(restore_button); + + QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { + line_edit->setText(to_hex(setting.ToStringGlobal())); + checkbox->setCheckState(other_setting->ToStringGlobal() == "true" ? Qt::Checked + : Qt::Unchecked); + + restore_button->setEnabled(false); + restore_button->setVisible(false); + }); + + QObject::connect(line_edit, &QLineEdit::textEdited, [&]() { + restore_button->setEnabled(true); + restore_button->setVisible(true); + }); + + QObject::connect(checkbox, &QAbstractButton::clicked, [&]() { + restore_button->setEnabled(true); + restore_button->setVisible(true); + }); + + load_func = [=]() { + const bool using_global = !restore_button->isEnabled(); + other_setting->SetGlobal(using_global); + setting.SetGlobal(using_global); + + if (!using_global) { + other_setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); + setting.LoadString(hex_to_dec()); + } + }; + } +} + +void Widget::CreateDateTimeEdit(const QString& label, std::function& load_func, + bool managed, bool restrict, + Settings::BasicSetting* const other_setting) { + const bool has_checkbox = other_setting != nullptr; + if ((restrict && !has_checkbox) || (has_checkbox && other_setting->TypeId() != typeid(bool))) { + LOG_WARNING(Frontend, "Extra setting or restrict requested but is not boolean"); return; } created = true; - std::function checkbox_load_func; - CreateCheckBox(label, checkbox_load_func); + QHBoxLayout* layout{nullptr}; + std::function checkbox_load_func = []() {}; - QHBoxLayout* layout = reinterpret_cast(this->layout()); - const bool disabled = setting.ToString() != "true"; + if (has_checkbox) { + layout = CreateCheckBox(other_setting, label, checkbox_load_func, managed); + } else { + layout = new QHBoxLayout(this); + QLabel* q_label = CreateLabel(label); + layout->addWidget(q_label); + } + + const bool disabled = other_setting->ToString() != "true"; const long long current_time = QDateTime::currentSecsSinceEpoch(); - const s64 the_time = disabled ? current_time : std::stoll(other_setting->ToString()); + const s64 the_time = disabled ? current_time : std::stoll(setting.ToString()); const auto default_val = QDateTime::fromSecsSinceEpoch(the_time); date_time_edit = new QDateTimeEdit(this); date_time_edit->setDateTime(default_val); - date_time_edit->setMinimumDateTime(QDateTime::fromSecsSinceEpoch(0)); - date_time_edit->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->insertWidget(1, date_time_edit); + if (!managed) { + return; + } + if (Settings::IsConfiguringGlobal()) { load_func = [=]() { checkbox_load_func(); - if (checkbox->checkState() == Qt::Unchecked) { + if (restrict && checkbox->checkState() == Qt::Unchecked) { return; } @@ -448,9 +465,14 @@ void Widget::CreateCheckBoxWithDateTimeEdit(const QString& label, std::to_string(date_time_edit->dateTime().toSecsSinceEpoch())); }; } else { + if (!has_checkbox) { + restore_button = CreateRestoreGlobalButton(setting, this); + layout->addWidget(restore_button); + } + auto get_clear_val = [=]() { return QDateTime::fromSecsSinceEpoch([=]() { - if (checkbox->checkState() == Qt::Checked) { + if (restrict && checkbox->checkState() == Qt::Checked) { return std::stoll(other_setting->ToStringGlobal()); } return current_time; @@ -469,7 +491,7 @@ void Widget::CreateCheckBoxWithDateTimeEdit(const QString& label, load_func = [=]() { checkbox_load_func(); - if (checkbox->checkState() == Qt::Unchecked) { + if (restrict && checkbox->checkState() == Qt::Unchecked) { return; } @@ -489,12 +511,18 @@ bool Widget::Valid() { Widget::~Widget() = default; +Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, + QWidget* parent_, std::forward_list>& apply_funcs_) + : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_}, + apply_funcs{apply_funcs_} {} + Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, QWidget* parent_, bool runtime_lock, - std::forward_list>& apply_funcs, RequestType request, + std::forward_list>& apply_funcs_, RequestType request, bool managed, float multiplier, Settings::BasicSetting* other_setting, const std::string& string) - : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_} { + : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_}, + apply_funcs{apply_funcs_} { if (!Settings::IsConfiguringGlobal() && !setting.Switchable()) { LOG_DEBUG(Frontend, "\"{}\" is not switchable, skipping...", setting.GetLabel()); return; @@ -523,51 +551,44 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati if (type == typeid(bool)) { switch (request) { case RequestType::Default: - CreateCheckBox(label, load_func); + CreateCheckBox(&setting, label, load_func, managed); break; - case RequestType::SpinBox: - CreateCheckBoxWithSpinBox(label, other_setting, load_func, string); - break; - case RequestType::HexEdit: - CreateCheckBoxWithHexEdit(label, other_setting, load_func); - break; - case RequestType::LineEdit: - CreateCheckBoxWithLineEdit(label, other_setting, load_func); - break; - case RequestType::DateTimeEdit: - CreateCheckBoxWithDateTimeEdit(label, other_setting, load_func); - break; - case RequestType::ComboBox: - case RequestType::Slider: - case RequestType::ReverseSlider: - case RequestType::MaxEnum: - LOG_DEBUG(Frontend, "Requested widget is unimplemented."); + default: + LOG_WARNING(Frontend, "Requested widget is unimplemented."); break; } } else if (setting.IsEnum()) { - CreateCombobox(label, managed, load_func); - } else if (type == typeid(u32) || type == typeid(int)) { + CreateCombobox(label, load_func, managed); + } else if (type == typeid(u32) || type == typeid(int) || type == typeid(u16) || + type == typeid(s64)) { switch (request) { case RequestType::Slider: case RequestType::ReverseSlider: - CreateSlider(label, request == RequestType::ReverseSlider, multiplier, load_func); + CreateSlider(label, request == RequestType::ReverseSlider, multiplier, load_func, + managed); break; case RequestType::LineEdit: case RequestType::Default: - CreateLineEdit(label, managed, load_func); + CreateLineEdit(label, load_func, managed); break; case RequestType::ComboBox: - CreateCombobox(label, managed, load_func); + CreateCombobox(label, load_func, managed); break; case RequestType::DateTimeEdit: + CreateDateTimeEdit(label, load_func, managed, true, other_setting); + break; case RequestType::SpinBox: + CreateSpinBox(label, load_func, managed, string, other_setting); + break; case RequestType::HexEdit: - case RequestType::MaxEnum: - LOG_DEBUG(Frontend, "Requested widget is unimplemented."); + CreateHexEdit(label, load_func, managed, other_setting); + break; + default: + LOG_WARNING(Frontend, "Requested widget is unimplemented."); break; } } else if (type == typeid(std::string)) { - CreateLineEdit(label, managed, load_func); + CreateLineEdit(label, load_func, managed); } if (!created) { diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 9923aa2ea..c4e686574 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -9,6 +9,8 @@ class QComboBox; class QLineEdit; class QSlider; class QCheckBox; +class QLabel; +class QHBoxLayout; class QDateTimeEdit; namespace Settings { @@ -34,9 +36,11 @@ class Widget : public QWidget { public: Widget(Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, - bool runtime_lock, std::forward_list>& apply_funcs, + bool runtime_lock, std::forward_list>& apply_funcs_, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, Settings::BasicSetting* other_setting = nullptr, const std::string& format = ""); + Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, QWidget* parent_, + std::forward_list>& apply_funcs_); virtual ~Widget(); bool Valid(); @@ -53,23 +57,28 @@ public: QDateTimeEdit* date_time_edit{}; private: - void CreateCheckBox(const QString& label, std::function& load_func); - void CreateCheckBoxWithLineEdit(const QString& label, Settings::BasicSetting* other_setting, - std::function& load_func); - void CreateCheckBoxWithHexEdit(const QString& label, Settings::BasicSetting* other_setting, - std::function& load_func); - void CreateCheckBoxWithSpinBox(const QString& label, Settings::BasicSetting* other_setting, - std::function& load_func, const std::string& suffix); - void CreateCheckBoxWithDateTimeEdit(const QString& label, Settings::BasicSetting* other_setting, - std::function& load_func); - void CreateCombobox(const QString& label, bool managed, std::function& load_func); - void CreateLineEdit(const QString& label, bool managed, std::function& load_func); + QLabel* CreateLabel(const QString& text); + QHBoxLayout* CreateCheckBox(Settings::BasicSetting* bool_setting, const QString& label, + std::function& load_func, bool managed); + + void CreateCombobox(const QString& label, std::function& load_func, bool managed, + Settings::BasicSetting* const other_setting = nullptr); + void CreateLineEdit(const QString& label, std::function& load_func, bool managed, + Settings::BasicSetting* const other_setting = nullptr); + void CreateHexEdit(const QString& label, std::function& load_func, bool managed, + Settings::BasicSetting* const other_setting = nullptr); void CreateSlider(const QString& label, bool reversed, float multiplier, - std::function& load_func); + std::function& load_func, bool managed, + Settings::BasicSetting* const other_setting = nullptr); + void CreateDateTimeEdit(const QString& label, std::function& load_func, bool managed, + bool restrict, Settings::BasicSetting* const other_setting = nullptr); + void CreateSpinBox(const QString& label, std::function& load_func, bool managed, + const std::string& suffix, Settings::BasicSetting* other_setting = nullptr); QWidget* parent; const TranslationMap& translations; Settings::BasicSetting& setting; + std::forward_list>& apply_funcs; bool created{false}; }; From f055f2dcf40580b6f1e9e0394ef401da5e332a75 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 16:07:48 -0400 Subject: [PATCH 043/155] shared_widget: Use a better icon This one looks more relevant on Windows. --- src/yuzu/configuration/shared_widget.cpp | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 3ef2c25c6..f39e3fccb 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -26,7 +26,7 @@ namespace ConfigurationShared { QPushButton* Widget::CreateRestoreGlobalButton(Settings::BasicSetting& setting, QWidget* parent) { QStyle* style = parent->style(); - QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_DialogResetButton)); + QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_LineEditClearButton)); QPushButton* restore_button = new QPushButton(*icon, QStringLiteral(""), parent); restore_button->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred); @@ -271,7 +271,7 @@ void Widget::CreateSlider(const QString& label, bool reversed, float multiplier, restore_button->setVisible(false); }); - QObject::connect(slider, &QAbstractSlider::sliderMoved, [=](int) { + QObject::connect(slider, &QAbstractSlider::valueChanged, [=]() { restore_button->setEnabled(true); restore_button->setVisible(true); }); @@ -461,8 +461,7 @@ void Widget::CreateDateTimeEdit(const QString& label, std::function& loa return; } - other_setting->LoadString( - std::to_string(date_time_edit->dateTime().toSecsSinceEpoch())); + setting.LoadString(std::to_string(date_time_edit->dateTime().toSecsSinceEpoch())); }; } else { if (!has_checkbox) { @@ -473,7 +472,7 @@ void Widget::CreateDateTimeEdit(const QString& label, std::function& loa auto get_clear_val = [=]() { return QDateTime::fromSecsSinceEpoch([=]() { if (restrict && checkbox->checkState() == Qt::Checked) { - return std::stoll(other_setting->ToStringGlobal()); + return std::stoll(setting.ToStringGlobal()); } return current_time; }()); @@ -498,8 +497,7 @@ void Widget::CreateDateTimeEdit(const QString& label, std::function& loa const bool using_global = !restore_button->isEnabled(); other_setting->SetGlobal(using_global); if (!using_global) { - other_setting->LoadString( - std::to_string(date_time_edit->dateTime().toSecsSinceEpoch())); + setting.LoadString(std::to_string(date_time_edit->dateTime().toSecsSinceEpoch())); } }; } From 88d3de4e85751b32faa577345a828994575d2eb1 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 6 Jun 2023 01:31:43 -0400 Subject: [PATCH 044/155] settings: Split enums to new file --- src/common/CMakeLists.txt | 1 + src/common/settings.h | 189 +--------------------------- src/common/settings_enums.h | 237 ++++++++++++++++++++++++++++++++++++ 3 files changed, 241 insertions(+), 186 deletions(-) create mode 100644 src/common/settings_enums.h diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt index 3adf13a3f..5902dd617 100644 --- a/src/common/CMakeLists.txt +++ b/src/common/CMakeLists.txt @@ -110,6 +110,7 @@ add_library(common STATIC scratch_buffer.h settings.cpp settings.h + settings_enums.h settings_input.cpp settings_input.h socket_types.h diff --git a/src/common/settings.h b/src/common/settings.h index 51708706b..0ac5078c6 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -16,194 +16,11 @@ #include #include "common/common_types.h" +#include "common/settings_enums.h" #include "common/settings_input.h" namespace Settings { -enum class Language : u32 { - Japanese, - EnglishAmerican, - French, - German, - Italian, - Spanish, - Chinese, - Korean, - Dutch, - Portuguese, - Russian, - Taiwanese, - EnglishBritish, - FrenchCanadian, - SpanishLatin, - ChineseSimplified, - ChineseTraditional, - PortugueseBrazilian, -}; - -enum class Region : u32 { - Japan, - USA, - Europe, - Australia, - China, - Korea, - Taiwan, -}; - -enum class TimeZone : u32 { - Auto, - Default, - CET, - CST6CDT, - Cuba, - EET, - Egypt, - Eire, - EST, - EST5EDT, - GB, - GBEire, - GMT, - GMTPlusZero, - GMTMinusZero, - GMTZero, - Greenwich, - Hongkong, - HST, - Iceland, - Iran, - Israel, - Jamaica, - Japan, - Kwajalein, - Libya, - MET, - MST, - MST7MDT, - Navajo, - NZ, - NZCHAT, - Poland, - Portugal, - PRC, - PST8PDT, - ROC, - ROK, - Singapore, - Turkey, - UCT, - Universal, - UTC, - W_SU, - WET, - Zulu, -}; - -enum class AnisotropyMode : u32 { - Automatic = 0, - Default = 1, - X2 = 2, - X4 = 3, - X8 = 4, - X16 = 5, -}; - -enum class AstcDecodeMode : u32 { - CPU = 0, - GPU = 1, - CPUAsynchronous = 2, -}; - -enum class VSyncMode : u32 { - Immediate = 0, - Mailbox = 1, - FIFO = 2, - FIFORelaxed = 3, -}; - -enum class RendererBackend : u32 { - OpenGL = 0, - Vulkan = 1, - Null = 2, -}; - -enum class ShaderBackend : u32 { - GLSL = 0, - GLASM = 1, - SPIRV = 2, -}; - -enum class GPUAccuracy : u32 { - Normal = 0, - High = 1, - Extreme = 2, - MaxEnum = 3, -}; - -enum class CPUAccuracy : u32 { - Auto = 0, - Accurate = 1, - Unsafe = 2, - Paranoid = 3, -}; - -enum class FullscreenMode : u32 { - Borderless = 0, - Exclusive = 1, -}; - -enum class NvdecEmulation : u32 { - Off = 0, - CPU = 1, - GPU = 2, -}; - -enum class ResolutionSetup : u32 { - Res1_2X = 0, - Res3_4X = 1, - Res1X = 2, - Res3_2X = 3, - Res2X = 4, - Res3X = 5, - Res4X = 6, - Res5X = 7, - Res6X = 8, - Res7X = 9, - Res8X = 10, -}; - -enum class ScalingFilter : u32 { - NearestNeighbor = 0, - Bilinear = 1, - Bicubic = 2, - Gaussian = 3, - ScaleForce = 4, - Fsr = 5, - LastFilter = Fsr, -}; - -enum class AntiAliasing : u32 { - None = 0, - Fxaa = 1, - Smaa = 2, - LastAA = Smaa, -}; - -enum class AstcRecompression : u32 { - Uncompressed = 0, - Bc1 = 1, - Bc3 = 2, -}; - -enum class AspectRatio : u32 { - R16_9, - R4_3, - R21_9, - R16_10, - Stretch, -}; - enum class Category : u32 { Audio, Core, @@ -278,7 +95,7 @@ public: virtual std::string DefaultToString() const = 0; virtual bool Save() const = 0; virtual std::type_index TypeId() const = 0; - virtual bool IsEnum() const = 0; + virtual constexpr bool IsEnum() const = 0; virtual bool RuntimeModfiable() const = 0; virtual void SetGlobal(bool global) {} virtual constexpr u32 Id() const = 0; @@ -406,7 +223,7 @@ public: return runtime_modifiable; } - [[nodiscard]] bool IsEnum() const override { + [[nodiscard]] constexpr bool IsEnum() const override { return std::is_enum::value; } diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h new file mode 100644 index 000000000..f48fb7bd4 --- /dev/null +++ b/src/common/settings_enums.h @@ -0,0 +1,237 @@ +// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + +#pragma once + +#include +#include +#include +#include +#include "common/common_types.h" + +namespace Settings { + +enum class AudioEngine : u32 { + Auto, + Cubeb, + Sdl2, + Null, +}; + +enum class AudioMode : u32 { + Mono, + Stereo, + Surround, +}; + +enum class Language : u32 { + Japanese, + EnglishAmerican, + French, + German, + Italian, + Spanish, + Chinese, + Korean, + Dutch, + Portuguese, + Russian, + Taiwanese, + EnglishBritish, + FrenchCanadian, + SpanishLatin, + ChineseSimplified, + ChineseTraditional, + PortugueseBrazilian, +}; + +enum class Region : u32 { + Japan, + USA, + Europe, + Australia, + China, + Korea, + Taiwan, +}; + +enum class TimeZone : u32 { + Auto, + Default, + CET, + CST6CDT, + Cuba, + EET, + Egypt, + Eire, + EST, + EST5EDT, + GB, + GBEire, + GMT, + GMTPlusZero, + GMTMinusZero, + GMTZero, + Greenwich, + Hongkong, + HST, + Iceland, + Iran, + Israel, + Jamaica, + Japan, + Kwajalein, + Libya, + MET, + MST, + MST7MDT, + Navajo, + NZ, + NZCHAT, + Poland, + Portugal, + PRC, + PST8PDT, + ROC, + ROK, + Singapore, + Turkey, + UCT, + Universal, + UTC, + W_SU, + WET, + Zulu, +}; + +enum class AnisotropyMode : u32 { + Automatic = 0, + Default = 1, + X2 = 2, + X4 = 3, + X8 = 4, + X16 = 5, +}; + +enum class AstcDecodeMode : u32 { + CPU = 0, + GPU = 1, + CPUAsynchronous = 2, +}; + +enum class AstcRecompression : u32 { + Uncompressed = 0, + Bc1 = 1, + Bc3 = 2, +}; + +enum class VSyncMode : u32 { + Immediate = 0, + Mailbox = 1, + FIFO = 2, + FIFORelaxed = 3, +}; + +enum class RendererBackend : u32 { + OpenGL = 0, + Vulkan = 1, + Null = 2, +}; + +enum class ShaderBackend : u32 { + GLSL = 0, + GLASM = 1, + SPIRV = 2, +}; + +enum class GPUAccuracy : u32 { + Normal = 0, + High = 1, + Extreme = 2, + MaxEnum = 3, +}; + +enum class CPUAccuracy : u32 { + Auto = 0, + Accurate = 1, + Unsafe = 2, + Paranoid = 3, +}; + +enum class FullscreenMode : u32 { + Borderless = 0, + Exclusive = 1, +}; + +enum class NvdecEmulation : u32 { + Off = 0, + CPU = 1, + GPU = 2, +}; + +enum class ResolutionSetup : u32 { + Res1_2X = 0, + Res3_4X = 1, + Res1X = 2, + Res3_2X = 3, + Res2X = 4, + Res3X = 5, + Res4X = 6, + Res5X = 7, + Res6X = 8, + Res7X = 9, + Res8X = 10, +}; + +enum class ScalingFilter : u32 { + NearestNeighbor = 0, + Bilinear = 1, + Bicubic = 2, + Gaussian = 3, + ScaleForce = 4, + Fsr = 5, + LastFilter = Fsr, +}; + +enum class AntiAliasing : u32 { + None = 0, + Fxaa = 1, + Smaa = 2, + LastAA = Smaa, +}; + +enum class AspectRatio : u32 { + R16_9, + R4_3, + R21_9, + R16_10, + Stretch, +}; + +static std::map> translations = { + {typeid(AudioEngine), + { + {"auto", static_cast(AudioEngine::Auto)}, + {"cubeb", static_cast(AudioEngine::Cubeb)}, + {"sdl2", static_cast(AudioEngine::Sdl2)}, + {"null", static_cast(AudioEngine::Null)}, + }}}; + +static std::string empty_string{}; + +template +const std::string& TranslateEnum(Type id) { + auto& group = translations.at(typeid(Type)); + for (auto& [name, value] : group) { + if (static_cast(value) == id) { + return name; + } + } + return empty_string; +} + +template +static Type ToEnum(const std::string& text) { + return static_cast(translations.at(typeid(Type)).at(text)); +} +} // namespace Settings From 432f68ad29df7a368ba375d75d667c954e9c80b9 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 17:54:22 -0400 Subject: [PATCH 045/155] configure_audio: Implement ui generation Needs a considerable amount of management specific to some of the comoboboxes due to the audio engine configuration. general: Partial audio config implmentation configure_audio: Implement ui generation Needs a considerable amount of management specific to some of the comoboboxes due to the audio engine configuration. general: Partial audio config implmentation settings: Make audio settings as enums --- src/audio_core/sink/sink_details.cpp | 33 +-- src/audio_core/sink/sink_details.h | 9 +- src/common/settings.cpp | 2 +- src/common/settings.h | 11 +- src/core/telemetry_session.cpp | 3 +- src/yuzu/configuration/configure_audio.cpp | 208 +++++++++--------- src/yuzu/configuration/configure_audio.h | 16 +- src/yuzu/configuration/configure_audio.ui | 162 +------------- src/yuzu/configuration/configure_dialog.cpp | 2 +- src/yuzu/configuration/configure_graphics.cpp | 8 +- src/yuzu/configuration/configure_per_game.cpp | 2 +- src/yuzu/configuration/shared_translation.cpp | 7 + src/yuzu/configuration/shared_widget.cpp | 78 ++++--- src/yuzu/configuration/shared_widget.h | 11 +- 14 files changed, 221 insertions(+), 331 deletions(-) diff --git a/src/audio_core/sink/sink_details.cpp b/src/audio_core/sink/sink_details.cpp index 39ea6d91b..751e97bfc 100644 --- a/src/audio_core/sink/sink_details.cpp +++ b/src/audio_core/sink/sink_details.cpp @@ -15,6 +15,7 @@ #endif #include "audio_core/sink/null_sink.h" #include "common/logging/log.h" +#include "common/settings_enums.h" namespace AudioCore::Sink { namespace { @@ -24,7 +25,7 @@ struct SinkDetails { using LatencyFn = u32 (*)(); /// Name for this sink. - std::string_view id; + Settings::AudioEngine id; /// A method to call to construct an instance of this type of sink. FactoryFn factory; /// A method to call to list available devices. @@ -37,7 +38,7 @@ struct SinkDetails { constexpr SinkDetails sink_details[] = { #ifdef HAVE_CUBEB SinkDetails{ - "cubeb", + Settings::AudioEngine::Cubeb, [](std::string_view device_id) -> std::unique_ptr { return std::make_unique(device_id); }, @@ -47,7 +48,7 @@ constexpr SinkDetails sink_details[] = { #endif #ifdef HAVE_SDL2 SinkDetails{ - "sdl2", + Settings::AudioEngine::Sdl2, [](std::string_view device_id) -> std::unique_ptr { return std::make_unique(device_id); }, @@ -55,46 +56,46 @@ constexpr SinkDetails sink_details[] = { &GetSDLLatency, }, #endif - SinkDetails{"null", + SinkDetails{Settings::AudioEngine::Null, [](std::string_view device_id) -> std::unique_ptr { return std::make_unique(device_id); }, [](bool capture) { return std::vector{"null"}; }, []() { return 0u; }}, }; -const SinkDetails& GetOutputSinkDetails(std::string_view sink_id) { - const auto find_backend{[](std::string_view id) { +const SinkDetails& GetOutputSinkDetails(Settings::AudioEngine sink_id) { + const auto find_backend{[](Settings::AudioEngine id) { return std::find_if(std::begin(sink_details), std::end(sink_details), [&id](const auto& sink_detail) { return sink_detail.id == id; }); }}; auto iter = find_backend(sink_id); - if (sink_id == "auto") { + if (sink_id == Settings::AudioEngine::Auto) { // Auto-select a backend. Prefer CubeB, but it may report a large minimum latency which // causes audio issues, in that case go with SDL. #if defined(HAVE_CUBEB) && defined(HAVE_SDL2) - iter = find_backend("cubeb"); + iter = find_backend(Settings::AudioEngine::Cubeb); if (iter->latency() > TargetSampleCount * 3) { - iter = find_backend("sdl2"); + iter = find_backend(Settings::AudioEngine::Sdl2); } #else iter = std::begin(sink_details); #endif - LOG_INFO(Service_Audio, "Auto-selecting the {} backend", iter->id); + LOG_INFO(Service_Audio, "Auto-selecting the {} backend", Settings::TranslateEnum(iter->id)); } if (iter == std::end(sink_details)) { - LOG_ERROR(Audio, "Invalid sink_id {}", sink_id); - iter = find_backend("null"); + LOG_ERROR(Audio, "Invalid sink_id {}", Settings::TranslateEnum(sink_id)); + iter = find_backend(Settings::AudioEngine::Null); } return *iter; } } // Anonymous namespace -std::vector GetSinkIDs() { - std::vector sink_ids(std::size(sink_details)); +std::vector GetSinkIDs() { + std::vector sink_ids(std::size(sink_details)); std::transform(std::begin(sink_details), std::end(sink_details), std::begin(sink_ids), [](const auto& sink) { return sink.id; }); @@ -102,11 +103,11 @@ std::vector GetSinkIDs() { return sink_ids; } -std::vector GetDeviceListForSink(std::string_view sink_id, bool capture) { +std::vector GetDeviceListForSink(Settings::AudioEngine sink_id, bool capture) { return GetOutputSinkDetails(sink_id).list_devices(capture); } -std::unique_ptr CreateSinkFromID(std::string_view sink_id, std::string_view device_id) { +std::unique_ptr CreateSinkFromID(Settings::AudioEngine sink_id, std::string_view device_id) { return GetOutputSinkDetails(sink_id).factory(device_id); } diff --git a/src/audio_core/sink/sink_details.h b/src/audio_core/sink/sink_details.h index e75932898..44403db71 100644 --- a/src/audio_core/sink/sink_details.h +++ b/src/audio_core/sink/sink_details.h @@ -7,6 +7,9 @@ #include #include +namespace Settings { +enum class AudioEngine : u32; +} namespace AudioCore { class AudioManager; @@ -19,7 +22,7 @@ class Sink; * * @return Vector of available sink names. */ -std::vector GetSinkIDs(); +std::vector GetSinkIDs(); /** * Gets the list of devices for a particular sink identified by the given ID. @@ -28,7 +31,7 @@ std::vector GetSinkIDs(); * @param capture - Get capture (input) devices, or output devices? * @return Vector of device names. */ -std::vector GetDeviceListForSink(std::string_view sink_id, bool capture); +std::vector GetDeviceListForSink(Settings::AudioEngine sink_id, bool capture); /** * Creates an audio sink identified by the given device ID. @@ -37,7 +40,7 @@ std::vector GetDeviceListForSink(std::string_view sink_id, bool cap * @param device_id - Name of the device to create. * @return Pointer to the created sink. */ -std::unique_ptr CreateSinkFromID(std::string_view sink_id, std::string_view device_id); +std::unique_ptr CreateSinkFromID(Settings::AudioEngine sink_id, std::string_view device_id); } // namespace Sink } // namespace AudioCore diff --git a/src/common/settings.cpp b/src/common/settings.cpp index c8651925e..8bfda5667 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -90,7 +90,7 @@ void LogSettings() { log_setting("Renderer_ShaderBackend", values.shader_backend.GetValue()); log_setting("Renderer_UseAsynchronousShaders", values.use_asynchronous_shaders.GetValue()); log_setting("Renderer_AnisotropicFilteringLevel", values.max_anisotropy.GetValue()); - log_setting("Audio_OutputEngine", values.sink_id.GetValue()); + log_setting("Audio_OutputEngine", Settings::TranslateEnum(values.sink_id.GetValue())); log_setting("Audio_OutputDevice", values.audio_output_device_id.GetValue()); log_setting("Audio_InputDevice", values.audio_input_device_id.GetValue()); log_setting("DataStorage_UseVirtualSd", values.use_virtual_sd.GetValue()); diff --git a/src/common/settings.h b/src/common/settings.h index 0ac5078c6..d4b41a162 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -244,6 +244,8 @@ protected: return value_.has_value() ? std::to_string(*value_) : "none"; } else if constexpr (std::is_same()) { return value_ ? "true" : "false"; + } else if (std::is_same()) { + return TranslateEnum(value_); } else { return std::to_string(static_cast(value_)); } @@ -309,6 +311,8 @@ public: this->SetValue(static_cast(std::stoul(input))); } else if constexpr (std::is_same()) { this->SetValue(input == "true"); + } else if constexpr (std::is_same()) { + this->SetValue(ToEnum(input)); } else { this->SetValue(static_cast(std::stoll(input))); } @@ -542,7 +546,7 @@ struct Values { Linkage linkage{}; // Audio - Setting sink_id{linkage, "auto", "output_engine", Category::Audio}; + Setting sink_id{linkage, AudioEngine::Auto, "output_engine", Category::Audio}; Setting audio_output_device_id{linkage, "auto", "output_device", Category::Audio}; Setting audio_input_device_id{linkage, "auto", "input_device", Category::Audio}; Setting audio_muted{linkage, false, "audio_muted", Category::Audio, false}; @@ -731,8 +735,9 @@ struct Values { SwitchableSetting time_zone_index{linkage, TimeZone::Auto, TimeZone::Auto, TimeZone::Zulu, "time_zone_index", Category::System}; - SwitchableSetting sound_index{ - linkage, 1, 0, 2, "sound_index", Category::SystemAudio}; + SwitchableSetting sound_index{linkage, AudioMode::Stereo, + AudioMode::Mono, AudioMode::Surround, + "sound_index", Category::SystemAudio}; SwitchableSetting use_docked_mode{linkage, true, "use_docked_mode", Category::System}; diff --git a/src/core/telemetry_session.cpp b/src/core/telemetry_session.cpp index a3505a505..c058ac2c7 100644 --- a/src/core/telemetry_session.cpp +++ b/src/core/telemetry_session.cpp @@ -254,7 +254,8 @@ void TelemetrySession::AddInitialInfo(Loader::AppLoader& app_loader, // Log user configuration information constexpr auto field_type = Telemetry::FieldType::UserConfig; - AddField(field_type, "Audio_SinkId", Settings::values.sink_id.GetValue()); + AddField(field_type, "Audio_SinkId", + Settings::TranslateEnum(Settings::values.sink_id.GetValue())); AddField(field_type, "Core_UseMultiCore", Settings::values.use_multi_core.GetValue()); AddField(field_type, "Renderer_Backend", TranslateRenderer(Settings::values.renderer_backend.GetValue())); diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 335662144..dd9eb4dc1 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -1,6 +1,7 @@ // SPDX-FileCopyrightText: Copyright 2018 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#include #include #include "audio_core/sink/sink.h" @@ -10,80 +11,105 @@ #include "ui_configure_audio.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_audio.h" +#include "yuzu/configuration/shared_translation.h" +#include "yuzu/configuration/shared_widget.h" #include "yuzu/uisettings.h" ConfigureAudio::ConfigureAudio(const Core::System& system_, std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, QWidget* parent) - : Tab(group, parent), ui(std::make_unique()), system{system_} { + : Tab(group, parent), + ui(std::make_unique()), system{system_}, translations{translations_} { ui->setupUi(this); - - InitializeAudioSinkComboBox(); - - connect(ui->volume_slider, &QSlider::valueChanged, this, - &ConfigureAudio::SetVolumeIndicatorText); - connect(ui->sink_combo_box, qOverload(&QComboBox::currentIndexChanged), this, - &ConfigureAudio::UpdateAudioDevices); - - ui->volume_label->setVisible(Settings::IsConfiguringGlobal()); - ui->volume_combo_box->setVisible(!Settings::IsConfiguringGlobal()); - - SetupPerGameUI(); + Setup(); SetConfiguration(); - - const bool is_powered_on = system_.IsPoweredOn(); - ui->sink_combo_box->setEnabled(!is_powered_on); - ui->output_combo_box->setEnabled(!is_powered_on); - ui->input_combo_box->setEnabled(!is_powered_on); } ConfigureAudio::~ConfigureAudio() = default; +void ConfigureAudio::Setup() { + const bool runtime_lock = !system.IsPoweredOn(); + auto& layout = *ui->audio_widget->layout(); + + std::forward_list settings; + + auto push = [&](Settings::Category category) { + for (auto* setting : Settings::values.linkage.by_category[category]) { + settings.push_front(setting); + } + }; + + push(Settings::Category::Audio); + push(Settings::Category::SystemAudio); + + for (auto* setting : settings) { + auto* widget = [&]() { + if (setting->Id() == Settings::values.volume.Id()) { + return new ConfigurationShared::Widget( + setting, translations, this, runtime_lock, apply_funcs, + ConfigurationShared::RequestType::Slider, true, 1.0f, nullptr, + tr("%1%", "Volume percentage (e.g. 50%)")); + } else if (setting->Id() == Settings::values.audio_output_device_id.Id() || + setting->Id() == Settings::values.audio_input_device_id.Id() || + setting->Id() == Settings::values.sink_id.Id()) { + return new ConfigurationShared::Widget( + setting, translations, this, runtime_lock, apply_funcs, + ConfigurationShared::RequestType::ComboBox, false); + } else { + return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, + apply_funcs); + } + }(); + + if (!widget->Valid()) { + delete widget; + continue; + } + + layout.addWidget(widget); + + if (setting->Id() == Settings::values.sink_id.Id()) { + sink_combo_box = widget->combobox; + InitializeAudioSinkComboBox(); + + connect(sink_combo_box, qOverload(&QComboBox::currentIndexChanged), this, + &ConfigureAudio::UpdateAudioDevices); + } else if (setting->Id() == Settings::values.audio_output_device_id.Id()) { + output_device_combo_box = widget->combobox; + } else if (setting->Id() == Settings::values.audio_input_device_id.Id()) { + input_device_combo_box = widget->combobox; + } + } +} + void ConfigureAudio::SetConfiguration() { + if (!Settings::IsConfiguringGlobal()) { + return; + } + SetOutputSinkFromSinkID(); // The device list cannot be pre-populated (nor listed) until the output sink is known. - UpdateAudioDevices(ui->sink_combo_box->currentIndex()); + UpdateAudioDevices(sink_combo_box->currentIndex()); SetAudioDevicesFromDeviceID(); - - const auto volume_value = static_cast(Settings::values.volume.GetValue()); - ui->volume_slider->setValue(volume_value); - ui->toggle_background_mute->setChecked(UISettings::values.mute_when_in_background.GetValue()); - - if (!Settings::IsConfiguringGlobal()) { - if (Settings::values.volume.UsingGlobal()) { - ui->volume_combo_box->setCurrentIndex(0); - ui->volume_slider->setEnabled(false); - } else { - ui->volume_combo_box->setCurrentIndex(1); - ui->volume_slider->setEnabled(true); - } - ConfigurationShared::SetPerGameSetting(ui->combo_sound, &Settings::values.sound_index); - ConfigurationShared::SetHighlight(ui->mode_label, - !Settings::values.sound_index.UsingGlobal()); - ConfigurationShared::SetHighlight(ui->volume_layout, - !Settings::values.volume.UsingGlobal()); - } else { - ui->combo_sound->setCurrentIndex(Settings::values.sound_index.GetValue()); - } - SetVolumeIndicatorText(ui->volume_slider->sliderPosition()); } void ConfigureAudio::SetOutputSinkFromSinkID() { - [[maybe_unused]] const QSignalBlocker blocker(ui->sink_combo_box); + [[maybe_unused]] const QSignalBlocker blocker(sink_combo_box); int new_sink_index = 0; - const QString sink_id = QString::fromStdString(Settings::values.sink_id.GetValue()); - for (int index = 0; index < ui->sink_combo_box->count(); index++) { - if (ui->sink_combo_box->itemText(index) == sink_id) { + const QString sink_id = QString::fromStdString(Settings::values.sink_id.ToString()); + for (int index = 0; index < sink_combo_box->count(); index++) { + if (sink_combo_box->itemText(index) == sink_id) { new_sink_index = index; break; } } - ui->sink_combo_box->setCurrentIndex(new_sink_index); + sink_combo_box->setCurrentIndex(new_sink_index); } void ConfigureAudio::SetAudioDevicesFromDeviceID() { @@ -91,57 +117,42 @@ void ConfigureAudio::SetAudioDevicesFromDeviceID() { const QString output_device_id = QString::fromStdString(Settings::values.audio_output_device_id.GetValue()); - for (int index = 0; index < ui->output_combo_box->count(); index++) { - if (ui->output_combo_box->itemText(index) == output_device_id) { + for (int index = 0; index < output_device_combo_box->count(); index++) { + if (output_device_combo_box->itemText(index) == output_device_id) { new_device_index = index; break; } } - ui->output_combo_box->setCurrentIndex(new_device_index); + output_device_combo_box->setCurrentIndex(new_device_index); new_device_index = -1; const QString input_device_id = QString::fromStdString(Settings::values.audio_input_device_id.GetValue()); - for (int index = 0; index < ui->input_combo_box->count(); index++) { - if (ui->input_combo_box->itemText(index) == input_device_id) { + for (int index = 0; index < input_device_combo_box->count(); index++) { + if (input_device_combo_box->itemText(index) == input_device_id) { new_device_index = index; break; } } - ui->input_combo_box->setCurrentIndex(new_device_index); -} - -void ConfigureAudio::SetVolumeIndicatorText(int percentage) { - ui->volume_indicator->setText(tr("%1%", "Volume percentage (e.g. 50%)").arg(percentage)); + input_device_combo_box->setCurrentIndex(new_device_index); } void ConfigureAudio::ApplyConfiguration() { - ConfigurationShared::ApplyPerGameSetting(&Settings::values.sound_index, ui->combo_sound); + const bool is_powered_on = system.IsPoweredOn(); + for (const auto& apply_func : apply_funcs) { + apply_func(is_powered_on); + } if (Settings::IsConfiguringGlobal()) { - Settings::values.sink_id = - ui->sink_combo_box->itemText(ui->sink_combo_box->currentIndex()).toStdString(); + Settings::values.sink_id.LoadString( + sink_combo_box->itemText(sink_combo_box->currentIndex()).toStdString()); Settings::values.audio_output_device_id.SetValue( - ui->output_combo_box->itemText(ui->output_combo_box->currentIndex()).toStdString()); + output_device_combo_box->itemText(output_device_combo_box->currentIndex()) + .toStdString()); Settings::values.audio_input_device_id.SetValue( - ui->input_combo_box->itemText(ui->input_combo_box->currentIndex()).toStdString()); - UISettings::values.mute_when_in_background = ui->toggle_background_mute->isChecked(); - - // Guard if during game and set to game-specific value - if (Settings::values.volume.UsingGlobal()) { - const auto volume = static_cast(ui->volume_slider->value()); - Settings::values.volume.SetValue(volume); - } - } else { - if (ui->volume_combo_box->currentIndex() == 0) { - Settings::values.volume.SetGlobal(true); - } else { - Settings::values.volume.SetGlobal(false); - const auto volume = static_cast(ui->volume_slider->value()); - Settings::values.volume.SetValue(volume); - } + input_device_combo_box->itemText(input_device_combo_box->currentIndex()).toStdString()); } } @@ -154,54 +165,31 @@ void ConfigureAudio::changeEvent(QEvent* event) { } void ConfigureAudio::UpdateAudioDevices(int sink_index) { - ui->output_combo_box->clear(); - ui->output_combo_box->addItem(QString::fromUtf8(AudioCore::Sink::auto_device_name)); + output_device_combo_box->clear(); + output_device_combo_box->addItem(QString::fromUtf8(AudioCore::Sink::auto_device_name)); - const std::string sink_id = ui->sink_combo_box->itemText(sink_index).toStdString(); + const auto sink_id = + Settings::ToEnum(sink_combo_box->itemText(sink_index).toStdString()); for (const auto& device : AudioCore::Sink::GetDeviceListForSink(sink_id, false)) { - ui->output_combo_box->addItem(QString::fromStdString(device)); + output_device_combo_box->addItem(QString::fromStdString(device)); } - ui->input_combo_box->clear(); - ui->input_combo_box->addItem(QString::fromUtf8(AudioCore::Sink::auto_device_name)); + input_device_combo_box->clear(); + input_device_combo_box->addItem(QString::fromUtf8(AudioCore::Sink::auto_device_name)); for (const auto& device : AudioCore::Sink::GetDeviceListForSink(sink_id, true)) { - ui->input_combo_box->addItem(QString::fromStdString(device)); + input_device_combo_box->addItem(QString::fromStdString(device)); } } void ConfigureAudio::InitializeAudioSinkComboBox() { - ui->sink_combo_box->clear(); - ui->sink_combo_box->addItem(QString::fromUtf8(AudioCore::Sink::auto_device_name)); + sink_combo_box->clear(); + sink_combo_box->addItem(QString::fromUtf8(AudioCore::Sink::auto_device_name)); for (const auto& id : AudioCore::Sink::GetSinkIDs()) { - ui->sink_combo_box->addItem(QString::fromUtf8(id.data(), static_cast(id.length()))); + sink_combo_box->addItem(QString::fromStdString(Settings::TranslateEnum(id))); } } void ConfigureAudio::RetranslateUI() { ui->retranslateUi(this); - SetVolumeIndicatorText(ui->volume_slider->sliderPosition()); -} - -void ConfigureAudio::SetupPerGameUI() { - if (Settings::IsConfiguringGlobal()) { - ui->combo_sound->setEnabled(Settings::values.sound_index.UsingGlobal()); - ui->volume_slider->setEnabled(Settings::values.volume.UsingGlobal()); - return; - } - - ConfigurationShared::SetColoredComboBox(ui->combo_sound, ui->mode_label, - Settings::values.sound_index.GetValue(true)); - - connect(ui->volume_combo_box, qOverload(&QComboBox::activated), this, [this](int index) { - ui->volume_slider->setEnabled(index == 1); - ConfigurationShared::SetHighlight(ui->volume_layout, index == 1); - }); - - ui->sink_combo_box->setVisible(false); - ui->sink_label->setVisible(false); - ui->output_combo_box->setVisible(false); - ui->output_label->setVisible(false); - ui->input_combo_box->setVisible(false); - ui->input_label->setVisible(false); } diff --git a/src/yuzu/configuration/configure_audio.h b/src/yuzu/configuration/configure_audio.h index d134ac957..170e0bce8 100644 --- a/src/yuzu/configuration/configure_audio.h +++ b/src/yuzu/configuration/configure_audio.h @@ -3,9 +3,14 @@ #pragma once +#include +#include #include #include #include "yuzu/configuration/configuration_shared.h" +#include "yuzu/configuration/shared_translation.h" + +class QPushButton; namespace Core { class System; @@ -19,6 +24,7 @@ class ConfigureAudio : public ConfigurationShared::Tab { public: explicit ConfigureAudio(const Core::System& system_, std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, QWidget* parent = nullptr); ~ConfigureAudio() override; @@ -36,11 +42,17 @@ private: void SetOutputSinkFromSinkID(); void SetAudioDevicesFromDeviceID(); - void SetVolumeIndicatorText(int percentage); - void SetupPerGameUI(); + void Setup(); std::unique_ptr ui; const Core::System& system; + const ConfigurationShared::TranslationMap& translations; + + std::forward_list> apply_funcs{}; + + QComboBox* sink_combo_box; + QComboBox* output_device_combo_box; + QComboBox* input_device_combo_box; }; diff --git a/src/yuzu/configuration/configure_audio.ui b/src/yuzu/configuration/configure_audio.ui index 4128c83ad..1181aeb00 100644 --- a/src/yuzu/configuration/configure_audio.ui +++ b/src/yuzu/configuration/configure_audio.ui @@ -21,80 +21,14 @@ - - - - - Output Engine: - - - - - - - - - - - - - - Output Device: - - - - - - - - - - - - - - Input Device: - - - - - - - - - - - - - - Sound Output Mode: - - - - - - - - Mono - - - - - Stereo - - - - - Surround - - - - - - - - - + + + + 16777215 + 16777213 + + + 0 @@ -107,89 +41,9 @@ 0 - - - - - Use global volume - - - - - Set volume: - - - - - - - - Volume: - - - - - - - Qt::Horizontal - - - - 30 - 20 - - - - - - - - - 0 - 0 - - - - 200 - - - 5 - - - Qt::Horizontal - - - - - - - - 32 - 0 - - - - 0 % - - - Qt::AlignCenter - - - - - - - - - Mute audio when in background - - - - - diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index 3a94fee9e..f0f00be83 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -34,7 +34,7 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, : QDialog(parent), ui{std::make_unique()}, registry(registry_), system{system_}, translations{ConfigurationShared::InitializeTranslations(this)}, - audio_tab{std::make_unique(system_, nullptr, this)}, + audio_tab{std::make_unique(system_, nullptr, *translations, this)}, cpu_tab{std::make_unique(system_, nullptr, this)}, debug_tab_tab{std::make_unique(system_, this)}, filesystem_tab{std::make_unique(this)}, diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 2354323b8..45a4db430 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -240,12 +240,14 @@ void ConfigureGraphics::Setup() { } else if (setting->Id() == Settings::values.fsr_sharpening_slider.Id()) { return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::ReverseSlider, true, 0.5f); + ConfigurationShared::RequestType::ReverseSlider, true, 0.5f, nullptr, + tr("%1%", "FSR sharpening percentage (e.g. 50%)")); } else if (setting->Id() == Settings::values.speed_limit.Id()) { return new ConfigurationShared::Widget( setting, translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::SpinBox, true, 1.0f, - &Settings::values.use_speed_limit, "%"); + &Settings::values.use_speed_limit, + tr("%", "Limit speed percentage (e.g. 50%)")); } else { return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); @@ -304,7 +306,7 @@ void ConfigureGraphics::Setup() { }); } else { QPushButton* bg_restore_button = ConfigurationShared::Widget::CreateRestoreGlobalButton( - Settings::values.bg_red, ui->bg_widget); + Settings::values.bg_red.UsingGlobal(), ui->bg_widget); ui->bg_widget->layout()->addWidget(bg_restore_button); QObject::connect(bg_restore_button, &QAbstractButton::clicked, diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index c39855334..2ee0a8ffa 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -50,7 +50,7 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st game_config = std::make_unique(config_file_name, Config::ConfigType::PerGameConfig); addons_tab = std::make_unique(system_, this); - audio_tab = std::make_unique(system_, tab_group, this); + audio_tab = std::make_unique(system_, tab_group, *translations, this); cpu_tab = std::make_unique(system_, tab_group, this); graphics_advanced_tab = std::make_unique(system_, tab_group, *translations, this); diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 6038e8c25..c3b38f776 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -30,6 +30,7 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(Settings, audio_input_device_id, "Input Device:", ""); INSERT(Settings, audio_muted, "Mute audio when in background", ""); INSERT(Settings, volume, "Volume:", ""); + INSERT(Settings, dump_audio_commands, "", ""); // Core INSERT(Settings, use_multi_core, "Multicore CPU Emulation", ""); @@ -270,6 +271,12 @@ std::forward_list ComboboxEnumeration(std::type_index type, QWidget* pa tr("ROC"), tr("ROK"), tr("Singapore"), tr("Turkey"), tr("UCT"), tr("W-SU"), tr("WET"), tr("Zulu"), }; + } else if (type == typeid(Settings::AudioMode)) { + return { + tr("Mono"), + tr("Stereo"), + tr("Surround"), + }; } return {}; diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index f39e3fccb..d7b7ed164 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -24,7 +24,7 @@ namespace ConfigurationShared { -QPushButton* Widget::CreateRestoreGlobalButton(Settings::BasicSetting& setting, QWidget* parent) { +QPushButton* Widget::CreateRestoreGlobalButton(bool using_global, QWidget* parent) { QStyle* style = parent->style(); QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_LineEditClearButton)); QPushButton* restore_button = new QPushButton(*icon, QStringLiteral(""), parent); @@ -34,8 +34,8 @@ QPushButton* Widget::CreateRestoreGlobalButton(Settings::BasicSetting& setting, sp_retain.setRetainSizeWhenHidden(true); restore_button->setSizePolicy(sp_retain); - restore_button->setEnabled(!setting.UsingGlobal()); - restore_button->setVisible(!setting.UsingGlobal()); + restore_button->setEnabled(!using_global); + restore_button->setVisible(!using_global); return restore_button; } @@ -57,6 +57,10 @@ QHBoxLayout* Widget::CreateCheckBox(Settings::BasicSetting* bool_setting, const : Qt::CheckState::Unchecked); checkbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + if (!bool_setting->Save() && !Settings::IsConfiguringGlobal() && runtime_lock) { + checkbox->setEnabled(false); + } + layout->addWidget(checkbox); layout->setContentsMargins(0, 0, 0, 0); @@ -70,7 +74,8 @@ QHBoxLayout* Widget::CreateCheckBox(Settings::BasicSetting* bool_setting, const bool_setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); }; } else { - restore_button = CreateRestoreGlobalButton(*bool_setting, this); + restore_button = + CreateRestoreGlobalButton(bool_setting->UsingGlobal() && setting.UsingGlobal(), this); layout->addWidget(restore_button); QObject::connect(checkbox, &QCheckBox::stateChanged, [=](int) { @@ -128,7 +133,7 @@ void Widget::CreateCombobox(const QString& label, std::function& load_fu if (Settings::IsConfiguringGlobal()) { load_func = [=]() { setting.LoadString(std::to_string(combobox->currentIndex())); }; } else { - restore_button = CreateRestoreGlobalButton(setting, this); + restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); layout->addWidget(restore_button); QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { @@ -194,7 +199,7 @@ void Widget::CreateLineEdit(const QString& label, std::function& load_fu }; } else { if (!has_checkbox) { - restore_button = CreateRestoreGlobalButton(setting, this); + restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); layout->addWidget(restore_button); } @@ -223,7 +228,7 @@ void Widget::CreateLineEdit(const QString& label, std::function& load_fu } void Widget::CreateSlider(const QString& label, bool reversed, float multiplier, - std::function& load_func, bool managed, + std::function& load_func, bool managed, const QString& format, Settings::BasicSetting* const other_setting) { created = true; @@ -242,15 +247,16 @@ void Widget::CreateSlider(const QString& label, bool reversed, float multiplier, int max_val = std::stoi(setting.MaxVal()); + const QString use_format = format == QStringLiteral("") ? QStringLiteral("%1") : format; + QObject::connect(slider, &QAbstractSlider::valueChanged, [=](int value) { - int present = (reversed ? max_val - value : value) * multiplier; - feedback->setText( - QStringLiteral("%1%").arg(QString::fromStdString(std::to_string(present)))); + int present = (reversed ? max_val - value : value) * multiplier + 0.5f; + feedback->setText(use_format.arg(QVariant::fromValue(present).value())); }); - slider->setValue(std::stoi(setting.ToString())); slider->setMinimum(std::stoi(setting.MinVal())); slider->setMaximum(max_val); + slider->setValue(std::stoi(setting.ToString())); slider->setInvertedAppearance(reversed); @@ -261,7 +267,7 @@ void Widget::CreateSlider(const QString& label, bool reversed, float multiplier, if (Settings::IsConfiguringGlobal()) { load_func = [=]() { setting.LoadString(std::to_string(slider->value())); }; } else { - restore_button = CreateRestoreGlobalButton(setting, this); + restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); layout->addWidget(restore_button); QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { @@ -287,7 +293,7 @@ void Widget::CreateSlider(const QString& label, bool reversed, float multiplier, } void Widget::CreateSpinBox(const QString& label, std::function& load_func, bool managed, - const std::string& suffix, Settings::BasicSetting* other_setting) { + const QString& suffix, Settings::BasicSetting* other_setting) { const bool has_checkbox = other_setting != nullptr; if (has_checkbox && other_setting->TypeId() != typeid(bool)) { LOG_WARNING(Frontend, "Extra setting requested but setting is not boolean"); @@ -315,7 +321,7 @@ void Widget::CreateSpinBox(const QString& label, std::function& load_fun spinbox = new QSpinBox(this); spinbox->setRange(min_val, max_val); spinbox->setValue(default_val); - spinbox->setSuffix(QString::fromStdString(suffix)); + spinbox->setSuffix(suffix); spinbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->insertWidget(1, spinbox); @@ -327,7 +333,8 @@ void Widget::CreateSpinBox(const QString& label, std::function& load_fun }; } else { if (!has_checkbox) { - restore_button = CreateRestoreGlobalButton(setting, this); + restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); + layout->addWidget(restore_button); } QObject::connect(restore_button, &QAbstractButton::clicked, @@ -382,7 +389,7 @@ void Widget::CreateHexEdit(const QString& label, std::function& load_fun setting.LoadString(hex_to_dec()); }; } else { - restore_button = CreateRestoreGlobalButton(setting, this); + restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); layout->addWidget(restore_button); QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { @@ -465,7 +472,7 @@ void Widget::CreateDateTimeEdit(const QString& label, std::function& loa }; } else { if (!has_checkbox) { - restore_button = CreateRestoreGlobalButton(setting, this); + restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); layout->addWidget(restore_button); } @@ -515,12 +522,12 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati apply_funcs{apply_funcs_} {} Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, - QWidget* parent_, bool runtime_lock, + QWidget* parent_, bool runtime_lock_, std::forward_list>& apply_funcs_, RequestType request, bool managed, float multiplier, Settings::BasicSetting* other_setting, - const std::string& string) + const QString& string) : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_}, - apply_funcs{apply_funcs_} { + apply_funcs{apply_funcs_}, runtime_lock{runtime_lock_} { if (!Settings::IsConfiguringGlobal() && !setting.Switchable()) { LOG_DEBUG(Frontend, "\"{}\" is not switchable, skipping...", setting.GetLabel()); return; @@ -547,23 +554,16 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati std::function load_func = []() {}; if (type == typeid(bool)) { - switch (request) { - case RequestType::Default: - CreateCheckBox(&setting, label, load_func, managed); - break; - default: - LOG_WARNING(Frontend, "Requested widget is unimplemented."); - break; - } + CreateCheckBox(&setting, label, load_func, managed); } else if (setting.IsEnum()) { CreateCombobox(label, load_func, managed); } else if (type == typeid(u32) || type == typeid(int) || type == typeid(u16) || - type == typeid(s64)) { + type == typeid(s64) || type == typeid(u8)) { switch (request) { case RequestType::Slider: case RequestType::ReverseSlider: CreateSlider(label, request == RequestType::ReverseSlider, multiplier, load_func, - managed); + managed, string); break; case RequestType::LineEdit: case RequestType::Default: @@ -586,7 +586,23 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati break; } } else if (type == typeid(std::string)) { - CreateLineEdit(label, load_func, managed); + switch (request) { + case RequestType::Default: + case RequestType::LineEdit: + CreateLineEdit(label, load_func, managed); + break; + case RequestType::ComboBox: + CreateCombobox(label, load_func, false); + break; + case RequestType::SpinBox: + case RequestType::Slider: + case RequestType::ReverseSlider: + case RequestType::HexEdit: + case RequestType::DateTimeEdit: + case RequestType::MaxEnum: + LOG_WARNING(Frontend, "Requested widget is unimplemented."); + break; + } } if (!created) { diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index c4e686574..331316040 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -38,15 +38,15 @@ public: Widget(Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, bool runtime_lock, std::forward_list>& apply_funcs_, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, - Settings::BasicSetting* other_setting = nullptr, const std::string& format = ""); + Settings::BasicSetting* other_setting = nullptr, + const QString& string = QStringLiteral("")); Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, QWidget* parent_, std::forward_list>& apply_funcs_); virtual ~Widget(); bool Valid(); - [[nodiscard]] static QPushButton* CreateRestoreGlobalButton(Settings::BasicSetting& setting, - QWidget* parent); + [[nodiscard]] static QPushButton* CreateRestoreGlobalButton(bool using_global, QWidget* parent); QPushButton* restore_button{}; QLineEdit* line_edit{}; @@ -68,12 +68,12 @@ private: void CreateHexEdit(const QString& label, std::function& load_func, bool managed, Settings::BasicSetting* const other_setting = nullptr); void CreateSlider(const QString& label, bool reversed, float multiplier, - std::function& load_func, bool managed, + std::function& load_func, bool managed, const QString& format, Settings::BasicSetting* const other_setting = nullptr); void CreateDateTimeEdit(const QString& label, std::function& load_func, bool managed, bool restrict, Settings::BasicSetting* const other_setting = nullptr); void CreateSpinBox(const QString& label, std::function& load_func, bool managed, - const std::string& suffix, Settings::BasicSetting* other_setting = nullptr); + const QString& suffix, Settings::BasicSetting* other_setting = nullptr); QWidget* parent; const TranslationMap& translations; @@ -81,6 +81,7 @@ private: std::forward_list>& apply_funcs; bool created{false}; + bool runtime_lock{false}; }; } // namespace ConfigurationShared From 86ed82cddefe7ec30393072db84791f9bb7dfc69 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 16:06:54 -0400 Subject: [PATCH 046/155] settings, shared_widget: typo fixes --- src/yuzu/configuration/shared_widget.cpp | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index d7b7ed164..4b21e5be8 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -124,12 +124,18 @@ void Widget::CreateCombobox(const QString& label, std::function& load_fu layout->setSpacing(6); layout->setContentsMargins(0, 0, 0, 0); - combobox->setCurrentIndex(std::stoi(setting.ToString())); - if (!managed) { return; } + // TODO: Remove audio engine specialization + if (setting.TypeId() != typeid(Settings::AudioEngine)) { + combobox->setCurrentIndex(std::stoi(setting.ToString())); + } else { + combobox->setCurrentIndex( + static_cast(Settings::ToEnum(setting.ToString()))); + } + if (Settings::IsConfiguringGlobal()) { load_func = [=]() { setting.LoadString(std::to_string(combobox->currentIndex())); }; } else { From c5a3642cb62b4676d0c8b98949daec20e7c02e6b Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 22:17:36 -0400 Subject: [PATCH 047/155] configuration: Use a mapping of setting value to name Makes comboboxes always correspond to the value of the setting they're modifying. --- src/yuzu/configuration/configure_audio.cpp | 21 +- src/yuzu/configuration/configure_audio.h | 11 +- src/yuzu/configuration/configure_dialog.cpp | 16 +- src/yuzu/configuration/configure_dialog.h | 1 + src/yuzu/configuration/configure_general.cpp | 9 +- src/yuzu/configuration/configure_general.h | 11 +- src/yuzu/configuration/configure_graphics.cpp | 45 ++- src/yuzu/configuration/configure_graphics.h | 17 +- .../configure_graphics_advanced.cpp | 9 +- .../configure_graphics_advanced.h | 5 +- src/yuzu/configuration/configure_per_game.cpp | 13 +- src/yuzu/configuration/configure_per_game.h | 1 + src/yuzu/configuration/configure_system.cpp | 14 +- src/yuzu/configuration/configure_system.h | 12 +- src/yuzu/configuration/shared_translation.cpp | 318 +++++++++++------- src/yuzu/configuration/shared_translation.h | 6 +- src/yuzu/configuration/shared_widget.cpp | 65 ++-- src/yuzu/configuration/shared_widget.h | 8 +- 18 files changed, 354 insertions(+), 228 deletions(-) diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index dd9eb4dc1..1cafeaa31 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -15,12 +15,13 @@ #include "yuzu/configuration/shared_widget.h" #include "yuzu/uisettings.h" -ConfigureAudio::ConfigureAudio(const Core::System& system_, - std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, - QWidget* parent) - : Tab(group, parent), - ui(std::make_unique()), system{system_}, translations{translations_} { +ConfigureAudio::ConfigureAudio( + const Core::System& system_, + std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) + : Tab(group, parent), ui(std::make_unique()), system{system_}, + translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); Setup(); @@ -48,18 +49,18 @@ void ConfigureAudio::Setup() { auto* widget = [&]() { if (setting->Id() == Settings::values.volume.Id()) { return new ConfigurationShared::Widget( - setting, translations, this, runtime_lock, apply_funcs, + setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::Slider, true, 1.0f, nullptr, tr("%1%", "Volume percentage (e.g. 50%)")); } else if (setting->Id() == Settings::values.audio_output_device_id.Id() || setting->Id() == Settings::values.audio_input_device_id.Id() || setting->Id() == Settings::values.sink_id.Id()) { return new ConfigurationShared::Widget( - setting, translations, this, runtime_lock, apply_funcs, + setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ComboBox, false); } else { - return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, - apply_funcs); + return new ConfigurationShared::Widget(setting, translations, combobox_translations, + this, runtime_lock, apply_funcs); } }(); diff --git a/src/yuzu/configuration/configure_audio.h b/src/yuzu/configuration/configure_audio.h index 170e0bce8..a9b005433 100644 --- a/src/yuzu/configuration/configure_audio.h +++ b/src/yuzu/configuration/configure_audio.h @@ -22,10 +22,12 @@ class ConfigureAudio; class ConfigureAudio : public ConfigurationShared::Tab { public: - explicit ConfigureAudio(const Core::System& system_, - std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, - QWidget* parent = nullptr); + explicit ConfigureAudio( + const Core::System& system_, + std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, + QWidget* parent = nullptr); ~ConfigureAudio() override; void ApplyConfiguration() override; @@ -49,6 +51,7 @@ private: const Core::System& system; const ConfigurationShared::TranslationMap& translations; + const ConfigurationShared::ComboboxTranslationMap& combobox_translations; std::forward_list> apply_funcs{}; diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index f0f00be83..1a339a227 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -34,21 +34,25 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, : QDialog(parent), ui{std::make_unique()}, registry(registry_), system{system_}, translations{ConfigurationShared::InitializeTranslations(this)}, - audio_tab{std::make_unique(system_, nullptr, *translations, this)}, + combobox_translations{ConfigurationShared::ComboboxEnumeration(this)}, + audio_tab{std::make_unique(system_, nullptr, *translations, + *combobox_translations, this)}, cpu_tab{std::make_unique(system_, nullptr, this)}, debug_tab_tab{std::make_unique(system_, this)}, filesystem_tab{std::make_unique(this)}, - general_tab{std::make_unique(system_, nullptr, *translations, this)}, - graphics_advanced_tab{ - std::make_unique(system_, nullptr, *translations, this)}, + general_tab{std::make_unique(system_, nullptr, *translations, + *combobox_translations, this)}, + graphics_advanced_tab{std::make_unique( + system_, nullptr, *translations, *combobox_translations, this)}, graphics_tab{std::make_unique( system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, - nullptr, *translations, this)}, + nullptr, *translations, *combobox_translations, this)}, hotkeys_tab{std::make_unique(system_.HIDCore(), this)}, input_tab{std::make_unique(system_, this)}, network_tab{std::make_unique(system_, this)}, profile_tab{std::make_unique(system_, this)}, - system_tab{std::make_unique(system_, nullptr, *translations, this)}, + system_tab{std::make_unique(system_, nullptr, *translations, + *combobox_translations, this)}, ui_tab{std::make_unique(system_, this)}, web_tab{std::make_unique( this)} { Settings::SetConfiguringGlobal(true); diff --git a/src/yuzu/configuration/configure_dialog.h b/src/yuzu/configuration/configure_dialog.h index 0416b01d9..4f8c1912f 100644 --- a/src/yuzu/configuration/configure_dialog.h +++ b/src/yuzu/configuration/configure_dialog.h @@ -72,6 +72,7 @@ private: Core::System& system; std::unique_ptr translations; + std::unique_ptr combobox_translations; std::forward_list tab_group; std::unique_ptr audio_tab; diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index 7eb6cb9ec..fdae83c64 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -15,9 +15,10 @@ ConfigureGeneral::ConfigureGeneral( const Core::System& system_, std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, QWidget* parent) + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) : Tab(group, parent), ui{std::make_unique()}, system{system_}, - translations{translations_} { + translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); SetConfiguration(); @@ -40,8 +41,8 @@ void ConfigureGeneral::SetConfiguration() { for (const auto setting : UISettings::values.linkage.by_category[Settings::Category::UiGeneral]) { - auto* widget = - new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); + auto* widget = new ConfigurationShared::Widget(setting, translations, combobox_translations, + this, runtime_lock, apply_funcs); if (!widget->Valid()) { delete widget; diff --git a/src/yuzu/configuration/configure_general.h b/src/yuzu/configuration/configure_general.h index 7692c16da..864dc3d2e 100644 --- a/src/yuzu/configuration/configure_general.h +++ b/src/yuzu/configuration/configure_general.h @@ -22,10 +22,12 @@ class ConfigureGeneral; class ConfigureGeneral : public ConfigurationShared::Tab { public: - explicit ConfigureGeneral(const Core::System& system_, - std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, - QWidget* parent = nullptr); + explicit ConfigureGeneral( + const Core::System& system_, + std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, + QWidget* parent = nullptr); ~ConfigureGeneral() override; void SetResetCallback(std::function callback); @@ -45,4 +47,5 @@ private: const Core::System& system; const ConfigurationShared::TranslationMap& translations; + const ConfigurationShared::ComboboxTranslationMap& combobox_translations; }; diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 45a4db430..a4dac659f 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -79,10 +79,12 @@ ConfigureGraphics::ConfigureGraphics( const Core::System& system_, std::vector& records_, const std::function& expose_compute_option_, std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, QWidget* parent) + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) : ConfigurationShared::Tab(group, parent), ui{std::make_unique()}, records{records_}, expose_compute_option{expose_compute_option_}, system{system_}, - translations{translations_} { + translations{translations_}, combobox_translations{combobox_translations_}, + shader_mapping{combobox_translations.at(typeid(Settings::ShaderBackend))} { vulkan_device = Settings::values.vulkan_device.GetValue(); RetrieveVulkanDevices(); @@ -235,22 +237,22 @@ void ConfigureGraphics::Setup() { setting->Id() == Settings::values.shader_backend.Id() || setting->Id() == Settings::values.vsync_mode.Id()) { return new ConfigurationShared::Widget( - setting, translations, this, runtime_lock, apply_funcs, + setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ComboBox, false); } else if (setting->Id() == Settings::values.fsr_sharpening_slider.Id()) { return new ConfigurationShared::Widget( - setting, translations, this, runtime_lock, apply_funcs, + setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ReverseSlider, true, 0.5f, nullptr, tr("%1%", "FSR sharpening percentage (e.g. 50%)")); } else if (setting->Id() == Settings::values.speed_limit.Id()) { return new ConfigurationShared::Widget( - setting, translations, this, runtime_lock, apply_funcs, + setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::SpinBox, true, 1.0f, &Settings::values.use_speed_limit, tr("%", "Limit speed percentage (e.g. 50%)")); } else { - return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, - apply_funcs); + return new ConfigurationShared::Widget(setting, translations, combobox_translations, + this, runtime_lock, apply_funcs); } }(); @@ -360,6 +362,15 @@ const QString ConfigureGraphics::TranslateVSyncMode(VkPresentModeKHR mode, } } +int ConfigureGraphics::FindIndex(std::type_index enumeration, int value) const { + for (u32 i = 0; i < combobox_translations.at(enumeration).size(); i++) { + if (combobox_translations.at(enumeration)[i].first == static_cast(value)) { + return i; + } + } + return -1; +} + void ConfigureGraphics::ApplyConfiguration() { const bool powered_on = system.IsPoweredOn(); for (const auto& func : apply_funcs) { @@ -374,13 +385,17 @@ void ConfigureGraphics::ApplyConfiguration() { Settings::values.shader_backend.SetGlobal(true); Settings::values.vulkan_device.SetGlobal(true); - if (!Settings::IsConfiguringGlobal() && api_restore_global_button->isEnabled()) { - auto backend = static_cast(api_combobox->currentIndex()); + if (Settings::IsConfiguringGlobal() || + (!Settings::IsConfiguringGlobal() && api_restore_global_button->isEnabled())) { + auto backend = static_cast( + combobox_translations + .at(typeid(Settings::RendererBackend))[api_combobox->currentIndex()] + .first); switch (backend) { case Settings::RendererBackend::OpenGL: Settings::values.shader_backend.SetGlobal(false); - Settings::values.shader_backend.SetValue( - static_cast(shader_backend_combobox->currentIndex())); + Settings::values.shader_backend.SetValue(static_cast( + shader_mapping[shader_backend_combobox->currentIndex()].first)); break; case Settings::RendererBackend::Vulkan: Settings::values.vulkan_device.SetGlobal(false); @@ -430,7 +445,8 @@ void ConfigureGraphics::UpdateAPILayout() { switch (GetCurrentGraphicsBackend()) { case Settings::RendererBackend::OpenGL: - shader_backend_combobox->setCurrentIndex(static_cast(shader_backend)); + shader_backend_combobox->setCurrentIndex( + FindIndex(typeid(Settings::ShaderBackend), static_cast(shader_backend))); vulkan_device_widget->setVisible(false); shader_backend_widget->setVisible(true); break; @@ -467,5 +483,8 @@ Settings::RendererBackend ConfigureGraphics::GetCurrentGraphicsBackend() const { if (!Settings::IsConfiguringGlobal() && !api_restore_global_button->isEnabled()) { return Settings::values.renderer_backend.GetValue(true); } - return static_cast(api_combobox->currentIndex()); + return static_cast( + combobox_translations.at(typeid(Settings::RendererBackend)) + .at(api_combobox->currentIndex()) + .first); } diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index f36495ed3..9e421d024 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -36,12 +36,13 @@ class ConfigureGraphics; class ConfigureGraphics : public ConfigurationShared::Tab { public: - explicit ConfigureGraphics(const Core::System& system_, - std::vector& records, - const std::function& expose_compute_option_, - std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, - QWidget* parent = nullptr); + explicit ConfigureGraphics( + const Core::System& system_, std::vector& records, + const std::function& expose_compute_option_, + std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, + QWidget* parent = nullptr); ~ConfigureGraphics() override; void ApplyConfiguration() override; @@ -68,6 +69,8 @@ private: Settings::RendererBackend GetCurrentGraphicsBackend() const; + int FindIndex(std::type_index enumeration, int value) const; + std::unique_ptr ui; QColor bg_color; @@ -85,6 +88,8 @@ private: const Core::System& system; const ConfigurationShared::TranslationMap& translations; + const ConfigurationShared::ComboboxTranslationMap& combobox_translations; + const std::vector>& shader_mapping; QPushButton* api_restore_global_button; QComboBox* vulkan_device_combobox; diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 4f57a7ae6..61e9b3d69 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -13,9 +13,10 @@ ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced( const Core::System& system_, std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, QWidget* parent) + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) : Tab(group, parent), ui{std::make_unique()}, system{system_}, - translations{translations_} { + translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); @@ -33,8 +34,8 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { for (auto setting : Settings::values.linkage.by_category[Settings::Category::RendererAdvanced]) { - ConfigurationShared::Widget* widget = - new ConfigurationShared::Widget(setting, translations, this, runtime_lock, apply_funcs); + ConfigurationShared::Widget* widget = new ConfigurationShared::Widget( + setting, translations, combobox_translations, this, runtime_lock, apply_funcs); if (!widget->Valid()) { delete widget; diff --git a/src/yuzu/configuration/configure_graphics_advanced.h b/src/yuzu/configuration/configure_graphics_advanced.h index 327134ee6..42634d3ff 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.h +++ b/src/yuzu/configuration/configure_graphics_advanced.h @@ -20,7 +20,9 @@ public: explicit ConfigureGraphicsAdvanced( const Core::System& system_, std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, QWidget* parent = nullptr); + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, + QWidget* parent = nullptr); ~ConfigureGraphicsAdvanced() override; void ApplyConfiguration() override; @@ -36,6 +38,7 @@ private: const Core::System& system; const ConfigurationShared::TranslationMap& translations; + const ConfigurationShared::ComboboxTranslationMap& combobox_translations; std::forward_list> apply_funcs; QWidget* checkbox_enable_compute_pipelines{}; diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index 2ee0a8ffa..845ffeeb8 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -43,6 +43,7 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st : QDialog(parent), ui(std::make_unique()), title_id{title_id_}, system{system_}, translations{ConfigurationShared::InitializeTranslations(this)}, + combobox_translations{ConfigurationShared::ComboboxEnumeration(this)}, tab_group{std::make_shared>()} { const auto file_path = std::filesystem::path(Common::FS::ToU8String(file_name)); const auto config_file_name = title_id == 0 ? Common::FS::PathToUTF8String(file_path.filename()) @@ -50,15 +51,17 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st game_config = std::make_unique(config_file_name, Config::ConfigType::PerGameConfig); addons_tab = std::make_unique(system_, this); - audio_tab = std::make_unique(system_, tab_group, *translations, this); + audio_tab = std::make_unique(system_, tab_group, *translations, + *combobox_translations, this); cpu_tab = std::make_unique(system_, tab_group, this); - graphics_advanced_tab = - std::make_unique(system_, tab_group, *translations, this); + graphics_advanced_tab = std::make_unique( + system_, tab_group, *translations, *combobox_translations, this); graphics_tab = std::make_unique( system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, - tab_group, *translations, this); + tab_group, *translations, *combobox_translations, this); input_tab = std::make_unique(system_, game_config.get(), this); - system_tab = std::make_unique(system_, tab_group, *translations, this); + system_tab = std::make_unique(system_, tab_group, *translations, + *combobox_translations, this); ui->setupUi(this); diff --git a/src/yuzu/configuration/configure_per_game.h b/src/yuzu/configuration/configure_per_game.h index 32217c1f1..e43d4df94 100644 --- a/src/yuzu/configuration/configure_per_game.h +++ b/src/yuzu/configuration/configure_per_game.h @@ -75,6 +75,7 @@ private: Core::System& system; std::unique_ptr translations; + std::unique_ptr combobox_translations; std::shared_ptr> tab_group; std::unique_ptr addons_tab; diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 128860800..40d0be8ca 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -44,9 +44,10 @@ static bool IsValidLocale(u32 region_index, u32 language_index) { ConfigureSystem::ConfigureSystem( Core::System& system_, std::shared_ptr> group, - ConfigurationShared::TranslationMap& translations_, QWidget* parent) + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) : Tab(group, parent), ui{std::make_unique()}, system{system_}, - translations{translations_} { + translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); Setup(); @@ -121,18 +122,17 @@ void ConfigureSystem::Setup() { ConfigurationShared::Widget* widget = [=]() { if (setting->Id() == Settings::values.custom_rtc.Id()) { return new ConfigurationShared::Widget( - setting, translations, this, runtime_lock, apply_funcs, + setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::DateTimeEdit, true, 1.0f, &Settings::values.custom_rtc_enabled); } else if (setting->Id() == Settings::values.rng_seed.Id()) { return new ConfigurationShared::Widget( - setting, translations, this, runtime_lock, apply_funcs, + setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::HexEdit, true, 1.0f, &Settings::values.rng_seed_enabled); } else { - return new ConfigurationShared::Widget(setting, translations, this, runtime_lock, - - apply_funcs); + return new ConfigurationShared::Widget(setting, translations, combobox_translations, + this, runtime_lock, apply_funcs); } }(); diff --git a/src/yuzu/configuration/configure_system.h b/src/yuzu/configuration/configure_system.h index 87b575060..c598c07f3 100644 --- a/src/yuzu/configuration/configure_system.h +++ b/src/yuzu/configuration/configure_system.h @@ -22,10 +22,11 @@ class ConfigureSystem; class ConfigureSystem : public ConfigurationShared::Tab { public: - explicit ConfigureSystem(Core::System& system_, - std::shared_ptr> group, - ConfigurationShared::TranslationMap& translations, - QWidget* parent = nullptr); + explicit ConfigureSystem( + Core::System& system_, std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations, + QWidget* parent = nullptr); ~ConfigureSystem() override; void ApplyConfiguration() override; @@ -46,7 +47,8 @@ private: ConfigurationShared::CheckState use_unsafe_extended_memory_layout; Core::System& system; - ConfigurationShared::TranslationMap& translations; + const ConfigurationShared::TranslationMap& translations; + const ConfigurationShared::ComboboxTranslationMap& combobox_translations; QCheckBox* rng_seed_checkbox; QLineEdit* rng_seed_edit; diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index c3b38f776..8fd8f3076 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -152,134 +152,204 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { return translations; } -std::forward_list ComboboxEnumeration(std::type_index type, QWidget* parent) { +std::unique_ptr ComboboxEnumeration(QWidget* parent) { + std::unique_ptr translations = + std::make_unique(); const auto& tr = [&](const char* text) { return parent->tr(text); }; // Intentionally skipping VSyncMode to let the UI fill that one out - if (type == typeid(Settings::AstcDecodeMode)) { - return { - tr("CPU"), - tr("GPU"), - tr("CPU Asynchronous"), - }; - } else if (type == typeid(Settings::RendererBackend)) { - return { - tr("OpenGL"), - tr("Vulkan"), - tr("Null"), - }; - } else if (type == typeid(Settings::ShaderBackend)) { - return { - tr("GLSL"), - tr("GLASM (Assembly Shaders, NVIDIA Only)"), - tr("SPIR-V (Experimental, Mesa Only)"), - }; - } else if (type == typeid(Settings::GPUAccuracy)) { - return { - tr("Normal"), - tr("High"), - tr("Extreme"), - }; - } else if (type == typeid(Settings::CPUAccuracy)) { - return { - tr("Auto"), - tr("Accurate"), - tr("Unsafe"), - tr("Paranoid (disables most optimizations)"), - }; - } else if (type == typeid(Settings::FullscreenMode)) { - return { - tr("Borderless Windowed"), - tr("Exclusive Fullscreen"), - }; - } else if (type == typeid(Settings::NvdecEmulation)) { - return { - tr("No Video Output"), - tr("CPU Video Decoding"), - tr("GPU Video Decoding (Default)"), - }; - } else if (type == typeid(Settings::ResolutionSetup)) { - return { - tr("0.5X (360p/540p) [EXPERIMENTAL]"), - tr("0.75X (540p/810p) [EXPERIMENTAL]"), - tr("1X (720p/1080p)"), - tr("1.5X (1080p/1620p) [EXPERIMENTAL]"), - tr("2X (1440p/2160p)"), - tr("3X (2160p/3240p)"), - tr("4X (2880p/4320p)"), - tr("5X (3600p/5400p)"), - tr("6X (4320p/6480p)"), - tr("7X (5040p/7560p)"), - tr("8X (5760p/8640p)"), - }; - } else if (type == typeid(Settings::ScalingFilter)) { - return { - tr("Nearest Neighbor"), tr("Bilinear"), tr("Bicubic"), - tr("Gaussian"), tr("ScaleForce"), tr("AMD FidelityFX™️ Super Resolution"), - }; - } else if (type == typeid(Settings::AntiAliasing)) { - return { - tr("None"), - tr("FXAA"), - tr("SMAA"), - }; - } else if (type == typeid(Settings::AspectRatio)) { - return { - tr("Default (16:9)"), tr("Force 4:3"), tr("Force 21:9"), - tr("Force 16:10"), tr("Stretch to Window"), - }; - } else if (type == typeid(Settings::AnisotropyMode)) { - return { - tr("Automatic"), tr("Default"), tr("2x"), tr("4x"), tr("8x"), tr("16x"), - }; - } else if (type == typeid(Settings::Language)) { - return { - tr("Japanese (日本語)"), - tr("American English"), - tr("French (français)"), - tr("German (Deutsch)"), - tr("Italian (italiano)"), - tr("Spanish (español)"), - tr("Chinese"), - tr("Korean (한국어)"), - tr("Dutch (Nederlands)"), - tr("Portuguese (português)"), - tr("Russian (Русский)"), - tr("Taiwanese"), - tr("British English"), - tr("Canadian French"), - tr("Latin American Spanish"), - tr("Simplified Chinese"), - tr("Traditional Chinese (正體中文)"), - tr("Brazilian Portuguese (português do Brasil)"), - }; - } else if (type == typeid(Settings::Region)) { - return { - tr("Japan"), tr("USA"), tr("Europe"), tr("Australia"), - tr("China"), tr("Korea"), tr("Taiwan"), - }; - } else if (type == typeid(Settings::TimeZone)) { - return { - tr("Auto"), tr("Default"), tr("CET"), tr("CST6CDT"), tr("Cuba"), - tr("EET"), tr("Egypt"), tr("Eire"), tr("EST"), tr("EST5EDT"), - tr("GB"), tr("GB-Eire"), tr("GMT"), tr("GMT+0"), tr("GMT-0"), - tr("GMT0"), tr("Greenwich"), tr("Hongkong"), tr("HST"), tr("Iceland"), - tr("Iran"), tr("Israel"), tr("Jamaica"), tr("Kwajalein"), tr("Libya"), - tr("MET"), tr("MST"), tr("MST7MDT"), tr("Navajo"), tr("NZ"), - tr("NZ-CHAT"), tr("Poland"), tr("Portugal"), tr("PRC"), tr("PST8PDT"), - tr("ROC"), tr("ROK"), tr("Singapore"), tr("Turkey"), tr("UCT"), - tr("W-SU"), tr("WET"), tr("Zulu"), - }; - } else if (type == typeid(Settings::AudioMode)) { - return { - tr("Mono"), - tr("Stereo"), - tr("Surround"), - }; - } + translations->insert( + {typeid(Settings::AstcDecodeMode), + { + {static_cast(Settings::AstcDecodeMode::CPU), tr("CPU")}, + {static_cast(Settings::AstcDecodeMode::GPU), tr("GPU")}, + {static_cast(Settings::AstcDecodeMode::CPUAsynchronous), tr("CPU Asynchronous")}, + }}); + translations->insert({typeid(Settings::RendererBackend), + { +#ifdef HAS_OPENGL + {static_cast(Settings::RendererBackend::OpenGL), tr("OpenGL")}, +#endif + {static_cast(Settings::RendererBackend::Vulkan), tr("Vulkan")}, + {static_cast(Settings::RendererBackend::Null), tr("Null")}, + }}); + translations->insert({typeid(Settings::ShaderBackend), + { + {static_cast(Settings::ShaderBackend::GLSL), tr("GLSL")}, + {static_cast(Settings::ShaderBackend::GLASM), + tr("GLASM (Assembly Shaders, NVIDIA Only)")}, + {static_cast(Settings::ShaderBackend::SPIRV), + tr("SPIR-V (Experimental, Mesa Only)")}, + }}); + translations->insert({typeid(Settings::GPUAccuracy), + { + {static_cast(Settings::GPUAccuracy::Normal), tr("Normal")}, + {static_cast(Settings::GPUAccuracy::High), tr("High")}, + {static_cast(Settings::GPUAccuracy::Extreme), tr("Extreme")}, + }}); + translations->insert({typeid(Settings::CPUAccuracy), + { + {static_cast(Settings::CPUAccuracy::Auto), tr("Auto")}, + {static_cast(Settings::CPUAccuracy::Accurate), tr("Accurate")}, + {static_cast(Settings::CPUAccuracy::Unsafe), tr("Unsafe")}, + {static_cast(Settings::CPUAccuracy::Paranoid), + tr("Paranoid (disables most optimizations)")}, + }}); + translations->insert( + {typeid(Settings::FullscreenMode), + { + {static_cast(Settings::FullscreenMode::Borderless), tr("Borderless Windowed")}, + {static_cast(Settings::FullscreenMode::Exclusive), tr("Exclusive Fullscreen")}, + }}); + translations->insert( + {typeid(Settings::NvdecEmulation), + { + {static_cast(Settings::NvdecEmulation::Off), tr("No Video Output")}, + {static_cast(Settings::NvdecEmulation::CPU), tr("CPU Video Decoding")}, + {static_cast(Settings::NvdecEmulation::GPU), tr("GPU Video Decoding (Default)")}, + }}); + translations->insert( + {typeid(Settings::ResolutionSetup), + { + {static_cast(Settings::ResolutionSetup::Res1_2X), + tr("0.5X (360p/540p) [EXPERIMENTAL]")}, + {static_cast(Settings::ResolutionSetup::Res3_4X), + tr("0.75X (540p/810p) [EXPERIMENTAL]")}, + {static_cast(Settings::ResolutionSetup::Res1X), tr("1X (720p/1080p)")}, + {static_cast(Settings::ResolutionSetup::Res3_2X), + tr("1.5X (1080p/1620p) [EXPERIMENTAL]")}, + {static_cast(Settings::ResolutionSetup::Res2X), tr("2X (1440p/2160p)")}, + {static_cast(Settings::ResolutionSetup::Res3X), tr("3X (2160p/3240p)")}, + {static_cast(Settings::ResolutionSetup::Res4X), tr("4X (2880p/4320p)")}, + {static_cast(Settings::ResolutionSetup::Res5X), tr("5X (3600p/5400p)")}, + {static_cast(Settings::ResolutionSetup::Res6X), tr("6X (4320p/6480p)")}, + {static_cast(Settings::ResolutionSetup::Res7X), tr("7X (5040p/7560p)")}, + {static_cast(Settings::ResolutionSetup::Res8X), tr("8X (5760p/8640p)")}, + }}); + translations->insert( + {typeid(Settings::ScalingFilter), + { + {static_cast(Settings::ScalingFilter::NearestNeighbor), tr("Nearest Neighbor")}, + {static_cast(Settings::ScalingFilter::Bilinear), tr("Bilinear")}, + {static_cast(Settings::ScalingFilter::Bicubic), tr("Bicubic")}, + {static_cast(Settings::ScalingFilter::Gaussian), tr("Gaussian")}, + {static_cast(Settings::ScalingFilter::ScaleForce), tr("ScaleForce")}, + {static_cast(Settings::ScalingFilter::Fsr), + tr("AMD FidelityFX™️ Super Resolution")}, + }}); + translations->insert({typeid(Settings::AntiAliasing), + { + {static_cast(Settings::AntiAliasing::None), tr("None")}, + {static_cast(Settings::AntiAliasing::Fxaa), tr("FXAA")}, + {static_cast(Settings::AntiAliasing::Smaa), tr("SMAA")}, + }}); + translations->insert( + {typeid(Settings::AspectRatio), + { + {static_cast(Settings::AspectRatio::R16_9), tr("Default (16:9)")}, + {static_cast(Settings::AspectRatio::R4_3), tr("Force 4:3")}, + {static_cast(Settings::AspectRatio::R21_9), tr("Force 21:9")}, + {static_cast(Settings::AspectRatio::R16_10), tr("Force 16:10")}, + {static_cast(Settings::AspectRatio::Stretch), tr("Stretch to Window")}, + }}); + translations->insert( + {typeid(Settings::AnisotropyMode), + { + {static_cast(Settings::AnisotropyMode::Automatic), tr("Automatic")}, + {static_cast(Settings::AnisotropyMode::Default), tr("Default")}, + {static_cast(Settings::AnisotropyMode::X2), tr("2x")}, + {static_cast(Settings::AnisotropyMode::X4), tr("4x")}, + {static_cast(Settings::AnisotropyMode::X8), tr("8x")}, + {static_cast(Settings::AnisotropyMode::X16), tr("16x")}, + }}); + translations->insert( + {typeid(Settings::Language), + { + {static_cast(Settings::Language::Japanese), tr("Japanese (日本語)")}, + {static_cast(Settings::Language::EnglishAmerican), tr("American English")}, + {static_cast(Settings::Language::French), tr("French (français)")}, + {static_cast(Settings::Language::German), tr("German (Deutsch)")}, + {static_cast(Settings::Language::Italian), tr("Italian (italiano)")}, + {static_cast(Settings::Language::Spanish), tr("Spanish (español)")}, + {static_cast(Settings::Language::Chinese), tr("Chinese")}, + {static_cast(Settings::Language::Korean), tr("Korean (한국어)")}, + {static_cast(Settings::Language::Dutch), tr("Dutch (Nederlands)")}, + {static_cast(Settings::Language::Portuguese), tr("Portuguese (português)")}, + {static_cast(Settings::Language::Russian), tr("Russian (Русский)")}, + {static_cast(Settings::Language::Taiwanese), tr("Taiwanese")}, + {static_cast(Settings::Language::EnglishBritish), tr("British English")}, + {static_cast(Settings::Language::FrenchCanadian), tr("Canadian French")}, + {static_cast(Settings::Language::SpanishLatin), tr("Latin American Spanish")}, + {static_cast(Settings::Language::ChineseSimplified), tr("Simplified Chinese")}, + {static_cast(Settings::Language::ChineseTraditional), + tr("Traditional Chinese (正體中文)")}, + {static_cast(Settings::Language::PortugueseBrazilian), + tr("Brazilian Portuguese (português do Brasil)")}, + }}); + translations->insert({typeid(Settings::Region), + { + {static_cast(Settings::Region::Japan), tr("Japan")}, + {static_cast(Settings::Region::USA), tr("USA")}, + {static_cast(Settings::Region::Europe), tr("Europe")}, + {static_cast(Settings::Region::Australia), tr("Australia")}, + {static_cast(Settings::Region::China), tr("China")}, + {static_cast(Settings::Region::Korea), tr("Korea")}, + {static_cast(Settings::Region::Taiwan), tr("Taiwan")}, + }}); + translations->insert({typeid(Settings::TimeZone), + { + {static_cast(Settings::TimeZone::Auto), tr("Auto")}, + {static_cast(Settings::TimeZone::Default), tr("Default")}, + {static_cast(Settings::TimeZone::CET), tr("CET")}, + {static_cast(Settings::TimeZone::CST6CDT), tr("CST6CDT")}, + {static_cast(Settings::TimeZone::Cuba), tr("Cuba")}, + {static_cast(Settings::TimeZone::EET), tr("EET")}, + {static_cast(Settings::TimeZone::Egypt), tr("Egypt")}, + {static_cast(Settings::TimeZone::Eire), tr("Eire")}, + {static_cast(Settings::TimeZone::EST), tr("EST")}, + {static_cast(Settings::TimeZone::EST5EDT), tr("EST5EDT")}, + {static_cast(Settings::TimeZone::GB), tr("GB")}, + {static_cast(Settings::TimeZone::GBEire), tr("GB-Eire")}, + {static_cast(Settings::TimeZone::GMT), tr("GMT")}, + {static_cast(Settings::TimeZone::GMTPlusZero), tr("GMT+0")}, + {static_cast(Settings::TimeZone::GMTMinusZero), tr("GMT-0")}, + {static_cast(Settings::TimeZone::GMTZero), tr("GMT0")}, + {static_cast(Settings::TimeZone::Greenwich), tr("Greenwich")}, + {static_cast(Settings::TimeZone::Hongkong), tr("Hongkong")}, + {static_cast(Settings::TimeZone::HST), tr("HST")}, + {static_cast(Settings::TimeZone::Iceland), tr("Iceland")}, + {static_cast(Settings::TimeZone::Iran), tr("Iran")}, + {static_cast(Settings::TimeZone::Israel), tr("Israel")}, + {static_cast(Settings::TimeZone::Jamaica), tr("Jamaica")}, + {static_cast(Settings::TimeZone::Kwajalein), tr("Kwajalein")}, + {static_cast(Settings::TimeZone::Libya), tr("Libya")}, + {static_cast(Settings::TimeZone::MET), tr("MET")}, + {static_cast(Settings::TimeZone::MST), tr("MST")}, + {static_cast(Settings::TimeZone::MST7MDT), tr("MST7MDT")}, + {static_cast(Settings::TimeZone::Navajo), tr("Navajo")}, + {static_cast(Settings::TimeZone::NZ), tr("NZ")}, + {static_cast(Settings::TimeZone::NZCHAT), tr("NZ-CHAT")}, + {static_cast(Settings::TimeZone::Poland), tr("Poland")}, + {static_cast(Settings::TimeZone::Portugal), tr("Portugal")}, + {static_cast(Settings::TimeZone::PRC), tr("PRC")}, + {static_cast(Settings::TimeZone::PST8PDT), tr("PST8PDT")}, + {static_cast(Settings::TimeZone::ROC), tr("ROC")}, + {static_cast(Settings::TimeZone::ROK), tr("ROK")}, + {static_cast(Settings::TimeZone::Singapore), tr("Singapore")}, + {static_cast(Settings::TimeZone::Turkey), tr("Turkey")}, + {static_cast(Settings::TimeZone::UCT), tr("UCT")}, + {static_cast(Settings::TimeZone::W_SU), tr("W-SU")}, + {static_cast(Settings::TimeZone::WET), tr("WET")}, + {static_cast(Settings::TimeZone::Zulu), tr("Zulu")}, + }}); + translations->insert({typeid(Settings::AudioMode), + { + {static_cast(Settings::AudioMode::Mono), tr("Mono")}, + {static_cast(Settings::AudioMode::Stereo), tr("Stereo")}, + {static_cast(Settings::AudioMode::Surround), tr("Surround")}, + }}); - return {}; + return translations; } - } // namespace ConfigurationShared diff --git a/src/yuzu/configuration/shared_translation.h b/src/yuzu/configuration/shared_translation.h index fcf638ea5..abe9c89b1 100644 --- a/src/yuzu/configuration/shared_translation.h +++ b/src/yuzu/configuration/shared_translation.h @@ -1,21 +1,23 @@ // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later -#include #include #include #include #include #include +#include #include class QWidget; namespace ConfigurationShared { using TranslationMap = std::map>; +using ComboboxTranslations = std::vector>; +using ComboboxTranslationMap = std::map; std::unique_ptr InitializeTranslations(QWidget* parent); -std::forward_list ComboboxEnumeration(std::type_index type, QWidget* parent); +std::unique_ptr ComboboxEnumeration(QWidget* parent); } // namespace ConfigurationShared diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 4b21e5be8..64e1d90ad 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -113,40 +113,51 @@ void Widget::CreateCombobox(const QString& label, std::function& load_fu QLabel* qt_label = new QLabel(label, this); combobox = new QComboBox(this); - std::forward_list combobox_enumerations = ComboboxEnumeration(type, this); - for (const auto& item : combobox_enumerations) { - combobox->addItem(item); - } - layout->addWidget(qt_label); layout->addWidget(combobox); layout->setSpacing(6); layout->setContentsMargins(0, 0, 0, 0); - if (!managed) { + const ComboboxTranslations* enumeration{nullptr}; + if (combobox_enumerations.contains(type)) { + enumeration = &combobox_enumerations.at(type); + for (const auto& [id, name] : *enumeration) { + combobox->addItem(name); + } + } + + if (!managed || enumeration == nullptr) { return; } - // TODO: Remove audio engine specialization - if (setting.TypeId() != typeid(Settings::AudioEngine)) { - combobox->setCurrentIndex(std::stoi(setting.ToString())); - } else { - combobox->setCurrentIndex( - static_cast(Settings::ToEnum(setting.ToString()))); - } + const auto find_index = [=](u32 value) -> int { + for (u32 i = 0; i < enumeration->size(); i++) { + if (enumeration->at(i).first == value) { + return i; + } + } + return -1; + }; + + const u32 setting_value = std::stoi(setting.ToString()); + combobox->setCurrentIndex(find_index(setting_value)); if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { setting.LoadString(std::to_string(combobox->currentIndex())); }; + load_func = [=]() { + int current = combobox->currentIndex(); + setting.LoadString(std::to_string(enumeration->at(current).first)); + }; } else { restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); layout->addWidget(restore_button); - QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { + QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { restore_button->setEnabled(false); restore_button->setVisible(false); - combobox->setCurrentIndex(std::stoi(setting.ToStringGlobal())); + const u32 global_value = std::stoi(setting.ToStringGlobal()); + combobox->setCurrentIndex(find_index(global_value)); }); QObject::connect(combobox, QOverload::of(&QComboBox::activated), [=](int) { @@ -158,7 +169,8 @@ void Widget::CreateCombobox(const QString& label, std::function& load_fu bool using_global = !restore_button->isEnabled(); setting.SetGlobal(using_global); if (!using_global) { - setting.LoadString(std::to_string(combobox->currentIndex())); + int current = combobox->currentIndex(); + setting.LoadString(std::to_string(enumeration->at(current).first)); } }; } @@ -523,17 +535,13 @@ bool Widget::Valid() { Widget::~Widget() = default; Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, - QWidget* parent_, std::forward_list>& apply_funcs_) - : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_}, - apply_funcs{apply_funcs_} {} - -Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, - QWidget* parent_, bool runtime_lock_, - std::forward_list>& apply_funcs_, RequestType request, - bool managed, float multiplier, Settings::BasicSetting* other_setting, - const QString& string) - : QWidget(parent_), parent{parent_}, translations{translations_}, setting{*setting_}, - apply_funcs{apply_funcs_}, runtime_lock{runtime_lock_} { + const ComboboxTranslationMap& combobox_translations_, QWidget* parent_, + bool runtime_lock_, std::forward_list>& apply_funcs_, + RequestType request, bool managed, float multiplier, + Settings::BasicSetting* other_setting, const QString& string) + : QWidget(parent_), parent{parent_}, translations{translations_}, + combobox_enumerations{combobox_translations_}, setting{*setting_}, apply_funcs{apply_funcs_}, + runtime_lock{runtime_lock_} { if (!Settings::IsConfiguringGlobal() && !setting.Switchable()) { LOG_DEBUG(Frontend, "\"{}\" is not switchable, skipping...", setting.GetLabel()); return; @@ -632,5 +640,4 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati this->setToolTip(tooltip); } - } // namespace ConfigurationShared diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 331316040..6077f045d 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -35,13 +35,12 @@ class Widget : public QWidget { Q_OBJECT public: - Widget(Settings::BasicSetting* setting, const TranslationMap& translations, QWidget* parent, - bool runtime_lock, std::forward_list>& apply_funcs_, + Widget(Settings::BasicSetting* setting, const TranslationMap& translations, + const ComboboxTranslationMap& combobox_translations, QWidget* parent, bool runtime_lock, + std::forward_list>& apply_funcs_, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, Settings::BasicSetting* other_setting = nullptr, const QString& string = QStringLiteral("")); - Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, QWidget* parent_, - std::forward_list>& apply_funcs_); virtual ~Widget(); bool Valid(); @@ -77,6 +76,7 @@ private: QWidget* parent; const TranslationMap& translations; + const ComboboxTranslationMap& combobox_enumerations; Settings::BasicSetting& setting; std::forward_list>& apply_funcs; From daa31121ee75dedcb636011e02815b816a7cc446 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 22:54:58 -0400 Subject: [PATCH 048/155] configure_cpu: Generate UI --- src/yuzu/configuration/configure_cpu.cpp | 134 +++++++----------- src/yuzu/configuration/configure_cpu.h | 11 +- src/yuzu/configuration/configure_cpu.ui | 129 ++++------------- src/yuzu/configuration/configure_dialog.cpp | 3 +- src/yuzu/configuration/configure_per_game.cpp | 3 +- 5 files changed, 92 insertions(+), 188 deletions(-) diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index ecaeb1a6b..0982e006d 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -5,88 +5,83 @@ #include #include "common/common_types.h" #include "common/settings.h" +#include "configuration/shared_widget.h" #include "core/core.h" #include "ui_configure_cpu.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_cpu.h" -ConfigureCpu::ConfigureCpu(const Core::System& system_, - std::shared_ptr> group, - QWidget* parent) - : Tab(group, parent), ui{std::make_unique()}, system{system_} { +ConfigureCpu::ConfigureCpu( + const Core::System& system_, + std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations_, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) + : Tab(group, parent), ui{std::make_unique()}, system{system_}, + translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); - SetupPerGameUI(); + Setup(); SetConfiguration(); - connect(ui->accuracy, qOverload(&QComboBox::currentIndexChanged), this, + connect(accuracy_combobox, qOverload(&QComboBox::currentIndexChanged), this, &ConfigureCpu::UpdateGroup); } ConfigureCpu::~ConfigureCpu() = default; -void ConfigureCpu::SetConfiguration() { +void ConfigureCpu::SetConfiguration() {} +void ConfigureCpu::Setup() { const bool runtime_lock = !system.IsPoweredOn(); + auto* accuracy_layout = ui->widget_accuracy->layout(); + auto* unsafe_layout = ui->unsafe_widget->layout(); + std::map unsafe_hold{}; - ui->accuracy->setEnabled(runtime_lock); - ui->cpuopt_unsafe_unfuse_fma->setEnabled(runtime_lock); - ui->cpuopt_unsafe_reduce_fp_error->setEnabled(runtime_lock); - ui->cpuopt_unsafe_ignore_standard_fpcr->setEnabled(runtime_lock); - ui->cpuopt_unsafe_inaccurate_nan->setEnabled(runtime_lock); - ui->cpuopt_unsafe_fastmem_check->setEnabled(runtime_lock); - ui->cpuopt_unsafe_ignore_global_monitor->setEnabled(runtime_lock); + std::forward_list settings; + const auto push = [&](Settings::Category category) { + for (const auto setting : Settings::values.linkage.by_category[category]) { + settings.push_front(setting); + } + }; - ui->cpuopt_unsafe_unfuse_fma->setChecked(Settings::values.cpuopt_unsafe_unfuse_fma.GetValue()); - ui->cpuopt_unsafe_reduce_fp_error->setChecked( - Settings::values.cpuopt_unsafe_reduce_fp_error.GetValue()); - ui->cpuopt_unsafe_ignore_standard_fpcr->setChecked( - Settings::values.cpuopt_unsafe_ignore_standard_fpcr.GetValue()); - ui->cpuopt_unsafe_inaccurate_nan->setChecked( - Settings::values.cpuopt_unsafe_inaccurate_nan.GetValue()); - ui->cpuopt_unsafe_fastmem_check->setChecked( - Settings::values.cpuopt_unsafe_fastmem_check.GetValue()); - ui->cpuopt_unsafe_ignore_global_monitor->setChecked( - Settings::values.cpuopt_unsafe_ignore_global_monitor.GetValue()); + push(Settings::Category::Cpu); + push(Settings::Category::CpuUnsafe); - if (Settings::IsConfiguringGlobal()) { - ui->accuracy->setCurrentIndex(static_cast(Settings::values.cpu_accuracy.GetValue())); - } else { - ConfigurationShared::SetPerGameSetting(ui->accuracy, &Settings::values.cpu_accuracy); - ConfigurationShared::SetHighlight(ui->widget_accuracy, - !Settings::values.cpu_accuracy.UsingGlobal()); + for (const auto setting : settings) { + auto* widget = new ConfigurationShared::Widget(setting, translations, combobox_translations, + this, runtime_lock, apply_funcs); + + if (!widget->Valid()) { + delete widget; + continue; + } + + if (setting->Id() == Settings::values.cpu_accuracy.Id()) { + accuracy_layout->addWidget(widget); + accuracy_combobox = widget->combobox; + } else { + unsafe_hold.insert({setting->GetLabel(), widget}); + } } - UpdateGroup(ui->accuracy->currentIndex()); + + for (const auto& [label, widget] : unsafe_hold) { + unsafe_layout->addWidget(widget); + } + + UpdateGroup(accuracy_combobox->currentIndex()); } void ConfigureCpu::UpdateGroup(int index) { - if (!Settings::IsConfiguringGlobal()) { - index -= ConfigurationShared::USE_GLOBAL_OFFSET; - } - const auto accuracy = static_cast(index); + const auto accuracy = static_cast( + combobox_translations.at(typeid(Settings::CPUAccuracy))[index].first); ui->unsafe_group->setVisible(accuracy == Settings::CPUAccuracy::Unsafe); } void ConfigureCpu::ApplyConfiguration() { - ConfigurationShared::ApplyPerGameSetting(&Settings::values.cpu_accuracy, ui->accuracy); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.cpuopt_unsafe_unfuse_fma, - ui->cpuopt_unsafe_unfuse_fma, - cpuopt_unsafe_unfuse_fma); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.cpuopt_unsafe_reduce_fp_error, - ui->cpuopt_unsafe_reduce_fp_error, - cpuopt_unsafe_reduce_fp_error); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.cpuopt_unsafe_ignore_standard_fpcr, - ui->cpuopt_unsafe_ignore_standard_fpcr, - cpuopt_unsafe_ignore_standard_fpcr); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.cpuopt_unsafe_inaccurate_nan, - ui->cpuopt_unsafe_inaccurate_nan, - cpuopt_unsafe_inaccurate_nan); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.cpuopt_unsafe_fastmem_check, - ui->cpuopt_unsafe_fastmem_check, - cpuopt_unsafe_fastmem_check); - ConfigurationShared::ApplyPerGameSetting(&Settings::values.cpuopt_unsafe_ignore_global_monitor, - ui->cpuopt_unsafe_ignore_global_monitor, - cpuopt_unsafe_ignore_global_monitor); + const bool is_powered_on = system.IsPoweredOn(); + for (const auto& apply_func : apply_funcs) { + apply_func(is_powered_on); + } } void ConfigureCpu::changeEvent(QEvent* event) { @@ -100,32 +95,3 @@ void ConfigureCpu::changeEvent(QEvent* event) { void ConfigureCpu::RetranslateUI() { ui->retranslateUi(this); } - -void ConfigureCpu::SetupPerGameUI() { - if (Settings::IsConfiguringGlobal()) { - return; - } - - ConfigurationShared::SetColoredComboBox( - ui->accuracy, ui->widget_accuracy, - static_cast(Settings::values.cpu_accuracy.GetValue(true))); - - ConfigurationShared::SetColoredTristate(ui->cpuopt_unsafe_unfuse_fma, - Settings::values.cpuopt_unsafe_unfuse_fma, - cpuopt_unsafe_unfuse_fma); - ConfigurationShared::SetColoredTristate(ui->cpuopt_unsafe_reduce_fp_error, - Settings::values.cpuopt_unsafe_reduce_fp_error, - cpuopt_unsafe_reduce_fp_error); - ConfigurationShared::SetColoredTristate(ui->cpuopt_unsafe_ignore_standard_fpcr, - Settings::values.cpuopt_unsafe_ignore_standard_fpcr, - cpuopt_unsafe_ignore_standard_fpcr); - ConfigurationShared::SetColoredTristate(ui->cpuopt_unsafe_inaccurate_nan, - Settings::values.cpuopt_unsafe_inaccurate_nan, - cpuopt_unsafe_inaccurate_nan); - ConfigurationShared::SetColoredTristate(ui->cpuopt_unsafe_fastmem_check, - Settings::values.cpuopt_unsafe_fastmem_check, - cpuopt_unsafe_fastmem_check); - ConfigurationShared::SetColoredTristate(ui->cpuopt_unsafe_ignore_global_monitor, - Settings::values.cpuopt_unsafe_ignore_global_monitor, - cpuopt_unsafe_ignore_global_monitor); -} diff --git a/src/yuzu/configuration/configure_cpu.h b/src/yuzu/configuration/configure_cpu.h index 187d080b6..fb970122d 100644 --- a/src/yuzu/configuration/configure_cpu.h +++ b/src/yuzu/configuration/configure_cpu.h @@ -19,6 +19,8 @@ class ConfigureCpu : public ConfigurationShared::Tab { public: explicit ConfigureCpu(const Core::System& system_, std::shared_ptr> group, + const ConfigurationShared::TranslationMap& translations, + const ConfigurationShared::ComboboxTranslationMap& combobox_translations, QWidget* parent = nullptr); ~ConfigureCpu() override; @@ -31,7 +33,7 @@ private: void UpdateGroup(int index); - void SetupPerGameUI(); + void Setup(); std::unique_ptr ui; @@ -43,4 +45,11 @@ private: ConfigurationShared::CheckState cpuopt_unsafe_ignore_global_monitor; const Core::System& system; + + const ConfigurationShared::TranslationMap& translations; + const ConfigurationShared::ComboboxTranslationMap& combobox_translations; + + std::forward_list> apply_funcs{}; + + QComboBox* accuracy_combobox; }; diff --git a/src/yuzu/configuration/configure_cpu.ui b/src/yuzu/configuration/configure_cpu.ui index 8ae569ee6..835788c1f 100644 --- a/src/yuzu/configuration/configure_cpu.ui +++ b/src/yuzu/configuration/configure_cpu.ui @@ -27,38 +27,19 @@ - - - - - Accuracy: - - - - - - - - Auto - - - - - Accurate - - - - - Unsafe - - - - - Paranoid (disables most optimizations) - - - - + + + 0 + + + 0 + + + 0 + + + 0 + @@ -96,75 +77,21 @@ - - - - <div>This option improves speed by reducing accuracy of fused-multiply-add instructions on CPUs without native FMA support.</div> - - - - Unfuse FMA (improve performance on CPUs without FMA) - - - - - - - - <div>This option improves the speed of some approximate floating-point functions by using less accurate native approximations.</div> - - - - Faster FRSQRTE and FRECPE - - - - - - - - <div>This option improves the speed of 32 bits ASIMD floating-point functions by running with incorrect rounding modes.</div> - - - - Faster ASIMD instructions (32 bits only) - - - - - - - - <div>This option improves speed by removing NaN checking. Please note this also reduces accuracy of certain floating-point instructions.</div> - - - - Inaccurate NaN handling - - - - - - - - <div>This option improves speed by eliminating a safety check before every memory read/write in guest. Disabling it may allow a game to read/write the emulator's memory.</div> - - - - Disable address space checks - - - - - - - - <div>This option improves speed by relying only on the semantics of cmpxchg to ensure safety of exclusive access instructions. Please note this may result in deadlocks and other race conditions.</div> - - - - Ignore global monitor - + + + + 0 + + + 0 + + + 0 + + + 0 + + diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index 1a339a227..c7d132fc8 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -37,7 +37,8 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, combobox_translations{ConfigurationShared::ComboboxEnumeration(this)}, audio_tab{std::make_unique(system_, nullptr, *translations, *combobox_translations, this)}, - cpu_tab{std::make_unique(system_, nullptr, this)}, + cpu_tab{std::make_unique(system_, nullptr, *translations, + *combobox_translations, this)}, debug_tab_tab{std::make_unique(system_, this)}, filesystem_tab{std::make_unique(this)}, general_tab{std::make_unique(system_, nullptr, *translations, diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index 845ffeeb8..5863beca0 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -53,7 +53,8 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st addons_tab = std::make_unique(system_, this); audio_tab = std::make_unique(system_, tab_group, *translations, *combobox_translations, this); - cpu_tab = std::make_unique(system_, tab_group, this); + cpu_tab = std::make_unique(system_, tab_group, *translations, + *combobox_translations, this); graphics_advanced_tab = std::make_unique( system_, tab_group, *translations, *combobox_translations, this); graphics_tab = std::make_unique( From 333725074644f0e6cf13b29dc24e654b07617380 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 22:56:48 -0400 Subject: [PATCH 049/155] configuration_shared: Remove old custom config setup functions --- .../configuration/configuration_shared.cpp | 75 ------------------- src/yuzu/configuration/configuration_shared.h | 69 ----------------- 2 files changed, 144 deletions(-) diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index dff70f04b..624d9ba1b 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -38,78 +38,3 @@ Tab::Tab(std::shared_ptr> group_, QWidget* parent) Tab::~Tab() = default; } // namespace ConfigurationShared - -void ConfigurationShared::ApplyPerGameSetting(Settings::SwitchableSetting* setting, - const QCheckBox* checkbox, - const CheckState& tracker) { - if (Settings::IsConfiguringGlobal() && setting->UsingGlobal()) { - setting->SetValue(checkbox->checkState()); - } else if (!Settings::IsConfiguringGlobal()) { - if (tracker == CheckState::Global) { - setting->SetGlobal(true); - } else { - setting->SetGlobal(false); - setting->SetValue(checkbox->checkState()); - } - } -} - -void ConfigurationShared::SetPerGameSetting(QCheckBox* checkbox, - const Settings::SwitchableSetting* setting) { - if (setting->UsingGlobal()) { - checkbox->setCheckState(Qt::PartiallyChecked); - } else { - checkbox->setCheckState(setting->GetValue() ? Qt::Checked : Qt::Unchecked); - } -} - -void ConfigurationShared::SetHighlight(QWidget* widget, bool highlighted) { - if (highlighted) { - widget->setStyleSheet(QStringLiteral("QWidget#%1 { background-color:rgba(0,203,255,0.5) }") - .arg(widget->objectName())); - } else { - widget->setStyleSheet(QStringLiteral("")); - } - widget->show(); -} - -void ConfigurationShared::SetColoredTristate(QCheckBox* checkbox, bool global, bool state, - bool global_state, CheckState& tracker) { - if (global) { - tracker = CheckState::Global; - } else { - tracker = (state == global_state) ? CheckState::On : CheckState::Off; - } - SetHighlight(checkbox, tracker != CheckState::Global); - QObject::connect(checkbox, &QCheckBox::clicked, checkbox, [checkbox, global_state, &tracker] { - tracker = static_cast((static_cast(tracker) + 1) % - static_cast(CheckState::Count)); - if (tracker == CheckState::Global) { - checkbox->setChecked(global_state); - } - SetHighlight(checkbox, tracker != CheckState::Global); - }); -} - -void ConfigurationShared::SetColoredComboBox(QComboBox* combobox, QWidget* target, int global) { - InsertGlobalItem(combobox, global); - QObject::connect(combobox, qOverload(&QComboBox::activated), target, - [target](int index) { SetHighlight(target, index != 0); }); -} - -void ConfigurationShared::InsertGlobalItem(QComboBox* combobox, int global_index) { - const QString use_global_text = - ConfigurePerGame::tr("Use global configuration (%1)").arg(combobox->itemText(global_index)); - combobox->insertItem(ConfigurationShared::USE_GLOBAL_INDEX, use_global_text); - combobox->insertSeparator(ConfigurationShared::USE_GLOBAL_SEPARATOR_INDEX); -} - -int ConfigurationShared::GetComboboxIndex(int global_setting_index, const QComboBox* combobox) { - if (Settings::IsConfiguringGlobal()) { - return combobox->currentIndex(); - } - if (combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - return global_setting_index; - } - return combobox->currentIndex() - ConfigurationShared::USE_GLOBAL_OFFSET; -} diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 83a0dd574..046d78e2b 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -41,73 +41,4 @@ enum class CheckState { Count, // Simply the number of states, not a valid checkbox state }; -// Global-aware apply and set functions - -// ApplyPerGameSetting, given a Settings::Setting and a Qt UI element, properly applies a Setting -void ApplyPerGameSetting(Settings::SwitchableSetting* setting, const QCheckBox* checkbox, - const CheckState& tracker); -template -void ApplyPerGameSetting(Settings::SwitchableSetting* setting, - const QComboBox* combobox) { - if (Settings::IsConfiguringGlobal() && setting->UsingGlobal()) { - setting->SetValue(static_cast(combobox->currentIndex())); - } else if (!Settings::IsConfiguringGlobal()) { - if (combobox->currentIndex() == ConfigurationShared::USE_GLOBAL_INDEX) { - setting->SetGlobal(true); - } else { - setting->SetGlobal(false); - setting->SetValue(static_cast(combobox->currentIndex() - - ConfigurationShared::USE_GLOBAL_OFFSET)); - } - } -} - -// Sets a Qt UI element given a Settings::Setting -void SetPerGameSetting(QCheckBox* checkbox, const Settings::SwitchableSetting* setting); - -template -void SetPerGameSetting(QComboBox* combobox, - const Settings::SwitchableSetting* setting) { - combobox->setCurrentIndex(setting->UsingGlobal() ? ConfigurationShared::USE_GLOBAL_INDEX - : static_cast(setting->GetValue()) + - ConfigurationShared::USE_GLOBAL_OFFSET); -} - -// (Un)highlights a Qt UI element -void SetHighlight(QWidget* widget, bool highlighted); - -// Sets up a QCheckBox like a tristate one, given a Setting -template -void SetColoredTristate(QCheckBox* checkbox, - const Settings::SwitchableSetting& setting, - CheckState& tracker) { - if (setting.UsingGlobal()) { - tracker = CheckState::Global; - } else { - tracker = (setting.GetValue() == setting.GetValue(true)) ? CheckState::On : CheckState::Off; - } - SetHighlight(checkbox, tracker != CheckState::Global); - QObject::connect(checkbox, &QCheckBox::clicked, checkbox, [checkbox, setting, &tracker] { - tracker = static_cast((static_cast(tracker) + 1) % - static_cast(CheckState::Count)); - if (tracker == CheckState::Global) { - checkbox->setChecked(setting.GetValue(true)); - } - SetHighlight(checkbox, tracker != CheckState::Global); - }); -} - -void SetColoredTristate(QCheckBox* checkbox, bool global, bool state, bool global_state, - CheckState& tracker); - -// Sets up coloring of a QWidget `target` based on the state of a QComboBox, and calls -// InsertGlobalItem -void SetColoredComboBox(QComboBox* combobox, QWidget* target, int global); - -// Adds the "Use Global Configuration" selection and separator to the beginning of a QComboBox -void InsertGlobalItem(QComboBox* combobox, int global_index); - -// Returns the correct index of a QComboBox taking into account global configuration -int GetComboboxIndex(int global_setting_index, const QComboBox* combobox); - } // namespace ConfigurationShared From 217fa040809c083a8b680962589da264f8d8e4c4 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 23:05:21 -0400 Subject: [PATCH 050/155] configuration: Clean up includes a bit --- .../configuration/configuration_shared.cpp | 23 +------------------ src/yuzu/configuration/configuration_shared.h | 20 +++------------- src/yuzu/configuration/configure_audio.cpp | 1 + src/yuzu/configuration/configure_audio.h | 2 +- src/yuzu/configuration/configure_cpu.cpp | 1 + src/yuzu/configuration/configure_cpu.h | 10 +++----- src/yuzu/configuration/configure_dialog.h | 3 ++- src/yuzu/configuration/configure_graphics.h | 2 ++ .../configure_graphics_advanced.cpp | 1 + .../configure_graphics_advanced.h | 1 + src/yuzu/configuration/configure_per_game.h | 1 + src/yuzu/configuration/configure_system.cpp | 2 ++ src/yuzu/configuration/configure_system.h | 7 +++--- src/yuzu/configuration/shared_widget.cpp | 3 +++ 14 files changed, 26 insertions(+), 51 deletions(-) diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 624d9ba1b..d3cfacf48 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -2,29 +2,8 @@ // SPDX-License-Identifier: GPL-2.0-or-later #include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include "common/settings.h" +#include #include "yuzu/configuration/configuration_shared.h" -#include "yuzu/configuration/configure_per_game.h" -#include "yuzu/configuration/shared_translation.h" namespace ConfigurationShared { diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 046d78e2b..5313bfb4f 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -4,14 +4,12 @@ #pragma once #include -#include #include -#include -#include +#include #include #include -#include "common/settings.h" -#include "yuzu/configuration/shared_translation.h" + +class QObject; namespace ConfigurationShared { @@ -29,16 +27,4 @@ private: std::shared_ptr> group; }; -constexpr int USE_GLOBAL_INDEX = 0; -constexpr int USE_GLOBAL_SEPARATOR_INDEX = 1; -constexpr int USE_GLOBAL_OFFSET = 2; - -// CheckBoxes require a tracker for their state since we emulate a tristate CheckBox -enum class CheckState { - Off, // Checkbox overrides to off/false - On, // Checkbox overrides to on/true - Global, // Checkbox defers to the global state - Count, // Simply the number of states, not a valid checkbox state -}; - } // namespace ConfigurationShared diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 1cafeaa31..0496bd78f 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -3,6 +3,7 @@ #include #include +#include #include "audio_core/sink/sink.h" #include "audio_core/sink/sink_details.h" diff --git a/src/yuzu/configuration/configure_audio.h b/src/yuzu/configuration/configure_audio.h index a9b005433..31cf682e0 100644 --- a/src/yuzu/configuration/configure_audio.h +++ b/src/yuzu/configuration/configure_audio.h @@ -10,7 +10,7 @@ #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/shared_translation.h" -class QPushButton; +class QComboBox; namespace Core { class System; diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 0982e006d..ac298a50f 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -3,6 +3,7 @@ #include #include +#include #include "common/common_types.h" #include "common/settings.h" #include "configuration/shared_widget.h" diff --git a/src/yuzu/configuration/configure_cpu.h b/src/yuzu/configuration/configure_cpu.h index fb970122d..57603e5c9 100644 --- a/src/yuzu/configuration/configure_cpu.h +++ b/src/yuzu/configuration/configure_cpu.h @@ -6,6 +6,9 @@ #include #include #include "yuzu/configuration/configuration_shared.h" +#include "yuzu/configuration/shared_translation.h" + +class QComboBox; namespace Core { class System; @@ -37,13 +40,6 @@ private: std::unique_ptr ui; - ConfigurationShared::CheckState cpuopt_unsafe_unfuse_fma; - ConfigurationShared::CheckState cpuopt_unsafe_reduce_fp_error; - ConfigurationShared::CheckState cpuopt_unsafe_ignore_standard_fpcr; - ConfigurationShared::CheckState cpuopt_unsafe_inaccurate_nan; - ConfigurationShared::CheckState cpuopt_unsafe_fastmem_check; - ConfigurationShared::CheckState cpuopt_unsafe_ignore_global_monitor; - const Core::System& system; const ConfigurationShared::TranslationMap& translations; diff --git a/src/yuzu/configuration/configure_dialog.h b/src/yuzu/configuration/configure_dialog.h index 4f8c1912f..931900b7d 100644 --- a/src/yuzu/configuration/configure_dialog.h +++ b/src/yuzu/configuration/configure_dialog.h @@ -7,7 +7,8 @@ #include #include #include -#include "configuration/configuration_shared.h" +#include "yuzu/configuration/configuration_shared.h" +#include "yuzu/configuration/shared_translation.h" #include "yuzu/vk_device_info.h" namespace Core { diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index 9e421d024..718ba54f5 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -5,6 +5,7 @@ #include #include +#include #include #include #include @@ -14,6 +15,7 @@ #include "common/common_types.h" #include "vk_device_info.h" #include "yuzu/configuration/configuration_shared.h" +#include "yuzu/configuration/shared_translation.h" class QPushButton; class QEvent; diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 61e9b3d69..c5e21da02 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -8,6 +8,7 @@ #include "ui_configure_graphics_advanced.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_graphics_advanced.h" +#include "yuzu/configuration/shared_translation.h" #include "yuzu/configuration/shared_widget.h" ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced( diff --git a/src/yuzu/configuration/configure_graphics_advanced.h b/src/yuzu/configuration/configure_graphics_advanced.h index 42634d3ff..90b79f786 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.h +++ b/src/yuzu/configuration/configure_graphics_advanced.h @@ -6,6 +6,7 @@ #include #include #include "yuzu/configuration/configuration_shared.h" +#include "yuzu/configuration/shared_translation.h" namespace Core { class System; diff --git a/src/yuzu/configuration/configure_per_game.h b/src/yuzu/configuration/configure_per_game.h index e43d4df94..4849ac291 100644 --- a/src/yuzu/configuration/configure_per_game.h +++ b/src/yuzu/configuration/configure_per_game.h @@ -15,6 +15,7 @@ #include "vk_device_info.h" #include "yuzu/configuration/config.h" #include "yuzu/configuration/configuration_shared.h" +#include "yuzu/configuration/shared_translation.h" namespace Core { class System; diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 40d0be8ca..5fe3c4a7f 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -5,6 +5,8 @@ #include #include +#include +#include #include #include #include diff --git a/src/yuzu/configuration/configure_system.h b/src/yuzu/configuration/configure_system.h index c598c07f3..4457ccc21 100644 --- a/src/yuzu/configuration/configure_system.h +++ b/src/yuzu/configuration/configure_system.h @@ -9,7 +9,11 @@ #include #include "yuzu/configuration/configuration_shared.h" +#include "yuzu/configuration/shared_translation.h" +class QCheckBox; +class QLineEdit; +class QComboBox; class QDateTimeEdit; namespace Core { @@ -43,9 +47,6 @@ private: std::unique_ptr ui; bool enabled = false; - ConfigurationShared::CheckState use_rng_seed; - ConfigurationShared::CheckState use_unsafe_extended_memory_layout; - Core::System& system; const ConfigurationShared::TranslationMap& translations; const ConfigurationShared::ComboboxTranslationMap& combobox_translations; diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 64e1d90ad..71f4eadbe 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -1,6 +1,7 @@ #include #include #include +#include #include #include #include @@ -8,7 +9,9 @@ #include #include #include +#include #include +#include #include #include #include From 3281ea935ff66cef6fbfa1b83564fb4ac96918cc Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 16:30:39 -0700 Subject: [PATCH 051/155] settings: Make volume runtime-configurable --- src/common/settings.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/common/settings.h b/src/common/settings.h index d4b41a162..a9ce113ef 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -550,7 +550,7 @@ struct Values { Setting audio_output_device_id{linkage, "auto", "output_device", Category::Audio}; Setting audio_input_device_id{linkage, "auto", "input_device", Category::Audio}; Setting audio_muted{linkage, false, "audio_muted", Category::Audio, false}; - SwitchableSetting volume{linkage, 100, 0, 200, "volume", Category::Audio}; + SwitchableSetting volume{linkage, 100, 0, 200, "volume", Category::Audio, true, true}; Setting dump_audio_commands{linkage, false, "dump_audio_commands", Category::Audio, false}; From 7734127f9e9d950c50045942bb24f76652e86788 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 19 May 2023 00:51:57 -0400 Subject: [PATCH 052/155] shared_translation: Add missing tooltips --- src/yuzu/configuration/shared_translation.cpp | 28 ++++++++++++++----- 1 file changed, 21 insertions(+), 7 deletions(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 8fd8f3076..49cb94d2e 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -45,13 +45,26 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { // Cpu Unsafe INSERT(Settings, cpuopt_unsafe_unfuse_fma, - "Unfuse FMA (improve performance on CPUs without FMA)", ""); - INSERT(Settings, cpuopt_unsafe_reduce_fp_error, "Faster FRSQRTE and FRECPE", ""); + "Unfuse FMA (improve performance on CPUs without FMA)", + "This option improves speed by reducing accuracy of fused-multiply-add instructions on " + "CPUs without native FMA support."); + INSERT(Settings, cpuopt_unsafe_reduce_fp_error, "Faster FRSQRTE and FRECPE", + "This option improves the speed of some approximate floating-point functions by using " + "less accurate native approximations."); INSERT(Settings, cpuopt_unsafe_ignore_standard_fpcr, "Faster ASIMD instructions (32 bits only)", - ""); - INSERT(Settings, cpuopt_unsafe_inaccurate_nan, "Inaccurate NaN handling", ""); - INSERT(Settings, cpuopt_unsafe_fastmem_check, "Disable address space checks", ""); - INSERT(Settings, cpuopt_unsafe_ignore_global_monitor, "Ignore global monitor", ""); + "This option improves the speed of 32 bits ASIMD floating-point functions by running " + "with incorrect rounding modes."); + INSERT(Settings, cpuopt_unsafe_inaccurate_nan, "Inaccurate NaN handling", + "This option improves speed by removing NaN checking. Please note this also reduces " + "accuracy of certain floating-point instructions."); + INSERT( + Settings, cpuopt_unsafe_fastmem_check, "Disable address space checks", + "This option improves speed by eliminating a safety check before every memory read/write " + "in guest. Disabling it may allow a game to read/write the emulator's memory."); + INSERT(Settings, cpuopt_unsafe_ignore_global_monitor, "Ignore global monitor", + "This option improves speed by relying only on the semantics of cmpxchg to ensure " + "safety of exclusive access instructions. Please note this may result in deadlocks and " + "other race conditions."); // Renderer INSERT(Settings, renderer_backend, "API:", ""); @@ -114,7 +127,8 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(Settings, device_name, "Device Name", ""); INSERT(Settings, custom_rtc, "Custom RTC", ""); INSERT(Settings, custom_rtc_enabled, "", ""); - INSERT(Settings, language_index, "Language:", ""); + INSERT(Settings, language_index, + "Language:", "Note: this can be overridden when region setting is auto-select"); INSERT(Settings, region_index, "Region:", ""); INSERT(Settings, time_zone_index, "Time Zone:", ""); INSERT(Settings, sound_index, "Sound Output Mode:", ""); From 3d932416e313d829fe384e62193ccedc17c6463f Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 22:33:16 -0700 Subject: [PATCH 053/155] configuration: Workaround for Windows Qt bug Odd issue happens that dragging the cpu or system tabs in custom configs would cause the window to take up the entire verticle space of the screen. --- src/yuzu/configuration/configure.ui | 31 ++++++++++++-- src/yuzu/configuration/configure_cpu.ui | 50 +++++++++------------- src/yuzu/configuration/configure_system.ui | 30 +++++-------- 3 files changed, 58 insertions(+), 53 deletions(-) diff --git a/src/yuzu/configuration/configure.ui b/src/yuzu/configuration/configure.ui index eb8078467..573c40801 100644 --- a/src/yuzu/configuration/configure.ui +++ b/src/yuzu/configuration/configure.ui @@ -48,11 +48,34 @@ - - - QDialogButtonBox::Cancel|QDialogButtonBox::Ok + + + 0 - + + 0 + + + 0 + + + 0 + + + + + Some settings are only available when a game is not running. + + + + + + + QDialogButtonBox::Cancel|QDialogButtonBox::Ok + + + + diff --git a/src/yuzu/configuration/configure_cpu.ui b/src/yuzu/configuration/configure_cpu.ui index 835788c1f..f734e842e 100644 --- a/src/yuzu/configuration/configure_cpu.ui +++ b/src/yuzu/configuration/configure_cpu.ui @@ -16,9 +16,12 @@ CPU - + - + + + 0 + @@ -56,10 +59,6 @@ - - - - @@ -97,31 +96,24 @@ + + + + Qt::Vertical + + + QSizePolicy::Expanding + + + + 20 + 40 + + + + - - - - Qt::Vertical - - - - 20 - 40 - - - - - - - - CPU settings are available only when game is not running. - - - true - - - diff --git a/src/yuzu/configuration/configure_system.ui b/src/yuzu/configuration/configure_system.ui index a5a3e2dc3..2a735836e 100644 --- a/src/yuzu/configuration/configure_system.ui +++ b/src/yuzu/configuration/configure_system.ui @@ -43,6 +43,16 @@ + + + + + + + true + + + @@ -86,26 +96,6 @@ - - - - - - - true - - - - - - - System settings are available only when game is not running. - - - true - - - From b570b719de11512ab2acc2c1fd8a8a9ae8391763 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 18 May 2023 23:19:08 -0700 Subject: [PATCH 054/155] shared_widget: Force min width of 100 for restore button Dark theme mandates a 100px minimum width for QAbstractButton, even though this is not desired here. --- src/yuzu/configuration/shared_widget.cpp | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 71f4eadbe..d5b2bd60e 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -18,6 +18,7 @@ #include #include #include +#include #include #include "common/common_types.h" #include "common/settings.h" @@ -27,11 +28,20 @@ namespace ConfigurationShared { +static int restore_button_count = 0; + QPushButton* Widget::CreateRestoreGlobalButton(bool using_global, QWidget* parent) { + restore_button_count++; + QStyle* style = parent->style(); QIcon* icon = new QIcon(style->standardIcon(QStyle::SP_LineEditClearButton)); QPushButton* restore_button = new QPushButton(*icon, QStringLiteral(""), parent); - restore_button->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred); + restore_button->setObjectName(QStringLiteral("RestoreButton%1").arg(restore_button_count)); + restore_button->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Preferred); + + // Workaround for dark theme causing min-width to be much larger than 0 + restore_button->setStyleSheet( + QStringLiteral("QAbstractButton#%1 { min-width: 0px }").arg(restore_button->objectName())); QSizePolicy sp_retain = restore_button->sizePolicy(); sp_retain.setRetainSizeWhenHidden(true); @@ -113,8 +123,9 @@ void Widget::CreateCombobox(const QString& label, std::function& load_fu QLayout* layout = new QHBoxLayout(this); - QLabel* qt_label = new QLabel(label, this); + QLabel* qt_label = CreateLabel(label); combobox = new QComboBox(this); + combobox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->addWidget(qt_label); layout->addWidget(combobox); From 81860b431753719322e98435577d0981d55ea6d7 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 5 Jun 2023 16:03:45 -0400 Subject: [PATCH 055/155] configure_system: Hide locale warn at start --- src/yuzu/configuration/configure_system.cpp | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 5fe3c4a7f..ae59d2ee7 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -68,7 +68,7 @@ ConfigureSystem::ConfigureSystem( } }); - const auto locale_check = [this](int index) { + const auto locale_check = [this]() { const auto region_index = combo_region->currentIndex(); const auto language_index = combo_language->currentIndex(); const bool valid_locale = IsValidLocale(region_index, language_index); @@ -84,6 +84,9 @@ ConfigureSystem::ConfigureSystem( connect(combo_language, qOverload(&QComboBox::currentIndexChanged), this, locale_check); connect(combo_region, qOverload(&QComboBox::currentIndexChanged), this, locale_check); + ui->label_warn_invalid_locale->setVisible(false); + locale_check(); + SetConfiguration(); } From 09f61656e36b1a1e2efa0d34a51ccf8b1aa9c130 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 5 Jun 2023 16:04:05 -0400 Subject: [PATCH 056/155] shared_translation: Add translation for AstcRecompression --- src/yuzu/configuration/shared_translation.cpp | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 49cb94d2e..50e19ede1 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -80,6 +80,7 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(Settings, use_asynchronous_gpu_emulation, "Use asynchronous GPU emulation", ""); INSERT(Settings, nvdec_emulation, "NVDEC emulation:", ""); INSERT(Settings, accelerate_astc, "ASTC Decoding Method:", ""); + INSERT(Settings, astc_recompression, "ASTC Recompression Method:", ""); INSERT(Settings, vsync_mode, "VSync Mode:", "FIFO (VSync) does not drop frames or exhibit tearing but is limited by the screen " "refresh rate.\nFIFO Relaxed is similar to FIFO but allows tearing as it recovers from " @@ -180,6 +181,14 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { {static_cast(Settings::AstcDecodeMode::GPU), tr("GPU")}, {static_cast(Settings::AstcDecodeMode::CPUAsynchronous), tr("CPU Asynchronous")}, }}); + translations->insert( + {typeid(Settings::AstcRecompression), + { + {static_cast(Settings::AstcRecompression::Uncompressed), + tr("Uncompressed (Best quality)")}, + {static_cast(Settings::AstcRecompression::Bc1), tr("BC1 (Low quality)")}, + {static_cast(Settings::AstcRecompression::Bc3), tr("BC3 (Medium quality)")}, + }}); translations->insert({typeid(Settings::RendererBackend), { #ifdef HAS_OPENGL From cd1d8adc491e6b613aae13d77643a062851e58b0 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 5 Jun 2023 18:15:37 -0400 Subject: [PATCH 057/155] shared_translation: Fix pragma once --- src/yuzu/configuration/shared_translation.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/yuzu/configuration/shared_translation.h b/src/yuzu/configuration/shared_translation.h index abe9c89b1..52ef4f2dd 100644 --- a/src/yuzu/configuration/shared_translation.h +++ b/src/yuzu/configuration/shared_translation.h @@ -1,6 +1,8 @@ // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#pragma once + #include #include #include From e6d65bf61c5f242e630cc86e84b04f20bab0ef73 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 6 Jun 2023 01:54:24 -0400 Subject: [PATCH 058/155] c_per_game: Inform when settings might not be configurable --- src/yuzu/configuration/configure_per_game.ui | 47 ++++++++++++++------ 1 file changed, 33 insertions(+), 14 deletions(-) diff --git a/src/yuzu/configuration/configure_per_game.ui b/src/yuzu/configuration/configure_per_game.ui index 85c86e107..99ba2fd18 100644 --- a/src/yuzu/configuration/configure_per_game.ui +++ b/src/yuzu/configuration/configure_per_game.ui @@ -2,6 +2,14 @@ ConfigurePerGame + + + 0 + 0 + 900 + 607 + + 900 @@ -225,20 +233,31 @@ - - - - 0 - 0 - - - - Qt::Horizontal - - - QDialogButtonBox::Cancel|QDialogButtonBox::Ok - - + + + + + Some settings are only available when a game is not running. + + + + + + + + 0 + 0 + + + + Qt::Horizontal + + + QDialogButtonBox::Cancel|QDialogButtonBox::Ok + + + + From d373cc3d3ff624507d2165518eeb0616f34a8004 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 6 Jun 2023 03:50:48 -0400 Subject: [PATCH 059/155] android-config: Adapt settings rework --- src/android/app/src/main/jni/config.cpp | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/src/android/app/src/main/jni/config.cpp b/src/android/app/src/main/jni/config.cpp index 43e8aa72a..2a06ca024 100644 --- a/src/android/app/src/main/jni/config.cpp +++ b/src/android/app/src/main/jni/config.cpp @@ -150,15 +150,17 @@ void Config::ReadValues() { if (rng_seed_enabled) { Settings::values.rng_seed.SetValue(config->GetInteger("System", "rng_seed", 0)); } else { - Settings::values.rng_seed.SetValue(std::nullopt); + Settings::values.rng_seed.SetValue(0); } + Settings::values.rng_seed_enabled.SetValue(rng_seed_enabled); const auto custom_rtc_enabled = config->GetBoolean("System", "custom_rtc_enabled", false); if (custom_rtc_enabled) { Settings::values.custom_rtc = config->GetInteger("System", "custom_rtc", 0); } else { - Settings::values.custom_rtc = std::nullopt; + Settings::values.custom_rtc = 0; } + Settings::values.custom_rtc_enabled = custom_rtc_enabled; ReadSetting("System", Settings::values.language_index); ReadSetting("System", Settings::values.region_index); @@ -226,10 +228,10 @@ void Config::ReadValues() { "Renderer", "gpu_accuracy", static_cast(Settings::GPUAccuracy::Normal))); // Use GPU default anisotropic filtering on Android - Settings::values.max_anisotropy = config->GetInteger("Renderer", "max_anisotropy", 1); + Settings::values.max_anisotropy = static_cast(config->GetInteger("Renderer", "max_anisotropy", 1)); // Disable ASTC compute by default on Android - Settings::values.accelerate_astc = config->GetBoolean("Renderer", "accelerate_astc", false); + Settings::values.accelerate_astc.SetValue(config->GetBoolean("Renderer", "accelerate_astc", false) ? Settings::AstcDecodeMode::GPU : Settings::AstcDecodeMode::CPU); // Enable asynchronous presentation by default on Android Settings::values.async_presentation = From d7dd023409d01b09631e02a2dff591c847de32b3 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 6 Jun 2023 15:45:44 -0400 Subject: [PATCH 060/155] shared_widget: Refactor again Starting with combobox Putting code specific to the sub-widget in their own function. --- src/yuzu/configuration/shared_widget.cpp | 163 ++++++++++++++++------- src/yuzu/configuration/shared_widget.h | 10 +- 2 files changed, 121 insertions(+), 52 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index d5b2bd60e..564c46e5e 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -115,23 +115,18 @@ QHBoxLayout* Widget::CreateCheckBox(Settings::BasicSetting* bool_setting, const return layout; } -void Widget::CreateCombobox(const QString& label, std::function& load_func, bool managed, - Settings::BasicSetting* const other_setting) { - created = true; - +QWidget* Widget::CreateCombobox(std::function& serializer, + std::function& restore_func, + const std::function& touched) { const auto type = setting.TypeId(); - QLayout* layout = new QHBoxLayout(this); - - QLabel* qt_label = CreateLabel(label); combobox = new QComboBox(this); combobox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - layout->addWidget(qt_label); - layout->addWidget(combobox); - - layout->setSpacing(6); - layout->setContentsMargins(0, 0, 0, 0); + if (!Settings::IsConfiguringGlobal()) { + QObject::connect(combobox, QOverload::of(&QComboBox::activated), + [touched]() { touched(); }); + } const ComboboxTranslations* enumeration{nullptr}; if (combobox_enumerations.contains(type)) { @@ -139,10 +134,8 @@ void Widget::CreateCombobox(const QString& label, std::function& load_fu for (const auto& [id, name] : *enumeration) { combobox->addItem(name); } - } - - if (!managed || enumeration == nullptr) { - return; + } else { + return combobox; } const auto find_index = [=](u32 value) -> int { @@ -157,37 +150,17 @@ void Widget::CreateCombobox(const QString& label, std::function& load_fu const u32 setting_value = std::stoi(setting.ToString()); combobox->setCurrentIndex(find_index(setting_value)); - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { - int current = combobox->currentIndex(); - setting.LoadString(std::to_string(enumeration->at(current).first)); - }; - } else { - restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); - layout->addWidget(restore_button); + serializer = [this, enumeration]() { + int current = combobox->currentIndex(); + return std::to_string(enumeration->at(current).first); + }; - QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { - restore_button->setEnabled(false); - restore_button->setVisible(false); + restore_func = [this, find_index]() { + const u32 global_value = std::stoi(setting.ToStringGlobal()); + combobox->setCurrentIndex(find_index(global_value)); + }; - const u32 global_value = std::stoi(setting.ToStringGlobal()); - combobox->setCurrentIndex(find_index(global_value)); - }); - - QObject::connect(combobox, QOverload::of(&QComboBox::activated), [=](int) { - restore_button->setEnabled(true); - restore_button->setVisible(true); - }); - - load_func = [=]() { - bool using_global = !restore_button->isEnabled(); - setting.SetGlobal(using_global); - if (!using_global) { - int current = combobox->currentIndex(); - setting.LoadString(std::to_string(enumeration->at(current).first)); - } - }; - } + return combobox; } void Widget::CreateLineEdit(const QString& label, std::function& load_func, bool managed, @@ -542,7 +515,99 @@ void Widget::CreateDateTimeEdit(const QString& label, std::function& loa } } -bool Widget::Valid() { +void Widget::SetupComponent(const QString& label, std::function& load_func, bool managed, + RequestType request, Settings::BasicSetting* other_setting) { + created = true; + const auto type = setting.TypeId(); + + QLayout* layout = new QHBoxLayout(this); + layout->setContentsMargins(0, 0, 0, 0); + + const bool require_checkbox = + other_setting != nullptr && other_setting->TypeId() == typeid(bool); + + if (other_setting != nullptr && other_setting->TypeId() != typeid(bool)) { + LOG_WARNING(Frontend, + "Extra setting specified but is not bool, refusing to create checkbox for it."); + } + + if (require_checkbox) { + } else { + QLabel* qt_label = CreateLabel(label); + layout->addWidget(qt_label); + } + + std::function touched = []() {}; + std::function serializer = []() -> std::string { return {}; }; + std::function restore_func = []() {}; + + QWidget* data_component{nullptr}; + + if (!Settings::IsConfiguringGlobal()) { + restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); + + touched = [this]() { + restore_button->setEnabled(true); + restore_button->setVisible(true); + }; + } + + if (setting.IsEnum()) { + data_component = CreateCombobox(serializer, restore_func, touched); + } else if (type == typeid(u32) || type == typeid(int) || type == typeid(u16) || + type == typeid(s64) || type == typeid(u8)) { + switch (request) { + case RequestType::ComboBox: + data_component = CreateCombobox(serializer, restore_func, touched); + break; + default: + UNIMPLEMENTED(); + } + } else if (type == typeid(std::string)) { + switch (request) { + case RequestType::ComboBox: + data_component = CreateCombobox(serializer, restore_func, touched); + break; + default: + UNIMPLEMENTED(); + } + } + + if (data_component == nullptr) { + LOG_ERROR(Frontend, "Failed to create widget for {}", setting.GetLabel()); + created = false; + return; + } + + layout->addWidget(data_component); + + if (!managed) { + return; + } + + if (Settings::IsConfiguringGlobal()) { + load_func = [this, serializer]() { setting.LoadString(serializer()); }; + } else { + layout->addWidget(restore_button); + + QObject::connect(restore_button, &QAbstractButton::clicked, [this, restore_func](bool) { + restore_button->setEnabled(false); + restore_button->setVisible(false); + + restore_func(); + }); + + load_func = [this, serializer]() { + bool using_global = !restore_button->isEnabled(); + setting.SetGlobal(using_global); + if (!using_global) { + setting.LoadString(serializer()); + } + }; + } +} + +bool Widget::Valid() const { return created; } @@ -584,7 +649,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati if (type == typeid(bool)) { CreateCheckBox(&setting, label, load_func, managed); } else if (setting.IsEnum()) { - CreateCombobox(label, load_func, managed); + SetupComponent(label, load_func, managed, request, other_setting); } else if (type == typeid(u32) || type == typeid(int) || type == typeid(u16) || type == typeid(s64) || type == typeid(u8)) { switch (request) { @@ -598,7 +663,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati CreateLineEdit(label, load_func, managed); break; case RequestType::ComboBox: - CreateCombobox(label, load_func, managed); + SetupComponent(label, load_func, managed, request, other_setting); break; case RequestType::DateTimeEdit: CreateDateTimeEdit(label, load_func, managed, true, other_setting); @@ -620,7 +685,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati CreateLineEdit(label, load_func, managed); break; case RequestType::ComboBox: - CreateCombobox(label, load_func, false); + SetupComponent(label, load_func, managed, request, other_setting); break; case RequestType::SpinBox: case RequestType::Slider: diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 6077f045d..2ed738a06 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -43,7 +43,7 @@ public: const QString& string = QStringLiteral("")); virtual ~Widget(); - bool Valid(); + bool Valid() const; [[nodiscard]] static QPushButton* CreateRestoreGlobalButton(bool using_global, QWidget* parent); @@ -56,12 +56,16 @@ public: QDateTimeEdit* date_time_edit{}; private: + void SetupComponent(const QString& label, std::function& load_func, bool managed, + RequestType request, Settings::BasicSetting* other_setting); + QLabel* CreateLabel(const QString& text); QHBoxLayout* CreateCheckBox(Settings::BasicSetting* bool_setting, const QString& label, std::function& load_func, bool managed); - void CreateCombobox(const QString& label, std::function& load_func, bool managed, - Settings::BasicSetting* const other_setting = nullptr); + QWidget* CreateCombobox(std::function& serializer, + std::function& restore_func, + const std::function& touched); void CreateLineEdit(const QString& label, std::function& load_func, bool managed, Settings::BasicSetting* const other_setting = nullptr); void CreateHexEdit(const QString& label, std::function& load_func, bool managed, From 9a2a92673c8cae4589e0e801f49235a4890719f9 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 6 Jun 2023 21:20:37 -0400 Subject: [PATCH 061/155] shared_widget: Complete refactoring Reduces code bloat a good bit by moving code specific to each sub widget to their own functions. --- src/yuzu/configuration/shared_widget.cpp | 512 +++++++---------------- src/yuzu/configuration/shared_widget.h | 36 +- 2 files changed, 169 insertions(+), 379 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 564c46e5e..096ec451d 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -59,12 +59,10 @@ QLabel* Widget::CreateLabel(const QString& text) { return qt_label; } -QHBoxLayout* Widget::CreateCheckBox(Settings::BasicSetting* bool_setting, const QString& label, - std::function& load_func, bool managed) { - created = true; - - QHBoxLayout* layout = new QHBoxLayout(this); - +QWidget* Widget::CreateCheckBox(Settings::BasicSetting* bool_setting, const QString& label, + std::function& serializer, + std::function& restore_func, + const std::function& touch) { checkbox = new QCheckBox(label, this); checkbox->setCheckState(bool_setting->ToString() == "true" ? Qt::CheckState::Checked : Qt::CheckState::Unchecked); @@ -74,60 +72,30 @@ QHBoxLayout* Widget::CreateCheckBox(Settings::BasicSetting* bool_setting, const checkbox->setEnabled(false); } - layout->addWidget(checkbox); + serializer = [this]() { + return checkbox->checkState() == Qt::CheckState::Checked ? "true" : "false"; + }; - layout->setContentsMargins(0, 0, 0, 0); - - if (!managed) { - return layout; - } - - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { - bool_setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); - }; - } else { - restore_button = - CreateRestoreGlobalButton(bool_setting->UsingGlobal() && setting.UsingGlobal(), this); - layout->addWidget(restore_button); - - QObject::connect(checkbox, &QCheckBox::stateChanged, [=](int) { - restore_button->setVisible(true); - restore_button->setEnabled(true); - }); - - QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { + if (!Settings::IsConfiguringGlobal()) { + restore_func = [this, bool_setting]() { checkbox->setCheckState(bool_setting->ToStringGlobal() == "true" ? Qt::Checked : Qt::Unchecked); - restore_button->setEnabled(false); - restore_button->setVisible(false); - }); - - load_func = [=]() { - bool using_global = !restore_button->isEnabled(); - bool_setting->SetGlobal(using_global); - if (!using_global) { - bool_setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); - } }; + + QObject::connect(checkbox, &QCheckBox::clicked, [touch]() { touch(); }); } - return layout; + return checkbox; } QWidget* Widget::CreateCombobox(std::function& serializer, std::function& restore_func, - const std::function& touched) { + const std::function& touch) { const auto type = setting.TypeId(); combobox = new QComboBox(this); combobox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - if (!Settings::IsConfiguringGlobal()) { - QObject::connect(combobox, QOverload::of(&QComboBox::activated), - [touched]() { touched(); }); - } - const ComboboxTranslations* enumeration{nullptr}; if (combobox_enumerations.contains(type)) { enumeration = &combobox_enumerations.at(type); @@ -155,98 +123,57 @@ QWidget* Widget::CreateCombobox(std::function& serializer, return std::to_string(enumeration->at(current).first); }; - restore_func = [this, find_index]() { - const u32 global_value = std::stoi(setting.ToStringGlobal()); - combobox->setCurrentIndex(find_index(global_value)); - }; + if (!Settings::IsConfiguringGlobal()) { + restore_func = [this, find_index]() { + const u32 global_value = std::stoi(setting.ToStringGlobal()); + combobox->setCurrentIndex(find_index(global_value)); + }; + + QObject::connect(combobox, QOverload::of(&QComboBox::activated), + [touch]() { touch(); }); + } return combobox; } -void Widget::CreateLineEdit(const QString& label, std::function& load_func, bool managed, - Settings::BasicSetting* other_setting) { - const bool has_checkbox = other_setting != nullptr; - if (has_checkbox && other_setting->TypeId() != typeid(bool)) { - LOG_WARNING(Frontend, "Extra setting requested but setting is not boolean"); - return; - } - - created = true; - - QHBoxLayout* layout{nullptr}; - std::function checkbox_load_func = []() {}; - - if (has_checkbox) { - layout = CreateCheckBox(other_setting, label, checkbox_load_func, managed); - } else { - layout = new QHBoxLayout(this); - layout->setContentsMargins(0, 0, 0, 0); - QLabel* q_label = CreateLabel(label); - layout->addWidget(q_label); - } - +QWidget* Widget::CreateLineEdit(std::function& serializer, + std::function& restore_func, + const std::function& touch, bool managed) { const QString text = QString::fromStdString(setting.ToString()); line_edit = new QLineEdit(this); line_edit->setText(text); - layout->addWidget(line_edit); + serializer = [this]() { return line_edit->text().toStdString(); }; if (!managed) { - return; + return line_edit; } - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { - checkbox_load_func(); - - std::string load_text = line_edit->text().toStdString(); - setting.LoadString(load_text); - }; - } else { - if (!has_checkbox) { - restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); - layout->addWidget(restore_button); - } - - QObject::connect(restore_button, &QAbstractButton::clicked, [&](bool) { - restore_button->setEnabled(false); - restore_button->setVisible(false); - + if (!Settings::IsConfiguringGlobal()) { + restore_func = [this]() { line_edit->setText(QString::fromStdString(setting.ToStringGlobal())); - }); - - QObject::connect(line_edit, &QLineEdit::textChanged, [&](QString) { - restore_button->setEnabled(true); - restore_button->setVisible(true); - }); - - load_func = [=]() { - checkbox_load_func(); - - bool using_global = !restore_button->isEnabled(); - setting.SetGlobal(using_global); - if (!using_global) { - setting.LoadString(line_edit->text().toStdString()); - } }; + + QObject::connect(line_edit, &QLineEdit::textChanged, [touch]() { touch(); }); } + + return line_edit; } -void Widget::CreateSlider(const QString& label, bool reversed, float multiplier, - std::function& load_func, bool managed, const QString& format, - Settings::BasicSetting* const other_setting) { - created = true; +QWidget* Widget::CreateSlider(bool reversed, float multiplier, const QString& format, + std::function& serializer, + std::function& restore_func, + const std::function& touch) { + QWidget* container = new QWidget(this); + QHBoxLayout* layout = new QHBoxLayout(container); - QHBoxLayout* layout = new QHBoxLayout(this); slider = new QSlider(Qt::Horizontal, this); - QLabel* qt_label = new QLabel(label, this); QLabel* feedback = new QLabel(this); - layout->addWidget(qt_label); layout->addWidget(slider); layout->addWidget(feedback); - qt_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + container->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->setContentsMargins(0, 0, 0, 0); @@ -265,60 +192,20 @@ void Widget::CreateSlider(const QString& label, bool reversed, float multiplier, slider->setInvertedAppearance(reversed); - if (!managed) { - return; + serializer = [this]() { return std::to_string(slider->value()); }; + + if (!Settings::IsConfiguringGlobal()) { + restore_func = [this]() { slider->setValue(std::stoi(setting.ToStringGlobal())); }; + + QObject::connect(slider, &QAbstractSlider::sliderReleased, [touch]() { touch(); }); } - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { setting.LoadString(std::to_string(slider->value())); }; - } else { - restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); - layout->addWidget(restore_button); - - QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { - slider->setValue(std::stoi(setting.ToStringGlobal())); - - restore_button->setEnabled(false); - restore_button->setVisible(false); - }); - - QObject::connect(slider, &QAbstractSlider::valueChanged, [=]() { - restore_button->setEnabled(true); - restore_button->setVisible(true); - }); - - load_func = [=]() { - bool using_global = !restore_button->isEnabled(); - setting.SetGlobal(using_global); - if (!using_global) { - setting.LoadString(std::to_string(slider->value())); - } - }; - } + return container; } -void Widget::CreateSpinBox(const QString& label, std::function& load_func, bool managed, - const QString& suffix, Settings::BasicSetting* other_setting) { - const bool has_checkbox = other_setting != nullptr; - if (has_checkbox && other_setting->TypeId() != typeid(bool)) { - LOG_WARNING(Frontend, "Extra setting requested but setting is not boolean"); - return; - } - created = true; - - QHBoxLayout* layout{nullptr}; - std::function checkbox_load_func = []() {}; - QLabel* q_label{nullptr}; - - if (has_checkbox) { - layout = CreateCheckBox(other_setting, label, checkbox_load_func, managed); - } else { - layout = new QHBoxLayout(this); - layout->setContentsMargins(0, 0, 0, 0); - q_label = CreateLabel(label); - layout->addWidget(q_label); - } - +QWidget* Widget::CreateSpinBox(const QString& suffix, std::function& serializer, + std::function& restore_func, + const std::function& touch) { const int min_val = std::stoi(setting.MinVal()); const int max_val = std::stoi(setting.MaxVal()); const int default_val = std::stoi(setting.ToString()); @@ -329,48 +216,29 @@ void Widget::CreateSpinBox(const QString& label, std::function& load_fun spinbox->setSuffix(suffix); spinbox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - layout->insertWidget(1, spinbox); + serializer = [this]() { return std::to_string(spinbox->value()); }; - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { - checkbox_load_func(); - setting.LoadString(std::to_string(spinbox->value())); - }; - } else { - if (!has_checkbox) { - restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); - layout->addWidget(restore_button); - } + if (!Settings::IsConfiguringGlobal()) { + restore_func = [this]() { spinbox->setValue(std::stoi(setting.ToStringGlobal())); }; - QObject::connect(restore_button, &QAbstractButton::clicked, - [this](bool) { spinbox->setValue(std::stoi(setting.ToStringGlobal())); }); - - QObject::connect(spinbox, QOverload::of(&QSpinBox::valueChanged), [this](int) { - restore_button->setEnabled(true); - restore_button->setVisible(true); - }); - - load_func = [=]() { - checkbox_load_func(); - - const bool using_global = !restore_button->isEnabled(); - setting.SetGlobal(using_global); - if (!using_global) { - setting.LoadString(std::to_string(spinbox->value())); + QObject::connect(spinbox, QOverload::of(&QSpinBox::valueChanged), [this, touch]() { + if (spinbox->value() != std::stoi(setting.ToStringGlobal())) { + touch(); } - }; + }); } + + return spinbox; } -void Widget::CreateHexEdit(const QString& label, std::function& load_func, bool managed, - Settings::BasicSetting* const other_setting) { - CreateLineEdit(label, load_func, false, other_setting); - if (!created || !managed) { - return; +QWidget* Widget::CreateHexEdit(std::function& serializer, + std::function& restore_func, + const std::function& touch) { + auto* data_component = CreateLineEdit(serializer, restore_func, touch, false); + if (data_component == nullptr) { + return nullptr; } - QLayout* layout = this->layout(); - auto to_hex = [=](const std::string& input) { return QString::fromStdString(fmt::format("{:08x}", std::stoi(input))); }; @@ -388,69 +256,21 @@ void Widget::CreateHexEdit(const QString& label, std::function& load_fun return std::to_string(std::stoul(line_edit->text().toStdString(), nullptr, 16)); }; - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { - other_setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); - setting.LoadString(hex_to_dec()); - }; - } else { - restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); - layout->addWidget(restore_button); + serializer = [hex_to_dec]() { return hex_to_dec(); }; - QObject::connect(restore_button, &QAbstractButton::clicked, [=](bool) { - line_edit->setText(to_hex(setting.ToStringGlobal())); - checkbox->setCheckState(other_setting->ToStringGlobal() == "true" ? Qt::Checked - : Qt::Unchecked); + if (!Settings::IsConfiguringGlobal()) { + restore_func = [this, to_hex]() { line_edit->setText(to_hex(setting.ToStringGlobal())); }; - restore_button->setEnabled(false); - restore_button->setVisible(false); - }); - - QObject::connect(line_edit, &QLineEdit::textEdited, [&]() { - restore_button->setEnabled(true); - restore_button->setVisible(true); - }); - - QObject::connect(checkbox, &QAbstractButton::clicked, [&]() { - restore_button->setEnabled(true); - restore_button->setVisible(true); - }); - - load_func = [=]() { - const bool using_global = !restore_button->isEnabled(); - other_setting->SetGlobal(using_global); - setting.SetGlobal(using_global); - - if (!using_global) { - other_setting->LoadString(checkbox->checkState() == Qt::Checked ? "true" : "false"); - setting.LoadString(hex_to_dec()); - } - }; + QObject::connect(line_edit, &QLineEdit::textChanged, [touch]() { touch(); }); } + + return line_edit; } -void Widget::CreateDateTimeEdit(const QString& label, std::function& load_func, - bool managed, bool restrict, - Settings::BasicSetting* const other_setting) { - const bool has_checkbox = other_setting != nullptr; - if ((restrict && !has_checkbox) || (has_checkbox && other_setting->TypeId() != typeid(bool))) { - LOG_WARNING(Frontend, "Extra setting or restrict requested but is not boolean"); - return; - } - created = true; - - QHBoxLayout* layout{nullptr}; - std::function checkbox_load_func = []() {}; - - if (has_checkbox) { - layout = CreateCheckBox(other_setting, label, checkbox_load_func, managed); - } else { - layout = new QHBoxLayout(this); - QLabel* q_label = CreateLabel(label); - layout->addWidget(q_label); - } - - const bool disabled = other_setting->ToString() != "true"; +QWidget* Widget::CreateDateTimeEdit(bool disabled, bool restrict, + std::function& serializer, + std::function& restore_func, + const std::function& touch) { const long long current_time = QDateTime::currentSecsSinceEpoch(); const s64 the_time = disabled ? current_time : std::stoll(setting.ToString()); const auto default_val = QDateTime::fromSecsSinceEpoch(the_time); @@ -460,27 +280,9 @@ void Widget::CreateDateTimeEdit(const QString& label, std::function& loa date_time_edit->setMinimumDateTime(QDateTime::fromSecsSinceEpoch(0)); date_time_edit->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - layout->insertWidget(1, date_time_edit); - - if (!managed) { - return; - } - - if (Settings::IsConfiguringGlobal()) { - load_func = [=]() { - checkbox_load_func(); - if (restrict && checkbox->checkState() == Qt::Unchecked) { - return; - } - - setting.LoadString(std::to_string(date_time_edit->dateTime().toSecsSinceEpoch())); - }; - } else { - if (!has_checkbox) { - restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); - layout->addWidget(restore_button); - } + serializer = [this]() { return std::to_string(date_time_edit->dateTime().toSecsSinceEpoch()); }; + if (!Settings::IsConfiguringGlobal()) { auto get_clear_val = [=]() { return QDateTime::fromSecsSinceEpoch([=]() { if (restrict && checkbox->checkState() == Qt::Checked) { @@ -490,33 +292,21 @@ void Widget::CreateDateTimeEdit(const QString& label, std::function& loa }()); }; - QObject::connect(restore_button, &QAbstractButton::clicked, - [=](bool) { date_time_edit->setDateTime(get_clear_val()); }); + restore_func = [=]() { date_time_edit->setDateTime(get_clear_val()); }; QObject::connect(date_time_edit, &QDateTimeEdit::editingFinished, [=]() { if (date_time_edit->dateTime() != get_clear_val()) { - restore_button->setEnabled(true); - restore_button->setVisible(true); + touch(); } }); - - load_func = [=]() { - checkbox_load_func(); - if (restrict && checkbox->checkState() == Qt::Unchecked) { - return; - } - - const bool using_global = !restore_button->isEnabled(); - other_setting->SetGlobal(using_global); - if (!using_global) { - setting.LoadString(std::to_string(date_time_edit->dateTime().toSecsSinceEpoch())); - } - }; } + + return date_time_edit; } void Widget::SetupComponent(const QString& label, std::function& load_func, bool managed, - RequestType request, Settings::BasicSetting* other_setting) { + RequestType request, float multiplier, + Settings::BasicSetting* other_setting, const QString& string) { created = true; const auto type = setting.TypeId(); @@ -531,42 +321,74 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu "Extra setting specified but is not bool, refusing to create checkbox for it."); } - if (require_checkbox) { - } else { - QLabel* qt_label = CreateLabel(label); - layout->addWidget(qt_label); - } + std::function checkbox_serializer = []() -> std::string { return {}; }; + std::function checkbox_restore_func = []() {}; - std::function touched = []() {}; + std::function touch = []() {}; std::function serializer = []() -> std::string { return {}; }; std::function restore_func = []() {}; QWidget* data_component{nullptr}; - if (!Settings::IsConfiguringGlobal()) { + if (!Settings::IsConfiguringGlobal() && managed) { restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); - touched = [this]() { + touch = [this]() { + LOG_DEBUG(Frontend, "Setting custom setting for {}", setting.GetLabel()); restore_button->setEnabled(true); restore_button->setVisible(true); }; } - if (setting.IsEnum()) { - data_component = CreateCombobox(serializer, restore_func, touched); + if (require_checkbox) { + QWidget* lhs = + CreateCheckBox(other_setting, label, checkbox_serializer, checkbox_restore_func, touch); + layout->addWidget(lhs); + } else if (setting.TypeId() != typeid(bool)) { + QLabel* qt_label = CreateLabel(label); + layout->addWidget(qt_label); + } + + if (setting.TypeId() == typeid(bool)) { + data_component = CreateCheckBox(&setting, label, serializer, restore_func, touch); + } else if (setting.IsEnum()) { + data_component = CreateCombobox(serializer, restore_func, touch); } else if (type == typeid(u32) || type == typeid(int) || type == typeid(u16) || type == typeid(s64) || type == typeid(u8)) { switch (request) { + case RequestType::Slider: + case RequestType::ReverseSlider: + data_component = CreateSlider(request == RequestType::ReverseSlider, multiplier, string, + serializer, restore_func, touch); + break; + case RequestType::Default: + case RequestType::LineEdit: + data_component = CreateLineEdit(serializer, restore_func, touch); + break; + case RequestType::DateTimeEdit: + data_component = CreateDateTimeEdit(other_setting->ToString() != "true", true, + serializer, restore_func, touch); + break; + case RequestType::SpinBox: + data_component = CreateSpinBox(string, serializer, restore_func, touch); + break; + case RequestType::HexEdit: + data_component = CreateHexEdit(serializer, restore_func, touch); + break; case RequestType::ComboBox: - data_component = CreateCombobox(serializer, restore_func, touched); + data_component = CreateCombobox(serializer, restore_func, touch); break; default: UNIMPLEMENTED(); } } else if (type == typeid(std::string)) { switch (request) { + case RequestType::Default: + case RequestType::LineEdit: + data_component = CreateLineEdit(serializer, restore_func, touch); + break; case RequestType::ComboBox: - data_component = CreateCombobox(serializer, restore_func, touched); + data_component = CreateCombobox(serializer, restore_func, touch); break; default: UNIMPLEMENTED(); @@ -586,23 +408,36 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu } if (Settings::IsConfiguringGlobal()) { - load_func = [this, serializer]() { setting.LoadString(serializer()); }; + load_func = [this, serializer, checkbox_serializer, require_checkbox, other_setting]() { + if (require_checkbox) { + other_setting->LoadString(checkbox_serializer()); + } + setting.LoadString(serializer()); + }; } else { layout->addWidget(restore_button); - QObject::connect(restore_button, &QAbstractButton::clicked, [this, restore_func](bool) { - restore_button->setEnabled(false); - restore_button->setVisible(false); + QObject::connect(restore_button, &QAbstractButton::clicked, + [this, restore_func, checkbox_restore_func](bool) { + restore_button->setEnabled(false); + restore_button->setVisible(false); - restore_func(); - }); + checkbox_restore_func(); + restore_func(); + }); - load_func = [this, serializer]() { + load_func = [this, serializer, require_checkbox, checkbox_serializer, other_setting]() { bool using_global = !restore_button->isEnabled(); setting.SetGlobal(using_global); if (!using_global) { setting.LoadString(serializer()); } + if (require_checkbox) { + other_setting->SetGlobal(using_global); + if (!using_global) { + other_setting->LoadString(checkbox_serializer()); + } + } }; } } @@ -626,7 +461,6 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati return; } - const auto type = setting.TypeId(); const int id = setting.Id(); const auto [label, tooltip] = [&]() { @@ -646,57 +480,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati std::function load_func = []() {}; - if (type == typeid(bool)) { - CreateCheckBox(&setting, label, load_func, managed); - } else if (setting.IsEnum()) { - SetupComponent(label, load_func, managed, request, other_setting); - } else if (type == typeid(u32) || type == typeid(int) || type == typeid(u16) || - type == typeid(s64) || type == typeid(u8)) { - switch (request) { - case RequestType::Slider: - case RequestType::ReverseSlider: - CreateSlider(label, request == RequestType::ReverseSlider, multiplier, load_func, - managed, string); - break; - case RequestType::LineEdit: - case RequestType::Default: - CreateLineEdit(label, load_func, managed); - break; - case RequestType::ComboBox: - SetupComponent(label, load_func, managed, request, other_setting); - break; - case RequestType::DateTimeEdit: - CreateDateTimeEdit(label, load_func, managed, true, other_setting); - break; - case RequestType::SpinBox: - CreateSpinBox(label, load_func, managed, string, other_setting); - break; - case RequestType::HexEdit: - CreateHexEdit(label, load_func, managed, other_setting); - break; - default: - LOG_WARNING(Frontend, "Requested widget is unimplemented."); - break; - } - } else if (type == typeid(std::string)) { - switch (request) { - case RequestType::Default: - case RequestType::LineEdit: - CreateLineEdit(label, load_func, managed); - break; - case RequestType::ComboBox: - SetupComponent(label, load_func, managed, request, other_setting); - break; - case RequestType::SpinBox: - case RequestType::Slider: - case RequestType::ReverseSlider: - case RequestType::HexEdit: - case RequestType::DateTimeEdit: - case RequestType::MaxEnum: - LOG_WARNING(Frontend, "Requested widget is unimplemented."); - break; - } - } + SetupComponent(label, load_func, managed, request, multiplier, other_setting, string); if (!created) { LOG_WARNING(Frontend, "No widget was created for \"{}\"", setting.GetLabel()); diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 2ed738a06..01348e442 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -57,26 +57,32 @@ public: private: void SetupComponent(const QString& label, std::function& load_func, bool managed, - RequestType request, Settings::BasicSetting* other_setting); + RequestType request, float multiplier, + Settings::BasicSetting* other_setting, const QString& string); QLabel* CreateLabel(const QString& text); - QHBoxLayout* CreateCheckBox(Settings::BasicSetting* bool_setting, const QString& label, - std::function& load_func, bool managed); + QWidget* CreateCheckBox(Settings::BasicSetting* bool_setting, const QString& label, + std::function& serializer, + std::function& restore_func, + const std::function& touch); QWidget* CreateCombobox(std::function& serializer, std::function& restore_func, - const std::function& touched); - void CreateLineEdit(const QString& label, std::function& load_func, bool managed, - Settings::BasicSetting* const other_setting = nullptr); - void CreateHexEdit(const QString& label, std::function& load_func, bool managed, - Settings::BasicSetting* const other_setting = nullptr); - void CreateSlider(const QString& label, bool reversed, float multiplier, - std::function& load_func, bool managed, const QString& format, - Settings::BasicSetting* const other_setting = nullptr); - void CreateDateTimeEdit(const QString& label, std::function& load_func, bool managed, - bool restrict, Settings::BasicSetting* const other_setting = nullptr); - void CreateSpinBox(const QString& label, std::function& load_func, bool managed, - const QString& suffix, Settings::BasicSetting* other_setting = nullptr); + const std::function& touch); + QWidget* CreateLineEdit(std::function& serializer, + std::function& restore_func, const std::function& touch, + bool managed = true); + QWidget* CreateHexEdit(std::function& serializer, + std::function& restore_func, const std::function& touch); + QWidget* CreateSlider(bool reversed, float multiplier, const QString& format, + std::function& serializer, + std::function& restore_func, const std::function& touch); + QWidget* CreateDateTimeEdit(bool disabled, bool restrict, + std::function& serializer, + std::function& restore_func, + const std::function& touch); + QWidget* CreateSpinBox(const QString& suffix, std::function& serializer, + std::function& restore_func, const std::function& touch); QWidget* parent; const TranslationMap& translations; From 25cea2ef27cd93a797cdbb5ec9aac79845d6af1e Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 6 Jun 2023 21:41:51 -0400 Subject: [PATCH 062/155] shared_widget: Fix includes --- src/yuzu/configuration/shared_widget.cpp | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 096ec451d..52e617da2 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -1,5 +1,8 @@ #include #include +#include +#include +#include #include #include #include @@ -12,14 +15,8 @@ #include #include #include +#include #include -#include -#include -#include -#include -#include -#include -#include #include "common/common_types.h" #include "common/settings.h" #include "yuzu/configuration/configuration_shared.h" From f7948b7b64900451b34a639ca0564c6950b5e58e Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 6 Jun 2023 21:55:46 -0400 Subject: [PATCH 063/155] settings,general: Rename/reorder setting ids --- src/yuzu/configuration/shared_translation.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 50e19ede1..5d4e29a08 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -72,7 +72,7 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(Settings, shader_backend, "Shader Backend:", ""); INSERT(Settings, resolution_setup, "Resolution:", ""); INSERT(Settings, scaling_filter, "Window Adapting Filter:", ""); - INSERT(Settings, fsr_sharpening_slider, "AMD FidelityFX™ Super Resolution Sharpness:", ""); + INSERT(Settings, fsr_sharpening_slider, "FSR Sharpness:", ""); INSERT(Settings, anti_aliasing, "Anti-Aliasing Method:", ""); INSERT(Settings, fullscreen_mode, "Fullscreen Mode:", ""); INSERT(Settings, aspect_ratio, "Aspect Ratio:", ""); From 9e3c94bb3dd1a9065977930a985be43f6052044c Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 6 Jun 2023 22:30:02 -0400 Subject: [PATCH 064/155] configuration: Use IDs to sort holds --- src/yuzu/configuration/configure_general.cpp | 6 +++--- src/yuzu/configuration/configure_graphics.cpp | 14 +++++--------- .../configuration/configure_graphics_advanced.cpp | 10 +++------- src/yuzu/configuration/configure_system.cpp | 13 +++++-------- 4 files changed, 16 insertions(+), 27 deletions(-) diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index fdae83c64..625dd75dd 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -37,7 +37,7 @@ void ConfigureGeneral::SetConfiguration() { const bool runtime_lock = !system.IsPoweredOn(); QLayout& layout = *ui->general_widget->layout(); - std::map hold{}; + std::map hold{}; for (const auto setting : UISettings::values.linkage.by_category[Settings::Category::UiGeneral]) { @@ -49,10 +49,10 @@ void ConfigureGeneral::SetConfiguration() { continue; } - hold.insert({setting->GetLabel(), widget}); + hold.emplace(setting->Id(), widget); } - for (const auto& [label, widget] : hold) { + for (const auto& [id, widget] : hold) { layout.addWidget(widget); } } diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index a4dac659f..59702603a 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -226,12 +226,10 @@ void ConfigureGraphics::Setup() { QLayout& graphics_layout = *ui->graphics_widget->layout(); - std::map> hold_graphics; + std::map hold_graphics; std::forward_list hold_api; for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { - const auto& setting_label = setting->GetLabel(); - ConfigurationShared::Widget* widget = [&]() { if (setting->Id() == Settings::values.vulkan_device.Id() || setting->Id() == Settings::values.shader_backend.Id() || @@ -284,16 +282,14 @@ void ConfigureGraphics::Setup() { shader_backend_widget = widget; } else if (setting->Id() == Settings::values.vsync_mode.Id()) { vsync_mode_combobox = widget->combobox; - hold_graphics[setting->IsEnum()][setting_label] = widget; + hold_graphics.emplace(setting->Id(), widget); } else { - hold_graphics[setting->IsEnum()][setting_label] = widget; + hold_graphics.emplace(setting->Id(), widget); } } - for (const auto& [_, settings] : hold_graphics) { - for (const auto& [label, widget] : settings) { - graphics_layout.addWidget(widget); - } + for (const auto& [id, widget] : hold_graphics) { + graphics_layout.addWidget(widget); } for (auto widget : hold_api) { diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index c5e21da02..8c932f10a 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -31,7 +31,7 @@ ConfigureGraphicsAdvanced::~ConfigureGraphicsAdvanced() = default; void ConfigureGraphicsAdvanced::SetConfiguration() { const bool runtime_lock = !system.IsPoweredOn(); auto& layout = *ui->populate_target->layout(); - std::map hold{}; // A map will sort the data for us + std::map hold{}; // A map will sort the data for us for (auto setting : Settings::values.linkage.by_category[Settings::Category::RendererAdvanced]) { @@ -43,17 +43,13 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { continue; } - if (!setting->IsEnum()) { - hold.emplace(setting->GetLabel(), widget); - } else { - layout.addWidget(widget); - } + hold.emplace(setting->Id(), widget); if (setting->Id() == Settings::values.enable_compute_pipelines.Id()) { checkbox_enable_compute_pipelines = widget; } } - for (const auto& [label, widget] : hold) { + for (const auto& [id, widget] : hold) { layout.addWidget(widget); } } diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index ae59d2ee7..4b0e0a649 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -109,8 +109,8 @@ void ConfigureSystem::Setup() { auto& core_layout = *ui->core_widget->layout(); auto& system_layout = *ui->system_widget->layout(); - std::map core_hold{}; - std::map> system_hold{}; + std::map core_hold{}; + std::map system_hold{}; std::forward_list settings; auto push = [&settings](std::forward_list& list) { @@ -165,10 +165,10 @@ void ConfigureSystem::Setup() { switch (setting->Category()) { case Settings::Category::Core: - core_hold[setting->GetLabel()] = widget; + core_hold.emplace(setting->Id(), widget); break; case Settings::Category::System: - system_hold[setting->IsEnum()].insert(std::pair{setting->GetLabel(), widget}); + system_hold.emplace(setting->Id(), widget); break; default: delete widget; @@ -177,10 +177,7 @@ void ConfigureSystem::Setup() { for (const auto& [label, widget] : core_hold) { core_layout.addWidget(widget); } - for (const auto& [label, widget] : system_hold[true]) { - system_layout.addWidget(widget); - } - for (const auto& [label, widget] : system_hold[false]) { + for (const auto& [id, widget] : system_hold) { system_layout.addWidget(widget); } } From d146dd9d123a999e40307a93403239b81b04bffc Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 7 Jun 2023 01:52:23 -0400 Subject: [PATCH 065/155] settings,general: Rename non-confirming enums --- src/audio_core/sink/sink_details.cpp | 5 ++- src/common/settings.cpp | 6 +-- src/common/settings.h | 40 +++++++++++-------- src/common/settings_enums.h | 37 +++++++++-------- src/core/arm/dynarmic/arm_dynarmic_32.cpp | 6 +-- src/core/arm/dynarmic/arm_dynarmic_64.cpp | 6 +-- src/core/telemetry_session.cpp | 26 ++++++------ src/video_core/host1x/codecs/codec.cpp | 2 +- src/video_core/host1x/codecs/h264.cpp | 2 +- .../renderer_opengl/gl_compute_pipeline.cpp | 6 +-- src/video_core/renderer_opengl/gl_device.cpp | 8 ++-- .../renderer_opengl/gl_graphics_pipeline.cpp | 6 +-- .../renderer_opengl/gl_shader_cache.cpp | 12 +++--- .../renderer_opengl/gl_texture_cache.cpp | 4 +- .../renderer_vulkan/vk_swapchain.cpp | 12 +++--- .../renderer_vulkan/vk_texture_cache.cpp | 6 +-- src/yuzu/configuration/config.cpp | 8 ++-- src/yuzu/configuration/config.h | 6 +-- src/yuzu/configuration/configure_audio.cpp | 2 +- src/yuzu/configuration/configure_cpu.cpp | 6 +-- src/yuzu/configuration/configure_graphics.cpp | 10 ++--- src/yuzu/configuration/shared_translation.cpp | 36 ++++++++--------- src/yuzu/main.cpp | 14 +++---- 23 files changed, 136 insertions(+), 130 deletions(-) diff --git a/src/audio_core/sink/sink_details.cpp b/src/audio_core/sink/sink_details.cpp index 751e97bfc..027bfa517 100644 --- a/src/audio_core/sink/sink_details.cpp +++ b/src/audio_core/sink/sink_details.cpp @@ -82,11 +82,12 @@ const SinkDetails& GetOutputSinkDetails(Settings::AudioEngine sink_id) { #else iter = std::begin(sink_details); #endif - LOG_INFO(Service_Audio, "Auto-selecting the {} backend", Settings::TranslateEnum(iter->id)); + LOG_INFO(Service_Audio, "Auto-selecting the {} backend", + Settings::CanonicalizeEnum(iter->id)); } if (iter == std::end(sink_details)) { - LOG_ERROR(Audio, "Invalid sink_id {}", Settings::TranslateEnum(sink_id)); + LOG_ERROR(Audio, "Invalid sink_id {}", Settings::CanonicalizeEnum(sink_id)); iter = find_backend(Settings::AudioEngine::Null); } diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 8bfda5667..0a8729b5a 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -122,12 +122,12 @@ void SetConfiguringGlobal(bool is_global) { } bool IsGPULevelExtreme() { - return values.gpu_accuracy.GetValue() == GPUAccuracy::Extreme; + return values.gpu_accuracy.GetValue() == GpuAccuracy::Extreme; } bool IsGPULevelHigh() { - return values.gpu_accuracy.GetValue() == GPUAccuracy::Extreme || - values.gpu_accuracy.GetValue() == GPUAccuracy::High; + return values.gpu_accuracy.GetValue() == GpuAccuracy::Extreme || + values.gpu_accuracy.GetValue() == GpuAccuracy::High; } bool IsFastmemEnabled() { diff --git a/src/common/settings.h b/src/common/settings.h index a9ce113ef..141408d3e 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -91,6 +91,7 @@ public: return {}; } virtual void LoadString(const std::string& load) = 0; + virtual std::string Canonicalize() const = 0; virtual const std::string& GetLabel() const = 0; virtual std::string DefaultToString() const = 0; virtual bool Save() const = 0; @@ -102,7 +103,7 @@ public: virtual std::string MinVal() const = 0; virtual std::string MaxVal() const = 0; virtual bool UsingGlobal() const { - return false; + return true; } }; @@ -245,7 +246,7 @@ protected: } else if constexpr (std::is_same()) { return value_ ? "true" : "false"; } else if (std::is_same()) { - return TranslateEnum(value_); + return CanonicalizeEnum(value_); } else { return std::to_string(static_cast(value_)); } @@ -321,6 +322,13 @@ public: } } + [[nodiscard]] std::string constexpr Canonicalize() const override { + if constexpr (std::is_enum::value) { + return CanonicalizeEnum(this->GetValue()); + } + return ToString(this->GetValue()); + } + /** * Returns the save preference of the setting i.e. when saving or reading the setting from a * frontend, whether this setting should be skipped. @@ -560,8 +568,8 @@ struct Values { linkage, false, "use_unsafe_extended_memory_layout", Category::Core}; // Cpu - SwitchableSetting cpu_accuracy{linkage, CPUAccuracy::Auto, - CPUAccuracy::Auto, CPUAccuracy::Paranoid, + SwitchableSetting cpu_accuracy{linkage, CpuAccuracy::Auto, + CpuAccuracy::Auto, CpuAccuracy::Paranoid, "cpu_accuracy", Category::Cpu}; // TODO: remove cpu_accuracy_first_time, migration setting added 8 July 2021 Setting cpu_accuracy_first_time{linkage, true, "cpu_accuracy_first_time", Category::Cpu}; @@ -657,28 +665,28 @@ struct Values { linkage, 100, 0, 9999, "speed_limit", Category::Renderer, true, true}; SwitchableSetting use_disk_shader_cache{linkage, true, "use_disk_shader_cache", Category::Renderer}; - SwitchableSetting gpu_accuracy{linkage, - GPUAccuracy::High, - GPUAccuracy::Normal, - GPUAccuracy::Extreme, + SwitchableSetting gpu_accuracy{linkage, + GpuAccuracy::High, + GpuAccuracy::Normal, + GpuAccuracy::Extreme, "gpu_accuracy", Category::RendererAdvanced, true, true}; SwitchableSetting use_asynchronous_gpu_emulation{ linkage, true, "use_asynchronous_gpu_emulation", Category::Renderer}; - SwitchableSetting nvdec_emulation{linkage, NvdecEmulation::GPU, + SwitchableSetting nvdec_emulation{linkage, NvdecEmulation::Gpu, "nvdec_emulation", Category::Renderer}; SwitchableSetting accelerate_astc{linkage, - AstcDecodeMode::CPU, - AstcDecodeMode::CPU, - AstcDecodeMode::CPUAsynchronous, + AstcDecodeMode::Cpu, + AstcDecodeMode::Cpu, + AstcDecodeMode::CpuAsynchronous, "accelerate_astc", Category::Renderer}; Setting vsync_mode{linkage, - VSyncMode::FIFO, + VSyncMode::Fifo, VSyncMode::Immediate, - VSyncMode::FIFORelaxed, + VSyncMode::FifoRelaxed, "use_vsync", Category::Renderer, true, @@ -686,7 +694,7 @@ struct Values { SwitchableSetting use_reactive_flushing{linkage, true, "use_reactive_flushing", Category::RendererAdvanced}; SwitchableSetting shader_backend{ - linkage, ShaderBackend::GLSL, ShaderBackend::GLSL, ShaderBackend::SPIRV, + linkage, ShaderBackend::Glsl, ShaderBackend::Glsl, ShaderBackend::SpirV, "shader_backend", Category::Renderer}; SwitchableSetting use_asynchronous_shaders{linkage, false, "use_asynchronous_shaders", Category::RendererAdvanced}; @@ -730,7 +738,7 @@ struct Values { Language::PortugueseBrazilian, "language_index", Category::System}; - SwitchableSetting region_index{linkage, Region::USA, Region::Japan, + SwitchableSetting region_index{linkage, Region::Usa, Region::Japan, Region::Taiwan, "region_index", Category::System}; SwitchableSetting time_zone_index{linkage, TimeZone::Auto, TimeZone::Auto, TimeZone::Zulu, diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index f48fb7bd4..6cd2ac28b 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -47,7 +47,7 @@ enum class Language : u32 { enum class Region : u32 { Japan, - USA, + Usa, Europe, Australia, China, @@ -114,9 +114,9 @@ enum class AnisotropyMode : u32 { }; enum class AstcDecodeMode : u32 { - CPU = 0, - GPU = 1, - CPUAsynchronous = 2, + Cpu = 0, + Gpu = 1, + CpuAsynchronous = 2, }; enum class AstcRecompression : u32 { @@ -128,8 +128,8 @@ enum class AstcRecompression : u32 { enum class VSyncMode : u32 { Immediate = 0, Mailbox = 1, - FIFO = 2, - FIFORelaxed = 3, + Fifo = 2, + FifoRelaxed = 3, }; enum class RendererBackend : u32 { @@ -139,19 +139,18 @@ enum class RendererBackend : u32 { }; enum class ShaderBackend : u32 { - GLSL = 0, - GLASM = 1, - SPIRV = 2, + Glsl = 0, + Glasm = 1, + SpirV = 2, }; -enum class GPUAccuracy : u32 { +enum class GpuAccuracy : u32 { Normal = 0, High = 1, Extreme = 2, - MaxEnum = 3, }; -enum class CPUAccuracy : u32 { +enum class CpuAccuracy : u32 { Auto = 0, Accurate = 1, Unsafe = 2, @@ -165,8 +164,8 @@ enum class FullscreenMode : u32 { enum class NvdecEmulation : u32 { Off = 0, - CPU = 1, - GPU = 2, + Cpu = 1, + Gpu = 2, }; enum class ResolutionSetup : u32 { @@ -220,18 +219,18 @@ static std::map> translations = { static std::string empty_string{}; template -const std::string& TranslateEnum(Type id) { - auto& group = translations.at(typeid(Type)); +const std::string& CanonicalizeEnum(Type id) { + auto& group = canonicalizations.at(typeid(Type)); for (auto& [name, value] : group) { if (static_cast(value) == id) { return name; } } - return empty_string; + return invalid_string; } template -static Type ToEnum(const std::string& text) { - return static_cast(translations.at(typeid(Type)).at(text)); +static Type ToEnum(const std::string& canonicalization) { + return static_cast(canonicalizations.at(typeid(Type)).at(canonicalization)); } } // namespace Settings diff --git a/src/core/arm/dynarmic/arm_dynarmic_32.cpp b/src/core/arm/dynarmic/arm_dynarmic_32.cpp index 3b82fb73c..dc7cfd239 100644 --- a/src/core/arm/dynarmic/arm_dynarmic_32.cpp +++ b/src/core/arm/dynarmic/arm_dynarmic_32.cpp @@ -287,7 +287,7 @@ std::shared_ptr ARM_Dynarmic_32::MakeJit(Common::PageTable* } } else { // Unsafe optimizations - if (Settings::values.cpu_accuracy.GetValue() == Settings::CPUAccuracy::Unsafe) { + if (Settings::values.cpu_accuracy.GetValue() == Settings::CpuAccuracy::Unsafe) { config.unsafe_optimizations = true; if (Settings::values.cpuopt_unsafe_unfuse_fma) { config.optimizations |= Dynarmic::OptimizationFlag::Unsafe_UnfuseFMA; @@ -307,7 +307,7 @@ std::shared_ptr ARM_Dynarmic_32::MakeJit(Common::PageTable* } // Curated optimizations - if (Settings::values.cpu_accuracy.GetValue() == Settings::CPUAccuracy::Auto) { + if (Settings::values.cpu_accuracy.GetValue() == Settings::CpuAccuracy::Auto) { config.unsafe_optimizations = true; config.optimizations |= Dynarmic::OptimizationFlag::Unsafe_UnfuseFMA; config.optimizations |= Dynarmic::OptimizationFlag::Unsafe_IgnoreStandardFPCRValue; @@ -316,7 +316,7 @@ std::shared_ptr ARM_Dynarmic_32::MakeJit(Common::PageTable* } // Paranoia mode for debugging optimizations - if (Settings::values.cpu_accuracy.GetValue() == Settings::CPUAccuracy::Paranoid) { + if (Settings::values.cpu_accuracy.GetValue() == Settings::CpuAccuracy::Paranoid) { config.unsafe_optimizations = false; config.optimizations = Dynarmic::no_optimizations; } diff --git a/src/core/arm/dynarmic/arm_dynarmic_64.cpp b/src/core/arm/dynarmic/arm_dynarmic_64.cpp index bb97ed5bc..a4cc74ebf 100644 --- a/src/core/arm/dynarmic/arm_dynarmic_64.cpp +++ b/src/core/arm/dynarmic/arm_dynarmic_64.cpp @@ -347,7 +347,7 @@ std::shared_ptr ARM_Dynarmic_64::MakeJit(Common::PageTable* } } else { // Unsafe optimizations - if (Settings::values.cpu_accuracy.GetValue() == Settings::CPUAccuracy::Unsafe) { + if (Settings::values.cpu_accuracy.GetValue() == Settings::CpuAccuracy::Unsafe) { config.unsafe_optimizations = true; if (Settings::values.cpuopt_unsafe_unfuse_fma) { config.optimizations |= Dynarmic::OptimizationFlag::Unsafe_UnfuseFMA; @@ -367,7 +367,7 @@ std::shared_ptr ARM_Dynarmic_64::MakeJit(Common::PageTable* } // Curated optimizations - if (Settings::values.cpu_accuracy.GetValue() == Settings::CPUAccuracy::Auto) { + if (Settings::values.cpu_accuracy.GetValue() == Settings::CpuAccuracy::Auto) { config.unsafe_optimizations = true; config.optimizations |= Dynarmic::OptimizationFlag::Unsafe_UnfuseFMA; config.fastmem_address_space_bits = 64; @@ -375,7 +375,7 @@ std::shared_ptr ARM_Dynarmic_64::MakeJit(Common::PageTable* } // Paranoia mode for debugging optimizations - if (Settings::values.cpu_accuracy.GetValue() == Settings::CPUAccuracy::Paranoid) { + if (Settings::values.cpu_accuracy.GetValue() == Settings::CpuAccuracy::Paranoid) { config.unsafe_optimizations = false; config.optimizations = Dynarmic::no_optimizations; } diff --git a/src/core/telemetry_session.cpp b/src/core/telemetry_session.cpp index c058ac2c7..62b3f6636 100644 --- a/src/core/telemetry_session.cpp +++ b/src/core/telemetry_session.cpp @@ -61,16 +61,14 @@ static const char* TranslateRenderer(Settings::RendererBackend backend) { return "Unknown"; } -static const char* TranslateGPUAccuracyLevel(Settings::GPUAccuracy backend) { +static const char* TranslateGPUAccuracyLevel(Settings::GpuAccuracy backend) { switch (backend) { - case Settings::GPUAccuracy::Normal: + case Settings::GpuAccuracy::Normal: return "Normal"; - case Settings::GPUAccuracy::High: + case Settings::GpuAccuracy::High: return "High"; - case Settings::GPUAccuracy::Extreme: + case Settings::GpuAccuracy::Extreme: return "Extreme"; - case Settings::GPUAccuracy::MaxEnum: - break; } return "Unknown"; } @@ -79,9 +77,9 @@ static const char* TranslateNvdecEmulation(Settings::NvdecEmulation backend) { switch (backend) { case Settings::NvdecEmulation::Off: return "Off"; - case Settings::NvdecEmulation::CPU: + case Settings::NvdecEmulation::Cpu: return "CPU"; - case Settings::NvdecEmulation::GPU: + case Settings::NvdecEmulation::Gpu: return "GPU"; } return "Unknown"; @@ -93,9 +91,9 @@ static constexpr const char* TranslateVSyncMode(Settings::VSyncMode mode) { return "Immediate"; case Settings::VSyncMode::Mailbox: return "Mailbox"; - case Settings::VSyncMode::FIFO: + case Settings::VSyncMode::Fifo: return "FIFO"; - case Settings::VSyncMode::FIFORelaxed: + case Settings::VSyncMode::FifoRelaxed: return "FIFO Relaxed"; } return "Unknown"; @@ -103,11 +101,11 @@ static constexpr const char* TranslateVSyncMode(Settings::VSyncMode mode) { static constexpr const char* TranslateASTCDecodeMode(Settings::AstcDecodeMode mode) { switch (mode) { - case Settings::AstcDecodeMode::CPU: + case Settings::AstcDecodeMode::Cpu: return "CPU"; - case Settings::AstcDecodeMode::GPU: + case Settings::AstcDecodeMode::Gpu: return "GPU"; - case Settings::AstcDecodeMode::CPUAsynchronous: + case Settings::AstcDecodeMode::CpuAsynchronous: return "CPU Asynchronous"; } return "Unknown"; @@ -255,7 +253,7 @@ void TelemetrySession::AddInitialInfo(Loader::AppLoader& app_loader, // Log user configuration information constexpr auto field_type = Telemetry::FieldType::UserConfig; AddField(field_type, "Audio_SinkId", - Settings::TranslateEnum(Settings::values.sink_id.GetValue())); + Settings::CanonicalizeEnum(Settings::values.sink_id.GetValue())); AddField(field_type, "Core_UseMultiCore", Settings::values.use_multi_core.GetValue()); AddField(field_type, "Renderer_Backend", TranslateRenderer(Settings::values.renderer_backend.GetValue())); diff --git a/src/video_core/host1x/codecs/codec.cpp b/src/video_core/host1x/codecs/codec.cpp index da07a556f..220cce28a 100644 --- a/src/video_core/host1x/codecs/codec.cpp +++ b/src/video_core/host1x/codecs/codec.cpp @@ -247,7 +247,7 @@ void Codec::Initialize() { av_codec = avcodec_find_decoder(codec); InitializeAvCodecContext(); - if (Settings::values.nvdec_emulation.GetValue() == Settings::NvdecEmulation::GPU) { + if (Settings::values.nvdec_emulation.GetValue() == Settings::NvdecEmulation::Gpu) { InitializeGpuDecoder(); } if (const int res = avcodec_open2(av_codec_ctx, av_codec, nullptr); res < 0) { diff --git a/src/video_core/host1x/codecs/h264.cpp b/src/video_core/host1x/codecs/h264.cpp index 862904e39..ece79b1e2 100644 --- a/src/video_core/host1x/codecs/h264.cpp +++ b/src/video_core/host1x/codecs/h264.cpp @@ -84,7 +84,7 @@ std::span H264::ComposeFrame(const Host1x::NvdecCommon::NvdecRegisters // TODO (ameerj): Where do we get this number, it seems to be particular for each stream const auto nvdec_decoding = Settings::values.nvdec_emulation.GetValue(); - const bool uses_gpu_decoding = nvdec_decoding == Settings::NvdecEmulation::GPU; + const bool uses_gpu_decoding = nvdec_decoding == Settings::NvdecEmulation::Gpu; const u32 max_num_ref_frames = uses_gpu_decoding ? 6u : 16u; writer.WriteUe(max_num_ref_frames); writer.WriteBit(false); diff --git a/src/video_core/renderer_opengl/gl_compute_pipeline.cpp b/src/video_core/renderer_opengl/gl_compute_pipeline.cpp index f9ca55c36..d70501860 100644 --- a/src/video_core/renderer_opengl/gl_compute_pipeline.cpp +++ b/src/video_core/renderer_opengl/gl_compute_pipeline.cpp @@ -34,13 +34,13 @@ ComputePipeline::ComputePipeline(const Device& device, TextureCache& texture_cac : texture_cache{texture_cache_}, buffer_cache{buffer_cache_}, program_manager{program_manager_}, info{info_} { switch (device.GetShaderBackend()) { - case Settings::ShaderBackend::GLSL: + case Settings::ShaderBackend::Glsl: source_program = CreateProgram(code, GL_COMPUTE_SHADER); break; - case Settings::ShaderBackend::GLASM: + case Settings::ShaderBackend::Glasm: assembly_program = CompileProgram(code, GL_COMPUTE_PROGRAM_NV); break; - case Settings::ShaderBackend::SPIRV: + case Settings::ShaderBackend::SpirV: source_program = CreateProgram(code_v, GL_COMPUTE_SHADER); break; } diff --git a/src/video_core/renderer_opengl/gl_device.cpp b/src/video_core/renderer_opengl/gl_device.cpp index 33e63c17d..ee140c9c2 100644 --- a/src/video_core/renderer_opengl/gl_device.cpp +++ b/src/video_core/renderer_opengl/gl_device.cpp @@ -177,15 +177,15 @@ Device::Device(Core::Frontend::EmuWindow& emu_window) { has_fast_buffer_sub_data = is_nvidia && !disable_fast_buffer_sub_data; shader_backend = Settings::values.shader_backend.GetValue(); - use_assembly_shaders = shader_backend == Settings::ShaderBackend::GLASM && + use_assembly_shaders = shader_backend == Settings::ShaderBackend::Glasm && GLAD_GL_NV_gpu_program5 && GLAD_GL_NV_compute_program5 && GLAD_GL_NV_transform_feedback && GLAD_GL_NV_transform_feedback2; - if (shader_backend == Settings::ShaderBackend::GLASM && !use_assembly_shaders) { + if (shader_backend == Settings::ShaderBackend::Glasm && !use_assembly_shaders) { LOG_ERROR(Render_OpenGL, "Assembly shaders enabled but not supported"); - shader_backend = Settings::ShaderBackend::GLSL; + shader_backend = Settings::ShaderBackend::Glsl; } - if (shader_backend == Settings::ShaderBackend::GLSL && is_nvidia) { + if (shader_backend == Settings::ShaderBackend::Glsl && is_nvidia) { const std::string_view driver_version = version.substr(13); const int version_major = std::atoi(driver_version.substr(0, driver_version.find(".")).data()); diff --git a/src/video_core/renderer_opengl/gl_graphics_pipeline.cpp b/src/video_core/renderer_opengl/gl_graphics_pipeline.cpp index 71f720c63..f822fa856 100644 --- a/src/video_core/renderer_opengl/gl_graphics_pipeline.cpp +++ b/src/video_core/renderer_opengl/gl_graphics_pipeline.cpp @@ -236,18 +236,18 @@ GraphicsPipeline::GraphicsPipeline(const Device& device, TextureCache& texture_c force_context_flush](ShaderContext::Context*) mutable { for (size_t stage = 0; stage < 5; ++stage) { switch (backend) { - case Settings::ShaderBackend::GLSL: + case Settings::ShaderBackend::Glsl: if (!sources_[stage].empty()) { source_programs[stage] = CreateProgram(sources_[stage], Stage(stage)); } break; - case Settings::ShaderBackend::GLASM: + case Settings::ShaderBackend::Glasm: if (!sources_[stage].empty()) { assembly_programs[stage] = CompileProgram(sources_[stage], AssemblyStage(stage)); } break; - case Settings::ShaderBackend::SPIRV: + case Settings::ShaderBackend::SpirV: if (!sources_spirv_[stage].empty()) { source_programs[stage] = CreateProgram(sources_spirv_[stage], Stage(stage)); } diff --git a/src/video_core/renderer_opengl/gl_shader_cache.cpp b/src/video_core/renderer_opengl/gl_shader_cache.cpp index 7e1d7f92e..618cb6354 100644 --- a/src/video_core/renderer_opengl/gl_shader_cache.cpp +++ b/src/video_core/renderer_opengl/gl_shader_cache.cpp @@ -522,14 +522,14 @@ std::unique_ptr ShaderCache::CreateGraphicsPipeline( const auto runtime_info{ MakeRuntimeInfo(key, program, previous_program, glasm_use_storage_buffers, use_glasm)}; switch (device.GetShaderBackend()) { - case Settings::ShaderBackend::GLSL: + case Settings::ShaderBackend::Glsl: ConvertLegacyToGeneric(program, runtime_info); sources[stage_index] = EmitGLSL(profile, runtime_info, program, binding); break; - case Settings::ShaderBackend::GLASM: + case Settings::ShaderBackend::Glasm: sources[stage_index] = EmitGLASM(profile, runtime_info, program, binding); break; - case Settings::ShaderBackend::SPIRV: + case Settings::ShaderBackend::SpirV: ConvertLegacyToGeneric(program, runtime_info); sources_spirv[stage_index] = EmitSPIRV(profile, runtime_info, program, binding); break; @@ -582,13 +582,13 @@ std::unique_ptr ShaderCache::CreateComputePipeline( std::string code{}; std::vector code_spirv; switch (device.GetShaderBackend()) { - case Settings::ShaderBackend::GLSL: + case Settings::ShaderBackend::Glsl: code = EmitGLSL(profile, program); break; - case Settings::ShaderBackend::GLASM: + case Settings::ShaderBackend::Glasm: code = EmitGLASM(profile, info, program); break; - case Settings::ShaderBackend::SPIRV: + case Settings::ShaderBackend::SpirV: code_spirv = EmitSPIRV(profile, program); break; } diff --git a/src/video_core/renderer_opengl/gl_texture_cache.cpp b/src/video_core/renderer_opengl/gl_texture_cache.cpp index 38ae12d8e..9cafd2983 100644 --- a/src/video_core/renderer_opengl/gl_texture_cache.cpp +++ b/src/video_core/renderer_opengl/gl_texture_cache.cpp @@ -232,7 +232,7 @@ void ApplySwizzle(GLuint handle, PixelFormat format, std::arraydevice.IsOptimalAstcSupported()) { switch (Settings::values.accelerate_astc.GetValue()) { - case Settings::AstcDecodeMode::GPU: + case Settings::AstcDecodeMode::Gpu: if (Settings::values.astc_recompression.GetValue() == Settings::AstcRecompression::Uncompressed && info.size.depth == 1) { flags |= VideoCommon::ImageFlagBits::AcceleratedUpload; } break; - case Settings::AstcDecodeMode::CPUAsynchronous: + case Settings::AstcDecodeMode::CpuAsynchronous: flags |= VideoCommon::ImageFlagBits::AsynchronousDecode; break; default: diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 28ee5d492..051756452 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -89,10 +89,10 @@ const std::map Config::use_docked_mode_texts_map = { {false, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "Handheld"))}, }; -const std::map Config::gpu_accuracy_texts_map = { - {Settings::GPUAccuracy::Normal, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "Normal"))}, - {Settings::GPUAccuracy::High, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "High"))}, - {Settings::GPUAccuracy::Extreme, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "Extreme"))}, +const std::map Config::gpu_accuracy_texts_map = { + {Settings::GpuAccuracy::Normal, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "Normal"))}, + {Settings::GpuAccuracy::High, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "High"))}, + {Settings::GpuAccuracy::Extreme, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "Extreme"))}, }; const std::map Config::renderer_backend_texts_map = { diff --git a/src/yuzu/configuration/config.h b/src/yuzu/configuration/config.h index 553a82295..c00e717b8 100644 --- a/src/yuzu/configuration/config.h +++ b/src/yuzu/configuration/config.h @@ -52,7 +52,7 @@ public: static const std::map anti_aliasing_texts_map; static const std::map scaling_filter_texts_map; static const std::map use_docked_mode_texts_map; - static const std::map gpu_accuracy_texts_map; + static const std::map gpu_accuracy_texts_map; static const std::map renderer_backend_texts_map; static const std::map shader_backend_texts_map; @@ -211,8 +211,8 @@ private: }; // These metatype declarations cannot be in common/settings.h because core is devoid of QT -Q_DECLARE_METATYPE(Settings::CPUAccuracy); -Q_DECLARE_METATYPE(Settings::GPUAccuracy); +Q_DECLARE_METATYPE(Settings::CpuAccuracy); +Q_DECLARE_METATYPE(Settings::GpuAccuracy); Q_DECLARE_METATYPE(Settings::FullscreenMode); Q_DECLARE_METATYPE(Settings::NvdecEmulation); Q_DECLARE_METATYPE(Settings::ResolutionSetup); diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 0496bd78f..7cc8affb7 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -188,7 +188,7 @@ void ConfigureAudio::InitializeAudioSinkComboBox() { sink_combo_box->addItem(QString::fromUtf8(AudioCore::Sink::auto_device_name)); for (const auto& id : AudioCore::Sink::GetSinkIDs()) { - sink_combo_box->addItem(QString::fromStdString(Settings::TranslateEnum(id))); + sink_combo_box->addItem(QString::fromStdString(Settings::CanonicalizeEnum(id))); } } diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index ac298a50f..67b811014 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -73,9 +73,9 @@ void ConfigureCpu::Setup() { } void ConfigureCpu::UpdateGroup(int index) { - const auto accuracy = static_cast( - combobox_translations.at(typeid(Settings::CPUAccuracy))[index].first); - ui->unsafe_group->setVisible(accuracy == Settings::CPUAccuracy::Unsafe); + const auto accuracy = static_cast( + combobox_translations.at(typeid(Settings::CpuAccuracy))[index].first); + ui->unsafe_group->setVisible(accuracy == Settings::CpuAccuracy::Unsafe); } void ConfigureCpu::ApplyConfiguration() { diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 59702603a..1e26267a0 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -51,9 +51,9 @@ static constexpr VkPresentModeKHR VSyncSettingToMode(Settings::VSyncMode mode) { return VK_PRESENT_MODE_IMMEDIATE_KHR; case Settings::VSyncMode::Mailbox: return VK_PRESENT_MODE_MAILBOX_KHR; - case Settings::VSyncMode::FIFO: + case Settings::VSyncMode::Fifo: return VK_PRESENT_MODE_FIFO_KHR; - case Settings::VSyncMode::FIFORelaxed: + case Settings::VSyncMode::FifoRelaxed: return VK_PRESENT_MODE_FIFO_RELAXED_KHR; default: return VK_PRESENT_MODE_FIFO_KHR; @@ -67,11 +67,11 @@ static constexpr Settings::VSyncMode PresentModeToSetting(VkPresentModeKHR mode) case VK_PRESENT_MODE_MAILBOX_KHR: return Settings::VSyncMode::Mailbox; case VK_PRESENT_MODE_FIFO_KHR: - return Settings::VSyncMode::FIFO; + return Settings::VSyncMode::Fifo; case VK_PRESENT_MODE_FIFO_RELAXED_KHR: - return Settings::VSyncMode::FIFORelaxed; + return Settings::VSyncMode::FifoRelaxed; default: - return Settings::VSyncMode::FIFO; + return Settings::VSyncMode::Fifo; } } diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 5d4e29a08..4caa44e1b 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -177,9 +177,9 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { translations->insert( {typeid(Settings::AstcDecodeMode), { - {static_cast(Settings::AstcDecodeMode::CPU), tr("CPU")}, - {static_cast(Settings::AstcDecodeMode::GPU), tr("GPU")}, - {static_cast(Settings::AstcDecodeMode::CPUAsynchronous), tr("CPU Asynchronous")}, + {static_cast(Settings::AstcDecodeMode::Cpu), tr("CPU")}, + {static_cast(Settings::AstcDecodeMode::Gpu), tr("GPU")}, + {static_cast(Settings::AstcDecodeMode::CpuAsynchronous), tr("CPU Asynchronous")}, }}); translations->insert( {typeid(Settings::AstcRecompression), @@ -199,24 +199,24 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { }}); translations->insert({typeid(Settings::ShaderBackend), { - {static_cast(Settings::ShaderBackend::GLSL), tr("GLSL")}, - {static_cast(Settings::ShaderBackend::GLASM), + {static_cast(Settings::ShaderBackend::Glsl), tr("GLSL")}, + {static_cast(Settings::ShaderBackend::Glasm), tr("GLASM (Assembly Shaders, NVIDIA Only)")}, - {static_cast(Settings::ShaderBackend::SPIRV), + {static_cast(Settings::ShaderBackend::SpirV), tr("SPIR-V (Experimental, Mesa Only)")}, }}); - translations->insert({typeid(Settings::GPUAccuracy), + translations->insert({typeid(Settings::GpuAccuracy), { - {static_cast(Settings::GPUAccuracy::Normal), tr("Normal")}, - {static_cast(Settings::GPUAccuracy::High), tr("High")}, - {static_cast(Settings::GPUAccuracy::Extreme), tr("Extreme")}, + {static_cast(Settings::GpuAccuracy::Normal), tr("Normal")}, + {static_cast(Settings::GpuAccuracy::High), tr("High")}, + {static_cast(Settings::GpuAccuracy::Extreme), tr("Extreme")}, }}); - translations->insert({typeid(Settings::CPUAccuracy), + translations->insert({typeid(Settings::CpuAccuracy), { - {static_cast(Settings::CPUAccuracy::Auto), tr("Auto")}, - {static_cast(Settings::CPUAccuracy::Accurate), tr("Accurate")}, - {static_cast(Settings::CPUAccuracy::Unsafe), tr("Unsafe")}, - {static_cast(Settings::CPUAccuracy::Paranoid), + {static_cast(Settings::CpuAccuracy::Auto), tr("Auto")}, + {static_cast(Settings::CpuAccuracy::Accurate), tr("Accurate")}, + {static_cast(Settings::CpuAccuracy::Unsafe), tr("Unsafe")}, + {static_cast(Settings::CpuAccuracy::Paranoid), tr("Paranoid (disables most optimizations)")}, }}); translations->insert( @@ -229,8 +229,8 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { {typeid(Settings::NvdecEmulation), { {static_cast(Settings::NvdecEmulation::Off), tr("No Video Output")}, - {static_cast(Settings::NvdecEmulation::CPU), tr("CPU Video Decoding")}, - {static_cast(Settings::NvdecEmulation::GPU), tr("GPU Video Decoding (Default)")}, + {static_cast(Settings::NvdecEmulation::Cpu), tr("CPU Video Decoding")}, + {static_cast(Settings::NvdecEmulation::Gpu), tr("GPU Video Decoding (Default)")}, }}); translations->insert( {typeid(Settings::ResolutionSetup), @@ -313,7 +313,7 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { translations->insert({typeid(Settings::Region), { {static_cast(Settings::Region::Japan), tr("Japan")}, - {static_cast(Settings::Region::USA), tr("USA")}, + {static_cast(Settings::Region::Usa), tr("USA")}, {static_cast(Settings::Region::Europe), tr("Europe")}, {static_cast(Settings::Region::Australia), tr("Australia")}, {static_cast(Settings::Region::China), tr("China")}, diff --git a/src/yuzu/main.cpp b/src/yuzu/main.cpp index 6cd557c29..2922b3347 100644 --- a/src/yuzu/main.cpp +++ b/src/yuzu/main.cpp @@ -1183,7 +1183,7 @@ void GMainWindow::InitializeWidgets() { QMenu context_menu; for (auto const& gpu_accuracy_pair : Config::gpu_accuracy_texts_map) { - if (gpu_accuracy_pair.first == Settings::GPUAccuracy::Extreme) { + if (gpu_accuracy_pair.first == Settings::GpuAccuracy::Extreme) { continue; } context_menu.addAction(gpu_accuracy_pair.second, [this, gpu_accuracy_pair] { @@ -3651,14 +3651,14 @@ void GMainWindow::OnToggleDockedMode() { void GMainWindow::OnToggleGpuAccuracy() { switch (Settings::values.gpu_accuracy.GetValue()) { - case Settings::GPUAccuracy::High: { - Settings::values.gpu_accuracy.SetValue(Settings::GPUAccuracy::Normal); + case Settings::GpuAccuracy::High: { + Settings::values.gpu_accuracy.SetValue(Settings::GpuAccuracy::Normal); break; } - case Settings::GPUAccuracy::Normal: - case Settings::GPUAccuracy::Extreme: + case Settings::GpuAccuracy::Normal: + case Settings::GpuAccuracy::Extreme: default: { - Settings::values.gpu_accuracy.SetValue(Settings::GPUAccuracy::High); + Settings::values.gpu_accuracy.SetValue(Settings::GpuAccuracy::High); break; } } @@ -4071,7 +4071,7 @@ void GMainWindow::UpdateGPUAccuracyButton() { const auto gpu_accuracy = Settings::values.gpu_accuracy.GetValue(); const auto gpu_accuracy_text = Config::gpu_accuracy_texts_map.find(gpu_accuracy)->second; gpu_accuracy_button->setText(gpu_accuracy_text.toUpper()); - gpu_accuracy_button->setChecked(gpu_accuracy != Settings::GPUAccuracy::Normal); + gpu_accuracy_button->setChecked(gpu_accuracy != Settings::GpuAccuracy::Normal); } void GMainWindow::UpdateDockedButton() { From 8c17a945f71b8532b0a4c3903b00a09d99ff0d6c Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 7 Jun 2023 01:53:05 -0400 Subject: [PATCH 066/155] settings_enums: Cannonicalize settings names Gives every option of the enums a string literal via a macro. --- src/common/settings_enums.h | 165 +++++++++++++++++++++++++++++++++++- 1 file changed, 163 insertions(+), 2 deletions(-) diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index 6cd2ac28b..d820bc48e 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -207,16 +207,177 @@ enum class AspectRatio : u32 { Stretch, }; -static std::map> translations = { +#define X(ENUM, NAME) \ + { (#NAME), static_cast(ENUM::NAME) } + +static std::map> canonicalizations = { {typeid(AudioEngine), { {"auto", static_cast(AudioEngine::Auto)}, {"cubeb", static_cast(AudioEngine::Cubeb)}, {"sdl2", static_cast(AudioEngine::Sdl2)}, {"null", static_cast(AudioEngine::Null)}, + }}, + {typeid(AudioMode), + { + X(AudioMode, Mono), + X(AudioMode, Stereo), + X(AudioMode, Surround), + }}, + {typeid(Language), + { + X(Language, Japanese), + X(Language, EnglishAmerican), + X(Language, French), + X(Language, German), + X(Language, Italian), + X(Language, Spanish), + X(Language, Chinese), + X(Language, Korean), + X(Language, Dutch), + X(Language, Portuguese), + X(Language, Russian), + X(Language, Taiwanese), + X(Language, EnglishBritish), + X(Language, FrenchCanadian), + X(Language, SpanishLatin), + X(Language, ChineseSimplified), + X(Language, ChineseTraditional), + X(Language, PortugueseBrazilian), + }}, + {typeid(Region), + { + X(Region, Japan), + X(Region, Usa), + X(Region, Europe), + X(Region, Australia), + X(Region, China), + X(Region, Korea), + X(Region, Taiwan), + }}, + {typeid(TimeZone), + { + X(TimeZone, Auto), X(TimeZone, Default), X(TimeZone, CET), + X(TimeZone, CST6CDT), X(TimeZone, Cuba), X(TimeZone, EET), + X(TimeZone, Egypt), X(TimeZone, Eire), X(TimeZone, EST5EDT), + X(TimeZone, GB), X(TimeZone, GBEire), X(TimeZone, GMT), + X(TimeZone, GMTPlusZero), X(TimeZone, GMTMinusZero), X(TimeZone, GMTZero), + X(TimeZone, Greenwich), X(TimeZone, Hongkong), X(TimeZone, HST), + X(TimeZone, Iceland), X(TimeZone, Iran), X(TimeZone, Israel), + X(TimeZone, Jamaica), X(TimeZone, Japan), X(TimeZone, Kwajalein), + X(TimeZone, Libya), X(TimeZone, MET), X(TimeZone, MST), + X(TimeZone, MST7MDT), X(TimeZone, Navajo), X(TimeZone, NZ), + X(TimeZone, NZCHAT), X(TimeZone, Poland), X(TimeZone, Portugal), + X(TimeZone, PRC), X(TimeZone, ROC), X(TimeZone, ROK), + X(TimeZone, Singapore), X(TimeZone, Turkey), X(TimeZone, UCT), + X(TimeZone, Universal), X(TimeZone, UTC), X(TimeZone, W_SU), + X(TimeZone, WET), X(TimeZone, Zulu), + }}, + {typeid(AnisotropyMode), + { + X(AnisotropyMode, Automatic), + X(AnisotropyMode, Default), + X(AnisotropyMode, X2), + X(AnisotropyMode, X4), + X(AnisotropyMode, X8), + X(AnisotropyMode, X16), + }}, + {typeid(AstcDecodeMode), + { + X(AstcDecodeMode, Cpu), + X(AstcDecodeMode, Gpu), + X(AstcDecodeMode, CpuAsynchronous), + }}, + {typeid(AstcRecompression), + { + X(AstcRecompression, Uncompressed), + X(AstcRecompression, Bc1), + X(AstcRecompression, Bc3), + }}, + {typeid(VSyncMode), + { + X(VSyncMode, Immediate), + X(VSyncMode, Mailbox), + X(VSyncMode, Fifo), + X(VSyncMode, FifoRelaxed), + }}, + {typeid(RendererBackend), + { + X(RendererBackend, OpenGL), + X(RendererBackend, Vulkan), + X(RendererBackend, Null), + }}, + {typeid(ShaderBackend), + { + X(ShaderBackend, Glsl), + X(ShaderBackend, Glasm), + X(ShaderBackend, SpirV), + }}, + {typeid(GpuAccuracy), + { + X(GpuAccuracy, Normal), + X(GpuAccuracy, High), + X(GpuAccuracy, Extreme), + }}, + {typeid(CpuAccuracy), + { + X(CpuAccuracy, Auto), + X(CpuAccuracy, Accurate), + X(CpuAccuracy, Unsafe), + X(CpuAccuracy, Paranoid), + }}, + {typeid(FullscreenMode), + { + X(FullscreenMode, Borderless), + X(FullscreenMode, Exclusive), + }}, + {typeid(NvdecEmulation), + { + X(NvdecEmulation, Off), + X(NvdecEmulation, Cpu), + X(NvdecEmulation, Gpu), + }}, + {typeid(ResolutionSetup), + { + X(ResolutionSetup, Res1_2X), + X(ResolutionSetup, Res3_4X), + X(ResolutionSetup, Res1X), + X(ResolutionSetup, Res3_2X), + X(ResolutionSetup, Res2X), + X(ResolutionSetup, Res3X), + X(ResolutionSetup, Res4X), + X(ResolutionSetup, Res5X), + X(ResolutionSetup, Res6X), + X(ResolutionSetup, Res7X), + X(ResolutionSetup, Res8X), + }}, + {typeid(ScalingFilter), + { + X(ScalingFilter, NearestNeighbor), + X(ScalingFilter, Bilinear), + X(ScalingFilter, Bicubic), + X(ScalingFilter, Gaussian), + X(ScalingFilter, ScaleForce), + X(ScalingFilter, Fsr), + }}, + {typeid(AntiAliasing), + { + X(AntiAliasing, None), + X(AntiAliasing, Fxaa), + X(AntiAliasing, Smaa), + }}, + {typeid(AspectRatio), + { + X(AspectRatio, R16_9), + X(AspectRatio, R4_3), + X(AspectRatio, R21_9), + X(AspectRatio, R16_10), + X(AspectRatio, Stretch), }}}; -static std::string empty_string{}; +#undef X + +static std::string invalid_string{"(invalid setting)"}; template const std::string& CanonicalizeEnum(Type id) { From 78b270937367b813ef27a019e1a7a3728e3f9d55 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 7 Jun 2023 01:53:57 -0400 Subject: [PATCH 067/155] settings: Report all contained settings values Also adds a couple characters that denotes the state of the setting. M for modified, or not default. C for custom, in context of per-game settings. --- src/common/settings.cpp | 64 ++++++++++++----------------------------- 1 file changed, 19 insertions(+), 45 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 0a8729b5a..84e90f893 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -61,56 +61,30 @@ void LogSettings() { }; LOG_INFO(Config, "yuzu Configuration:"); - log_setting("Controls_UseDockedMode", values.use_docked_mode.GetValue()); - log_setting("System_RngSeedEnabled", values.rng_seed_enabled.GetValue()); - log_setting("System_RngSeed", values.rng_seed.GetValue()); - log_setting("System_DeviceName", values.device_name.GetValue()); - log_setting("System_CurrentUser", values.current_user.GetValue()); - log_setting("System_LanguageIndex", values.language_index.GetValue()); - log_setting("System_RegionIndex", values.region_index.GetValue()); - log_setting("System_TimeZoneIndex", values.time_zone_index.GetValue()); - log_setting("System_UnsafeMemoryLayout", values.use_unsafe_extended_memory_layout.GetValue()); - log_setting("Core_UseMultiCore", values.use_multi_core.GetValue()); - log_setting("CPU_Accuracy", values.cpu_accuracy.GetValue()); - log_setting("Renderer_UseResolutionScaling", values.resolution_setup.GetValue()); - log_setting("Renderer_ScalingFilter", values.scaling_filter.GetValue()); - log_setting("Renderer_FSRSlider", values.fsr_sharpening_slider.GetValue()); - log_setting("Renderer_AntiAliasing", values.anti_aliasing.GetValue()); - log_setting("Renderer_UseSpeedLimit", values.use_speed_limit.GetValue()); - log_setting("Renderer_SpeedLimit", values.speed_limit.GetValue()); - log_setting("Renderer_UseDiskShaderCache", values.use_disk_shader_cache.GetValue()); - log_setting("Renderer_GPUAccuracyLevel", values.gpu_accuracy.GetValue()); - log_setting("Renderer_UseAsynchronousGpuEmulation", - values.use_asynchronous_gpu_emulation.GetValue()); - log_setting("Renderer_NvdecEmulation", values.nvdec_emulation.GetValue()); - log_setting("Renderer_AccelerateASTC", values.accelerate_astc.GetValue()); - log_setting("Renderer_AstcRecompression", values.astc_recompression.GetValue()); - log_setting("Renderer_UseVsync", values.vsync_mode.GetValue()); - log_setting("Renderer_UseReactiveFlushing", values.use_reactive_flushing.GetValue()); - log_setting("Renderer_ShaderBackend", values.shader_backend.GetValue()); - log_setting("Renderer_UseAsynchronousShaders", values.use_asynchronous_shaders.GetValue()); - log_setting("Renderer_AnisotropicFilteringLevel", values.max_anisotropy.GetValue()); - log_setting("Audio_OutputEngine", Settings::TranslateEnum(values.sink_id.GetValue())); - log_setting("Audio_OutputDevice", values.audio_output_device_id.GetValue()); - log_setting("Audio_InputDevice", values.audio_input_device_id.GetValue()); - log_setting("DataStorage_UseVirtualSd", values.use_virtual_sd.GetValue()); + for (auto& [category, settings] : values.linkage.by_category) { + settings.sort([](const BasicSetting* a, const BasicSetting* b) { + return a->GetLabel() < b->GetLabel(); + }); + + for (const auto& setting : settings) { + if (setting->Id() == values.yuzu_token.Id()) { + // Hide the token secret, which could be used to share patreon builds + continue; + } + + std::string name = fmt::format( + "{:c}{:c} {}.{}", setting->ToString() == setting->DefaultToString() ? '-' : 'M', + setting->UsingGlobal() ? '-' : 'C', TranslateCategory(category), + setting->GetLabel()); + + log_setting(name, setting->Canonicalize()); + } + } log_path("DataStorage_CacheDir", Common::FS::GetYuzuPath(Common::FS::YuzuPath::CacheDir)); log_path("DataStorage_ConfigDir", Common::FS::GetYuzuPath(Common::FS::YuzuPath::ConfigDir)); log_path("DataStorage_LoadDir", Common::FS::GetYuzuPath(Common::FS::YuzuPath::LoadDir)); log_path("DataStorage_NANDDir", Common::FS::GetYuzuPath(Common::FS::YuzuPath::NANDDir)); log_path("DataStorage_SDMCDir", Common::FS::GetYuzuPath(Common::FS::YuzuPath::SDMCDir)); - log_setting("Debugging_ProgramArgs", values.program_args.GetValue()); - log_setting("Debugging_GDBStub", values.use_gdbstub.GetValue()); - log_setting("Input_EnableMotion", values.motion_enabled.GetValue()); - log_setting("Input_EnableVibration", values.vibration_enabled.GetValue()); - log_setting("Input_EnableTouch", values.touchscreen.enabled); - log_setting("Input_EnableMouse", values.mouse_enabled.GetValue()); - log_setting("Input_EnableKeyboard", values.keyboard_enabled.GetValue()); - log_setting("Input_EnableRingController", values.enable_ring_controller.GetValue()); - log_setting("Input_EnableIrSensor", values.enable_ir_sensor.GetValue()); - log_setting("Input_EnableCustomJoycon", values.enable_joycon_driver.GetValue()); - log_setting("Input_EnableCustomProController", values.enable_procon_driver.GetValue()); - log_setting("Input_EnableRawInput", values.enable_raw_input.GetValue()); } bool IsConfiguringGlobal() { From 681ebcf4a5accd0315fd939ce66f672ab318affe Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 9 Jun 2023 14:09:41 -0400 Subject: [PATCH 068/155] shared_translation: Add translation for use video framrate --- src/yuzu/configuration/shared_translation.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 4caa44e1b..cf5d74c83 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -115,6 +115,9 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(Settings, use_reactive_flushing, "Enable Reactive Flushing", "Uses reactive flushing instead of predictive flushing, allowing more accurate memory " "syncing."); + INSERT(Settings, use_video_framerate, "Sync to framerate of video playback", + "Run the game at normal speed during video playback, even when the framerate is " + "unlocked."); // Renderer (Debug) From 163f229d2641426a163356c877ecd5b8b7555558 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 9 Jun 2023 17:24:29 -0400 Subject: [PATCH 069/155] settings: Reorder Groups graphics audio and system settings together in a way that reflects the frontend. This also just conceptually groups them more nicely than they were. --- src/common/settings.h | 153 +++++++++++++++++++++--------------------- 1 file changed, 78 insertions(+), 75 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 141408d3e..f6e977e96 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -557,8 +557,11 @@ struct Values { Setting sink_id{linkage, AudioEngine::Auto, "output_engine", Category::Audio}; Setting audio_output_device_id{linkage, "auto", "output_device", Category::Audio}; Setting audio_input_device_id{linkage, "auto", "input_device", Category::Audio}; - Setting audio_muted{linkage, false, "audio_muted", Category::Audio, false}; + SwitchableSetting sound_index{linkage, AudioMode::Stereo, + AudioMode::Mono, AudioMode::Surround, + "sound_index", Category::SystemAudio}; SwitchableSetting volume{linkage, 100, 0, 200, "volume", Category::Audio, true, true}; + Setting audio_muted{linkage, false, "audio_muted", Category::Audio, false}; Setting dump_audio_commands{linkage, false, "dump_audio_commands", Category::Audio, false}; @@ -612,28 +615,35 @@ struct Values { SwitchableSetting renderer_backend{ linkage, RendererBackend::Vulkan, RendererBackend::OpenGL, RendererBackend::Null, "backend", Category::Renderer}; - SwitchableSetting async_presentation{linkage, false, "async_presentation", - Category::RendererAdvanced}; - SwitchableSetting renderer_force_max_clock{linkage, false, "force_max_clock", - Category::RendererAdvanced}; - Setting renderer_debug{linkage, false, "debug", Category::RendererDebug}; - Setting renderer_shader_feedback{linkage, false, "shader_feedback", - Category::RendererDebug}; - Setting enable_nsight_aftermath{linkage, false, "nsight_aftermath", - Category::RendererDebug}; - Setting disable_shader_loop_safety_checks{ - linkage, false, "disable_shader_loop_safety_checks", Category::RendererDebug}; + SwitchableSetting shader_backend{ + linkage, ShaderBackend::Glsl, ShaderBackend::Glsl, ShaderBackend::SpirV, + "shader_backend", Category::Renderer}; SwitchableSetting vulkan_device{linkage, 0, "vulkan_device", Category::Renderer}; - ResolutionScalingInfo resolution_info{}; - SwitchableSetting resolution_setup{linkage, ResolutionSetup::Res1X, - "resolution_setup", Category::Renderer}; - SwitchableSetting scaling_filter{ - linkage, ScalingFilter::Bilinear, "scaling_filter", Category::Renderer, true, true}; - SwitchableSetting fsr_sharpening_slider{ - linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer, true, true}; - SwitchableSetting anti_aliasing{ - linkage, AntiAliasing::None, "anti_aliasing", Category::Renderer, true, true}; + SwitchableSetting use_disk_shader_cache{linkage, true, "use_disk_shader_cache", + Category::Renderer}; + SwitchableSetting use_asynchronous_gpu_emulation{ + linkage, true, "use_asynchronous_gpu_emulation", Category::Renderer}; + SwitchableSetting use_speed_limit{ + linkage, true, "use_speed_limit", Category::Renderer, false, true}; + SwitchableSetting speed_limit{ + linkage, 100, 0, 9999, "speed_limit", Category::Renderer, true, true}; + SwitchableSetting accelerate_astc{linkage, + AstcDecodeMode::Cpu, + AstcDecodeMode::Cpu, + AstcDecodeMode::CpuAsynchronous, + "accelerate_astc", + Category::Renderer}; + Setting vsync_mode{linkage, + VSyncMode::Fifo, + VSyncMode::Immediate, + VSyncMode::FifoRelaxed, + "use_vsync", + Category::Renderer, + true, + true}; + SwitchableSetting nvdec_emulation{linkage, NvdecEmulation::Gpu, + "nvdec_emulation", Category::Renderer}; // *nix platforms may have issues with the borderless windowed fullscreen mode. // Default to exclusive fullscreen on these platforms for now. SwitchableSetting fullscreen_mode{linkage, @@ -656,15 +666,21 @@ struct Values { Category::Renderer, true, true}; - SwitchableSetting max_anisotropy{ - linkage, AnisotropyMode::Automatic, AnisotropyMode::Automatic, AnisotropyMode::X16, - "max_anisotropy", Category::RendererAdvanced}; - SwitchableSetting use_speed_limit{ - linkage, true, "use_speed_limit", Category::Renderer, false, true}; - SwitchableSetting speed_limit{ - linkage, 100, 0, 9999, "speed_limit", Category::Renderer, true, true}; - SwitchableSetting use_disk_shader_cache{linkage, true, "use_disk_shader_cache", - Category::Renderer}; + + ResolutionScalingInfo resolution_info{}; + SwitchableSetting resolution_setup{linkage, ResolutionSetup::Res1X, + "resolution_setup", Category::Renderer}; + SwitchableSetting scaling_filter{ + linkage, ScalingFilter::Bilinear, "scaling_filter", Category::Renderer, true, true}; + SwitchableSetting anti_aliasing{ + linkage, AntiAliasing::None, "anti_aliasing", Category::Renderer, true, true}; + SwitchableSetting fsr_sharpening_slider{ + linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer, true, true}; + + SwitchableSetting bg_red{linkage, 0, "bg_red", Category::Renderer, true, true}; + SwitchableSetting bg_green{linkage, 0, "bg_green", Category::Renderer, true, true}; + SwitchableSetting bg_blue{linkage, 0, "bg_blue", Category::Renderer, true, true}; + SwitchableSetting gpu_accuracy{linkage, GpuAccuracy::High, GpuAccuracy::Normal, @@ -673,29 +689,21 @@ struct Values { Category::RendererAdvanced, true, true}; - SwitchableSetting use_asynchronous_gpu_emulation{ - linkage, true, "use_asynchronous_gpu_emulation", Category::Renderer}; - SwitchableSetting nvdec_emulation{linkage, NvdecEmulation::Gpu, - "nvdec_emulation", Category::Renderer}; - SwitchableSetting accelerate_astc{linkage, - AstcDecodeMode::Cpu, - AstcDecodeMode::Cpu, - AstcDecodeMode::CpuAsynchronous, - "accelerate_astc", - Category::Renderer}; - Setting vsync_mode{linkage, - VSyncMode::Fifo, - VSyncMode::Immediate, - VSyncMode::FifoRelaxed, - "use_vsync", - Category::Renderer, - true, - true}; + SwitchableSetting max_anisotropy{ + linkage, AnisotropyMode::Automatic, AnisotropyMode::Automatic, AnisotropyMode::X16, + "max_anisotropy", Category::RendererAdvanced}; + SwitchableSetting astc_recompression{linkage, + AstcRecompression::Uncompressed, + AstcRecompression::Uncompressed, + AstcRecompression::Bc3, + "astc_recompression", + Category::RendererAdvanced}; + SwitchableSetting async_presentation{linkage, false, "async_presentation", + Category::RendererAdvanced}; + SwitchableSetting renderer_force_max_clock{linkage, false, "force_max_clock", + Category::RendererAdvanced}; SwitchableSetting use_reactive_flushing{linkage, true, "use_reactive_flushing", Category::RendererAdvanced}; - SwitchableSetting shader_backend{ - linkage, ShaderBackend::Glsl, ShaderBackend::Glsl, ShaderBackend::SpirV, - "shader_backend", Category::Renderer}; SwitchableSetting use_asynchronous_shaders{linkage, false, "use_asynchronous_shaders", Category::RendererAdvanced}; SwitchableSetting use_fast_gpu_time{ @@ -704,34 +712,20 @@ struct Values { linkage, true, "use_vulkan_driver_pipeline_cache", Category::RendererAdvanced, true, true}; SwitchableSetting enable_compute_pipelines{linkage, false, "enable_compute_pipelines", Category::RendererAdvanced}; - SwitchableSetting astc_recompression{linkage, - AstcRecompression::Uncompressed, - AstcRecompression::Uncompressed, - AstcRecompression::Bc3, - "astc_recompression", - Category::RendererAdvanced}; SwitchableSetting use_video_framerate{linkage, false, "use_video_framerate", Category::RendererAdvanced}; SwitchableSetting barrier_feedback_loops{linkage, true, "barrier_feedback_loops", Category::RendererAdvanced}; - SwitchableSetting bg_red{linkage, 0, "bg_red", Category::Renderer, true, true}; - SwitchableSetting bg_green{linkage, 0, "bg_green", Category::Renderer, true, true}; - SwitchableSetting bg_blue{linkage, 0, "bg_blue", Category::Renderer, true, true}; + Setting renderer_debug{linkage, false, "debug", Category::RendererDebug}; + Setting renderer_shader_feedback{linkage, false, "shader_feedback", + Category::RendererDebug}; + Setting enable_nsight_aftermath{linkage, false, "nsight_aftermath", + Category::RendererDebug}; + Setting disable_shader_loop_safety_checks{ + linkage, false, "disable_shader_loop_safety_checks", Category::RendererDebug}; // System - SwitchableSetting rng_seed_enabled{linkage, false, "rng_seed_enabled", - Category::System, true, true}; - SwitchableSetting rng_seed{linkage, 0, "rng_seed", Category::System, true, true}; - Setting device_name{linkage, "Yuzu", "device_name", Category::System, true, true}; - // Measured in seconds since epoch - SwitchableSetting custom_rtc_enabled{linkage, false, "custom_rtc_enabled", - Category::System, true, true}; - SwitchableSetting custom_rtc{linkage, 0, "custom_rtc", Category::System, true, true}; - // Set on game boot, reset on stop. Seconds difference between current time and `custom_rtc` - s64 custom_rtc_differential; - - Setting current_user{linkage, 0, "current_user", Category::System}; SwitchableSetting language_index{linkage, Language::EnglishAmerican, Language::Japanese, @@ -743,9 +737,18 @@ struct Values { SwitchableSetting time_zone_index{linkage, TimeZone::Auto, TimeZone::Auto, TimeZone::Zulu, "time_zone_index", Category::System}; - SwitchableSetting sound_index{linkage, AudioMode::Stereo, - AudioMode::Mono, AudioMode::Surround, - "sound_index", Category::SystemAudio}; + // Measured in seconds since epoch + SwitchableSetting custom_rtc_enabled{linkage, false, "custom_rtc_enabled", + Category::System, true, true}; + SwitchableSetting custom_rtc{linkage, 0, "custom_rtc", Category::System, true, true}; + // Set on game boot, reset on stop. Seconds difference between current time and `custom_rtc` + s64 custom_rtc_differential; + SwitchableSetting rng_seed_enabled{linkage, false, "rng_seed_enabled", + Category::System, true, true}; + SwitchableSetting rng_seed{linkage, 0, "rng_seed", Category::System, true, true}; + Setting device_name{linkage, "Yuzu", "device_name", Category::System, true, true}; + + Setting current_user{linkage, 0, "current_user", Category::System}; SwitchableSetting use_docked_mode{linkage, true, "use_docked_mode", Category::System}; From 81e9cf09349119cb84c5f52e2d7b64f0fe2482b8 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 9 Jun 2023 17:40:25 -0400 Subject: [PATCH 070/155] configuration: Document odd widget cases Explain why we need to do things differently at times, to serve as a reference. --- src/yuzu/configuration/configure_audio.cpp | 4 ++++ src/yuzu/configuration/configure_cpu.cpp | 2 ++ src/yuzu/configuration/configure_graphics.cpp | 10 ++++++++++ src/yuzu/configuration/configure_graphics_advanced.cpp | 1 + src/yuzu/configuration/configure_system.cpp | 9 ++++++++- 5 files changed, 25 insertions(+), 1 deletion(-) diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 7cc8affb7..9f9e4df8b 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -49,6 +49,7 @@ void ConfigureAudio::Setup() { for (auto* setting : settings) { auto* widget = [&]() { if (setting->Id() == Settings::values.volume.Id()) { + // volume needs to be a slider (default is line edit) return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::Slider, true, 1.0f, nullptr, @@ -56,6 +57,7 @@ void ConfigureAudio::Setup() { } else if (setting->Id() == Settings::values.audio_output_device_id.Id() || setting->Id() == Settings::values.audio_input_device_id.Id() || setting->Id() == Settings::values.sink_id.Id()) { + // These need to be unmanaged comboboxes, so we can populate them ourselves return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ComboBox, false); @@ -79,6 +81,8 @@ void ConfigureAudio::Setup() { connect(sink_combo_box, qOverload(&QComboBox::currentIndexChanged), this, &ConfigureAudio::UpdateAudioDevices); } else if (setting->Id() == Settings::values.audio_output_device_id.Id()) { + // Keep track of output (and input) device comboboxes to populate them with system + // devices, which are determined at run time output_device_combo_box = widget->combobox; } else if (setting->Id() == Settings::values.audio_input_device_id.Id()) { input_device_combo_box = widget->combobox; diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 67b811014..159837ebd 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -58,9 +58,11 @@ void ConfigureCpu::Setup() { } if (setting->Id() == Settings::values.cpu_accuracy.Id()) { + // Keep track of cpu_accuracy combobox to display/hide the unsafe settings accuracy_layout->addWidget(widget); accuracy_combobox = widget->combobox; } else { + // Presently, all other settings here are unsafe checkboxes unsafe_hold.insert({setting->GetLabel(), widget}); } } diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 1e26267a0..c053da0cd 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -231,6 +231,7 @@ void ConfigureGraphics::Setup() { for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { ConfigurationShared::Widget* widget = [&]() { + // Set managed to false on these and set up the comboboxes ourselves if (setting->Id() == Settings::values.vulkan_device.Id() || setting->Id() == Settings::values.shader_backend.Id() || setting->Id() == Settings::values.vsync_mode.Id()) { @@ -238,11 +239,13 @@ void ConfigureGraphics::Setup() { setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ComboBox, false); } else if (setting->Id() == Settings::values.fsr_sharpening_slider.Id()) { + // FSR needs a reversed slider return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ReverseSlider, true, 0.5f, nullptr, tr("%1%", "FSR sharpening percentage (e.g. 50%)")); } else if (setting->Id() == Settings::values.speed_limit.Id()) { + // speed_limit needs a checkbox to set use_speed_limit, as well as a spinbox return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::SpinBox, true, 1.0f, @@ -269,18 +272,23 @@ void ConfigureGraphics::Setup() { [=](bool) { UpdateAPILayout(); }); // Detach API's restore button and place it where we want + // Lets us put it on the side, and it will automatically scale if there's a second + // combobox (shader_backend, vulkan_device) widget->layout()->removeWidget(api_restore_global_button); api_layout->addWidget(api_restore_global_button); } } else if (setting->Id() == Settings::values.vulkan_device.Id()) { + // Keep track of vulkan_device's combobox so we can populate it hold_api.push_front(widget); vulkan_device_combobox = widget->combobox; vulkan_device_widget = widget; } else if (setting->Id() == Settings::values.shader_backend.Id()) { + // Keep track of shader_backend's combobox so we can populate it hold_api.push_front(widget); shader_backend_combobox = widget->combobox; shader_backend_widget = widget; } else if (setting->Id() == Settings::values.vsync_mode.Id()) { + // Keep track of vsync_mode's combobox so we can populate it vsync_mode_combobox = widget->combobox; hold_graphics.emplace(setting->Id(), widget); } else { @@ -296,6 +304,8 @@ void ConfigureGraphics::Setup() { api_grid_layout->addWidget(widget); } + // Background color is too specific to build into the new system, so we manage it here + // (3 settings, all collected into a single widget with a QColor to manage on top) if (Settings::IsConfiguringGlobal()) { apply_funcs.push_front([this](bool powered_on) { Settings::values.bg_red.SetValue(static_cast(bg_color.red())); diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 8c932f10a..843af230b 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -45,6 +45,7 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { hold.emplace(setting->Id(), widget); + // Keep track of enable_compute_pipelines so we can display it when needed if (setting->Id() == Settings::values.enable_compute_pipelines.Id()) { checkbox_enable_compute_pipelines = widget; } diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 4b0e0a649..ffcbab6d9 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -126,11 +126,15 @@ void ConfigureSystem::Setup() { [[maybe_unused]] std::string label = setting->GetLabel(); ConfigurationShared::Widget* widget = [=]() { if (setting->Id() == Settings::values.custom_rtc.Id()) { + // custom_rtc needs a DateTimeEdit (default is LineEdit), and a checkbox to manage + // it and custom_rtc_enabled return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::DateTimeEdit, true, 1.0f, &Settings::values.custom_rtc_enabled); } else if (setting->Id() == Settings::values.rng_seed.Id()) { + // rng_seed needs a HexEdit (default is LineEdit), and a checkbox to manage + // it and rng_seed_enabled return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::HexEdit, true, 1.0f, @@ -147,17 +151,20 @@ void ConfigureSystem::Setup() { } if (setting->Id() == Settings::values.rng_seed.Id()) { + // Keep track of rng_seed's widgets to reset it with the checkbox state rng_seed_checkbox = widget->checkbox; rng_seed_edit = widget->line_edit; rng_seed_edit->setEnabled(Settings::values.rng_seed_enabled.GetValue()); } else if (setting->Id() == Settings::values.custom_rtc.Id()) { + // Keep track of custom_rtc's widgets to reset it with the checkbox state custom_rtc_checkbox = widget->checkbox; custom_rtc_edit = widget->date_time_edit; custom_rtc_edit->setEnabled(Settings::values.custom_rtc_enabled.GetValue()); } else if (setting->Id() == Settings::values.region_index.Id()) { - + // Keep track of the region_index (and langauge_index) combobox to validate the selected + // settings combo_region = widget->combobox; } else if (setting->Id() == Settings::values.language_index.Id()) { combo_language = widget->combobox; From b86171d2b58e3f37e27d6d362548be5560c44764 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 9 Jun 2023 19:40:04 -0400 Subject: [PATCH 071/155] settings: yuzu is not capitalized why is it capitalized stop no bad --- src/common/settings.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/common/settings.h b/src/common/settings.h index f6e977e96..384a8ecb6 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -746,7 +746,7 @@ struct Values { SwitchableSetting rng_seed_enabled{linkage, false, "rng_seed_enabled", Category::System, true, true}; SwitchableSetting rng_seed{linkage, 0, "rng_seed", Category::System, true, true}; - Setting device_name{linkage, "Yuzu", "device_name", Category::System, true, true}; + Setting device_name{linkage, "yuzu", "device_name", Category::System, true, true}; Setting current_user{linkage, 0, "current_user", Category::System}; From 47d870b11f86e8af43c32f762aa2eedfd51ed7b0 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 9 Jun 2023 19:52:59 -0400 Subject: [PATCH 072/155] shared_translation: Populate combobox enums with macro --- src/yuzu/configuration/shared_translation.cpp | 326 +++++++++--------- 1 file changed, 158 insertions(+), 168 deletions(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index cf5d74c83..1787a35ff 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -175,207 +175,197 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { std::make_unique(); const auto& tr = [&](const char* text) { return parent->tr(text); }; +#define PAIR(ENUM, VALUE, TRANSLATION) \ + { static_cast(Settings::ENUM::VALUE), tr(TRANSLATION) } +#define CTX_PAIR(ENUM, VALUE, TRANSLATION, CONTEXT) \ + { static_cast(Settings::ENUM::VALUE), tr(TRANSLATION, CONTEXT) } + // Intentionally skipping VSyncMode to let the UI fill that one out - translations->insert( - {typeid(Settings::AstcDecodeMode), - { - {static_cast(Settings::AstcDecodeMode::Cpu), tr("CPU")}, - {static_cast(Settings::AstcDecodeMode::Gpu), tr("GPU")}, - {static_cast(Settings::AstcDecodeMode::CpuAsynchronous), tr("CPU Asynchronous")}, - }}); - translations->insert( - {typeid(Settings::AstcRecompression), - { - {static_cast(Settings::AstcRecompression::Uncompressed), - tr("Uncompressed (Best quality)")}, - {static_cast(Settings::AstcRecompression::Bc1), tr("BC1 (Low quality)")}, - {static_cast(Settings::AstcRecompression::Bc3), tr("BC3 (Medium quality)")}, - }}); + translations->insert({typeid(Settings::AstcDecodeMode), + { + PAIR(AstcDecodeMode, Cpu, "CPU"), + PAIR(AstcDecodeMode, Gpu, "GPU"), + PAIR(AstcDecodeMode, CpuAsynchronous, "CPU Asynchronous"), + }}); + translations->insert({typeid(Settings::AstcRecompression), + { + PAIR(AstcRecompression, Uncompressed, "Uncompressed (Best quality)"), + PAIR(AstcRecompression, Bc1, "BC1 (Low quality)"), + PAIR(AstcRecompression, Bc3, "BC3 (Medium quality)"), + }}); translations->insert({typeid(Settings::RendererBackend), { #ifdef HAS_OPENGL - {static_cast(Settings::RendererBackend::OpenGL), tr("OpenGL")}, + PAIR(RendererBackend, OpenGL, "OpenGL"), #endif - {static_cast(Settings::RendererBackend::Vulkan), tr("Vulkan")}, - {static_cast(Settings::RendererBackend::Null), tr("Null")}, + PAIR(RendererBackend, Vulkan, "Vulkan"), + PAIR(RendererBackend, Null, "Null"), }}); translations->insert({typeid(Settings::ShaderBackend), { - {static_cast(Settings::ShaderBackend::Glsl), tr("GLSL")}, - {static_cast(Settings::ShaderBackend::Glasm), - tr("GLASM (Assembly Shaders, NVIDIA Only)")}, - {static_cast(Settings::ShaderBackend::SpirV), - tr("SPIR-V (Experimental, Mesa Only)")}, + PAIR(ShaderBackend, Glsl, "GLSL"), + PAIR(ShaderBackend, Glasm, "GLASM (Assembly Shaders, NVIDIA Only)"), + PAIR(ShaderBackend, SpirV, "SPIR-V (Experimental, Mesa Only)"), }}); translations->insert({typeid(Settings::GpuAccuracy), { - {static_cast(Settings::GpuAccuracy::Normal), tr("Normal")}, - {static_cast(Settings::GpuAccuracy::High), tr("High")}, - {static_cast(Settings::GpuAccuracy::Extreme), tr("Extreme")}, + PAIR(GpuAccuracy, Normal, "Normal"), + PAIR(GpuAccuracy, High, "High"), + PAIR(GpuAccuracy, Extreme, "Extreme"), }}); translations->insert({typeid(Settings::CpuAccuracy), { - {static_cast(Settings::CpuAccuracy::Auto), tr("Auto")}, - {static_cast(Settings::CpuAccuracy::Accurate), tr("Accurate")}, - {static_cast(Settings::CpuAccuracy::Unsafe), tr("Unsafe")}, - {static_cast(Settings::CpuAccuracy::Paranoid), - tr("Paranoid (disables most optimizations)")}, + PAIR(CpuAccuracy, Auto, "Auto"), + PAIR(CpuAccuracy, Accurate, "Accurate"), + PAIR(CpuAccuracy, Unsafe, "Unsafe"), + PAIR(CpuAccuracy, Paranoid, "Paranoid (disables most optimizations)"), + }}); + translations->insert({typeid(Settings::FullscreenMode), + { + PAIR(FullscreenMode, Borderless, "Borderless Windowed"), + PAIR(FullscreenMode, Exclusive, "Exclusive Fullscreen"), + }}); + translations->insert({typeid(Settings::NvdecEmulation), + { + PAIR(NvdecEmulation, Off, "No Video Output"), + PAIR(NvdecEmulation, Cpu, "CPU Video Decoding"), + PAIR(NvdecEmulation, Gpu, "GPU Video Decoding (Default)"), + }}); + translations->insert({typeid(Settings::ResolutionSetup), + { + PAIR(ResolutionSetup, Res1_2X, "0.5X (360p/540p) [EXPERIMENTAL]"), + PAIR(ResolutionSetup, Res3_4X, "0.75X (540p/810p) [EXPERIMENTAL]"), + PAIR(ResolutionSetup, Res1X, "1X (720p/1080p)"), + PAIR(ResolutionSetup, Res3_2X, "1.5X (1080p/1620p) [EXPERIMENTAL]"), + PAIR(ResolutionSetup, Res2X, "2X (1440p/2160p)"), + PAIR(ResolutionSetup, Res3X, "3X (2160p/3240p)"), + PAIR(ResolutionSetup, Res4X, "4X (2880p/4320p)"), + PAIR(ResolutionSetup, Res5X, "5X (3600p/5400p)"), + PAIR(ResolutionSetup, Res6X, "6X (4320p/6480p)"), + PAIR(ResolutionSetup, Res7X, "7X (5040p/7560p)"), + PAIR(ResolutionSetup, Res8X, "8X (5760p/8640p)"), + }}); + translations->insert({typeid(Settings::ScalingFilter), + { + PAIR(ScalingFilter, NearestNeighbor, "Nearest Neighbor"), + PAIR(ScalingFilter, Bilinear, "Bilinear"), + PAIR(ScalingFilter, Bicubic, "Bicubic"), + PAIR(ScalingFilter, Gaussian, "Gaussian"), + PAIR(ScalingFilter, ScaleForce, "ScaleForce"), + PAIR(ScalingFilter, Fsr, "AMD FidelityFX™️ Super Resolution"), }}); - translations->insert( - {typeid(Settings::FullscreenMode), - { - {static_cast(Settings::FullscreenMode::Borderless), tr("Borderless Windowed")}, - {static_cast(Settings::FullscreenMode::Exclusive), tr("Exclusive Fullscreen")}, - }}); - translations->insert( - {typeid(Settings::NvdecEmulation), - { - {static_cast(Settings::NvdecEmulation::Off), tr("No Video Output")}, - {static_cast(Settings::NvdecEmulation::Cpu), tr("CPU Video Decoding")}, - {static_cast(Settings::NvdecEmulation::Gpu), tr("GPU Video Decoding (Default)")}, - }}); - translations->insert( - {typeid(Settings::ResolutionSetup), - { - {static_cast(Settings::ResolutionSetup::Res1_2X), - tr("0.5X (360p/540p) [EXPERIMENTAL]")}, - {static_cast(Settings::ResolutionSetup::Res3_4X), - tr("0.75X (540p/810p) [EXPERIMENTAL]")}, - {static_cast(Settings::ResolutionSetup::Res1X), tr("1X (720p/1080p)")}, - {static_cast(Settings::ResolutionSetup::Res3_2X), - tr("1.5X (1080p/1620p) [EXPERIMENTAL]")}, - {static_cast(Settings::ResolutionSetup::Res2X), tr("2X (1440p/2160p)")}, - {static_cast(Settings::ResolutionSetup::Res3X), tr("3X (2160p/3240p)")}, - {static_cast(Settings::ResolutionSetup::Res4X), tr("4X (2880p/4320p)")}, - {static_cast(Settings::ResolutionSetup::Res5X), tr("5X (3600p/5400p)")}, - {static_cast(Settings::ResolutionSetup::Res6X), tr("6X (4320p/6480p)")}, - {static_cast(Settings::ResolutionSetup::Res7X), tr("7X (5040p/7560p)")}, - {static_cast(Settings::ResolutionSetup::Res8X), tr("8X (5760p/8640p)")}, - }}); - translations->insert( - {typeid(Settings::ScalingFilter), - { - {static_cast(Settings::ScalingFilter::NearestNeighbor), tr("Nearest Neighbor")}, - {static_cast(Settings::ScalingFilter::Bilinear), tr("Bilinear")}, - {static_cast(Settings::ScalingFilter::Bicubic), tr("Bicubic")}, - {static_cast(Settings::ScalingFilter::Gaussian), tr("Gaussian")}, - {static_cast(Settings::ScalingFilter::ScaleForce), tr("ScaleForce")}, - {static_cast(Settings::ScalingFilter::Fsr), - tr("AMD FidelityFX™️ Super Resolution")}, - }}); translations->insert({typeid(Settings::AntiAliasing), { - {static_cast(Settings::AntiAliasing::None), tr("None")}, - {static_cast(Settings::AntiAliasing::Fxaa), tr("FXAA")}, - {static_cast(Settings::AntiAliasing::Smaa), tr("SMAA")}, + PAIR(AntiAliasing, None, "None"), + PAIR(AntiAliasing, Fxaa, "FXAA"), + PAIR(AntiAliasing, Smaa, "SMAA"), + }}); + translations->insert({typeid(Settings::AspectRatio), + { + PAIR(AspectRatio, R16_9, "Default (16:9)"), + PAIR(AspectRatio, R4_3, "Force 4:3"), + PAIR(AspectRatio, R21_9, "Force 21:9"), + PAIR(AspectRatio, R16_10, "Force 16:10"), + PAIR(AspectRatio, Stretch, "Stretch to Window"), + }}); + translations->insert({typeid(Settings::AnisotropyMode), + { + PAIR(AnisotropyMode, Automatic, "Automatic"), + PAIR(AnisotropyMode, Default, "Default"), + PAIR(AnisotropyMode, X2, "2x"), + PAIR(AnisotropyMode, X4, "4x"), + PAIR(AnisotropyMode, X8, "8x"), + PAIR(AnisotropyMode, X16, "16x"), }}); - translations->insert( - {typeid(Settings::AspectRatio), - { - {static_cast(Settings::AspectRatio::R16_9), tr("Default (16:9)")}, - {static_cast(Settings::AspectRatio::R4_3), tr("Force 4:3")}, - {static_cast(Settings::AspectRatio::R21_9), tr("Force 21:9")}, - {static_cast(Settings::AspectRatio::R16_10), tr("Force 16:10")}, - {static_cast(Settings::AspectRatio::Stretch), tr("Stretch to Window")}, - }}); - translations->insert( - {typeid(Settings::AnisotropyMode), - { - {static_cast(Settings::AnisotropyMode::Automatic), tr("Automatic")}, - {static_cast(Settings::AnisotropyMode::Default), tr("Default")}, - {static_cast(Settings::AnisotropyMode::X2), tr("2x")}, - {static_cast(Settings::AnisotropyMode::X4), tr("4x")}, - {static_cast(Settings::AnisotropyMode::X8), tr("8x")}, - {static_cast(Settings::AnisotropyMode::X16), tr("16x")}, - }}); translations->insert( {typeid(Settings::Language), { - {static_cast(Settings::Language::Japanese), tr("Japanese (日本語)")}, - {static_cast(Settings::Language::EnglishAmerican), tr("American English")}, - {static_cast(Settings::Language::French), tr("French (français)")}, - {static_cast(Settings::Language::German), tr("German (Deutsch)")}, - {static_cast(Settings::Language::Italian), tr("Italian (italiano)")}, - {static_cast(Settings::Language::Spanish), tr("Spanish (español)")}, - {static_cast(Settings::Language::Chinese), tr("Chinese")}, - {static_cast(Settings::Language::Korean), tr("Korean (한국어)")}, - {static_cast(Settings::Language::Dutch), tr("Dutch (Nederlands)")}, - {static_cast(Settings::Language::Portuguese), tr("Portuguese (português)")}, - {static_cast(Settings::Language::Russian), tr("Russian (Русский)")}, - {static_cast(Settings::Language::Taiwanese), tr("Taiwanese")}, - {static_cast(Settings::Language::EnglishBritish), tr("British English")}, - {static_cast(Settings::Language::FrenchCanadian), tr("Canadian French")}, - {static_cast(Settings::Language::SpanishLatin), tr("Latin American Spanish")}, - {static_cast(Settings::Language::ChineseSimplified), tr("Simplified Chinese")}, - {static_cast(Settings::Language::ChineseTraditional), - tr("Traditional Chinese (正體中文)")}, - {static_cast(Settings::Language::PortugueseBrazilian), - tr("Brazilian Portuguese (português do Brasil)")}, + PAIR(Language, Japanese, "Japanese (日本語)"), + PAIR(Language, EnglishAmerican, "American English"), + PAIR(Language, French, "French (français)"), + PAIR(Language, German, "German (Deutsch)"), + PAIR(Language, Italian, "Italian (italiano)"), + PAIR(Language, Spanish, "Spanish (español)"), + PAIR(Language, Chinese, "Chinese"), + PAIR(Language, Korean, "Korean (한국어)"), + PAIR(Language, Dutch, "Dutch (Nederlands)"), + PAIR(Language, Portuguese, "Portuguese (português)"), + PAIR(Language, Russian, "Russian (Русский)"), + PAIR(Language, Taiwanese, "Taiwanese"), + PAIR(Language, EnglishBritish, "British English"), + PAIR(Language, FrenchCanadian, "Canadian French"), + PAIR(Language, SpanishLatin, "Latin American Spanish"), + PAIR(Language, ChineseSimplified, "Simplified Chinese"), + PAIR(Language, ChineseTraditional, "Traditional Chinese (正體中文)"), + PAIR(Language, PortugueseBrazilian, "Brazilian Portuguese (português do Brasil)"), }}); translations->insert({typeid(Settings::Region), { - {static_cast(Settings::Region::Japan), tr("Japan")}, - {static_cast(Settings::Region::Usa), tr("USA")}, - {static_cast(Settings::Region::Europe), tr("Europe")}, - {static_cast(Settings::Region::Australia), tr("Australia")}, - {static_cast(Settings::Region::China), tr("China")}, - {static_cast(Settings::Region::Korea), tr("Korea")}, - {static_cast(Settings::Region::Taiwan), tr("Taiwan")}, + PAIR(Region, Japan, "Japan"), + PAIR(Region, Usa, "USA"), + PAIR(Region, Europe, "Europe"), + PAIR(Region, Australia, "Australia"), + PAIR(Region, China, "China"), + PAIR(Region, Korea, "Korea"), + PAIR(Region, Taiwan, "Taiwan"), }}); translations->insert({typeid(Settings::TimeZone), { - {static_cast(Settings::TimeZone::Auto), tr("Auto")}, - {static_cast(Settings::TimeZone::Default), tr("Default")}, - {static_cast(Settings::TimeZone::CET), tr("CET")}, - {static_cast(Settings::TimeZone::CST6CDT), tr("CST6CDT")}, - {static_cast(Settings::TimeZone::Cuba), tr("Cuba")}, - {static_cast(Settings::TimeZone::EET), tr("EET")}, - {static_cast(Settings::TimeZone::Egypt), tr("Egypt")}, - {static_cast(Settings::TimeZone::Eire), tr("Eire")}, - {static_cast(Settings::TimeZone::EST), tr("EST")}, - {static_cast(Settings::TimeZone::EST5EDT), tr("EST5EDT")}, - {static_cast(Settings::TimeZone::GB), tr("GB")}, - {static_cast(Settings::TimeZone::GBEire), tr("GB-Eire")}, - {static_cast(Settings::TimeZone::GMT), tr("GMT")}, - {static_cast(Settings::TimeZone::GMTPlusZero), tr("GMT+0")}, - {static_cast(Settings::TimeZone::GMTMinusZero), tr("GMT-0")}, - {static_cast(Settings::TimeZone::GMTZero), tr("GMT0")}, - {static_cast(Settings::TimeZone::Greenwich), tr("Greenwich")}, - {static_cast(Settings::TimeZone::Hongkong), tr("Hongkong")}, - {static_cast(Settings::TimeZone::HST), tr("HST")}, - {static_cast(Settings::TimeZone::Iceland), tr("Iceland")}, - {static_cast(Settings::TimeZone::Iran), tr("Iran")}, - {static_cast(Settings::TimeZone::Israel), tr("Israel")}, - {static_cast(Settings::TimeZone::Jamaica), tr("Jamaica")}, - {static_cast(Settings::TimeZone::Kwajalein), tr("Kwajalein")}, - {static_cast(Settings::TimeZone::Libya), tr("Libya")}, - {static_cast(Settings::TimeZone::MET), tr("MET")}, - {static_cast(Settings::TimeZone::MST), tr("MST")}, - {static_cast(Settings::TimeZone::MST7MDT), tr("MST7MDT")}, - {static_cast(Settings::TimeZone::Navajo), tr("Navajo")}, - {static_cast(Settings::TimeZone::NZ), tr("NZ")}, - {static_cast(Settings::TimeZone::NZCHAT), tr("NZ-CHAT")}, - {static_cast(Settings::TimeZone::Poland), tr("Poland")}, - {static_cast(Settings::TimeZone::Portugal), tr("Portugal")}, - {static_cast(Settings::TimeZone::PRC), tr("PRC")}, - {static_cast(Settings::TimeZone::PST8PDT), tr("PST8PDT")}, - {static_cast(Settings::TimeZone::ROC), tr("ROC")}, - {static_cast(Settings::TimeZone::ROK), tr("ROK")}, - {static_cast(Settings::TimeZone::Singapore), tr("Singapore")}, - {static_cast(Settings::TimeZone::Turkey), tr("Turkey")}, - {static_cast(Settings::TimeZone::UCT), tr("UCT")}, - {static_cast(Settings::TimeZone::W_SU), tr("W-SU")}, - {static_cast(Settings::TimeZone::WET), tr("WET")}, - {static_cast(Settings::TimeZone::Zulu), tr("Zulu")}, + PAIR(TimeZone, Auto, "Auto"), + PAIR(TimeZone, Default, "Default"), + PAIR(TimeZone, CET, "CET"), + PAIR(TimeZone, CST6CDT, "CST6CDT"), + PAIR(TimeZone, Cuba, "Cuba"), + PAIR(TimeZone, EET, "EET"), + PAIR(TimeZone, Egypt, "Egypt"), + PAIR(TimeZone, Eire, "Eire"), + PAIR(TimeZone, EST, "EST"), + PAIR(TimeZone, EST5EDT, "EST5EDT"), + PAIR(TimeZone, GB, "GB"), + PAIR(TimeZone, GBEire, "GB-Eire"), + PAIR(TimeZone, GMT, "GMT"), + PAIR(TimeZone, GMTPlusZero, "GMT+0"), + PAIR(TimeZone, GMTMinusZero, "GMT-0"), + PAIR(TimeZone, GMTZero, "GMT0"), + PAIR(TimeZone, Greenwich, "Greenwich"), + PAIR(TimeZone, Hongkong, "Hongkong"), + PAIR(TimeZone, HST, "HST"), + PAIR(TimeZone, Iceland, "Iceland"), + PAIR(TimeZone, Iran, "Iran"), + PAIR(TimeZone, Israel, "Israel"), + PAIR(TimeZone, Jamaica, "Jamaica"), + PAIR(TimeZone, Kwajalein, "Kwajalein"), + PAIR(TimeZone, Libya, "Libya"), + PAIR(TimeZone, MET, "MET"), + PAIR(TimeZone, MST, "MST"), + PAIR(TimeZone, MST7MDT, "MST7MDT"), + PAIR(TimeZone, Navajo, "Navajo"), + PAIR(TimeZone, NZ, "NZ"), + PAIR(TimeZone, NZCHAT, "NZ-CHAT"), + PAIR(TimeZone, Poland, "Poland"), + PAIR(TimeZone, Portugal, "Portugal"), + PAIR(TimeZone, PRC, "PRC"), + PAIR(TimeZone, PST8PDT, "PST8PDT"), + PAIR(TimeZone, ROC, "ROC"), + PAIR(TimeZone, ROK, "ROK"), + PAIR(TimeZone, Singapore, "Singapore"), + PAIR(TimeZone, Turkey, "Turkey"), + PAIR(TimeZone, UCT, "UCT"), + PAIR(TimeZone, W_SU, "W-SU"), + PAIR(TimeZone, WET, "WET"), + PAIR(TimeZone, Zulu, "Zulu"), }}); translations->insert({typeid(Settings::AudioMode), { - {static_cast(Settings::AudioMode::Mono), tr("Mono")}, - {static_cast(Settings::AudioMode::Stereo), tr("Stereo")}, - {static_cast(Settings::AudioMode::Surround), tr("Surround")}, + PAIR(AudioMode, Mono, "Mono"), + PAIR(AudioMode, Stereo, "Stereo"), + PAIR(AudioMode, Surround, "Surround"), }}); +#undef PAIR +#undef CTX_PAIR + return translations; } } // namespace ConfigurationShared From fe6e765b2dcb892a7b52259bac1318e5f8e30a2b Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 10 Jun 2023 00:20:59 -0400 Subject: [PATCH 073/155] shared_widget: Use actionTriggered for user input signals Clicking the slider without directly interacting with the slider handle would change the value, but not trigger the restore button. --- src/yuzu/configuration/shared_widget.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 52e617da2..b83150f2b 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -194,7 +194,7 @@ QWidget* Widget::CreateSlider(bool reversed, float multiplier, const QString& fo if (!Settings::IsConfiguringGlobal()) { restore_func = [this]() { slider->setValue(std::stoi(setting.ToStringGlobal())); }; - QObject::connect(slider, &QAbstractSlider::sliderReleased, [touch]() { touch(); }); + QObject::connect(slider, &QAbstractSlider::actionTriggered, [touch]() { touch(); }); } return container; From 2fba913d0bc022085a0de8848ced02f38e48cd54 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 10 Jun 2023 00:35:45 -0400 Subject: [PATCH 074/155] settings_enums: Add const type where needed --- src/common/settings_enums.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index d820bc48e..2710f136d 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -210,7 +210,7 @@ enum class AspectRatio : u32 { #define X(ENUM, NAME) \ { (#NAME), static_cast(ENUM::NAME) } -static std::map> canonicalizations = { +static const std::map> canonicalizations = { {typeid(AudioEngine), { {"auto", static_cast(AudioEngine::Auto)}, @@ -377,7 +377,7 @@ static std::map> canonicalizations = #undef X -static std::string invalid_string{"(invalid setting)"}; +static const std::string invalid_string{"(invalid setting)"}; template const std::string& CanonicalizeEnum(Type id) { From 0193add060ecc591ca27d029916823911df5d503 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 10 Jun 2023 00:44:03 -0400 Subject: [PATCH 075/155] general: Add typeinfo where needed Using typeid without including typeinfo first produces an ill-formed program. --- src/common/settings.h | 1 + src/common/settings_enums.h | 1 + src/yuzu/configuration/configure_cpu.cpp | 1 + src/yuzu/configuration/configure_graphics.cpp | 1 + src/yuzu/configuration/shared_translation.cpp | 1 + src/yuzu/configuration/shared_widget.cpp | 1 + 6 files changed, 6 insertions(+) diff --git a/src/common/settings.h b/src/common/settings.h index 384a8ecb6..29dad27fc 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -12,6 +12,7 @@ #include #include #include +#include #include #include diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index 2710f136d..f3d76b927 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -7,6 +7,7 @@ #include #include #include +#include #include "common/common_types.h" namespace Settings { diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 159837ebd..3f321039f 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -3,6 +3,7 @@ #include #include +#include #include #include "common/common_types.h" #include "common/settings.h" diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index c053da0cd..4d638a11b 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -7,6 +7,7 @@ #include #include #include +#include #include #include #include diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 1787a35ff..0f9dc77ff 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -6,6 +6,7 @@ #include #include #include +#include #include #include #include diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index b83150f2b..c8d6b0a01 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -1,5 +1,6 @@ #include #include +#include #include #include #include From c5f8b909ecee8d58b86b3e70e5e6defe56d4780c Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 10 Jun 2023 00:45:04 -0400 Subject: [PATCH 076/155] shared_widget: Add SPDX header --- src/yuzu/configuration/shared_widget.cpp | 3 +++ src/yuzu/configuration/shared_widget.h | 3 +++ 2 files changed, 6 insertions(+) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index c8d6b0a01..04c332bc2 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -1,3 +1,6 @@ +// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + #include #include #include diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 01348e442..d99a5eace 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -1,3 +1,6 @@ +// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + #pragma once #include "yuzu/configuration/configuration_shared.h" From 79024bb9554ba676a654ff76335008e37181be1c Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 10 Jun 2023 16:40:38 -0400 Subject: [PATCH 077/155] FIXME configuration: Avoid unnecessary allocations ConfigurationShared::Widget needs to be created with a builder. This would avoid some duplicated code. --- src/yuzu/configuration/configure_audio.cpp | 4 ++++ src/yuzu/configuration/configure_cpu.cpp | 4 ++++ src/yuzu/configuration/configure_graphics.cpp | 8 ++++++-- src/yuzu/configuration/configure_graphics_advanced.cpp | 4 ++++ src/yuzu/configuration/configure_system.cpp | 4 ++++ 5 files changed, 22 insertions(+), 2 deletions(-) diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 9f9e4df8b..98c6b6f44 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -47,6 +47,10 @@ void ConfigureAudio::Setup() { push(Settings::Category::SystemAudio); for (auto* setting : settings) { + if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { + continue; + } + auto* widget = [&]() { if (setting->Id() == Settings::values.volume.Id()) { // volume needs to be a slider (default is line edit) diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 3f321039f..f4bec1155 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -50,6 +50,10 @@ void ConfigureCpu::Setup() { push(Settings::Category::CpuUnsafe); for (const auto setting : settings) { + if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { + continue; + } + auto* widget = new ConfigurationShared::Widget(setting, translations, combobox_translations, this, runtime_lock, apply_funcs); diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 4d638a11b..9afab6d91 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -231,6 +231,10 @@ void ConfigureGraphics::Setup() { std::forward_list hold_api; for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { + if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { + continue; + } + ConfigurationShared::Widget* widget = [&]() { // Set managed to false on these and set up the comboboxes ourselves if (setting->Id() == Settings::values.vulkan_device.Id() || @@ -273,8 +277,8 @@ void ConfigureGraphics::Setup() { [=](bool) { UpdateAPILayout(); }); // Detach API's restore button and place it where we want - // Lets us put it on the side, and it will automatically scale if there's a second - // combobox (shader_backend, vulkan_device) + // Lets us put it on the side, and it will automatically scale if there's a + // second combobox (shader_backend, vulkan_device) widget->layout()->removeWidget(api_restore_global_button); api_layout->addWidget(api_restore_global_button); } diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 843af230b..20ca3fa96 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -35,6 +35,10 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { for (auto setting : Settings::values.linkage.by_category[Settings::Category::RendererAdvanced]) { + if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { + continue; + } + ConfigurationShared::Widget* widget = new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs); diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index ffcbab6d9..b9d58b083 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -123,6 +123,10 @@ void ConfigureSystem::Setup() { push(Settings::values.linkage.by_category[Settings::Category::System]); for (auto setting : settings) { + if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { + continue; + } + [[maybe_unused]] std::string label = setting->GetLabel(); ConfigurationShared::Widget* widget = [=]() { if (setting->Id() == Settings::values.custom_rtc.Id()) { From 7515c502c5c417e733f55b3f95400464491dd057 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 10 Jun 2023 16:42:16 -0400 Subject: [PATCH 078/155] shared_widget: Avoid calling QWidgetPrivate::setVisible This particular setVisible function is unnecessary. It also has horrible runtime performance, so much that it consumed maybe 80% of the time used to create a widget. --- src/yuzu/configuration/shared_widget.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 04c332bc2..efb3b329c 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -500,8 +500,6 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati } this->setEnabled(enable); - this->setVisible(Settings::IsConfiguringGlobal() || setting.Switchable()); - this->setToolTip(tooltip); } } // namespace ConfigurationShared From 02265f19d996f7266da7c4cba5c9d93ab3727f9f Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 10 Jun 2023 23:39:47 -0400 Subject: [PATCH 079/155] settings: Remove redundant false literals --- src/common/settings.h | 35 ++++++++++++++++------------------- 1 file changed, 16 insertions(+), 19 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 29dad27fc..ec0686120 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -625,8 +625,8 @@ struct Values { Category::Renderer}; SwitchableSetting use_asynchronous_gpu_emulation{ linkage, true, "use_asynchronous_gpu_emulation", Category::Renderer}; - SwitchableSetting use_speed_limit{ - linkage, true, "use_speed_limit", Category::Renderer, false, true}; + SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", Category::Renderer, + false, true}; SwitchableSetting speed_limit{ linkage, 100, 0, 9999, "speed_limit", Category::Renderer, true, true}; SwitchableSetting accelerate_astc{linkage, @@ -671,9 +671,9 @@ struct Values { ResolutionScalingInfo resolution_info{}; SwitchableSetting resolution_setup{linkage, ResolutionSetup::Res1X, "resolution_setup", Category::Renderer}; - SwitchableSetting scaling_filter{ + SwitchableSetting scaling_filter{ linkage, ScalingFilter::Bilinear, "scaling_filter", Category::Renderer, true, true}; - SwitchableSetting anti_aliasing{ + SwitchableSetting anti_aliasing{ linkage, AntiAliasing::None, "anti_aliasing", Category::Renderer, true, true}; SwitchableSetting fsr_sharpening_slider{ linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer, true, true}; @@ -707,9 +707,9 @@ struct Values { Category::RendererAdvanced}; SwitchableSetting use_asynchronous_shaders{linkage, false, "use_asynchronous_shaders", Category::RendererAdvanced}; - SwitchableSetting use_fast_gpu_time{ + SwitchableSetting use_fast_gpu_time{ linkage, true, "use_fast_gpu_time", Category::RendererAdvanced, true, true}; - SwitchableSetting use_vulkan_driver_pipeline_cache{ + SwitchableSetting use_vulkan_driver_pipeline_cache{ linkage, true, "use_vulkan_driver_pipeline_cache", Category::RendererAdvanced, true, true}; SwitchableSetting enable_compute_pipelines{linkage, false, "enable_compute_pipelines", Category::RendererAdvanced}; @@ -756,12 +756,12 @@ struct Values { // Controls InputSetting> players; - Setting enable_raw_input{linkage, false, "enable_raw_input", Category::Controls, + Setting enable_raw_input{linkage, false, "enable_raw_input", Category::Controls, // Only read/write enable_raw_input on Windows platforms #ifdef _WIN32 - true + true #else - false + false #endif }; Setting controller_navigation{linkage, true, "controller_navigation", Category::Controls}; @@ -783,7 +783,7 @@ struct Values { Setting tas_enable{linkage, false, "tas_enable", Category::Controls}; Setting tas_loop{linkage, false, "tas_loop", Category::Controls}; - Setting mouse_panning{linkage, false, "mouse_panning", Category::Controls, false}; + Setting mouse_panning{linkage, false, "mouse_panning", Category::Controls, false}; Setting mouse_panning_sensitivity{ linkage, 50, 1, 100, "mouse_panning_sensitivity", Category::Controls}; Setting mouse_enabled{linkage, false, "mouse_enabled", Category::Controls}; @@ -839,22 +839,19 @@ struct Values { Setting program_args{linkage, std::string(), "program_args", Category::Debugging}; Setting dump_exefs{linkage, false, "dump_exefs", Category::Debugging}; Setting dump_nso{linkage, false, "dump_nso", Category::Debugging}; - Setting dump_shaders{linkage, false, "dump_shaders", Category::DebuggingGraphics, - false}; - Setting dump_macros{linkage, false, "dump_macros", Category::DebuggingGraphics, - false}; + Setting dump_shaders{linkage, false, "dump_shaders", Category::DebuggingGraphics, false}; + Setting dump_macros{linkage, false, "dump_macros", Category::DebuggingGraphics, false}; Setting enable_fs_access_log{linkage, false, "enable_fs_access_log", Category::Debugging}; - Setting reporting_services{linkage, false, "reporting_services", - Category::Debugging, false}; + Setting reporting_services{linkage, false, "reporting_services", Category::Debugging, + false}; Setting quest_flag{linkage, false, "quest_flag", Category::Debugging}; Setting disable_macro_jit{linkage, false, "disable_macro_jit", Category::DebuggingGraphics}; Setting disable_macro_hle{linkage, false, "disable_macro_hle", Category::DebuggingGraphics}; - Setting extended_logging{linkage, false, "extended_logging", Category::Debugging, - false}; + Setting extended_logging{linkage, false, "extended_logging", Category::Debugging, false}; Setting use_debug_asserts{linkage, false, "use_debug_asserts", Category::Debugging}; - Setting use_auto_stub{linkage, false, "use_auto_stub", Category::Debugging, false}; + Setting use_auto_stub{linkage, false, "use_auto_stub", Category::Debugging, false}; Setting enable_all_controllers{linkage, false, "enable_all_controllers", Category::Debugging}; Setting create_crash_dumps{linkage, false, "create_crash_dumps", Category::Debugging}; From 04d4b6ab802a1238eaca6c0a16d1a739503b81d9 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 10 Jun 2023 23:40:39 -0400 Subject: [PATCH 080/155] (ui,)settings: Use explicit instantiation Reduces compile times a tad on clang. --- src/audio_core/sink/sink_details.h | 5 +- src/common/CMakeLists.txt | 2 + src/common/settings.cpp | 52 +++ src/common/settings.h | 509 ++--------------------- src/common/settings_common.h | 78 ++++ src/common/settings_setting.h | 413 ++++++++++++++++++ src/yuzu/configuration/config.cpp | 6 +- src/yuzu/configuration/shared_widget.cpp | 3 + src/yuzu/uisettings.cpp | 10 + src/yuzu/uisettings.h | 10 + 10 files changed, 613 insertions(+), 475 deletions(-) create mode 100644 src/common/settings_common.h create mode 100644 src/common/settings_setting.h diff --git a/src/audio_core/sink/sink_details.h b/src/audio_core/sink/sink_details.h index 44403db71..c8498842b 100644 --- a/src/audio_core/sink/sink_details.h +++ b/src/audio_core/sink/sink_details.h @@ -3,13 +3,12 @@ #pragma once +#include #include #include #include +#include "common/settings_enums.h" -namespace Settings { -enum class AudioEngine : u32; -} namespace AudioCore { class AudioManager; diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt index 5902dd617..3c8368bb2 100644 --- a/src/common/CMakeLists.txt +++ b/src/common/CMakeLists.txt @@ -110,9 +110,11 @@ add_library(common STATIC scratch_buffer.h settings.cpp settings.h + settings_common.h settings_enums.h settings_input.cpp settings_input.h + settings_setting.h socket_types.h spin_lock.cpp spin_lock.h diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 84e90f893..10cdea844 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -7,10 +7,17 @@ #include #include #endif +#include +#include +#include +#include #include #include +#include +#include #include "common/assert.h" +#include "common/fs/fs_util.h" #include "common/fs/path_util.h" #include "common/logging/log.h" #include "common/settings.h" @@ -18,6 +25,43 @@ namespace Settings { +#define SETTING(TYPE, RANGED) template class Setting +#define SWITCHABLE(TYPE, RANGED) template class SwitchableSetting + +SETTING(AudioEngine, false); +SETTING(bool, false); +SETTING(int, false); +SETTING(std::string, false); +SETTING(u16, false); +SWITCHABLE(AnisotropyMode, true); +SWITCHABLE(AntiAliasing, false); +SWITCHABLE(AspectRatio, true); +SWITCHABLE(AstcDecodeMode, true); +SWITCHABLE(AstcRecompression, true); +SWITCHABLE(AudioMode, true); +SWITCHABLE(CpuAccuracy, true); +SWITCHABLE(FullscreenMode, true); +SWITCHABLE(GpuAccuracy, true); +SWITCHABLE(Language, true); +SWITCHABLE(NvdecEmulation, false); +SWITCHABLE(Region, true); +SWITCHABLE(RendererBackend, true); +SWITCHABLE(ScalingFilter, false); +SWITCHABLE(ShaderBackend, true); +SWITCHABLE(TimeZone, true); +SETTING(VSyncMode, true); +SWITCHABLE(bool, false); +SWITCHABLE(int, false); +SWITCHABLE(int, true); +SWITCHABLE(s64, false); +SWITCHABLE(u16, true); +SWITCHABLE(u32, false); +SWITCHABLE(u8, false); +SWITCHABLE(u8, true); + +#undef SETTING +#undef SWITCHABLE + Values values; static bool configuring_global = true; @@ -238,6 +282,14 @@ void UpdateRescalingInfo() { info.active = info.up_scale != 1 || info.down_shift != 0; } +std::string BasicSetting::ToStringGlobal() const { + return {}; +} + +bool BasicSetting::UsingGlobal() const { + return true; +} + void RestoreGlobalState(bool is_powered_on) { // If a game is running, DO NOT restore the global settings state if (is_powered_on) { diff --git a/src/common/settings.h b/src/common/settings.h index ec0686120..e03233eaf 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -5,54 +5,21 @@ #include #include -#include -#include #include -#include +#include #include #include -#include -#include #include #include #include "common/common_types.h" +#include "common/settings_common.h" #include "common/settings_enums.h" #include "common/settings_input.h" +#include "common/settings_setting.h" namespace Settings { -enum class Category : u32 { - Audio, - Core, - Cpu, - CpuDebug, - CpuUnsafe, - Renderer, - RendererAdvanced, - RendererDebug, - System, - SystemAudio, - DataStorage, - Debugging, - DebuggingGraphics, - Miscellaneous, - Network, - WebService, - AddOns, - Controls, - Ui, - UiGeneral, - UiLayout, - UiGameList, - Screenshots, - Shortcuts, - Multiplayer, - Services, - Paths, - MaxEnum, -}; - const char* TranslateCategory(Settings::Category category); struct ResolutionScalingInfo { @@ -78,441 +45,45 @@ struct ResolutionScalingInfo { } }; -class BasicSetting { -protected: - explicit BasicSetting() = default; +// Instantiate the classes elsewhere (settings.cpp) to reduce compiler/linker work +#define SETTING(TYPE, RANGED) extern template class Setting +#define SWITCHABLE(TYPE, RANGED) extern template class SwitchableSetting -public: - virtual ~BasicSetting() = default; +SETTING(AudioEngine, false); +SETTING(bool, false); +SETTING(int, false); +SETTING(s32, false); +SETTING(std::string, false); +SETTING(std::string, false); +SETTING(u16, false); +SWITCHABLE(AnisotropyMode, true); +SWITCHABLE(AntiAliasing, false); +SWITCHABLE(AspectRatio, true); +SWITCHABLE(AstcDecodeMode, true); +SWITCHABLE(AstcRecompression, true); +SWITCHABLE(AudioMode, true); +SWITCHABLE(CpuAccuracy, true); +SWITCHABLE(FullscreenMode, true); +SWITCHABLE(GpuAccuracy, true); +SWITCHABLE(Language, true); +SWITCHABLE(NvdecEmulation, false); +SWITCHABLE(Region, true); +SWITCHABLE(RendererBackend, true); +SWITCHABLE(ScalingFilter, false); +SWITCHABLE(ShaderBackend, true); +SWITCHABLE(TimeZone, true); +SETTING(VSyncMode, true); +SWITCHABLE(bool, false); +SWITCHABLE(int, false); +SWITCHABLE(int, true); +SWITCHABLE(s64, false); +SWITCHABLE(u16, true); +SWITCHABLE(u32, false); +SWITCHABLE(u8, false); +SWITCHABLE(u8, true); - virtual Category Category() const = 0; - virtual constexpr bool Switchable() const = 0; - virtual std::string ToString() const = 0; - virtual std::string ToStringGlobal() const { - return {}; - } - virtual void LoadString(const std::string& load) = 0; - virtual std::string Canonicalize() const = 0; - virtual const std::string& GetLabel() const = 0; - virtual std::string DefaultToString() const = 0; - virtual bool Save() const = 0; - virtual std::type_index TypeId() const = 0; - virtual constexpr bool IsEnum() const = 0; - virtual bool RuntimeModfiable() const = 0; - virtual void SetGlobal(bool global) {} - virtual constexpr u32 Id() const = 0; - virtual std::string MinVal() const = 0; - virtual std::string MaxVal() const = 0; - virtual bool UsingGlobal() const { - return true; - } -}; - -class Linkage { -public: - explicit Linkage(u32 initial_count = 0); - ~Linkage(); - std::map> by_category{}; - std::vector> restore_functions{}; - u32 count; -}; - -/** The Setting class is a simple resource manager. It defines a label and default value - * alongside the actual value of the setting for simpler and less-error prone use with frontend - * configurations. Specifying a default value and label is required. A minimum and maximum range - * can be specified for sanitization. - */ -template -class Setting : public BasicSetting { -protected: - Setting() = default; - - /** - * Only sets the setting to the given initializer, leaving the other members to their default - * initializers. - * - * @param global_val Initial value of the setting - */ - explicit Setting(const Type& val) : value{val} {} - -public: - /** - * Sets a default value, label, and setting value. - * - * @param linkage Setting registry - * @param default_val Initial value of the setting, and default value of the setting - * @param name Label for the setting - * @param category_ Category of the setting AKA INI group - */ - explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, - enum Category category_, bool save_ = true, bool runtime_modifiable_ = false) - requires(!ranged) - : value{default_val}, default_value{default_val}, label{name}, category{category_}, - id{linkage.count}, save{save_}, runtime_modifiable{runtime_modifiable_} { - linkage.by_category[category].push_front(this); - linkage.count++; - } - virtual ~Setting() = default; - - /** - * Sets a default value, minimum value, maximum value, and label. - * - * @param linkage Setting registry - * @param default_val Initial value of the setting, and default value of the setting - * @param min_val Sets the minimum allowed value of the setting - * @param max_val Sets the maximum allowed value of the setting - * @param name Label for the setting - * @param category_ Category of the setting AKA INI group - */ - explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, - const Type& max_val, const std::string& name, enum Category category_, - bool save_ = true, bool runtime_modifiable_ = false) - requires(ranged) - : value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val}, - label{name}, category{category_}, id{linkage.count}, save{save_}, - runtime_modifiable{runtime_modifiable_} { - linkage.by_category[category].push_front(this); - linkage.count++; - } - - /** - * Returns a reference to the setting's value. - * - * @returns A reference to the setting - */ - [[nodiscard]] virtual const Type& GetValue() const { - return value; - } - - /** - * Sets the setting to the given value. - * - * @param val The desired value - */ - virtual void SetValue(const Type& val) { - Type temp{ranged ? std::clamp(val, minimum, maximum) : val}; - std::swap(value, temp); - } - - /** - * Returns the value that this setting was created with. - * - * @returns A reference to the default value - */ - [[nodiscard]] const Type& GetDefault() const { - return default_value; - } - - /** - * Returns the label this setting was created with. - * - * @returns A reference to the label - */ - [[nodiscard]] const std::string& GetLabel() const override { - return label; - } - - /** - * Returns the setting's category AKA INI group. - * - * @returns The setting's category - */ - [[nodiscard]] enum Category Category() const override { - return category; - } - - [[nodiscard]] bool RuntimeModfiable() const override { - return runtime_modifiable; - } - - [[nodiscard]] constexpr bool IsEnum() const override { - return std::is_enum::value; - } - - /** - * Returns whether the current setting is Switchable. - * - * @returns If the setting is a SwitchableSetting - */ - [[nodiscard]] virtual constexpr bool Switchable() const override { - return false; - } - -protected: - std::string ToString(const Type& value_) const { - if constexpr (std::is_same()) { - return value_; - } else if constexpr (std::is_same>()) { - return value_.has_value() ? std::to_string(*value_) : "none"; - } else if constexpr (std::is_same()) { - return value_ ? "true" : "false"; - } else if (std::is_same()) { - return CanonicalizeEnum(value_); - } else { - return std::to_string(static_cast(value_)); - } - } - -public: - /** - * Converts the value of the setting to a std::string. Respects the global state if the setting - * has one. - * - * @returns The current setting as a std::string - */ - std::string ToString() const override { - return ToString(this->GetValue()); - } - - /** - * Returns the default value of the setting as a std::string. - * - * @returns The default value as a string. - */ - std::string DefaultToString() const override { - return ToString(default_value); - } - - /** - * Assigns a value to the setting. - * - * @param val The desired setting value - * - * @returns A reference to the setting - */ - virtual const Type& operator=(const Type& val) { - Type temp{ranged ? std::clamp(val, minimum, maximum) : val}; - std::swap(value, temp); - return value; - } - - /** - * Returns a reference to the setting. - * - * @returns A reference to the setting - */ - explicit virtual operator const Type&() const { - return value; - } - - /** - * Converts the given value to the Setting's type of value. Uses SetValue to enter the setting, - * thus respecting its constraints. - * - * @param input The desired value - */ - void LoadString(const std::string& input) override { - if (input.empty()) { - this->SetValue(this->GetDefault()); - return; - } - try { - if constexpr (std::is_same()) { - this->SetValue(input); - } else if constexpr (std::is_same>()) { - this->SetValue(static_cast(std::stoul(input))); - } else if constexpr (std::is_same()) { - this->SetValue(input == "true"); - } else if constexpr (std::is_same()) { - this->SetValue(ToEnum(input)); - } else { - this->SetValue(static_cast(std::stoll(input))); - } - } catch (std::invalid_argument) { - this->SetValue(this->GetDefault()); - } - } - - [[nodiscard]] std::string constexpr Canonicalize() const override { - if constexpr (std::is_enum::value) { - return CanonicalizeEnum(this->GetValue()); - } - return ToString(this->GetValue()); - } - - /** - * Returns the save preference of the setting i.e. when saving or reading the setting from a - * frontend, whether this setting should be skipped. - * - * @returns The save preference - */ - virtual bool Save() const override { - return save; - } - - /** - * Gives us another way to identify the setting without having to go through a string. - * - * @returns the type_index of the setting's type - */ - virtual std::type_index TypeId() const override { - return std::type_index(typeid(Type)); - } - - virtual constexpr u32 Id() const override { - return id; - } - - virtual std::string MinVal() const override { - return this->ToString(minimum); - } - virtual std::string MaxVal() const override { - return this->ToString(maximum); - } - -protected: - Type value{}; ///< The setting - const Type default_value{}; ///< The default value - const Type maximum{}; ///< Maximum allowed value of the setting - const Type minimum{}; ///< Minimum allowed value of the setting - const std::string label{}; ///< The setting's label - const enum Category category; ///< The setting's category AKA INI group - const u32 id; - bool save; - bool runtime_modifiable; -}; - -/** - * The SwitchableSetting class is a slightly more complex version of the Setting class. This adds a - * custom setting to switch to when a guest application specifically requires it. The effect is that - * other components of the emulator can access the setting's intended value without any need for the - * component to ask whether the custom or global setting is needed at the moment. - * - * By default, the global setting is used. - */ -template -class SwitchableSetting : virtual public Setting { -public: - /** - * Sets a default value, label, and setting value. - * - * @param linkage Setting registry - * @param default_val Initial value of the setting, and default value of the setting - * @param name Label for the setting - * @param category_ Category of the setting AKA INI group - */ - explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, - Category category, bool save = true, bool runtime_modifiable = false) - requires(!ranged) - : Setting{linkage, default_val, name, category, save, runtime_modifiable} { - linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); - } - virtual ~SwitchableSetting() = default; - - /** - * Sets a default value, minimum value, maximum value, and label. - * - * @param linkage Setting registry - * @param default_val Initial value of the setting, and default value of the setting - * @param min_val Sets the minimum allowed value of the setting - * @param max_val Sets the maximum allowed value of the setting - * @param name Label for the setting - * @param category_ Category of the setting AKA INI group - */ - explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, - const Type& max_val, const std::string& name, Category category, - bool save = true, bool runtime_modifiable = false) - requires(ranged) - : Setting{linkage, default_val, min_val, max_val, - name, category, save, runtime_modifiable} { - linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); - } - - /** - * Tells this setting to represent either the global or custom setting when other member - * functions are used. - * - * @param to_global Whether to use the global or custom setting. - */ - void SetGlobal(bool to_global) override { - use_global = to_global; - } - - /** - * Returns whether this setting is using the global setting or not. - * - * @returns The global state - */ - [[nodiscard]] bool UsingGlobal() const override { - return use_global; - } - - /** - * Returns either the global or custom setting depending on the values of this setting's global - * state or if the global value was specifically requested. - * - * @param need_global Request global value regardless of setting's state; defaults to false - * - * @returns The required value of the setting - */ - [[nodiscard]] virtual const Type& GetValue() const override { - if (use_global) { - return this->value; - } - return custom; - } - [[nodiscard]] virtual const Type& GetValue(bool need_global) const { - if (use_global || need_global) { - return this->value; - } - return custom; - } - - /** - * Sets the current setting value depending on the global state. - * - * @param val The new value - */ - void SetValue(const Type& val) override { - Type temp{ranged ? std::clamp(val, this->minimum, this->maximum) : val}; - if (use_global) { - std::swap(this->value, temp); - } else { - std::swap(custom, temp); - } - } - - [[nodiscard]] virtual constexpr bool Switchable() const override { - return true; - } - - [[nodiscard]] virtual std::string ToStringGlobal() const override { - return this->ToString(this->value); - } - - /** - * Assigns the current setting value depending on the global state. - * - * @param val The new value - * - * @returns A reference to the current setting value - */ - const Type& operator=(const Type& val) override { - Type temp{ranged ? std::clamp(val, this->minimum, this->maximum) : val}; - if (use_global) { - std::swap(this->value, temp); - return this->value; - } - std::swap(custom, temp); - return custom; - } - - /** - * Returns the current setting value depending on the global state. - * - * @returns A reference to the current setting value - */ - virtual explicit operator const Type&() const override { - if (use_global) { - return this->value; - } - return custom; - } - -protected: - bool use_global{true}; ///< The setting's global state - Type custom{}; ///< The custom value of the setting -}; +#undef SETTING +#undef SWITCHABLE /** * The InputSetting class allows for getting a reference to either the global or custom members. diff --git a/src/common/settings_common.h b/src/common/settings_common.h new file mode 100644 index 000000000..93fddeba6 --- /dev/null +++ b/src/common/settings_common.h @@ -0,0 +1,78 @@ +#pragma once + +#include +#include +#include +#include +#include +#include "common/common_types.h" + +namespace Settings { + +enum class Category : u32 { + Audio, + Core, + Cpu, + CpuDebug, + CpuUnsafe, + Renderer, + RendererAdvanced, + RendererDebug, + System, + SystemAudio, + DataStorage, + Debugging, + DebuggingGraphics, + Miscellaneous, + Network, + WebService, + AddOns, + Controls, + Ui, + UiGeneral, + UiLayout, + UiGameList, + Screenshots, + Shortcuts, + Multiplayer, + Services, + Paths, + MaxEnum, +}; + +class BasicSetting { +protected: + explicit BasicSetting() = default; + +public: + virtual ~BasicSetting() = default; + + virtual Category Category() const = 0; + virtual constexpr bool Switchable() const = 0; + virtual std::string ToString() const = 0; + virtual std::string ToStringGlobal() const; + virtual void LoadString(const std::string& load) = 0; + virtual std::string Canonicalize() const = 0; + virtual const std::string& GetLabel() const = 0; + virtual std::string DefaultToString() const = 0; + virtual bool Save() const = 0; + virtual std::type_index TypeId() const = 0; + virtual constexpr bool IsEnum() const = 0; + virtual bool RuntimeModfiable() const = 0; + virtual void SetGlobal(bool global) {} + virtual constexpr u32 Id() const = 0; + virtual std::string MinVal() const = 0; + virtual std::string MaxVal() const = 0; + virtual bool UsingGlobal() const; +}; + +class Linkage { +public: + explicit Linkage(u32 initial_count = 0); + ~Linkage(); + std::map> by_category{}; + std::vector> restore_functions{}; + u32 count; +}; + +} // namespace Settings diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h new file mode 100644 index 000000000..f226e38d4 --- /dev/null +++ b/src/common/settings_setting.h @@ -0,0 +1,413 @@ +#pragma once + +#include +#include +#include +#include +#include +#include "common/common_types.h" +#include "common/settings_common.h" +#include "common/settings_enums.h" + +namespace Settings { + +/** The Setting class is a simple resource manager. It defines a label and default value + * alongside the actual value of the setting for simpler and less-error prone use with frontend + * configurations. Specifying a default value and label is required. A minimum and maximum range + * can be specified for sanitization. + */ +template +class Setting : public BasicSetting { +protected: + Setting() = default; + + /** + * Only sets the setting to the given initializer, leaving the other members to their default + * initializers. + * + * @param global_val Initial value of the setting + */ + explicit Setting(const Type& val) + : value{val}, + default_value{}, maximum{}, minimum{}, label{}, category{Category::Miscellaneous}, id{} {} + +public: + /** + * Sets a default value, label, and setting value. + * + * @param linkage Setting registry + * @param default_val Initial value of the setting, and default value of the setting + * @param name Label for the setting + * @param category_ Category of the setting AKA INI group + */ + explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, + enum Category category_, bool save_ = true, bool runtime_modifiable_ = false) + requires(!ranged) + : value{default_val}, default_value{default_val}, label{name}, category{category_}, + id{linkage.count}, save{save_}, runtime_modifiable{runtime_modifiable_} { + linkage.by_category[category].push_front(this); + linkage.count++; + } + virtual ~Setting() = default; + + /** + * Sets a default value, minimum value, maximum value, and label. + * + * @param linkage Setting registry + * @param default_val Initial value of the setting, and default value of the setting + * @param min_val Sets the minimum allowed value of the setting + * @param max_val Sets the maximum allowed value of the setting + * @param name Label for the setting + * @param category_ Category of the setting AKA INI group + */ + explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, + const Type& max_val, const std::string& name, enum Category category_, + bool save_ = true, bool runtime_modifiable_ = false) + requires(ranged) + : value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val}, + label{name}, category{category_}, id{linkage.count}, save{save_}, + runtime_modifiable{runtime_modifiable_} { + linkage.by_category[category].push_front(this); + linkage.count++; + } + + /** + * Returns a reference to the setting's value. + * + * @returns A reference to the setting + */ + [[nodiscard]] virtual const Type& GetValue() const { + return value; + } + + /** + * Sets the setting to the given value. + * + * @param val The desired value + */ + virtual void SetValue(const Type& val) { + Type temp{ranged ? std::clamp(val, minimum, maximum) : val}; + std::swap(value, temp); + } + + /** + * Returns the value that this setting was created with. + * + * @returns A reference to the default value + */ + [[nodiscard]] const Type& GetDefault() const { + return default_value; + } + + /** + * Returns the label this setting was created with. + * + * @returns A reference to the label + */ + [[nodiscard]] const std::string& GetLabel() const override { + return label; + } + + /** + * Returns the setting's category AKA INI group. + * + * @returns The setting's category + */ + [[nodiscard]] enum Category Category() const override { + return category; + } + + [[nodiscard]] bool RuntimeModfiable() const override { + return runtime_modifiable; + } + + [[nodiscard]] constexpr bool IsEnum() const override { + return std::is_enum::value; + } + + /** + * Returns whether the current setting is Switchable. + * + * @returns If the setting is a SwitchableSetting + */ + [[nodiscard]] virtual constexpr bool Switchable() const override { + return false; + } + +protected: + std::string ToString(const Type& value_) const { + if constexpr (std::is_same()) { + return value_; + } else if constexpr (std::is_same>()) { + return value_.has_value() ? std::to_string(*value_) : "none"; + } else if constexpr (std::is_same()) { + return value_ ? "true" : "false"; + } else if (std::is_same()) { + return CanonicalizeEnum(value_); + } else { + return std::to_string(static_cast(value_)); + } + } + +public: + /** + * Converts the value of the setting to a std::string. Respects the global state if the setting + * has one. + * + * @returns The current setting as a std::string + */ + std::string ToString() const override { + return ToString(this->GetValue()); + } + + /** + * Returns the default value of the setting as a std::string. + * + * @returns The default value as a string. + */ + std::string DefaultToString() const override { + return ToString(default_value); + } + + /** + * Assigns a value to the setting. + * + * @param val The desired setting value + * + * @returns A reference to the setting + */ + virtual const Type& operator=(const Type& val) { + Type temp{ranged ? std::clamp(val, minimum, maximum) : val}; + std::swap(value, temp); + return value; + } + + /** + * Returns a reference to the setting. + * + * @returns A reference to the setting + */ + explicit virtual operator const Type&() const { + return value; + } + + /** + * Converts the given value to the Setting's type of value. Uses SetValue to enter the setting, + * thus respecting its constraints. + * + * @param input The desired value + */ + void LoadString(const std::string& input) override { + if (input.empty()) { + this->SetValue(this->GetDefault()); + return; + } + try { + if constexpr (std::is_same()) { + this->SetValue(input); + } else if constexpr (std::is_same>()) { + this->SetValue(static_cast(std::stoul(input))); + } else if constexpr (std::is_same()) { + this->SetValue(input == "true"); + } else if constexpr (std::is_same()) { + this->SetValue(ToEnum(input)); + } else { + this->SetValue(static_cast(std::stoll(input))); + } + } catch (std::invalid_argument) { + this->SetValue(this->GetDefault()); + } + } + + [[nodiscard]] std::string constexpr Canonicalize() const override { + if constexpr (std::is_enum::value) { + return CanonicalizeEnum(this->GetValue()); + } + return ToString(this->GetValue()); + } + + /** + * Returns the save preference of the setting i.e. when saving or reading the setting from a + * frontend, whether this setting should be skipped. + * + * @returns The save preference + */ + virtual bool Save() const override { + return save; + } + + /** + * Gives us another way to identify the setting without having to go through a string. + * + * @returns the type_index of the setting's type + */ + virtual std::type_index TypeId() const override { + return std::type_index(typeid(Type)); + } + + virtual constexpr u32 Id() const override { + return id; + } + + virtual std::string MinVal() const override { + return this->ToString(minimum); + } + virtual std::string MaxVal() const override { + return this->ToString(maximum); + } + +protected: + Type value{}; ///< The setting + const Type default_value{}; ///< The default value + const Type maximum{}; ///< Maximum allowed value of the setting + const Type minimum{}; ///< Minimum allowed value of the setting + const std::string label{}; ///< The setting's label + const enum Category category; ///< The setting's category AKA INI group + const u32 id; + bool save; + bool runtime_modifiable; +}; + +/** + * The SwitchableSetting class is a slightly more complex version of the Setting class. This adds a + * custom setting to switch to when a guest application specifically requires it. The effect is that + * other components of the emulator can access the setting's intended value without any need for the + * component to ask whether the custom or global setting is needed at the moment. + * + * By default, the global setting is used. + */ +template +class SwitchableSetting : virtual public Setting { +public: + /** + * Sets a default value, label, and setting value. + * + * @param linkage Setting registry + * @param default_val Initial value of the setting, and default value of the setting + * @param name Label for the setting + * @param category_ Category of the setting AKA INI group + */ + explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, + Category category, bool save = true, bool runtime_modifiable = false) + requires(!ranged) + : Setting{linkage, default_val, name, category, save, runtime_modifiable} { + linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); + } + virtual ~SwitchableSetting() = default; + + /** + * Sets a default value, minimum value, maximum value, and label. + * + * @param linkage Setting registry + * @param default_val Initial value of the setting, and default value of the setting + * @param min_val Sets the minimum allowed value of the setting + * @param max_val Sets the maximum allowed value of the setting + * @param name Label for the setting + * @param category_ Category of the setting AKA INI group + */ + explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, + const Type& max_val, const std::string& name, Category category, + bool save = true, bool runtime_modifiable = false) + requires(ranged) + : Setting{linkage, default_val, min_val, max_val, + name, category, save, runtime_modifiable} { + linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); + } + + /** + * Tells this setting to represent either the global or custom setting when other member + * functions are used. + * + * @param to_global Whether to use the global or custom setting. + */ + void SetGlobal(bool to_global) override { + use_global = to_global; + } + + /** + * Returns whether this setting is using the global setting or not. + * + * @returns The global state + */ + [[nodiscard]] bool UsingGlobal() const override { + return use_global; + } + + /** + * Returns either the global or custom setting depending on the values of this setting's global + * state or if the global value was specifically requested. + * + * @param need_global Request global value regardless of setting's state; defaults to false + * + * @returns The required value of the setting + */ + [[nodiscard]] virtual const Type& GetValue() const override { + if (use_global) { + return this->value; + } + return custom; + } + [[nodiscard]] virtual const Type& GetValue(bool need_global) const { + if (use_global || need_global) { + return this->value; + } + return custom; + } + + /** + * Sets the current setting value depending on the global state. + * + * @param val The new value + */ + void SetValue(const Type& val) override { + Type temp{ranged ? std::clamp(val, this->minimum, this->maximum) : val}; + if (use_global) { + std::swap(this->value, temp); + } else { + std::swap(custom, temp); + } + } + + [[nodiscard]] virtual constexpr bool Switchable() const override { + return true; + } + + [[nodiscard]] virtual std::string ToStringGlobal() const override { + return this->ToString(this->value); + } + + /** + * Assigns the current setting value depending on the global state. + * + * @param val The new value + * + * @returns A reference to the current setting value + */ + const Type& operator=(const Type& val) override { + Type temp{ranged ? std::clamp(val, this->minimum, this->maximum) : val}; + if (use_global) { + std::swap(this->value, temp); + return this->value; + } + std::swap(custom, temp); + return custom; + } + + /** + * Returns the current setting value depending on the global state. + * + * @returns A reference to the current setting value + */ + virtual explicit operator const Type&() const override { + if (use_global) { + return this->value; + } + return custom; + } + +protected: + bool use_global{true}; ///< The setting's global state + Type custom{}; ///< The custom value of the setting +}; + +} // namespace Settings diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 051756452..ba1847976 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -102,9 +102,9 @@ const std::map Config::renderer_backend_text }; const std::map Config::shader_backend_texts_map = { - {Settings::ShaderBackend::GLSL, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "GLSL"))}, - {Settings::ShaderBackend::GLASM, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "GLASM"))}, - {Settings::ShaderBackend::SPIRV, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "SPIRV"))}, + {Settings::ShaderBackend::Glsl, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "GLSL"))}, + {Settings::ShaderBackend::Glasm, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "GLASM"))}, + {Settings::ShaderBackend::SpirV, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "SPIRV"))}, }; // This shouldn't have anything except static initializers (no functions). So diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index efb3b329c..6142c3cb9 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -21,7 +21,10 @@ #include #include #include +#include +#include "common/assert.h" #include "common/common_types.h" +#include "common/logging/log.h" #include "common/settings.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/shared_translation.h" diff --git a/src/yuzu/uisettings.cpp b/src/yuzu/uisettings.cpp index 2c1b547fb..2a02a27bc 100644 --- a/src/yuzu/uisettings.cpp +++ b/src/yuzu/uisettings.cpp @@ -3,6 +3,16 @@ #include "yuzu/uisettings.h" +namespace Settings { +template class Setting; +template class Setting; +template class Setting; +template class Setting; +template class Setting; +template class Setting; +template class Setting; +} // namespace Settings + namespace UISettings { const Themes themes{{ diff --git a/src/yuzu/uisettings.h b/src/yuzu/uisettings.h index a734513ea..2152b0b3b 100644 --- a/src/yuzu/uisettings.h +++ b/src/yuzu/uisettings.h @@ -17,6 +17,16 @@ using Settings::Category; using Settings::Setting; +namespace Settings { +extern template class Setting; +extern template class Setting; +extern template class Setting; +extern template class Setting; +extern template class Setting; +extern template class Setting; +extern template class Setting; +} // namespace Settings + namespace UISettings { bool IsDarkTheme(); From 4903f40efe7b0c193309708ea01bd6abea8bac16 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 11 Jun 2023 00:41:14 -0400 Subject: [PATCH 081/155] settings_setting: Fix errors ToString didn't have a constexpr if statement where needed. Canonicalize missed an else, causing unreachable code error on MSVC. --- src/common/settings_setting.h | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index f226e38d4..99a4bad01 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -142,7 +142,7 @@ protected: return value_.has_value() ? std::to_string(*value_) : "none"; } else if constexpr (std::is_same()) { return value_ ? "true" : "false"; - } else if (std::is_same()) { + } else if constexpr (std::is_same()) { return CanonicalizeEnum(value_); } else { return std::to_string(static_cast(value_)); @@ -222,8 +222,9 @@ public: [[nodiscard]] std::string constexpr Canonicalize() const override { if constexpr (std::is_enum::value) { return CanonicalizeEnum(this->GetValue()); + } else { + return ToString(this->GetValue()); } - return ToString(this->GetValue()); } /** From 11e7e1b8cec5a665bdc6c9e702f83ad6ea35dd6b Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 12 Jun 2023 17:05:30 -0400 Subject: [PATCH 082/155] settings: Move some simple data to BasicSetting Reduces the need for the compiler to duplicate this code, by about 100KB executable size. --- src/common/CMakeLists.txt | 2 + src/common/settings.cpp | 8 --- src/common/settings_common.cpp | 45 ++++++++++++++++ src/common/settings_common.h | 96 +++++++++++++++++++++++++--------- src/common/settings_setting.h | 86 ++++-------------------------- 5 files changed, 129 insertions(+), 108 deletions(-) create mode 100644 src/common/settings_common.cpp diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt index 3c8368bb2..09e7e673e 100644 --- a/src/common/CMakeLists.txt +++ b/src/common/CMakeLists.txt @@ -110,6 +110,7 @@ add_library(common STATIC scratch_buffer.h settings.cpp settings.h + settings_common.cpp settings_common.h settings_enums.h settings_input.cpp @@ -199,6 +200,7 @@ if (MSVC) else() target_compile_options(common PRIVATE $<$:-fsized-deallocation> + $<$:-Werror=unreachable-code-aggressive> ) endif() diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 10cdea844..d98dd2925 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -282,14 +282,6 @@ void UpdateRescalingInfo() { info.active = info.up_scale != 1 || info.down_shift != 0; } -std::string BasicSetting::ToStringGlobal() const { - return {}; -} - -bool BasicSetting::UsingGlobal() const { - return true; -} - void RestoreGlobalState(bool is_powered_on) { // If a game is running, DO NOT restore the global settings state if (is_powered_on) { diff --git a/src/common/settings_common.cpp b/src/common/settings_common.cpp new file mode 100644 index 000000000..a7ce99515 --- /dev/null +++ b/src/common/settings_common.cpp @@ -0,0 +1,45 @@ +// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + +#include +#include "common/settings_common.h" + +namespace Settings { + +BasicSetting::BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, + bool save_, bool runtime_modifiable_) + : label{name}, category{category_}, id{linkage.count}, save{save_}, runtime_modifiable{ + runtime_modifiable_} { + linkage.by_category[category].push_front(this); + linkage.count++; +} + +BasicSetting::~BasicSetting() = default; + +std::string BasicSetting::ToStringGlobal() const { + return this->ToString(); +} + +bool BasicSetting::UsingGlobal() const { + return true; +} + +void BasicSetting::SetGlobal(bool global) {} + +bool BasicSetting::Save() const { + return save; +} + +bool BasicSetting::RuntimeModfiable() const { + return runtime_modifiable; +} + +Category BasicSetting::Category() const { + return category; +} + +const std::string& BasicSetting::GetLabel() const { + return label; +} + +} // namespace Settings diff --git a/src/common/settings_common.h b/src/common/settings_common.h index 93fddeba6..81d59115d 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -1,3 +1,6 @@ +// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + #pragma once #include @@ -40,31 +43,7 @@ enum class Category : u32 { MaxEnum, }; -class BasicSetting { -protected: - explicit BasicSetting() = default; - -public: - virtual ~BasicSetting() = default; - - virtual Category Category() const = 0; - virtual constexpr bool Switchable() const = 0; - virtual std::string ToString() const = 0; - virtual std::string ToStringGlobal() const; - virtual void LoadString(const std::string& load) = 0; - virtual std::string Canonicalize() const = 0; - virtual const std::string& GetLabel() const = 0; - virtual std::string DefaultToString() const = 0; - virtual bool Save() const = 0; - virtual std::type_index TypeId() const = 0; - virtual constexpr bool IsEnum() const = 0; - virtual bool RuntimeModfiable() const = 0; - virtual void SetGlobal(bool global) {} - virtual constexpr u32 Id() const = 0; - virtual std::string MinVal() const = 0; - virtual std::string MaxVal() const = 0; - virtual bool UsingGlobal() const; -}; +class BasicSetting; class Linkage { public: @@ -75,4 +54,71 @@ public: u32 count; }; +class BasicSetting { +protected: + explicit BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, + bool save_, bool runtime_modifiable_); + +public: + virtual ~BasicSetting(); + + /* Data retrieval */ + + [[nodiscard]] virtual std::string ToString() const = 0; + [[nodiscard]] virtual std::string ToStringGlobal() const; + [[nodiscard]] virtual std::string DefaultToString() const = 0; + [[nodiscard]] virtual std::string MinVal() const = 0; + [[nodiscard]] virtual std::string MaxVal() const = 0; + virtual void LoadString(const std::string& load) = 0; + [[nodiscard]] virtual std::string Canonicalize() const = 0; + + /* Identification */ + + [[nodiscard]] virtual std::type_index TypeId() const = 0; + [[nodiscard]] virtual constexpr bool IsEnum() const = 0; + /** + * Returns whether the current setting is Switchable. + * + * @returns If the setting is a SwitchableSetting + */ + [[nodiscard]] virtual constexpr bool Switchable() const { + return false; + } + /** + * Returns the save preference of the setting i.e. when saving or reading the setting from a + * frontend, whether this setting should be skipped. + * + * @returns The save preference + */ + [[nodiscard]] bool Save() const; + [[nodiscard]] bool RuntimeModfiable() const; + [[nodiscard]] constexpr u32 Id() const { + return id; + } + /** + * Returns the setting's category AKA INI group. + * + * @returns The setting's category + */ + [[nodiscard]] Category Category() const; + /** + * Returns the label this setting was created with. + * + * @returns A reference to the label + */ + [[nodiscard]] const std::string& GetLabel() const; + + /* Switchable settings */ + + virtual void SetGlobal(bool global); + [[nodiscard]] virtual bool UsingGlobal() const; + +private: + const std::string label; ///< The setting's label + const enum Category category; ///< The setting's category AKA INI group + const u32 id; + const bool save; + const bool runtime_modifiable; +}; + } // namespace Settings diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index 99a4bad01..1ca3acf18 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -1,3 +1,6 @@ +// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + #pragma once #include @@ -21,16 +24,6 @@ class Setting : public BasicSetting { protected: Setting() = default; - /** - * Only sets the setting to the given initializer, leaving the other members to their default - * initializers. - * - * @param global_val Initial value of the setting - */ - explicit Setting(const Type& val) - : value{val}, - default_value{}, maximum{}, minimum{}, label{}, category{Category::Miscellaneous}, id{} {} - public: /** * Sets a default value, label, and setting value. @@ -43,11 +36,8 @@ public: explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, enum Category category_, bool save_ = true, bool runtime_modifiable_ = false) requires(!ranged) - : value{default_val}, default_value{default_val}, label{name}, category{category_}, - id{linkage.count}, save{save_}, runtime_modifiable{runtime_modifiable_} { - linkage.by_category[category].push_front(this); - linkage.count++; - } + : BasicSetting(linkage, name, category_, save_, runtime_modifiable_), value{default_val}, + default_value{default_val} {} virtual ~Setting() = default; /** @@ -64,12 +54,8 @@ public: const Type& max_val, const std::string& name, enum Category category_, bool save_ = true, bool runtime_modifiable_ = false) requires(ranged) - : value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val}, - label{name}, category{category_}, id{linkage.count}, save{save_}, - runtime_modifiable{runtime_modifiable_} { - linkage.by_category[category].push_front(this); - linkage.count++; - } + : BasicSetting(linkage, name, category_, save_, runtime_modifiable_), value{default_val}, + default_value{default_val}, maximum{max_val}, minimum{min_val} {} /** * Returns a reference to the setting's value. @@ -99,41 +85,10 @@ public: return default_value; } - /** - * Returns the label this setting was created with. - * - * @returns A reference to the label - */ - [[nodiscard]] const std::string& GetLabel() const override { - return label; - } - - /** - * Returns the setting's category AKA INI group. - * - * @returns The setting's category - */ - [[nodiscard]] enum Category Category() const override { - return category; - } - - [[nodiscard]] bool RuntimeModfiable() const override { - return runtime_modifiable; - } - [[nodiscard]] constexpr bool IsEnum() const override { return std::is_enum::value; } - /** - * Returns whether the current setting is Switchable. - * - * @returns If the setting is a SwitchableSetting - */ - [[nodiscard]] virtual constexpr bool Switchable() const override { - return false; - } - protected: std::string ToString(const Type& value_) const { if constexpr (std::is_same()) { @@ -227,16 +182,6 @@ public: } } - /** - * Returns the save preference of the setting i.e. when saving or reading the setting from a - * frontend, whether this setting should be skipped. - * - * @returns The save preference - */ - virtual bool Save() const override { - return save; - } - /** * Gives us another way to identify the setting without having to go through a string. * @@ -246,10 +191,6 @@ public: return std::type_index(typeid(Type)); } - virtual constexpr u32 Id() const override { - return id; - } - virtual std::string MinVal() const override { return this->ToString(minimum); } @@ -258,15 +199,10 @@ public: } protected: - Type value{}; ///< The setting - const Type default_value{}; ///< The default value - const Type maximum{}; ///< Maximum allowed value of the setting - const Type minimum{}; ///< Minimum allowed value of the setting - const std::string label{}; ///< The setting's label - const enum Category category; ///< The setting's category AKA INI group - const u32 id; - bool save; - bool runtime_modifiable; + Type value{}; ///< The setting + const Type default_value{}; ///< The default value + const Type maximum{}; ///< Maximum allowed value of the setting + const Type minimum{}; ///< Minimum allowed value of the setting }; /** From 512fb3abff5e4bf94c9d1a8f46980833f846642a Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 12 Jun 2023 17:05:45 -0400 Subject: [PATCH 083/155] configure_graphics: Fix vulkan_device bug --- src/yuzu/configuration/configure_graphics.cpp | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 9afab6d91..44d1603d0 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -394,8 +394,6 @@ void ConfigureGraphics::ApplyConfiguration() { Settings::values.vsync_mode.SetValue(vsync_mode); } - Settings::values.shader_backend.SetGlobal(true); - Settings::values.vulkan_device.SetGlobal(true); if (Settings::IsConfiguringGlobal() || (!Settings::IsConfiguringGlobal() && api_restore_global_button->isEnabled())) { auto backend = static_cast( @@ -404,12 +402,12 @@ void ConfigureGraphics::ApplyConfiguration() { .first); switch (backend) { case Settings::RendererBackend::OpenGL: - Settings::values.shader_backend.SetGlobal(false); + Settings::values.shader_backend.SetGlobal(Settings::IsConfiguringGlobal()); Settings::values.shader_backend.SetValue(static_cast( shader_mapping[shader_backend_combobox->currentIndex()].first)); break; case Settings::RendererBackend::Vulkan: - Settings::values.vulkan_device.SetGlobal(false); + Settings::values.vulkan_device.SetGlobal(Settings::IsConfiguringGlobal()); Settings::values.vulkan_device.SetValue(vulkan_device_combobox->currentIndex()); break; case Settings::RendererBackend::Null: From 3b0650b70d8196b30102e73305066e0dba9da8fe Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 12 Jun 2023 17:42:21 -0400 Subject: [PATCH 084/155] configuration/shared: Clean up includes [IWYU] --- src/yuzu/configuration/shared_translation.cpp | 11 ++++----- src/yuzu/configuration/shared_translation.h | 2 +- src/yuzu/configuration/shared_widget.cpp | 22 ++++++++++++----- src/yuzu/configuration/shared_widget.h | 24 ++++++++++++------- 4 files changed, 37 insertions(+), 22 deletions(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 0f9dc77ff..b5a3fba4d 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -1,17 +1,16 @@ // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later -#include +#include "yuzu/configuration/shared_translation.h" + #include #include -#include -#include -#include +#include #include -#include #include #include "common/settings.h" -#include "yuzu/configuration/shared_translation.h" +#include "common/settings_enums.h" +#include "common/settings_setting.h" #include "yuzu/uisettings.h" namespace ConfigurationShared { diff --git a/src/yuzu/configuration/shared_translation.h b/src/yuzu/configuration/shared_translation.h index 52ef4f2dd..cc8419e03 100644 --- a/src/yuzu/configuration/shared_translation.h +++ b/src/yuzu/configuration/shared_translation.h @@ -5,11 +5,11 @@ #include #include -#include #include #include #include #include +#include "common/common_types.h" class QWidget; diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 6142c3cb9..6fdd00c67 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -1,34 +1,44 @@ // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#include "yuzu/configuration/shared_widget.h" + #include -#include +#include #include +#include +#include #include -#include +#include #include #include #include +#include #include -#include #include #include +#include #include +#include #include +#include #include #include #include #include #include -#include +#include +#include +#include #include +#include +#include #include "common/assert.h" #include "common/common_types.h" #include "common/logging/log.h" #include "common/settings.h" -#include "yuzu/configuration/configuration_shared.h" +#include "common/settings_common.h" #include "yuzu/configuration/shared_translation.h" -#include "yuzu/configuration/shared_widget.h" namespace ConfigurationShared { diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index d99a5eace..8ce72b238 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -3,22 +3,28 @@ #pragma once -#include "yuzu/configuration/configuration_shared.h" +#include +#include +#include +#include +#include +#include +#include #include "yuzu/configuration/shared_translation.h" -class QPushButton; -class QSpinBox; -class QComboBox; -class QLineEdit; -class QSlider; class QCheckBox; -class QLabel; -class QHBoxLayout; +class QComboBox; class QDateTimeEdit; +class QLabel; +class QLineEdit; +class QObject; +class QPushButton; +class QSlider; +class QSpinBox; namespace Settings { class BasicSetting; -} +} // namespace Settings namespace ConfigurationShared { From b4f2ad3ff5c49549bc72997360c31d0662a97439 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 13 Jun 2023 19:37:41 -0400 Subject: [PATCH 085/155] settings: Move IsConfiguringGlobal to settings_common --- src/common/settings.cpp | 9 --------- src/common/settings.h | 3 --- src/common/settings_common.cpp | 10 ++++++++++ src/common/settings_common.h | 3 +++ 4 files changed, 13 insertions(+), 12 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index d98dd2925..a1cc76a38 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -63,7 +63,6 @@ SWITCHABLE(u8, true); #undef SWITCHABLE Values values; -static bool configuring_global = true; std::string GetTimeZoneString() { const auto time_zone_index = static_cast(values.time_zone_index.GetValue()); @@ -131,14 +130,6 @@ void LogSettings() { log_path("DataStorage_SDMCDir", Common::FS::GetYuzuPath(Common::FS::YuzuPath::SDMCDir)); } -bool IsConfiguringGlobal() { - return configuring_global; -} - -void SetConfiguringGlobal(bool is_global) { - configuring_global = is_global; -} - bool IsGPULevelExtreme() { return values.gpu_accuracy.GetValue() == GpuAccuracy::Extreme; } diff --git a/src/common/settings.h b/src/common/settings.h index e03233eaf..afda3ccaf 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -450,9 +450,6 @@ struct Values { extern Values values; -bool IsConfiguringGlobal(); -void SetConfiguringGlobal(bool is_global); - bool IsGPULevelExtreme(); bool IsGPULevelHigh(); diff --git a/src/common/settings_common.cpp b/src/common/settings_common.cpp index a7ce99515..fb42991fa 100644 --- a/src/common/settings_common.cpp +++ b/src/common/settings_common.cpp @@ -42,4 +42,14 @@ const std::string& BasicSetting::GetLabel() const { return label; } +static bool configuring_global = true; + +bool IsConfiguringGlobal() { + return configuring_global; +} + +void SetConfiguringGlobal(bool is_global) { + configuring_global = is_global; +} + } // namespace Settings diff --git a/src/common/settings_common.h b/src/common/settings_common.h index 81d59115d..9d1044a19 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -43,6 +43,9 @@ enum class Category : u32 { MaxEnum, }; +bool IsConfiguringGlobal(); +void SetConfiguringGlobal(bool is_global); + class BasicSetting; class Linkage { From 27e53990ed7100159cc08fd8470a9faecd011cbe Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 13 Jun 2023 19:37:54 -0400 Subject: [PATCH 086/155] settings: Document BasicSetting, add Ranged --- src/common/settings_common.h | 119 ++++++++++++++++++++++++++++++---- src/common/settings_setting.h | 4 ++ 2 files changed, 112 insertions(+), 11 deletions(-) diff --git a/src/common/settings_common.h b/src/common/settings_common.h index 9d1044a19..4d6d3021e 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -57,6 +57,10 @@ public: u32 count; }; +/** + * BasicSetting is an abstract class that only keeps track of metadata. The string methods are + * available to get data values out. + */ class BasicSetting { protected: explicit BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, @@ -65,45 +69,117 @@ protected: public: virtual ~BasicSetting(); - /* Data retrieval */ + /* + * Data retrieval + */ + /** + * Returns a string representation of the internal data. If the Setting is Switchable, it + * respects the internal global state: it is based on GetValue(). + * + * @returns A string representation of the internal data. + */ [[nodiscard]] virtual std::string ToString() const = 0; + + /** + * Returns a string representation of the global version of internal data. If the Setting is + * not Switchable, it behaves like ToString. + * + * @returns A string representation of the global version of internal data. + */ [[nodiscard]] virtual std::string ToStringGlobal() const; + + /** + * @returns A string representation of the Setting's default value. + */ [[nodiscard]] virtual std::string DefaultToString() const = 0; + + /** + * Returns a string representation of the minimum value of the setting. If the Setting is not + * ranged, the string represents the default initialization of the data type. + * + * @returns A string representation of the minimum value of the setting. + */ [[nodiscard]] virtual std::string MinVal() const = 0; + + /** + * Returns a string representation of the maximum value of the setting. If the Setting is not + * ranged, the string represents the default initialization of the data type. + * + * @returns A string representation of the maximum value of the setting. + */ [[nodiscard]] virtual std::string MaxVal() const = 0; + + /** + * Takes a string input, converts it to the internal data type if necessary, and then runs + * SetValue with it. + * + * @param load String of the input data. + */ virtual void LoadString(const std::string& load) = 0; + + /** + * Returns a string representation of the data. If the data is an enum, it returns a string of + * the enum value. If the internal data type is not an enum, this is equivalent to ToString. + * + * e.g. renderer_backend.Canonicalize() == "OpenGL" + * + * @returns Canonicalized string representation of the internal data + */ [[nodiscard]] virtual std::string Canonicalize() const = 0; - /* Identification */ + /* + * Metadata + */ - [[nodiscard]] virtual std::type_index TypeId() const = 0; - [[nodiscard]] virtual constexpr bool IsEnum() const = 0; /** - * Returns whether the current setting is Switchable. + * @returns A unique identifier for the Setting's internal data type. + */ + [[nodiscard]] virtual std::type_index TypeId() const = 0; + + /** + * Returns true if the Setting's internal data type is an enum. + * + * @returns True if the Setting's internal data type is an enum + */ + [[nodiscard]] virtual constexpr bool IsEnum() const = 0; + + /** + * Returns true if the current setting is Switchable. * * @returns If the setting is a SwitchableSetting */ [[nodiscard]] virtual constexpr bool Switchable() const { return false; } + /** - * Returns the save preference of the setting i.e. when saving or reading the setting from a - * frontend, whether this setting should be skipped. + * Returns true to suggest that a frontend can read or write the setting to a configuration + * file. * * @returns The save preference */ [[nodiscard]] bool Save() const; + + /** + * @returns true if the current setting can be changed while the guest is running. + */ [[nodiscard]] bool RuntimeModfiable() const; + + /** + * @returns A unique number corresponding to the setting. + */ [[nodiscard]] constexpr u32 Id() const { return id; } + /** * Returns the setting's category AKA INI group. * * @returns The setting's category */ [[nodiscard]] Category Category() const; + /** * Returns the label this setting was created with. * @@ -111,17 +187,38 @@ public: */ [[nodiscard]] const std::string& GetLabel() const; - /* Switchable settings */ + /** + * @returns If the Setting checks input values for valid ranges. + */ + [[nodiscard]] virtual constexpr bool Ranged() const = 0; + /* + * Switchable settings + */ + + /** + * Sets a setting's global state. True means use the normal setting, false to use a custom + * value. Has no effect if the Setting is not Switchable. + * + * @param global The desired state + */ virtual void SetGlobal(bool global); + + /** + * Returns true if the setting is using the normal setting value. Always true if the setting is + * not Switchable. + * + * @returns The Setting's global state + */ [[nodiscard]] virtual bool UsingGlobal() const; private: const std::string label; ///< The setting's label const enum Category category; ///< The setting's category AKA INI group - const u32 id; - const bool save; - const bool runtime_modifiable; + const u32 id; ///< Unique integer for the setting + const bool save; ///< Suggests if the setting should be saved and read to a frontend config + const bool + runtime_modifiable; ///< Suggests if the setting can be modified while a guest is running }; } // namespace Settings diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index 1ca3acf18..658b6328d 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -198,6 +198,10 @@ public: return this->ToString(maximum); } + constexpr bool Ranged() const override { + return ranged; + } + protected: Type value{}; ///< The setting const Type default_value{}; ///< The default value From 7c52bb27729fcd3aab08af70d512b1ad17927c39 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 13 Jun 2023 19:38:12 -0400 Subject: [PATCH 087/155] shared_widget: Improve logging, use Setting::Ranged --- src/yuzu/configuration/shared_widget.cpp | 26 +++++++++++++++++------- 1 file changed, 19 insertions(+), 7 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 6fdd00c67..f644b2ade 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -4,10 +4,12 @@ #include "yuzu/configuration/shared_widget.h" #include +#include #include #include #include #include + #include #include #include @@ -33,10 +35,10 @@ #include #include #include + #include "common/assert.h" #include "common/common_types.h" #include "common/logging/log.h" -#include "common/settings.h" #include "common/settings_common.h" #include "yuzu/configuration/shared_translation.h" @@ -178,6 +180,12 @@ QWidget* Widget::CreateSlider(bool reversed, float multiplier, const QString& fo std::function& serializer, std::function& restore_func, const std::function& touch) { + if (!setting.Ranged()) { + LOG_ERROR(Frontend, "\"{}\" is not a ranged setting, but a slider was requested.", + setting.GetLabel()); + return nullptr; + } + QWidget* container = new QWidget(this); QHBoxLayout* layout = new QHBoxLayout(container); @@ -220,8 +228,10 @@ QWidget* Widget::CreateSlider(bool reversed, float multiplier, const QString& fo QWidget* Widget::CreateSpinBox(const QString& suffix, std::function& serializer, std::function& restore_func, const std::function& touch) { - const int min_val = std::stoi(setting.MinVal()); - const int max_val = std::stoi(setting.MaxVal()); + const int min_val = + setting.Ranged() ? std::stoi(setting.MinVal()) : std::numeric_limits::min(); + const int max_val = + setting.Ranged() ? std::stoi(setting.MaxVal()) : std::numeric_limits::max(); const int default_val = std::stoi(setting.ToString()); spinbox = new QSpinBox(this); @@ -331,8 +341,10 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu other_setting != nullptr && other_setting->TypeId() == typeid(bool); if (other_setting != nullptr && other_setting->TypeId() != typeid(bool)) { - LOG_WARNING(Frontend, - "Extra setting specified but is not bool, refusing to create checkbox for it."); + LOG_WARNING( + Frontend, + "Extra setting \"{}\" specified but is not bool, refusing to create checkbox for it.", + other_setting->GetLabel()); } std::function checkbox_serializer = []() -> std::string { return {}; }; @@ -348,7 +360,7 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); touch = [this]() { - LOG_DEBUG(Frontend, "Setting custom setting for {}", setting.GetLabel()); + LOG_DEBUG(Frontend, "Enabling custom setting for \"{}\"", setting.GetLabel()); restore_button->setEnabled(true); restore_button->setVisible(true); }; @@ -410,7 +422,7 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu } if (data_component == nullptr) { - LOG_ERROR(Frontend, "Failed to create widget for {}", setting.GetLabel()); + LOG_ERROR(Frontend, "Failed to create widget for \"{}\"", setting.GetLabel()); created = false; return; } From a0883526d6a104404404ead384788adb767c88d5 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 13 Jun 2023 19:45:51 -0400 Subject: [PATCH 088/155] settings: Delete cpu_accuracy_first_time Almost a 2 year old migration setting now --- src/common/settings.h | 2 -- src/yuzu/configuration/config.cpp | 5 ----- src/yuzu/configuration/shared_translation.cpp | 1 - 3 files changed, 8 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index afda3ccaf..e510036b4 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -146,8 +146,6 @@ struct Values { SwitchableSetting cpu_accuracy{linkage, CpuAccuracy::Auto, CpuAccuracy::Auto, CpuAccuracy::Paranoid, "cpu_accuracy", Category::Cpu}; - // TODO: remove cpu_accuracy_first_time, migration setting added 8 July 2021 - Setting cpu_accuracy_first_time{linkage, true, "cpu_accuracy_first_time", Category::Cpu}; Setting cpu_debug_mode{linkage, false, "cpu_debug_mode", Category::CpuDebug}; Setting cpuopt_page_tables{linkage, true, "cpuopt_page_tables", Category::CpuDebug}; diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index ba1847976..ffd4c623d 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -635,11 +635,6 @@ void Config::ReadCpuValues() { ReadCategory(Settings::Category::CpuDebug); ReadCategory(Settings::Category::CpuUnsafe); - if (Settings::values.cpu_accuracy_first_time) { - Settings::values.cpu_accuracy.SetValue(Settings::values.cpu_accuracy.GetDefault()); - Settings::values.cpu_accuracy_first_time.SetValue(false); - } - qt_config->endGroup(); } diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index b5a3fba4d..fa9683b21 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -39,7 +39,6 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { // Cpu INSERT(Settings, cpu_accuracy, "Accuracy:", ""); - INSERT(Settings, cpu_accuracy_first_time, "", ""); // Cpu Debug From 3240d199a29ca8a8d21f5008045767a7cb89b51d Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 13 Jun 2023 20:35:24 -0400 Subject: [PATCH 089/155] config: Remove unused functions --- src/yuzu/configuration/config.cpp | 81 ------------------------------- src/yuzu/configuration/config.h | 47 ------------------ 2 files changed, 128 deletions(-) diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index ffd4c623d..5755e5b2d 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -171,66 +171,6 @@ bool Config::IsCustomConfig() { return type == ConfigType::PerGameConfig; } -/* {Read,Write}BasicSetting and WriteGlobalSetting templates must be defined here before their - * usages later in this file. This allows explicit definition of some types that don't work - * nicely with the general version. - */ - -// Explicit std::string definition: Qt can't implicitly convert a std::string to a QVariant, nor -// can it implicitly convert a QVariant back to a {std::,Q}string -template <> -void Config::ReadBasicSetting(Settings::Setting& setting) { - const QString name = QString::fromStdString(setting.GetLabel()); - const auto default_value = QString::fromStdString(setting.GetDefault()); - if (qt_config->value(name + QStringLiteral("/default"), false).toBool()) { - setting.SetValue(default_value.toStdString()); - } else { - setting.SetValue(qt_config->value(name, default_value).toString().toStdString()); - } -} - -template -void Config::ReadBasicSetting(Settings::Setting& setting) { - const QString name = QString::fromStdString(setting.GetLabel()); - const Type default_value = setting.GetDefault(); - if (qt_config->value(name + QStringLiteral("/default"), false).toBool()) { - setting.SetValue(default_value); - } else { - setting.SetValue( - static_cast(qt_config->value(name, default_value)).value()); - } -} - -// Explicit std::string definition: Qt can't implicitly convert a std::string to a QVariant -template <> -void Config::WriteBasicSetting(const Settings::Setting& setting) { - const QString name = QString::fromStdString(setting.GetLabel()); - const std::string& value = setting.GetValue(); - qt_config->setValue(name + QStringLiteral("/default"), value == setting.GetDefault()); - qt_config->setValue(name, QString::fromStdString(value)); -} - -template -void Config::WriteBasicSetting(const Settings::Setting& setting) { - const QString name = QString::fromStdString(setting.GetLabel()); - const Type value = setting.GetValue(); - qt_config->setValue(name + QStringLiteral("/default"), value == setting.GetDefault()); - qt_config->setValue(name, value); -} - -template -void Config::WriteGlobalSetting(const Settings::SwitchableSetting& setting) { - const QString name = QString::fromStdString(setting.GetLabel()); - const Type& value = setting.GetValue(global); - if (!global) { - qt_config->setValue(name + QStringLiteral("/use_global"), setting.UsingGlobal()); - } - if (global || !setting.UsingGlobal()) { - qt_config->setValue(name + QStringLiteral("/default"), value == setting.GetDefault()); - qt_config->setValue(name, value); - } -} - void Config::ReadPlayerValue(std::size_t player_index) { const QString player_prefix = [this, player_index] { if (type == ConfigType::InputProfile) { @@ -1230,27 +1170,6 @@ QVariant Config::ReadSetting(const QString& name, const QVariant& default_value) return result; } -template -void Config::ReadGlobalSetting(Settings::SwitchableSetting& setting) { - QString name = QString::fromStdString(setting.GetLabel()); - const bool use_global = qt_config->value(name + QStringLiteral("/use_global"), true).toBool(); - setting.SetGlobal(use_global); - if (global || !use_global) { - setting.SetValue(static_cast( - ReadSetting(name, QVariant::fromValue(setting.GetDefault()))) - .value()); - } -} - -template -void Config::ReadSettingGlobal(Type& setting, const QString& name, - const QVariant& default_value) const { - const bool use_global = qt_config->value(name + QStringLiteral("/use_global"), true).toBool(); - if (global || !use_global) { - setting = ReadSetting(name, default_value).value(); - } -} - void Config::WriteSetting(const QString& name, const QVariant& value) { qt_config->setValue(name, value); } diff --git a/src/yuzu/configuration/config.h b/src/yuzu/configuration/config.h index c00e717b8..a68f291a2 100644 --- a/src/yuzu/configuration/config.h +++ b/src/yuzu/configuration/config.h @@ -138,18 +138,6 @@ private: QVariant ReadSetting(const QString& name) const; QVariant ReadSetting(const QString& name, const QVariant& default_value) const; - /** - * Only reads a setting from the qt_config if the current config is a global config, or if the - * current config is a custom config and the setting is overriding the global setting. Otherwise - * it does nothing. - * - * @param setting The variable to be modified - * @param name The setting's identifier - * @param default_value The value to use when the setting is not already present in the config - */ - template - void ReadSettingGlobal(Type& setting, const QString& name, const QVariant& default_value) const; - /** * Writes a setting to the qt_config. * @@ -164,41 +152,6 @@ private: void WriteSetting(const QString& name, const QVariant& value, const QVariant& default_value, bool use_global); - /** - * Reads a value from the qt_config and applies it to the setting, using its label and default - * value. If the config is a custom config, this will also read the global state of the setting - * and apply that information to it. - * - * @param The setting - */ - template - void ReadGlobalSetting(Settings::SwitchableSetting& setting); - - /** - * Sets a value to the qt_config using the setting's label and default value. If the config is a - * custom config, it will apply the global state, and the custom value if needed. - * - * @param The setting - */ - template - void WriteGlobalSetting(const Settings::SwitchableSetting& setting); - - /** - * Reads a value from the qt_config using the setting's label and default value and applies the - * value to the setting. - * - * @param The setting - */ - template - void ReadBasicSetting(Settings::Setting& setting); - - /** Sets a value from the setting in the qt_config using the setting's label and default value. - * - * @param The setting - */ - template - void WriteBasicSetting(const Settings::Setting& setting); - void ReadCategory(Settings::Category category); void WriteCategory(Settings::Category category); void ReadSettingGeneric(Settings::BasicSetting* const setting); From 6935332cbab11b08ce6b644c48c6d82e94bd90f9 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 15 Jun 2023 16:45:09 -0400 Subject: [PATCH 090/155] shared_widget: Some documentation, add shorter constructor The shorter constructor enables us to specify some options without needing to specify the default values of multiplier which wasn't always appropriate and could be confusing. --- src/yuzu/configuration/shared_widget.cpp | 8 +++ src/yuzu/configuration/shared_widget.h | 65 +++++++++++++++++++++--- 2 files changed, 65 insertions(+), 8 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index f644b2ade..a855559b6 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -527,4 +527,12 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati this->setToolTip(tooltip); } + +Widget::Widget(Settings::BasicSetting* setting, const TranslationMap& translations, + const ComboboxTranslationMap& combobox_translations, QWidget* parent, + bool runtime_lock, std::forward_list>& apply_funcs_, + Settings::BasicSetting* other_setting, RequestType request, const QString& string) + : Widget(setting, translations, combobox_translations, parent, runtime_lock, apply_funcs_, + request, true, 1.0f, other_setting, string) {} + } // namespace ConfigurationShared diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 8ce72b238..10d2d353e 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -44,20 +44,69 @@ class Widget : public QWidget { Q_OBJECT public: - Widget(Settings::BasicSetting* setting, const TranslationMap& translations, - const ComboboxTranslationMap& combobox_translations, QWidget* parent, bool runtime_lock, - std::forward_list>& apply_funcs_, - RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, - Settings::BasicSetting* other_setting = nullptr, - const QString& string = QStringLiteral("")); + /** + * Shorter-hand version of the constructor + * + * @param setting The primary Setting to create the Widget for + * @param translations Map of translations to display on the left side label/checkbox + * @param combobox_translations Map of translations for enumerating combo boxes + * @param parent Qt parent + * @param runtime_lock Emulated guest powered on state, for use on settings that should be + * configured during guest execution + * @param apply_funcs_ List to append, functions to run to apply the widget state to the setting + * @param other_setting Second setting to modify, to replace the label with a checkbox + * @param request What type of data representation component to create -- not always respected + * for the Setting data type + * @param string Set to specify formats for Slider feedback labels or SpinBox + */ + explicit Widget(Settings::BasicSetting* setting, const TranslationMap& translations, + const ComboboxTranslationMap& combobox_translations, QWidget* parent, + bool runtime_lock, std::forward_list>& apply_funcs_, + Settings::BasicSetting* other_setting, + RequestType request = RequestType::Default, + const QString& string = QStringLiteral("")); + + /** + * @param setting The primary Setting to create the Widget for + * @param translations Map of translations to display on the left side label/checkbox + * @param combobox_translations Map of translations for enumerating combo boxes + * @param parent Qt parent + * @param runtime_lock Emulated guest powered on state, for use on settings that should be + * configured during guest execution + * @param apply_funcs_ List to append, functions to run to apply the widget state to the setting + * @param request What type of data representation component to create -- not always respected + * for the Setting data type + * @param managed Set true if the caller will set up component data and handling + * @param multiplier Value to multiply the slider feedback label + * @param other_setting Second setting to modify, to replace the label with a checkbox + * @param string Set to specify formats for Slider feedback labels or SpinBox + */ + explicit Widget(Settings::BasicSetting* setting, const TranslationMap& translations, + const ComboboxTranslationMap& combobox_translations, QWidget* parent, + bool runtime_lock, std::forward_list>& apply_funcs_, + RequestType request = RequestType::Default, bool managed = true, + float multiplier = 1.0f, Settings::BasicSetting* other_setting = nullptr, + const QString& string = QStringLiteral("")); virtual ~Widget(); + /** + * @returns True if the Widget successfully created the components for the setting + */ bool Valid() const; + /** + * Creates a button to appear when a setting has been modified. This exists for custom + * configurations and wasn't designed to work for the global configuration. It has public access + * for settings that need to be unmanaged but can be custom. + * + * @param using_global The global state of the setting this button is for + * @param parent QWidget parent + */ [[nodiscard]] static QPushButton* CreateRestoreGlobalButton(bool using_global, QWidget* parent); - QPushButton* restore_button{}; - QLineEdit* line_edit{}; + // Direct handles to sub components created + QPushButton* restore_button{}; ///< Restore button for custom configurations + QLineEdit* line_edit{}; ///< QLineEdit, used for LineEdit and HexEdit QSpinBox* spinbox{}; QCheckBox* checkbox{}; QSlider* slider{}; From a7ee9d999f612dcf5e9fcf68b410a3b49039d8ed Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 15 Jun 2023 16:45:42 -0400 Subject: [PATCH 091/155] configuration: Use shorter constructor as needed Reduces some confusion hopefully, since some parameters specified were not specific to the setting in question. --- src/yuzu/configuration/configure_audio.cpp | 9 +++++---- src/yuzu/configuration/configure_graphics.cpp | 3 +-- src/yuzu/configuration/configure_system.cpp | 7 +++---- 3 files changed, 9 insertions(+), 10 deletions(-) diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 98c6b6f44..c90316725 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -54,14 +54,15 @@ void ConfigureAudio::Setup() { auto* widget = [&]() { if (setting->Id() == Settings::values.volume.Id()) { // volume needs to be a slider (default is line edit) - return new ConfigurationShared::Widget( - setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::Slider, true, 1.0f, nullptr, - tr("%1%", "Volume percentage (e.g. 50%)")); + return new ConfigurationShared::Widget(setting, translations, combobox_translations, + this, runtime_lock, apply_funcs, nullptr, + ConfigurationShared::RequestType::Slider, + tr("%1%", "Volume percentage (e.g. 50%)")); } else if (setting->Id() == Settings::values.audio_output_device_id.Id() || setting->Id() == Settings::values.audio_input_device_id.Id() || setting->Id() == Settings::values.sink_id.Id()) { // These need to be unmanaged comboboxes, so we can populate them ourselves + // TODO (lat9nq): Let it manage sink_id return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ComboBox, false); diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 44d1603d0..cf1333cc8 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -253,8 +253,7 @@ void ConfigureGraphics::Setup() { // speed_limit needs a checkbox to set use_speed_limit, as well as a spinbox return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::SpinBox, true, 1.0f, - &Settings::values.use_speed_limit, + &Settings::values.use_speed_limit, ConfigurationShared::RequestType::SpinBox, tr("%", "Limit speed percentage (e.g. 50%)")); } else { return new ConfigurationShared::Widget(setting, translations, combobox_translations, diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index b9d58b083..f78ed7c24 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -134,15 +134,14 @@ void ConfigureSystem::Setup() { // it and custom_rtc_enabled return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::DateTimeEdit, true, 1.0f, - &Settings::values.custom_rtc_enabled); + &Settings::values.custom_rtc_enabled, + ConfigurationShared::RequestType::DateTimeEdit); } else if (setting->Id() == Settings::values.rng_seed.Id()) { // rng_seed needs a HexEdit (default is LineEdit), and a checkbox to manage // it and rng_seed_enabled return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::HexEdit, true, 1.0f, - &Settings::values.rng_seed_enabled); + &Settings::values.rng_seed_enabled, ConfigurationShared::RequestType::HexEdit); } else { return new ConfigurationShared::Widget(setting, translations, combobox_translations, this, runtime_lock, apply_funcs); From 57a00e01d69eaf413d162899c32dd1e04aa3e157 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 15 Jun 2023 17:17:50 -0400 Subject: [PATCH 092/155] configure_graphcs: Fix setting shader/device in custom config --- src/yuzu/configuration/configure_graphics.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index cf1333cc8..673921649 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -267,6 +267,7 @@ void ConfigureGraphics::Setup() { } if (setting->Id() == Settings::values.renderer_backend.Id()) { + // Add the renderer combobox now so it's at the top api_grid_layout->addWidget(widget); api_combobox = widget->combobox; api_restore_global_button = widget->restore_button; @@ -393,6 +394,8 @@ void ConfigureGraphics::ApplyConfiguration() { Settings::values.vsync_mode.SetValue(vsync_mode); } + Settings::values.vulkan_device.SetGlobal(true); + Settings::values.shader_backend.SetGlobal(true); if (Settings::IsConfiguringGlobal() || (!Settings::IsConfiguringGlobal() && api_restore_global_button->isEnabled())) { auto backend = static_cast( From 916c6cd1a0baab21cf2c029179290d73fd8dab89 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 15 Jun 2023 17:45:33 -0400 Subject: [PATCH 093/155] configure_graphics: Simplify UpdateAPILayout Reduces branching/swictch cases for simplicity/code size --- src/yuzu/configuration/configure_graphics.cpp | 43 +++++++------------ 1 file changed, 16 insertions(+), 27 deletions(-) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 673921649..62d74d12b 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -33,6 +33,7 @@ #include "common/dynamic_library.h" #include "common/logging/log.h" #include "common/settings.h" +#include "common/settings_enums.h" #include "core/core.h" #include "ui_configure_graphics.h" #include "yuzu/configuration/configuration_shared.h" @@ -442,36 +443,24 @@ void ConfigureGraphics::UpdateBackgroundColorButton(QColor color) { void ConfigureGraphics::UpdateAPILayout() { bool runtime_lock = !system.IsPoweredOn(); - if (!Settings::IsConfiguringGlobal() && !api_restore_global_button->isEnabled()) { - vulkan_device = Settings::values.vulkan_device.GetValue(true); - shader_backend = Settings::values.shader_backend.GetValue(true); - vulkan_device_widget->setEnabled(false); - shader_backend_widget->setEnabled(false); - } else { - vulkan_device = Settings::values.vulkan_device.GetValue(); - shader_backend = Settings::values.shader_backend.GetValue(); - vulkan_device_widget->setEnabled(runtime_lock); - shader_backend_widget->setEnabled(runtime_lock); - } + bool need_global = !(Settings::IsConfiguringGlobal() || api_restore_global_button->isEnabled()); + vulkan_device = Settings::values.vulkan_device.GetValue(need_global); + shader_backend = Settings::values.shader_backend.GetValue(need_global); + vulkan_device_widget->setEnabled(!need_global && runtime_lock); + shader_backend_widget->setEnabled(!need_global && runtime_lock); - switch (GetCurrentGraphicsBackend()) { - case Settings::RendererBackend::OpenGL: + const auto current_backend = GetCurrentGraphicsBackend(); + const bool is_opengl = current_backend == Settings::RendererBackend::OpenGL; + const bool is_vulkan = current_backend == Settings::RendererBackend::Vulkan; + + vulkan_device_widget->setVisible(is_vulkan); + shader_backend_widget->setVisible(is_opengl); + + if (is_opengl) { shader_backend_combobox->setCurrentIndex( FindIndex(typeid(Settings::ShaderBackend), static_cast(shader_backend))); - vulkan_device_widget->setVisible(false); - shader_backend_widget->setVisible(true); - break; - case Settings::RendererBackend::Vulkan: - if (static_cast(vulkan_device) < vulkan_device_combobox->count()) { - vulkan_device_combobox->setCurrentIndex(vulkan_device); - } - vulkan_device_widget->setVisible(true); - shader_backend_widget->setVisible(false); - break; - case Settings::RendererBackend::Null: - vulkan_device_widget->setVisible(false); - shader_backend_widget->setVisible(false); - break; + } else if (is_vulkan && static_cast(vulkan_device) < vulkan_device_combobox->count()) { + vulkan_device_combobox->setCurrentIndex(vulkan_device); } } From ee32b177823b9b8499c9fd188a571884f00cf655 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 18 Jun 2023 03:52:41 -0400 Subject: [PATCH 094/155] common,yuzu-qt: GCC warning silences Fixes -Wshadow, -Wdeprecated, and catch by copy rather than by ref. --- src/common/settings_common.h | 2 +- src/common/settings_setting.h | 14 +++++----- src/yuzu/configuration/configure_audio.cpp | 4 +-- src/yuzu/configuration/configure_cpu.cpp | 4 +-- src/yuzu/configuration/configure_general.cpp | 4 +-- src/yuzu/configuration/configure_graphics.cpp | 6 ++--- .../configure_graphics_advanced.cpp | 4 +-- src/yuzu/configuration/configure_system.cpp | 6 ++--- src/yuzu/configuration/shared_widget.cpp | 27 ++++++++++--------- 9 files changed, 37 insertions(+), 34 deletions(-) diff --git a/src/common/settings_common.h b/src/common/settings_common.h index 4d6d3021e..2b5c72f41 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -178,7 +178,7 @@ public: * * @returns The setting's category */ - [[nodiscard]] Category Category() const; + [[nodiscard]] enum Category Category() const; /** * Returns the label this setting was created with. diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index 658b6328d..f803e4e6e 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -5,6 +5,7 @@ #include #include +#include #include #include #include @@ -169,7 +170,7 @@ public: } else { this->SetValue(static_cast(std::stoll(input))); } - } catch (std::invalid_argument) { + } catch (std::invalid_argument& e) { this->SetValue(this->GetDefault()); } } @@ -229,9 +230,10 @@ public: * @param category_ Category of the setting AKA INI group */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, - Category category, bool save = true, bool runtime_modifiable = false) + Category category_, bool save_ = true, + bool runtime_modifiable_ = false) requires(!ranged) - : Setting{linkage, default_val, name, category, save, runtime_modifiable} { + : Setting{linkage, default_val, name, category_, save_, runtime_modifiable_} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } virtual ~SwitchableSetting() = default; @@ -247,11 +249,11 @@ public: * @param category_ Category of the setting AKA INI group */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, - const Type& max_val, const std::string& name, Category category, - bool save = true, bool runtime_modifiable = false) + const Type& max_val, const std::string& name, Category category_, + bool save_ = true, bool runtime_modifiable_ = false) requires(ranged) : Setting{linkage, default_val, min_val, max_val, - name, category, save, runtime_modifiable} { + name, category_, save_, runtime_modifiable_} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index c90316725..8c5378925 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -18,10 +18,10 @@ ConfigureAudio::ConfigureAudio( const Core::System& system_, - std::shared_ptr> group, + std::shared_ptr> group_, const ConfigurationShared::TranslationMap& translations_, const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : Tab(group, parent), ui(std::make_unique()), system{system_}, + : Tab(group_, parent), ui(std::make_unique()), system{system_}, translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); Setup(); diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index f4bec1155..210af146d 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -15,10 +15,10 @@ ConfigureCpu::ConfigureCpu( const Core::System& system_, - std::shared_ptr> group, + std::shared_ptr> group_, const ConfigurationShared::TranslationMap& translations_, const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : Tab(group, parent), ui{std::make_unique()}, system{system_}, + : Tab(group_, parent), ui{std::make_unique()}, system{system_}, translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index 625dd75dd..ca5b92bc0 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -14,10 +14,10 @@ ConfigureGeneral::ConfigureGeneral( const Core::System& system_, - std::shared_ptr> group, + std::shared_ptr> group_, const ConfigurationShared::TranslationMap& translations_, const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : Tab(group, parent), ui{std::make_unique()}, system{system_}, + : Tab(group_, parent), ui{std::make_unique()}, system{system_}, translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 62d74d12b..5537118ef 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -80,10 +80,10 @@ static constexpr Settings::VSyncMode PresentModeToSetting(VkPresentModeKHR mode) ConfigureGraphics::ConfigureGraphics( const Core::System& system_, std::vector& records_, const std::function& expose_compute_option_, - std::shared_ptr> group, + std::shared_ptr> group_, const ConfigurationShared::TranslationMap& translations_, const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : ConfigurationShared::Tab(group, parent), ui{std::make_unique()}, + : ConfigurationShared::Tab(group_, parent), ui{std::make_unique()}, records{records_}, expose_compute_option{expose_compute_option_}, system{system_}, translations{translations_}, combobox_translations{combobox_translations_}, shader_mapping{combobox_translations.at(typeid(Settings::ShaderBackend))} { @@ -275,7 +275,7 @@ void ConfigureGraphics::Setup() { if (!Settings::IsConfiguringGlobal()) { QObject::connect(api_restore_global_button, &QAbstractButton::clicked, - [=](bool) { UpdateAPILayout(); }); + [this](bool) { UpdateAPILayout(); }); // Detach API's restore button and place it where we want // Lets us put it on the side, and it will automatically scale if there's a diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 20ca3fa96..e2f7d284d 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -13,10 +13,10 @@ ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced( const Core::System& system_, - std::shared_ptr> group, + std::shared_ptr> group_, const ConfigurationShared::TranslationMap& translations_, const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : Tab(group, parent), ui{std::make_unique()}, system{system_}, + : Tab(group_, parent), ui{std::make_unique()}, system{system_}, translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index f78ed7c24..51b0629a6 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -45,10 +45,10 @@ static bool IsValidLocale(u32 region_index, u32 language_index) { } ConfigureSystem::ConfigureSystem( - Core::System& system_, std::shared_ptr> group, + Core::System& system_, std::shared_ptr> group_, const ConfigurationShared::TranslationMap& translations_, const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : Tab(group, parent), ui{std::make_unique()}, system{system_}, + : Tab(group_, parent), ui{std::make_unique()}, system{system_}, translations{translations_}, combobox_translations{combobox_translations_} { ui->setupUi(this); @@ -128,7 +128,7 @@ void ConfigureSystem::Setup() { } [[maybe_unused]] std::string label = setting->GetLabel(); - ConfigurationShared::Widget* widget = [=]() { + ConfigurationShared::Widget* widget = [this, setting, runtime_lock]() { if (setting->Id() == Settings::values.custom_rtc.Id()) { // custom_rtc needs a DateTimeEdit (default is LineEdit), and a checkbox to manage // it and custom_rtc_enabled diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index a855559b6..882cd9eda 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -276,7 +276,7 @@ QWidget* Widget::CreateHexEdit(std::function& serializer, line_edit->setMaxLength(8); line_edit->setValidator(regex); - auto hex_to_dec = [=]() -> std::string { + auto hex_to_dec = [this]() -> std::string { return std::to_string(std::stoul(line_edit->text().toStdString(), nullptr, 16)); }; @@ -307,8 +307,8 @@ QWidget* Widget::CreateDateTimeEdit(bool disabled, bool restrict, serializer = [this]() { return std::to_string(date_time_edit->dateTime().toSecsSinceEpoch()); }; if (!Settings::IsConfiguringGlobal()) { - auto get_clear_val = [=]() { - return QDateTime::fromSecsSinceEpoch([=]() { + auto get_clear_val = [this, restrict, current_time]() { + return QDateTime::fromSecsSinceEpoch([this, restrict, current_time]() { if (restrict && checkbox->checkState() == Qt::Checked) { return std::stoll(setting.ToStringGlobal()); } @@ -316,13 +316,14 @@ QWidget* Widget::CreateDateTimeEdit(bool disabled, bool restrict, }()); }; - restore_func = [=]() { date_time_edit->setDateTime(get_clear_val()); }; + restore_func = [this, get_clear_val]() { date_time_edit->setDateTime(get_clear_val()); }; - QObject::connect(date_time_edit, &QDateTimeEdit::editingFinished, [=]() { - if (date_time_edit->dateTime() != get_clear_val()) { - touch(); - } - }); + QObject::connect(date_time_edit, &QDateTimeEdit::editingFinished, + [this, get_clear_val, touch]() { + if (date_time_edit->dateTime() != get_clear_val()) { + touch(); + } + }); } return date_time_edit; @@ -528,11 +529,11 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati this->setToolTip(tooltip); } -Widget::Widget(Settings::BasicSetting* setting, const TranslationMap& translations, - const ComboboxTranslationMap& combobox_translations, QWidget* parent, - bool runtime_lock, std::forward_list>& apply_funcs_, +Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, + const ComboboxTranslationMap& combobox_translations, QWidget* parent_, + bool runtime_lock_, std::forward_list>& apply_funcs_, Settings::BasicSetting* other_setting, RequestType request, const QString& string) - : Widget(setting, translations, combobox_translations, parent, runtime_lock, apply_funcs_, + : Widget(setting_, translations_, combobox_translations, parent_, runtime_lock_, apply_funcs_, request, true, 1.0f, other_setting, string) {} } // namespace ConfigurationShared From ab795fe0e26c2ea9b05e7ca0f388f53c9b3c94d5 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 18 Jun 2023 17:36:56 -0400 Subject: [PATCH 095/155] (android)config: Clang format --- src/android/app/src/main/jni/config.cpp | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/android/app/src/main/jni/config.cpp b/src/android/app/src/main/jni/config.cpp index 2a06ca024..9cdd1db1a 100644 --- a/src/android/app/src/main/jni/config.cpp +++ b/src/android/app/src/main/jni/config.cpp @@ -228,10 +228,13 @@ void Config::ReadValues() { "Renderer", "gpu_accuracy", static_cast(Settings::GPUAccuracy::Normal))); // Use GPU default anisotropic filtering on Android - Settings::values.max_anisotropy = static_cast(config->GetInteger("Renderer", "max_anisotropy", 1)); + Settings::values.max_anisotropy = + static_cast(config->GetInteger("Renderer", "max_anisotropy", 1)); // Disable ASTC compute by default on Android - Settings::values.accelerate_astc.SetValue(config->GetBoolean("Renderer", "accelerate_astc", false) ? Settings::AstcDecodeMode::GPU : Settings::AstcDecodeMode::CPU); + Settings::values.accelerate_astc.SetValue( + config->GetBoolean("Renderer", "accelerate_astc", false) ? Settings::AstcDecodeMode::GPU + : Settings::AstcDecodeMode::CPU); // Enable asynchronous presentation by default on Android Settings::values.async_presentation = From 89f89cf1df70cce9600793765982ebe32154bc86 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 18 Jun 2023 17:38:10 -0400 Subject: [PATCH 096/155] shared_widget: Correct spelling --- src/yuzu/configuration/shared_widget.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 882cd9eda..d153d8d6b 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -500,7 +500,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati }(); if (label == QStringLiteral("")) { - LOG_DEBUG(Frontend, "Translation table has emtpy entry for \"{}\", skipping...", + LOG_DEBUG(Frontend, "Translation table has empty entry for \"{}\", skipping...", setting.GetLabel()); return; } From 246740f1027ff42f1626f36cefbe88b3ed0ff03d Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 18 Jun 2023 17:57:54 -0400 Subject: [PATCH 097/155] codespellrc: Ignore canonicalizations --- .codespellrc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.codespellrc b/.codespellrc index 01ddd2362..944194a25 100644 --- a/.codespellrc +++ b/.codespellrc @@ -3,4 +3,4 @@ [codespell] skip = ./.git,./build,./dist,./Doxyfile,./externals,./LICENSES,./src/android/app/src/main/res -ignore-words-list = aci,allright,ba,deques,froms,hda,inout,lod,masia,nam,nax,nd,optin,pullrequests,pullrequest,te,transfered,unstall,uscaled,zink +ignore-words-list = aci,allright,ba,canonicalizations,deques,froms,hda,inout,lod,masia,nam,nax,nd,optin,pullrequests,pullrequest,te,transfered,unstall,uscaled,zink From c97cbd089b371ed07234c66633f105862462826a Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 18 Jun 2023 17:58:07 -0400 Subject: [PATCH 098/155] settings_setting: Fix MSVC error --- src/common/settings_setting.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index f803e4e6e..a0a05da54 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -170,7 +170,7 @@ public: } else { this->SetValue(static_cast(std::stoll(input))); } - } catch (std::invalid_argument& e) { + } catch (std::invalid_argument&) { this->SetValue(this->GetDefault()); } } From 3f0cc544cf7184adacec22aedd81f6d796bbea31 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 18 Jun 2023 19:57:14 -0400 Subject: [PATCH 099/155] common,yuzu-qt: Avoid explicit instantiation on old clang Clang versions < 15 have compile issues with explicit instantiation. Disable it for these versions. --- src/common/CMakeLists.txt | 11 ++++++++--- src/common/settings.cpp | 2 ++ src/common/settings.h | 2 ++ src/yuzu/CMakeLists.txt | 6 ++++++ src/yuzu/uisettings.cpp | 2 ++ src/yuzu/uisettings.h | 2 ++ 6 files changed, 22 insertions(+), 3 deletions(-) diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt index 09e7e673e..cf05ae364 100644 --- a/src/common/CMakeLists.txt +++ b/src/common/CMakeLists.txt @@ -197,10 +197,15 @@ if (MSVC) /we4254 # 'operator': conversion from 'type1:field_bits' to 'type2:field_bits', possible loss of data /we4800 # Implicit conversion from 'type' to bool. Possible information loss ) -else() +endif() + +if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang") target_compile_options(common PRIVATE - $<$:-fsized-deallocation> - $<$:-Werror=unreachable-code-aggressive> + -fsized-deallocation + -Werror=unreachable-code-aggressive + ) + target_compile_definitions(common PRIVATE + $<$,15>:_CANNOT_EXPLICITLY_INSTANTIATE> ) endif() diff --git a/src/common/settings.cpp b/src/common/settings.cpp index a1cc76a38..f4eb2d2fb 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -25,6 +25,7 @@ namespace Settings { +#ifndef _CANNOT_EXPLICITLY_INSTANTIATE #define SETTING(TYPE, RANGED) template class Setting #define SWITCHABLE(TYPE, RANGED) template class SwitchableSetting @@ -61,6 +62,7 @@ SWITCHABLE(u8, true); #undef SETTING #undef SWITCHABLE +#endif Values values; diff --git a/src/common/settings.h b/src/common/settings.h index e510036b4..35fa4cf3d 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -45,6 +45,7 @@ struct ResolutionScalingInfo { } }; +#ifndef _CANNOT_EXPLICITLY_INSTANTIATE // Instantiate the classes elsewhere (settings.cpp) to reduce compiler/linker work #define SETTING(TYPE, RANGED) extern template class Setting #define SWITCHABLE(TYPE, RANGED) extern template class SwitchableSetting @@ -84,6 +85,7 @@ SWITCHABLE(u8, true); #undef SETTING #undef SWITCHABLE +#endif /** * The InputSetting class allows for getting a reference to either the global or custom members. diff --git a/src/yuzu/CMakeLists.txt b/src/yuzu/CMakeLists.txt index 899b75871..5183aabdf 100644 --- a/src/yuzu/CMakeLists.txt +++ b/src/yuzu/CMakeLists.txt @@ -235,6 +235,12 @@ if (WIN32 AND YUZU_CRASH_DUMPS) target_compile_definitions(yuzu PRIVATE -DYUZU_DBGHELP) endif() +if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang") + target_compile_definitions(yuzu PRIVATE + $<$,15>:_CANNOT_EXPLICITLY_INSTANTIATE> + ) +endif() + file(GLOB COMPAT_LIST ${PROJECT_BINARY_DIR}/dist/compatibility_list/compatibility_list.qrc ${PROJECT_BINARY_DIR}/dist/compatibility_list/compatibility_list.json) diff --git a/src/yuzu/uisettings.cpp b/src/yuzu/uisettings.cpp index 2a02a27bc..41e2493b3 100644 --- a/src/yuzu/uisettings.cpp +++ b/src/yuzu/uisettings.cpp @@ -3,6 +3,7 @@ #include "yuzu/uisettings.h" +#ifndef _CANNOT_EXPLICITLY_INSTANTIATE namespace Settings { template class Setting; template class Setting; @@ -12,6 +13,7 @@ template class Setting; template class Setting; template class Setting; } // namespace Settings +#endif namespace UISettings { diff --git a/src/yuzu/uisettings.h b/src/yuzu/uisettings.h index 2152b0b3b..08049f9c4 100644 --- a/src/yuzu/uisettings.h +++ b/src/yuzu/uisettings.h @@ -17,6 +17,7 @@ using Settings::Category; using Settings::Setting; +#ifndef _CANNOT_EXPLICITLY_INSTANTIATE namespace Settings { extern template class Setting; extern template class Setting; @@ -26,6 +27,7 @@ extern template class Setting; extern template class Setting; extern template class Setting; } // namespace Settings +#endif namespace UISettings { From 69bc8ea1487b3082d1339020f0df4c59ef6797e3 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 18 Jun 2023 21:09:37 -0400 Subject: [PATCH 100/155] android-config: Update enum labels --- src/android/app/src/main/jni/config.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/android/app/src/main/jni/config.cpp b/src/android/app/src/main/jni/config.cpp index 9cdd1db1a..09c095c09 100644 --- a/src/android/app/src/main/jni/config.cpp +++ b/src/android/app/src/main/jni/config.cpp @@ -224,8 +224,8 @@ void Config::ReadValues() { ReadSetting("Renderer", Settings::values.bg_blue); // Use GPU accuracy normal by default on Android - Settings::values.gpu_accuracy = static_cast(config->GetInteger( - "Renderer", "gpu_accuracy", static_cast(Settings::GPUAccuracy::Normal))); + Settings::values.gpu_accuracy = static_cast(config->GetInteger( + "Renderer", "gpu_accuracy", static_cast(Settings::GpuAccuracy::Normal))); // Use GPU default anisotropic filtering on Android Settings::values.max_anisotropy = @@ -233,8 +233,8 @@ void Config::ReadValues() { // Disable ASTC compute by default on Android Settings::values.accelerate_astc.SetValue( - config->GetBoolean("Renderer", "accelerate_astc", false) ? Settings::AstcDecodeMode::GPU - : Settings::AstcDecodeMode::CPU); + config->GetBoolean("Renderer", "accelerate_astc", false) ? Settings::AstcDecodeMode::Gpu + : Settings::AstcDecodeMode::Cpu); // Enable asynchronous presentation by default on Android Settings::values.async_presentation = From 3a7705e7744305bc788b948e9893b0b504a662df Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 19 Jun 2023 16:41:15 -0400 Subject: [PATCH 101/155] settings: Move speed_limit to core --- src/common/settings.h | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 35fa4cf3d..c9fe6f045 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -143,6 +143,10 @@ struct Values { SwitchableSetting use_multi_core{linkage, true, "use_multi_core", Category::Core}; SwitchableSetting use_unsafe_extended_memory_layout{ linkage, false, "use_unsafe_extended_memory_layout", Category::Core}; + SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", + Category::Core, false, true}; + SwitchableSetting speed_limit{linkage, 100, 0, 9999, "speed_limit", + Category::Core, true, true}; // Cpu SwitchableSetting cpu_accuracy{linkage, CpuAccuracy::Auto, @@ -196,10 +200,6 @@ struct Values { Category::Renderer}; SwitchableSetting use_asynchronous_gpu_emulation{ linkage, true, "use_asynchronous_gpu_emulation", Category::Renderer}; - SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", Category::Renderer, - false, true}; - SwitchableSetting speed_limit{ - linkage, 100, 0, 9999, "speed_limit", Category::Renderer, true, true}; SwitchableSetting accelerate_astc{linkage, AstcDecodeMode::Cpu, AstcDecodeMode::Cpu, From 81a96bafe210c218efed4e3f1138510bb8a0748c Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 19 Jun 2023 16:41:25 -0400 Subject: [PATCH 102/155] configuration: Move speed_limit to core --- src/yuzu/configuration/configure_graphics.cpp | 6 ------ src/yuzu/configuration/configure_system.cpp | 6 ++++++ src/yuzu/configuration/shared_translation.cpp | 6 ++---- 3 files changed, 8 insertions(+), 10 deletions(-) diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 5537118ef..2f041cba6 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -250,12 +250,6 @@ void ConfigureGraphics::Setup() { setting, translations, combobox_translations, this, runtime_lock, apply_funcs, ConfigurationShared::RequestType::ReverseSlider, true, 0.5f, nullptr, tr("%1%", "FSR sharpening percentage (e.g. 50%)")); - } else if (setting->Id() == Settings::values.speed_limit.Id()) { - // speed_limit needs a checkbox to set use_speed_limit, as well as a spinbox - return new ConfigurationShared::Widget( - setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - &Settings::values.use_speed_limit, ConfigurationShared::RequestType::SpinBox, - tr("%", "Limit speed percentage (e.g. 50%)")); } else { return new ConfigurationShared::Widget(setting, translations, combobox_translations, this, runtime_lock, apply_funcs); diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 51b0629a6..6a985c515 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -142,6 +142,12 @@ void ConfigureSystem::Setup() { return new ConfigurationShared::Widget( setting, translations, combobox_translations, this, runtime_lock, apply_funcs, &Settings::values.rng_seed_enabled, ConfigurationShared::RequestType::HexEdit); + } else if (setting->Id() == Settings::values.speed_limit.Id()) { + // speed_limit needs a checkbox to set use_speed_limit, as well as a spinbox + return new ConfigurationShared::Widget( + setting, translations, combobox_translations, this, runtime_lock, apply_funcs, + &Settings::values.use_speed_limit, ConfigurationShared::RequestType::SpinBox, + tr("%", "Limit speed percentage (e.g. 50%)")); } else { return new ConfigurationShared::Widget(setting, translations, combobox_translations, this, runtime_lock, apply_funcs); diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index fa9683b21..ec4bddb26 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -36,6 +36,8 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(Settings, use_multi_core, "Multicore CPU Emulation", ""); INSERT(Settings, use_unsafe_extended_memory_layout, "Unsafe extended memory layout (8GB DRAM)", ""); + INSERT(Settings, use_speed_limit, "", ""); + INSERT(Settings, speed_limit, "Limit Speed Percent", ""); // Cpu INSERT(Settings, cpu_accuracy, "Accuracy:", ""); @@ -120,10 +122,6 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { // Renderer (Debug) - // Renderer (General) - INSERT(Settings, use_speed_limit, "", ""); - INSERT(Settings, speed_limit, "Limit Speed Percent", ""); - // System INSERT(Settings, rng_seed, "RNG Seed", ""); INSERT(Settings, rng_seed_enabled, "", ""); From fdbeb841682b89d4c9fb112786e716f5fac9540c Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 20 Jun 2023 19:26:12 -0400 Subject: [PATCH 103/155] settings,uisettings: Remove leading underscore --- src/common/CMakeLists.txt | 2 +- src/common/settings.cpp | 2 +- src/common/settings.h | 2 +- src/yuzu/CMakeLists.txt | 2 +- src/yuzu/uisettings.cpp | 2 +- src/yuzu/uisettings.h | 2 +- 6 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt index cf05ae364..e205055e6 100644 --- a/src/common/CMakeLists.txt +++ b/src/common/CMakeLists.txt @@ -205,7 +205,7 @@ if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang") -Werror=unreachable-code-aggressive ) target_compile_definitions(common PRIVATE - $<$,15>:_CANNOT_EXPLICITLY_INSTANTIATE> + $<$,15>:CANNOT_EXPLICITLY_INSTANTIATE> ) endif() diff --git a/src/common/settings.cpp b/src/common/settings.cpp index f4eb2d2fb..d9948dde8 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -25,7 +25,7 @@ namespace Settings { -#ifndef _CANNOT_EXPLICITLY_INSTANTIATE +#ifndef CANNOT_EXPLICITLY_INSTANTIATE #define SETTING(TYPE, RANGED) template class Setting #define SWITCHABLE(TYPE, RANGED) template class SwitchableSetting diff --git a/src/common/settings.h b/src/common/settings.h index c9fe6f045..0ae71dd1b 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -45,7 +45,7 @@ struct ResolutionScalingInfo { } }; -#ifndef _CANNOT_EXPLICITLY_INSTANTIATE +#ifndef CANNOT_EXPLICITLY_INSTANTIATE // Instantiate the classes elsewhere (settings.cpp) to reduce compiler/linker work #define SETTING(TYPE, RANGED) extern template class Setting #define SWITCHABLE(TYPE, RANGED) extern template class SwitchableSetting diff --git a/src/yuzu/CMakeLists.txt b/src/yuzu/CMakeLists.txt index 5183aabdf..2e4da696c 100644 --- a/src/yuzu/CMakeLists.txt +++ b/src/yuzu/CMakeLists.txt @@ -237,7 +237,7 @@ endif() if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang") target_compile_definitions(yuzu PRIVATE - $<$,15>:_CANNOT_EXPLICITLY_INSTANTIATE> + $<$,15>:CANNOT_EXPLICITLY_INSTANTIATE> ) endif() diff --git a/src/yuzu/uisettings.cpp b/src/yuzu/uisettings.cpp index 41e2493b3..f03dc01dd 100644 --- a/src/yuzu/uisettings.cpp +++ b/src/yuzu/uisettings.cpp @@ -3,7 +3,7 @@ #include "yuzu/uisettings.h" -#ifndef _CANNOT_EXPLICITLY_INSTANTIATE +#ifndef CANNOT_EXPLICITLY_INSTANTIATE namespace Settings { template class Setting; template class Setting; diff --git a/src/yuzu/uisettings.h b/src/yuzu/uisettings.h index 08049f9c4..ee8c9f214 100644 --- a/src/yuzu/uisettings.h +++ b/src/yuzu/uisettings.h @@ -17,7 +17,7 @@ using Settings::Category; using Settings::Setting; -#ifndef _CANNOT_EXPLICITLY_INSTANTIATE +#ifndef CANNOT_EXPLICITLY_INSTANTIATE namespace Settings { extern template class Setting; extern template class Setting; From 02c48a80f6f8f88716cdacbfb62643d04632949a Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 20 Jun 2023 19:34:50 -0400 Subject: [PATCH 104/155] config_shared: Remove storing the group from tab --- src/yuzu/configuration/configuration_shared.cpp | 3 +-- src/yuzu/configuration/configuration_shared.h | 5 +---- 2 files changed, 2 insertions(+), 6 deletions(-) diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index d3cfacf48..8c12d063e 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -7,8 +7,7 @@ namespace ConfigurationShared { -Tab::Tab(std::shared_ptr> group_, QWidget* parent) - : QWidget(parent), group{group_} { +Tab::Tab(std::shared_ptr> group, QWidget* parent) : QWidget(parent) { if (group != nullptr) { group->push_front(this); } diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 5313bfb4f..2a084b584 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -17,14 +17,11 @@ class Tab : public QWidget { Q_OBJECT public: - explicit Tab(std::shared_ptr> group_, QWidget* parent = nullptr); + explicit Tab(std::shared_ptr> group, QWidget* parent = nullptr); ~Tab(); virtual void ApplyConfiguration() = 0; virtual void SetConfiguration() = 0; - -private: - std::shared_ptr> group; }; } // namespace ConfigurationShared From 7ffbffe170326eb8e21fa96e5374ba6b68370db6 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 20 Jun 2023 23:25:39 -0400 Subject: [PATCH 105/155] settings_enums: More aggressively use macros This lets us define an enum and all the textual representations of its values in one swing. All for the price of some ugly macros. --- src/common/settings_enums.h | 500 +++++++++++------------------------- 1 file changed, 149 insertions(+), 351 deletions(-) diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index f3d76b927..71515257a 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -3,15 +3,72 @@ #pragma once -#include #include -#include -#include -#include +#include +#include #include "common/common_types.h" namespace Settings { +template +struct Canonicalization { + static constexpr std::vector> Get(); +}; + +#define PAIR_45(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_46(N, __VA_ARGS__)) +#define PAIR_44(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_45(N, __VA_ARGS__)) +#define PAIR_43(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_44(N, __VA_ARGS__)) +#define PAIR_42(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_43(N, __VA_ARGS__)) +#define PAIR_41(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_42(N, __VA_ARGS__)) +#define PAIR_40(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_41(N, __VA_ARGS__)) +#define PAIR_39(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_40(N, __VA_ARGS__)) +#define PAIR_38(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_39(N, __VA_ARGS__)) +#define PAIR_37(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_38(N, __VA_ARGS__)) +#define PAIR_36(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_37(N, __VA_ARGS__)) +#define PAIR_35(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_36(N, __VA_ARGS__)) +#define PAIR_34(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_35(N, __VA_ARGS__)) +#define PAIR_33(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_34(N, __VA_ARGS__)) +#define PAIR_32(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_33(N, __VA_ARGS__)) +#define PAIR_31(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_32(N, __VA_ARGS__)) +#define PAIR_30(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_31(N, __VA_ARGS__)) +#define PAIR_29(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_30(N, __VA_ARGS__)) +#define PAIR_28(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_29(N, __VA_ARGS__)) +#define PAIR_27(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_28(N, __VA_ARGS__)) +#define PAIR_26(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_27(N, __VA_ARGS__)) +#define PAIR_25(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_26(N, __VA_ARGS__)) +#define PAIR_24(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_25(N, __VA_ARGS__)) +#define PAIR_23(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_24(N, __VA_ARGS__)) +#define PAIR_22(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_23(N, __VA_ARGS__)) +#define PAIR_21(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_22(N, __VA_ARGS__)) +#define PAIR_20(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_21(N, __VA_ARGS__)) +#define PAIR_19(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_20(N, __VA_ARGS__)) +#define PAIR_18(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_19(N, __VA_ARGS__)) +#define PAIR_17(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_18(N, __VA_ARGS__)) +#define PAIR_16(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_17(N, __VA_ARGS__)) +#define PAIR_15(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_16(N, __VA_ARGS__)) +#define PAIR_14(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_15(N, __VA_ARGS__)) +#define PAIR_13(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_14(N, __VA_ARGS__)) +#define PAIR_12(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_13(N, __VA_ARGS__)) +#define PAIR_11(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_12(N, __VA_ARGS__)) +#define PAIR_10(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_11(N, __VA_ARGS__)) +#define PAIR_9(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_10(N, __VA_ARGS__)) +#define PAIR_8(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_9(N, __VA_ARGS__)) +#define PAIR_7(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_8(N, __VA_ARGS__)) +#define PAIR_6(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_7(N, __VA_ARGS__)) +#define PAIR_5(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_6(N, __VA_ARGS__)) +#define PAIR_4(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_5(N, __VA_ARGS__)) +#define PAIR_3(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_4(N, __VA_ARGS__)) +#define PAIR_2(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_3(N, __VA_ARGS__)) +#define PAIR_1(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_2(N, __VA_ARGS__)) +#define PAIR(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_1(N, __VA_ARGS__)) + +#define ENUM(NAME, ...) \ + enum class NAME : u32 { __VA_ARGS__ }; \ + template <> \ + constexpr std::vector> Canonicalization::Get() { \ + return {PAIR(NAME, __VA_ARGS__)}; \ + } + enum class AudioEngine : u32 { Auto, Cubeb, @@ -19,380 +76,121 @@ enum class AudioEngine : u32 { Null, }; -enum class AudioMode : u32 { - Mono, - Stereo, - Surround, -}; +template <> +constexpr std::vector> Canonicalization::Get() { + return { + {"auto", static_cast(AudioEngine::Auto)}, + {"cubeb", static_cast(AudioEngine::Cubeb)}, + {"sdl2", static_cast(AudioEngine::Sdl2)}, + {"null", static_cast(AudioEngine::Null)}, + }; +} -enum class Language : u32 { - Japanese, - EnglishAmerican, - French, - German, - Italian, - Spanish, - Chinese, - Korean, - Dutch, - Portuguese, - Russian, - Taiwanese, - EnglishBritish, - FrenchCanadian, - SpanishLatin, - ChineseSimplified, - ChineseTraditional, - PortugueseBrazilian, -}; +ENUM(AudioMode, Mono, Stereo, Surround); -enum class Region : u32 { - Japan, - Usa, - Europe, - Australia, - China, - Korea, - Taiwan, -}; +ENUM(Language, Japanese, EnglishAmerican, French, German, Italian, Spanish, Chinese, Korean, Dutch, + Portuguese, Russian, Taiwanese, EnglishBritish, FrenchCanadian, SpanishLatin, + ChineseSimplified, ChineseTraditional, PortugueseBrazilian); -enum class TimeZone : u32 { - Auto, - Default, - CET, - CST6CDT, - Cuba, - EET, - Egypt, - Eire, - EST, - EST5EDT, - GB, - GBEire, - GMT, - GMTPlusZero, - GMTMinusZero, - GMTZero, - Greenwich, - Hongkong, - HST, - Iceland, - Iran, - Israel, - Jamaica, - Japan, - Kwajalein, - Libya, - MET, - MST, - MST7MDT, - Navajo, - NZ, - NZCHAT, - Poland, - Portugal, - PRC, - PST8PDT, - ROC, - ROK, - Singapore, - Turkey, - UCT, - Universal, - UTC, - W_SU, - WET, - Zulu, -}; +ENUM(Region, Japan, Usa, Europe, Australia, China, Korea, Taiwan); -enum class AnisotropyMode : u32 { - Automatic = 0, - Default = 1, - X2 = 2, - X4 = 3, - X8 = 4, - X16 = 5, -}; +ENUM(TimeZone, Auto, Default, CET, CST6CDT, Cuba, EET, Egypt, Eire, EST, EST5EDT, GB, GBEire, GMT, + GMTPlusZero, GMTMinusZero, GMTZero, Greenwich, Hongkong, HST, Iceland, Iran, Israel, Jamaica, + Japan, Kwajalein, Libya, MET, MST, MST7MDT, Navajo, NZ, NZCHAT, Poland, Portugal, PRC, PST8PDT, + ROC, ROK, Singapore, Turkey, UCT, Universal, UTC, W_SU, WET, Zulu); -enum class AstcDecodeMode : u32 { - Cpu = 0, - Gpu = 1, - CpuAsynchronous = 2, -}; +ENUM(AnisotropyMode, Automatic, Default, X2, X4, X8, X16); -enum class AstcRecompression : u32 { - Uncompressed = 0, - Bc1 = 1, - Bc3 = 2, -}; +ENUM(AstcDecodeMode, Cpu, Gpu, CpuAsynchronous); -enum class VSyncMode : u32 { - Immediate = 0, - Mailbox = 1, - Fifo = 2, - FifoRelaxed = 3, -}; +ENUM(AstcRecompression, Uncompressed, Bc1, Bc3); -enum class RendererBackend : u32 { - OpenGL = 0, - Vulkan = 1, - Null = 2, -}; +ENUM(VSyncMode, Immediate, Mailbox, Fifo, FifoRelaxed); -enum class ShaderBackend : u32 { - Glsl = 0, - Glasm = 1, - SpirV = 2, -}; +ENUM(RendererBackend, OpenGL, Vulkan, Null); -enum class GpuAccuracy : u32 { - Normal = 0, - High = 1, - Extreme = 2, -}; +ENUM(ShaderBackend, Glsl, Glasm, SpirV); -enum class CpuAccuracy : u32 { - Auto = 0, - Accurate = 1, - Unsafe = 2, - Paranoid = 3, -}; +ENUM(GpuAccuracy, Normal, High, Extreme); -enum class FullscreenMode : u32 { - Borderless = 0, - Exclusive = 1, -}; +ENUM(CpuAccuracy, Auto, Accurate, Unsafe, Paranoid); -enum class NvdecEmulation : u32 { - Off = 0, - Cpu = 1, - Gpu = 2, -}; +ENUM(FullscreenMode, Borderless, Exclusive); -enum class ResolutionSetup : u32 { - Res1_2X = 0, - Res3_4X = 1, - Res1X = 2, - Res3_2X = 3, - Res2X = 4, - Res3X = 5, - Res4X = 6, - Res5X = 7, - Res6X = 8, - Res7X = 9, - Res8X = 10, -}; +ENUM(NvdecEmulation, Off, Cpu, Gpu); -enum class ScalingFilter : u32 { - NearestNeighbor = 0, - Bilinear = 1, - Bicubic = 2, - Gaussian = 3, - ScaleForce = 4, - Fsr = 5, - LastFilter = Fsr, -}; +ENUM(ResolutionSetup, Res1_2X, Res3_4X, Res1X, Res3_2X, Res2X, Res3X, Res4X, Res5X, Res6X, Res7X, + Res8X); -enum class AntiAliasing : u32 { - None = 0, - Fxaa = 1, - Smaa = 2, - LastAA = Smaa, -}; +ENUM(ScalingFilter, NearestNeighbor, Bilinear, Bicubic, Gaussian, ScaleForce, Fsr, LastFilter); -enum class AspectRatio : u32 { - R16_9, - R4_3, - R21_9, - R16_10, - Stretch, -}; +ENUM(AntiAliasing, None, Fxaa, Smaa, LastAA); -#define X(ENUM, NAME) \ - { (#NAME), static_cast(ENUM::NAME) } - -static const std::map> canonicalizations = { - {typeid(AudioEngine), - { - {"auto", static_cast(AudioEngine::Auto)}, - {"cubeb", static_cast(AudioEngine::Cubeb)}, - {"sdl2", static_cast(AudioEngine::Sdl2)}, - {"null", static_cast(AudioEngine::Null)}, - }}, - {typeid(AudioMode), - { - X(AudioMode, Mono), - X(AudioMode, Stereo), - X(AudioMode, Surround), - }}, - {typeid(Language), - { - X(Language, Japanese), - X(Language, EnglishAmerican), - X(Language, French), - X(Language, German), - X(Language, Italian), - X(Language, Spanish), - X(Language, Chinese), - X(Language, Korean), - X(Language, Dutch), - X(Language, Portuguese), - X(Language, Russian), - X(Language, Taiwanese), - X(Language, EnglishBritish), - X(Language, FrenchCanadian), - X(Language, SpanishLatin), - X(Language, ChineseSimplified), - X(Language, ChineseTraditional), - X(Language, PortugueseBrazilian), - }}, - {typeid(Region), - { - X(Region, Japan), - X(Region, Usa), - X(Region, Europe), - X(Region, Australia), - X(Region, China), - X(Region, Korea), - X(Region, Taiwan), - }}, - {typeid(TimeZone), - { - X(TimeZone, Auto), X(TimeZone, Default), X(TimeZone, CET), - X(TimeZone, CST6CDT), X(TimeZone, Cuba), X(TimeZone, EET), - X(TimeZone, Egypt), X(TimeZone, Eire), X(TimeZone, EST5EDT), - X(TimeZone, GB), X(TimeZone, GBEire), X(TimeZone, GMT), - X(TimeZone, GMTPlusZero), X(TimeZone, GMTMinusZero), X(TimeZone, GMTZero), - X(TimeZone, Greenwich), X(TimeZone, Hongkong), X(TimeZone, HST), - X(TimeZone, Iceland), X(TimeZone, Iran), X(TimeZone, Israel), - X(TimeZone, Jamaica), X(TimeZone, Japan), X(TimeZone, Kwajalein), - X(TimeZone, Libya), X(TimeZone, MET), X(TimeZone, MST), - X(TimeZone, MST7MDT), X(TimeZone, Navajo), X(TimeZone, NZ), - X(TimeZone, NZCHAT), X(TimeZone, Poland), X(TimeZone, Portugal), - X(TimeZone, PRC), X(TimeZone, ROC), X(TimeZone, ROK), - X(TimeZone, Singapore), X(TimeZone, Turkey), X(TimeZone, UCT), - X(TimeZone, Universal), X(TimeZone, UTC), X(TimeZone, W_SU), - X(TimeZone, WET), X(TimeZone, Zulu), - }}, - {typeid(AnisotropyMode), - { - X(AnisotropyMode, Automatic), - X(AnisotropyMode, Default), - X(AnisotropyMode, X2), - X(AnisotropyMode, X4), - X(AnisotropyMode, X8), - X(AnisotropyMode, X16), - }}, - {typeid(AstcDecodeMode), - { - X(AstcDecodeMode, Cpu), - X(AstcDecodeMode, Gpu), - X(AstcDecodeMode, CpuAsynchronous), - }}, - {typeid(AstcRecompression), - { - X(AstcRecompression, Uncompressed), - X(AstcRecompression, Bc1), - X(AstcRecompression, Bc3), - }}, - {typeid(VSyncMode), - { - X(VSyncMode, Immediate), - X(VSyncMode, Mailbox), - X(VSyncMode, Fifo), - X(VSyncMode, FifoRelaxed), - }}, - {typeid(RendererBackend), - { - X(RendererBackend, OpenGL), - X(RendererBackend, Vulkan), - X(RendererBackend, Null), - }}, - {typeid(ShaderBackend), - { - X(ShaderBackend, Glsl), - X(ShaderBackend, Glasm), - X(ShaderBackend, SpirV), - }}, - {typeid(GpuAccuracy), - { - X(GpuAccuracy, Normal), - X(GpuAccuracy, High), - X(GpuAccuracy, Extreme), - }}, - {typeid(CpuAccuracy), - { - X(CpuAccuracy, Auto), - X(CpuAccuracy, Accurate), - X(CpuAccuracy, Unsafe), - X(CpuAccuracy, Paranoid), - }}, - {typeid(FullscreenMode), - { - X(FullscreenMode, Borderless), - X(FullscreenMode, Exclusive), - }}, - {typeid(NvdecEmulation), - { - X(NvdecEmulation, Off), - X(NvdecEmulation, Cpu), - X(NvdecEmulation, Gpu), - }}, - {typeid(ResolutionSetup), - { - X(ResolutionSetup, Res1_2X), - X(ResolutionSetup, Res3_4X), - X(ResolutionSetup, Res1X), - X(ResolutionSetup, Res3_2X), - X(ResolutionSetup, Res2X), - X(ResolutionSetup, Res3X), - X(ResolutionSetup, Res4X), - X(ResolutionSetup, Res5X), - X(ResolutionSetup, Res6X), - X(ResolutionSetup, Res7X), - X(ResolutionSetup, Res8X), - }}, - {typeid(ScalingFilter), - { - X(ScalingFilter, NearestNeighbor), - X(ScalingFilter, Bilinear), - X(ScalingFilter, Bicubic), - X(ScalingFilter, Gaussian), - X(ScalingFilter, ScaleForce), - X(ScalingFilter, Fsr), - }}, - {typeid(AntiAliasing), - { - X(AntiAliasing, None), - X(AntiAliasing, Fxaa), - X(AntiAliasing, Smaa), - }}, - {typeid(AspectRatio), - { - X(AspectRatio, R16_9), - X(AspectRatio, R4_3), - X(AspectRatio, R21_9), - X(AspectRatio, R16_10), - X(AspectRatio, Stretch), - }}}; - -#undef X - -static const std::string invalid_string{"(invalid setting)"}; +ENUM(AspectRatio, R16_9, R4_3, R21_9, R16_10, Stretch); template -const std::string& CanonicalizeEnum(Type id) { - auto& group = canonicalizations.at(typeid(Type)); +constexpr std::string CanonicalizeEnum(Type id) { + const auto group = Canonicalization::Get(); for (auto& [name, value] : group) { if (static_cast(value) == id) { return name; } } - return invalid_string; + return "unknown"; } template -static Type ToEnum(const std::string& canonicalization) { - return static_cast(canonicalizations.at(typeid(Type)).at(canonicalization)); +constexpr Type ToEnum(const std::string& canonicalization) { + const auto group = Canonicalization::Get(); + for (auto& [name, value] : group) { + if (name == canonicalization) { + return static_cast(value); + } + } + return {}; } } // namespace Settings + +#undef ENUM +#undef PAIR +#undef PAIR_1 +#undef PAIR_2 +#undef PAIR_3 +#undef PAIR_4 +#undef PAIR_5 +#undef PAIR_6 +#undef PAIR_7 +#undef PAIR_8 +#undef PAIR_9 +#undef PAIR_10 +#undef PAIR_12 +#undef PAIR_13 +#undef PAIR_14 +#undef PAIR_15 +#undef PAIR_16 +#undef PAIR_17 +#undef PAIR_18 +#undef PAIR_19 +#undef PAIR_20 +#undef PAIR_22 +#undef PAIR_23 +#undef PAIR_24 +#undef PAIR_25 +#undef PAIR_26 +#undef PAIR_27 +#undef PAIR_28 +#undef PAIR_29 +#undef PAIR_30 +#undef PAIR_32 +#undef PAIR_33 +#undef PAIR_34 +#undef PAIR_35 +#undef PAIR_36 +#undef PAIR_37 +#undef PAIR_38 +#undef PAIR_39 +#undef PAIR_40 +#undef PAIR_42 +#undef PAIR_43 +#undef PAIR_44 +#undef PAIR_45 From 8366736b67d6febe278b6599badf4e945599bc30 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 20 Jun 2023 23:29:07 -0400 Subject: [PATCH 106/155] settings,opengl,yuzu-qt: Fix AA, Filter maximums The new enum macros don't support setting values directly. For LastAA and LastFilter, this means we need a simpler approach to loop around the toggle in the frontend... --- src/common/settings_enums.h | 4 ++-- src/video_core/renderer_opengl/renderer_opengl.cpp | 2 +- src/yuzu/main.cpp | 11 +++++------ 3 files changed, 8 insertions(+), 9 deletions(-) diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index 71515257a..cc5c929cf 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -122,9 +122,9 @@ ENUM(NvdecEmulation, Off, Cpu, Gpu); ENUM(ResolutionSetup, Res1_2X, Res3_4X, Res1X, Res3_2X, Res2X, Res3X, Res4X, Res5X, Res6X, Res7X, Res8X); -ENUM(ScalingFilter, NearestNeighbor, Bilinear, Bicubic, Gaussian, ScaleForce, Fsr, LastFilter); +ENUM(ScalingFilter, NearestNeighbor, Bilinear, Bicubic, Gaussian, ScaleForce, Fsr, MaxEnum); -ENUM(AntiAliasing, None, Fxaa, Smaa, LastAA); +ENUM(AntiAliasing, None, Fxaa, Smaa, MaxEnum); ENUM(AspectRatio, R16_9, R4_3, R21_9, R16_10, Stretch); diff --git a/src/video_core/renderer_opengl/renderer_opengl.cpp b/src/video_core/renderer_opengl/renderer_opengl.cpp index 2a74c1d05..6b8d4e554 100644 --- a/src/video_core/renderer_opengl/renderer_opengl.cpp +++ b/src/video_core/renderer_opengl/renderer_opengl.cpp @@ -473,7 +473,7 @@ void RendererOpenGL::DrawScreen(const Layout::FramebufferLayout& layout) { glBindTextureUnit(0, screen_info.display_texture); auto anti_aliasing = Settings::values.anti_aliasing.GetValue(); - if (anti_aliasing > Settings::AntiAliasing::LastAA) { + if (anti_aliasing >= Settings::AntiAliasing::MaxEnum) { LOG_ERROR(Render_OpenGL, "Invalid antialiasing option selected {}", anti_aliasing); anti_aliasing = Settings::AntiAliasing::None; Settings::values.anti_aliasing.SetValue(anti_aliasing); diff --git a/src/yuzu/main.cpp b/src/yuzu/main.cpp index 2922b3347..97ae9e49a 100644 --- a/src/yuzu/main.cpp +++ b/src/yuzu/main.cpp @@ -24,6 +24,7 @@ #include "applets/qt_software_keyboard.h" #include "applets/qt_web_browser.h" #include "common/nvidia_flags.h" +#include "common/settings_enums.h" #include "configuration/configure_input.h" #include "configuration/configure_per_game.h" #include "configuration/configure_tas.h" @@ -1095,10 +1096,9 @@ void GMainWindow::InitializeWidgets() { aa_status_button->setFocusPolicy(Qt::NoFocus); connect(aa_status_button, &QPushButton::clicked, [&] { auto aa_mode = Settings::values.anti_aliasing.GetValue(); - if (aa_mode == Settings::AntiAliasing::LastAA) { + aa_mode = static_cast(static_cast(aa_mode) + 1); + if (aa_mode == Settings::AntiAliasing::MaxEnum) { aa_mode = Settings::AntiAliasing::None; - } else { - aa_mode = static_cast(static_cast(aa_mode) + 1); } Settings::values.anti_aliasing.SetValue(aa_mode); aa_status_button->setChecked(true); @@ -3702,10 +3702,9 @@ void GMainWindow::OnIncreaseVolume() { void GMainWindow::OnToggleAdaptingFilter() { auto filter = Settings::values.scaling_filter.GetValue(); - if (filter == Settings::ScalingFilter::LastFilter) { + filter = static_cast(static_cast(filter) + 1); + if (filter == Settings::ScalingFilter::MaxEnum) { filter = Settings::ScalingFilter::NearestNeighbor; - } else { - filter = static_cast(static_cast(filter) + 1); } Settings::values.scaling_filter.SetValue(filter); filter_status_button->setChecked(true); From 8b28aa45b99cc6f6c9399bbe421460de67088cff Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 20 Jun 2023 23:34:03 -0400 Subject: [PATCH 107/155] settings,translation: Fix time zone enum Renames enum values to conform to naming convention. --- src/common/settings_enums.h | 8 ++-- src/yuzu/configuration/shared_translation.cpp | 48 +++++++++---------- 2 files changed, 28 insertions(+), 28 deletions(-) diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index cc5c929cf..c380e409e 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -94,10 +94,10 @@ ENUM(Language, Japanese, EnglishAmerican, French, German, Italian, Spanish, Chin ENUM(Region, Japan, Usa, Europe, Australia, China, Korea, Taiwan); -ENUM(TimeZone, Auto, Default, CET, CST6CDT, Cuba, EET, Egypt, Eire, EST, EST5EDT, GB, GBEire, GMT, - GMTPlusZero, GMTMinusZero, GMTZero, Greenwich, Hongkong, HST, Iceland, Iran, Israel, Jamaica, - Japan, Kwajalein, Libya, MET, MST, MST7MDT, Navajo, NZ, NZCHAT, Poland, Portugal, PRC, PST8PDT, - ROC, ROK, Singapore, Turkey, UCT, Universal, UTC, W_SU, WET, Zulu); +ENUM(TimeZone, Auto, Default, Cet, Cst6Cdt, Cuba, Eet, Egypt, Eire, Est, Est5Edt, Gb, GbEire, Gmt, + GmtPlusZero, GmtMinusZero, GmtZero, Greenwich, Hongkong, Hst, Iceland, Iran, Israel, Jamaica, + Japan, Kwajalein, Libya, Met, Mst, Mst7Mdt, Navajo, Nz, NzChat, Poland, Portugal, Prc, Pst8Pdt, + Roc, Rok, Singapore, Turkey, Uct, Universal, Utc, WSu, Wet, Zulu); ENUM(AnisotropyMode, Automatic, Default, X2, X4, X8, X16); diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index ec4bddb26..a75574530 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -311,46 +311,46 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { { PAIR(TimeZone, Auto, "Auto"), PAIR(TimeZone, Default, "Default"), - PAIR(TimeZone, CET, "CET"), - PAIR(TimeZone, CST6CDT, "CST6CDT"), + PAIR(TimeZone, Cet, "CET"), + PAIR(TimeZone, Cst6Cdt, "CST6CDT"), PAIR(TimeZone, Cuba, "Cuba"), - PAIR(TimeZone, EET, "EET"), + PAIR(TimeZone, Eet, "EET"), PAIR(TimeZone, Egypt, "Egypt"), PAIR(TimeZone, Eire, "Eire"), - PAIR(TimeZone, EST, "EST"), - PAIR(TimeZone, EST5EDT, "EST5EDT"), - PAIR(TimeZone, GB, "GB"), - PAIR(TimeZone, GBEire, "GB-Eire"), - PAIR(TimeZone, GMT, "GMT"), - PAIR(TimeZone, GMTPlusZero, "GMT+0"), - PAIR(TimeZone, GMTMinusZero, "GMT-0"), - PAIR(TimeZone, GMTZero, "GMT0"), + PAIR(TimeZone, Est, "EST"), + PAIR(TimeZone, Est5Edt, "EST5EDT"), + PAIR(TimeZone, Gb, "GB"), + PAIR(TimeZone, GbEire, "GB-Eire"), + PAIR(TimeZone, Gmt, "GMT"), + PAIR(TimeZone, GmtPlusZero, "GMT+0"), + PAIR(TimeZone, GmtMinusZero, "GMT-0"), + PAIR(TimeZone, GmtZero, "GMT0"), PAIR(TimeZone, Greenwich, "Greenwich"), PAIR(TimeZone, Hongkong, "Hongkong"), - PAIR(TimeZone, HST, "HST"), + PAIR(TimeZone, Hst, "HST"), PAIR(TimeZone, Iceland, "Iceland"), PAIR(TimeZone, Iran, "Iran"), PAIR(TimeZone, Israel, "Israel"), PAIR(TimeZone, Jamaica, "Jamaica"), PAIR(TimeZone, Kwajalein, "Kwajalein"), PAIR(TimeZone, Libya, "Libya"), - PAIR(TimeZone, MET, "MET"), - PAIR(TimeZone, MST, "MST"), - PAIR(TimeZone, MST7MDT, "MST7MDT"), + PAIR(TimeZone, Met, "MET"), + PAIR(TimeZone, Mst, "MST"), + PAIR(TimeZone, Mst7Mdt, "MST7MDT"), PAIR(TimeZone, Navajo, "Navajo"), - PAIR(TimeZone, NZ, "NZ"), - PAIR(TimeZone, NZCHAT, "NZ-CHAT"), + PAIR(TimeZone, Nz, "NZ"), + PAIR(TimeZone, NzChat, "NZ-CHAT"), PAIR(TimeZone, Poland, "Poland"), PAIR(TimeZone, Portugal, "Portugal"), - PAIR(TimeZone, PRC, "PRC"), - PAIR(TimeZone, PST8PDT, "PST8PDT"), - PAIR(TimeZone, ROC, "ROC"), - PAIR(TimeZone, ROK, "ROK"), + PAIR(TimeZone, Prc, "PRC"), + PAIR(TimeZone, Pst8Pdt, "PST8PDT"), + PAIR(TimeZone, Roc, "ROC"), + PAIR(TimeZone, Rok, "ROK"), PAIR(TimeZone, Singapore, "Singapore"), PAIR(TimeZone, Turkey, "Turkey"), - PAIR(TimeZone, UCT, "UCT"), - PAIR(TimeZone, W_SU, "W-SU"), - PAIR(TimeZone, WET, "WET"), + PAIR(TimeZone, Uct, "UCT"), + PAIR(TimeZone, WSu, "W-SU"), + PAIR(TimeZone, Wet, "WET"), PAIR(TimeZone, Zulu, "Zulu"), }}); translations->insert({typeid(Settings::AudioMode), From 62ffaa730fabd2101947dd28e50fae6d03162aa4 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 00:13:06 -0400 Subject: [PATCH 108/155] shared_translation: Fix context usage Currently unused, but I don't want to start headaches when someone decides to use it the first time. --- src/yuzu/configuration/shared_translation.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index a75574530..a1030efb0 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -170,7 +170,9 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { std::unique_ptr ComboboxEnumeration(QWidget* parent) { std::unique_ptr translations = std::make_unique(); - const auto& tr = [&](const char* text) { return parent->tr(text); }; + const auto& tr = [&](const char* text, const char* context = "") { + return parent->tr(text, context); + }; #define PAIR(ENUM, VALUE, TRANSLATION) \ { static_cast(Settings::ENUM::VALUE), tr(TRANSLATION) } From ad645c29a44bd117cad90bda56e1f4d6296f2666 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 01:42:42 -0400 Subject: [PATCH 109/155] configuration: Use a builder to create widgets This gets rid of some repeated code and sets us up to send more information to the new widget. --- src/yuzu/configuration/configure_audio.cpp | 38 ++++++-------- src/yuzu/configuration/configure_audio.h | 18 +++---- src/yuzu/configuration/configure_cpu.cpp | 23 ++++----- src/yuzu/configuration/configure_cpu.h | 12 ++--- src/yuzu/configuration/configure_dialog.cpp | 23 ++++----- src/yuzu/configuration/configure_dialog.h | 4 +- src/yuzu/configuration/configure_general.cpp | 19 ++++--- src/yuzu/configuration/configure_general.h | 19 +++---- src/yuzu/configuration/configure_graphics.cpp | 32 +++++------- src/yuzu/configuration/configure_graphics.h | 23 +++++---- .../configure_graphics_advanced.cpp | 21 ++++---- .../configure_graphics_advanced.h | 13 ++--- src/yuzu/configuration/configure_per_game.cpp | 19 +++---- src/yuzu/configuration/configure_per_game.h | 4 +- src/yuzu/configuration/configure_system.cpp | 43 +++++++--------- src/yuzu/configuration/configure_system.h | 19 ++++--- src/yuzu/configuration/shared_widget.cpp | 35 ++++++++++--- src/yuzu/configuration/shared_widget.h | 50 +++++++++++-------- 18 files changed, 206 insertions(+), 209 deletions(-) diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 8c5378925..6db47fd61 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -16,23 +16,19 @@ #include "yuzu/configuration/shared_widget.h" #include "yuzu/uisettings.h" -ConfigureAudio::ConfigureAudio( - const Core::System& system_, - std::shared_ptr> group_, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : Tab(group_, parent), ui(std::make_unique()), system{system_}, - translations{translations_}, combobox_translations{combobox_translations_} { +ConfigureAudio::ConfigureAudio(const Core::System& system_, + std::shared_ptr> group_, + const ConfigurationShared::Builder& builder, QWidget* parent) + : Tab(group_, parent), ui(std::make_unique()), system{system_} { ui->setupUi(this); - Setup(); + Setup(builder); SetConfiguration(); } ConfigureAudio::~ConfigureAudio() = default; -void ConfigureAudio::Setup() { - const bool runtime_lock = !system.IsPoweredOn(); +void ConfigureAudio::Setup(const ConfigurationShared::Builder& builder) { auto& layout = *ui->audio_widget->layout(); std::forward_list settings; @@ -47,31 +43,27 @@ void ConfigureAudio::Setup() { push(Settings::Category::SystemAudio); for (auto* setting : settings) { - if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { - continue; - } - auto* widget = [&]() { if (setting->Id() == Settings::values.volume.Id()) { // volume needs to be a slider (default is line edit) - return new ConfigurationShared::Widget(setting, translations, combobox_translations, - this, runtime_lock, apply_funcs, nullptr, - ConfigurationShared::RequestType::Slider, - tr("%1%", "Volume percentage (e.g. 50%)")); + return builder.BuildWidget(setting, apply_funcs, nullptr, + ConfigurationShared::RequestType::Slider, + tr("%1%", "Volume percentage (e.g. 50%)")); } else if (setting->Id() == Settings::values.audio_output_device_id.Id() || setting->Id() == Settings::values.audio_input_device_id.Id() || setting->Id() == Settings::values.sink_id.Id()) { // These need to be unmanaged comboboxes, so we can populate them ourselves // TODO (lat9nq): Let it manage sink_id - return new ConfigurationShared::Widget( - setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::ComboBox, false); + return builder.BuildWidget(setting, apply_funcs, + ConfigurationShared::RequestType::ComboBox, false); } else { - return new ConfigurationShared::Widget(setting, translations, combobox_translations, - this, runtime_lock, apply_funcs); + return builder.BuildWidget(setting, apply_funcs); } }(); + if (widget == nullptr) { + continue; + } if (!widget->Valid()) { delete widget; continue; diff --git a/src/yuzu/configuration/configure_audio.h b/src/yuzu/configuration/configure_audio.h index 31cf682e0..94606f210 100644 --- a/src/yuzu/configuration/configure_audio.h +++ b/src/yuzu/configuration/configure_audio.h @@ -8,7 +8,6 @@ #include #include #include "yuzu/configuration/configuration_shared.h" -#include "yuzu/configuration/shared_translation.h" class QComboBox; @@ -20,14 +19,15 @@ namespace Ui { class ConfigureAudio; } +namespace ConfigurationShared { +class Builder; +} + class ConfigureAudio : public ConfigurationShared::Tab { public: - explicit ConfigureAudio( - const Core::System& system_, - std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, - QWidget* parent = nullptr); + explicit ConfigureAudio(const Core::System& system_, + std::shared_ptr> group, + const ConfigurationShared::Builder& builder, QWidget* parent = nullptr); ~ConfigureAudio() override; void ApplyConfiguration() override; @@ -45,13 +45,11 @@ private: void SetOutputSinkFromSinkID(); void SetAudioDevicesFromDeviceID(); - void Setup(); + void Setup(const ConfigurationShared::Builder& builder); std::unique_ptr ui; const Core::System& system; - const ConfigurationShared::TranslationMap& translations; - const ConfigurationShared::ComboboxTranslationMap& combobox_translations; std::forward_list> apply_funcs{}; diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 210af146d..57cdc4c63 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -13,16 +13,14 @@ #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_cpu.h" -ConfigureCpu::ConfigureCpu( - const Core::System& system_, - std::shared_ptr> group_, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) +ConfigureCpu::ConfigureCpu(const Core::System& system_, + std::shared_ptr> group_, + const ConfigurationShared::Builder& builder, QWidget* parent) : Tab(group_, parent), ui{std::make_unique()}, system{system_}, - translations{translations_}, combobox_translations{combobox_translations_} { + combobox_translations(builder.ComboboxTranslations()) { ui->setupUi(this); - Setup(); + Setup(builder); SetConfiguration(); @@ -33,8 +31,7 @@ ConfigureCpu::ConfigureCpu( ConfigureCpu::~ConfigureCpu() = default; void ConfigureCpu::SetConfiguration() {} -void ConfigureCpu::Setup() { - const bool runtime_lock = !system.IsPoweredOn(); +void ConfigureCpu::Setup(const ConfigurationShared::Builder& builder) { auto* accuracy_layout = ui->widget_accuracy->layout(); auto* unsafe_layout = ui->unsafe_widget->layout(); std::map unsafe_hold{}; @@ -50,13 +47,11 @@ void ConfigureCpu::Setup() { push(Settings::Category::CpuUnsafe); for (const auto setting : settings) { - if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { + auto* widget = builder.BuildWidget(setting, apply_funcs); + + if (widget == nullptr) { continue; } - - auto* widget = new ConfigurationShared::Widget(setting, translations, combobox_translations, - this, runtime_lock, apply_funcs); - if (!widget->Valid()) { delete widget; continue; diff --git a/src/yuzu/configuration/configure_cpu.h b/src/yuzu/configuration/configure_cpu.h index 57603e5c9..ab19c0ba1 100644 --- a/src/yuzu/configuration/configure_cpu.h +++ b/src/yuzu/configuration/configure_cpu.h @@ -18,13 +18,15 @@ namespace Ui { class ConfigureCpu; } +namespace ConfigurationShared { +class Builder; +} + class ConfigureCpu : public ConfigurationShared::Tab { public: explicit ConfigureCpu(const Core::System& system_, std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations, - QWidget* parent = nullptr); + const ConfigurationShared::Builder& builder, QWidget* parent = nullptr); ~ConfigureCpu() override; void ApplyConfiguration() override; @@ -36,15 +38,13 @@ private: void UpdateGroup(int index); - void Setup(); + void Setup(const ConfigurationShared::Builder& builder); std::unique_ptr ui; const Core::System& system; - const ConfigurationShared::TranslationMap& translations; const ConfigurationShared::ComboboxTranslationMap& combobox_translations; - std::forward_list> apply_funcs{}; QComboBox* accuracy_combobox; diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index c7d132fc8..183555acd 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -32,28 +32,23 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, std::vector& vk_device_records, Core::System& system_, bool enable_web_config) : QDialog(parent), ui{std::make_unique()}, - registry(registry_), system{system_}, - translations{ConfigurationShared::InitializeTranslations(this)}, - combobox_translations{ConfigurationShared::ComboboxEnumeration(this)}, - audio_tab{std::make_unique(system_, nullptr, *translations, - *combobox_translations, this)}, - cpu_tab{std::make_unique(system_, nullptr, *translations, - *combobox_translations, this)}, + registry(registry_), system{system_}, builder{std::make_unique( + this, !system_.IsPoweredOn())}, + audio_tab{std::make_unique(system_, nullptr, *builder, this)}, + cpu_tab{std::make_unique(system_, nullptr, *builder, this)}, debug_tab_tab{std::make_unique(system_, this)}, filesystem_tab{std::make_unique(this)}, - general_tab{std::make_unique(system_, nullptr, *translations, - *combobox_translations, this)}, - graphics_advanced_tab{std::make_unique( - system_, nullptr, *translations, *combobox_translations, this)}, + general_tab{std::make_unique(system_, nullptr, *builder, this)}, + graphics_advanced_tab{ + std::make_unique(system_, nullptr, *builder, this)}, graphics_tab{std::make_unique( system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, - nullptr, *translations, *combobox_translations, this)}, + nullptr, *builder, this)}, hotkeys_tab{std::make_unique(system_.HIDCore(), this)}, input_tab{std::make_unique(system_, this)}, network_tab{std::make_unique(system_, this)}, profile_tab{std::make_unique(system_, this)}, - system_tab{std::make_unique(system_, nullptr, *translations, - *combobox_translations, this)}, + system_tab{std::make_unique(system_, nullptr, *builder, this)}, ui_tab{std::make_unique(system_, this)}, web_tab{std::make_unique( this)} { Settings::SetConfiguringGlobal(true); diff --git a/src/yuzu/configuration/configure_dialog.h b/src/yuzu/configuration/configure_dialog.h index 931900b7d..1bfc9f9d0 100644 --- a/src/yuzu/configuration/configure_dialog.h +++ b/src/yuzu/configuration/configure_dialog.h @@ -7,6 +7,7 @@ #include #include #include +#include "configuration/shared_widget.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/shared_translation.h" #include "yuzu/vk_device_info.h" @@ -72,8 +73,7 @@ private: HotkeyRegistry& registry; Core::System& system; - std::unique_ptr translations; - std::unique_ptr combobox_translations; + std::unique_ptr builder; std::forward_list tab_group; std::unique_ptr audio_tab; diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index ca5b92bc0..54113543a 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -15,12 +15,12 @@ ConfigureGeneral::ConfigureGeneral( const Core::System& system_, std::shared_ptr> group_, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : Tab(group_, parent), ui{std::make_unique()}, system{system_}, - translations{translations_}, combobox_translations{combobox_translations_} { + const ConfigurationShared::Builder& builder, QWidget* parent) + : Tab(group_, parent), ui{std::make_unique()}, system{system_} { ui->setupUi(this); + Setup(builder); + SetConfiguration(); connect(ui->button_reset_defaults, &QPushButton::clicked, this, @@ -33,17 +33,20 @@ ConfigureGeneral::ConfigureGeneral( ConfigureGeneral::~ConfigureGeneral() = default; -void ConfigureGeneral::SetConfiguration() { - const bool runtime_lock = !system.IsPoweredOn(); +void ConfigureGeneral::SetConfiguration() {} + +void ConfigureGeneral::Setup(const ConfigurationShared::Builder& builder) { QLayout& layout = *ui->general_widget->layout(); std::map hold{}; for (const auto setting : UISettings::values.linkage.by_category[Settings::Category::UiGeneral]) { - auto* widget = new ConfigurationShared::Widget(setting, translations, combobox_translations, - this, runtime_lock, apply_funcs); + auto* widget = builder.BuildWidget(setting, apply_funcs); + if (widget == nullptr) { + continue; + } if (!widget->Valid()) { delete widget; continue; diff --git a/src/yuzu/configuration/configure_general.h b/src/yuzu/configuration/configure_general.h index 864dc3d2e..f8ed3f8ab 100644 --- a/src/yuzu/configuration/configure_general.h +++ b/src/yuzu/configuration/configure_general.h @@ -7,7 +7,6 @@ #include #include #include "yuzu/configuration/configuration_shared.h" -#include "yuzu/configuration/shared_widget.h" namespace Core { class System; @@ -20,14 +19,16 @@ namespace Ui { class ConfigureGeneral; } +namespace ConfigurationShared { +class Builder; +} + class ConfigureGeneral : public ConfigurationShared::Tab { public: - explicit ConfigureGeneral( - const Core::System& system_, - std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, - QWidget* parent = nullptr); + explicit ConfigureGeneral(const Core::System& system_, + std::shared_ptr> group, + const ConfigurationShared::Builder& builder, + QWidget* parent = nullptr); ~ConfigureGeneral() override; void SetResetCallback(std::function callback); @@ -36,6 +37,8 @@ public: void SetConfiguration() override; private: + void Setup(const ConfigurationShared::Builder& builder); + void changeEvent(QEvent* event) override; void RetranslateUI(); @@ -46,6 +49,4 @@ private: std::forward_list> apply_funcs{}; const Core::System& system; - const ConfigurationShared::TranslationMap& translations; - const ConfigurationShared::ComboboxTranslationMap& combobox_translations; }; diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 2f041cba6..18872fa69 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -81,18 +81,17 @@ ConfigureGraphics::ConfigureGraphics( const Core::System& system_, std::vector& records_, const std::function& expose_compute_option_, std::shared_ptr> group_, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) + const ConfigurationShared::Builder& builder, QWidget* parent) : ConfigurationShared::Tab(group_, parent), ui{std::make_unique()}, records{records_}, expose_compute_option{expose_compute_option_}, system{system_}, - translations{translations_}, combobox_translations{combobox_translations_}, + combobox_translations{builder.ComboboxTranslations()}, shader_mapping{combobox_translations.at(typeid(Settings::ShaderBackend))} { vulkan_device = Settings::values.vulkan_device.GetValue(); RetrieveVulkanDevices(); ui->setupUi(this); - Setup(); + Setup(builder); for (const auto& device : vulkan_devices) { vulkan_device_combobox->addItem(device); @@ -218,8 +217,7 @@ ConfigureGraphics::~ConfigureGraphics() = default; void ConfigureGraphics::SetConfiguration() {} -void ConfigureGraphics::Setup() { - const bool runtime_lock = !system.IsPoweredOn(); +void ConfigureGraphics::Setup(const ConfigurationShared::Builder& builder) { QLayout* api_layout = ui->api_widget->layout(); QWidget* api_grid_widget = new QWidget(this); QVBoxLayout* api_grid_layout = new QVBoxLayout(api_grid_widget); @@ -232,30 +230,26 @@ void ConfigureGraphics::Setup() { std::forward_list hold_api; for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { - if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { - continue; - } - ConfigurationShared::Widget* widget = [&]() { // Set managed to false on these and set up the comboboxes ourselves if (setting->Id() == Settings::values.vulkan_device.Id() || setting->Id() == Settings::values.shader_backend.Id() || setting->Id() == Settings::values.vsync_mode.Id()) { - return new ConfigurationShared::Widget( - setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::ComboBox, false); + return builder.BuildWidget(setting, apply_funcs, + ConfigurationShared::RequestType::ComboBox, false); } else if (setting->Id() == Settings::values.fsr_sharpening_slider.Id()) { // FSR needs a reversed slider - return new ConfigurationShared::Widget( - setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - ConfigurationShared::RequestType::ReverseSlider, true, 0.5f, nullptr, - tr("%1%", "FSR sharpening percentage (e.g. 50%)")); + return builder.BuildWidget( + setting, apply_funcs, ConfigurationShared::RequestType::ReverseSlider, true, + 0.5f, nullptr, tr("%1%", "FSR sharpening percentage (e.g. 50%)")); } else { - return new ConfigurationShared::Widget(setting, translations, combobox_translations, - this, runtime_lock, apply_funcs); + return builder.BuildWidget(setting, apply_funcs); } }(); + if (widget == nullptr) { + continue; + } if (!widget->Valid()) { delete widget; continue; diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index 718ba54f5..1848b1593 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -6,6 +6,7 @@ #include #include #include +#include #include #include #include @@ -13,9 +14,9 @@ #include #include #include "common/common_types.h" +#include "configuration/shared_translation.h" #include "vk_device_info.h" #include "yuzu/configuration/configuration_shared.h" -#include "yuzu/configuration/shared_translation.h" class QPushButton; class QEvent; @@ -36,15 +37,18 @@ namespace Ui { class ConfigureGraphics; } +namespace ConfigurationShared { +class Builder; +} + class ConfigureGraphics : public ConfigurationShared::Tab { public: - explicit ConfigureGraphics( - const Core::System& system_, std::vector& records, - const std::function& expose_compute_option_, - std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, - QWidget* parent = nullptr); + explicit ConfigureGraphics(const Core::System& system_, + std::vector& records, + const std::function& expose_compute_option_, + std::shared_ptr> group, + const ConfigurationShared::Builder& builder, + QWidget* parent = nullptr); ~ConfigureGraphics() override; void ApplyConfiguration() override; @@ -54,7 +58,7 @@ private: void changeEvent(QEvent* event) override; void RetranslateUI(); - void Setup(); + void Setup(const ConfigurationShared::Builder& builder); void PopulateVSyncModeSelection(); void UpdateBackgroundColorButton(QColor color); @@ -89,7 +93,6 @@ private: const std::function& expose_compute_option; const Core::System& system; - const ConfigurationShared::TranslationMap& translations; const ConfigurationShared::ComboboxTranslationMap& combobox_translations; const std::vector>& shader_mapping; diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index e2f7d284d..757e4659d 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -14,13 +14,13 @@ ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced( const Core::System& system_, std::shared_ptr> group_, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : Tab(group_, parent), ui{std::make_unique()}, system{system_}, - translations{translations_}, combobox_translations{combobox_translations_} { + const ConfigurationShared::Builder& builder, QWidget* parent) + : Tab(group_, parent), ui{std::make_unique()}, system{system_} { ui->setupUi(this); + Setup(builder); + SetConfiguration(); checkbox_enable_compute_pipelines->setVisible(false); @@ -28,20 +28,19 @@ ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced( ConfigureGraphicsAdvanced::~ConfigureGraphicsAdvanced() = default; -void ConfigureGraphicsAdvanced::SetConfiguration() { - const bool runtime_lock = !system.IsPoweredOn(); +void ConfigureGraphicsAdvanced::SetConfiguration() {} + +void ConfigureGraphicsAdvanced::Setup(const ConfigurationShared::Builder& builder) { auto& layout = *ui->populate_target->layout(); std::map hold{}; // A map will sort the data for us for (auto setting : Settings::values.linkage.by_category[Settings::Category::RendererAdvanced]) { - if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { + ConfigurationShared::Widget* widget = builder.BuildWidget(setting, apply_funcs); + + if (widget == nullptr) { continue; } - - ConfigurationShared::Widget* widget = new ConfigurationShared::Widget( - setting, translations, combobox_translations, this, runtime_lock, apply_funcs); - if (!widget->Valid()) { delete widget; continue; diff --git a/src/yuzu/configuration/configure_graphics_advanced.h b/src/yuzu/configuration/configure_graphics_advanced.h index 90b79f786..5530827d1 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.h +++ b/src/yuzu/configuration/configure_graphics_advanced.h @@ -6,7 +6,6 @@ #include #include #include "yuzu/configuration/configuration_shared.h" -#include "yuzu/configuration/shared_translation.h" namespace Core { class System; @@ -16,14 +15,16 @@ namespace Ui { class ConfigureGraphicsAdvanced; } +namespace ConfigurationShared { +class Builder; +} + class ConfigureGraphicsAdvanced : public ConfigurationShared::Tab { public: explicit ConfigureGraphicsAdvanced( const Core::System& system_, std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, - QWidget* parent = nullptr); + const ConfigurationShared::Builder& builder, QWidget* parent = nullptr); ~ConfigureGraphicsAdvanced() override; void ApplyConfiguration() override; @@ -32,14 +33,14 @@ public: void ExposeComputeOption(); private: + void Setup(const ConfigurationShared::Builder& builder); void changeEvent(QEvent* event) override; void RetranslateUI(); std::unique_ptr ui; const Core::System& system; - const ConfigurationShared::TranslationMap& translations; - const ConfigurationShared::ComboboxTranslationMap& combobox_translations; + std::forward_list> apply_funcs; QWidget* checkbox_enable_compute_pipelines{}; diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index 5863beca0..cee8e726d 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -17,6 +17,7 @@ #include #include "common/fs/fs_util.h" +#include "configuration/shared_widget.h" #include "core/core.h" #include "core/file_sys/control_metadata.h" #include "core/file_sys/patch_manager.h" @@ -42,8 +43,7 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st Core::System& system_) : QDialog(parent), ui(std::make_unique()), title_id{title_id_}, system{system_}, - translations{ConfigurationShared::InitializeTranslations(this)}, - combobox_translations{ConfigurationShared::ComboboxEnumeration(this)}, + builder{std::make_unique(this, !system_.IsPoweredOn())}, tab_group{std::make_shared>()} { const auto file_path = std::filesystem::path(Common::FS::ToU8String(file_name)); const auto config_file_name = title_id == 0 ? Common::FS::PathToUTF8String(file_path.filename()) @@ -51,18 +51,15 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st game_config = std::make_unique(config_file_name, Config::ConfigType::PerGameConfig); addons_tab = std::make_unique(system_, this); - audio_tab = std::make_unique(system_, tab_group, *translations, - *combobox_translations, this); - cpu_tab = std::make_unique(system_, tab_group, *translations, - *combobox_translations, this); - graphics_advanced_tab = std::make_unique( - system_, tab_group, *translations, *combobox_translations, this); + audio_tab = std::make_unique(system_, tab_group, *builder, this); + cpu_tab = std::make_unique(system_, tab_group, *builder, this); + graphics_advanced_tab = + std::make_unique(system_, tab_group, *builder, this); graphics_tab = std::make_unique( system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, - tab_group, *translations, *combobox_translations, this); + tab_group, *builder, this); input_tab = std::make_unique(system_, game_config.get(), this); - system_tab = std::make_unique(system_, tab_group, *translations, - *combobox_translations, this); + system_tab = std::make_unique(system_, tab_group, *builder, this); ui->setupUi(this); diff --git a/src/yuzu/configuration/configure_per_game.h b/src/yuzu/configuration/configure_per_game.h index 4849ac291..4ddd18c1f 100644 --- a/src/yuzu/configuration/configure_per_game.h +++ b/src/yuzu/configuration/configure_per_game.h @@ -11,6 +11,7 @@ #include #include +#include "configuration/shared_widget.h" #include "core/file_sys/vfs_types.h" #include "vk_device_info.h" #include "yuzu/configuration/config.h" @@ -75,8 +76,7 @@ private: std::unique_ptr game_config; Core::System& system; - std::unique_ptr translations; - std::unique_ptr combobox_translations; + std::unique_ptr builder; std::shared_ptr> tab_group; std::unique_ptr addons_tab; diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 6a985c515..9be09244a 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -46,13 +46,11 @@ static bool IsValidLocale(u32 region_index, u32 language_index) { ConfigureSystem::ConfigureSystem( Core::System& system_, std::shared_ptr> group_, - const ConfigurationShared::TranslationMap& translations_, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations_, QWidget* parent) - : Tab(group_, parent), ui{std::make_unique()}, system{system_}, - translations{translations_}, combobox_translations{combobox_translations_} { + const ConfigurationShared::Builder& builder, QWidget* parent) + : Tab(group_, parent), ui{std::make_unique()}, system{system_} { ui->setupUi(this); - Setup(); + Setup(builder); connect(rng_seed_checkbox, &QCheckBox::stateChanged, this, [this](int state) { rng_seed_edit->setEnabled(state == Qt::Checked); @@ -104,8 +102,7 @@ void ConfigureSystem::RetranslateUI() { ui->retranslateUi(this); } -void ConfigureSystem::Setup() { - const bool runtime_lock = !system.IsPoweredOn(); +void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { auto& core_layout = *ui->core_widget->layout(); auto& system_layout = *ui->system_widget->layout(); @@ -123,37 +120,31 @@ void ConfigureSystem::Setup() { push(Settings::values.linkage.by_category[Settings::Category::System]); for (auto setting : settings) { - if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { - continue; - } - - [[maybe_unused]] std::string label = setting->GetLabel(); - ConfigurationShared::Widget* widget = [this, setting, runtime_lock]() { + ConfigurationShared::Widget* widget = [this, setting, &builder]() { if (setting->Id() == Settings::values.custom_rtc.Id()) { // custom_rtc needs a DateTimeEdit (default is LineEdit), and a checkbox to manage // it and custom_rtc_enabled - return new ConfigurationShared::Widget( - setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - &Settings::values.custom_rtc_enabled, - ConfigurationShared::RequestType::DateTimeEdit); + return builder.BuildWidget(setting, apply_funcs, + &Settings::values.custom_rtc_enabled, + ConfigurationShared::RequestType::DateTimeEdit); } else if (setting->Id() == Settings::values.rng_seed.Id()) { // rng_seed needs a HexEdit (default is LineEdit), and a checkbox to manage // it and rng_seed_enabled - return new ConfigurationShared::Widget( - setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - &Settings::values.rng_seed_enabled, ConfigurationShared::RequestType::HexEdit); + return builder.BuildWidget(setting, apply_funcs, &Settings::values.rng_seed_enabled, + ConfigurationShared::RequestType::HexEdit); } else if (setting->Id() == Settings::values.speed_limit.Id()) { // speed_limit needs a checkbox to set use_speed_limit, as well as a spinbox - return new ConfigurationShared::Widget( - setting, translations, combobox_translations, this, runtime_lock, apply_funcs, - &Settings::values.use_speed_limit, ConfigurationShared::RequestType::SpinBox, - tr("%", "Limit speed percentage (e.g. 50%)")); + return builder.BuildWidget(setting, apply_funcs, &Settings::values.use_speed_limit, + ConfigurationShared::RequestType::SpinBox, + tr("%", "Limit speed percentage (e.g. 50%)")); } else { - return new ConfigurationShared::Widget(setting, translations, combobox_translations, - this, runtime_lock, apply_funcs); + return builder.BuildWidget(setting, apply_funcs); } }(); + if (widget == nullptr) { + continue; + } if (!widget->Valid()) { delete widget; continue; diff --git a/src/yuzu/configuration/configure_system.h b/src/yuzu/configuration/configure_system.h index 4457ccc21..7f4259698 100644 --- a/src/yuzu/configuration/configure_system.h +++ b/src/yuzu/configuration/configure_system.h @@ -9,13 +9,11 @@ #include #include "yuzu/configuration/configuration_shared.h" -#include "yuzu/configuration/shared_translation.h" class QCheckBox; class QLineEdit; class QComboBox; class QDateTimeEdit; - namespace Core { class System; } @@ -24,13 +22,16 @@ namespace Ui { class ConfigureSystem; } +namespace ConfigurationShared { +class Builder; +} + class ConfigureSystem : public ConfigurationShared::Tab { public: - explicit ConfigureSystem( - Core::System& system_, std::shared_ptr> group, - const ConfigurationShared::TranslationMap& translations, - const ConfigurationShared::ComboboxTranslationMap& combobox_translations, - QWidget* parent = nullptr); + explicit ConfigureSystem(Core::System& system_, + std::shared_ptr> group, + const ConfigurationShared::Builder& builder, + QWidget* parent = nullptr); ~ConfigureSystem() override; void ApplyConfiguration() override; @@ -40,7 +41,7 @@ private: void changeEvent(QEvent* event) override; void RetranslateUI(); - void Setup(); + void Setup(const ConfigurationShared::Builder& builder); std::forward_list> apply_funcs{}; @@ -48,8 +49,6 @@ private: bool enabled = false; Core::System& system; - const ConfigurationShared::TranslationMap& translations; - const ConfigurationShared::ComboboxTranslationMap& combobox_translations; QCheckBox* rng_seed_checkbox; QLineEdit* rng_seed_edit; diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index d153d8d6b..dc8b31238 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -529,11 +529,34 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati this->setToolTip(tooltip); } -Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, - const ComboboxTranslationMap& combobox_translations, QWidget* parent_, - bool runtime_lock_, std::forward_list>& apply_funcs_, - Settings::BasicSetting* other_setting, RequestType request, const QString& string) - : Widget(setting_, translations_, combobox_translations, parent_, runtime_lock_, apply_funcs_, - request, true, 1.0f, other_setting, string) {} +Builder::Builder(QWidget* parent_, bool runtime_lock_) + : translations{InitializeTranslations(parent_)}, + combobox_translations{ComboboxEnumeration(parent_)}, parent{parent_}, runtime_lock{ + runtime_lock_} {} + +Builder::~Builder() = default; + +Widget* Builder::BuildWidget(Settings::BasicSetting* setting, + std::forward_list>& apply_funcs, + RequestType request, bool managed, float multiplier, + Settings::BasicSetting* other_setting, const QString& string) const { + if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { + return nullptr; + } + + return new Widget(setting, *translations, *combobox_translations, parent, runtime_lock, + apply_funcs, request, managed, multiplier, other_setting, string); +} + +Widget* Builder::BuildWidget(Settings::BasicSetting* setting, + std::forward_list>& apply_funcs, + Settings::BasicSetting* other_setting, RequestType request, + const QString& string) const { + return BuildWidget(setting, apply_funcs, request, true, 1.0f, other_setting, string); +} + +const ComboboxTranslationMap& Builder::ComboboxTranslations() const { + return *combobox_translations; +} } // namespace ConfigurationShared diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index 10d2d353e..e8c281b81 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -5,6 +5,7 @@ #include #include +#include #include #include #include @@ -44,28 +45,6 @@ class Widget : public QWidget { Q_OBJECT public: - /** - * Shorter-hand version of the constructor - * - * @param setting The primary Setting to create the Widget for - * @param translations Map of translations to display on the left side label/checkbox - * @param combobox_translations Map of translations for enumerating combo boxes - * @param parent Qt parent - * @param runtime_lock Emulated guest powered on state, for use on settings that should be - * configured during guest execution - * @param apply_funcs_ List to append, functions to run to apply the widget state to the setting - * @param other_setting Second setting to modify, to replace the label with a checkbox - * @param request What type of data representation component to create -- not always respected - * for the Setting data type - * @param string Set to specify formats for Slider feedback labels or SpinBox - */ - explicit Widget(Settings::BasicSetting* setting, const TranslationMap& translations, - const ComboboxTranslationMap& combobox_translations, QWidget* parent, - bool runtime_lock, std::forward_list>& apply_funcs_, - Settings::BasicSetting* other_setting, - RequestType request = RequestType::Default, - const QString& string = QStringLiteral("")); - /** * @param setting The primary Setting to create the Widget for * @param translations Map of translations to display on the left side label/checkbox @@ -152,4 +131,31 @@ private: bool runtime_lock{false}; }; +class Builder { +public: + explicit Builder(QWidget* parent, bool runtime_lock); + ~Builder(); + + Widget* BuildWidget(Settings::BasicSetting* setting, + std::forward_list>& apply_funcs, + RequestType request = RequestType::Default, bool managed = true, + float multiplier = 1.0f, Settings::BasicSetting* other_setting = nullptr, + const QString& string = QStringLiteral("")) const; + + Widget* BuildWidget(Settings::BasicSetting* setting, + std::forward_list>& apply_funcs, + Settings::BasicSetting* other_setting, + RequestType request = RequestType::Default, + const QString& string = QStringLiteral("")) const; + + const ComboboxTranslationMap& ComboboxTranslations() const; + +private: + std::unique_ptr translations; + std::unique_ptr combobox_translations; + + QWidget* parent; + const bool runtime_lock; +}; + } // namespace ConfigurationShared From b2438f1fb7d083ffe8c8afdc30e9c612631d6ace Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 03:23:36 -0400 Subject: [PATCH 110/155] settings: Define specializations for settings Suggests to a frontend how to represent each setting. --- src/common/settings.h | 136 +++++++++++++++++++++------------ src/common/settings_common.cpp | 11 ++- src/common/settings_common.h | 20 ++++- src/common/settings_setting.h | 27 ++++--- 4 files changed, 130 insertions(+), 64 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 0ae71dd1b..c78dd85c8 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -128,25 +128,31 @@ struct Values { Linkage linkage{}; // Audio - Setting sink_id{linkage, AudioEngine::Auto, "output_engine", Category::Audio}; - Setting audio_output_device_id{linkage, "auto", "output_device", Category::Audio}; - Setting audio_input_device_id{linkage, "auto", "input_device", Category::Audio}; + Setting sink_id{linkage, AudioEngine::Auto, "output_engine", Category::Audio, + Specialization::RuntimeList}; + Setting audio_output_device_id{linkage, "auto", "output_device", Category::Audio, + Specialization::RuntimeList}; + Setting audio_input_device_id{linkage, "auto", "input_device", Category::Audio, + Specialization::RuntimeList}; SwitchableSetting sound_index{linkage, AudioMode::Stereo, AudioMode::Mono, AudioMode::Surround, "sound_index", Category::SystemAudio}; - SwitchableSetting volume{linkage, 100, 0, 200, "volume", Category::Audio, true, true}; - Setting audio_muted{linkage, false, "audio_muted", Category::Audio, false}; - Setting dump_audio_commands{linkage, false, "dump_audio_commands", Category::Audio, - false}; + SwitchableSetting volume{ + linkage, 100, 0, 200, "volume", Category::Audio, Specialization::Scalar, true, true}; + Setting audio_muted{ + linkage, false, "audio_muted", Category::Audio, Specialization::Default, false}; + Setting dump_audio_commands{ + linkage, false, "dump_audio_commands", Category::Audio, Specialization::Default, false}; // Core SwitchableSetting use_multi_core{linkage, true, "use_multi_core", Category::Core}; SwitchableSetting use_unsafe_extended_memory_layout{ linkage, false, "use_unsafe_extended_memory_layout", Category::Core}; - SwitchableSetting use_speed_limit{linkage, true, "use_speed_limit", - Category::Core, false, true}; - SwitchableSetting speed_limit{linkage, 100, 0, 9999, "speed_limit", - Category::Core, true, true}; + SwitchableSetting use_speed_limit{ + linkage, true, "use_speed_limit", Category::Core, Specialization::Paired, false, true}; + SwitchableSetting speed_limit{ + linkage, 100, 0, 9999, "speed_limit", Category::Core, Specialization::Countable, + true, true}; // Cpu SwitchableSetting cpu_accuracy{linkage, CpuAccuracy::Auto, @@ -192,9 +198,10 @@ struct Values { linkage, RendererBackend::Vulkan, RendererBackend::OpenGL, RendererBackend::Null, "backend", Category::Renderer}; SwitchableSetting shader_backend{ - linkage, ShaderBackend::Glsl, ShaderBackend::Glsl, ShaderBackend::SpirV, - "shader_backend", Category::Renderer}; - SwitchableSetting vulkan_device{linkage, 0, "vulkan_device", Category::Renderer}; + linkage, ShaderBackend::Glsl, ShaderBackend::Glsl, ShaderBackend::SpirV, + "shader_backend", Category::Renderer, Specialization::RuntimeList}; + SwitchableSetting vulkan_device{linkage, 0, "vulkan_device", Category::Renderer, + Specialization::RuntimeList}; SwitchableSetting use_disk_shader_cache{linkage, true, "use_disk_shader_cache", Category::Renderer}; @@ -206,14 +213,10 @@ struct Values { AstcDecodeMode::CpuAsynchronous, "accelerate_astc", Category::Renderer}; - Setting vsync_mode{linkage, - VSyncMode::Fifo, - VSyncMode::Immediate, - VSyncMode::FifoRelaxed, - "use_vsync", - Category::Renderer, - true, - true}; + Setting vsync_mode{ + linkage, VSyncMode::Fifo, VSyncMode::Immediate, VSyncMode::FifoRelaxed, + "use_vsync", Category::Renderer, Specialization::RuntimeList, true, + true}; SwitchableSetting nvdec_emulation{linkage, NvdecEmulation::Gpu, "nvdec_emulation", Category::Renderer}; // *nix platforms may have issues with the borderless windowed fullscreen mode. @@ -228,6 +231,7 @@ struct Values { FullscreenMode::Exclusive, "fullscreen_mode", Category::Renderer, + Specialization::Default, true, true}; SwitchableSetting aspect_ratio{linkage, @@ -236,22 +240,37 @@ struct Values { AspectRatio::Stretch, "aspect_ratio", Category::Renderer, + Specialization::Default, true, true}; ResolutionScalingInfo resolution_info{}; SwitchableSetting resolution_setup{linkage, ResolutionSetup::Res1X, "resolution_setup", Category::Renderer}; - SwitchableSetting scaling_filter{ - linkage, ScalingFilter::Bilinear, "scaling_filter", Category::Renderer, true, true}; - SwitchableSetting anti_aliasing{ - linkage, AntiAliasing::None, "anti_aliasing", Category::Renderer, true, true}; + SwitchableSetting scaling_filter{linkage, + ScalingFilter::Bilinear, + "scaling_filter", + Category::Renderer, + Specialization::Default, + true, + true}; + SwitchableSetting anti_aliasing{linkage, + AntiAliasing::None, + "anti_aliasing", + Category::Renderer, + Specialization::Default, + true, + true}; SwitchableSetting fsr_sharpening_slider{ - linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer, true, true}; + linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer, Specialization::Scalar, + true, true}; - SwitchableSetting bg_red{linkage, 0, "bg_red", Category::Renderer, true, true}; - SwitchableSetting bg_green{linkage, 0, "bg_green", Category::Renderer, true, true}; - SwitchableSetting bg_blue{linkage, 0, "bg_blue", Category::Renderer, true, true}; + SwitchableSetting bg_red{ + linkage, 0, "bg_red", Category::Renderer, Specialization::Default, true, true}; + SwitchableSetting bg_green{ + linkage, 0, "bg_green", Category::Renderer, Specialization::Default, true, true}; + SwitchableSetting bg_blue{ + linkage, 0, "bg_blue", Category::Renderer, Specialization::Default, true, true}; SwitchableSetting gpu_accuracy{linkage, GpuAccuracy::High, @@ -259,6 +278,7 @@ struct Values { GpuAccuracy::Extreme, "gpu_accuracy", Category::RendererAdvanced, + Specialization::Default, true, true}; SwitchableSetting max_anisotropy{ @@ -279,9 +299,15 @@ struct Values { SwitchableSetting use_asynchronous_shaders{linkage, false, "use_asynchronous_shaders", Category::RendererAdvanced}; SwitchableSetting use_fast_gpu_time{ - linkage, true, "use_fast_gpu_time", Category::RendererAdvanced, true, true}; - SwitchableSetting use_vulkan_driver_pipeline_cache{ - linkage, true, "use_vulkan_driver_pipeline_cache", Category::RendererAdvanced, true, true}; + linkage, true, "use_fast_gpu_time", Category::RendererAdvanced, Specialization::Default, + true, true}; + SwitchableSetting use_vulkan_driver_pipeline_cache{linkage, + true, + "use_vulkan_driver_pipeline_cache", + Category::RendererAdvanced, + Specialization::Default, + true, + true}; SwitchableSetting enable_compute_pipelines{linkage, false, "enable_compute_pipelines", Category::RendererAdvanced}; SwitchableSetting use_video_framerate{linkage, false, "use_video_framerate", @@ -310,15 +336,18 @@ struct Values { TimeZone::Auto, TimeZone::Zulu, "time_zone_index", Category::System}; // Measured in seconds since epoch - SwitchableSetting custom_rtc_enabled{linkage, false, "custom_rtc_enabled", - Category::System, true, true}; - SwitchableSetting custom_rtc{linkage, 0, "custom_rtc", Category::System, true, true}; + SwitchableSetting custom_rtc_enabled{ + linkage, false, "custom_rtc_enabled", Category::System, Specialization::Paired, true, true}; + SwitchableSetting custom_rtc{ + linkage, 0, "custom_rtc", Category::System, Specialization::Time, true, true}; // Set on game boot, reset on stop. Seconds difference between current time and `custom_rtc` s64 custom_rtc_differential; - SwitchableSetting rng_seed_enabled{linkage, false, "rng_seed_enabled", - Category::System, true, true}; - SwitchableSetting rng_seed{linkage, 0, "rng_seed", Category::System, true, true}; - Setting device_name{linkage, "yuzu", "device_name", Category::System, true, true}; + SwitchableSetting rng_seed_enabled{ + linkage, false, "rng_seed_enabled", Category::System, Specialization::Paired, true, true}; + SwitchableSetting rng_seed{linkage, 0, "rng_seed", Category::System, Specialization::Hex, + true, true}; + Setting device_name{ + linkage, "yuzu", "device_name", Category::System, Specialization::Default, true, true}; Setting current_user{linkage, 0, "current_user", Category::System}; @@ -327,12 +356,13 @@ struct Values { // Controls InputSetting> players; - Setting enable_raw_input{linkage, false, "enable_raw_input", Category::Controls, + Setting enable_raw_input{ + linkage, false, "enable_raw_input", Category::Controls, Specialization::Default, // Only read/write enable_raw_input on Windows platforms #ifdef _WIN32 - true + true #else - false + false #endif }; Setting controller_navigation{linkage, true, "controller_navigation", Category::Controls}; @@ -354,7 +384,8 @@ struct Values { Setting tas_enable{linkage, false, "tas_enable", Category::Controls}; Setting tas_loop{linkage, false, "tas_loop", Category::Controls}; - Setting mouse_panning{linkage, false, "mouse_panning", Category::Controls, false}; + Setting mouse_panning{ + linkage, false, "mouse_panning", Category::Controls, Specialization::Default, false}; Setting mouse_panning_sensitivity{ linkage, 50, 1, 100, "mouse_panning_sensitivity", Category::Controls}; Setting mouse_enabled{linkage, false, "mouse_enabled", Category::Controls}; @@ -410,19 +441,24 @@ struct Values { Setting program_args{linkage, std::string(), "program_args", Category::Debugging}; Setting dump_exefs{linkage, false, "dump_exefs", Category::Debugging}; Setting dump_nso{linkage, false, "dump_nso", Category::Debugging}; - Setting dump_shaders{linkage, false, "dump_shaders", Category::DebuggingGraphics, false}; - Setting dump_macros{linkage, false, "dump_macros", Category::DebuggingGraphics, false}; + Setting dump_shaders{ + linkage, false, "dump_shaders", Category::DebuggingGraphics, Specialization::Default, + false}; + Setting dump_macros{ + linkage, false, "dump_macros", Category::DebuggingGraphics, Specialization::Default, false}; Setting enable_fs_access_log{linkage, false, "enable_fs_access_log", Category::Debugging}; - Setting reporting_services{linkage, false, "reporting_services", Category::Debugging, - false}; + Setting reporting_services{ + linkage, false, "reporting_services", Category::Debugging, Specialization::Default, false}; Setting quest_flag{linkage, false, "quest_flag", Category::Debugging}; Setting disable_macro_jit{linkage, false, "disable_macro_jit", Category::DebuggingGraphics}; Setting disable_macro_hle{linkage, false, "disable_macro_hle", Category::DebuggingGraphics}; - Setting extended_logging{linkage, false, "extended_logging", Category::Debugging, false}; + Setting extended_logging{ + linkage, false, "extended_logging", Category::Debugging, Specialization::Default, false}; Setting use_debug_asserts{linkage, false, "use_debug_asserts", Category::Debugging}; - Setting use_auto_stub{linkage, false, "use_auto_stub", Category::Debugging, false}; + Setting use_auto_stub{ + linkage, false, "use_auto_stub", Category::Debugging, Specialization::Default, false}; Setting enable_all_controllers{linkage, false, "enable_all_controllers", Category::Debugging}; Setting create_crash_dumps{linkage, false, "create_crash_dumps", Category::Debugging}; diff --git a/src/common/settings_common.cpp b/src/common/settings_common.cpp index fb42991fa..3e86c7347 100644 --- a/src/common/settings_common.cpp +++ b/src/common/settings_common.cpp @@ -7,9 +7,10 @@ namespace Settings { BasicSetting::BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, - bool save_, bool runtime_modifiable_) - : label{name}, category{category_}, id{linkage.count}, save{save_}, runtime_modifiable{ - runtime_modifiable_} { + bool save_, bool runtime_modifiable_, + enum Specialization specialization_) + : label{name}, category{category_}, id{linkage.count}, save{save_}, + runtime_modifiable{runtime_modifiable_}, specialization{specialization_} { linkage.by_category[category].push_front(this); linkage.count++; } @@ -38,6 +39,10 @@ Category BasicSetting::Category() const { return category; } +Specialization BasicSetting::Specialization() const { + return specialization; +} + const std::string& BasicSetting::GetLabel() const { return label; } diff --git a/src/common/settings_common.h b/src/common/settings_common.h index 2b5c72f41..664c807f1 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -43,6 +43,17 @@ enum class Category : u32 { MaxEnum, }; +enum class Specialization : u32 { + Default, + Time, + Hex, + List, + RuntimeList, + Scalar, + Countable, + Paired, +}; + bool IsConfiguringGlobal(); void SetConfiguringGlobal(bool is_global); @@ -64,7 +75,7 @@ public: class BasicSetting { protected: explicit BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, - bool save_, bool runtime_modifiable_); + bool save_, bool runtime_modifiable_, Specialization spec); public: virtual ~BasicSetting(); @@ -180,6 +191,11 @@ public: */ [[nodiscard]] enum Category Category() const; + /** + * @returns Extra metadata for data representation in frontend implementations. + */ + [[nodiscard]] enum Specialization Specialization() const; + /** * Returns the label this setting was created with. * @@ -219,6 +235,8 @@ private: const bool save; ///< Suggests if the setting should be saved and read to a frontend config const bool runtime_modifiable; ///< Suggests if the setting can be modified while a guest is running + const enum Specialization + specialization; ///< Extra data to identify representation of a setting }; } // namespace Settings diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index a0a05da54..9805a5b5d 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -35,10 +35,12 @@ public: * @param category_ Category of the setting AKA INI group */ explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, - enum Category category_, bool save_ = true, bool runtime_modifiable_ = false) + enum Category category_, + enum Specialization specialization = Specialization::Default, + bool save_ = true, bool runtime_modifiable_ = false) requires(!ranged) - : BasicSetting(linkage, name, category_, save_, runtime_modifiable_), value{default_val}, - default_value{default_val} {} + : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization), + value{default_val}, default_value{default_val} {} virtual ~Setting() = default; /** @@ -53,10 +55,11 @@ public: */ explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, enum Category category_, + enum Specialization specialization = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false) requires(ranged) - : BasicSetting(linkage, name, category_, save_, runtime_modifiable_), value{default_val}, - default_value{default_val}, maximum{max_val}, minimum{min_val} {} + : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization), + value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val} {} /** * Returns a reference to the setting's value. @@ -230,10 +233,12 @@ public: * @param category_ Category of the setting AKA INI group */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, - Category category_, bool save_ = true, - bool runtime_modifiable_ = false) + Category category_, + enum Specialization specialization = Specialization::Default, + bool save_ = true, bool runtime_modifiable_ = false) requires(!ranged) - : Setting{linkage, default_val, name, category_, save_, runtime_modifiable_} { + : Setting{linkage, default_val, name, category_, specialization, + save_, runtime_modifiable_} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } virtual ~SwitchableSetting() = default; @@ -250,10 +255,12 @@ public: */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, Category category_, + enum Specialization specialization = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false) requires(ranged) - : Setting{linkage, default_val, min_val, max_val, - name, category_, save_, runtime_modifiable_} { + : Setting{linkage, default_val, min_val, + max_val, name, category_, + specialization, save_, runtime_modifiable_} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } From 21723879e7631b2d81d3c3ff14f93c834bc1cdd8 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 03:29:20 -0400 Subject: [PATCH 111/155] configuration: Use specialization of settings Reduces some ugliness in frontend code. --- src/yuzu/configuration/configure_audio.cpp | 8 +---- src/yuzu/configuration/configure_graphics.cpp | 8 +---- src/yuzu/configuration/configure_system.cpp | 7 ++--- src/yuzu/configuration/shared_widget.cpp | 31 +++++++++++++++++++ 4 files changed, 36 insertions(+), 18 deletions(-) diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 6db47fd61..cdb89ccda 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -44,18 +44,12 @@ void ConfigureAudio::Setup(const ConfigurationShared::Builder& builder) { for (auto* setting : settings) { auto* widget = [&]() { + // TODO (lat9nq): Let the system manage sink_id if (setting->Id() == Settings::values.volume.Id()) { // volume needs to be a slider (default is line edit) return builder.BuildWidget(setting, apply_funcs, nullptr, ConfigurationShared::RequestType::Slider, tr("%1%", "Volume percentage (e.g. 50%)")); - } else if (setting->Id() == Settings::values.audio_output_device_id.Id() || - setting->Id() == Settings::values.audio_input_device_id.Id() || - setting->Id() == Settings::values.sink_id.Id()) { - // These need to be unmanaged comboboxes, so we can populate them ourselves - // TODO (lat9nq): Let it manage sink_id - return builder.BuildWidget(setting, apply_funcs, - ConfigurationShared::RequestType::ComboBox, false); } else { return builder.BuildWidget(setting, apply_funcs); } diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 18872fa69..74449e6d4 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -231,13 +231,7 @@ void ConfigureGraphics::Setup(const ConfigurationShared::Builder& builder) { for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { ConfigurationShared::Widget* widget = [&]() { - // Set managed to false on these and set up the comboboxes ourselves - if (setting->Id() == Settings::values.vulkan_device.Id() || - setting->Id() == Settings::values.shader_backend.Id() || - setting->Id() == Settings::values.vsync_mode.Id()) { - return builder.BuildWidget(setting, apply_funcs, - ConfigurationShared::RequestType::ComboBox, false); - } else if (setting->Id() == Settings::values.fsr_sharpening_slider.Id()) { + if (setting->Id() == Settings::values.fsr_sharpening_slider.Id()) { // FSR needs a reversed slider return builder.BuildWidget( setting, apply_funcs, ConfigurationShared::RequestType::ReverseSlider, true, diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 9be09244a..796ebc44f 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -125,13 +125,12 @@ void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { // custom_rtc needs a DateTimeEdit (default is LineEdit), and a checkbox to manage // it and custom_rtc_enabled return builder.BuildWidget(setting, apply_funcs, - &Settings::values.custom_rtc_enabled, - ConfigurationShared::RequestType::DateTimeEdit); + &Settings::values.custom_rtc_enabled); } else if (setting->Id() == Settings::values.rng_seed.Id()) { // rng_seed needs a HexEdit (default is LineEdit), and a checkbox to manage // it and rng_seed_enabled - return builder.BuildWidget(setting, apply_funcs, &Settings::values.rng_seed_enabled, - ConfigurationShared::RequestType::HexEdit); + return builder.BuildWidget(setting, apply_funcs, + &Settings::values.rng_seed_enabled); } else if (setting->Id() == Settings::values.speed_limit.Id()) { // speed_limit needs a checkbox to set use_speed_limit, as well as a spinbox return builder.BuildWidget(setting, apply_funcs, &Settings::values.use_speed_limit, diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index dc8b31238..807d1d668 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -376,6 +376,32 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu layout->addWidget(qt_label); } + request = [&]() { + if (request != RequestType::Default) { + return request; + } + switch (setting.Specialization()) { + case Settings::Specialization::Default: + return RequestType::Default; + case Settings::Specialization::Time: + return RequestType::DateTimeEdit; + case Settings::Specialization::Hex: + return RequestType::HexEdit; + case Settings::Specialization::RuntimeList: + managed = false; + [[fallthrough]]; + case Settings::Specialization::List: + return RequestType::ComboBox; + case Settings::Specialization::Scalar: + return RequestType::Slider; + case Settings::Specialization::Countable: + return RequestType::SpinBox; + default: + break; + } + return request; + }(); + if (setting.TypeId() == typeid(bool)) { data_component = CreateCheckBox(&setting, label, serializer, restore_func, touch); } else if (setting.IsEnum()) { @@ -544,6 +570,11 @@ Widget* Builder::BuildWidget(Settings::BasicSetting* setting, return nullptr; } + if (setting->Specialization() == Settings::Specialization::Paired) { + LOG_DEBUG(Frontend, "\"{}\" has specialization Paired: ignoring", setting->GetLabel()); + return nullptr; + } + return new Widget(setting, *translations, *combobox_translations, parent, runtime_lock, apply_funcs, request, managed, multiplier, other_setting, string); } From d1de1c3bedcd2526eb78c7eaa21f2eef6041a590 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 04:04:48 -0400 Subject: [PATCH 112/155] shared_widget: Internalize component restoring --- src/yuzu/configuration/configure_system.cpp | 28 +------- src/yuzu/configuration/configure_system.h | 4 -- src/yuzu/configuration/shared_widget.cpp | 80 +++++++++++++-------- 3 files changed, 50 insertions(+), 62 deletions(-) diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 796ebc44f..ef26fb6ce 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -52,20 +52,6 @@ ConfigureSystem::ConfigureSystem( Setup(builder); - connect(rng_seed_checkbox, &QCheckBox::stateChanged, this, [this](int state) { - rng_seed_edit->setEnabled(state == Qt::Checked); - if (state != Qt::Checked) { - rng_seed_edit->setText(QStringLiteral("00000000")); - } - }); - - connect(custom_rtc_checkbox, &QCheckBox::stateChanged, this, [this](int state) { - custom_rtc_edit->setEnabled(state == Qt::Checked); - if (state != Qt::Checked) { - custom_rtc_edit->setDateTime(QDateTime::currentDateTime()); - } - }); - const auto locale_check = [this]() { const auto region_index = combo_region->currentIndex(); const auto language_index = combo_language->currentIndex(); @@ -149,19 +135,7 @@ void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { continue; } - if (setting->Id() == Settings::values.rng_seed.Id()) { - // Keep track of rng_seed's widgets to reset it with the checkbox state - rng_seed_checkbox = widget->checkbox; - rng_seed_edit = widget->line_edit; - - rng_seed_edit->setEnabled(Settings::values.rng_seed_enabled.GetValue()); - } else if (setting->Id() == Settings::values.custom_rtc.Id()) { - // Keep track of custom_rtc's widgets to reset it with the checkbox state - custom_rtc_checkbox = widget->checkbox; - custom_rtc_edit = widget->date_time_edit; - - custom_rtc_edit->setEnabled(Settings::values.custom_rtc_enabled.GetValue()); - } else if (setting->Id() == Settings::values.region_index.Id()) { + if (setting->Id() == Settings::values.region_index.Id()) { // Keep track of the region_index (and langauge_index) combobox to validate the selected // settings combo_region = widget->combobox; diff --git a/src/yuzu/configuration/configure_system.h b/src/yuzu/configuration/configure_system.h index 7f4259698..f63aedda0 100644 --- a/src/yuzu/configuration/configure_system.h +++ b/src/yuzu/configuration/configure_system.h @@ -50,10 +50,6 @@ private: Core::System& system; - QCheckBox* rng_seed_checkbox; - QLineEdit* rng_seed_edit; - QCheckBox* custom_rtc_checkbox; - QDateTimeEdit* custom_rtc_edit; QComboBox* combo_region; QComboBox* combo_language; }; diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 807d1d668..7670475be 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -46,6 +46,10 @@ namespace ConfigurationShared { static int restore_button_count = 0; +static std::string RelevantDefault(const Settings::BasicSetting& setting) { + return Settings::IsConfiguringGlobal() ? setting.DefaultToString() : setting.ToStringGlobal(); +} + QPushButton* Widget::CreateRestoreGlobalButton(bool using_global, QWidget* parent) { restore_button_count++; @@ -92,12 +96,12 @@ QWidget* Widget::CreateCheckBox(Settings::BasicSetting* bool_setting, const QStr return checkbox->checkState() == Qt::CheckState::Checked ? "true" : "false"; }; - if (!Settings::IsConfiguringGlobal()) { - restore_func = [this, bool_setting]() { - checkbox->setCheckState(bool_setting->ToStringGlobal() == "true" ? Qt::Checked - : Qt::Unchecked); - }; + restore_func = [this, bool_setting]() { + checkbox->setCheckState(RelevantDefault(*bool_setting) == "true" ? Qt::Checked + : Qt::Unchecked); + }; + if (!Settings::IsConfiguringGlobal()) { QObject::connect(checkbox, &QCheckBox::clicked, [touch]() { touch(); }); } @@ -139,12 +143,12 @@ QWidget* Widget::CreateCombobox(std::function& serializer, return std::to_string(enumeration->at(current).first); }; - if (!Settings::IsConfiguringGlobal()) { - restore_func = [this, find_index]() { - const u32 global_value = std::stoi(setting.ToStringGlobal()); - combobox->setCurrentIndex(find_index(global_value)); - }; + restore_func = [this, find_index]() { + const u32 global_value = std::stoi(RelevantDefault(setting)); + combobox->setCurrentIndex(find_index(global_value)); + }; + if (!Settings::IsConfiguringGlobal()) { QObject::connect(combobox, QOverload::of(&QComboBox::activated), [touch]() { touch(); }); } @@ -165,11 +169,11 @@ QWidget* Widget::CreateLineEdit(std::function& serializer, return line_edit; } - if (!Settings::IsConfiguringGlobal()) { - restore_func = [this]() { - line_edit->setText(QString::fromStdString(setting.ToStringGlobal())); - }; + restore_func = [this]() { + line_edit->setText(QString::fromStdString(RelevantDefault(setting))); + }; + if (!Settings::IsConfiguringGlobal()) { QObject::connect(line_edit, &QLineEdit::textChanged, [touch]() { touch(); }); } @@ -215,10 +219,9 @@ QWidget* Widget::CreateSlider(bool reversed, float multiplier, const QString& fo slider->setInvertedAppearance(reversed); serializer = [this]() { return std::to_string(slider->value()); }; + restore_func = [this]() { slider->setValue(std::stoi(RelevantDefault(setting))); }; if (!Settings::IsConfiguringGlobal()) { - restore_func = [this]() { slider->setValue(std::stoi(setting.ToStringGlobal())); }; - QObject::connect(slider, &QAbstractSlider::actionTriggered, [touch]() { touch(); }); } @@ -242,9 +245,12 @@ QWidget* Widget::CreateSpinBox(const QString& suffix, std::functionvalue()); }; - if (!Settings::IsConfiguringGlobal()) { - restore_func = [this]() { spinbox->setValue(std::stoi(setting.ToStringGlobal())); }; + restore_func = [this]() { + auto value{std::stol(RelevantDefault(setting))}; + spinbox->setValue(value); + }; + if (!Settings::IsConfiguringGlobal()) { QObject::connect(spinbox, QOverload::of(&QSpinBox::valueChanged), [this, touch]() { if (spinbox->value() != std::stoi(setting.ToStringGlobal())) { touch(); @@ -264,7 +270,7 @@ QWidget* Widget::CreateHexEdit(std::function& serializer, } auto to_hex = [=](const std::string& input) { - return QString::fromStdString(fmt::format("{:08x}", std::stoi(input))); + return QString::fromStdString(fmt::format("{:08x}", std::stoul(input))); }; QRegExpValidator* regex = @@ -282,8 +288,9 @@ QWidget* Widget::CreateHexEdit(std::function& serializer, serializer = [hex_to_dec]() { return hex_to_dec(); }; + restore_func = [this, to_hex]() { line_edit->setText(to_hex(RelevantDefault(setting))); }; + if (!Settings::IsConfiguringGlobal()) { - restore_func = [this, to_hex]() { line_edit->setText(to_hex(setting.ToStringGlobal())); }; QObject::connect(line_edit, &QLineEdit::textChanged, [touch]() { touch(); }); } @@ -306,18 +313,18 @@ QWidget* Widget::CreateDateTimeEdit(bool disabled, bool restrict, serializer = [this]() { return std::to_string(date_time_edit->dateTime().toSecsSinceEpoch()); }; + auto get_clear_val = [this, restrict, current_time]() { + return QDateTime::fromSecsSinceEpoch([this, restrict, current_time]() { + if (restrict && checkbox->checkState() == Qt::Checked) { + return std::stoll(RelevantDefault(setting)); + } + return current_time; + }()); + }; + + restore_func = [this, get_clear_val]() { date_time_edit->setDateTime(get_clear_val()); }; + if (!Settings::IsConfiguringGlobal()) { - auto get_clear_val = [this, restrict, current_time]() { - return QDateTime::fromSecsSinceEpoch([this, restrict, current_time]() { - if (restrict && checkbox->checkState() == Qt::Checked) { - return std::stoll(setting.ToStringGlobal()); - } - return current_time; - }()); - }; - - restore_func = [this, get_clear_val]() { date_time_edit->setDateTime(get_clear_val()); }; - QObject::connect(date_time_edit, &QDateTimeEdit::editingFinished, [this, get_clear_val, touch]() { if (date_time_edit->dateTime() != get_clear_val()) { @@ -493,6 +500,17 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu } }; } + + if (other_setting != nullptr) { + const auto reset = [restore_func, data_component](int state) { + data_component->setEnabled(state == Qt::Checked); + if (state != Qt::Checked) { + restore_func(); + } + }; + connect(checkbox, &QCheckBox::stateChanged, reset); + reset(checkbox->checkState()); + } } bool Widget::Valid() const { From 7f708e8d77fb6237407f49246622dbe1b445d536 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 04:32:13 -0400 Subject: [PATCH 113/155] settings: Define paired settings settings_common: Remove unused optional --- src/common/settings.h | 21 +++++++++++++++------ src/common/settings_common.cpp | 9 +++++++-- src/common/settings_common.h | 11 +++++++++-- src/common/settings_setting.h | 29 ++++++++++++++++++----------- 4 files changed, 49 insertions(+), 21 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index c78dd85c8..b87301d4e 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -150,9 +150,16 @@ struct Values { linkage, false, "use_unsafe_extended_memory_layout", Category::Core}; SwitchableSetting use_speed_limit{ linkage, true, "use_speed_limit", Category::Core, Specialization::Paired, false, true}; - SwitchableSetting speed_limit{ - linkage, 100, 0, 9999, "speed_limit", Category::Core, Specialization::Countable, - true, true}; + SwitchableSetting speed_limit{linkage, + 100, + 0, + 9999, + "speed_limit", + Category::Core, + Specialization::Countable, + true, + true, + &use_speed_limit}; // Cpu SwitchableSetting cpu_accuracy{linkage, CpuAccuracy::Auto, @@ -339,13 +346,15 @@ struct Values { SwitchableSetting custom_rtc_enabled{ linkage, false, "custom_rtc_enabled", Category::System, Specialization::Paired, true, true}; SwitchableSetting custom_rtc{ - linkage, 0, "custom_rtc", Category::System, Specialization::Time, true, true}; + linkage, 0, "custom_rtc", Category::System, Specialization::Time, + true, true, &custom_rtc_enabled}; // Set on game boot, reset on stop. Seconds difference between current time and `custom_rtc` s64 custom_rtc_differential; SwitchableSetting rng_seed_enabled{ linkage, false, "rng_seed_enabled", Category::System, Specialization::Paired, true, true}; - SwitchableSetting rng_seed{linkage, 0, "rng_seed", Category::System, Specialization::Hex, - true, true}; + SwitchableSetting rng_seed{ + linkage, 0, "rng_seed", Category::System, Specialization::Hex, + true, true, &rng_seed_enabled}; Setting device_name{ linkage, "yuzu", "device_name", Category::System, Specialization::Default, true, true}; diff --git a/src/common/settings_common.cpp b/src/common/settings_common.cpp index 3e86c7347..53d4548f5 100644 --- a/src/common/settings_common.cpp +++ b/src/common/settings_common.cpp @@ -8,9 +8,10 @@ namespace Settings { BasicSetting::BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, bool save_, bool runtime_modifiable_, - enum Specialization specialization_) + enum Specialization specialization_, BasicSetting* other_setting_) : label{name}, category{category_}, id{linkage.count}, save{save_}, - runtime_modifiable{runtime_modifiable_}, specialization{specialization_} { + runtime_modifiable{runtime_modifiable_}, specialization{specialization_}, + other_setting{other_setting_} { linkage.by_category[category].push_front(this); linkage.count++; } @@ -43,6 +44,10 @@ Specialization BasicSetting::Specialization() const { return specialization; } +BasicSetting* BasicSetting::PairedSetting() const { + return other_setting; +} + const std::string& BasicSetting::GetLabel() const { return label; } diff --git a/src/common/settings_common.h b/src/common/settings_common.h index 664c807f1..ad005ca4e 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -75,7 +75,8 @@ public: class BasicSetting { protected: explicit BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, - bool save_, bool runtime_modifiable_, Specialization spec); + bool save_, bool runtime_modifiable_, Specialization spec, + BasicSetting* other_setting); public: virtual ~BasicSetting(); @@ -196,6 +197,11 @@ public: */ [[nodiscard]] enum Specialization Specialization() const; + /** + * @returns Another BasicSetting if one is paired, or nullptr otherwise. + */ + [[nodiscard]] BasicSetting* PairedSetting() const; + /** * Returns the label this setting was created with. * @@ -236,7 +242,8 @@ private: const bool runtime_modifiable; ///< Suggests if the setting can be modified while a guest is running const enum Specialization - specialization; ///< Extra data to identify representation of a setting + specialization; ///< Extra data to identify representation of a setting + BasicSetting* const other_setting; ///< A paired setting }; } // namespace Settings diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index 9805a5b5d..dd91250a1 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -37,9 +37,11 @@ public: explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, enum Category category_, enum Specialization specialization = Specialization::Default, - bool save_ = true, bool runtime_modifiable_ = false) + bool save_ = true, bool runtime_modifiable_ = false, + BasicSetting* other_setting = nullptr) requires(!ranged) - : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization), + : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization, + other_setting), value{default_val}, default_value{default_val} {} virtual ~Setting() = default; @@ -56,9 +58,11 @@ public: explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, enum Category category_, enum Specialization specialization = Specialization::Default, - bool save_ = true, bool runtime_modifiable_ = false) + bool save_ = true, bool runtime_modifiable_ = false, + BasicSetting* other_setting = nullptr) requires(ranged) - : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization), + : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization, + other_setting), value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val} {} /** @@ -235,10 +239,12 @@ public: explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, Category category_, enum Specialization specialization = Specialization::Default, - bool save_ = true, bool runtime_modifiable_ = false) + bool save_ = true, bool runtime_modifiable_ = false, + BasicSetting* other_setting = nullptr) requires(!ranged) - : Setting{linkage, default_val, name, category_, specialization, - save_, runtime_modifiable_} { + : Setting{ + linkage, default_val, name, category_, specialization, + save_, runtime_modifiable_, other_setting} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } virtual ~SwitchableSetting() = default; @@ -256,11 +262,12 @@ public: explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, Category category_, enum Specialization specialization = Specialization::Default, - bool save_ = true, bool runtime_modifiable_ = false) + bool save_ = true, bool runtime_modifiable_ = false, + BasicSetting* other_setting = nullptr) requires(ranged) - : Setting{linkage, default_val, min_val, - max_val, name, category_, - specialization, save_, runtime_modifiable_} { + : Setting{ + linkage, default_val, min_val, max_val, name, category_, specialization, + save_, runtime_modifiable_, other_setting} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } From 9de50d6194027bf4d757ef58f291763eacea6bfe Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 04:32:21 -0400 Subject: [PATCH 114/155] configuration: Use paired settings --- src/yuzu/configuration/configure_system.cpp | 14 ++------------ src/yuzu/configuration/shared_widget.cpp | 4 ++++ 2 files changed, 6 insertions(+), 12 deletions(-) diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index ef26fb6ce..cb708051e 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -107,18 +107,8 @@ void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { for (auto setting : settings) { ConfigurationShared::Widget* widget = [this, setting, &builder]() { - if (setting->Id() == Settings::values.custom_rtc.Id()) { - // custom_rtc needs a DateTimeEdit (default is LineEdit), and a checkbox to manage - // it and custom_rtc_enabled - return builder.BuildWidget(setting, apply_funcs, - &Settings::values.custom_rtc_enabled); - } else if (setting->Id() == Settings::values.rng_seed.Id()) { - // rng_seed needs a HexEdit (default is LineEdit), and a checkbox to manage - // it and rng_seed_enabled - return builder.BuildWidget(setting, apply_funcs, - &Settings::values.rng_seed_enabled); - } else if (setting->Id() == Settings::values.speed_limit.Id()) { - // speed_limit needs a checkbox to set use_speed_limit, as well as a spinbox + if (setting->Id() == Settings::values.speed_limit.Id()) { + // speed_limit must be specified to translate the percentage return builder.BuildWidget(setting, apply_funcs, &Settings::values.use_speed_limit, ConfigurationShared::RequestType::SpinBox, tr("%", "Limit speed percentage (e.g. 50%)")); diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 7670475be..bbcee7488 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -345,6 +345,10 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu QLayout* layout = new QHBoxLayout(this); layout->setContentsMargins(0, 0, 0, 0); + if (other_setting == nullptr) { + other_setting = setting.PairedSetting(); + } + const bool require_checkbox = other_setting != nullptr && other_setting->TypeId() == typeid(bool); From 926f3e3d3e6ff57633d2d44085f02754ffe1c988 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 05:04:21 -0400 Subject: [PATCH 115/155] settings,configuration: Add a default suffix --- src/common/settings.h | 26 +++++++--- src/common/settings_common.cpp | 6 +-- src/common/settings_common.h | 33 +++++++------ src/common/settings_setting.h | 15 +++--- src/yuzu/configuration/configure_audio.cpp | 13 +---- src/yuzu/configuration/configure_graphics.cpp | 4 +- src/yuzu/configuration/configure_system.cpp | 11 +---- src/yuzu/configuration/shared_widget.cpp | 47 ++++++++++++++----- src/yuzu/configuration/shared_widget.h | 12 ++--- 9 files changed, 93 insertions(+), 74 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index b87301d4e..c4339cb1f 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -137,8 +137,15 @@ struct Values { SwitchableSetting sound_index{linkage, AudioMode::Stereo, AudioMode::Mono, AudioMode::Surround, "sound_index", Category::SystemAudio}; - SwitchableSetting volume{ - linkage, 100, 0, 200, "volume", Category::Audio, Specialization::Scalar, true, true}; + SwitchableSetting volume{linkage, + 100, + 0, + 200, + "volume", + Category::Audio, + Specialization::Scalar | Specialization::Percentage, + true, + true}; Setting audio_muted{ linkage, false, "audio_muted", Category::Audio, Specialization::Default, false}; Setting dump_audio_commands{ @@ -156,7 +163,7 @@ struct Values { 9999, "speed_limit", Category::Core, - Specialization::Countable, + Specialization::Countable | Specialization::Percentage, true, true, &use_speed_limit}; @@ -268,9 +275,16 @@ struct Values { Specialization::Default, true, true}; - SwitchableSetting fsr_sharpening_slider{ - linkage, 25, 0, 200, "fsr_sharpening_slider", Category::Renderer, Specialization::Scalar, - true, true}; + SwitchableSetting fsr_sharpening_slider{linkage, + 25, + 0, + 200, + "fsr_sharpening_slider", + Category::Renderer, + Specialization::Scalar | + Specialization::Percentage, + true, + true}; SwitchableSetting bg_red{ linkage, 0, "bg_red", Category::Renderer, Specialization::Default, true, true}; diff --git a/src/common/settings_common.cpp b/src/common/settings_common.cpp index 53d4548f5..799942980 100644 --- a/src/common/settings_common.cpp +++ b/src/common/settings_common.cpp @@ -7,8 +7,8 @@ namespace Settings { BasicSetting::BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, - bool save_, bool runtime_modifiable_, - enum Specialization specialization_, BasicSetting* other_setting_) + bool save_, bool runtime_modifiable_, u32 specialization_, + BasicSetting* other_setting_) : label{name}, category{category_}, id{linkage.count}, save{save_}, runtime_modifiable{runtime_modifiable_}, specialization{specialization_}, other_setting{other_setting_} { @@ -40,7 +40,7 @@ Category BasicSetting::Category() const { return category; } -Specialization BasicSetting::Specialization() const { +u32 BasicSetting::Specialization() const { return specialization; } diff --git a/src/common/settings_common.h b/src/common/settings_common.h index ad005ca4e..6b717deb1 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -43,15 +43,21 @@ enum class Category : u32 { MaxEnum, }; -enum class Specialization : u32 { - Default, - Time, - Hex, - List, - RuntimeList, - Scalar, - Countable, - Paired, +constexpr u8 SpecializationTypeMask = 0xf; +constexpr u8 SpecializationAttributeMask = 0xf0; +constexpr u8 SpecializationAttributeOffset = 4; + +enum Specialization : u8 { + Default = 0, + Time = 1, + Hex = 2, + List = 3, + RuntimeList = 4, + Scalar = 5, + Countable = 6, + Paired = 7, + + Percentage = (1 << SpecializationAttributeOffset), }; bool IsConfiguringGlobal(); @@ -75,7 +81,7 @@ public: class BasicSetting { protected: explicit BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, - bool save_, bool runtime_modifiable_, Specialization spec, + bool save_, bool runtime_modifiable_, u32 specialization, BasicSetting* other_setting); public: @@ -195,7 +201,7 @@ public: /** * @returns Extra metadata for data representation in frontend implementations. */ - [[nodiscard]] enum Specialization Specialization() const; + [[nodiscard]] u32 Specialization() const; /** * @returns Another BasicSetting if one is paired, or nullptr otherwise. @@ -240,9 +246,8 @@ private: const u32 id; ///< Unique integer for the setting const bool save; ///< Suggests if the setting should be saved and read to a frontend config const bool - runtime_modifiable; ///< Suggests if the setting can be modified while a guest is running - const enum Specialization - specialization; ///< Extra data to identify representation of a setting + runtime_modifiable; ///< Suggests if the setting can be modified while a guest is running + const u32 specialization; ///< Extra data to identify representation of a setting BasicSetting* const other_setting; ///< A paired setting }; diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index dd91250a1..d1915cb43 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -35,8 +35,7 @@ public: * @param category_ Category of the setting AKA INI group */ explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, - enum Category category_, - enum Specialization specialization = Specialization::Default, + enum Category category_, u32 specialization = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, BasicSetting* other_setting = nullptr) requires(!ranged) @@ -57,9 +56,8 @@ public: */ explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, enum Category category_, - enum Specialization specialization = Specialization::Default, - bool save_ = true, bool runtime_modifiable_ = false, - BasicSetting* other_setting = nullptr) + u32 specialization = Specialization::Default, bool save_ = true, + bool runtime_modifiable_ = false, BasicSetting* other_setting = nullptr) requires(ranged) : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization, other_setting), @@ -237,8 +235,7 @@ public: * @param category_ Category of the setting AKA INI group */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, - Category category_, - enum Specialization specialization = Specialization::Default, + Category category_, u32 specialization = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, BasicSetting* other_setting = nullptr) requires(!ranged) @@ -261,8 +258,8 @@ public: */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, Category category_, - enum Specialization specialization = Specialization::Default, - bool save_ = true, bool runtime_modifiable_ = false, + u32 specialization = Specialization::Default, bool save_ = true, + bool runtime_modifiable_ = false, BasicSetting* other_setting = nullptr) requires(ranged) : Setting{ diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index cdb89ccda..11714b86d 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -43,17 +43,7 @@ void ConfigureAudio::Setup(const ConfigurationShared::Builder& builder) { push(Settings::Category::SystemAudio); for (auto* setting : settings) { - auto* widget = [&]() { - // TODO (lat9nq): Let the system manage sink_id - if (setting->Id() == Settings::values.volume.Id()) { - // volume needs to be a slider (default is line edit) - return builder.BuildWidget(setting, apply_funcs, nullptr, - ConfigurationShared::RequestType::Slider, - tr("%1%", "Volume percentage (e.g. 50%)")); - } else { - return builder.BuildWidget(setting, apply_funcs); - } - }(); + auto* widget = builder.BuildWidget(setting, apply_funcs); if (widget == nullptr) { continue; @@ -66,6 +56,7 @@ void ConfigureAudio::Setup(const ConfigurationShared::Builder& builder) { layout.addWidget(widget); if (setting->Id() == Settings::values.sink_id.Id()) { + // TODO (lat9nq): Let the system manage sink_id sink_combo_box = widget->combobox; InitializeAudioSinkComboBox(); diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 74449e6d4..7263af13f 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -232,10 +232,10 @@ void ConfigureGraphics::Setup(const ConfigurationShared::Builder& builder) { for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { ConfigurationShared::Widget* widget = [&]() { if (setting->Id() == Settings::values.fsr_sharpening_slider.Id()) { - // FSR needs a reversed slider + // FSR needs a reversed slider and a 0.5 multiplier return builder.BuildWidget( setting, apply_funcs, ConfigurationShared::RequestType::ReverseSlider, true, - 0.5f, nullptr, tr("%1%", "FSR sharpening percentage (e.g. 50%)")); + 0.5f, nullptr, tr("%", "FSR sharpening percentage (e.g. 50%)")); } else { return builder.BuildWidget(setting, apply_funcs); } diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index cb708051e..05706c4de 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -106,16 +106,7 @@ void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { push(Settings::values.linkage.by_category[Settings::Category::System]); for (auto setting : settings) { - ConfigurationShared::Widget* widget = [this, setting, &builder]() { - if (setting->Id() == Settings::values.speed_limit.Id()) { - // speed_limit must be specified to translate the percentage - return builder.BuildWidget(setting, apply_funcs, &Settings::values.use_speed_limit, - ConfigurationShared::RequestType::SpinBox, - tr("%", "Limit speed percentage (e.g. 50%)")); - } else { - return builder.BuildWidget(setting, apply_funcs); - } - }(); + ConfigurationShared::Widget* widget = builder.BuildWidget(setting, apply_funcs); if (widget == nullptr) { continue; diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index bbcee7488..978bfa590 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -50,6 +50,20 @@ static std::string RelevantDefault(const Settings::BasicSetting& setting) { return Settings::IsConfiguringGlobal() ? setting.DefaultToString() : setting.ToStringGlobal(); } +static QString DefaultSuffix(QWidget* parent, Settings::BasicSetting& setting) { + const auto tr = [parent](const char* text, const char* context) { + return parent->tr(text, context); + }; + + if ((setting.Specialization() & Settings::SpecializationAttributeMask) == + Settings::Specialization::Percentage) { + std::string context{fmt::format("{} percentage (e.g. 50%)", setting.GetLabel())}; + return tr("%", context.c_str()); + } + + return QStringLiteral(""); +} + QPushButton* Widget::CreateRestoreGlobalButton(bool using_global, QWidget* parent) { restore_button_count++; @@ -180,7 +194,7 @@ QWidget* Widget::CreateLineEdit(std::function& serializer, return line_edit; } -QWidget* Widget::CreateSlider(bool reversed, float multiplier, const QString& format, +QWidget* Widget::CreateSlider(bool reversed, float multiplier, const QString& given_suffix, std::function& serializer, std::function& restore_func, const std::function& touch) { @@ -205,7 +219,10 @@ QWidget* Widget::CreateSlider(bool reversed, float multiplier, const QString& fo int max_val = std::stoi(setting.MaxVal()); - const QString use_format = format == QStringLiteral("") ? QStringLiteral("%1") : format; + QString suffix = + given_suffix == QStringLiteral("") ? DefaultSuffix(this, setting) : given_suffix; + + const QString use_format = QStringLiteral("%1").append(suffix); QObject::connect(slider, &QAbstractSlider::valueChanged, [=](int value) { int present = (reversed ? max_val - value : value) * multiplier + 0.5f; @@ -228,7 +245,8 @@ QWidget* Widget::CreateSlider(bool reversed, float multiplier, const QString& fo return container; } -QWidget* Widget::CreateSpinBox(const QString& suffix, std::function& serializer, +QWidget* Widget::CreateSpinBox(const QString& given_suffix, + std::function& serializer, std::function& restore_func, const std::function& touch) { const int min_val = @@ -237,6 +255,9 @@ QWidget* Widget::CreateSpinBox(const QString& suffix, std::function::max(); const int default_val = std::stoi(setting.ToString()); + QString suffix = + given_suffix == QStringLiteral("") ? DefaultSuffix(this, setting) : given_suffix; + spinbox = new QSpinBox(this); spinbox->setRange(min_val, max_val); spinbox->setValue(default_val); @@ -338,7 +359,7 @@ QWidget* Widget::CreateDateTimeEdit(bool disabled, bool restrict, void Widget::SetupComponent(const QString& label, std::function& load_func, bool managed, RequestType request, float multiplier, - Settings::BasicSetting* other_setting, const QString& string) { + Settings::BasicSetting* other_setting, const QString& suffix) { created = true; const auto type = setting.TypeId(); @@ -391,7 +412,7 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu if (request != RequestType::Default) { return request; } - switch (setting.Specialization()) { + switch (setting.Specialization() & Settings::SpecializationTypeMask) { case Settings::Specialization::Default: return RequestType::Default; case Settings::Specialization::Time: @@ -422,7 +443,7 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu switch (request) { case RequestType::Slider: case RequestType::ReverseSlider: - data_component = CreateSlider(request == RequestType::ReverseSlider, multiplier, string, + data_component = CreateSlider(request == RequestType::ReverseSlider, multiplier, suffix, serializer, restore_func, touch); break; case RequestType::Default: @@ -434,7 +455,7 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu serializer, restore_func, touch); break; case RequestType::SpinBox: - data_component = CreateSpinBox(string, serializer, restore_func, touch); + data_component = CreateSpinBox(suffix, serializer, restore_func, touch); break; case RequestType::HexEdit: data_component = CreateHexEdit(serializer, restore_func, touch); @@ -527,7 +548,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati const ComboboxTranslationMap& combobox_translations_, QWidget* parent_, bool runtime_lock_, std::forward_list>& apply_funcs_, RequestType request, bool managed, float multiplier, - Settings::BasicSetting* other_setting, const QString& string) + Settings::BasicSetting* other_setting, const QString& suffix) : QWidget(parent_), parent{parent_}, translations{translations_}, combobox_enumerations{combobox_translations_}, setting{*setting_}, apply_funcs{apply_funcs_}, runtime_lock{runtime_lock_} { @@ -555,7 +576,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati std::function load_func = []() {}; - SetupComponent(label, load_func, managed, request, multiplier, other_setting, string); + SetupComponent(label, load_func, managed, request, multiplier, other_setting, suffix); if (!created) { LOG_WARNING(Frontend, "No widget was created for \"{}\"", setting.GetLabel()); @@ -587,7 +608,7 @@ Builder::~Builder() = default; Widget* Builder::BuildWidget(Settings::BasicSetting* setting, std::forward_list>& apply_funcs, RequestType request, bool managed, float multiplier, - Settings::BasicSetting* other_setting, const QString& string) const { + Settings::BasicSetting* other_setting, const QString& suffix) const { if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { return nullptr; } @@ -598,14 +619,14 @@ Widget* Builder::BuildWidget(Settings::BasicSetting* setting, } return new Widget(setting, *translations, *combobox_translations, parent, runtime_lock, - apply_funcs, request, managed, multiplier, other_setting, string); + apply_funcs, request, managed, multiplier, other_setting, suffix); } Widget* Builder::BuildWidget(Settings::BasicSetting* setting, std::forward_list>& apply_funcs, Settings::BasicSetting* other_setting, RequestType request, - const QString& string) const { - return BuildWidget(setting, apply_funcs, request, true, 1.0f, other_setting, string); + const QString& suffix) const { + return BuildWidget(setting, apply_funcs, request, true, 1.0f, other_setting, suffix); } const ComboboxTranslationMap& Builder::ComboboxTranslations() const { diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index e8c281b81..b3f9efd78 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -58,14 +58,14 @@ public: * @param managed Set true if the caller will set up component data and handling * @param multiplier Value to multiply the slider feedback label * @param other_setting Second setting to modify, to replace the label with a checkbox - * @param string Set to specify formats for Slider feedback labels or SpinBox + * @param suffix Set to specify formats for Slider feedback labels or SpinBox */ explicit Widget(Settings::BasicSetting* setting, const TranslationMap& translations, const ComboboxTranslationMap& combobox_translations, QWidget* parent, bool runtime_lock, std::forward_list>& apply_funcs_, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, Settings::BasicSetting* other_setting = nullptr, - const QString& string = QStringLiteral("")); + const QString& suffix = QStringLiteral("")); virtual ~Widget(); /** @@ -95,7 +95,7 @@ public: private: void SetupComponent(const QString& label, std::function& load_func, bool managed, RequestType request, float multiplier, - Settings::BasicSetting* other_setting, const QString& string); + Settings::BasicSetting* other_setting, const QString& suffix); QLabel* CreateLabel(const QString& text); QWidget* CreateCheckBox(Settings::BasicSetting* bool_setting, const QString& label, @@ -111,7 +111,7 @@ private: bool managed = true); QWidget* CreateHexEdit(std::function& serializer, std::function& restore_func, const std::function& touch); - QWidget* CreateSlider(bool reversed, float multiplier, const QString& format, + QWidget* CreateSlider(bool reversed, float multiplier, const QString& suffix, std::function& serializer, std::function& restore_func, const std::function& touch); QWidget* CreateDateTimeEdit(bool disabled, bool restrict, @@ -140,13 +140,13 @@ public: std::forward_list>& apply_funcs, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, Settings::BasicSetting* other_setting = nullptr, - const QString& string = QStringLiteral("")) const; + const QString& suffix = QStringLiteral("")) const; Widget* BuildWidget(Settings::BasicSetting* setting, std::forward_list>& apply_funcs, Settings::BasicSetting* other_setting, RequestType request = RequestType::Default, - const QString& string = QStringLiteral("")) const; + const QString& suffix = QStringLiteral("")) const; const ComboboxTranslationMap& ComboboxTranslations() const; From 54d58130a0818efc4d70d72624f734f2b6f0a6d3 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 15:38:30 -0400 Subject: [PATCH 116/155] settings_setting: Silence shadowing warnings --- src/common/settings_setting.h | 35 ++++++++++++++++++----------------- 1 file changed, 18 insertions(+), 17 deletions(-) diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index d1915cb43..eb46b2b6d 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -35,12 +35,12 @@ public: * @param category_ Category of the setting AKA INI group */ explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, - enum Category category_, u32 specialization = Specialization::Default, + enum Category category_, u32 specialization_ = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, - BasicSetting* other_setting = nullptr) + BasicSetting* other_setting_ = nullptr) requires(!ranged) - : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization, - other_setting), + : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization_, + other_setting_), value{default_val}, default_value{default_val} {} virtual ~Setting() = default; @@ -56,11 +56,11 @@ public: */ explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, enum Category category_, - u32 specialization = Specialization::Default, bool save_ = true, - bool runtime_modifiable_ = false, BasicSetting* other_setting = nullptr) + u32 specialization_ = Specialization::Default, bool save_ = true, + bool runtime_modifiable_ = false, BasicSetting* other_setting_ = nullptr) requires(ranged) - : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization, - other_setting), + : BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization_, + other_setting_), value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val} {} /** @@ -235,13 +235,13 @@ public: * @param category_ Category of the setting AKA INI group */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, - Category category_, u32 specialization = Specialization::Default, + Category category_, u32 specialization_ = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, - BasicSetting* other_setting = nullptr) + BasicSetting* other_setting_ = nullptr) requires(!ranged) : Setting{ - linkage, default_val, name, category_, specialization, - save_, runtime_modifiable_, other_setting} { + linkage, default_val, name, category_, specialization_, + save_, runtime_modifiable_, other_setting_} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } virtual ~SwitchableSetting() = default; @@ -258,13 +258,14 @@ public: */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, Category category_, - u32 specialization = Specialization::Default, bool save_ = true, + u32 specialization_ = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, - BasicSetting* other_setting = nullptr) + BasicSetting* other_setting_ = nullptr) requires(ranged) - : Setting{ - linkage, default_val, min_val, max_val, name, category_, specialization, - save_, runtime_modifiable_, other_setting} { + : Setting{linkage, default_val, min_val, + max_val, name, category_, + specialization_, save_, runtime_modifiable_, + other_setting_} { linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); }); } From 8497fb0a046a208b0abcda9ba31ec77866ec922d Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 15:39:28 -0400 Subject: [PATCH 117/155] settings_enums: Remove casting Not sure how I missed this earlier, but these vectors can be constructed using the type of the enum. --- src/common/settings_enums.h | 110 ++++++++++++++++++------------------ 1 file changed, 55 insertions(+), 55 deletions(-) diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index c380e409e..a5f87c956 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -12,60 +12,60 @@ namespace Settings { template struct Canonicalization { - static constexpr std::vector> Get(); + static constexpr std::vector> Get(); }; -#define PAIR_45(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_46(N, __VA_ARGS__)) -#define PAIR_44(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_45(N, __VA_ARGS__)) -#define PAIR_43(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_44(N, __VA_ARGS__)) -#define PAIR_42(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_43(N, __VA_ARGS__)) -#define PAIR_41(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_42(N, __VA_ARGS__)) -#define PAIR_40(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_41(N, __VA_ARGS__)) -#define PAIR_39(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_40(N, __VA_ARGS__)) -#define PAIR_38(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_39(N, __VA_ARGS__)) -#define PAIR_37(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_38(N, __VA_ARGS__)) -#define PAIR_36(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_37(N, __VA_ARGS__)) -#define PAIR_35(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_36(N, __VA_ARGS__)) -#define PAIR_34(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_35(N, __VA_ARGS__)) -#define PAIR_33(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_34(N, __VA_ARGS__)) -#define PAIR_32(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_33(N, __VA_ARGS__)) -#define PAIR_31(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_32(N, __VA_ARGS__)) -#define PAIR_30(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_31(N, __VA_ARGS__)) -#define PAIR_29(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_30(N, __VA_ARGS__)) -#define PAIR_28(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_29(N, __VA_ARGS__)) -#define PAIR_27(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_28(N, __VA_ARGS__)) -#define PAIR_26(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_27(N, __VA_ARGS__)) -#define PAIR_25(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_26(N, __VA_ARGS__)) -#define PAIR_24(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_25(N, __VA_ARGS__)) -#define PAIR_23(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_24(N, __VA_ARGS__)) -#define PAIR_22(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_23(N, __VA_ARGS__)) -#define PAIR_21(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_22(N, __VA_ARGS__)) -#define PAIR_20(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_21(N, __VA_ARGS__)) -#define PAIR_19(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_20(N, __VA_ARGS__)) -#define PAIR_18(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_19(N, __VA_ARGS__)) -#define PAIR_17(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_18(N, __VA_ARGS__)) -#define PAIR_16(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_17(N, __VA_ARGS__)) -#define PAIR_15(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_16(N, __VA_ARGS__)) -#define PAIR_14(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_15(N, __VA_ARGS__)) -#define PAIR_13(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_14(N, __VA_ARGS__)) -#define PAIR_12(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_13(N, __VA_ARGS__)) -#define PAIR_11(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_12(N, __VA_ARGS__)) -#define PAIR_10(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_11(N, __VA_ARGS__)) -#define PAIR_9(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_10(N, __VA_ARGS__)) -#define PAIR_8(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_9(N, __VA_ARGS__)) -#define PAIR_7(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_8(N, __VA_ARGS__)) -#define PAIR_6(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_7(N, __VA_ARGS__)) -#define PAIR_5(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_6(N, __VA_ARGS__)) -#define PAIR_4(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_5(N, __VA_ARGS__)) -#define PAIR_3(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_4(N, __VA_ARGS__)) -#define PAIR_2(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_3(N, __VA_ARGS__)) -#define PAIR_1(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_2(N, __VA_ARGS__)) -#define PAIR(N, X, ...) {#X, static_cast(N::X)} __VA_OPT__(, PAIR_1(N, __VA_ARGS__)) +#define PAIR_45(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_46(N, __VA_ARGS__)) +#define PAIR_44(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_45(N, __VA_ARGS__)) +#define PAIR_43(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_44(N, __VA_ARGS__)) +#define PAIR_42(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_43(N, __VA_ARGS__)) +#define PAIR_41(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_42(N, __VA_ARGS__)) +#define PAIR_40(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_41(N, __VA_ARGS__)) +#define PAIR_39(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_40(N, __VA_ARGS__)) +#define PAIR_38(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_39(N, __VA_ARGS__)) +#define PAIR_37(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_38(N, __VA_ARGS__)) +#define PAIR_36(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_37(N, __VA_ARGS__)) +#define PAIR_35(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_36(N, __VA_ARGS__)) +#define PAIR_34(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_35(N, __VA_ARGS__)) +#define PAIR_33(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_34(N, __VA_ARGS__)) +#define PAIR_32(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_33(N, __VA_ARGS__)) +#define PAIR_31(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_32(N, __VA_ARGS__)) +#define PAIR_30(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_31(N, __VA_ARGS__)) +#define PAIR_29(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_30(N, __VA_ARGS__)) +#define PAIR_28(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_29(N, __VA_ARGS__)) +#define PAIR_27(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_28(N, __VA_ARGS__)) +#define PAIR_26(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_27(N, __VA_ARGS__)) +#define PAIR_25(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_26(N, __VA_ARGS__)) +#define PAIR_24(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_25(N, __VA_ARGS__)) +#define PAIR_23(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_24(N, __VA_ARGS__)) +#define PAIR_22(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_23(N, __VA_ARGS__)) +#define PAIR_21(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_22(N, __VA_ARGS__)) +#define PAIR_20(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_21(N, __VA_ARGS__)) +#define PAIR_19(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_20(N, __VA_ARGS__)) +#define PAIR_18(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_19(N, __VA_ARGS__)) +#define PAIR_17(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_18(N, __VA_ARGS__)) +#define PAIR_16(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_17(N, __VA_ARGS__)) +#define PAIR_15(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_16(N, __VA_ARGS__)) +#define PAIR_14(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_15(N, __VA_ARGS__)) +#define PAIR_13(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_14(N, __VA_ARGS__)) +#define PAIR_12(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_13(N, __VA_ARGS__)) +#define PAIR_11(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_12(N, __VA_ARGS__)) +#define PAIR_10(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_11(N, __VA_ARGS__)) +#define PAIR_9(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_10(N, __VA_ARGS__)) +#define PAIR_8(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_9(N, __VA_ARGS__)) +#define PAIR_7(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_8(N, __VA_ARGS__)) +#define PAIR_6(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_7(N, __VA_ARGS__)) +#define PAIR_5(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_6(N, __VA_ARGS__)) +#define PAIR_4(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_5(N, __VA_ARGS__)) +#define PAIR_3(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_4(N, __VA_ARGS__)) +#define PAIR_2(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_3(N, __VA_ARGS__)) +#define PAIR_1(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_2(N, __VA_ARGS__)) +#define PAIR(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_1(N, __VA_ARGS__)) #define ENUM(NAME, ...) \ enum class NAME : u32 { __VA_ARGS__ }; \ template <> \ - constexpr std::vector> Canonicalization::Get() { \ + constexpr std::vector> Canonicalization::Get() { \ return {PAIR(NAME, __VA_ARGS__)}; \ } @@ -77,12 +77,12 @@ enum class AudioEngine : u32 { }; template <> -constexpr std::vector> Canonicalization::Get() { +constexpr std::vector> Canonicalization::Get() { return { - {"auto", static_cast(AudioEngine::Auto)}, - {"cubeb", static_cast(AudioEngine::Cubeb)}, - {"sdl2", static_cast(AudioEngine::Sdl2)}, - {"null", static_cast(AudioEngine::Null)}, + {"auto", AudioEngine::Auto}, + {"cubeb", AudioEngine::Cubeb}, + {"sdl2", AudioEngine::Sdl2}, + {"null", AudioEngine::Null}, }; } @@ -132,7 +132,7 @@ template constexpr std::string CanonicalizeEnum(Type id) { const auto group = Canonicalization::Get(); for (auto& [name, value] : group) { - if (static_cast(value) == id) { + if (value == id) { return name; } } @@ -144,7 +144,7 @@ constexpr Type ToEnum(const std::string& canonicalization) { const auto group = Canonicalization::Get(); for (auto& [name, value] : group) { if (name == canonicalization) { - return static_cast(value); + return value; } } return {}; From 9186f08c3c6cad014c671ca152c78d9d2ee307e6 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 17:02:42 -0400 Subject: [PATCH 118/155] shared_translation: Deobfuscate auto time zone --- src/yuzu/configuration/shared_translation.cpp | 98 ++++++++++--------- 1 file changed, 52 insertions(+), 46 deletions(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index a1030efb0..f120a632c 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -1,6 +1,7 @@ // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#include "common/time_zone.h" #include "yuzu/configuration/shared_translation.h" #include @@ -309,52 +310,57 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(Region, Korea, "Korea"), PAIR(Region, Taiwan, "Taiwan"), }}); - translations->insert({typeid(Settings::TimeZone), - { - PAIR(TimeZone, Auto, "Auto"), - PAIR(TimeZone, Default, "Default"), - PAIR(TimeZone, Cet, "CET"), - PAIR(TimeZone, Cst6Cdt, "CST6CDT"), - PAIR(TimeZone, Cuba, "Cuba"), - PAIR(TimeZone, Eet, "EET"), - PAIR(TimeZone, Egypt, "Egypt"), - PAIR(TimeZone, Eire, "Eire"), - PAIR(TimeZone, Est, "EST"), - PAIR(TimeZone, Est5Edt, "EST5EDT"), - PAIR(TimeZone, Gb, "GB"), - PAIR(TimeZone, GbEire, "GB-Eire"), - PAIR(TimeZone, Gmt, "GMT"), - PAIR(TimeZone, GmtPlusZero, "GMT+0"), - PAIR(TimeZone, GmtMinusZero, "GMT-0"), - PAIR(TimeZone, GmtZero, "GMT0"), - PAIR(TimeZone, Greenwich, "Greenwich"), - PAIR(TimeZone, Hongkong, "Hongkong"), - PAIR(TimeZone, Hst, "HST"), - PAIR(TimeZone, Iceland, "Iceland"), - PAIR(TimeZone, Iran, "Iran"), - PAIR(TimeZone, Israel, "Israel"), - PAIR(TimeZone, Jamaica, "Jamaica"), - PAIR(TimeZone, Kwajalein, "Kwajalein"), - PAIR(TimeZone, Libya, "Libya"), - PAIR(TimeZone, Met, "MET"), - PAIR(TimeZone, Mst, "MST"), - PAIR(TimeZone, Mst7Mdt, "MST7MDT"), - PAIR(TimeZone, Navajo, "Navajo"), - PAIR(TimeZone, Nz, "NZ"), - PAIR(TimeZone, NzChat, "NZ-CHAT"), - PAIR(TimeZone, Poland, "Poland"), - PAIR(TimeZone, Portugal, "Portugal"), - PAIR(TimeZone, Prc, "PRC"), - PAIR(TimeZone, Pst8Pdt, "PST8PDT"), - PAIR(TimeZone, Roc, "ROC"), - PAIR(TimeZone, Rok, "ROK"), - PAIR(TimeZone, Singapore, "Singapore"), - PAIR(TimeZone, Turkey, "Turkey"), - PAIR(TimeZone, Uct, "UCT"), - PAIR(TimeZone, WSu, "W-SU"), - PAIR(TimeZone, Wet, "WET"), - PAIR(TimeZone, Zulu, "Zulu"), - }}); + translations->insert( + {typeid(Settings::TimeZone), + { + {static_cast(Settings::TimeZone::Auto), + tr("Auto (%1)", "Auto select time zone") + .arg(QString::fromStdString(Settings::GetTimeZoneString()))}, + {static_cast(Settings::TimeZone::Default), + tr("Default (%1)", "Default time zone") + .arg(QString::fromStdString(Common::TimeZone::GetDefaultTimeZone()))}, + PAIR(TimeZone, Cet, "CET"), + PAIR(TimeZone, Cst6Cdt, "CST6CDT"), + PAIR(TimeZone, Cuba, "Cuba"), + PAIR(TimeZone, Eet, "EET"), + PAIR(TimeZone, Egypt, "Egypt"), + PAIR(TimeZone, Eire, "Eire"), + PAIR(TimeZone, Est, "EST"), + PAIR(TimeZone, Est5Edt, "EST5EDT"), + PAIR(TimeZone, Gb, "GB"), + PAIR(TimeZone, GbEire, "GB-Eire"), + PAIR(TimeZone, Gmt, "GMT"), + PAIR(TimeZone, GmtPlusZero, "GMT+0"), + PAIR(TimeZone, GmtMinusZero, "GMT-0"), + PAIR(TimeZone, GmtZero, "GMT0"), + PAIR(TimeZone, Greenwich, "Greenwich"), + PAIR(TimeZone, Hongkong, "Hongkong"), + PAIR(TimeZone, Hst, "HST"), + PAIR(TimeZone, Iceland, "Iceland"), + PAIR(TimeZone, Iran, "Iran"), + PAIR(TimeZone, Israel, "Israel"), + PAIR(TimeZone, Jamaica, "Jamaica"), + PAIR(TimeZone, Kwajalein, "Kwajalein"), + PAIR(TimeZone, Libya, "Libya"), + PAIR(TimeZone, Met, "MET"), + PAIR(TimeZone, Mst, "MST"), + PAIR(TimeZone, Mst7Mdt, "MST7MDT"), + PAIR(TimeZone, Navajo, "Navajo"), + PAIR(TimeZone, Nz, "NZ"), + PAIR(TimeZone, NzChat, "NZ-CHAT"), + PAIR(TimeZone, Poland, "Poland"), + PAIR(TimeZone, Portugal, "Portugal"), + PAIR(TimeZone, Prc, "PRC"), + PAIR(TimeZone, Pst8Pdt, "PST8PDT"), + PAIR(TimeZone, Roc, "ROC"), + PAIR(TimeZone, Rok, "ROK"), + PAIR(TimeZone, Singapore, "Singapore"), + PAIR(TimeZone, Turkey, "Turkey"), + PAIR(TimeZone, Uct, "UCT"), + PAIR(TimeZone, WSu, "W-SU"), + PAIR(TimeZone, Wet, "WET"), + PAIR(TimeZone, Zulu, "Zulu"), + }}); translations->insert({typeid(Settings::AudioMode), { PAIR(AudioMode, Mono, "Mono"), From 52cc7b438bbaccb440382d0fd38d2d0805907814 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 17:06:10 -0400 Subject: [PATCH 119/155] settings_common: Remove unncessary enum spec --- src/common/settings_common.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/common/settings_common.h b/src/common/settings_common.h index 6b717deb1..669d32204 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -80,8 +80,8 @@ public: */ class BasicSetting { protected: - explicit BasicSetting(Linkage& linkage, const std::string& name, enum Category category_, - bool save_, bool runtime_modifiable_, u32 specialization, + explicit BasicSetting(Linkage& linkage, const std::string& name, Category category_, bool save_, + bool runtime_modifiable_, u32 specialization, BasicSetting* other_setting); public: From ecc1feff6478c1429648ebe003b54d974d9a3c3d Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 13:51:23 -0400 Subject: [PATCH 120/155] cmake: Use standard preprocessor on MSVC --- src/CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 0696201df..e814cff19 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -48,6 +48,7 @@ if (MSVC) /volatile:iso /Zc:externConstexpr /Zc:inline + /Zc:preprocessor # Use standards-conforming preprocessor /Zc:throwingNew /GT From e7f01128f181a7b754f6d5f94122cde059c7ed1a Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 21:41:06 -0400 Subject: [PATCH 121/155] settings: Give indices to enums --- src/common/settings_common.h | 5 +++++ src/common/settings_enums.h | 28 ++++++++++++++++++++++------ src/common/settings_setting.h | 9 +++++++++ 3 files changed, 36 insertions(+), 6 deletions(-) diff --git a/src/common/settings_common.h b/src/common/settings_common.h index 669d32204..b355384a4 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -220,6 +220,11 @@ public: */ [[nodiscard]] virtual constexpr bool Ranged() const = 0; + /** + * @returns The index of the enum if the underlying setting type is an enum, else max of u32. + */ + [[nodiscard]] virtual constexpr u32 EnumIndex() const = 0; + /* * Switchable settings */ diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index a5f87c956..f9bb75840 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -11,8 +11,9 @@ namespace Settings { template -struct Canonicalization { - static constexpr std::vector> Get(); +struct EnumMetadata { + static constexpr std::vector> Canonicalizations(); + static constexpr u32 Index(); }; #define PAIR_45(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_46(N, __VA_ARGS__)) @@ -65,10 +66,17 @@ struct Canonicalization { #define ENUM(NAME, ...) \ enum class NAME : u32 { __VA_ARGS__ }; \ template <> \ - constexpr std::vector> Canonicalization::Get() { \ + constexpr std::vector> EnumMetadata::Canonicalizations() { \ return {PAIR(NAME, __VA_ARGS__)}; \ + } \ + template <> \ + constexpr u32 EnumMetadata::Index() { \ + return __COUNTER__; \ } +// AudioEngine must be specified discretely due to having existing but slightly different +// canonicalizations +// TODO (lat9nq): Remove explicit definition of AudioEngine/sink_id enum class AudioEngine : u32 { Auto, Cubeb, @@ -77,7 +85,8 @@ enum class AudioEngine : u32 { }; template <> -constexpr std::vector> Canonicalization::Get() { +constexpr std::vector> +EnumMetadata::Canonicalizations() { return { {"auto", AudioEngine::Auto}, {"cubeb", AudioEngine::Cubeb}, @@ -86,6 +95,13 @@ constexpr std::vector> Canonicalization +constexpr u32 EnumMetadata::Index() { + // This is just a sufficiently large number that is more than the number of other enums declared + // here + return 100; +} + ENUM(AudioMode, Mono, Stereo, Surround); ENUM(Language, Japanese, EnglishAmerican, French, German, Italian, Spanish, Chinese, Korean, Dutch, @@ -130,7 +146,7 @@ ENUM(AspectRatio, R16_9, R4_3, R21_9, R16_10, Stretch); template constexpr std::string CanonicalizeEnum(Type id) { - const auto group = Canonicalization::Get(); + const auto group = EnumMetadata::Canonicalizations(); for (auto& [name, value] : group) { if (value == id) { return name; @@ -141,7 +157,7 @@ constexpr std::string CanonicalizeEnum(Type id) { template constexpr Type ToEnum(const std::string& canonicalization) { - const auto group = Canonicalization::Get(); + const auto group = EnumMetadata::Canonicalizations(); for (auto& [name, value] : group) { if (name == canonicalization) { return value; diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index eb46b2b6d..2e708fa0d 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -3,6 +3,7 @@ #pragma once +#include #include #include #include @@ -197,6 +198,14 @@ public: return std::type_index(typeid(Type)); } + constexpr u32 EnumIndex() const override { + if constexpr (std::is_enum()) { + return EnumMetadata::Index(); + } else { + return std::numeric_limits::max(); + } + } + virtual std::string MinVal() const override { return this->ToString(minimum); } From ca8509d205d20d034c548489d729f65656da611d Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 21:41:15 -0400 Subject: [PATCH 122/155] configuration: Use enum index --- src/yuzu/configuration/configure_cpu.cpp | 4 ++- src/yuzu/configuration/configure_graphics.cpp | 13 ++++--- src/yuzu/configuration/configure_graphics.h | 2 +- src/yuzu/configuration/shared_translation.cpp | 34 +++++++++---------- src/yuzu/configuration/shared_translation.h | 2 +- src/yuzu/configuration/shared_widget.cpp | 2 +- 6 files changed, 31 insertions(+), 26 deletions(-) diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 57cdc4c63..7d122906e 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -7,6 +7,7 @@ #include #include "common/common_types.h" #include "common/settings.h" +#include "common/settings_enums.h" #include "configuration/shared_widget.h" #include "core/core.h" #include "ui_configure_cpu.h" @@ -76,7 +77,8 @@ void ConfigureCpu::Setup(const ConfigurationShared::Builder& builder) { void ConfigureCpu::UpdateGroup(int index) { const auto accuracy = static_cast( - combobox_translations.at(typeid(Settings::CpuAccuracy))[index].first); + combobox_translations.at(Settings::EnumMetadata::Index())[index] + .first); ui->unsafe_group->setVisible(accuracy == Settings::CpuAccuracy::Unsafe); } diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 7263af13f..31e87ccf5 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -85,7 +85,8 @@ ConfigureGraphics::ConfigureGraphics( : ConfigurationShared::Tab(group_, parent), ui{std::make_unique()}, records{records_}, expose_compute_option{expose_compute_option_}, system{system_}, combobox_translations{builder.ComboboxTranslations()}, - shader_mapping{combobox_translations.at(typeid(Settings::ShaderBackend))} { + shader_mapping{ + combobox_translations.at(Settings::EnumMetadata::Index())} { vulkan_device = Settings::values.vulkan_device.GetValue(); RetrieveVulkanDevices(); @@ -356,7 +357,7 @@ const QString ConfigureGraphics::TranslateVSyncMode(VkPresentModeKHR mode, } } -int ConfigureGraphics::FindIndex(std::type_index enumeration, int value) const { +int ConfigureGraphics::FindIndex(u32 enumeration, int value) const { for (u32 i = 0; i < combobox_translations.at(enumeration).size(); i++) { if (combobox_translations.at(enumeration)[i].first == static_cast(value)) { return i; @@ -383,7 +384,8 @@ void ConfigureGraphics::ApplyConfiguration() { (!Settings::IsConfiguringGlobal() && api_restore_global_button->isEnabled())) { auto backend = static_cast( combobox_translations - .at(typeid(Settings::RendererBackend))[api_combobox->currentIndex()] + .at(Settings::EnumMetadata< + Settings::RendererBackend>::Index())[api_combobox->currentIndex()] .first); switch (backend) { case Settings::RendererBackend::OpenGL: @@ -440,7 +442,8 @@ void ConfigureGraphics::UpdateAPILayout() { if (is_opengl) { shader_backend_combobox->setCurrentIndex( - FindIndex(typeid(Settings::ShaderBackend), static_cast(shader_backend))); + FindIndex(Settings::EnumMetadata::Index(), + static_cast(shader_backend))); } else if (is_vulkan && static_cast(vulkan_device) < vulkan_device_combobox->count()) { vulkan_device_combobox->setCurrentIndex(vulkan_device); } @@ -466,7 +469,7 @@ Settings::RendererBackend ConfigureGraphics::GetCurrentGraphicsBackend() const { return Settings::values.renderer_backend.GetValue(true); } return static_cast( - combobox_translations.at(typeid(Settings::RendererBackend)) + combobox_translations.at(Settings::EnumMetadata::Index()) .at(api_combobox->currentIndex()) .first); } diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index 1848b1593..633a28414 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -75,7 +75,7 @@ private: Settings::RendererBackend GetCurrentGraphicsBackend() const; - int FindIndex(std::type_index enumeration, int value) const; + int FindIndex(u32 enumeration, int value) const; std::unique_ptr ui; QColor bg_color; diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index f120a632c..d51286b0e 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -182,19 +182,19 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { // Intentionally skipping VSyncMode to let the UI fill that one out - translations->insert({typeid(Settings::AstcDecodeMode), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(AstcDecodeMode, Cpu, "CPU"), PAIR(AstcDecodeMode, Gpu, "GPU"), PAIR(AstcDecodeMode, CpuAsynchronous, "CPU Asynchronous"), }}); - translations->insert({typeid(Settings::AstcRecompression), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(AstcRecompression, Uncompressed, "Uncompressed (Best quality)"), PAIR(AstcRecompression, Bc1, "BC1 (Low quality)"), PAIR(AstcRecompression, Bc3, "BC3 (Medium quality)"), }}); - translations->insert({typeid(Settings::RendererBackend), + translations->insert({Settings::EnumMetadata::Index(), { #ifdef HAS_OPENGL PAIR(RendererBackend, OpenGL, "OpenGL"), @@ -202,37 +202,37 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(RendererBackend, Vulkan, "Vulkan"), PAIR(RendererBackend, Null, "Null"), }}); - translations->insert({typeid(Settings::ShaderBackend), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(ShaderBackend, Glsl, "GLSL"), PAIR(ShaderBackend, Glasm, "GLASM (Assembly Shaders, NVIDIA Only)"), PAIR(ShaderBackend, SpirV, "SPIR-V (Experimental, Mesa Only)"), }}); - translations->insert({typeid(Settings::GpuAccuracy), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(GpuAccuracy, Normal, "Normal"), PAIR(GpuAccuracy, High, "High"), PAIR(GpuAccuracy, Extreme, "Extreme"), }}); - translations->insert({typeid(Settings::CpuAccuracy), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(CpuAccuracy, Auto, "Auto"), PAIR(CpuAccuracy, Accurate, "Accurate"), PAIR(CpuAccuracy, Unsafe, "Unsafe"), PAIR(CpuAccuracy, Paranoid, "Paranoid (disables most optimizations)"), }}); - translations->insert({typeid(Settings::FullscreenMode), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(FullscreenMode, Borderless, "Borderless Windowed"), PAIR(FullscreenMode, Exclusive, "Exclusive Fullscreen"), }}); - translations->insert({typeid(Settings::NvdecEmulation), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(NvdecEmulation, Off, "No Video Output"), PAIR(NvdecEmulation, Cpu, "CPU Video Decoding"), PAIR(NvdecEmulation, Gpu, "GPU Video Decoding (Default)"), }}); - translations->insert({typeid(Settings::ResolutionSetup), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(ResolutionSetup, Res1_2X, "0.5X (360p/540p) [EXPERIMENTAL]"), PAIR(ResolutionSetup, Res3_4X, "0.75X (540p/810p) [EXPERIMENTAL]"), @@ -246,7 +246,7 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(ResolutionSetup, Res7X, "7X (5040p/7560p)"), PAIR(ResolutionSetup, Res8X, "8X (5760p/8640p)"), }}); - translations->insert({typeid(Settings::ScalingFilter), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(ScalingFilter, NearestNeighbor, "Nearest Neighbor"), PAIR(ScalingFilter, Bilinear, "Bilinear"), @@ -255,13 +255,13 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(ScalingFilter, ScaleForce, "ScaleForce"), PAIR(ScalingFilter, Fsr, "AMD FidelityFX™️ Super Resolution"), }}); - translations->insert({typeid(Settings::AntiAliasing), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(AntiAliasing, None, "None"), PAIR(AntiAliasing, Fxaa, "FXAA"), PAIR(AntiAliasing, Smaa, "SMAA"), }}); - translations->insert({typeid(Settings::AspectRatio), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(AspectRatio, R16_9, "Default (16:9)"), PAIR(AspectRatio, R4_3, "Force 4:3"), @@ -269,7 +269,7 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(AspectRatio, R16_10, "Force 16:10"), PAIR(AspectRatio, Stretch, "Stretch to Window"), }}); - translations->insert({typeid(Settings::AnisotropyMode), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(AnisotropyMode, Automatic, "Automatic"), PAIR(AnisotropyMode, Default, "Default"), @@ -279,7 +279,7 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(AnisotropyMode, X16, "16x"), }}); translations->insert( - {typeid(Settings::Language), + {Settings::EnumMetadata::Index(), { PAIR(Language, Japanese, "Japanese (日本語)"), PAIR(Language, EnglishAmerican, "American English"), @@ -300,7 +300,7 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(Language, ChineseTraditional, "Traditional Chinese (正體中文)"), PAIR(Language, PortugueseBrazilian, "Brazilian Portuguese (português do Brasil)"), }}); - translations->insert({typeid(Settings::Region), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(Region, Japan, "Japan"), PAIR(Region, Usa, "USA"), @@ -311,7 +311,7 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(Region, Taiwan, "Taiwan"), }}); translations->insert( - {typeid(Settings::TimeZone), + {Settings::EnumMetadata::Index(), { {static_cast(Settings::TimeZone::Auto), tr("Auto (%1)", "Auto select time zone") @@ -361,7 +361,7 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(TimeZone, Wet, "WET"), PAIR(TimeZone, Zulu, "Zulu"), }}); - translations->insert({typeid(Settings::AudioMode), + translations->insert({Settings::EnumMetadata::Index(), { PAIR(AudioMode, Mono, "Mono"), PAIR(AudioMode, Stereo, "Stereo"), diff --git a/src/yuzu/configuration/shared_translation.h b/src/yuzu/configuration/shared_translation.h index cc8419e03..99a0e808c 100644 --- a/src/yuzu/configuration/shared_translation.h +++ b/src/yuzu/configuration/shared_translation.h @@ -16,7 +16,7 @@ class QWidget; namespace ConfigurationShared { using TranslationMap = std::map>; using ComboboxTranslations = std::vector>; -using ComboboxTranslationMap = std::map; +using ComboboxTranslationMap = std::map; std::unique_ptr InitializeTranslations(QWidget* parent); diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 978bfa590..ba7f60c2d 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -125,7 +125,7 @@ QWidget* Widget::CreateCheckBox(Settings::BasicSetting* bool_setting, const QStr QWidget* Widget::CreateCombobox(std::function& serializer, std::function& restore_func, const std::function& touch) { - const auto type = setting.TypeId(); + const auto type = setting.EnumIndex(); combobox = new QComboBox(this); combobox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); From c1717b3f47af88a2c836ebbf2c4c3f773ae58cb0 Mon Sep 17 00:00:00 2001 From: toast2903 <22451773+lat9nq@users.noreply.github.com> Date: Wed, 21 Jun 2023 22:57:40 -0400 Subject: [PATCH 123/155] cmake: Reposition preprocessor switch comment Co-authored-by: Morph <39850852+Morph1984@users.noreply.github.com> --- src/CMakeLists.txt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index e814cff19..2da983cad 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -35,6 +35,7 @@ if (MSVC) # /volatile:iso - Use strict standards-compliant volatile semantics. # /Zc:externConstexpr - Allow extern constexpr variables to have external linkage, like the standard mandates # /Zc:inline - Let codegen omit inline functions in object files + # /Zc:preprocessor - Enable standards-conforming preprocessor # /Zc:throwingNew - Let codegen assume `operator new` (without std::nothrow) will never return null # /GT - Supports fiber safety for data allocated using static thread-local storage add_compile_options( @@ -48,7 +49,7 @@ if (MSVC) /volatile:iso /Zc:externConstexpr /Zc:inline - /Zc:preprocessor # Use standards-conforming preprocessor + /Zc:preprocessor /Zc:throwingNew /GT From a14d2a6f83591fe2ae27fcaa2ad96da4567df99f Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Thu, 22 Jun 2023 00:31:19 -0400 Subject: [PATCH 124/155] shared_translation: Add barrier_feedback_loops --- src/yuzu/configuration/shared_translation.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index d51286b0e..6e8cea625 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -120,6 +120,8 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(Settings, use_video_framerate, "Sync to framerate of video playback", "Run the game at normal speed during video playback, even when the framerate is " "unlocked."); + INSERT(Settings, barrier_feedback_loops, "Barrier feedback loops", + "Improves rendering of transparency effects in specific games."); // Renderer (Debug) From ef6406a66652e2879abe44c66b517dd7d9b9338c Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 27 Jun 2023 19:50:22 -0400 Subject: [PATCH 125/155] shared_translation: Add controller_applet_disabled --- src/yuzu/configuration/shared_translation.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 6e8cea625..473e29479 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -158,6 +158,7 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { INSERT(UISettings, pause_when_in_background, "Pause emulation when in background", ""); INSERT(UISettings, confirm_before_closing, "Confirm exit while emulation is running", ""); INSERT(UISettings, hide_mouse, "Hide mouse on inactivity", ""); + INSERT(UISettings, controller_applet_disabled, "Disable controller applet", ""); // Ui Debugging From 07e8477f5a897730dd547d8b6af6d05db0cede81 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 4 Jul 2023 16:40:11 -0400 Subject: [PATCH 126/155] shared_translation: Add missing time zones --- src/yuzu/configuration/shared_translation.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 473e29479..05cc942de 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -343,6 +343,7 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(TimeZone, Iran, "Iran"), PAIR(TimeZone, Israel, "Israel"), PAIR(TimeZone, Jamaica, "Jamaica"), + PAIR(TimeZone, Japan, "Japan"), PAIR(TimeZone, Kwajalein, "Kwajalein"), PAIR(TimeZone, Libya, "Libya"), PAIR(TimeZone, Met, "MET"), @@ -360,6 +361,8 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(TimeZone, Singapore, "Singapore"), PAIR(TimeZone, Turkey, "Turkey"), PAIR(TimeZone, Uct, "UCT"), + PAIR(TimeZone, Universal, "Universal"), + PAIR(TimeZone, Utc, "UTC"), PAIR(TimeZone, WSu, "W-SU"), PAIR(TimeZone, Wet, "WET"), PAIR(TimeZone, Zulu, "Zulu"), From ff6a5031d5ea509375a5dc1ee7b9eeddda6d9ebc Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 4 Jul 2023 16:48:48 -0400 Subject: [PATCH 127/155] settings: Require time zone setting value for stirng --- src/common/settings.cpp | 4 ++-- src/common/settings.h | 2 +- src/core/hle/service/time/time_zone_content_manager.cpp | 3 ++- src/yuzu/configuration/shared_translation.cpp | 3 ++- 4 files changed, 7 insertions(+), 5 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index d9948dde8..78fa99113 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -66,8 +66,8 @@ SWITCHABLE(u8, true); Values values; -std::string GetTimeZoneString() { - const auto time_zone_index = static_cast(values.time_zone_index.GetValue()); +std::string GetTimeZoneString(TimeZone time_zone) { + const auto time_zone_index = static_cast(time_zone); ASSERT(time_zone_index < Common::TimeZone::GetTimeZoneStrings().size()); std::string location_name; diff --git a/src/common/settings.h b/src/common/settings.h index c4339cb1f..928636c72 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -516,7 +516,7 @@ bool IsFastmemEnabled(); float Volume(); -std::string GetTimeZoneString(); +std::string GetTimeZoneString(TimeZone time_zone); void LogSettings(); diff --git a/src/core/hle/service/time/time_zone_content_manager.cpp b/src/core/hle/service/time/time_zone_content_manager.cpp index 5d60be67a..565f6b39b 100644 --- a/src/core/hle/service/time/time_zone_content_manager.cpp +++ b/src/core/hle/service/time/time_zone_content_manager.cpp @@ -76,7 +76,8 @@ TimeZoneContentManager::TimeZoneContentManager(Core::System& system_) : system{system_}, location_name_cache{BuildLocationNameCache(system)} {} void TimeZoneContentManager::Initialize(TimeManager& time_manager) { - const auto timezone_setting = Settings::GetTimeZoneString(); + const auto timezone_setting = + Settings::GetTimeZoneString(Settings::values.time_zone_index.GetValue()); if (FileSys::VirtualFile vfs_file; GetTimeZoneInfoFile(timezone_setting, vfs_file) == ResultSuccess) { diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index 05cc942de..fadc8034e 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -318,7 +318,8 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { { {static_cast(Settings::TimeZone::Auto), tr("Auto (%1)", "Auto select time zone") - .arg(QString::fromStdString(Settings::GetTimeZoneString()))}, + .arg(QString::fromStdString( + Settings::GetTimeZoneString(Settings::TimeZone::Auto)))}, {static_cast(Settings::TimeZone::Default), tr("Default (%1)", "Default time zone") .arg(QString::fromStdString(Common::TimeZone::GetDefaultTimeZone()))}, From 127b3da0f13ea0850c10115d45488dfe32a0a3f4 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 17 Jul 2023 19:59:22 -0400 Subject: [PATCH 128/155] core,common: Give memory layout setting an enum Allows for 6GB and 8GB layouts to be selected. --- src/common/settings.h | 8 ++++++-- src/common/settings_enums.h | 2 ++ src/core/core.cpp | 10 +++++++--- .../board/nintendo/nx/k_system_control.cpp | 20 +++++++++++++++---- 4 files changed, 31 insertions(+), 9 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 928636c72..618c34334 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -153,8 +153,12 @@ struct Values { // Core SwitchableSetting use_multi_core{linkage, true, "use_multi_core", Category::Core}; - SwitchableSetting use_unsafe_extended_memory_layout{ - linkage, false, "use_unsafe_extended_memory_layout", Category::Core}; + SwitchableSetting memory_layout_mode{linkage, + MemoryLayout::Memory_4Gb, + MemoryLayout::Memory_4Gb, + MemoryLayout::Memory_8Gb, + "memory_layout_mode", + Category::Core}; SwitchableSetting use_speed_limit{ linkage, true, "use_speed_limit", Category::Core, Specialization::Paired, false, true}; SwitchableSetting speed_limit{linkage, diff --git a/src/common/settings_enums.h b/src/common/settings_enums.h index f9bb75840..a1a29ebf6 100644 --- a/src/common/settings_enums.h +++ b/src/common/settings_enums.h @@ -131,6 +131,8 @@ ENUM(GpuAccuracy, Normal, High, Extreme); ENUM(CpuAccuracy, Auto, Accurate, Unsafe, Paranoid); +ENUM(MemoryLayout, Memory_4Gb, Memory_6Gb, Memory_8Gb); + ENUM(FullscreenMode, Borderless, Exclusive); ENUM(NvdecEmulation, Off, Cpu, Gpu); diff --git a/src/core/core.cpp b/src/core/core.cpp index e2902a91f..951942083 100644 --- a/src/core/core.cpp +++ b/src/core/core.cpp @@ -12,6 +12,7 @@ #include "common/logging/log.h" #include "common/microprofile.h" #include "common/settings.h" +#include "common/settings_enums.h" #include "common/string_util.h" #include "core/arm/exclusive_monitor.h" #include "core/core.h" @@ -140,7 +141,8 @@ struct System::Impl { device_memory = std::make_unique(); is_multicore = Settings::values.use_multi_core.GetValue(); - extended_memory_layout = Settings::values.use_unsafe_extended_memory_layout.GetValue(); + extended_memory_layout = + Settings::values.memory_layout_mode.GetValue() != Settings::MemoryLayout::Memory_4Gb; core_timing.SetMulticore(is_multicore); core_timing.Initialize([&system]() { system.RegisterHostThread(); }); @@ -168,7 +170,8 @@ struct System::Impl { void ReinitializeIfNecessary(System& system) { const bool must_reinitialize = is_multicore != Settings::values.use_multi_core.GetValue() || - extended_memory_layout != Settings::values.use_unsafe_extended_memory_layout.GetValue(); + extended_memory_layout != (Settings::values.memory_layout_mode.GetValue() != + Settings::MemoryLayout::Memory_4Gb); if (!must_reinitialize) { return; @@ -177,7 +180,8 @@ struct System::Impl { LOG_DEBUG(Kernel, "Re-initializing"); is_multicore = Settings::values.use_multi_core.GetValue(); - extended_memory_layout = Settings::values.use_unsafe_extended_memory_layout.GetValue(); + extended_memory_layout = + Settings::values.memory_layout_mode.GetValue() != Settings::MemoryLayout::Memory_4Gb; Initialize(system); } diff --git a/src/core/hle/kernel/board/nintendo/nx/k_system_control.cpp b/src/core/hle/kernel/board/nintendo/nx/k_system_control.cpp index 49bdc671e..7320b87b9 100644 --- a/src/core/hle/kernel/board/nintendo/nx/k_system_control.cpp +++ b/src/core/hle/kernel/board/nintendo/nx/k_system_control.cpp @@ -35,13 +35,25 @@ namespace { using namespace Common::Literals; u32 GetMemorySizeForInit() { - return Settings::values.use_unsafe_extended_memory_layout ? Smc::MemorySize_8GB - : Smc::MemorySize_4GB; + switch (Settings::values.memory_layout_mode.GetValue()) { + case Settings::MemoryLayout::Memory_4Gb: + return Smc::MemorySize_4GB; + case Settings::MemoryLayout::Memory_6Gb: + return Smc::MemorySize_6GB; + case Settings::MemoryLayout::Memory_8Gb: + return Smc::MemorySize_8GB; + } } Smc::MemoryArrangement GetMemoryArrangeForInit() { - return Settings::values.use_unsafe_extended_memory_layout ? Smc::MemoryArrangement_8GB - : Smc::MemoryArrangement_4GB; + switch (Settings::values.memory_layout_mode.GetValue()) { + case Settings::MemoryLayout::Memory_4Gb: + return Smc::MemoryArrangement_4GB; + case Settings::MemoryLayout::Memory_6Gb: + return Smc::MemoryArrangement_6GB; + case Settings::MemoryLayout::Memory_8Gb: + return Smc::MemoryArrangement_8GB; + } } } // namespace From 35872ad95b998e77b7bf1dce8ef41b87156952c3 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 17 Jul 2023 19:59:47 -0400 Subject: [PATCH 129/155] shared_translation: Update memory layout mode strings --- src/yuzu/configuration/shared_translation.cpp | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/src/yuzu/configuration/shared_translation.cpp b/src/yuzu/configuration/shared_translation.cpp index fadc8034e..335810788 100644 --- a/src/yuzu/configuration/shared_translation.cpp +++ b/src/yuzu/configuration/shared_translation.cpp @@ -35,8 +35,7 @@ std::unique_ptr InitializeTranslations(QWidget* parent) { // Core INSERT(Settings, use_multi_core, "Multicore CPU Emulation", ""); - INSERT(Settings, use_unsafe_extended_memory_layout, "Unsafe extended memory layout (8GB DRAM)", - ""); + INSERT(Settings, memory_layout_mode, "Memory Layout", ""); INSERT(Settings, use_speed_limit, "", ""); INSERT(Settings, speed_limit, "Limit Speed Percent", ""); @@ -374,6 +373,12 @@ std::unique_ptr ComboboxEnumeration(QWidget* parent) { PAIR(AudioMode, Stereo, "Stereo"), PAIR(AudioMode, Surround, "Surround"), }}); + translations->insert({Settings::EnumMetadata::Index(), + { + PAIR(MemoryLayout, Memory_4Gb, "4GB DRAM (Default)"), + PAIR(MemoryLayout, Memory_6Gb, "6GB DRAM (Unsafe)"), + PAIR(MemoryLayout, Memory_8Gb, "8GB DRAM (Unsafe)"), + }}); #undef PAIR #undef CTX_PAIR From 267f3c7905972ad78713cd92f96e3073ea1c8996 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 18 Jul 2023 15:36:20 -0400 Subject: [PATCH 130/155] settings: Cleanup Addresses review feedback Co-authored-by: Morph <39850852+Morph1984@users.noreply.github.com> --- src/common/CMakeLists.txt | 1 + src/common/settings.cpp | 5 ++- src/common/settings_setting.h | 77 +++++++++++++++++++++-------------- 3 files changed, 51 insertions(+), 32 deletions(-) diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt index e205055e6..bf97d9ba2 100644 --- a/src/common/CMakeLists.txt +++ b/src/common/CMakeLists.txt @@ -205,6 +205,7 @@ if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang") -Werror=unreachable-code-aggressive ) target_compile_definitions(common PRIVATE + # Clang 14 and earlier have errors when explicitly instantiating Settings::Setting $<$,15>:CANNOT_EXPLICITLY_INSTANTIATE> ) endif() diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 78fa99113..59d24a053 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -25,6 +25,7 @@ namespace Settings { +// Clang 14 and earlier have errors when explicitly instantiating these classes #ifndef CANNOT_EXPLICITLY_INSTANTIATE #define SETTING(TYPE, RANGED) template class Setting #define SWITCHABLE(TYPE, RANGED) template class SwitchableSetting @@ -113,11 +114,11 @@ void LogSettings() { for (const auto& setting : settings) { if (setting->Id() == values.yuzu_token.Id()) { - // Hide the token secret, which could be used to share patreon builds + // Hide the token secret, for security reasons. continue; } - std::string name = fmt::format( + const auto name = fmt::format( "{:c}{:c} {}.{}", setting->ToString() == setting->DefaultToString() ? '-' : 'M', setting->UsingGlobal() ? '-' : 'C', TranslateCategory(category), setting->GetLabel()); diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index 2e708fa0d..959b4f3f9 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -34,6 +34,10 @@ public: * @param default_val Initial value of the setting, and default value of the setting * @param name Label for the setting * @param category_ Category of the setting AKA INI group + * @param specialization_ Suggestion for how frontend implemetations represent this in a config + * @param save_ Suggests that this should or should not be saved to a frontend config file + * @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded + * @param other_setting_ A second Setting to associate to this one in metadata */ explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, enum Category category_, u32 specialization_ = Specialization::Default, @@ -54,6 +58,10 @@ public: * @param max_val Sets the maximum allowed value of the setting * @param name Label for the setting * @param category_ Category of the setting AKA INI group + * @param specialization_ Suggestion for how frontend implemetations represent this in a config + * @param save_ Suggests that this should or should not be saved to a frontend config file + * @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded + * @param other_setting_ A second Setting to associate to this one in metadata */ explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, enum Category category_, @@ -93,18 +101,19 @@ public: } [[nodiscard]] constexpr bool IsEnum() const override { - return std::is_enum::value; + return std::is_enum_v; } protected: - std::string ToString(const Type& value_) const { - if constexpr (std::is_same()) { + [[nodiscard]] std::string ToString(const Type& value_) const { + if constexpr (std::is_same_v) { return value_; - } else if constexpr (std::is_same>()) { + } else if constexpr (std::is_same_v>) { return value_.has_value() ? std::to_string(*value_) : "none"; - } else if constexpr (std::is_same()) { + } else if constexpr (std::is_same_v) { return value_ ? "true" : "false"; - } else if constexpr (std::is_same()) { + } else if constexpr (std::is_same_v) { + // Compatibility with old AudioEngine setting being a string return CanonicalizeEnum(value_); } else { return std::to_string(static_cast(value_)); @@ -118,7 +127,7 @@ public: * * @returns The current setting as a std::string */ - std::string ToString() const override { + [[nodiscard]] std::string ToString() const override { return ToString(this->GetValue()); } @@ -127,7 +136,7 @@ public: * * @returns The default value as a string. */ - std::string DefaultToString() const override { + [[nodiscard]] std::string DefaultToString() const override { return ToString(default_value); } @@ -159,19 +168,19 @@ public: * * @param input The desired value */ - void LoadString(const std::string& input) override { + void LoadString(const std::string& input) override final { if (input.empty()) { this->SetValue(this->GetDefault()); return; } try { - if constexpr (std::is_same()) { + if constexpr (std::is_same_v) { this->SetValue(input); - } else if constexpr (std::is_same>()) { + } else if constexpr (std::is_same_v>) { this->SetValue(static_cast(std::stoul(input))); - } else if constexpr (std::is_same()) { + } else if constexpr (std::is_same_v) { this->SetValue(input == "true"); - } else if constexpr (std::is_same()) { + } else if constexpr (std::is_same_v) { this->SetValue(ToEnum(input)); } else { this->SetValue(static_cast(std::stoll(input))); @@ -181,8 +190,8 @@ public: } } - [[nodiscard]] std::string constexpr Canonicalize() const override { - if constexpr (std::is_enum::value) { + [[nodiscard]] std::string constexpr Canonicalize() const override final { + if constexpr (std::is_enum_v) { return CanonicalizeEnum(this->GetValue()); } else { return ToString(this->GetValue()); @@ -194,26 +203,26 @@ public: * * @returns the type_index of the setting's type */ - virtual std::type_index TypeId() const override { + [[nodiscard]] std::type_index TypeId() const override final { return std::type_index(typeid(Type)); } - constexpr u32 EnumIndex() const override { - if constexpr (std::is_enum()) { + [[nodiscard]] constexpr u32 EnumIndex() const override final { + if constexpr (std::is_enum_v) { return EnumMetadata::Index(); } else { return std::numeric_limits::max(); } } - virtual std::string MinVal() const override { + [[nodiscard]] std::string MinVal() const override final { return this->ToString(minimum); } - virtual std::string MaxVal() const override { + [[nodiscard]] std::string MaxVal() const override final { return this->ToString(maximum); } - constexpr bool Ranged() const override { + [[nodiscard]] constexpr bool Ranged() const override { return ranged; } @@ -242,6 +251,10 @@ public: * @param default_val Initial value of the setting, and default value of the setting * @param name Label for the setting * @param category_ Category of the setting AKA INI group + * @param specialization_ Suggestion for how frontend implemetations represent this in a config + * @param save_ Suggests that this should or should not be saved to a frontend config file + * @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded + * @param other_setting_ A second Setting to associate to this one in metadata */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, Category category_, u32 specialization_ = Specialization::Default, @@ -264,6 +277,10 @@ public: * @param max_val Sets the maximum allowed value of the setting * @param name Label for the setting * @param category_ Category of the setting AKA INI group + * @param specialization_ Suggestion for how frontend implemetations represent this in a config + * @param save_ Suggests that this should or should not be saved to a frontend config file + * @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded + * @param other_setting_ A second Setting to associate to this one in metadata */ explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, Category category_, @@ -284,7 +301,7 @@ public: * * @param to_global Whether to use the global or custom setting. */ - void SetGlobal(bool to_global) override { + void SetGlobal(bool to_global) override final { use_global = to_global; } @@ -293,7 +310,7 @@ public: * * @returns The global state */ - [[nodiscard]] bool UsingGlobal() const override { + [[nodiscard]] bool UsingGlobal() const override final { return use_global; } @@ -305,13 +322,13 @@ public: * * @returns The required value of the setting */ - [[nodiscard]] virtual const Type& GetValue() const override { + [[nodiscard]] const Type& GetValue() const override final { if (use_global) { return this->value; } return custom; } - [[nodiscard]] virtual const Type& GetValue(bool need_global) const { + [[nodiscard]] const Type& GetValue(bool need_global) const { if (use_global || need_global) { return this->value; } @@ -323,7 +340,7 @@ public: * * @param val The new value */ - void SetValue(const Type& val) override { + void SetValue(const Type& val) override final { Type temp{ranged ? std::clamp(val, this->minimum, this->maximum) : val}; if (use_global) { std::swap(this->value, temp); @@ -332,11 +349,11 @@ public: } } - [[nodiscard]] virtual constexpr bool Switchable() const override { + [[nodiscard]] constexpr bool Switchable() const override final { return true; } - [[nodiscard]] virtual std::string ToStringGlobal() const override { + [[nodiscard]] std::string ToStringGlobal() const override final { return this->ToString(this->value); } @@ -347,7 +364,7 @@ public: * * @returns A reference to the current setting value */ - const Type& operator=(const Type& val) override { + const Type& operator=(const Type& val) override final { Type temp{ranged ? std::clamp(val, this->minimum, this->maximum) : val}; if (use_global) { std::swap(this->value, temp); @@ -362,7 +379,7 @@ public: * * @returns A reference to the current setting value */ - virtual explicit operator const Type&() const override { + explicit operator const Type&() const override final { if (use_global) { return this->value; } From 1e093767a85ee0fdce6f1619e967a6560963dcf3 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 18 Jul 2023 15:42:59 -0400 Subject: [PATCH 131/155] common,configure_system: Rename method to GetCategory Fixes essentially a shadowing issue. --- src/common/settings_common.cpp | 2 +- src/common/settings_common.h | 8 ++++---- src/common/settings_setting.h | 4 ++-- src/yuzu/configuration/configure_system.cpp | 2 +- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/common/settings_common.cpp b/src/common/settings_common.cpp index 799942980..8b666f8b2 100644 --- a/src/common/settings_common.cpp +++ b/src/common/settings_common.cpp @@ -36,7 +36,7 @@ bool BasicSetting::RuntimeModfiable() const { return runtime_modifiable; } -Category BasicSetting::Category() const { +Category BasicSetting::GetCategory() const { return category; } diff --git a/src/common/settings_common.h b/src/common/settings_common.h index b355384a4..ca218e37b 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -196,7 +196,7 @@ public: * * @returns The setting's category */ - [[nodiscard]] enum Category Category() const; + [[nodiscard]] Category GetCategory() const; /** * @returns Extra metadata for data representation in frontend implementations. @@ -246,9 +246,9 @@ public: [[nodiscard]] virtual bool UsingGlobal() const; private: - const std::string label; ///< The setting's label - const enum Category category; ///< The setting's category AKA INI group - const u32 id; ///< Unique integer for the setting + const std::string label; ///< The setting's label + const Category category; ///< The setting's category AKA INI group + const u32 id; ///< Unique integer for the setting const bool save; ///< Suggests if the setting should be saved and read to a frontend config const bool runtime_modifiable; ///< Suggests if the setting can be modified while a guest is running diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index 959b4f3f9..55280fec4 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -40,7 +40,7 @@ public: * @param other_setting_ A second Setting to associate to this one in metadata */ explicit Setting(Linkage& linkage, const Type& default_val, const std::string& name, - enum Category category_, u32 specialization_ = Specialization::Default, + Category category_, u32 specialization_ = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, BasicSetting* other_setting_ = nullptr) requires(!ranged) @@ -64,7 +64,7 @@ public: * @param other_setting_ A second Setting to associate to this one in metadata */ explicit Setting(Linkage& linkage, const Type& default_val, const Type& min_val, - const Type& max_val, const std::string& name, enum Category category_, + const Type& max_val, const std::string& name, Category category_, u32 specialization_ = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, BasicSetting* other_setting_ = nullptr) requires(ranged) diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 05706c4de..d76630bcb 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -124,7 +124,7 @@ void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { combo_language = widget->combobox; } - switch (setting->Category()) { + switch (setting->GetCategory()) { case Settings::Category::Core: core_hold.emplace(setting->Id(), widget); break; From b02e7eea78cf5d5f3631b11a58f28d0888948fc0 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 18 Jul 2023 15:44:27 -0400 Subject: [PATCH 132/155] settings_setting: Fix typo --- src/common/settings_setting.h | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/common/settings_setting.h b/src/common/settings_setting.h index 55280fec4..a8beb06e9 100644 --- a/src/common/settings_setting.h +++ b/src/common/settings_setting.h @@ -34,7 +34,7 @@ public: * @param default_val Initial value of the setting, and default value of the setting * @param name Label for the setting * @param category_ Category of the setting AKA INI group - * @param specialization_ Suggestion for how frontend implemetations represent this in a config + * @param specialization_ Suggestion for how frontend implementations represent this in a config * @param save_ Suggests that this should or should not be saved to a frontend config file * @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded * @param other_setting_ A second Setting to associate to this one in metadata @@ -58,7 +58,7 @@ public: * @param max_val Sets the maximum allowed value of the setting * @param name Label for the setting * @param category_ Category of the setting AKA INI group - * @param specialization_ Suggestion for how frontend implemetations represent this in a config + * @param specialization_ Suggestion for how frontend implementations represent this in a config * @param save_ Suggests that this should or should not be saved to a frontend config file * @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded * @param other_setting_ A second Setting to associate to this one in metadata @@ -251,7 +251,7 @@ public: * @param default_val Initial value of the setting, and default value of the setting * @param name Label for the setting * @param category_ Category of the setting AKA INI group - * @param specialization_ Suggestion for how frontend implemetations represent this in a config + * @param specialization_ Suggestion for how frontend implementations represent this in a config * @param save_ Suggests that this should or should not be saved to a frontend config file * @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded * @param other_setting_ A second Setting to associate to this one in metadata @@ -277,7 +277,7 @@ public: * @param max_val Sets the maximum allowed value of the setting * @param name Label for the setting * @param category_ Category of the setting AKA INI group - * @param specialization_ Suggestion for how frontend implemetations represent this in a config + * @param specialization_ Suggestion for how frontend implementations represent this in a config * @param save_ Suggests that this should or should not be saved to a frontend config file * @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded * @param other_setting_ A second Setting to associate to this one in metadata From 32116231924bfc1ad356fc0f39df327a393b8df1 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 18 Jul 2023 15:49:36 -0400 Subject: [PATCH 133/155] common: Move global configuration state modifiers back to settings --- src/common/settings.cpp | 10 ++++++++++ src/common/settings.h | 3 +++ src/common/settings_common.cpp | 10 ---------- src/common/settings_common.h | 3 --- src/yuzu/configuration/shared_widget.cpp | 1 + 5 files changed, 14 insertions(+), 13 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 59d24a053..4c1cd1cac 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -287,4 +287,14 @@ void RestoreGlobalState(bool is_powered_on) { } } +static bool configuring_global = true; + +bool IsConfiguringGlobal() { + return configuring_global; +} + +void SetConfiguringGlobal(bool is_global) { + configuring_global = is_global; +} + } // namespace Settings diff --git a/src/common/settings.h b/src/common/settings.h index 618c34334..655f6468a 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -529,4 +529,7 @@ void UpdateRescalingInfo(); // Restore the global state of all applicable settings in the Values struct void RestoreGlobalState(bool is_powered_on); +bool IsConfiguringGlobal(); +void SetConfiguringGlobal(bool is_global); + } // namespace Settings diff --git a/src/common/settings_common.cpp b/src/common/settings_common.cpp index 8b666f8b2..1439fb451 100644 --- a/src/common/settings_common.cpp +++ b/src/common/settings_common.cpp @@ -52,14 +52,4 @@ const std::string& BasicSetting::GetLabel() const { return label; } -static bool configuring_global = true; - -bool IsConfiguringGlobal() { - return configuring_global; -} - -void SetConfiguringGlobal(bool is_global) { - configuring_global = is_global; -} - } // namespace Settings diff --git a/src/common/settings_common.h b/src/common/settings_common.h index ca218e37b..a7630a97f 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -60,9 +60,6 @@ enum Specialization : u8 { Percentage = (1 << SpecializationAttributeOffset), }; -bool IsConfiguringGlobal(); -void SetConfiguringGlobal(bool is_global); - class BasicSetting; class Linkage { diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index ba7f60c2d..c9ab461f6 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -39,6 +39,7 @@ #include "common/assert.h" #include "common/common_types.h" #include "common/logging/log.h" +#include "common/settings.h" #include "common/settings_common.h" #include "yuzu/configuration/shared_translation.h" From 8e91554e116b46f1c194012a2b21a15542743827 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 18 Jul 2023 17:11:23 -0400 Subject: [PATCH 134/155] k_system_control: Always return some memory size --- src/core/hle/kernel/board/nintendo/nx/k_system_control.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/core/hle/kernel/board/nintendo/nx/k_system_control.cpp b/src/core/hle/kernel/board/nintendo/nx/k_system_control.cpp index 7320b87b9..4cfdf4558 100644 --- a/src/core/hle/kernel/board/nintendo/nx/k_system_control.cpp +++ b/src/core/hle/kernel/board/nintendo/nx/k_system_control.cpp @@ -43,6 +43,7 @@ u32 GetMemorySizeForInit() { case Settings::MemoryLayout::Memory_8Gb: return Smc::MemorySize_8GB; } + return Smc::MemorySize_4GB; } Smc::MemoryArrangement GetMemoryArrangeForInit() { @@ -54,6 +55,7 @@ Smc::MemoryArrangement GetMemoryArrangeForInit() { case Settings::MemoryLayout::Memory_8Gb: return Smc::MemoryArrangement_8GB; } + return Smc::MemoryArrangement_4GB; } } // namespace From b55a763618db3e66fee70ff971a44f1779bed7ec Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 18 Jul 2023 19:04:01 -0400 Subject: [PATCH 135/155] config-android: Update memory layout member name --- src/android/app/src/main/jni/config.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/android/app/src/main/jni/config.cpp b/src/android/app/src/main/jni/config.cpp index 09c095c09..5e1f10f99 100644 --- a/src/android/app/src/main/jni/config.cpp +++ b/src/android/app/src/main/jni/config.cpp @@ -169,7 +169,7 @@ void Config::ReadValues() { // Core ReadSetting("Core", Settings::values.use_multi_core); - ReadSetting("Core", Settings::values.use_unsafe_extended_memory_layout); + ReadSetting("Core", Settings::values.memory_layout_mode); // Cpu ReadSetting("Cpu", Settings::values.cpu_accuracy); From b54c3fba6832ed5984d803f264ffdb7c0ded3cf6 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 19 Jul 2023 13:45:16 -0400 Subject: [PATCH 136/155] configure_system: Use lambda template to group settings --- src/yuzu/configuration/configure_system.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index d76630bcb..7884886c3 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -96,7 +96,7 @@ void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { std::map system_hold{}; std::forward_list settings; - auto push = [&settings](std::forward_list& list) { + auto push = [&settings](auto& list) { for (auto setting : list) { settings.push_front(setting); } From ffb384463f1f12264dbd8ad8827a8b42115921aa Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 19 Jul 2023 13:45:50 -0400 Subject: [PATCH 137/155] settings: Remove sorting from log Unecessary, and would run every time the settings are logged. --- src/common/settings.cpp | 4 ---- 1 file changed, 4 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 4c1cd1cac..0e2ccf857 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -108,10 +108,6 @@ void LogSettings() { LOG_INFO(Config, "yuzu Configuration:"); for (auto& [category, settings] : values.linkage.by_category) { - settings.sort([](const BasicSetting* a, const BasicSetting* b) { - return a->GetLabel() < b->GetLabel(); - }); - for (const auto& setting : settings) { if (setting->Id() == values.yuzu_token.Id()) { // Hide the token secret, for security reasons. From 2911988b852ec29016780aabb1f46e2d0c231744 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 19 Jul 2023 13:46:48 -0400 Subject: [PATCH 138/155] settings_common: Use a vector in category linkage Improve storage requirements. --- src/common/settings_common.cpp | 2 +- src/common/settings_common.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/common/settings_common.cpp b/src/common/settings_common.cpp index 1439fb451..90842e797 100644 --- a/src/common/settings_common.cpp +++ b/src/common/settings_common.cpp @@ -12,7 +12,7 @@ BasicSetting::BasicSetting(Linkage& linkage, const std::string& name, enum Categ : label{name}, category{category_}, id{linkage.count}, save{save_}, runtime_modifiable{runtime_modifiable_}, specialization{specialization_}, other_setting{other_setting_} { - linkage.by_category[category].push_front(this); + linkage.by_category[category].push_back(this); linkage.count++; } diff --git a/src/common/settings_common.h b/src/common/settings_common.h index a7630a97f..bfd1bad64 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -66,7 +66,7 @@ class Linkage { public: explicit Linkage(u32 initial_count = 0); ~Linkage(); - std::map> by_category{}; + std::map> by_category{}; std::vector> restore_functions{}; u32 count; }; From 17b9c1e1715a16bebcdd92c02ce7f7e503212462 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 21 Jul 2023 23:09:09 -0400 Subject: [PATCH 139/155] common,qt-config: Remove usage of forward_list --- src/common/settings.cpp | 1 - src/common/settings_common.h | 1 - .../configuration/configuration_shared.cpp | 5 +++-- src/yuzu/configuration/configuration_shared.h | 4 ++-- src/yuzu/configuration/configure_audio.cpp | 8 ++++---- src/yuzu/configuration/configure_audio.h | 6 +++--- src/yuzu/configuration/configure_cpu.cpp | 8 ++++---- src/yuzu/configuration/configure_cpu.h | 5 +++-- src/yuzu/configuration/configure_dialog.h | 3 +-- src/yuzu/configuration/configure_general.cpp | 8 ++++---- src/yuzu/configuration/configure_general.h | 5 +++-- src/yuzu/configuration/configure_graphics.cpp | 20 +++++++++---------- src/yuzu/configuration/configure_graphics.h | 4 ++-- .../configure_graphics_advanced.cpp | 4 ++-- .../configure_graphics_advanced.h | 6 +++--- src/yuzu/configuration/configure_per_game.cpp | 2 +- src/yuzu/configuration/configure_per_game.h | 3 +-- src/yuzu/configuration/configure_system.cpp | 12 +++++------ src/yuzu/configuration/configure_system.h | 6 +++--- src/yuzu/configuration/shared_widget.cpp | 8 ++++---- src/yuzu/configuration/shared_widget.h | 10 +++++----- 21 files changed, 64 insertions(+), 65 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 0e2ccf857..4a4ba307c 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -10,7 +10,6 @@ #include #include #include -#include #include #include #include diff --git a/src/common/settings_common.h b/src/common/settings_common.h index bfd1bad64..6f90ae90d 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -3,7 +3,6 @@ #pragma once -#include #include #include #include diff --git a/src/yuzu/configuration/configuration_shared.cpp b/src/yuzu/configuration/configuration_shared.cpp index 8c12d063e..0ed6146a0 100644 --- a/src/yuzu/configuration/configuration_shared.cpp +++ b/src/yuzu/configuration/configuration_shared.cpp @@ -3,13 +3,14 @@ #include #include +#include #include "yuzu/configuration/configuration_shared.h" namespace ConfigurationShared { -Tab::Tab(std::shared_ptr> group, QWidget* parent) : QWidget(parent) { +Tab::Tab(std::shared_ptr> group, QWidget* parent) : QWidget(parent) { if (group != nullptr) { - group->push_front(this); + group->push_back(this); } } diff --git a/src/yuzu/configuration/configuration_shared.h b/src/yuzu/configuration/configuration_shared.h index 2a084b584..31897a6b0 100644 --- a/src/yuzu/configuration/configuration_shared.h +++ b/src/yuzu/configuration/configuration_shared.h @@ -3,8 +3,8 @@ #pragma once -#include #include +#include #include #include #include @@ -17,7 +17,7 @@ class Tab : public QWidget { Q_OBJECT public: - explicit Tab(std::shared_ptr> group, QWidget* parent = nullptr); + explicit Tab(std::shared_ptr> group, QWidget* parent = nullptr); ~Tab(); virtual void ApplyConfiguration() = 0; diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 11714b86d..7eb752898 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -1,8 +1,8 @@ // SPDX-FileCopyrightText: Copyright 2018 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later -#include #include +#include #include #include "audio_core/sink/sink.h" @@ -17,7 +17,7 @@ #include "yuzu/uisettings.h" ConfigureAudio::ConfigureAudio(const Core::System& system_, - std::shared_ptr> group_, + std::shared_ptr> group_, const ConfigurationShared::Builder& builder, QWidget* parent) : Tab(group_, parent), ui(std::make_unique()), system{system_} { ui->setupUi(this); @@ -31,11 +31,11 @@ ConfigureAudio::~ConfigureAudio() = default; void ConfigureAudio::Setup(const ConfigurationShared::Builder& builder) { auto& layout = *ui->audio_widget->layout(); - std::forward_list settings; + std::vector settings; auto push = [&](Settings::Category category) { for (auto* setting : Settings::values.linkage.by_category[category]) { - settings.push_front(setting); + settings.push_back(setting); } }; diff --git a/src/yuzu/configuration/configure_audio.h b/src/yuzu/configuration/configure_audio.h index 94606f210..79538e81c 100644 --- a/src/yuzu/configuration/configure_audio.h +++ b/src/yuzu/configuration/configure_audio.h @@ -3,9 +3,9 @@ #pragma once -#include #include #include +#include #include #include "yuzu/configuration/configuration_shared.h" @@ -26,7 +26,7 @@ class Builder; class ConfigureAudio : public ConfigurationShared::Tab { public: explicit ConfigureAudio(const Core::System& system_, - std::shared_ptr> group, + std::shared_ptr> group, const ConfigurationShared::Builder& builder, QWidget* parent = nullptr); ~ConfigureAudio() override; @@ -51,7 +51,7 @@ private: const Core::System& system; - std::forward_list> apply_funcs{}; + std::vector> apply_funcs{}; QComboBox* sink_combo_box; QComboBox* output_device_combo_box; diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 7d122906e..8ed9a65f3 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -1,9 +1,9 @@ // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later -#include #include #include +#include #include #include "common/common_types.h" #include "common/settings.h" @@ -15,7 +15,7 @@ #include "yuzu/configuration/configure_cpu.h" ConfigureCpu::ConfigureCpu(const Core::System& system_, - std::shared_ptr> group_, + std::shared_ptr> group_, const ConfigurationShared::Builder& builder, QWidget* parent) : Tab(group_, parent), ui{std::make_unique()}, system{system_}, combobox_translations(builder.ComboboxTranslations()) { @@ -37,10 +37,10 @@ void ConfigureCpu::Setup(const ConfigurationShared::Builder& builder) { auto* unsafe_layout = ui->unsafe_widget->layout(); std::map unsafe_hold{}; - std::forward_list settings; + std::vector settings; const auto push = [&](Settings::Category category) { for (const auto setting : Settings::values.linkage.by_category[category]) { - settings.push_front(setting); + settings.push_back(setting); } }; diff --git a/src/yuzu/configuration/configure_cpu.h b/src/yuzu/configuration/configure_cpu.h index ab19c0ba1..61a6de7aa 100644 --- a/src/yuzu/configuration/configure_cpu.h +++ b/src/yuzu/configuration/configure_cpu.h @@ -4,6 +4,7 @@ #pragma once #include +#include #include #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/shared_translation.h" @@ -25,7 +26,7 @@ class Builder; class ConfigureCpu : public ConfigurationShared::Tab { public: explicit ConfigureCpu(const Core::System& system_, - std::shared_ptr> group, + std::shared_ptr> group, const ConfigurationShared::Builder& builder, QWidget* parent = nullptr); ~ConfigureCpu() override; @@ -45,7 +46,7 @@ private: const Core::System& system; const ConfigurationShared::ComboboxTranslationMap& combobox_translations; - std::forward_list> apply_funcs{}; + std::vector> apply_funcs{}; QComboBox* accuracy_combobox; }; diff --git a/src/yuzu/configuration/configure_dialog.h b/src/yuzu/configuration/configure_dialog.h index 1bfc9f9d0..96e9a8c3e 100644 --- a/src/yuzu/configuration/configure_dialog.h +++ b/src/yuzu/configuration/configure_dialog.h @@ -3,7 +3,6 @@ #pragma once -#include #include #include #include @@ -74,7 +73,7 @@ private: Core::System& system; std::unique_ptr builder; - std::forward_list tab_group; + std::vector tab_group; std::unique_ptr audio_tab; std::unique_ptr cpu_tab; diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index 54113543a..fc43a531d 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -3,6 +3,7 @@ #include #include +#include #include #include "common/settings.h" #include "core/core.h" @@ -12,10 +13,9 @@ #include "yuzu/configuration/shared_widget.h" #include "yuzu/uisettings.h" -ConfigureGeneral::ConfigureGeneral( - const Core::System& system_, - std::shared_ptr> group_, - const ConfigurationShared::Builder& builder, QWidget* parent) +ConfigureGeneral::ConfigureGeneral(const Core::System& system_, + std::shared_ptr> group_, + const ConfigurationShared::Builder& builder, QWidget* parent) : Tab(group_, parent), ui{std::make_unique()}, system{system_} { ui->setupUi(this); diff --git a/src/yuzu/configuration/configure_general.h b/src/yuzu/configuration/configure_general.h index f8ed3f8ab..2d953f679 100644 --- a/src/yuzu/configuration/configure_general.h +++ b/src/yuzu/configuration/configure_general.h @@ -5,6 +5,7 @@ #include #include +#include #include #include "yuzu/configuration/configuration_shared.h" @@ -26,7 +27,7 @@ class Builder; class ConfigureGeneral : public ConfigurationShared::Tab { public: explicit ConfigureGeneral(const Core::System& system_, - std::shared_ptr> group, + std::shared_ptr> group, const ConfigurationShared::Builder& builder, QWidget* parent = nullptr); ~ConfigureGeneral() override; @@ -46,7 +47,7 @@ private: std::unique_ptr ui; - std::forward_list> apply_funcs{}; + std::vector> apply_funcs{}; const Core::System& system; }; diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 31e87ccf5..a6f711597 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -77,11 +77,11 @@ static constexpr Settings::VSyncMode PresentModeToSetting(VkPresentModeKHR mode) } } -ConfigureGraphics::ConfigureGraphics( - const Core::System& system_, std::vector& records_, - const std::function& expose_compute_option_, - std::shared_ptr> group_, - const ConfigurationShared::Builder& builder, QWidget* parent) +ConfigureGraphics::ConfigureGraphics(const Core::System& system_, + std::vector& records_, + const std::function& expose_compute_option_, + std::shared_ptr> group_, + const ConfigurationShared::Builder& builder, QWidget* parent) : ConfigurationShared::Tab(group_, parent), ui{std::make_unique()}, records{records_}, expose_compute_option{expose_compute_option_}, system{system_}, combobox_translations{builder.ComboboxTranslations()}, @@ -228,7 +228,7 @@ void ConfigureGraphics::Setup(const ConfigurationShared::Builder& builder) { QLayout& graphics_layout = *ui->graphics_widget->layout(); std::map hold_graphics; - std::forward_list hold_api; + std::vector hold_api; for (const auto setting : Settings::values.linkage.by_category[Settings::Category::Renderer]) { ConfigurationShared::Widget* widget = [&]() { @@ -268,12 +268,12 @@ void ConfigureGraphics::Setup(const ConfigurationShared::Builder& builder) { } } else if (setting->Id() == Settings::values.vulkan_device.Id()) { // Keep track of vulkan_device's combobox so we can populate it - hold_api.push_front(widget); + hold_api.push_back(widget); vulkan_device_combobox = widget->combobox; vulkan_device_widget = widget; } else if (setting->Id() == Settings::values.shader_backend.Id()) { // Keep track of shader_backend's combobox so we can populate it - hold_api.push_front(widget); + hold_api.push_back(widget); shader_backend_combobox = widget->combobox; shader_backend_widget = widget; } else if (setting->Id() == Settings::values.vsync_mode.Id()) { @@ -296,7 +296,7 @@ void ConfigureGraphics::Setup(const ConfigurationShared::Builder& builder) { // Background color is too specific to build into the new system, so we manage it here // (3 settings, all collected into a single widget with a QColor to manage on top) if (Settings::IsConfiguringGlobal()) { - apply_funcs.push_front([this](bool powered_on) { + apply_funcs.push_back([this](bool powered_on) { Settings::values.bg_red.SetValue(static_cast(bg_color.red())); Settings::values.bg_green.SetValue(static_cast(bg_color.green())); Settings::values.bg_blue.SetValue(static_cast(bg_color.blue())); @@ -322,7 +322,7 @@ void ConfigureGraphics::Setup(const ConfigurationShared::Builder& builder) { bg_restore_button->setEnabled(true); }); - apply_funcs.push_front([bg_restore_button, this](bool powered_on) { + apply_funcs.push_back([bg_restore_button, this](bool powered_on) { const bool using_global = !bg_restore_button->isEnabled(); Settings::values.bg_red.SetGlobal(using_global); Settings::values.bg_green.SetGlobal(using_global); diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index 633a28414..02d9b00f1 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -46,7 +46,7 @@ public: explicit ConfigureGraphics(const Core::System& system_, std::vector& records, const std::function& expose_compute_option_, - std::shared_ptr> group, + std::shared_ptr> group, const ConfigurationShared::Builder& builder, QWidget* parent = nullptr); ~ConfigureGraphics() override; @@ -80,7 +80,7 @@ private: std::unique_ptr ui; QColor bg_color; - std::forward_list> apply_funcs{}; + std::vector> apply_funcs{}; std::vector& records; std::vector vulkan_devices; diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 757e4659d..f60214ff9 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -1,6 +1,7 @@ // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#include #include #include #include "common/settings.h" @@ -12,8 +13,7 @@ #include "yuzu/configuration/shared_widget.h" ConfigureGraphicsAdvanced::ConfigureGraphicsAdvanced( - const Core::System& system_, - std::shared_ptr> group_, + const Core::System& system_, std::shared_ptr> group_, const ConfigurationShared::Builder& builder, QWidget* parent) : Tab(group_, parent), ui{std::make_unique()}, system{system_} { diff --git a/src/yuzu/configuration/configure_graphics_advanced.h b/src/yuzu/configuration/configure_graphics_advanced.h index 5530827d1..78b5389c3 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.h +++ b/src/yuzu/configuration/configure_graphics_advanced.h @@ -4,6 +4,7 @@ #pragma once #include +#include #include #include "yuzu/configuration/configuration_shared.h" @@ -22,8 +23,7 @@ class Builder; class ConfigureGraphicsAdvanced : public ConfigurationShared::Tab { public: explicit ConfigureGraphicsAdvanced( - const Core::System& system_, - std::shared_ptr> group, + const Core::System& system_, std::shared_ptr> group, const ConfigurationShared::Builder& builder, QWidget* parent = nullptr); ~ConfigureGraphicsAdvanced() override; @@ -41,7 +41,7 @@ private: const Core::System& system; - std::forward_list> apply_funcs; + std::vector> apply_funcs; QWidget* checkbox_enable_compute_pipelines{}; }; diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index cee8e726d..cd8b3012e 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -44,7 +44,7 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st : QDialog(parent), ui(std::make_unique()), title_id{title_id_}, system{system_}, builder{std::make_unique(this, !system_.IsPoweredOn())}, - tab_group{std::make_shared>()} { + tab_group{std::make_shared>()} { const auto file_path = std::filesystem::path(Common::FS::ToU8String(file_name)); const auto config_file_name = title_id == 0 ? Common::FS::PathToUTF8String(file_path.filename()) : fmt::format("{:016X}", title_id); diff --git a/src/yuzu/configuration/configure_per_game.h b/src/yuzu/configuration/configure_per_game.h index 4ddd18c1f..1a727f32c 100644 --- a/src/yuzu/configuration/configure_per_game.h +++ b/src/yuzu/configuration/configure_per_game.h @@ -3,7 +3,6 @@ #pragma once -#include #include #include #include @@ -77,7 +76,7 @@ private: Core::System& system; std::unique_ptr builder; - std::shared_ptr> tab_group; + std::shared_ptr> tab_group; std::unique_ptr addons_tab; std::unique_ptr audio_tab; diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 7884886c3..93a0a4102 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -2,8 +2,8 @@ // SPDX-License-Identifier: GPL-2.0-or-later #include -#include #include +#include #include #include @@ -44,9 +44,9 @@ static bool IsValidLocale(u32 region_index, u32 language_index) { return ((LOCALE_BLOCKLIST.at(region_index) >> language_index) & 1) == 0; } -ConfigureSystem::ConfigureSystem( - Core::System& system_, std::shared_ptr> group_, - const ConfigurationShared::Builder& builder, QWidget* parent) +ConfigureSystem::ConfigureSystem(Core::System& system_, + std::shared_ptr> group_, + const ConfigurationShared::Builder& builder, QWidget* parent) : Tab(group_, parent), ui{std::make_unique()}, system{system_} { ui->setupUi(this); @@ -95,10 +95,10 @@ void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { std::map core_hold{}; std::map system_hold{}; - std::forward_list settings; + std::vector settings; auto push = [&settings](auto& list) { for (auto setting : list) { - settings.push_front(setting); + settings.push_back(setting); } }; diff --git a/src/yuzu/configuration/configure_system.h b/src/yuzu/configuration/configure_system.h index f63aedda0..eab99a48a 100644 --- a/src/yuzu/configuration/configure_system.h +++ b/src/yuzu/configuration/configure_system.h @@ -3,9 +3,9 @@ #pragma once -#include #include #include +#include #include #include "yuzu/configuration/configuration_shared.h" @@ -29,7 +29,7 @@ class Builder; class ConfigureSystem : public ConfigurationShared::Tab { public: explicit ConfigureSystem(Core::System& system_, - std::shared_ptr> group, + std::shared_ptr> group, const ConfigurationShared::Builder& builder, QWidget* parent = nullptr); ~ConfigureSystem() override; @@ -43,7 +43,7 @@ private: void Setup(const ConfigurationShared::Builder& builder); - std::forward_list> apply_funcs{}; + std::vector> apply_funcs{}; std::unique_ptr ui; bool enabled = false; diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index c9ab461f6..cf33bce2b 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -547,7 +547,7 @@ Widget::~Widget() = default; Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translations_, const ComboboxTranslationMap& combobox_translations_, QWidget* parent_, - bool runtime_lock_, std::forward_list>& apply_funcs_, + bool runtime_lock_, std::vector>& apply_funcs_, RequestType request, bool managed, float multiplier, Settings::BasicSetting* other_setting, const QString& suffix) : QWidget(parent_), parent{parent_}, translations{translations_}, @@ -584,7 +584,7 @@ Widget::Widget(Settings::BasicSetting* setting_, const TranslationMap& translati return; } - apply_funcs.push_front([load_func, setting_](bool powered_on) { + apply_funcs.push_back([load_func, setting_](bool powered_on) { if (setting_->RuntimeModfiable() || !powered_on) { load_func(); } @@ -607,7 +607,7 @@ Builder::Builder(QWidget* parent_, bool runtime_lock_) Builder::~Builder() = default; Widget* Builder::BuildWidget(Settings::BasicSetting* setting, - std::forward_list>& apply_funcs, + std::vector>& apply_funcs, RequestType request, bool managed, float multiplier, Settings::BasicSetting* other_setting, const QString& suffix) const { if (!Settings::IsConfiguringGlobal() && !setting->Switchable()) { @@ -624,7 +624,7 @@ Widget* Builder::BuildWidget(Settings::BasicSetting* setting, } Widget* Builder::BuildWidget(Settings::BasicSetting* setting, - std::forward_list>& apply_funcs, + std::vector>& apply_funcs, Settings::BasicSetting* other_setting, RequestType request, const QString& suffix) const { return BuildWidget(setting, apply_funcs, request, true, 1.0f, other_setting, suffix); diff --git a/src/yuzu/configuration/shared_widget.h b/src/yuzu/configuration/shared_widget.h index b3f9efd78..e64693bab 100644 --- a/src/yuzu/configuration/shared_widget.h +++ b/src/yuzu/configuration/shared_widget.h @@ -3,10 +3,10 @@ #pragma once -#include #include #include #include +#include #include #include #include @@ -62,7 +62,7 @@ public: */ explicit Widget(Settings::BasicSetting* setting, const TranslationMap& translations, const ComboboxTranslationMap& combobox_translations, QWidget* parent, - bool runtime_lock, std::forward_list>& apply_funcs_, + bool runtime_lock, std::vector>& apply_funcs_, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, Settings::BasicSetting* other_setting = nullptr, const QString& suffix = QStringLiteral("")); @@ -125,7 +125,7 @@ private: const TranslationMap& translations; const ComboboxTranslationMap& combobox_enumerations; Settings::BasicSetting& setting; - std::forward_list>& apply_funcs; + std::vector>& apply_funcs; bool created{false}; bool runtime_lock{false}; @@ -137,13 +137,13 @@ public: ~Builder(); Widget* BuildWidget(Settings::BasicSetting* setting, - std::forward_list>& apply_funcs, + std::vector>& apply_funcs, RequestType request = RequestType::Default, bool managed = true, float multiplier = 1.0f, Settings::BasicSetting* other_setting = nullptr, const QString& suffix = QStringLiteral("")) const; Widget* BuildWidget(Settings::BasicSetting* setting, - std::forward_list>& apply_funcs, + std::vector>& apply_funcs, Settings::BasicSetting* other_setting, RequestType request = RequestType::Default, const QString& suffix = QStringLiteral("")) const; From 1d4f813c6ab59ffe41ccd9be27786aeab344a1f4 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 21 Jul 2023 23:25:22 -0400 Subject: [PATCH 140/155] qt/configuration: Use deleteLater --- src/yuzu/configuration/configure_audio.cpp | 2 +- src/yuzu/configuration/configure_cpu.cpp | 2 +- src/yuzu/configuration/configure_general.cpp | 2 +- src/yuzu/configuration/configure_graphics.cpp | 2 +- src/yuzu/configuration/configure_graphics_advanced.cpp | 2 +- src/yuzu/configuration/configure_system.cpp | 4 ++-- 6 files changed, 7 insertions(+), 7 deletions(-) diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index 7eb752898..d32328087 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -49,7 +49,7 @@ void ConfigureAudio::Setup(const ConfigurationShared::Builder& builder) { continue; } if (!widget->Valid()) { - delete widget; + widget->deleteLater(); continue; } diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 8ed9a65f3..08f2b4d9c 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -54,7 +54,7 @@ void ConfigureCpu::Setup(const ConfigurationShared::Builder& builder) { continue; } if (!widget->Valid()) { - delete widget; + widget->deleteLater(); continue; } diff --git a/src/yuzu/configuration/configure_general.cpp b/src/yuzu/configuration/configure_general.cpp index fc43a531d..c727fadd1 100644 --- a/src/yuzu/configuration/configure_general.cpp +++ b/src/yuzu/configuration/configure_general.cpp @@ -48,7 +48,7 @@ void ConfigureGeneral::Setup(const ConfigurationShared::Builder& builder) { continue; } if (!widget->Valid()) { - delete widget; + widget->deleteLater(); continue; } diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index a6f711597..a94fbc89a 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -246,7 +246,7 @@ void ConfigureGraphics::Setup(const ConfigurationShared::Builder& builder) { continue; } if (!widget->Valid()) { - delete widget; + widget->deleteLater(); continue; } diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index f60214ff9..4db18673d 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -42,7 +42,7 @@ void ConfigureGraphicsAdvanced::Setup(const ConfigurationShared::Builder& builde continue; } if (!widget->Valid()) { - delete widget; + widget->deleteLater(); continue; } diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 93a0a4102..c4833f4e7 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -112,7 +112,7 @@ void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { continue; } if (!widget->Valid()) { - delete widget; + widget->deleteLater(); continue; } @@ -132,7 +132,7 @@ void ConfigureSystem::Setup(const ConfigurationShared::Builder& builder) { system_hold.emplace(setting->Id(), widget); break; default: - delete widget; + widget->deleteLater(); } } for (const auto& [label, widget] : core_hold) { From 33d118509ad201cecf60519e41437740705148ea Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Fri, 21 Jul 2023 23:56:01 -0400 Subject: [PATCH 141/155] configure_dialog: Focus the button box on start Without this, the Reset All Settings button would be selected by default --- src/yuzu/configuration/configure_dialog.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index 183555acd..3c6bb3eb1 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -97,6 +97,9 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, adjustSize(); ui->selectorList->setCurrentRow(0); + + // Selects the leftmost button on the bottom bar (Cancel as of writing) + ui->buttonBox->setFocus(); } ConfigureDialog::~ConfigureDialog() = default; From 85ed10f31f0aae93a12bc7e79bb98b9b2aac20bb Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 22 Jul 2023 00:42:15 -0400 Subject: [PATCH 142/155] configure_audio/cpu: Sort settings Was producing out of order settings as a result of the switch to vectors --- src/yuzu/configuration/configure_audio.cpp | 11 ++++++++++- src/yuzu/configuration/configure_cpu.cpp | 4 ++-- 2 files changed, 12 insertions(+), 3 deletions(-) diff --git a/src/yuzu/configuration/configure_audio.cpp b/src/yuzu/configuration/configure_audio.cpp index d32328087..9ccfb2435 100644 --- a/src/yuzu/configuration/configure_audio.cpp +++ b/src/yuzu/configuration/configure_audio.cpp @@ -1,13 +1,16 @@ // SPDX-FileCopyrightText: Copyright 2018 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later +#include #include #include #include #include "audio_core/sink/sink.h" #include "audio_core/sink/sink_details.h" +#include "common/common_types.h" #include "common/settings.h" +#include "common/settings_common.h" #include "core/core.h" #include "ui_configure_audio.h" #include "yuzu/configuration/configuration_shared.h" @@ -33,6 +36,8 @@ void ConfigureAudio::Setup(const ConfigurationShared::Builder& builder) { std::vector settings; + std::map hold; + auto push = [&](Settings::Category category) { for (auto* setting : Settings::values.linkage.by_category[category]) { settings.push_back(setting); @@ -53,7 +58,7 @@ void ConfigureAudio::Setup(const ConfigurationShared::Builder& builder) { continue; } - layout.addWidget(widget); + hold.emplace(std::pair{setting->Id(), widget}); if (setting->Id() == Settings::values.sink_id.Id()) { // TODO (lat9nq): Let the system manage sink_id @@ -70,6 +75,10 @@ void ConfigureAudio::Setup(const ConfigurationShared::Builder& builder) { input_device_combo_box = widget->combobox; } } + + for (const auto& [id, widget] : hold) { + layout.addWidget(widget); + } } void ConfigureAudio::SetConfiguration() { diff --git a/src/yuzu/configuration/configure_cpu.cpp b/src/yuzu/configuration/configure_cpu.cpp index 08f2b4d9c..a51359903 100644 --- a/src/yuzu/configuration/configure_cpu.cpp +++ b/src/yuzu/configuration/configure_cpu.cpp @@ -35,7 +35,7 @@ void ConfigureCpu::SetConfiguration() {} void ConfigureCpu::Setup(const ConfigurationShared::Builder& builder) { auto* accuracy_layout = ui->widget_accuracy->layout(); auto* unsafe_layout = ui->unsafe_widget->layout(); - std::map unsafe_hold{}; + std::map unsafe_hold{}; std::vector settings; const auto push = [&](Settings::Category category) { @@ -64,7 +64,7 @@ void ConfigureCpu::Setup(const ConfigurationShared::Builder& builder) { accuracy_combobox = widget->combobox; } else { // Presently, all other settings here are unsafe checkboxes - unsafe_hold.insert({setting->GetLabel(), widget}); + unsafe_hold.insert({setting->Id(), widget}); } } From fb7da1fa11901b38e4e1ff4d0295fac6aad018db Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 22 Jul 2023 14:50:32 -0400 Subject: [PATCH 143/155] config: Read the Network category --- src/yuzu/configuration/config.cpp | 11 +++++++++++ src/yuzu/configuration/config.h | 1 + 2 files changed, 12 insertions(+) diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 5755e5b2d..f2ef34cbc 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -8,6 +8,7 @@ #include "common/fs/fs.h" #include "common/fs/path_util.h" #include "common/settings.h" +#include "common/settings_common.h" #include "core/core.h" #include "core/hle/service/acc/profile_manager.h" #include "core/hle/service/hid/controllers/npad.h" @@ -725,11 +726,21 @@ void Config::ReadMultiplayerValues() { qt_config->endGroup(); } +void Config::ReadNetworkValues() { + qt_config->beginGroup( + QString::fromUtf8(Settings::TranslateCategory(Settings::Category::Network))); + + ReadCategory(Settings::Category::Network); + + qt_config->endGroup(); +} + void Config::ReadValues() { if (global) { ReadDataStorageValues(); ReadDebuggingValues(); ReadDisabledAddOnValues(); + ReadNetworkValues(); ReadServiceValues(); ReadUIValues(); ReadWebServiceValues(); diff --git a/src/yuzu/configuration/config.h b/src/yuzu/configuration/config.h index a68f291a2..0ac74c8e7 100644 --- a/src/yuzu/configuration/config.h +++ b/src/yuzu/configuration/config.h @@ -98,6 +98,7 @@ private: void ReadUILayoutValues(); void ReadWebServiceValues(); void ReadMultiplayerValues(); + void ReadNetworkValues(); void SaveValues(); void SavePlayerValue(std::size_t player_index); From fc1bb93b01cea583bfae3743f973796a37cdeb6b Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 22 Jul 2023 15:07:34 -0400 Subject: [PATCH 144/155] shared_widget: Use QRegularExpression --- src/yuzu/configuration/shared_widget.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index cf33bce2b..74985129b 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -23,7 +23,7 @@ #include #include #include -#include +#include #include #include #include @@ -295,8 +295,8 @@ QWidget* Widget::CreateHexEdit(std::function& serializer, return QString::fromStdString(fmt::format("{:08x}", std::stoul(input))); }; - QRegExpValidator* regex = - new QRegExpValidator{QRegExp{QStringLiteral("^[0-9a-fA-F]{0,8}$")}, line_edit}; + QRegularExpressionValidator* regex = new QRegularExpressionValidator( + QRegularExpression{QStringLiteral("^[0-9a-fA-F]{0,8}$")}, line_edit); const QString default_val = to_hex(setting.ToString()); From f84e7b4656f1e69cced4e58117df920efaec922e Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 23 Jul 2023 16:21:08 -0400 Subject: [PATCH 145/155] settings_common: Document specializations --- src/common/settings_common.h | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/src/common/settings_common.h b/src/common/settings_common.h index 6f90ae90d..2efb329b0 100644 --- a/src/common/settings_common.h +++ b/src/common/settings_common.h @@ -46,17 +46,18 @@ constexpr u8 SpecializationTypeMask = 0xf; constexpr u8 SpecializationAttributeMask = 0xf0; constexpr u8 SpecializationAttributeOffset = 4; +// Scalar and countable could have better names enum Specialization : u8 { Default = 0, - Time = 1, - Hex = 2, - List = 3, - RuntimeList = 4, - Scalar = 5, - Countable = 6, - Paired = 7, + Time = 1, // Duration or specific moment in time + Hex = 2, // Hexadecimal number + List = 3, // Setting has specific members + RuntimeList = 4, // Members of the list are determined during runtime + Scalar = 5, // Values are continuous + Countable = 6, // Can be stepped through + Paired = 7, // Another setting is associated with this setting - Percentage = (1 << SpecializationAttributeOffset), + Percentage = (1 << SpecializationAttributeOffset), // Should be represented as a percentage }; class BasicSetting; From ab2921121ec89feb8a926648728beee1551edcf3 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 23 Jul 2023 17:08:25 -0400 Subject: [PATCH 146/155] shared_widget: Determine default request earlier Fixes a bug where a restore button could be created for an unmanaged widget. --- src/yuzu/configuration/shared_widget.cpp | 41 +++++++++++++----------- 1 file changed, 22 insertions(+), 19 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 74985129b..410fa80cd 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -390,25 +390,6 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu QWidget* data_component{nullptr}; - if (!Settings::IsConfiguringGlobal() && managed) { - restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); - - touch = [this]() { - LOG_DEBUG(Frontend, "Enabling custom setting for \"{}\"", setting.GetLabel()); - restore_button->setEnabled(true); - restore_button->setVisible(true); - }; - } - - if (require_checkbox) { - QWidget* lhs = - CreateCheckBox(other_setting, label, checkbox_serializer, checkbox_restore_func, touch); - layout->addWidget(lhs); - } else if (setting.TypeId() != typeid(bool)) { - QLabel* qt_label = CreateLabel(label); - layout->addWidget(qt_label); - } - request = [&]() { if (request != RequestType::Default) { return request; @@ -435,6 +416,25 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu return request; }(); + if (!Settings::IsConfiguringGlobal() && managed) { + restore_button = CreateRestoreGlobalButton(setting.UsingGlobal(), this); + + touch = [this]() { + LOG_DEBUG(Frontend, "Enabling custom setting for \"{}\"", setting.GetLabel()); + restore_button->setEnabled(true); + restore_button->setVisible(true); + }; + } + + if (require_checkbox) { + QWidget* lhs = + CreateCheckBox(other_setting, label, checkbox_serializer, checkbox_restore_func, touch); + layout->addWidget(lhs); + } else if (setting.TypeId() != typeid(bool)) { + QLabel* qt_label = CreateLabel(label); + layout->addWidget(qt_label); + } + if (setting.TypeId() == typeid(bool)) { data_component = CreateCheckBox(&setting, label, serializer, restore_func, touch); } else if (setting.IsEnum()) { @@ -505,6 +505,9 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu QObject::connect(restore_button, &QAbstractButton::clicked, [this, restore_func, checkbox_restore_func](bool) { + LOG_DEBUG(Frontend, "Restore global state for \"{}\"", + setting.GetLabel()); + restore_button->setEnabled(false); restore_button->setVisible(false); From b1716a9e147f744dfe4bd977f4a5af12f3a2ec0f Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Mon, 24 Jul 2023 16:28:13 -0400 Subject: [PATCH 147/155] settings: Set GPU as default ASTC decoder --- src/common/settings.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/common/settings.h b/src/common/settings.h index 655f6468a..43ebeae9e 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -226,7 +226,7 @@ struct Values { SwitchableSetting use_asynchronous_gpu_emulation{ linkage, true, "use_asynchronous_gpu_emulation", Category::Renderer}; SwitchableSetting accelerate_astc{linkage, - AstcDecodeMode::Cpu, + AstcDecodeMode::Gpu, AstcDecodeMode::Cpu, AstcDecodeMode::CpuAsynchronous, "accelerate_astc", From 397333b2d51fc93c1285465f43668fb86e709fc3 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 25 Jul 2023 15:57:55 -0400 Subject: [PATCH 148/155] settings: Correct Linkage member impl location --- src/common/settings.cpp | 3 --- src/common/settings_common.cpp | 3 +++ 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 4a4ba307c..491adc30e 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -151,9 +151,6 @@ float Volume() { return values.volume.GetValue() / static_cast(values.volume.GetDefault()); } -Linkage::Linkage(u32 initial_count) : count{initial_count} {} -Linkage::~Linkage() = default; - const char* TranslateCategory(Category category) { switch (category) { case Category::Audio: diff --git a/src/common/settings_common.cpp b/src/common/settings_common.cpp index 90842e797..dedf5ef90 100644 --- a/src/common/settings_common.cpp +++ b/src/common/settings_common.cpp @@ -52,4 +52,7 @@ const std::string& BasicSetting::GetLabel() const { return label; } +Linkage::Linkage(u32 initial_count) : count{initial_count} {} +Linkage::~Linkage() = default; + } // namespace Settings From 1bc0b673aa2fc0510d332286e49f6c8d44568065 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 25 Jul 2023 22:31:21 -0400 Subject: [PATCH 149/155] backend: Remove usage of explicit operator overload Causes a crash on MSVC from a race condition on application quit. Intended to address yuzu-emu/yuzu/issues/11137 --- src/common/logging/backend.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/common/logging/backend.cpp b/src/common/logging/backend.cpp index 6e8e8eb36..d4f27197c 100644 --- a/src/common/logging/backend.cpp +++ b/src/common/logging/backend.cpp @@ -108,7 +108,7 @@ public: using namespace Common::Literals; // Prevent logs from exceeding a set maximum size in the event that log entries are spammed. - const auto write_limit = Settings::values.extended_logging ? 1_GiB : 100_MiB; + const auto write_limit = Settings::values.extended_logging.GetValue() ? 1_GiB : 100_MiB; const bool write_limit_exceeded = bytes_written > write_limit; if (entry.log_level >= Level::Error || write_limit_exceeded) { if (write_limit_exceeded) { From 195403c87cf17e91c686fc98c27429d23974af73 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Tue, 25 Jul 2023 23:13:54 -0400 Subject: [PATCH 150/155] (ui)settings: Add more runtime_modifiable settings --- src/common/settings.h | 9 +++++---- src/yuzu/uisettings.h | 29 +++++++++++++++++++++++------ 2 files changed, 28 insertions(+), 10 deletions(-) diff --git a/src/common/settings.h b/src/common/settings.h index 43ebeae9e..b0bc6519a 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -134,9 +134,10 @@ struct Values { Specialization::RuntimeList}; Setting audio_input_device_id{linkage, "auto", "input_device", Category::Audio, Specialization::RuntimeList}; - SwitchableSetting sound_index{linkage, AudioMode::Stereo, - AudioMode::Mono, AudioMode::Surround, - "sound_index", Category::SystemAudio}; + SwitchableSetting sound_index{ + linkage, AudioMode::Stereo, AudioMode::Mono, AudioMode::Surround, + "sound_index", Category::SystemAudio, Specialization::Default, true, + true}; SwitchableSetting volume{linkage, 100, 0, @@ -147,7 +148,7 @@ struct Values { true, true}; Setting audio_muted{ - linkage, false, "audio_muted", Category::Audio, Specialization::Default, false}; + linkage, false, "audio_muted", Category::Audio, Specialization::Default, false, true}; Setting dump_audio_commands{ linkage, false, "dump_audio_commands", Category::Audio, Specialization::Default, false}; diff --git a/src/yuzu/uisettings.h b/src/yuzu/uisettings.h index ee8c9f214..c9c89cee4 100644 --- a/src/yuzu/uisettings.h +++ b/src/yuzu/uisettings.h @@ -90,18 +90,35 @@ struct Values { Setting show_filter_bar{linkage, true, "showFilterBar", Category::Ui}; Setting show_status_bar{linkage, true, "showStatusBar", Category::Ui}; - Setting confirm_before_closing{linkage, true, "confirmClose", Category::UiGeneral}; + Setting confirm_before_closing{ + linkage, true, "confirmClose", Category::UiGeneral, Settings::Specialization::Default, + true, true}; Setting first_start{linkage, true, "firstStart", Category::Ui}; - Setting pause_when_in_background{linkage, false, "pauseWhenInBackground", - Category::UiGeneral}; - Setting mute_when_in_background{linkage, false, "muteWhenInBackground", Category::Ui}; - Setting hide_mouse{linkage, true, "hideInactiveMouse", Category::UiGeneral}; + Setting pause_when_in_background{linkage, + false, + "pauseWhenInBackground", + Category::UiGeneral, + Settings::Specialization::Default, + true, + true}; + Setting mute_when_in_background{ + linkage, false, "muteWhenInBackground", Category::Ui, Settings::Specialization::Default, + true, true}; + Setting hide_mouse{ + linkage, true, "hideInactiveMouse", Category::UiGeneral, Settings::Specialization::Default, + true, true}; Setting controller_applet_disabled{linkage, false, "disableControllerApplet", Category::UiGeneral}; // Set when Vulkan is known to crash the application bool has_broken_vulkan = false; - Setting select_user_on_boot{linkage, false, "select_user_on_boot", Category::UiGeneral}; + Setting select_user_on_boot{linkage, + false, + "select_user_on_boot", + Category::UiGeneral, + Settings::Specialization::Default, + true, + true}; Setting disable_web_applet{linkage, true, "disable_web_applet", Category::Ui}; // Discord RPC From 05c8063ac131ef5087f645c57b649157099f786b Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sat, 29 Jul 2023 13:23:06 -0400 Subject: [PATCH 151/155] config(qt): Fix generic read setting Previously was not respecting whether the setting was default. --- src/yuzu/configuration/config.cpp | 18 +++++++++++------- 1 file changed, 11 insertions(+), 7 deletions(-) diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index f2ef34cbc..785716735 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -1256,23 +1256,27 @@ void Config::WriteCategory(Settings::Category category) { } void Config::ReadSettingGeneric(Settings::BasicSetting* const setting) { - if (!setting->Save()) { + if (!setting->Save() || (!setting->Switchable() && !global)) { return; } const QString name = QString::fromStdString(setting->GetLabel()); const auto default_value = QVariant::fromValue(QString::fromStdString(setting->DefaultToString())); - if (setting->Switchable()) { - const bool use_global = - qt_config->value(name + QStringLiteral("/use_global"), true).value(); + bool use_global = true; + if (setting->Switchable() && !global) { + use_global = qt_config->value(name + QStringLiteral("/use_global"), true).value(); setting->SetGlobal(use_global); + } - if (global || !use_global) { + if (global || !use_global) { + const bool is_default = ReadSetting(name + QStringLiteral("/default"), true).value(); + if (!is_default) { setting->LoadString(ReadSetting(name, default_value).value().toStdString()); + } else { + // Empty string resets the Setting to default + setting->LoadString(""); } - } else if (global) { - setting->LoadString(ReadSetting(name, default_value).value().toStdString()); } } From 55c0b55d1d34c9f9c2b0309ee4e7533d9a535ed0 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 30 Jul 2023 12:09:32 -0400 Subject: [PATCH 152/155] config(qt): Write the UiGeneral category --- src/yuzu/configuration/config.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 785716735..880e5f4d6 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -1090,6 +1090,7 @@ void Config::SaveUIValues() { qt_config->beginGroup(QStringLiteral("UI")); WriteCategory(Settings::Category::Ui); + WriteCategory(Settings::Category::UiGeneral); WriteSetting(QStringLiteral("theme"), UISettings::values.theme, QString::fromUtf8(UISettings::themes[static_cast(default_theme)].second)); From 7aa848080df1e5672e6df2231f16fa37d68c03bc Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Sun, 30 Jul 2023 12:26:55 -0400 Subject: [PATCH 153/155] shared_widget: Only save global settings as needed Fixes a potential but not reproduced issue where the custom config is being applied to the global config. --- src/yuzu/configuration/shared_widget.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/yuzu/configuration/shared_widget.cpp b/src/yuzu/configuration/shared_widget.cpp index 410fa80cd..bdb38c8ea 100644 --- a/src/yuzu/configuration/shared_widget.cpp +++ b/src/yuzu/configuration/shared_widget.cpp @@ -495,10 +495,12 @@ void Widget::SetupComponent(const QString& label, std::function& load_fu if (Settings::IsConfiguringGlobal()) { load_func = [this, serializer, checkbox_serializer, require_checkbox, other_setting]() { - if (require_checkbox) { + if (require_checkbox && other_setting->UsingGlobal()) { other_setting->LoadString(checkbox_serializer()); } - setting.LoadString(serializer()); + if (setting.UsingGlobal()) { + setting.LoadString(serializer()); + } }; } else { layout->addWidget(restore_button); From 09e265c116ecbdcb61d9d26a1eb886abe2a6d05c Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 2 Aug 2023 12:20:19 -0400 Subject: [PATCH 154/155] config(qt): Use qt_config directly to read config ReadSetting with the default is a convenience function reading settings, not for use in an internal environment. It tries to manage the default value of a setting. --- src/yuzu/configuration/config.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 880e5f4d6..01310733d 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -1271,9 +1271,11 @@ void Config::ReadSettingGeneric(Settings::BasicSetting* const setting) { } if (global || !use_global) { - const bool is_default = ReadSetting(name + QStringLiteral("/default"), true).value(); + const bool is_default = + qt_config->value(name + QStringLiteral("/default"), true).value(); if (!is_default) { - setting->LoadString(ReadSetting(name, default_value).value().toStdString()); + setting->LoadString( + qt_config->value(name, default_value).value().toStdString()); } else { // Empty string resets the Setting to default setting->LoadString(""); From 32b4d63a5bdc838c26582235b9bf16bde300a760 Mon Sep 17 00:00:00 2001 From: lat9nq <22451773+lat9nq@users.noreply.github.com> Date: Wed, 2 Aug 2023 12:21:43 -0400 Subject: [PATCH 155/155] config(qt): Fix name of network category Turns out the network interface is in the Services category. Can't wait get rid of this whole config. Addresses yuzu-emu/yuzu/issues/11205 --- src/yuzu/configuration/config.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 01310733d..b2405f9b8 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -727,8 +727,7 @@ void Config::ReadMultiplayerValues() { } void Config::ReadNetworkValues() { - qt_config->beginGroup( - QString::fromUtf8(Settings::TranslateCategory(Settings::Category::Network))); + qt_config->beginGroup(QString::fromStdString("Services")); ReadCategory(Settings::Category::Network);