diff --git a/Source/Core/DolphinLib.props b/Source/Core/DolphinLib.props
index 5f1c59ac4d..854ce72ef3 100644
--- a/Source/Core/DolphinLib.props
+++ b/Source/Core/DolphinLib.props
@@ -697,6 +697,7 @@
+
@@ -1338,6 +1339,7 @@
+
diff --git a/Source/Core/VideoCommon/CMakeLists.txt b/Source/Core/VideoCommon/CMakeLists.txt
index e24680185e..3cfe4b1a87 100644
--- a/Source/Core/VideoCommon/CMakeLists.txt
+++ b/Source/Core/VideoCommon/CMakeLists.txt
@@ -85,6 +85,8 @@ add_library(videocommon
GraphicsModSystem/Runtime/Actions/PrintAction.h
GraphicsModSystem/Runtime/Actions/ScaleAction.cpp
GraphicsModSystem/Runtime/Actions/ScaleAction.h
+ GraphicsModSystem/Runtime/Actions/SetSettingsAction.cpp
+ GraphicsModSystem/Runtime/Actions/SetSettingsAction.h
GraphicsModSystem/Runtime/Actions/SkipAction.cpp
GraphicsModSystem/Runtime/Actions/SkipAction.h
GraphicsModSystem/Runtime/CustomPipeline.cpp
diff --git a/Source/Core/VideoCommon/GraphicsModSystem/Runtime/Actions/SetSettingsAction.cpp b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/Actions/SetSettingsAction.cpp
new file mode 100644
index 0000000000..1bfcc09aab
--- /dev/null
+++ b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/Actions/SetSettingsAction.cpp
@@ -0,0 +1,98 @@
+// Copyright 2023 Dolphin Emulator Project
+// SPDX-License-Identifier: GPL-2.0-or-later
+
+#include "VideoCommon/GraphicsModSystem/Runtime/Actions/SetSettingsAction.h"
+
+#include
+
+#include "Common/Config/Config.h"
+#include "Core/Config/GraphicsSettings.h"
+
+namespace
+{
+template
+class SetSettingsActionImpl final : public SetSettingsAction
+{
+public:
+ SetSettingsActionImpl(const Config::Info& setting, const picojson::value& json_data);
+
+ void OnDrawStarted(GraphicsModActionData::DrawStarted*) override;
+ void OnTextureLoad(GraphicsModActionData::TextureLoad*) override;
+ void OnEFB(GraphicsModActionData::EFB*) override;
+ void OnXFB(GraphicsModActionData::XFB*) override;
+
+private:
+ const Config::Info& m_setting;
+ T m_value;
+};
+
+template
+SetSettingsActionImpl::SetSettingsActionImpl(const Config::Info& setting,
+ const picojson::value& json_data)
+ : m_setting(setting)
+{
+ const auto& setting_value = json_data.get("setting_value");
+ if (setting_value.is())
+ m_value = setting_value.get();
+ else
+ m_value = Config::Get(setting);
+}
+
+template
+void SetSettingsActionImpl::OnDrawStarted(GraphicsModActionData::DrawStarted* draw_started)
+{
+ if (draw_started == nullptr) [[unlikely]]
+ return;
+
+ Config::SetBaseOrCurrent(m_setting, m_value);
+}
+
+template
+void SetSettingsActionImpl::OnTextureLoad(GraphicsModActionData::TextureLoad* texture_load)
+{
+ if (texture_load == nullptr) [[unlikely]]
+ return;
+
+ Config::SetBaseOrCurrent(m_setting, m_value);
+}
+
+template
+void SetSettingsActionImpl::OnEFB(GraphicsModActionData::EFB* efb)
+{
+ if (efb == nullptr) [[unlikely]]
+ return;
+
+ if (&m_setting == &Config::GFX_HACK_SKIP_EFB_COPY_TO_RAM)
+ *efb->force_copy_to_ram = !m_value;
+}
+
+template
+void SetSettingsActionImpl::OnXFB(GraphicsModActionData::XFB* xfb)
+{
+ if (xfb == nullptr) [[unlikely]]
+ return;
+
+ if (&m_setting == &Config::GFX_HACK_SKIP_XFB_COPY_TO_RAM)
+ *xfb->force_copy_to_ram = !m_value;
+}
+} // namespace
+
+std::unique_ptr SetSettingsAction::Create(const picojson::value& json_data)
+{
+ const auto& setting_name = json_data.get("setting_name");
+ if (!setting_name.is())
+ return nullptr;
+
+ const auto make_unique_ptr = [&json_data](const auto& setting) {
+ using setting_type = decltype(setting.GetCachedValue().value);
+ return std::make_unique>(setting, json_data);
+ };
+
+ const std::string setting_name_str = setting_name.to_str();
+ if (setting_name_str == "skip_efb_to_ram")
+ return make_unique_ptr(Config::GFX_HACK_SKIP_EFB_COPY_TO_RAM);
+ else if (setting_name_str == "skip_xfb_to_ram")
+ return make_unique_ptr(Config::GFX_HACK_SKIP_XFB_COPY_TO_RAM);
+
+ return nullptr;
+}
diff --git a/Source/Core/VideoCommon/GraphicsModSystem/Runtime/Actions/SetSettingsAction.h b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/Actions/SetSettingsAction.h
new file mode 100644
index 0000000000..6f1585e0f6
--- /dev/null
+++ b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/Actions/SetSettingsAction.h
@@ -0,0 +1,19 @@
+// Copyright 2023 Dolphin Emulator Project
+// SPDX-License-Identifier: GPL-2.0-or-later
+
+#pragma once
+
+#include
+
+#include "VideoCommon/GraphicsModSystem/Runtime/GraphicsModAction.h"
+
+namespace picojson
+{
+class value;
+}
+
+class SetSettingsAction : public GraphicsModAction
+{
+public:
+ static std::unique_ptr Create(const picojson::value& json_data);
+};
diff --git a/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModAction.h b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModAction.h
index 04a371a73e..cbf129a729 100644
--- a/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModAction.h
+++ b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModAction.h
@@ -17,7 +17,7 @@ public:
virtual void OnDrawStarted(GraphicsModActionData::DrawStarted*) {}
virtual void OnEFB(GraphicsModActionData::EFB*) {}
- virtual void OnXFB() {}
+ virtual void OnXFB(GraphicsModActionData::XFB*) {}
virtual void OnProjection(GraphicsModActionData::Projection*) {}
virtual void OnProjectionAndTexture(GraphicsModActionData::Projection*) {}
virtual void OnTextureLoad(GraphicsModActionData::TextureLoad*) {}
diff --git a/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModActionData.h b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModActionData.h
index cecd0ce94f..c35b28e299 100644
--- a/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModActionData.h
+++ b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModActionData.h
@@ -32,6 +32,12 @@ struct EFB
bool* skip;
u32* scaled_width;
u32* scaled_height;
+ bool* force_copy_to_ram;
+};
+
+struct XFB
+{
+ bool* force_copy_to_ram;
};
struct Projection
diff --git a/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModActionFactory.cpp b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModActionFactory.cpp
index 1059595ef1..0295d0f4e2 100644
--- a/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModActionFactory.cpp
+++ b/Source/Core/VideoCommon/GraphicsModSystem/Runtime/GraphicsModActionFactory.cpp
@@ -7,6 +7,7 @@
#include "VideoCommon/GraphicsModSystem/Runtime/Actions/MoveAction.h"
#include "VideoCommon/GraphicsModSystem/Runtime/Actions/PrintAction.h"
#include "VideoCommon/GraphicsModSystem/Runtime/Actions/ScaleAction.h"
+#include "VideoCommon/GraphicsModSystem/Runtime/Actions/SetSettingsAction.h"
#include "VideoCommon/GraphicsModSystem/Runtime/Actions/SkipAction.h"
namespace GraphicsModActionFactory
@@ -34,6 +35,10 @@ std::unique_ptr Create(std::string_view name, const picojson:
{
return CustomPipelineAction::Create(json_data, std::move(library));
}
+ else if (name == "set_settings")
+ {
+ return SetSettingsAction::Create(json_data);
+ }
return nullptr;
}
diff --git a/Source/Core/VideoCommon/TextureCacheBase.cpp b/Source/Core/VideoCommon/TextureCacheBase.cpp
index b99533eb02..eecdaced12 100644
--- a/Source/Core/VideoCommon/TextureCacheBase.cpp
+++ b/Source/Core/VideoCommon/TextureCacheBase.cpp
@@ -2305,21 +2305,37 @@ void TextureCacheBase::CopyRenderTargetToTexture(
info.m_width = tex_w;
info.m_height = tex_h;
info.m_texture_format = baseFormat;
+
+ bool force_copy_to_ram = false;
if (is_xfb_copy)
{
+ GraphicsModActionData::XFB xfb{.force_copy_to_ram = &force_copy_to_ram};
for (const auto& action : g_graphics_mod_manager->GetXFBActions(info))
{
- action->OnXFB();
+ action->OnXFB(&xfb);
+ }
+ if (force_copy_to_ram)
+ {
+ copy_to_ram = true;
}
}
else
{
bool skip = false;
- GraphicsModActionData::EFB efb{tex_w, tex_h, &skip, &scaled_tex_w, &scaled_tex_h};
+ GraphicsModActionData::EFB efb{.texture_width = tex_w,
+ .texture_height = tex_h,
+ .skip = &skip,
+ .scaled_width = &scaled_tex_w,
+ .scaled_height = &scaled_tex_h,
+ .force_copy_to_ram = &force_copy_to_ram};
for (const auto& action : g_graphics_mod_manager->GetEFBActions(info))
{
action->OnEFB(&efb);
}
+ if (force_copy_to_ram)
+ {
+ copy_to_ram = true;
+ }
if (skip == true)
{
if (copy_to_ram)