Skip to content

Commit

Permalink
small fixes for post processing
Browse files Browse the repository at this point in the history
  • Loading branch information
Tinob committed Feb 18, 2016
1 parent d2542e0 commit 3b27800
Show file tree
Hide file tree
Showing 7 changed files with 87 additions and 92 deletions.
19 changes: 9 additions & 10 deletions Source/Core/VideoBackends/DX11/PostProcessing.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ static const u32 FIRST_INPUT_BINDING_SLOT = 9;

static const char* s_shader_common = R"(
struct VS_INPUT
struct VS_INPUT
{
float4 position : POSITION;
float4 texCoord : TEXCOORD0;
Expand Down Expand Up @@ -66,7 +66,7 @@ output.layer = input.texCoord.z;

static const char* s_geometry_shader = R"(
[maxvertexcount(6)]
[maxvertexcount(6)]
void main(triangle VS_OUTPUT input[3], inout TriangleStream<GS_OUTPUT> output)
{
for (int layer = 0; layer < 2; layer++)
Expand Down Expand Up @@ -133,22 +133,21 @@ bool PostProcessingShader::Initialize(const PostProcessingShaderConfiguration* c

bool PostProcessingShader::Reconfigure(const TargetSize& new_size)
{
m_ready = false;
m_ready = true;

bool size_changed = (m_internal_size != new_size);
const bool size_changed = (m_internal_size != new_size);
if (size_changed)
ResizeOutputTextures(new_size);
m_ready = ResizeOutputTextures(new_size);

// Re-link on size change due to the input pointer changes
if (m_config->IsDirty() || size_changed)
if (m_ready && (m_config->IsDirty() || size_changed))
LinkPassOutputs();

// Recompile shaders if compile-time constants have changed
if (m_config->IsCompileTimeConstantsDirty() && !RecompileShaders())
return false;
if (m_ready && m_config->IsCompileTimeConstantsDirty())
m_ready = RecompileShaders();

m_ready = true;
return true;
return m_ready;
}

bool PostProcessingShader::CreatePasses()
Expand Down
2 changes: 1 addition & 1 deletion Source/Core/VideoBackends/DX11/Render.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -858,7 +858,7 @@ void Renderer::SwapImpl(u32 xfbAddr, u32 fbWidth, u32 fbStride, u32 fbHeight, co
D3D::context->OMSetRenderTargets(1, &D3D::GetBackBuffer()->GetRTV(), nullptr);
D3D::SetLinearCopySampler();
}
if (blit_depth_tex == nullptr && m_post_processor->GetScalingShaderConfig()->RequiresDepthBuffer())
if (blit_depth_tex == nullptr && (m_post_processor->GetScalingShaderConfig()->RequiresDepthBuffer() || (m_post_processor->ShouldTriggerAfterBlit() && m_post_processor->RequiresDepthBuffer())))
{
blit_depth_tex = FramebufferManager::GetResolvedEFBDepthTexture();
}
Expand Down
21 changes: 10 additions & 11 deletions Source/Core/VideoBackends/OGL/PostProcessing.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -146,22 +146,21 @@ bool PostProcessingShader::Initialize(const PostProcessingShaderConfiguration* c

bool PostProcessingShader::Reconfigure(const TargetSize& new_size)
{
m_ready = false;
m_ready = true;

bool size_changed = (m_internal_size != new_size);
if (size_changed && !ResizeOutputTextures(new_size))
return false;
const bool size_changed = (m_internal_size != new_size);
if (size_changed)
m_ready = ResizeOutputTextures(new_size);

// Also done on size change due to the input pointer changes
if (m_config->IsDirty() || size_changed)
// Re-link on size change due to the input pointer changes
if (m_ready && (m_config->IsDirty() || size_changed))
LinkPassOutputs();

// Recompile shaders if compile-time constants have changed
if (m_config->IsCompileTimeConstantsDirty() && !RecompileShaders())
return false;
if (m_ready && m_config->IsCompileTimeConstantsDirty())
m_ready = RecompileShaders();

m_ready = true;
return true;
return m_ready;
}

bool PostProcessingShader::CreatePasses()
Expand Down Expand Up @@ -985,7 +984,7 @@ void OGLPostProcessor::CopyTexture(const TargetRectangle& dst_rect, GLuint dst_t
for (int i = 0; i < layers_to_copy; i++)
{
int layer = (src_layer < 0) ? i : src_layer;
if (g_ogl_config.bSupportsCopySubImage && dst_texture != 0 && !force_blit)
if (g_ogl_config.bSupportsCopySubImage && dst_texture != 0 && !(force_blit || scaling))
{
// use (ARB|NV)_copy_image, but only for non-window-framebuffer cases
glCopyImageSubData(src_texture, GL_TEXTURE_2D_ARRAY, 0, src_rect.left, src_rect.bottom, layer,
Expand Down
2 changes: 1 addition & 1 deletion Source/Core/VideoBackends/OGL/Render.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1349,7 +1349,7 @@ void Renderer::SwapImpl(u32 xfbAddr, u32 fbWidth, u32 fbStride, u32 fbHeight, co
tex = static_cast<GLuint>(new_blit_tex);
}

if (!depth_tex && m_post_processor->GetScalingShaderConfig()->RequiresDepthBuffer())
if (!depth_tex && (m_post_processor->GetScalingShaderConfig()->RequiresDepthBuffer() || (m_post_processor->ShouldTriggerAfterBlit() && m_post_processor->RequiresDepthBuffer())))
depth_tex = FramebufferManager::ResolveAndGetDepthTarget(rc);

BlitScreen(flipped_trc, target_rc, tex_size, tex, depth_tex, Gamma);
Expand Down
120 changes: 55 additions & 65 deletions Source/Core/VideoCommon/PostProcessing.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -819,14 +819,6 @@ void PostProcessingShaderConfiguration::SaveOptionsConfiguration()
ini.Save(file_path);
}

void PostProcessingShaderConfiguration::ClearDirty()
{
m_any_options_dirty = false;
m_compile_time_constants_dirty = false;
for (auto& it : m_options)
it.second.m_dirty = false;
}

void PostProcessingShaderConfiguration::SetOptionf(const std::string& option, int index, float value)
{
auto it = m_options.find(option);
Expand Down Expand Up @@ -1511,16 +1503,16 @@ std::string PostProcessor::GetPassFragmentShaderSource(API_TYPE api, const PostP
if (pass->entry_point == "main")
shader_source += "#undef main\n";

shader_source += "void main(in float4 in_pos : SV_Position,\n";
shader_source += " in float2 in_srcTexCoord : TEXCOORD0,\n";
shader_source += " in float2 in_dstTexCoord : TEXCOORD1,\n";
shader_source += " in float in_layer : TEXCOORD2,\n";
shader_source += " out float4 out_col0 : SV_Target)\n";
shader_source += "{\n";
shader_source += "\tv_fragcoord = u_viewport_rect.xy + in_pos.xy;\n";
shader_source += "\tv_source_uv = in_srcTexCoord;\n";
shader_source += "\tv_target_uv = in_dstTexCoord;\n";
shader_source += "\tv_layer = in_layer;\n";
shader_source += "void main(in float4 in_pos : SV_Position,\n"
" in float2 in_srcTexCoord : TEXCOORD0,\n"
" in float2 in_dstTexCoord : TEXCOORD1,\n"
" in float in_layer : TEXCOORD2,\n"
" out float4 out_col0 : SV_Target)\n"
"{\n"
"\tv_fragcoord = u_viewport_rect.xy + in_pos.xy;\n"
"\tv_source_uv = in_srcTexCoord;\n"
"\tv_target_uv = in_dstTexCoord;\n"
"\tv_layer = in_layer;\n";

// No entry point? This pass should perform a copy.
if (pass->entry_point.empty())
Expand All @@ -1544,61 +1536,69 @@ bool PostProcessor::UpdateUniformBuffer(API_TYPE api,
{
// Check if the size has changed, due to options.
size_t active_constant_count = POST_PROCESSING_MAX_TEXTURE_INPUTS + 6 + config->GetOptions().size();
size_t active_constant_size = sizeof(Constant) * (u32)active_constant_count;
bool size_changed = (active_constant_count != m_current_constants.size());
*buffer_size = sizeof(Constant) * (u32)active_constant_count;
*buffer_size = active_constant_size;
m_new_constants.resize(active_constant_count);

Constant temp;
// float4 input_resolutions[4]
for (size_t i = 0; i < POST_PROCESSING_MAX_TEXTURE_INPUTS; i++)
{
m_new_constants[i].float_constant[0] = (float)input_sizes[i].width;
m_new_constants[i].float_constant[1] = (float)input_sizes[i].height;
m_new_constants[i].float_constant[2] = 1.0f / (float)input_sizes[i].width;
m_new_constants[i].float_constant[3] = 1.0f / (float)input_sizes[i].height;
temp.float_constant[0] = (float)input_sizes[i].width;
temp.float_constant[1] = (float)input_sizes[i].height;
temp.float_constant[2] = 1.0f / (float)input_sizes[i].width;
temp.float_constant[3] = 1.0f / (float)input_sizes[i].height;
m_new_constants[i] = temp;
}

// float4 target_resolution
u32 constant_idx = POST_PROCESSING_MAX_TEXTURE_INPUTS;
m_new_constants[constant_idx].float_constant[0] = (float)dst_size.width;
m_new_constants[constant_idx].float_constant[1] = (float)dst_size.height;
m_new_constants[constant_idx].float_constant[2] = 1.0f / (float)dst_size.width;
m_new_constants[constant_idx].float_constant[3] = 1.0f / (float)dst_size.height;
temp.float_constant[0] = (float)dst_size.width;
temp.float_constant[1] = (float)dst_size.height;
temp.float_constant[2] = 1.0f / (float)dst_size.width;
temp.float_constant[3] = 1.0f / (float)dst_size.height;
m_new_constants[constant_idx] = temp;
constant_idx++;

// float4 src_rect
m_new_constants[constant_idx].float_constant[0] = (float)src_rect.left / (float)src_size.width;
m_new_constants[constant_idx].float_constant[1] = (float)((api == API_OPENGL) ? src_rect.bottom : src_rect.top) / (float)src_size.height;
m_new_constants[constant_idx].float_constant[2] = (float)src_rect.GetWidth() / (float)src_size.width;
m_new_constants[constant_idx].float_constant[3] = (float)src_rect.GetHeight() / (float)src_size.height;
temp.float_constant[0] = (float)src_rect.left / (float)src_size.width;
temp.float_constant[1] = (float)((api == API_OPENGL) ? src_rect.bottom : src_rect.top) / (float)src_size.height;
temp.float_constant[2] = (float)src_rect.GetWidth() / (float)src_size.width;
temp.float_constant[3] = (float)src_rect.GetHeight() / (float)src_size.height;
m_new_constants[constant_idx] = temp;
constant_idx++;

// float4 target_rect
m_new_constants[constant_idx].float_constant[0] = (float)dst_rect.left / (float)dst_size.width;
m_new_constants[constant_idx].float_constant[1] = (float)((api == API_OPENGL) ? dst_rect.bottom : dst_rect.top) / (float)dst_size.height;
m_new_constants[constant_idx].float_constant[2] = (float)dst_rect.GetWidth() / (float)dst_size.width;
m_new_constants[constant_idx].float_constant[3] = (float)dst_rect.GetHeight() / (float)dst_size.height;
temp.float_constant[0] = (float)dst_rect.left / (float)dst_size.width;
temp.float_constant[1] = (float)((api == API_OPENGL) ? dst_rect.bottom : dst_rect.top) / (float)dst_size.height;
temp.float_constant[2] = (float)dst_rect.GetWidth() / (float)dst_size.width;
temp.float_constant[3] = (float)dst_rect.GetHeight() / (float)dst_size.height;
m_new_constants[constant_idx] = temp;
constant_idx++;

// float4 viewport_rect
m_new_constants[constant_idx].float_constant[0] = (float)dst_rect.left;
m_new_constants[constant_idx].float_constant[1] = (float)dst_rect.top;
m_new_constants[constant_idx].float_constant[2] = (float)dst_rect.right;
m_new_constants[constant_idx].float_constant[3] = (float)dst_rect.bottom;
temp.float_constant[0] = (float)dst_rect.left;
temp.float_constant[1] = (float)dst_rect.top;
temp.float_constant[2] = (float)dst_rect.right;
temp.float_constant[3] = (float)dst_rect.bottom;
m_new_constants[constant_idx] = temp;
constant_idx++;

// float4 window_rect
const TargetRectangle& window_rect = Renderer::GetWindowRectangle();
m_new_constants[constant_idx].float_constant[0] = (float)window_rect.left;
m_new_constants[constant_idx].float_constant[1] = (float)window_rect.top;
m_new_constants[constant_idx].float_constant[2] = (float)window_rect.right;
m_new_constants[constant_idx].float_constant[3] = (float)window_rect.bottom;
temp.float_constant[0] = (float)window_rect.left;
temp.float_constant[1] = (float)window_rect.top;
temp.float_constant[2] = (float)window_rect.right;
temp.float_constant[3] = (float)window_rect.bottom;
m_new_constants[constant_idx] = temp;
constant_idx++;

// float time, float layer
m_new_constants[constant_idx].float_constant[0] = float(double(m_timer.GetTimeDifference()) / 1000.0);
m_new_constants[constant_idx].float_constant[1] = float(std::max(src_layer, 0));
m_new_constants[constant_idx].float_constant[2] = gamma;
m_new_constants[constant_idx].int_constant[3] = (src_rect.GetWidth() > dst_rect.GetWidth() && dst_rect.GetHeight() > dst_rect.GetHeight() && g_ActiveConfig.bUseScalingFilter) ? 1u : 0;
temp.float_constant[0] = float(double(m_timer.GetTimeDifference()) / 1000.0);
temp.float_constant[1] = float(std::max(src_layer, 0));
temp.float_constant[2] = gamma;
temp.int_constant[3] = (src_rect.GetWidth() > dst_rect.GetWidth() && dst_rect.GetHeight() > dst_rect.GetHeight() && g_ActiveConfig.bUseScalingFilter) ? 1u : 0;
m_new_constants[constant_idx] = temp;
constant_idx++;

// Set from options. This is an ordered map so it will always match the order in the shader code generated.
Expand All @@ -1607,45 +1607,35 @@ bool PostProcessor::UpdateUniformBuffer(API_TYPE api,
// Skip compile-time constants, since they're set in the program source.
if (it.second.m_compile_time_constant)
continue;

temp = {};
switch (it.second.m_type)
{
case POST_PROCESSING_OPTION_TYPE_BOOL:
m_new_constants[constant_idx].int_constant[0] = (int)it.second.m_bool_value;
m_new_constants[constant_idx].int_constant[1] = 0;
m_new_constants[constant_idx].int_constant[2] = 0;
m_new_constants[constant_idx].int_constant[3] = 0;
constant_idx++;
temp.int_constant[0] = (int)it.second.m_bool_value;
break;

case POST_PROCESSING_OPTION_TYPE_INTEGER:
{
u32 components = std::max((u32)it.second.m_integer_values.size(), (u32)0);
for (u32 i = 0; i < components; i++)
m_new_constants[constant_idx].int_constant[i] = it.second.m_integer_values[i];
for (u32 i = components; i < 4; i++)
m_new_constants[constant_idx].int_constant[i] = 0;

constant_idx++;
temp.int_constant[i] = it.second.m_integer_values[i];
}
break;

case POST_PROCESSING_OPTION_TYPE_FLOAT:
{
u32 components = std::max((u32)it.second.m_float_values.size(), (u32)0);
for (u32 i = 0; i < components; i++)
m_new_constants[constant_idx].float_constant[i] = it.second.m_float_values[i];
for (u32 i = components; i < 4; i++)
m_new_constants[constant_idx].int_constant[i] = 0;

constant_idx++;
temp.float_constant[i] = it.second.m_float_values[i];
}
break;
}
m_new_constants[constant_idx] = temp;
constant_idx++;
}

// Any changes?
if (!size_changed && !memcmp(m_current_constants.data(), m_new_constants.data(), sizeof(Constant) * m_new_constants.size()))
if (!size_changed && !memcmp(m_current_constants.data(), m_new_constants.data(), active_constant_size))
return false;

// Swap buffer pointers, to avoid copying data again
Expand Down
12 changes: 10 additions & 2 deletions Source/Core/VideoCommon/PostProcessing.h
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,16 @@ class PostProcessingShaderConfiguration
bool IsDirty() const { return m_any_options_dirty; }
bool IsCompileTimeConstantsDirty() const { return m_compile_time_constants_dirty; }
void SetDirty(bool dirty = true) { m_any_options_dirty = dirty; }
void ClearDirty();
void ClearDirty()
{
if (m_any_options_dirty || m_compile_time_constants_dirty)
{
m_any_options_dirty = false;
m_compile_time_constants_dirty = false;
for (auto& it : m_options)
it.second.m_dirty = false;
}
}
bool RequiresDepthBuffer() const { return m_requires_depth_buffer; }

bool HasOptions() const { return !m_options.empty(); }
Expand Down Expand Up @@ -280,7 +289,6 @@ class PostProcessor
// Each option is aligned to a float4
union Constant
{
int bool_constant;
float float_constant[4];
s32 int_constant[4];
};
Expand Down
3 changes: 1 addition & 2 deletions Source/Core/VideoCommon/ShaderGenCommon.h
Original file line number Diff line number Diff line change
Expand Up @@ -63,8 +63,7 @@ class ShaderUid
// determines the storage order inside STL containers
bool operator < (const ShaderUid& obj) const
{
return data.NumValues() < obj.data.NumValues()
|| memcmp(reinterpret_cast<const u8*>(&data) + data.StartValue(), reinterpret_cast<const u8*>(&obj.data) + obj.data.StartValue(), data.NumValues()) < 0;
return memcmp(reinterpret_cast<const u8*>(&data) + data.StartValue(), reinterpret_cast<const u8*>(&obj.data) + obj.data.StartValue(), data.NumValues()) < 0;
}

template<class T>
Expand Down

0 comments on commit 3b27800

Please sign in to comment.