mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-07-21 13:20:27 -06:00
Video Backends: Implement vertical scaling for xfb copies. This fixes the
display of PAL games that run in 50hz mode.
This commit is contained in:
@ -50,6 +50,7 @@ struct EncodingProgram
|
||||
{
|
||||
SHADER program;
|
||||
GLint copy_position_uniform;
|
||||
GLint y_scale_uniform;
|
||||
};
|
||||
static std::map<EFBCopyParams, EncodingProgram> s_encoding_programs;
|
||||
|
||||
@ -166,6 +167,7 @@ static EncodingProgram& GetOrCreateEncodingShader(const EFBCopyParams& params)
|
||||
PanicAlert("Failed to compile texture encoding shader.");
|
||||
|
||||
program.copy_position_uniform = glGetUniformLocation(program.program.glprogid, "position");
|
||||
program.y_scale_uniform = glGetUniformLocation(program.program.glprogid, "y_scale");
|
||||
return s_encoding_programs.emplace(params, program).first->second;
|
||||
}
|
||||
|
||||
@ -217,7 +219,7 @@ void Shutdown()
|
||||
// dst_line_size, writeStride in bytes
|
||||
|
||||
static void EncodeToRamUsingShader(GLuint srcTexture, u8* destAddr, u32 dst_line_size,
|
||||
u32 dstHeight, u32 writeStride, bool linearFilter)
|
||||
u32 dstHeight, u32 writeStride, bool linearFilter, float y_scale)
|
||||
{
|
||||
// switch to texture converter frame buffer
|
||||
// attach render buffer as color destination
|
||||
@ -233,7 +235,7 @@ static void EncodeToRamUsingShader(GLuint srcTexture, u8* destAddr, u32 dst_line
|
||||
// TODO: This only produces perfect downsampling for 2x IR, other resolutions will need more
|
||||
// complex down filtering to average all pixels and produce the correct result.
|
||||
// Also, box filtering won't be correct for anything other than 1x IR
|
||||
if (linearFilter || g_renderer->GetEFBScale() != 1)
|
||||
if (linearFilter || g_renderer->GetEFBScale() != 1 || y_scale > 1.0f)
|
||||
g_sampler_cache->BindLinearSampler(9);
|
||||
else
|
||||
g_sampler_cache->BindNearestSampler(9);
|
||||
@ -282,13 +284,14 @@ void EncodeToRamFromTexture(u8* dest_ptr, const EFBCopyParams& params, u32 nativ
|
||||
texconv_shader.program.Bind();
|
||||
glUniform4i(texconv_shader.copy_position_uniform, src_rect.left, src_rect.top, native_width,
|
||||
scale_by_half ? 2 : 1);
|
||||
glUniform1f(texconv_shader.y_scale_uniform, params.y_scale);
|
||||
|
||||
const GLuint read_texture = params.depth ?
|
||||
FramebufferManager::ResolveAndGetDepthTarget(src_rect) :
|
||||
FramebufferManager::ResolveAndGetRenderTarget(src_rect);
|
||||
|
||||
EncodeToRamUsingShader(read_texture, dest_ptr, bytes_per_row, num_blocks_y, memory_stride,
|
||||
scale_by_half && !params.depth);
|
||||
scale_by_half && !params.depth, params.y_scale);
|
||||
|
||||
FramebufferManager::SetFramebuffer(0);
|
||||
g_renderer->RestoreAPIState();
|
||||
@ -308,7 +311,7 @@ void EncodeToRamYUYV(GLuint srcTexture, const TargetRectangle& sourceRc, u8* des
|
||||
// We enable linear filtering, because the GameCube does filtering in the vertical direction when
|
||||
// yscale is enabled.
|
||||
// Otherwise we get jaggies when a game uses yscaling (most PAL games)
|
||||
EncodeToRamUsingShader(srcTexture, destAddr, dstWidth * 2, dstHeight, dstStride, true);
|
||||
EncodeToRamUsingShader(srcTexture, destAddr, dstWidth * 2, dstHeight, dstStride, true, 1.0f);
|
||||
FramebufferManager::SetFramebuffer(0);
|
||||
OGLTexture::DisableStage(0);
|
||||
g_renderer->RestoreAPIState();
|
||||
|
Reference in New Issue
Block a user