summaryrefslogtreecommitdiff
path: root/Source/Core/VideoBackends
diff options
context:
space:
mode:
authorN.E.C <beholdnec@gmail.com>2017-07-30 12:45:55 -0700
committerN.E.C <beholdnec@gmail.com>2017-08-03 18:35:29 -0700
commitc3a57bbad53567af4546a68f0e9dbcd913bd9a75 (patch)
tree4ff1176b00c8df323df8610ff2076545e15c60de /Source/Core/VideoBackends
parent9649494f67b86b91c9086f4a9e356fb832c4a9b7 (diff)
Video: Clearly separate Texture and EFB Copy formats
Improve bookkeeping around formats. Hopefully make code less confusing. - Rename TlutFormat -> TLUTFormat to follow conventions. - Use enum classes to prevent using a Texture format where an EFB Copy format is expected or vice-versa. - Use common EFBCopyFormat names regardless of depth and YUV configurations.
Diffstat (limited to 'Source/Core/VideoBackends')
-rw-r--r--Source/Core/VideoBackends/D3D/PSTextureEncoder.cpp30
-rw-r--r--Source/Core/VideoBackends/D3D/PSTextureEncoder.h8
-rw-r--r--Source/Core/VideoBackends/D3D/TextureCache.cpp25
-rw-r--r--Source/Core/VideoBackends/D3D/TextureCache.h10
-rw-r--r--Source/Core/VideoBackends/Null/TextureCache.h10
-rw-r--r--Source/Core/VideoBackends/OGL/TextureCache.cpp111
-rw-r--r--Source/Core/VideoBackends/OGL/TextureCache.h14
-rw-r--r--Source/Core/VideoBackends/OGL/TextureConverter.cpp20
-rw-r--r--Source/Core/VideoBackends/OGL/TextureConverter.h7
-rw-r--r--Source/Core/VideoBackends/Software/SWmain.cpp10
-rw-r--r--Source/Core/VideoBackends/Software/TextureEncoder.cpp871
-rw-r--r--Source/Core/VideoBackends/Software/TextureSampler.cpp30
-rw-r--r--Source/Core/VideoBackends/Vulkan/TextureCache.cpp20
-rw-r--r--Source/Core/VideoBackends/Vulkan/TextureCache.h14
-rw-r--r--Source/Core/VideoBackends/Vulkan/TextureConverter.cpp49
-rw-r--r--Source/Core/VideoBackends/Vulkan/TextureConverter.h19
16 files changed, 630 insertions, 618 deletions
diff --git a/Source/Core/VideoBackends/D3D/PSTextureEncoder.cpp b/Source/Core/VideoBackends/D3D/PSTextureEncoder.cpp
index 403e768599..51a7dfda08 100644
--- a/Source/Core/VideoBackends/D3D/PSTextureEncoder.cpp
+++ b/Source/Core/VideoBackends/D3D/PSTextureEncoder.cpp
@@ -87,9 +87,9 @@ void PSTextureEncoder::Shutdown()
SAFE_RELEASE(m_out);
}
-void PSTextureEncoder::Encode(u8* dst, const EFBCopyFormat& format, u32 native_width,
+void PSTextureEncoder::Encode(u8* dst, const EFBCopyParams& params, u32 native_width,
u32 bytes_per_row, u32 num_blocks_y, u32 memory_stride,
- bool is_depth_copy, const EFBRectangle& src_rect, bool scale_by_half)
+ const EFBRectangle& src_rect, bool scale_by_half)
{
if (!m_ready) // Make sure we initialized OK
return;
@@ -100,7 +100,7 @@ void PSTextureEncoder::Encode(u8* dst, const EFBCopyFormat& format, u32 native_w
// FIXME: Instead of resolving EFB, it would be better to pick out a
// single sample from each pixel. The game may break if it isn't
// expecting the blurred edges around multisampled shapes.
- ID3D11ShaderResourceView* pEFB = is_depth_copy ?
+ ID3D11ShaderResourceView* pEFB = params.depth ?
FramebufferManager::GetResolvedEFBDepthTexture()->GetSRV() :
FramebufferManager::GetResolvedEFBColorTexture()->GetSRV();
@@ -119,12 +119,12 @@ void PSTextureEncoder::Encode(u8* dst, const EFBCopyFormat& format, u32 native_w
D3D::context->OMSetRenderTargets(1, &m_outRTV, nullptr);
- EFBEncodeParams params;
- params.SrcLeft = src_rect.left;
- params.SrcTop = src_rect.top;
- params.DestWidth = native_width;
- params.ScaleFactor = scale_by_half ? 2 : 1;
- D3D::context->UpdateSubresource(m_encodeParams, 0, nullptr, &params, 0, 0);
+ EFBEncodeParams encode_params;
+ encode_params.SrcLeft = src_rect.left;
+ encode_params.SrcTop = src_rect.top;
+ encode_params.DestWidth = native_width;
+ encode_params.ScaleFactor = scale_by_half ? 2 : 1;
+ D3D::context->UpdateSubresource(m_encodeParams, 0, nullptr, &encode_params, 0, 0);
D3D::stateman->SetPixelConstants(m_encodeParams);
// We also linear filtering for both box filtering and downsampling higher resolutions to 1x
@@ -137,7 +137,7 @@ void PSTextureEncoder::Encode(u8* dst, const EFBCopyFormat& format, u32 native_w
D3D::SetPointCopySampler();
D3D::drawShadedTexQuad(pEFB, targetRect.AsRECT(), g_renderer->GetTargetWidth(),
- g_renderer->GetTargetHeight(), GetEncodingPixelShader(format),
+ g_renderer->GetTargetHeight(), GetEncodingPixelShader(params),
VertexShaderCache::GetSimpleVertexShader(),
VertexShaderCache::GetSimpleInputLayout());
@@ -168,18 +168,18 @@ void PSTextureEncoder::Encode(u8* dst, const EFBCopyFormat& format, u32 native_w
FramebufferManager::GetEFBDepthTexture()->GetDSV());
}
-ID3D11PixelShader* PSTextureEncoder::GetEncodingPixelShader(const EFBCopyFormat& format)
+ID3D11PixelShader* PSTextureEncoder::GetEncodingPixelShader(const EFBCopyParams& params)
{
- auto iter = m_encoding_shaders.find(format);
+ auto iter = m_encoding_shaders.find(params);
if (iter != m_encoding_shaders.end())
return iter->second;
D3DBlob* bytecode = nullptr;
- const char* shader = TextureConversionShader::GenerateEncodingShader(format, APIType::D3D);
+ const char* shader = TextureConversionShader::GenerateEncodingShader(params, APIType::D3D);
if (!D3D::CompilePixelShader(shader, &bytecode))
{
PanicAlert("Failed to compile texture encoding shader.");
- m_encoding_shaders[format] = nullptr;
+ m_encoding_shaders[params] = nullptr;
return nullptr;
}
@@ -188,7 +188,7 @@ ID3D11PixelShader* PSTextureEncoder::GetEncodingPixelShader(const EFBCopyFormat&
D3D::device->CreatePixelShader(bytecode->Data(), bytecode->Size(), nullptr, &newShader);
CHECK(SUCCEEDED(hr), "create efb encoder pixel shader");
- m_encoding_shaders.emplace(format, newShader);
+ m_encoding_shaders.emplace(params, newShader);
return newShader;
}
}
diff --git a/Source/Core/VideoBackends/D3D/PSTextureEncoder.h b/Source/Core/VideoBackends/D3D/PSTextureEncoder.h
index c000777591..738f1b2d3e 100644
--- a/Source/Core/VideoBackends/D3D/PSTextureEncoder.h
+++ b/Source/Core/VideoBackends/D3D/PSTextureEncoder.h
@@ -32,12 +32,12 @@ public:
void Init();
void Shutdown();
- void Encode(u8* dst, const EFBCopyFormat& format, u32 native_width, u32 bytes_per_row,
- u32 num_blocks_y, u32 memory_stride, bool is_depth_copy, const EFBRectangle& src_rect,
+ void Encode(u8* dst, const EFBCopyParams& params, u32 native_width, u32 bytes_per_row,
+ u32 num_blocks_y, u32 memory_stride, const EFBRectangle& src_rect,
bool scale_by_half);
private:
- ID3D11PixelShader* GetEncodingPixelShader(const EFBCopyFormat& format);
+ ID3D11PixelShader* GetEncodingPixelShader(const EFBCopyParams& params);
bool m_ready;
@@ -45,6 +45,6 @@ private:
ID3D11RenderTargetView* m_outRTV;
ID3D11Texture2D* m_outStage;
ID3D11Buffer* m_encodeParams;
- std::map<EFBCopyFormat, ID3D11PixelShader*> m_encoding_shaders;
+ std::map<EFBCopyParams, ID3D11PixelShader*> m_encoding_shaders;
};
}
diff --git a/Source/Core/VideoBackends/D3D/TextureCache.cpp b/Source/Core/VideoBackends/D3D/TextureCache.cpp
index a696dba452..87b3a50260 100644
--- a/Source/Core/VideoBackends/D3D/TextureCache.cpp
+++ b/Source/Core/VideoBackends/D3D/TextureCache.cpp
@@ -38,12 +38,12 @@ std::unique_ptr<AbstractTexture> TextureCache::CreateTexture(const TextureConfig
return std::make_unique<DXTexture>(config);
}
-void TextureCache::CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_width,
+void TextureCache::CopyEFB(u8* dst, const EFBCopyParams& params, u32 native_width,
u32 bytes_per_row, u32 num_blocks_y, u32 memory_stride,
- bool is_depth_copy, const EFBRectangle& src_rect, bool scale_by_half)
+ const EFBRectangle& src_rect, bool scale_by_half)
{
- g_encoder->Encode(dst, format, native_width, bytes_per_row, num_blocks_y, memory_stride,
- is_depth_copy, src_rect, scale_by_half);
+ g_encoder->Encode(dst, params, native_width, bytes_per_row, num_blocks_y, memory_stride, src_rect,
+ scale_by_half);
}
const char palette_shader[] =
@@ -126,8 +126,8 @@ void main(
}
)HLSL";
-void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source, void* palette,
- TlutFormat format)
+void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source,
+ const void* palette, TLUTFormat format)
{
DXTexture* source_texture = static_cast<DXTexture*>(source->texture.get());
DXTexture* destination_texture = static_cast<DXTexture*>(destination->texture.get());
@@ -144,7 +144,7 @@ void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source,
D3D::stateman->SetTexture(1, palette_buf_srv);
// TODO: Add support for C14X2 format. (Different multiplier, more palette entries.)
- float params[4] = {(source->format & 0xf) == GX_TF_I4 ? 15.f : 255.f};
+ float params[4] = {source->format == TextureFormat::I4 ? 15.f : 255.f};
D3D::context->UpdateSubresource(palette_uniform, 0, nullptr, &params, 0, 0);
D3D::stateman->SetPixelConstants(palette_uniform);
@@ -163,8 +163,9 @@ void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source,
// Create texture copy
D3D::drawShadedTexQuad(
source_texture->GetRawTexIdentifier()->GetSRV(), &sourcerect, source->GetWidth(),
- source->GetHeight(), palette_pixel_shader[format], VertexShaderCache::GetSimpleVertexShader(),
- VertexShaderCache::GetSimpleInputLayout(), GeometryShaderCache::GetCopyGeometryShader());
+ source->GetHeight(), palette_pixel_shader[static_cast<int>(format)],
+ VertexShaderCache::GetSimpleVertexShader(), VertexShaderCache::GetSimpleInputLayout(),
+ GeometryShaderCache::GetCopyGeometryShader());
D3D::context->OMSetRenderTargets(1, &FramebufferManager::GetEFBColorTexture()->GetRTV(),
FramebufferManager::GetEFBDepthTexture()->GetDSV());
@@ -190,9 +191,9 @@ TextureCache::TextureCache()
palette_buf = nullptr;
palette_buf_srv = nullptr;
palette_uniform = nullptr;
- palette_pixel_shader[GX_TL_IA8] = GetConvertShader("IA8");
- palette_pixel_shader[GX_TL_RGB565] = GetConvertShader("RGB565");
- palette_pixel_shader[GX_TL_RGB5A3] = GetConvertShader("RGB5A3");
+ palette_pixel_shader[static_cast<int>(TLUTFormat::IA8)] = GetConvertShader("IA8");
+ palette_pixel_shader[static_cast<int>(TLUTFormat::RGB565)] = GetConvertShader("RGB565");
+ palette_pixel_shader[static_cast<int>(TLUTFormat::RGB5A3)] = GetConvertShader("RGB5A3");
auto lutBd = CD3D11_BUFFER_DESC(sizeof(u16) * 256, D3D11_BIND_SHADER_RESOURCE);
HRESULT hr = D3D::device->CreateBuffer(&lutBd, nullptr, &palette_buf);
CHECK(SUCCEEDED(hr), "create palette decoder lut buffer");
diff --git a/Source/Core/VideoBackends/D3D/TextureCache.h b/Source/Core/VideoBackends/D3D/TextureCache.h
index 87586ca7f3..afb3a1421d 100644
--- a/Source/Core/VideoBackends/D3D/TextureCache.h
+++ b/Source/Core/VideoBackends/D3D/TextureCache.h
@@ -28,12 +28,12 @@ private:
return 0;
};
- void ConvertTexture(TCacheEntry* destination, TCacheEntry* source, void* palette,
- TlutFormat format) override;
+ void ConvertTexture(TCacheEntry* destination, TCacheEntry* source, const void* palette,
+ TLUTFormat format) override;
- void CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_width, u32 bytes_per_row,
- u32 num_blocks_y, u32 memory_stride, bool is_depth_copy,
- const EFBRectangle& src_rect, bool scale_by_half) override;
+ void CopyEFB(u8* dst, const EFBCopyParams& params, u32 native_width, u32 bytes_per_row,
+ u32 num_blocks_y, u32 memory_stride, const EFBRectangle& src_rect,
+ bool scale_by_half) override;
void CopyEFBToCacheEntry(TCacheEntry* entry, bool is_depth_copy, const EFBRectangle& src_rect,
bool scale_by_half, unsigned int cbuf_id, const float* colmat) override;
diff --git a/Source/Core/VideoBackends/Null/TextureCache.h b/Source/Core/VideoBackends/Null/TextureCache.h
index e4d115d49d..2b3283c056 100644
--- a/Source/Core/VideoBackends/Null/TextureCache.h
+++ b/Source/Core/VideoBackends/Null/TextureCache.h
@@ -20,14 +20,14 @@ public:
~TextureCache() {}
bool CompileShaders() override { return true; }
void DeleteShaders() override {}
- void ConvertTexture(TCacheEntry* entry, TCacheEntry* unconverted, void* palette,
- TlutFormat format) override
+ void ConvertTexture(TCacheEntry* entry, TCacheEntry* unconverted, const void* palette,
+ TLUTFormat format) override
{
}
- void CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_width, u32 bytes_per_row,
- u32 num_blocks_y, u32 memory_stride, bool is_depth_copy,
- const EFBRectangle& src_rect, bool scale_by_half) override
+ void CopyEFB(u8* dst, const EFBCopyParams& params, u32 native_width, u32 bytes_per_row,
+ u32 num_blocks_y, u32 memory_stride, const EFBRectangle& src_rect,
+ bool scale_by_half) override
{
}
diff --git a/Source/Core/VideoBackends/OGL/TextureCache.cpp b/Source/Core/VideoBackends/OGL/TextureCache.cpp
index b4f16266ee..924f3d428c 100644
--- a/Source/Core/VideoBackends/OGL/TextureCache.cpp
+++ b/Source/Core/VideoBackends/OGL/TextureCache.cpp
@@ -9,6 +9,7 @@
#include <memory>
#include <vector>
+#include "Common/Assert.h"
#include "Common/GL/GLInterfaceBase.h"
#include "Common/MsgHandler.h"
#include "Common/StringUtil.h"
@@ -32,12 +33,18 @@ namespace OGL
{
static u32 s_ColorCbufid;
static u32 s_DepthCbufid;
-static SHADER s_palette_pixel_shader[3];
+
+struct PaletteShader
+{
+ SHADER shader;
+ GLuint buffer_offset_uniform;
+ GLuint multiplier_uniform;
+ GLuint copy_position_uniform;
+};
+
+static PaletteShader s_palette_shader[3];
static std::unique_ptr<StreamBuffer> s_palette_stream_buffer;
-static GLuint s_palette_resolv_texture;
-static GLuint s_palette_buffer_offset_uniform[3];
-static GLuint s_palette_multiplier_uniform[3];
-static GLuint s_palette_copy_position_uniform[3];
+static GLuint s_palette_resolv_texture = 0;
struct TextureDecodingProgramInfo
{
@@ -64,12 +71,12 @@ std::unique_ptr<AbstractTexture> TextureCache::CreateTexture(const TextureConfig
return std::make_unique<OGLTexture>(config);
}
-void TextureCache::CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_width,
+void TextureCache::CopyEFB(u8* dst, const EFBCopyParams& params, u32 native_width,
u32 bytes_per_row, u32 num_blocks_y, u32 memory_stride,
- bool is_depth_copy, const EFBRectangle& src_rect, bool scale_by_half)
+ const EFBRectangle& src_rect, bool scale_by_half)
{
- TextureConverter::EncodeToRamFromTexture(dst, format, native_width, bytes_per_row, num_blocks_y,
- memory_stride, is_depth_copy, src_rect, scale_by_half);
+ TextureConverter::EncodeToRamFromTexture(dst, params, native_width, bytes_per_row, num_blocks_y,
+ memory_stride, src_rect, scale_by_half);
}
TextureCache::TextureCache()
@@ -126,6 +133,23 @@ GLuint TextureCache::GetColorCopyPositionUniform() const
return m_colorCopyPositionUniform;
}
+static bool CompilePaletteShader(TLUTFormat tlutfmt, const std::string& vcode,
+ const std::string& pcode, const std::string& gcode)
+{
+ _assert_(IsValidTLUTFormat(tlutfmt));
+ PaletteShader& shader = s_palette_shader[static_cast<int>(tlutfmt)];
+
+ if (!ProgramShaderCache::CompileShader(shader.shader, vcode, pcode, gcode))
+ return false;
+
+ shader.buffer_offset_uniform =
+ glGetUniformLocation(shader.shader.glprogid, "texture_buffer_offset");
+ shader.multiplier_uniform = glGetUniformLocation(shader.shader.glprogid, "multiplier");
+ shader.copy_position_uniform = glGetUniformLocation(shader.shader.glprogid, "copy_position");
+
+ return true;
+}
+
bool TextureCache::CompileShaders()
{
constexpr const char* color_copy_program = "SAMPLER_BINDING(9) uniform sampler2DArray samp9;\n"
@@ -315,44 +339,17 @@ bool TextureCache::CompileShaders()
if (g_ActiveConfig.backend_info.bSupportsPaletteConversion)
{
- if (!ProgramShaderCache::CompileShader(
- s_palette_pixel_shader[GX_TL_IA8], StringFromFormat(vertex_program, prefix, prefix),
- "#define DECODE DecodePixel_IA8" + palette_shader, geo_program))
- {
+ if (!CompilePaletteShader(TLUTFormat::IA8, StringFromFormat(vertex_program, prefix, prefix),
+ "#define DECODE DecodePixel_IA8" + palette_shader, geo_program))
return false;
- }
- s_palette_buffer_offset_uniform[GX_TL_IA8] =
- glGetUniformLocation(s_palette_pixel_shader[GX_TL_IA8].glprogid, "texture_buffer_offset");
- s_palette_multiplier_uniform[GX_TL_IA8] =
- glGetUniformLocation(s_palette_pixel_shader[GX_TL_IA8].glprogid, "multiplier");
- s_palette_copy_position_uniform[GX_TL_IA8] =
- glGetUniformLocation(s_palette_pixel_shader[GX_TL_IA8].glprogid, "copy_position");
-
- if (!ProgramShaderCache::CompileShader(
- s_palette_pixel_shader[GX_TL_RGB565], StringFromFormat(vertex_program, prefix, prefix),
- "#define DECODE DecodePixel_RGB565" + palette_shader, geo_program))
- {
+
+ if (!CompilePaletteShader(TLUTFormat::RGB565, StringFromFormat(vertex_program, prefix, prefix),
+ "#define DECODE DecodePixel_RGB565" + palette_shader, geo_program))
return false;
- }
- s_palette_buffer_offset_uniform[GX_TL_RGB565] = glGetUniformLocation(
- s_palette_pixel_shader[GX_TL_RGB565].glprogid, "texture_buffer_offset");
- s_palette_multiplier_uniform[GX_TL_RGB565] =
- glGetUniformLocation(s_palette_pixel_shader[GX_TL_RGB565].glprogid, "multiplier");
- s_palette_copy_position_uniform[GX_TL_RGB565] =
- glGetUniformLocation(s_palette_pixel_shader[GX_TL_RGB565].glprogid, "copy_position");
-
- if (!ProgramShaderCache::CompileShader(
- s_palette_pixel_shader[GX_TL_RGB5A3], StringFromFormat(vertex_program, prefix, prefix),
- "#define DECODE DecodePixel_RGB5A3" + palette_shader, geo_program))
- {
+
+ if (!CompilePaletteShader(TLUTFormat::RGB5A3, StringFromFormat(vertex_program, prefix, prefix),
+ "#define DECODE DecodePixel_RGB5A3" + palette_shader, geo_program))
return false;
- }
- s_palette_buffer_offset_uniform[GX_TL_RGB5A3] = glGetUniformLocation(
- s_palette_pixel_shader[GX_TL_RGB5A3].glprogid, "texture_buffer_offset");
- s_palette_multiplier_uniform[GX_TL_RGB5A3] =
- glGetUniformLocation(s_palette_pixel_shader[GX_TL_RGB5A3].glprogid, "multiplier");
- s_palette_copy_position_uniform[GX_TL_RGB5A3] =
- glGetUniformLocation(s_palette_pixel_shader[GX_TL_RGB5A3].glprogid, "copy_position");
}
return true;
@@ -364,16 +361,19 @@ void TextureCache::DeleteShaders()
m_depthMatrixProgram.Destroy();
if (g_ActiveConfig.backend_info.bSupportsPaletteConversion)
- for (auto& shader : s_palette_pixel_shader)
- shader.Destroy();
+ for (auto& shader : s_palette_shader)
+ shader.shader.Destroy();
}
-void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source, void* palette,
- TlutFormat format)
+void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source,
+ const void* palette, TLUTFormat tlutfmt)
{
if (!g_ActiveConfig.backend_info.bSupportsPaletteConversion)
return;
+ _assert_(IsValidTLUTFormat(tlutfmt));
+ const PaletteShader& palette_shader = s_palette_shader[static_cast<int>(tlutfmt)];
+
g_renderer->ResetAPIState();
OGLTexture* source_texture = static_cast<OGLTexture*>(source->texture.get());
@@ -385,16 +385,17 @@ void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source,
FramebufferManager::SetFramebuffer(destination_texture->GetFramebuffer());
glViewport(0, 0, destination->GetWidth(), destination->GetHeight());
- s_palette_pixel_shader[format].Bind();
+ palette_shader.shader.Bind();
// C14 textures are currently unsupported
- int size = (source->format & 0xf) == GX_TF_I4 ? 32 : 512;
+ int size = source->format == TextureFormat::I4 ? 32 : 512;
auto buffer = s_palette_stream_buffer->Map(size);
memcpy(buffer.first, palette, size);
s_palette_stream_buffer->Unmap(size);
- glUniform1i(s_palette_buffer_offset_uniform[format], buffer.second / 2);
- glUniform1f(s_palette_multiplier_uniform[format], (source->format & 0xf) == 0 ? 15.0f : 255.0f);
- glUniform4f(s_palette_copy_position_uniform[format], 0.0f, 0.0f,
+ glUniform1i(palette_shader.buffer_offset_uniform, buffer.second / 2);
+ glUniform1f(palette_shader.multiplier_uniform,
+ source->format == TextureFormat::I4 ? 15.0f : 255.0f);
+ glUniform4f(palette_shader.copy_position_uniform, 0.0f, 0.0f,
static_cast<float>(source->GetWidth()), static_cast<float>(source->GetHeight()));
glActiveTexture(GL_TEXTURE10);
@@ -441,7 +442,7 @@ void DestroyTextureDecodingResources()
s_texture_decoding_program_info.clear();
}
-bool TextureCache::SupportsGPUTextureDecode(TextureFormat format, TlutFormat palette_format)
+bool TextureCache::SupportsGPUTextureDecode(TextureFormat format, TLUTFormat palette_format)
{
auto key = std::make_pair(static_cast<u32>(format), static_cast<u32>(palette_format));
auto iter = s_texture_decoding_program_info.find(key);
@@ -483,7 +484,7 @@ bool TextureCache::SupportsGPUTextureDecode(TextureFormat format, TlutFormat pal
void TextureCache::DecodeTextureOnGPU(TCacheEntry* entry, u32 dst_level, const u8* data,
size_t data_size, TextureFormat format, u32 width, u32 height,
u32 aligned_width, u32 aligned_height, u32 row_stride,
- const u8* palette, TlutFormat palette_format)
+ const u8* palette, TLUTFormat palette_format)
{
auto key = std::make_pair(static_cast<u32>(format), static_cast<u32>(palette_format));
auto iter = s_texture_decoding_program_info.find(key);
diff --git a/Source/Core/VideoBackends/OGL/TextureCache.h b/Source/Core/VideoBackends/OGL/TextureCache.h
index 93805de0d1..1cf4084007 100644
--- a/Source/Core/VideoBackends/OGL/TextureCache.h
+++ b/Source/Core/VideoBackends/OGL/TextureCache.h
@@ -26,23 +26,23 @@ public:
static TextureCache* GetInstance();
- bool SupportsGPUTextureDecode(TextureFormat format, TlutFormat palette_format) override;
+ bool SupportsGPUTextureDecode(TextureFormat format, TLUTFormat palette_format) override;
void DecodeTextureOnGPU(TCacheEntry* entry, u32 dst_level, const u8* data, size_t data_size,
TextureFormat format, u32 width, u32 height, u32 aligned_width,
u32 aligned_height, u32 row_stride, const u8* palette,
- TlutFormat palette_format) override;
+ TLUTFormat palette_format) override;
const SHADER& GetColorCopyProgram() const;
GLuint GetColorCopyPositionUniform() const;
private:
std::unique_ptr<AbstractTexture> CreateTexture(const TextureConfig& config) override;
- void ConvertTexture(TCacheEntry* destination, TCacheEntry* source, void* palette,
- TlutFormat format) override;
+ void ConvertTexture(TCacheEntry* destination, TCacheEntry* source, const void* palette,
+ TLUTFormat format) override;
- void CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_width, u32 bytes_per_row,
- u32 num_blocks_y, u32 memory_stride, bool is_depth_copy,
- const EFBRectangle& src_rect, bool scale_by_half) override;
+ void CopyEFB(u8* dst, const EFBCopyParams& params, u32 native_width, u32 bytes_per_row,
+ u32 num_blocks_y, u32 memory_stride, const EFBRectangle& src_rect,
+ bool scale_by_half) override;
void CopyEFBToCacheEntry(TCacheEntry* entry, bool is_depth_copy, const EFBRectangle& src_rect,
bool scale_by_half, unsigned int cbuf_id, const float* colmat) override;
diff --git a/Source/Core/VideoBackends/OGL/TextureConverter.cpp b/Source/Core/VideoBackends/OGL/TextureConverter.cpp
index d352ea6701..e9a3eaa94f 100644
--- a/Source/Core/VideoBackends/OGL/TextureConverter.cpp
+++ b/Source/Core/VideoBackends/OGL/TextureConverter.cpp
@@ -51,7 +51,7 @@ struct EncodingProgram
SHADER program;
GLint copy_position_uniform;
};
-static std::map<EFBCopyFormat, EncodingProgram> s_encoding_programs;
+static std::map<EFBCopyParams, EncodingProgram> s_encoding_programs;
static GLuint s_PBO = 0; // for readback with different strides
@@ -136,13 +136,13 @@ static void CreatePrograms()
ProgramShaderCache::CompileShader(s_yuyvToRgbProgram, VProgramYuyvToRgb, FProgramYuyvToRgb);
}
-static EncodingProgram& GetOrCreateEncodingShader(const EFBCopyFormat& format)
+static EncodingProgram& GetOrCreateEncodingShader(const EFBCopyParams& params)
{
- auto iter = s_encoding_programs.find(format);
+ auto iter = s_encoding_programs.find(params);
if (iter != s_encoding_programs.end())
return iter->second;
- const char* shader = TextureConversionShader::GenerateEncodingShader(format, APIType::OpenGL);
+ const char* shader = TextureConversionShader::GenerateEncodingShader(params, APIType::OpenGL);
#if defined(_DEBUG) || defined(DEBUGFAST)
if (g_ActiveConfig.iLog & CONF_SAVESHADERS && shader)
@@ -166,7 +166,7 @@ static EncodingProgram& GetOrCreateEncodingShader(const EFBCopyFormat& format)
PanicAlert("Failed to compile texture encoding shader.");
program.copy_position_uniform = glGetUniformLocation(program.program.glprogid, "position");
- return s_encoding_programs.emplace(format, program).first->second;
+ return s_encoding_programs.emplace(params, program).first->second;
}
void Init()
@@ -271,24 +271,24 @@ static void EncodeToRamUsingShader(GLuint srcTexture, u8* destAddr, u32 dst_line
glBindBuffer(GL_PIXEL_PACK_BUFFER, 0);
}
-void EncodeToRamFromTexture(u8* dest_ptr, const EFBCopyFormat& format, u32 native_width,
+void EncodeToRamFromTexture(u8* dest_ptr, const EFBCopyParams& params, u32 native_width,
u32 bytes_per_row, u32 num_blocks_y, u32 memory_stride,
- bool is_depth_copy, const EFBRectangle& src_rect, bool scale_by_half)
+ const EFBRectangle& src_rect, bool scale_by_half)
{
g_renderer->ResetAPIState();
- EncodingProgram& texconv_shader = GetOrCreateEncodingShader(format);
+ EncodingProgram& texconv_shader = GetOrCreateEncodingShader(params);
texconv_shader.program.Bind();
glUniform4i(texconv_shader.copy_position_uniform, src_rect.left, src_rect.top, native_width,
scale_by_half ? 2 : 1);
- const GLuint read_texture = is_depth_copy ?
+ 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 && !is_depth_copy);
+ scale_by_half && !params.depth);
FramebufferManager::SetFramebuffer(0);
g_renderer->RestoreAPIState();
diff --git a/Source/Core/VideoBackends/OGL/TextureConverter.h b/Source/Core/VideoBackends/OGL/TextureConverter.h
index 11576f9aa1..3b535752a3 100644
--- a/Source/Core/VideoBackends/OGL/TextureConverter.h
+++ b/Source/Core/VideoBackends/OGL/TextureConverter.h
@@ -7,9 +7,10 @@
#include "Common/CommonTypes.h"
#include "Common/GL/GLUtil.h"
-#include "VideoCommon/TextureDecoder.h"
#include "VideoCommon/VideoCommon.h"
+struct EFBCopyParams;
+
namespace OGL
{
// Converts textures between formats using shaders
@@ -25,9 +26,9 @@ void EncodeToRamYUYV(GLuint srcTexture, const TargetRectangle& sourceRc, u8* des
void DecodeToTexture(u32 xfbAddr, int srcWidth, int srcHeight, GLuint destTexture);
// returns size of the encoded data (in bytes)
-void EncodeToRamFromTexture(u8* dest_ptr, const EFBCopyFormat& format, u32 native_width,
+void EncodeToRamFromTexture(u8* dest_ptr, const EFBCopyParams& params, u32 native_width,
u32 bytes_per_row, u32 num_blocks_y, u32 memory_stride,
- bool is_depth_copy, const EFBRectangle& src_rect, bool scale_by_half);
+ const EFBRectangle& src_rect, bool scale_by_half);
}
} // namespace OGL
diff --git a/Source/Core/VideoBackends/Software/SWmain.cpp b/Source/Core/VideoBackends/Software/SWmain.cpp
index 910de9697d..d1f9ac3bb0 100644
--- a/Source/Core/VideoBackends/Software/SWmain.cpp
+++ b/Source/Core/VideoBackends/Software/SWmain.cpp
@@ -50,13 +50,13 @@ class TextureCache : public TextureCacheBase
public:
bool CompileShaders() override { return true; }
void DeleteShaders() override {}
- void ConvertTexture(TCacheEntry* entry, TCacheEntry* unconverted, void* palette,
- TlutFormat format) override
+ void ConvertTexture(TCacheEntry* entry, TCacheEntry* unconverted, const void* palette,
+ TLUTFormat format) override
{
}
- void CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_width, u32 bytes_per_row,
- u32 num_blocks_y, u32 memory_stride, bool is_depth_copy,
- const EFBRectangle& src_rect, bool scale_by_half) override
+ void CopyEFB(u8* dst, const EFBCopyParams& params, u32 native_width, u32 bytes_per_row,
+ u32 num_blocks_y, u32 memory_stride, const EFBRectangle& src_rect,
+ bool scale_by_half) override
{
EfbCopy::CopyEfb();
}
diff --git a/Source/Core/VideoBackends/Software/TextureEncoder.cpp b/Source/Core/VideoBackends/Software/TextureEncoder.cpp
index 92dffe1b4b..6181d56dd4 100644
--- a/Source/Core/VideoBackends/Software/TextureEncoder.cpp
+++ b/Source/Core/VideoBackends/Software/TextureEncoder.cpp
@@ -263,7 +263,7 @@ static void SetSpans(int sBlkSize, int tBlkSize, s32* tSpan, s32* sBlkSpan, s32*
dstBlockStart += writeStride; \
}
-static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
+static void EncodeRGBA6(u8* dst, const u8* src, EFBCopyFormat format, bool yuv)
{
u16 sBlkCount, tBlkCount, sBlkSize, tBlkSize;
s32 tSpan, sBlkSpan, tBlkSpan, writeStride;
@@ -273,62 +273,121 @@ static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
switch (format)
{
- case GX_TF_I4:
+ case EFBCopyFormat::R4:
SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
sBlkSize /= 2;
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- RGBA_to_RGB8(src, &r, &g, &b);
- src += readStride;
- *dst = RGB8_to_I(r, g, b) & 0xf0;
+ ENCODE_LOOP_BLOCKS
+ {
+ RGBA_to_RGB8(src, &r, &g, &b);
+ src += readStride;
+ *dst = RGB8_to_I(r, g, b) & 0xf0;
- RGBA_to_RGB8(src, &r, &g, &b);
- src += readStride;
- *dst |= RGB8_to_I(r, g, b) >> 4;
- dst++;
+ RGBA_to_RGB8(src, &r, &g, &b);
+ src += readStride;
+ *dst |= RGB8_to_I(r, g, b) >> 4;
+ dst++;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ u32 srcColor = *(u32*)src;
+ src += readStride;
+ *dst = (srcColor >> 16) & 0xf0;
+
+ srcColor = *(u32*)src;
+ src += readStride;
+ *dst |= (srcColor >> 20) & 0x0f;
+ dst++;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_I8:
+ case EFBCopyFormat::R8_0x1:
+ case EFBCopyFormat::R8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- RGBA_to_RGB8(src, &r, &g, &b);
- src += readStride;
- *dst++ = RGB8_to_I(r, g, b);
+ ENCODE_LOOP_BLOCKS
+ {
+ RGBA_to_RGB8(src, &r, &g, &b);
+ src += readStride;
+ *dst++ = RGB8_to_I(r, g, b);
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ u32 srcColor = *(u32*)src;
+ *dst++ = Convert6To8((srcColor >> 18) & 0x3f);
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_IA4:
+ case EFBCopyFormat::RA4:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- RGBA_to_RGBA8(src, &r, &g, &b, &a);
- src += readStride;
- *dst++ = (a & 0xf0) | (RGB8_to_I(r, g, b) >> 4);
+ ENCODE_LOOP_BLOCKS
+ {
+ RGBA_to_RGBA8(src, &r, &g, &b, &a);
+ src += readStride;
+ *dst++ = (a & 0xf0) | (RGB8_to_I(r, g, b) >> 4);
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ u32 srcColor = *(u32*)src;
+ src += readStride;
+ *dst++ = ((srcColor << 2) & 0xf0) | ((srcColor >> 20) & 0x0f);
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_IA8:
+ case EFBCopyFormat::RA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- RGBA_to_RGBA8(src, &r, &g, &b, &a);
- src += readStride;
- *dst++ = a;
- *dst++ = RGB8_to_I(r, g, b);
+ ENCODE_LOOP_BLOCKS
+ {
+ RGBA_to_RGBA8(src, &r, &g, &b, &a);
+ src += readStride;
+ *dst++ = a;
+ *dst++ = RGB8_to_I(r, g, b);
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ u32 srcColor = *(u32*)src;
+ src += readStride;
+ *dst++ = Convert6To8(srcColor & 0x3f);
+ *dst++ = Convert6To8((srcColor >> 18) & 0x3f);
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_RGB565:
+ case EFBCopyFormat::RGB565:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -344,7 +403,7 @@ static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_RGB5A3:
+ case EFBCopyFormat::RGB5A3:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -367,7 +426,7 @@ static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_RGBA8:
+ case EFBCopyFormat::RGBA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -379,50 +438,7 @@ static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS2
break;
- case GX_CTF_R4:
- SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- sBlkSize /= 2;
- ENCODE_LOOP_BLOCKS
- {
- u32 srcColor = *(u32*)src;
- src += readStride;
- *dst = (srcColor >> 16) & 0xf0;
-
- srcColor = *(u32*)src;
- src += readStride;
- *dst |= (srcColor >> 20) & 0x0f;
- dst++;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_RA4:
- SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- u32 srcColor = *(u32*)src;
- src += readStride;
- *dst++ = ((srcColor << 2) & 0xf0) | ((srcColor >> 20) & 0x0f);
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_RA8:
- SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- u32 srcColor = *(u32*)src;
- src += readStride;
- *dst++ = Convert6To8(srcColor & 0x3f);
- *dst++ = Convert6To8((srcColor >> 18) & 0x3f);
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_A8:
+ case EFBCopyFormat::A8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -434,19 +450,7 @@ static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_R8:
- SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- u32 srcColor = *(u32*)src;
- *dst++ = Convert6To8((srcColor >> 18) & 0x3f);
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_G8:
+ case EFBCopyFormat::G8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -458,7 +462,7 @@ static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_B8:
+ case EFBCopyFormat::B8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -470,7 +474,7 @@ static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_RG8:
+ case EFBCopyFormat::RG8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -483,7 +487,7 @@ static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_GB8:
+ case EFBCopyFormat::GB8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -497,12 +501,12 @@ static void EncodeRGBA6(u8* dst, const u8* src, u32 format)
break;
default:
- PanicAlert("Unknown texture copy format: 0x%x\n", format);
+ PanicAlert("Unknown texture copy format: 0x%x\n", static_cast<int>(format));
break;
}
}
-static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
+static void EncodeRGBA6halfscale(u8* dst, const u8* src, EFBCopyFormat format, bool yuv)
{
u16 sBlkCount, tBlkCount, sBlkSize, tBlkSize;
s32 tSpan, sBlkSpan, tBlkSpan, writeStride;
@@ -512,62 +516,121 @@ static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
switch (format)
{
- case GX_TF_I4:
+ case EFBCopyFormat::R4:
SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
sBlkSize /= 2;
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- BoxfilterRGBA_to_RGB8(src, &r, &g, &b);
- src += readStride;
- *dst = RGB8_to_I(r, g, b) & 0xf0;
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGBA_to_RGB8(src, &r, &g, &b);
+ src += readStride;
+ *dst = RGB8_to_I(r, g, b) & 0xf0;
- BoxfilterRGBA_to_RGB8(src, &r, &g, &b);
- src += readStride;
- *dst |= RGB8_to_I(r, g, b) >> 4;
- dst++;
+ BoxfilterRGBA_to_RGB8(src, &r, &g, &b);
+ src += readStride;
+ *dst |= RGB8_to_I(r, g, b) >> 4;
+ dst++;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGBA_to_x8(src, &r, 18);
+ src += readStride;
+ *dst = r & 0xf0;
+
+ BoxfilterRGBA_to_x8(src, &r, 18);
+ src += readStride;
+ *dst |= r >> 4;
+ dst++;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_I8:
+ case EFBCopyFormat::R8_0x1:
+ case EFBCopyFormat::R8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- BoxfilterRGBA_to_RGB8(src, &r, &g, &b);
- src += readStride;
- *dst++ = RGB8_to_I(r, g, b);
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGBA_to_RGB8(src, &r, &g, &b);
+ src += readStride;
+ *dst++ = RGB8_to_I(r, g, b);
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGBA_to_x8(src, &r, 18);
+ *dst++ = r;
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_IA4:
+ case EFBCopyFormat::RA4:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- BoxfilterRGBA_to_RGBA8(src, &r, &g, &b, &a);
- src += readStride;
- *dst++ = (a & 0xf0) | (RGB8_to_I(r, g, b) >> 4);
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGBA_to_RGBA8(src, &r, &g, &b, &a);
+ src += readStride;
+ *dst++ = (a & 0xf0) | (RGB8_to_I(r, g, b) >> 4);
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGBA_to_xx8(src, &r, &a, 18, 0);
+ src += readStride;
+ *dst++ = (a & 0xf0) | (r >> 4);
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_IA8:
+ case EFBCopyFormat::RA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- BoxfilterRGBA_to_RGBA8(src, &r, &g, &b, &a);
- src += readStride;
- *dst++ = a;
- *dst++ = RGB8_to_I(r, g, b);
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGBA_to_RGBA8(src, &r, &g, &b, &a);
+ src += readStride;
+ *dst++ = a;
+ *dst++ = RGB8_to_I(r, g, b);
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGBA_to_xx8(src, &r, &a, 18, 0);
+ src += readStride;
+ *dst++ = a;
+ *dst++ = r;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_RGB565:
+ case EFBCopyFormat::RGB565:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -582,7 +645,7 @@ static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_RGB5A3:
+ case EFBCopyFormat::RGB5A3:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -602,7 +665,7 @@ static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_RGBA8:
+ case EFBCopyFormat::RGBA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -614,50 +677,7 @@ static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS2
break;
- case GX_CTF_R4:
- SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- sBlkSize /= 2;
- ENCODE_LOOP_BLOCKS
- {
- BoxfilterRGBA_to_x8(src, &r, 18);
- src += readStride;
- *dst = r & 0xf0;
-
- BoxfilterRGBA_to_x8(src, &r, 18);
- src += readStride;
- *dst |= r >> 4;
- dst++;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_RA4:
- SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- BoxfilterRGBA_to_xx8(src, &r, &a, 18, 0);
- src += readStride;
- *dst++ = (a & 0xf0) | (r >> 4);
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_RA8:
- SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- BoxfilterRGBA_to_xx8(src, &r, &a, 18, 0);
- src += readStride;
- *dst++ = a;
- *dst++ = r;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_A8:
+ case EFBCopyFormat::A8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -669,19 +689,7 @@ static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_R8:
- SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- BoxfilterRGBA_to_x8(src, &r, 18);
- *dst++ = r;
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_G8:
+ case EFBCopyFormat::G8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -693,7 +701,7 @@ static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_B8:
+ case EFBCopyFormat::B8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -705,7 +713,7 @@ static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_RG8:
+ case EFBCopyFormat::RG8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -718,7 +726,7 @@ static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_GB8:
+ case EFBCopyFormat::GB8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -732,12 +740,12 @@ static void EncodeRGBA6halfscale(u8* dst, const u8* src, u32 format)
break;
default:
- PanicAlert("Unknown texture copy format: 0x%x\n", format);
+ PanicAlert("Unknown texture copy format: 0x%x\n", static_cast<int>(format));
break;
}
}
-static void EncodeRGB8(u8* dst, const u8* src, u32 format)
+static void EncodeRGB8(u8* dst, const u8* src, EFBCopyFormat format, bool yuv)
{
u16 sBlkCount, tBlkCount, sBlkSize, tBlkSize;
s32 tSpan, sBlkSpan, tBlkSpan, writeStride;
@@ -746,58 +754,113 @@ static void EncodeRGB8(u8* dst, const u8* src, u32 format)
switch (format)
{
- case GX_TF_I4:
+ case EFBCopyFormat::R4:
SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
sBlkSize /= 2;
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- *dst = RGB8_to_I(src[2], src[1], src[0]) & 0xf0;
- src += readStride;
+ ENCODE_LOOP_BLOCKS
+ {
+ *dst = RGB8_to_I(src[2], src[1], src[0]) & 0xf0;
+ src += readStride;
- *dst |= RGB8_to_I(src[2], src[1], src[0]) >> 4;
- src += readStride;
- dst++;
+ *dst |= RGB8_to_I(src[2], src[1], src[0]) >> 4;
+ src += readStride;
+ dst++;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ *dst = src[2] & 0xf0;
+ src += readStride;
+
+ *dst |= src[2] >> 4;
+ src += readStride;
+
+ dst++;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_I8:
+ case EFBCopyFormat::R8_0x1:
+ case EFBCopyFormat::R8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- *dst++ = RGB8_to_I(src[2], src[1], src[0]);
- src += readStride;
+ ENCODE_LOOP_BLOCKS
+ {
+ *dst++ = RGB8_to_I(src[2], src[1], src[0]);
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ *dst++ = src[2];
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_IA4:
+ case EFBCopyFormat::RA4:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- *dst++ = 0xf0 | (RGB8_to_I(src[2], src[1], src[0]) >> 4);
- src += readStride;
+ ENCODE_LOOP_BLOCKS
+ {
+ *dst++ = 0xf0 | (RGB8_to_I(src[2], src[1], src[0]) >> 4);
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ *dst++ = 0xf0 | (src[2] >> 4);
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_IA8:
+ case EFBCopyFormat::RA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- *dst++ = 0xff;
- *dst++ = RGB8_to_I(src[2], src[1], src[0]);
+ ENCODE_LOOP_BLOCKS
+ {
+ *dst++ = 0xff;
+ *dst++ = RGB8_to_I(src[2], src[1], src[0]);
- src += readStride;
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ *dst++ = 0xff;
+ *dst++ = src[2];
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_RGB565:
+ case EFBCopyFormat::RGB565:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -810,7 +873,7 @@ static void EncodeRGB8(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_RGB5A3:
+ case EFBCopyFormat::RGB5A3:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -824,7 +887,7 @@ static void EncodeRGB8(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_RGBA8:
+ case EFBCopyFormat::RGBA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -839,65 +902,14 @@ static void EncodeRGB8(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS2
break;
- case GX_CTF_R4:
- SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- sBlkSize /= 2;
- ENCODE_LOOP_BLOCKS
- {
- *dst = src[2] & 0xf0;
- src += readStride;
-
- *dst |= src[2] >> 4;
- src += readStride;
-
- dst++;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_RA4:
- SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- *dst++ = 0xf0 | (src[2] >> 4);
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_RA8:
- SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- *dst++ = 0xff;
- *dst++ = src[2];
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_A8:
+ case EFBCopyFormat::A8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS { *dst++ = 0xff; }
ENCODE_LOOP_SPANS
break;
- case GX_CTF_R8:
- SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- *dst++ = src[2];
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_G8:
+ case EFBCopyFormat::G8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -908,7 +920,7 @@ static void EncodeRGB8(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_B8:
+ case EFBCopyFormat::B8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -919,11 +931,12 @@ static void EncodeRGB8(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_RG8:
+ case EFBCopyFormat::RG8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
{
+ // FIXME: is this backwards?
*dst++ = src[1];
*dst++ = src[2];
src += readStride;
@@ -931,7 +944,7 @@ static void EncodeRGB8(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_GB8:
+ case EFBCopyFormat::GB8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -944,12 +957,12 @@ static void EncodeRGB8(u8* dst, const u8* src, u32 format)
break;
default:
- PanicAlert("Unknown texture copy format: 0x%x\n", format);
+ PanicAlert("Unknown texture copy format: 0x%x\n", static_cast<int>(format));
break;
}
}
-static void EncodeRGB8halfscale(u8* dst, const u8* src, u32 format)
+static void EncodeRGB8halfscale(u8* dst, const u8* src, EFBCopyFormat format, bool yuv)
{
u16 sBlkCount, tBlkCount, sBlkSize, tBlkSize;
s32 tSpan, sBlkSpan, tBlkSpan, writeStride;
@@ -959,62 +972,122 @@ static void EncodeRGB8halfscale(u8* dst, const u8* src, u32 format)
switch (format)
{
- case GX_TF_I4:
+ case EFBCopyFormat::R4:
SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
sBlkSize /= 2;
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- BoxfilterRGB_to_RGB8(src, &r, &g, &b);
- *dst = RGB8_to_I(r, g, b) & 0xf0;
- src += readStride;
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGB_to_RGB8(src, &r, &g, &b);
+ *dst = RGB8_to_I(r, g, b) & 0xf0;
+ src += readStride;
- BoxfilterRGB_to_RGB8(src, &r, &g, &b);
- *dst |= RGB8_to_I(r, g, b) >> 4;
- src += readStride;
- dst++;
+ BoxfilterRGB_to_RGB8(src, &r, &g, &b);
+ *dst |= RGB8_to_I(r, g, b) >> 4;
+ src += readStride;
+ dst++;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGB_to_x8(src, &r, 2);
+ *dst = r & 0xf0;
+ src += readStride;
+
+ BoxfilterRGB_to_x8(src, &r, 2);
+ *dst |= r >> 4;
+ src += readStride;
+
+ dst++;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_I8:
+ case EFBCopyFormat::R8_0x1:
+ case EFBCopyFormat::R8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- BoxfilterRGB_to_RGB8(src, &r, &g, &b);
- *dst++ = RGB8_to_I(r, g, b);
- src += readStride;
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGB_to_RGB8(src, &r, &g, &b);
+ *dst++ = RGB8_to_I(r, g, b);
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGB_to_x8(src, &r, 2);
+ *dst++ = r;
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_IA4:
+ case EFBCopyFormat::RA4:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- BoxfilterRGB_to_RGB8(src, &r, &g, &b);
- *dst++ = 0xf0 | (RGB8_to_I(r, g, b) >> 4);
- src += readStride;
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGB_to_RGB8(src, &r, &g, &b);
+ *dst++ = 0xf0 | (RGB8_to_I(r, g, b) >> 4);
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGB_to_x8(src, &r, 2);
+ *dst++ = 0xf0 | (r >> 4);
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_IA8:
+ case EFBCopyFormat::RA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
+ if (yuv)
{
- BoxfilterRGB_to_RGB8(src, &r, &g, &b);
- *dst++ = 0xff;
- *dst++ = RGB8_to_I(r, g, b);
- src += readStride;
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGB_to_RGB8(src, &r, &g, &b);
+ *dst++ = 0xff;
+ *dst++ = RGB8_to_I(r, g, b);
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
+ }
+ else
+ {
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGB_to_x8(src, &r, 2);
+ *dst++ = 0xff;
+ *dst++ = r;
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
}
- ENCODE_LOOP_SPANS
break;
- case GX_TF_RGB565:
+ case EFBCopyFormat::RGB565:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1028,7 +1101,7 @@ static void EncodeRGB8halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_RGB5A3:
+ case EFBCopyFormat::RGB5A3:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1042,7 +1115,7 @@ static void EncodeRGB8halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_RGBA8:
+ case EFBCopyFormat::RGBA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1058,70 +1131,14 @@ static void EncodeRGB8halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS2
break;
- case GX_CTF_R4:
- SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- sBlkSize /= 2;
- ENCODE_LOOP_BLOCKS
- {
- BoxfilterRGB_to_x8(src, &r, 2);
- *dst = r & 0xf0;
- src += readStride;
-
- BoxfilterRGB_to_x8(src, &r, 2);
- *dst |= r >> 4;
- src += readStride;
-
- dst++;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_RA4:
- SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- BoxfilterRGB_to_x8(src, &r, 2);
- *dst++ = 0xf0 | (r >> 4);
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_RA8:
- SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- BoxfilterRGB_to_x8(src, &r, 2);
- *dst++ = 0xff;
- *dst++ = r;
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_A8:
+ case EFBCopyFormat::A8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS { *dst++ = 0xff; }
ENCODE_LOOP_SPANS
break;
- case GX_CTF_R8:
- SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- BoxfilterRGB_to_x8(src, &r, 2);
- *dst++ = r;
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
-
- case GX_CTF_G8:
+ case EFBCopyFormat::G8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1133,7 +1150,7 @@ static void EncodeRGB8halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_B8:
+ case EFBCopyFormat::B8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1145,7 +1162,7 @@ static void EncodeRGB8halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_RG8:
+ case EFBCopyFormat::RG8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1158,7 +1175,7 @@ static void EncodeRGB8halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_GB8:
+ case EFBCopyFormat::GB8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1172,12 +1189,12 @@ static void EncodeRGB8halfscale(u8* dst, const u8* src, u32 format)
break;
default:
- PanicAlert("Unknown texture copy format: 0x%x\n", format);
+ PanicAlert("Unknown texture copy format: 0x%x\n", static_cast<int>(format));
break;
}
}
-static void EncodeZ24(u8* dst, const u8* src, u32 format)
+static void EncodeZ24(u8* dst, const u8* src, EFBCopyFormat format)
{
u16 sBlkCount, tBlkCount, sBlkSize, tBlkSize;
s32 tSpan, sBlkSpan, tBlkSpan, writeStride;
@@ -1186,7 +1203,8 @@ static void EncodeZ24(u8* dst, const u8* src, u32 format)
switch (format)
{
- case GX_TF_Z8:
+ case EFBCopyFormat::R8_0x1:
+ case EFBCopyFormat::R8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1197,19 +1215,9 @@ static void EncodeZ24(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_Z16:
- SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- *dst++ = src[1];
- *dst++ = src[2];
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
+ // FIXME: handle RA8?
- case GX_TF_Z24X8:
+ case EFBCopyFormat::RGBA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1224,7 +1232,7 @@ static void EncodeZ24(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS2
break;
- case GX_CTF_Z4:
+ case EFBCopyFormat::R4:
SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
sBlkSize /= 2;
@@ -1241,7 +1249,7 @@ static void EncodeZ24(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_Z8M:
+ case EFBCopyFormat::G8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1252,7 +1260,7 @@ static void EncodeZ24(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_Z8L:
+ case EFBCopyFormat::B8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1263,7 +1271,20 @@ static void EncodeZ24(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_Z16L:
+ case EFBCopyFormat::RG8:
+ SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
+ SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
+ ENCODE_LOOP_BLOCKS
+ {
+ // FIXME: should these be reversed?
+ *dst++ = src[1];
+ *dst++ = src[2];
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
+ break;
+
+ case EFBCopyFormat::GB8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1276,12 +1297,12 @@ static void EncodeZ24(u8* dst, const u8* src, u32 format)
break;
default:
- PanicAlert("Unknown texture copy format: 0x%x\n", format);
+ PanicAlert("Unknown texture copy format: 0x%x\n", static_cast<int>(format));
break;
}
}
-static void EncodeZ24halfscale(u8* dst, const u8* src, u32 format)
+static void EncodeZ24halfscale(u8* dst, const u8* src, EFBCopyFormat format)
{
u16 sBlkCount, tBlkCount, sBlkSize, tBlkSize;
s32 tSpan, sBlkSpan, tBlkSpan, writeStride;
@@ -1291,7 +1312,8 @@ static void EncodeZ24halfscale(u8* dst, const u8* src, u32 format)
switch (format)
{
- case GX_TF_Z8:
+ case EFBCopyFormat::R8_0x1:
+ case EFBCopyFormat::R8:
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1303,20 +1325,9 @@ static void EncodeZ24halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_TF_Z16:
- SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
- SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
- ENCODE_LOOP_BLOCKS
- {
- BoxfilterRGB_to_xx8(src, &g, &b, 1, 2);
- *dst++ = b;
- *dst++ = g;
- src += readStride;
- }
- ENCODE_LOOP_SPANS
- break;
+ // FIXME: handle RA8?
- case GX_TF_Z24X8:
+ case EFBCopyFormat::RGBA8:
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1329,7 +1340,7 @@ static void EncodeZ24halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS2
break;
- case GX_CTF_Z4:
+ case EFBCopyFormat::R4: // Z4
SetBlockDimensions(3, 3, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
sBlkSize /= 2;
@@ -1348,7 +1359,7 @@ static void EncodeZ24halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_Z8M:
+ case EFBCopyFormat::G8: // Z8M
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1360,7 +1371,7 @@ static void EncodeZ24halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_Z8L:
+ case EFBCopyFormat::B8: // Z8L
SetBlockDimensions(3, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1372,7 +1383,7 @@ static void EncodeZ24halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
- case GX_CTF_Z16L:
+ case EFBCopyFormat::RG8: // RG8
SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
ENCODE_LOOP_BLOCKS
@@ -1385,8 +1396,22 @@ static void EncodeZ24halfscale(u8* dst, const u8* src, u32 format)
ENCODE_LOOP_SPANS
break;
+ case EFBCopyFormat::GB8:
+ SetBlockDimensions(2, 2, &sBlkCount, &tBlkCount, &sBlkSize, &tBlkSize);
+ SetSpans(sBlkSize, tBlkSize, &tSpan, &sBlkSpan, &tBlkSpan, &writeStride);
+ ENCODE_LOOP_BLOCKS
+ {
+ BoxfilterRGB_to_xx8(src, &g, &b, 1, 2);
+ // FIXME: is this backwards?
+ *dst++ = b;
+ *dst++ = g;
+ src += readStride;
+ }
+ ENCODE_LOOP_SPANS
+ break;
+
default:
- PanicAlert("Unknown texture copy format: 0x%x\n", format);
+ PanicAlert("Unknown texture copy format: 0x%x\n", static_cast<int>(format));
break;
}
}
@@ -1396,21 +1421,7 @@ void Encode(u8* dest_ptr)
auto pixelformat = bpmem.zcontrol.pixel_format;
bool bFromZBuffer = pixelformat == PEControl::Z24;
bool bIsIntensityFmt = bpmem.triggerEFBCopy.intensity_fmt > 0;
- u32 copyfmt = ((bpmem.triggerEFBCopy.target_pixel_format / 2) +
- ((bpmem.triggerEFBCopy.target_pixel_format & 1) * 8));
-
- // pack copy format information into a single variable
- u32 format = copyfmt;
- if (bFromZBuffer)
- {
- format |= _GX_TF_ZTF;
- if (copyfmt == 11)
- format = GX_TF_Z16;
- else if (format < GX_TF_Z8 || format > GX_TF_Z24X8)
- format |= _GX_TF_CTF;
- }
- else if (copyfmt > GX_TF_RGBA8 || (copyfmt < GX_TF_RGB565 && !bIsIntensityFmt))
- format |= _GX_TF_CTF;
+ EFBCopyFormat copyfmt = bpmem.triggerEFBCopy.tp_realFormat();
const u8* src =
EfbInterface::GetPixelPointer(bpmem.copyTexSrcXY.x, bpmem.copyTexSrcXY.y, bFromZBuffer);
@@ -1418,24 +1429,24 @@ void Encode(u8* dest_ptr)
if (bpmem.triggerEFBCopy.half_scale)
{
if (pixelformat == PEControl::RGBA6_Z24)
- EncodeRGBA6halfscale(dest_ptr, src, format);
+ EncodeRGBA6halfscale(dest_ptr, src, copyfmt, bIsIntensityFmt);
else if (pixelformat == PEControl::RGB8_Z24)
- EncodeRGB8halfscale(dest_ptr, src, format);
+ EncodeRGB8halfscale(dest_ptr, src, copyfmt, bIsIntensityFmt);
else if (pixelformat == PEControl::RGB565_Z16) // not supported
- EncodeRGB8halfscale(dest_ptr, src, format);
+ EncodeRGB8halfscale(dest_ptr, src, copyfmt, bIsIntensityFmt);
else if (pixelformat == PEControl::Z24)
- EncodeZ24halfscale(dest_ptr, src, format);
+ EncodeZ24halfscale(dest_ptr, src, copyfmt);
}
else
{
if (pixelformat == PEControl::RGBA6_Z24)
- EncodeRGBA6(dest_ptr, src, format);
+ EncodeRGBA6(dest_ptr, src, copyfmt, bIsIntensityFmt);
else if (pixelformat == PEControl::RGB8_Z24)
- EncodeRGB8(dest_ptr, src, format);
+ EncodeRGB8(dest_ptr, src, copyfmt, bIsIntensityFmt);
else if (pixelformat == PEControl::RGB565_Z16) // not supported
- EncodeRGB8(dest_ptr, src, format);
+ EncodeRGB8(dest_ptr, src, copyfmt, bIsIntensityFmt);
else if (pixelformat == PEControl::Z24)
- EncodeZ24(dest_ptr, src, format);
+ EncodeZ24(dest_ptr, src, copyfmt);
}
}
}
diff --git a/Source/Core/VideoBackends/Software/TextureSampler.cpp b/Source/Core/VideoBackends/Software/TextureSampler.cpp
index 248e4a6f19..0decf134c9 100644
--- a/Source/Core/VideoBackends/Software/TextureSampler.cpp
+++ b/Source/Core/VideoBackends/Software/TextureSampler.cpp
@@ -111,13 +111,14 @@ void SampleMip(s32 s, s32 t, s32 mip, bool linear, u8 texmap, u8* sample)
TexMode0& tm0 = texUnit.texMode0[subTexmap];
TexImage0& ti0 = texUnit.texImage0[subTexmap];
TexTLUT& texTlut = texUnit.texTlut[subTexmap];
- TlutFormat tlutfmt = (TlutFormat)texTlut.tlut_format;
+ TextureFormat texfmt = static_cast<TextureFormat>(ti0.format);
+ TLUTFormat tlutfmt = static_cast<TLUTFormat>(texTlut.tlut_format);
u8 *imageSrc, *imageSrcOdd = nullptr;
if (texUnit.texImage1[subTexmap].image_type)
{
imageSrc = &texMem[texUnit.texImage1[subTexmap].tmem_even * TMEM_LINE_SIZE];
- if (ti0.format == GX_TF_RGBA8)
+ if (texfmt == TextureFormat::RGBA8)
imageSrcOdd = &texMem[texUnit.texImage2[subTexmap].tmem_odd * TMEM_LINE_SIZE];
}
else
@@ -139,9 +140,9 @@ void SampleMip(s32 s, s32 t, s32 mip, bool linear, u8 texmap, u8* sample)
int mipWidth = imageWidth + 1;
int mipHeight = imageHeight + 1;
- int fmtWidth = TexDecoder_GetBlockWidthInTexels(ti0.format);
- int fmtHeight = TexDecoder_GetBlockHeightInTexels(ti0.format);
- int fmtDepth = TexDecoder_GetTexelSizeInNibbles(ti0.format);
+ int fmtWidth = TexDecoder_GetBlockWidthInTexels(texfmt);
+ int fmtHeight = TexDecoder_GetBlockHeightInTexels(texfmt);
+ int fmtDepth = TexDecoder_GetTexelSizeInNibbles(texfmt);
imageWidth >>= mip;
imageHeight >>= mip;
@@ -186,21 +187,21 @@ void SampleMip(s32 s, s32 t, s32 mip, bool linear, u8 texmap, u8* sample)
WrapCoord(&imageSPlus1, tm0.wrap_s, imageWidth);
WrapCoord(&imageTPlus1, tm0.wrap_t, imageHeight);
- if (!(ti0.format == GX_TF_RGBA8 && texUnit.texImage1[subTexmap].image_type))
+ if (!(texfmt == TextureFormat::RGBA8 && texUnit.texImage1[subTexmap].image_type))
{
- TexDecoder_DecodeTexel(sampledTex, imageSrc, imageS, imageT, imageWidth, ti0.format, tlut,
+ TexDecoder_DecodeTexel(sampledTex, imageSrc, imageS, imageT, imageWidth, texfmt, tlut,
tlutfmt);
SetTexel(sampledTex, texel, (128 - fractS) * (128 - fractT));
- TexDecoder_DecodeTexel(sampledTex, imageSrc, imageSPlus1, imageT, imageWidth, ti0.format,
- tlut, tlutfmt);
+ TexDecoder_DecodeTexel(sampledTex, imageSrc, imageSPlus1, imageT, imageWidth, texfmt, tlut,
+ tlutfmt);
AddTexel(sampledTex, texel, (fractS) * (128 - fractT));
- TexDecoder_DecodeTexel(sampledTex, imageSrc, imageS, imageTPlus1, imageWidth, ti0.format,
- tlut, tlutfmt);
+ TexDecoder_DecodeTexel(sampledTex, imageSrc, imageS, imageTPlus1, imageWidth, texfmt, tlut,
+ tlutfmt);
AddTexel(sampledTex, texel, (128 - fractS) * (fractT));
- TexDecoder_DecodeTexel(sampledTex, imageSrc, imageSPlus1, imageTPlus1, imageWidth, ti0.format,
+ TexDecoder_DecodeTexel(sampledTex, imageSrc, imageSPlus1, imageTPlus1, imageWidth, texfmt,
tlut, tlutfmt);
AddTexel(sampledTex, texel, (fractS) * (fractT));
}
@@ -238,9 +239,8 @@ void SampleMip(s32 s, s32 t, s32 mip, bool linear, u8 texmap, u8* sample)
WrapCoord(&imageS, tm0.wrap_s, imageWidth);
WrapCoord(&imageT, tm0.wrap_t, imageHeight);
- if (!(ti0.format == GX_TF_RGBA8 && texUnit.texImage1[subTexmap].image_type))
- TexDecoder_DecodeTexel(sample, imageSrc, imageS, imageT, imageWidth, ti0.format, tlut,
- tlutfmt);
+ if (!(texfmt == TextureFormat::RGBA8 && texUnit.texImage1[subTexmap].image_type))
+ TexDecoder_DecodeTexel(sample, imageSrc, imageS, imageT, imageWidth, texfmt, tlut, tlutfmt);
else
TexDecoder_DecodeTexelRGBA8FromTmem(sample, imageSrc, imageSrcOdd, imageS, imageT,
imageWidth);
diff --git a/Source/Core/VideoBackends/Vulkan/TextureCache.cpp b/Source/Core/VideoBackends/Vulkan/TextureCache.cpp
index 30817706b7..1d8221f646 100644
--- a/Source/Core/VideoBackends/Vulkan/TextureCache.cpp
+++ b/Source/Core/VideoBackends/Vulkan/TextureCache.cpp
@@ -95,8 +95,8 @@ bool TextureCache::Initialize()
return true;
}
-void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source, void* palette,
- TlutFormat format)
+void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source,
+ const void* palette, TLUTFormat format)
{
m_texture_converter->ConvertTexture(destination, source, m_render_pass, palette, format);
@@ -111,9 +111,9 @@ void TextureCache::ConvertTexture(TCacheEntry* destination, TCacheEntry* source,
VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL);
}
-void TextureCache::CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_width,
+void TextureCache::CopyEFB(u8* dst, const EFBCopyParams& params, u32 native_width,
u32 bytes_per_row, u32 num_blocks_y, u32 memory_stride,
- bool is_depth_copy, const EFBRectangle& src_rect, bool scale_by_half)
+ const EFBRectangle& src_rect, bool scale_by_half)
{
// Flush EFB pokes first, as they're expected to be included.
FramebufferManager::GetInstance()->FlushEFBPokes();
@@ -128,7 +128,7 @@ void TextureCache::CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_widt
region = Util::ClampRect2D(region, FramebufferManager::GetInstance()->GetEFBWidth(),
FramebufferManager::GetInstance()->GetEFBHeight());
Texture2D* src_texture;
- if (is_depth_copy)
+ if (params.depth)
src_texture = FramebufferManager::GetInstance()->ResolveEFBDepthTexture(region);
else
src_texture = FramebufferManager::GetInstance()->ResolveEFBColorTexture(region);
@@ -144,15 +144,15 @@ void TextureCache::CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_widt
src_texture->TransitionToLayout(g_command_buffer_mgr->GetCurrentCommandBuffer(),
VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL);
- m_texture_converter->EncodeTextureToMemory(src_texture->GetView(), dst, format, native_width,
- bytes_per_row, num_blocks_y, memory_stride,
- is_depth_copy, src_rect, scale_by_half);
+ m_texture_converter->EncodeTextureToMemory(src_texture->GetView(), dst, params, native_width,
+ bytes_per_row, num_blocks_y, memory_stride, src_rect,
+ scale_by_half);
// Transition back to original state
src_texture->TransitionToLayout(g_command_buffer_mgr->GetCurrentCommandBuffer(), original_layout);
}
-bool TextureCache::SupportsGPUTextureDecode(TextureFormat format, TlutFormat palette_format)
+bool TextureCache::SupportsGPUTextureDecode(TextureFormat format, TLUTFormat palette_format)
{
return m_texture_converter->SupportsTextureDecoding(format, palette_format);
}
@@ -160,7 +160,7 @@ bool TextureCache::SupportsGPUTextureDecode(TextureFormat format, TlutFormat pal
void TextureCache::DecodeTextureOnGPU(TCacheEntry* entry, u32 dst_level, const u8* data,
size_t data_size, TextureFormat format, u32 width, u32 height,
u32 aligned_width, u32 aligned_height, u32 row_stride,
- const u8* palette, TlutFormat palette_format)
+ const u8* palette, TLUTFormat palette_format)
{
// Group compute shader dispatches together in the init command buffer. That way we don't have to
// pay a penalty for switching from graphics->compute, or end/restart our render pass.
diff --git a/Source/Core/VideoBackends/Vulkan/TextureCache.h b/Source/Core/VideoBackends/Vulkan/TextureCache.h
index d17dd3d1e7..9bfa2da04e 100644
--- a/Source/Core/VideoBackends/Vulkan/TextureCache.h
+++ b/Source/Core/VideoBackends/Vulkan/TextureCache.h
@@ -33,19 +33,19 @@ public:
std::unique_ptr<AbstractTexture> CreateTexture(const TextureConfig& config) override;
- void ConvertTexture(TCacheEntry* destination, TCacheEntry* source, void* palette,
- TlutFormat format) override;
+ void ConvertTexture(TCacheEntry* destination, TCacheEntry* source, const void* palette,
+ TLUTFormat format) override;
- void CopyEFB(u8* dst, const EFBCopyFormat& format, u32 native_width, u32 bytes_per_row,
- u32 num_blocks_y, u32 memory_stride, bool is_depth_copy,
- const EFBRectangle& src_rect, bool scale_by_half) override;
+ void CopyEFB(u8* dst, const EFBCopyParams& params, u32 native_width, u32 bytes_per_row,
+ u32 num_blocks_y, u32 memory_stride, const EFBRectangle& src_rect,
+ bool scale_by_half) override;
- bool SupportsGPUTextureDecode(TextureFormat format, TlutFormat palette_format) override;
+ bool SupportsGPUTextureDecode(TextureFormat format, TLUTFormat palette_format) override;
void DecodeTextureOnGPU(TCacheEntry* entry, u32 dst_level, const u8* data, size_t data_size,
TextureFormat format, u32 width, u32 height, u32 aligned_width,
u32 aligned_height, u32 row_stride, const u8* palette,
- TlutFormat palette_format) override;
+ TLUTFormat palette_format) override;
VkShaderModule GetCopyShader() const;
VkRenderPass GetTextureCopyRenderPass() const;
diff --git a/Source/Core/VideoBackends/Vulkan/TextureConverter.cpp b/Source/Core/VideoBackends/Vulkan/TextureConverter.cpp
index ca045ec0ce..20be913b6a 100644
--- a/Source/Core/VideoBackends/Vulkan/TextureConverter.cpp
+++ b/Source/Core/VideoBackends/Vulkan/TextureConverter.cpp
@@ -166,7 +166,7 @@ TextureConverter::GetCommandBufferForTextureConversion(const TextureCache::TCach
void TextureConverter::ConvertTexture(TextureCacheBase::TCacheEntry* dst_entry,
TextureCacheBase::TCacheEntry* src_entry,
VkRenderPass render_pass, const void* palette,
- TlutFormat palette_format)
+ TLUTFormat palette_format)
{
struct PSUniformBlock
{
@@ -182,7 +182,7 @@ void TextureConverter::ConvertTexture(TextureCacheBase::TCacheEntry* dst_entry,
_assert_(destination_texture->GetConfig().rendertarget);
// We want to align to 2 bytes (R16) or the device's texel buffer alignment, whichever is greater.
- size_t palette_size = (src_entry->format & 0xF) == GX_TF_I4 ? 32 : 512;
+ size_t palette_size = src_entry->format == TextureFormat::I4 ? 32 : 512;
if (!ReserveTexelBufferStorage(palette_size, sizeof(u16)))
return;
@@ -201,13 +201,13 @@ void TextureConverter::ConvertTexture(TextureCacheBase::TCacheEntry* dst_entry,
UtilityShaderDraw draw(command_buffer,
g_object_cache->GetPipelineLayout(PIPELINE_LAYOUT_TEXTURE_CONVERSION),
render_pass, g_shader_cache->GetScreenQuadVertexShader(), VK_NULL_HANDLE,
- m_palette_conversion_shaders[palette_format]);
+ m_palette_conversion_shaders[static_cast<int>(palette_format)]);
VkRect2D region = {{0, 0}, {dst_entry->GetWidth(), dst_entry->GetHeight()}};
draw.BeginRenderPass(destination_texture->GetFramebuffer(), region);
PSUniformBlock uniforms = {};
- uniforms.multiplier = (src_entry->format & 0xF) == GX_TF_I4 ? 15.0f : 255.0f;
+ uniforms.multiplier = src_entry->format == TextureFormat::I4 ? 15.0f : 255.0f;
uniforms.texel_buffer_offset = static_cast<int>(palette_offset / sizeof(u16));
draw.SetPushConstants(&uniforms, sizeof(uniforms));
draw.SetPSSampler(0, source_texture->GetRawTexIdentifier()->GetView(),
@@ -219,16 +219,15 @@ void TextureConverter::ConvertTexture(TextureCacheBase::TCacheEntry* dst_entry,
}
void TextureConverter::EncodeTextureToMemory(VkImageView src_texture, u8* dest_ptr,
- const EFBCopyFormat& format, u32 native_width,
+ const EFBCopyParams& params, u32 native_width,
u32 bytes_per_row, u32 num_blocks_y, u32 memory_stride,
- bool is_depth_copy, const EFBRectangle& src_rect,
- bool scale_by_half)
+ const EFBRectangle& src_rect, bool scale_by_half)
{
- VkShaderModule shader = GetEncodingShader(format);
+ VkShaderModule shader = GetEncodingShader(params);
if (shader == VK_NULL_HANDLE)
{
- ERROR_LOG(VIDEO, "Missing encoding fragment shader for format %u->%u", format.efb_format,
- static_cast<u32>(format.copy_format));
+ ERROR_LOG(VIDEO, "Missing encoding fragment shader for format %u->%u",
+ static_cast<unsigned>(params.efb_format), static_cast<unsigned>(params.copy_format));
return;
}
@@ -251,7 +250,7 @@ void TextureConverter::EncodeTextureToMemory(VkImageView src_texture, u8* dest_p
// We also linear filtering for both box filtering and downsampling higher resolutions to 1x
// TODO: This only produces perfect downsampling for 1.5x and 2x IR, other resolution will
// need more complex down filtering to average all pixels and produce the correct result.
- bool linear_filter = (scale_by_half && !is_depth_copy) || g_ActiveConfig.iEFBScale != SCALE_1X;
+ bool linear_filter = (scale_by_half && !params.depth) || g_ActiveConfig.iEFBScale != SCALE_1X;
draw.SetPSSampler(0, src_texture, linear_filter ? g_object_cache->GetLinearSampler() :
g_object_cache->GetPointSampler());
@@ -387,7 +386,7 @@ void TextureConverter::DecodeYUYVTextureFromMemory(VKTexture* dst_texture, const
draw.EndRenderPass();
}
-bool TextureConverter::SupportsTextureDecoding(TextureFormat format, TlutFormat palette_format)
+bool TextureConverter::SupportsTextureDecoding(TextureFormat format, TLUTFormat palette_format)
{
auto key = std::make_pair(format, palette_format);
auto iter = m_decoding_pipelines.find(key);
@@ -424,7 +423,7 @@ void TextureConverter::DecodeTexture(VkCommandBuffer command_buffer,
TextureCache::TCacheEntry* entry, u32 dst_level,
const u8* data, size_t data_size, TextureFormat format,
u32 width, u32 height, u32 aligned_width, u32 aligned_height,
- u32 row_stride, const u8* palette, TlutFormat palette_format)
+ u32 row_stride, const u8* palette, TLUTFormat palette_format)
{
VKTexture* destination_texture = static_cast<VKTexture*>(entry->texture.get());
auto key = std::make_pair(format, palette_format);
@@ -667,21 +666,21 @@ bool TextureConverter::CompilePaletteConversionShaders()
std::string palette_rgb5a3_program = StringFromFormat(
"%s\n%s", "#define DECODE DecodePixel_RGB5A3", PALETTE_CONVERSION_FRAGMENT_SHADER_SOURCE);
- m_palette_conversion_shaders[GX_TL_IA8] =
+ m_palette_conversion_shaders[static_cast<int>(TLUTFormat::IA8)] =
Util::CompileAndCreateFragmentShader(palette_ia8_program);
- m_palette_conversion_shaders[GX_TL_RGB565] =
+ m_palette_conversion_shaders[static_cast<int>(TLUTFormat::RGB565)] =
Util::CompileAndCreateFragmentShader(palette_rgb565_program);
- m_palette_conversion_shaders[GX_TL_RGB5A3] =
+ m_palette_conversion_shaders[static_cast<int>(TLUTFormat::RGB5A3)] =
Util::CompileAndCreateFragmentShader(palette_rgb5a3_program);
- return m_palette_conversion_shaders[GX_TL_IA8] != VK_NULL_HANDLE &&
- m_palette_conversion_shaders[GX_TL_RGB565] != VK_NULL_HANDLE &&
- m_palette_conversion_shaders[GX_TL_RGB5A3] != VK_NULL_HANDLE;
+ return m_palette_conversion_shaders[static_cast<int>(TLUTFormat::IA8)] != VK_NULL_HANDLE &&
+ m_palette_conversion_shaders[static_cast<int>(TLUTFormat::RGB565)] != VK_NULL_HANDLE &&
+ m_palette_conversion_shaders[static_cast<int>(TLUTFormat::RGB5A3)] != VK_NULL_HANDLE;
}
-VkShaderModule TextureConverter::CompileEncodingShader(const EFBCopyFormat& format)
+VkShaderModule TextureConverter::CompileEncodingShader(const EFBCopyParams& params)
{
- const char* shader = TextureConversionShader::GenerateEncodingShader(format, APIType::Vulkan);
+ const char* shader = TextureConversionShader::GenerateEncodingShader(params, APIType::Vulkan);
VkShaderModule module = Util::CompileAndCreateFragmentShader(shader);
if (module == VK_NULL_HANDLE)
PanicAlert("Failed to compile texture encoding shader.");
@@ -689,14 +688,14 @@ VkShaderModule TextureConverter::CompileEncodingShader(const EFBCopyFormat& form
return module;
}
-VkShaderModule TextureConverter::GetEncodingShader(const EFBCopyFormat& format)
+VkShaderModule TextureConverter::GetEncodingShader(const EFBCopyParams& params)
{
- auto iter = m_encoding_shaders.find(format);
+ auto iter = m_encoding_shaders.find(params);
if (iter != m_encoding_shaders.end())
return iter->second;
- VkShaderModule shader = CompileEncodingShader(format);
- m_encoding_shaders.emplace(format, shader);
+ VkShaderModule shader = CompileEncodingShader(params);
+ m_encoding_shaders.emplace(params, shader);
return shader;
}
diff --git a/Source/Core/VideoBackends/Vulkan/TextureConverter.h b/Source/Core/VideoBackends/Vulkan/TextureConverter.h
index 3b9afee9ea..2465691901 100644
--- a/Source/Core/VideoBackends/Vulkan/TextureConverter.h
+++ b/Source/Core/VideoBackends/Vulkan/TextureConverter.h
@@ -33,14 +33,13 @@ public:
// Applies palette to dst_entry, using indices from src_entry.
void ConvertTexture(TextureCacheBase::TCacheEntry* dst_entry,
TextureCache::TCacheEntry* src_entry, VkRenderPass render_pass,
- const void* palette, TlutFormat palette_format);
+ const void* palette, TLUTFormat palette_format);
// Uses an encoding shader to copy src_texture to dest_ptr.
// NOTE: Executes the current command buffer.
- void EncodeTextureToMemory(VkImageView src_texture, u8* dest_ptr, const EFBCopyFormat& format,
+ void EncodeTextureToMemory(VkImageView src_texture, u8* dest_ptr, const EFBCopyParams& params,
u32 native_width, u32 bytes_per_row, u32 num_blocks_y,
- u32 memory_stride, bool is_depth_copy, const EFBRectangle& src_rect,
- bool scale_by_half);
+ u32 memory_stride, const EFBRectangle& src_rect, bool scale_by_half);
// Encodes texture to guest memory in XFB (YUYV) format.
void EncodeTextureToMemoryYUYV(void* dst_ptr, u32 dst_width, u32 dst_stride, u32 dst_height,
@@ -50,11 +49,11 @@ public:
void DecodeYUYVTextureFromMemory(VKTexture* dst_texture, const void* src_ptr, u32 src_width,
u32 src_stride, u32 src_height);
- bool SupportsTextureDecoding(TextureFormat format, TlutFormat palette_format);
+ bool SupportsTextureDecoding(TextureFormat format, TLUTFormat palette_format);
void DecodeTexture(VkCommandBuffer command_buffer, TextureCache::TCacheEntry* entry,
u32 dst_level, const u8* data, size_t data_size, TextureFormat format,
u32 width, u32 height, u32 aligned_width, u32 aligned_height, u32 row_stride,
- const u8* palette, TlutFormat palette_format);
+ const u8* palette, TLUTFormat palette_format);
private:
static const u32 ENCODING_TEXTURE_WIDTH = EFB_WIDTH * 4;
@@ -71,8 +70,8 @@ private:
bool CompilePaletteConversionShaders();
- VkShaderModule CompileEncodingShader(const EFBCopyFormat& format);
- VkShaderModule GetEncodingShader(const EFBCopyFormat& format);
+ VkShaderModule CompileEncodingShader(const EFBCopyParams& params);
+ VkShaderModule GetEncodingShader(const EFBCopyParams& params);
bool CreateEncodingRenderPass();
bool CreateEncodingTexture();
@@ -105,7 +104,7 @@ private:
std::array<VkShaderModule, NUM_PALETTE_CONVERSION_SHADERS> m_palette_conversion_shaders = {};
// Texture encoding - RGBA8->GX format in memory
- std::map<EFBCopyFormat, VkShaderModule> m_encoding_shaders;
+ std::map<EFBCopyParams, VkShaderModule> m_encoding_shaders;
VkRenderPass m_encoding_render_pass = VK_NULL_HANDLE;
std::unique_ptr<Texture2D> m_encoding_render_texture;
VkFramebuffer m_encoding_render_framebuffer = VK_NULL_HANDLE;
@@ -118,7 +117,7 @@ private:
VkShaderModule compute_shader;
bool valid;
};
- std::map<std::pair<TextureFormat, TlutFormat>, TextureDecodingPipeline> m_decoding_pipelines;
+ std::map<std::pair<TextureFormat, TLUTFormat>, TextureDecodingPipeline> m_decoding_pipelines;
std::unique_ptr<Texture2D> m_decoding_texture;
// XFB encoding/decoding shaders